atexit.c 2.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117
  1. /* Copyright (C) 1995,1996 Robert de Bath <rdebath@cix.compulink.co.uk>
  2. * This file is part of the Linux-8086 C library and is distributed
  3. * under the GNU Library General Public License.
  4. */
  5. /*
  6. * This deals with both the atexit and on_exit function calls
  7. *
  8. * Note calls installed with atexit are called with the same args as on_exit
  9. * fuctions; the void* is given the NULL value.
  10. *
  11. */
  12. #include <errno.h>
  13. /* ATEXIT.H */
  14. #define MAXONEXIT 20 /* AIUI Posix requires 10 */
  15. typedef void (*vfuncp) ();
  16. extern vfuncp __cleanup;
  17. extern void __do_exit();
  18. extern struct exit_table
  19. {
  20. vfuncp called;
  21. void *argument;
  22. }
  23. __on_exit_table[MAXONEXIT];
  24. extern int __on_exit_count;
  25. /* End ATEXIT.H */
  26. #ifdef L_atexit
  27. vfuncp __cleanup;
  28. int
  29. atexit(ptr)
  30. vfuncp ptr;
  31. {
  32. if( __on_exit_count < 0 || __on_exit_count >= MAXONEXIT)
  33. {
  34. errno = ENOMEM;
  35. return -1;
  36. }
  37. __cleanup = __do_exit;
  38. if( ptr )
  39. {
  40. __on_exit_table[__on_exit_count].called = ptr;
  41. __on_exit_table[__on_exit_count].argument = 0;
  42. __on_exit_count++;
  43. }
  44. return 0;
  45. }
  46. #endif
  47. #ifdef L_on_exit
  48. int
  49. on_exit(ptr, arg)
  50. vfuncp ptr;
  51. void *arg;
  52. {
  53. if( __on_exit_count < 0 || __on_exit_count >= MAXONEXIT)
  54. {
  55. errno = ENOMEM;
  56. return -1;
  57. }
  58. __cleanup = __do_exit;
  59. if( ptr )
  60. {
  61. __on_exit_table[__on_exit_count].called = ptr;
  62. __on_exit_table[__on_exit_count].argument = arg;
  63. __on_exit_count++;
  64. }
  65. return 0;
  66. }
  67. #endif
  68. #ifdef L___do_exit
  69. int __on_exit_count = 0;
  70. struct exit_table __on_exit_table[MAXONEXIT];
  71. void
  72. __do_exit(rv)
  73. int rv;
  74. {
  75. register int count = __on_exit_count-1;
  76. register vfuncp ptr;
  77. __on_exit_count = -1; /* ensure no more will be added */
  78. __cleanup = 0; /* Calling exit won't re-do this */
  79. /* In reverse order */
  80. for (; count >= 0; count--)
  81. {
  82. ptr = __on_exit_table[count].called;
  83. (*ptr) (rv, __on_exit_table[count].argument);
  84. }
  85. }
  86. #endif
  87. #ifdef L_exit
  88. void
  89. exit(rv)
  90. int rv;
  91. {
  92. if (__cleanup)
  93. __cleanup();
  94. _exit(rv);
  95. }
  96. #endif