[PATCH 6/6] Use global atexit data for all configurations

Sebastian Huber <[email protected]>
Newsgroups gmane.comp.lib.newlib
Message-ID <[email protected]>
For the exit processing only members of _GLOBAL_REENT were used by default.  If
the _REENT_GLOBAL_ATEXIT option was enabled, then the data structures were
provided to dedicated global objects.  Make this option the default.  Remove
the option.  Provide the struct _reent _atexit and atexit members only if
backward binary compatibility is requested (_REENT_BACKWARD_BINARY_COMPAT).
---
 libgloss/arc/crt0.S                 | 11 ++++----
 libgloss/epiphany/crt0.S            | 26 ++++++++-----------
 libgloss/sparc_leon/locore_atexit.c |  4 +--
 newlib/README                       |  6 -----
 newlib/configure                    |  9 +------
 newlib/configure.ac                 | 10 +++-----
 newlib/libc/include/sys/config.h    |  1 -
 newlib/libc/include/sys/reent.h     | 39 +++++++++++------------------
 newlib/libc/reent/reent.c           | 19 --------------
 newlib/libc/stdlib/__atexit.c       | 15 ++++-------
 newlib/libc/stdlib/__call_atexit.c  |  8 +++---
 newlib/newlib.hin                   |  3 ---
 12 files changed, 46 insertions(+), 105 deletions(-)

diff --git a/libgloss/arc/crt0.S b/libgloss/arc/crt0.S
index 46c9efd71..8d9adaa52 100644
--- a/libgloss/arc/crt0.S
+++ b/libgloss/arc/crt0.S
@@ -187,12 +187,13 @@ __start:
 	; calling atexit drags in malloc, so instead poke the function
 	; address directly into the reent structure
 	ld	r1, [gp, @_impure_ptr@sda]
-	mov_s	r0, @_fini
-	add	r1, r1, 0x14c		; &_GLOBAL_REENT->atexit0
-	st	r1, [r1, -4]		; _GLOBAL_REENT->atexit
-	st_s	r0, [r1, 8]		; _GLOBAL_REENT->atexit0._fns[0]
+	mov_s	r1, @__atexit0
+	mov_s	r2, @__atexit
+	st_s	r1, [r2, 0]		; __atexit = &__atexit0
 	mov_s	r0, 1
-	st_s	r0, [r1, 4]		; _GLOBAL_REENT->atexit0._ind
+	st_s	r0, [r1, 4]		; __atexit0._ind = 1
+	mov_s	r0, @_fini
+	st_s	r0, [r1, 8]		; __atexit0._fns[0] = _fini
 ; branch to _init
 #if defined (__ARCEM__) || defined (__ARCHS__)
 	jl	@_init
diff --git a/libgloss/epiphany/crt0.S b/libgloss/epiphany/crt0.S
index d684e1e10..b0d9ecbab 100644
--- a/libgloss/epiphany/crt0.S
+++ b/libgloss/epiphany/crt0.S
@@ -113,23 +113,19 @@ _external_start:
 #else
 	; calling atexit drags in malloc, so instead poke the function
 	; address directly into the reent structure
-	mov	r2,%low(__impure_ptr)
-	movt	r2,%high(__impure_ptr)
-	ldr	r2,[r2]
-	mov	r1,%low(fini)
-	movt	r1,%high(fini)
+	mov	r1,%low(__atexit0)
+	movt	r1,%high(__atexit0)
+	mov	r2,%low(__atexit)
+	movt	r2,%high(__atexit)
 #ifdef __STRUCT_ALIGN_64__
-#error
-	add	r2,r2,need_to_find_out; &_GLOBAL_REENT->atexit0
-	str	r2, [r2,-1];??or -2?; _GLOBAL_REENT->atexit
-	mov	r0, 1
-	str	r0, [r2,1]	; _GLOBAL_REENT->atexit0._ind
-	str	r1, [r2,2]	; _GLOBAL_REENT->atexit0._fns[0]
+#error "not implemented"
 #else  /* !__STRUCT_ALIGN_64__ */
-	add	r0,r2,0x14c	; &_GLOBAL_REENT->atexit0
-	str	r0, [r0,-1]	; _GLOBAL_REENT->atexit
-	mov	r0, 1
-	strd	r0, [r2,0x2a]	; _GLOBAL_REENT->atexit0._ind
+	str	r1, [r2, 0]	; __atexit = &__atexit0
+	movr	r0, 1
+	str	r0, [r1, 4]	; __atexit0._ind = 1
+	mov	r0,%low(fini)
+	movt	r0,%high(fini)
+	str	r0, [r1, 8]	; __atexit0._fns[0] = fini
 #endif /* !__STRUCT_ALIGN_64__ */
 #endif /* !0 */
 	;; Call global and static constructors
diff --git a/libgloss/sparc_leon/locore_atexit.c b/libgloss/sparc_leon/locore_atexit.c
index b23054c77..e3e6df12f 100644
--- a/libgloss/sparc_leon/locore_atexit.c
+++ b/libgloss/sparc_leon/locore_atexit.c
@@ -37,9 +37,9 @@ atexit (void (*fn) (void))
 {
   register struct _atexit *p;
 
-  p = _GLOBAL_REENT->_atexit;
+  p = __atexit;
   if (p == NULL)
-    _GLOBAL_REENT->_atexit = p = &_GLOBAL_REENT->_atexit0;
+    __atexit = p = &__atexit0;
   if (p->_ind >= _ATEXIT_SIZE)
     {
       return -1;
diff --git a/newlib/README b/newlib/README
index c99ab47c6..68747c588 100644
--- a/newlib/README
+++ b/newlib/README
@@ -294,12 +294,6 @@ One feature can be enabled by specifying `--enable-FEATURE=yes' or
      Disable dynamic allocation of atexit entries.
      Most hosts and targets have it enabled in configure.host.
 
-`--enable-newlib-global-atexit'
-     Enable atexit data structure as global variable.  By doing so it is
-     move out of _reent structure, and can be garbage collected if atexit
-     is not referenced.
-     Disabled by default.
-
 `--enable-newlib-global-stdio-streams'
      Enable to move the stdio stream FILE objects out of struct _reent and make
      them global.  The stdio stream pointers of struct _reent are initialized
diff --git a/newlib/configure b/newlib/configure
index 4ff02360b..0114e2913 100755
--- a/newlib/configure
+++ b/newlib/configure
@@ -2373,12 +2373,11 @@ if test "${enable_newlib_global_atexit+set}" = set; then :
   enableval=$enable_newlib_global_atexit; if test "${newlib_global_atexit+set}" != set; then
   case "${enableval}" in
     yes) newlib_global_atexit=yes ;;
-    no)  newlib_global_atexit=no  ;;
     *)   as_fn_error $? "bad value ${enableval} for newlib-global-atexit option" "$LINENO" 5 ;;
   esac
  fi
 else
-  newlib_global_atexit=no
+  newlib_global_atexit=yes
 fi
 
 # Check whether --enable-newlib-reent-small was given.
@@ -6484,12 +6483,6 @@ $as_echo "#define _ATEXIT_DYNAMIC_ALLOC 1" >>confdefs.h
 
 fi
 
-if test "${newlib_global_atexit}" = "yes"; then
-
-$as_echo "#define _REENT_GLOBAL_ATEXIT 1" >>confdefs.h
-
-fi
-
 if test "${newlib_fvwrite_in_streamio}" = "yes"; then
 
 $as_echo "#define _FVWRITE_IN_STREAMIO 1" >>confdefs.h
diff --git a/newlib/configure.ac b/newlib/configure.ac
index 7c7297564..5be09fcd4 100644
--- a/newlib/configure.ac
+++ b/newlib/configure.ac
@@ -142,16 +142,16 @@ AC_ARG_ENABLE(newlib-atexit-dynamic-alloc,
 
 dnl Support --enable-newlib-global-atexit
 dnl Enable atexit data structure as global variables to save memory usage in
-dnl _reent.
+dnl _reent.  This is no longer optional.  It is enabled in all Newlib
+dnl configurations.
 AC_ARG_ENABLE(newlib-global-atexit,
 [  --enable-newlib-global-atexit	enable atexit data structure as global],
 [if test "${newlib_global_atexit+set}" != set; then
   case "${enableval}" in
     yes) newlib_global_atexit=yes ;;
-    no)  newlib_global_atexit=no  ;;
     *)   AC_MSG_ERROR(bad value ${enableval} for newlib-global-atexit option) ;;
   esac
- fi], [newlib_global_atexit=no])dnl
+ fi], [newlib_global_atexit=yes])dnl
 
 dnl Support --enable-newlib-reent-small
 AC_ARG_ENABLE(newlib-reent-small,
@@ -470,10 +470,6 @@ if test "${newlib_atexit_dynamic_alloc}" = "yes"; then
   AC_DEFINE(_ATEXIT_DYNAMIC_ALLOC, 1, [If atexit() may dynamically allocate space for cleanup functions.])
 fi
 
-if test "${newlib_global_atexit}" = "yes"; then
-  AC_DEFINE(_REENT_GLOBAL_ATEXIT, 1, [Define if declare atexit data as global.])
-fi
-
 if test "${newlib_fvwrite_in_streamio}" = "yes"; then
   AC_DEFINE(_FVWRITE_IN_STREAMIO, 1, [Define if ivo supported in streamio.])
 fi
diff --git a/newlib/libc/include/sys/config.h b/newlib/libc/include/sys/config.h
index b4d755957..c40bb51c2 100644
--- a/newlib/libc/include/sys/config.h
+++ b/newlib/libc/include/sys/config.h
@@ -242,7 +242,6 @@
 #define __FILENAME_MAX__ 255
 #define _READ_WRITE_RETURN_TYPE _ssize_t
 #define __DYNAMIC_REENT__
-#define _REENT_GLOBAL_ATEXIT
 #define _REENT_GLOBAL_STDIO_STREAMS
 #endif
 
diff --git a/newlib/libc/include/sys/reent.h b/newlib/libc/include/sys/reent.h
index 4683ecc2f..ab6188958 100644
--- a/newlib/libc/include/sys/reent.h
+++ b/newlib/libc/include/sys/reent.h
@@ -105,13 +105,6 @@ struct _atexit {
 # define _ATEXIT_INIT {_NULL, 0, {_NULL}, {{_NULL}, {_NULL}, 0, 0}}
 #endif
 
-#ifdef _REENT_GLOBAL_ATEXIT
-# define _REENT_INIT_ATEXIT
-#else
-# define _REENT_INIT_ATEXIT \
-  _NULL, _ATEXIT_INIT,
-#endif
-
 /*
  * Stdio buffers.
  *
@@ -343,10 +336,12 @@ struct _rand48 {
 #define _REENT_SIGNAL_SIZE 24
 
 #ifdef _REENT_BACKWARD_BINARY_COMPAT
+#define _REENT_INIT_UNUSED_ATEXIT _NULL, _ATEXIT_INIT,
 #define _REENT_INIT_UNUSED_LOCALE_INFO 0,
 #define _REENT_INIT_UNUSED_RAND 0,
 #define _REENT_INIT_UNUSED_SDIDINIT 0,
 #else
+#define _REENT_INIT_UNUSED_ATEXIT /* Nothing to initialize */
 #define _REENT_INIT_UNUSED_LOCALE_INFO /* Nothing to initialize */
 #define _REENT_INIT_UNUSED_RAND /* Nothing to initialize */
 #define _REENT_INIT_UNUSED_SDIDINIT /* Nothing to initialize */
@@ -431,11 +426,11 @@ struct _reent
   /* signal info */
   void (**(_sig_func))(int);
 
-# ifndef _REENT_GLOBAL_ATEXIT
+#ifdef _REENT_BACKWARD_BINARY_COMPAT
   /* atexit stuff */
-  struct _atexit *_atexit;
-  struct _atexit _atexit0;
-# endif
+  struct _atexit *_unused_atexit;
+  struct _atexit _unused_atexit0;
+#endif
 
   struct _glue __sglue;			/* root of glue chain */
   __FILE *__sf;			        /* file descriptors */
@@ -464,7 +459,7 @@ struct _reent
     _NULL, \
     _NULL, \
     _NULL, \
-    _REENT_INIT_ATEXIT \
+    _REENT_INIT_UNUSED_ATEXIT \
     {_NULL, 0, _NULL}, \
     _NULL, \
     _NULL, \
@@ -502,7 +497,7 @@ extern const struct __sFILE_fake __sf_fake_stderr;
     _NULL, \
     _NULL, \
     _NULL, \
-    _REENT_INIT_ATEXIT \
+    _REENT_INIT_UNUSED_ATEXIT \
     {_NULL, 0, _NULL}, \
     _NULL, \
     _NULL, \
@@ -704,11 +699,11 @@ struct _reent
 #endif
     } _new;
 
-# ifndef _REENT_GLOBAL_ATEXIT
+#ifdef _REENT_BACKWARD_BINARY_COMPAT
   /* atexit stuff */
-  struct _atexit *_atexit;	/* points to head of LIFO stack */
-  struct _atexit _atexit0;	/* one guaranteed table, required by ANSI */
-# endif
+  struct _atexit *_unused_atexit;
+  struct _atexit _unused_atexit0;
+#endif
 
   /* signal info */
   void (**_sig_func)(int);
@@ -777,7 +772,7 @@ struct _reent
         {0, {0}} \
       } \
     }, \
-    _REENT_INIT_ATEXIT \
+    _REENT_INIT_UNUSED_ATEXIT \
     _NULL \
     _REENT_INIT_SGLUE(&(var)) \
   }
@@ -879,12 +874,8 @@ extern int _fwalk_sglue (struct _reent *, int (*)(struct _reent *, __FILE *),
 
 #define _GLOBAL_REENT (&_impure_data)
 
-#ifdef _REENT_GLOBAL_ATEXIT
-extern struct _atexit *_global_atexit; /* points to head of LIFO stack */
-# define _GLOBAL_ATEXIT _global_atexit
-#else
-# define _GLOBAL_ATEXIT (_GLOBAL_REENT->_atexit)
-#endif
+extern struct _atexit *__atexit; /* points to head of LIFO stack */
+extern struct _atexit __atexit0; /* one guaranteed table, required by ANSI */
 
 #ifdef __cplusplus
 }
diff --git a/newlib/libc/reent/reent.c b/newlib/libc/reent/reent.c
index 70f1c5f45..04942ce4d 100644
--- a/newlib/libc/reent/reent.c
+++ b/newlib/libc/reent/reent.c
@@ -93,25 +93,6 @@ _reclaim_reent (struct _reent *ptr)
 	_free_r (ptr, ptr->_misc);
 #endif
 
-#ifndef _REENT_GLOBAL_ATEXIT
-      /* atexit stuff */
-# ifdef _REENT_SMALL
-      if (ptr->_atexit && ptr->_atexit->_on_exit_args_ptr)
-	_free_r (ptr, ptr->_atexit->_on_exit_args_ptr);
-# else
-      if ((ptr->_atexit) && (ptr->_atexit != &ptr->_atexit0))
-	{
-	  struct _atexit *p, *q;
-	  for (p = ptr->_atexit; p != &ptr->_atexit0;)
-	    {
-	      q = p;
-	      p = p->_next;
-	      _free_r (ptr, q);
-	    }
-	}
-# endif
-#endif
-
       if (ptr->_cvtbuf)
 	_free_r (ptr, ptr->_cvtbuf);
     /* We should free _sig_func to avoid a memory leak, but how to
diff --git a/newlib/libc/stdlib/__atexit.c b/newlib/libc/stdlib/__atexit.c
index 97ce053bf..04bdf194e 100644
--- a/newlib/libc/stdlib/__atexit.c
+++ b/newlib/libc/stdlib/__atexit.c
@@ -53,12 +53,7 @@ const void * __atexit_dummy = &__call_exitprocs;
 extern _LOCK_RECURSIVE_T __atexit_recursive_mutex;
 #endif
 
-#ifdef _REENT_GLOBAL_ATEXIT
-static struct _atexit _global_atexit0 = _ATEXIT_INIT;
-# define _GLOBAL_ATEXIT0 (&_global_atexit0)
-#else
-# define _GLOBAL_ATEXIT0 (&_GLOBAL_REENT->_atexit0)
-#endif
+struct _atexit __atexit0 = _ATEXIT_INIT;
 
 /*
  * Register a function to be performed at exit or on shared library unload.
@@ -77,10 +72,10 @@ __register_exitproc (int type,
   __lock_acquire_recursive(__atexit_recursive_mutex);
 #endif
 
-  p = _GLOBAL_ATEXIT;
+  p = __atexit;
   if (p == NULL)
     {
-      _GLOBAL_ATEXIT = p = _GLOBAL_ATEXIT0;
+      __atexit = p = &__atexit0;
 #ifdef _REENT_SMALL
       extern struct _on_exit_args * const __on_exit_args _ATTRIBUTE ((weak));
       if (&__on_exit_args != NULL)
@@ -104,8 +99,8 @@ __register_exitproc (int type,
 	  return -1;
 	}
       p->_ind = 0;
-      p->_next = _GLOBAL_ATEXIT;
-      _GLOBAL_ATEXIT = p;
+      p->_next = __atexit;
+      __atexit = p;
 #ifndef _REENT_SMALL
       p->_on_exit_args._fntypes = 0;
       p->_on_exit_args._is_cxa = 0;
diff --git a/newlib/libc/stdlib/__call_atexit.c b/newlib/libc/stdlib/__call_atexit.c
index c29a03c8e..710440389 100644
--- a/newlib/libc/stdlib/__call_atexit.c
+++ b/newlib/libc/stdlib/__call_atexit.c
@@ -17,9 +17,7 @@ void free(void *) _ATTRIBUTE((__weak__));
 __LOCK_INIT_RECURSIVE(, __atexit_recursive_mutex);
 #endif
 
-#ifdef _REENT_GLOBAL_ATEXIT
-struct _atexit *_global_atexit = _NULL;
-#endif
+struct _atexit *__atexit = _NULL;
 
 #ifdef _WANT_REGISTER_FINI
 
@@ -83,8 +81,8 @@ __call_exitprocs (int code, void *d)
 
  restart:
 
-  p = _GLOBAL_ATEXIT;
-  lastp = &_GLOBAL_ATEXIT;
+  p = __atexit;
+  lastp = &__atexit;
   while (p)
     {
 #ifdef _REENT_SMALL
diff --git a/newlib/newlib.hin b/newlib/newlib.hin
index 4a9614970..718e5d970 100644
--- a/newlib/newlib.hin
+++ b/newlib/newlib.hin
@@ -378,9 +378,6 @@
 /* Verify _REENT_CHECK macros allocate memory successfully. */
 #undef _REENT_CHECK_VERIFY
 
-/* Define if declare atexit data as global. */
-#undef _REENT_GLOBAL_ATEXIT
-
 /* Define if using retargetable functions for default lock routines. */
 #undef _RETARGETABLE_LOCKING
 
-- 
2.35.3
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.