logo

error-standalone

standalone <error.h> implementation intended for muslgit clone https://anongit.hacktivis.me/git/error-standalone.git/

error.c (1679B)


  1. // Copyright © 2024 Haelwenn (lanodan) Monnier <contact@hacktivis.me>
  2. // SPDX-License-Identifier: MIT
  3. #define _GNU_SOURCE // program_invocation_name
  4. #include <errno.h>
  5. #include <stdarg.h>
  6. #include <stdio.h>
  7. #include <stdlib.h>
  8. #include <string.h>
  9. #include "error.h"
  10. unsigned int error_message_count = 0;
  11. void (*error_print_progname)(void) = NULL;
  12. int error_one_per_line = 0;
  13. void
  14. error(int status, int errnum, const char *format, ...)
  15. {
  16. fflush(stdout);
  17. if(error_print_progname != NULL)
  18. {
  19. (*error_print_progname) ();
  20. }
  21. else
  22. {
  23. fprintf(stderr, "%s:", program_invocation_name);
  24. }
  25. va_list args;
  26. va_start(args, format);
  27. vfprintf(stderr, format, args);
  28. va_end(args);
  29. if(errnum != 0)
  30. fprintf(stderr, ": %s", strerror(errnum));
  31. putc('\n', stderr);
  32. error_message_count++;
  33. if(status != 0) exit(status);
  34. }
  35. void
  36. error_at_line(int status, int errnum, const char *filename, unsigned int linenum, const char *format, ...)
  37. {
  38. if(error_one_per_line != 0)
  39. {
  40. static const char *prev_filename;
  41. static unsigned int prev_linenum;
  42. if(prev_linenum == linenum &&
  43. (prev_filename == filename || strcmp(prev_filename, filename) == 0)
  44. ) return; // already printed, skip
  45. prev_filename = filename;
  46. prev_linenum = linenum;
  47. }
  48. fflush(stdout);
  49. if(error_print_progname != NULL)
  50. {
  51. (*error_print_progname) ();
  52. }
  53. else
  54. {
  55. fprintf(stderr, "%s:", program_invocation_name);
  56. }
  57. fprintf(stderr, " %s:%d: ", filename, linenum);
  58. va_list args;
  59. va_start(args, format);
  60. vfprintf(stderr, format, args);
  61. va_end(args);
  62. if(errnum != 0)
  63. fprintf(stderr, ": %s", strerror(errnum));
  64. putc('\n', stderr);
  65. error_message_count++;
  66. if(status != 0) exit(status);
  67. }