comparison src/gmalloc.c @ 78437:77430fdfce38

(_malloc_thread_enabled_p) [USE_PTHREAD]: New variable. [USE_PTHREAD] (LOCK, UNLOCK, LOCK_ALIGNED_BLOCKS) (UNLOCK_ALIGNED_BLOCKS): Conditionalize with it. (malloc_atfork_handler_prepare, malloc_atfork_handler_parent) (malloc_atfork_handler_child, malloc_enable_thread) [USE_PTHREAD]: New functions.
author YAMAMOTO Mitsuharu <mituharu@math.s.chiba-u.ac.jp>
date Tue, 07 Aug 2007 08:57:24 +0000
parents 2c30fdff6890
children c4c2bb082d62
comparison
equal deleted inserted replaced
78436:34b7a05ac98e 78437:77430fdfce38
134 /* Allocate SIZE bytes on a page boundary. */ 134 /* Allocate SIZE bytes on a page boundary. */
135 #if ! (defined (_MALLOC_INTERNAL) && defined (GMALLOC_INHIBIT_VALLOC)) 135 #if ! (defined (_MALLOC_INTERNAL) && defined (GMALLOC_INHIBIT_VALLOC))
136 extern __ptr_t valloc PP ((__malloc_size_t __size)); 136 extern __ptr_t valloc PP ((__malloc_size_t __size));
137 #endif 137 #endif
138 138
139 #ifdef USE_PTHREAD
140 /* Set up mutexes and make malloc etc. thread-safe. */
141 extern void malloc_enable_thread PP ((void));
142 #endif
139 143
140 #ifdef _MALLOC_INTERNAL 144 #ifdef _MALLOC_INTERNAL
141 145
142 /* The allocator divides the heap into blocks of fixed size; large 146 /* The allocator divides the heap into blocks of fixed size; large
143 requests receive one or more whole blocks, and small requests 147 requests receive one or more whole blocks, and small requests
240 extern __ptr_t _realloc_internal_nolock PP ((__ptr_t __ptr, __malloc_size_t __size)); 244 extern __ptr_t _realloc_internal_nolock PP ((__ptr_t __ptr, __malloc_size_t __size));
241 extern void _free_internal_nolock PP ((__ptr_t __ptr)); 245 extern void _free_internal_nolock PP ((__ptr_t __ptr));
242 246
243 #ifdef USE_PTHREAD 247 #ifdef USE_PTHREAD
244 extern pthread_mutex_t _malloc_mutex, _aligned_blocks_mutex; 248 extern pthread_mutex_t _malloc_mutex, _aligned_blocks_mutex;
245 #define LOCK() pthread_mutex_lock (&_malloc_mutex) 249 extern int _malloc_thread_enabled_p;
246 #define UNLOCK() pthread_mutex_unlock (&_malloc_mutex) 250 #define LOCK() \
247 #define LOCK_ALIGNED_BLOCKS() pthread_mutex_lock (&_aligned_blocks_mutex) 251 do { \
248 #define UNLOCK_ALIGNED_BLOCKS() pthread_mutex_unlock (&_aligned_blocks_mutex) 252 if (_malloc_thread_enabled_p) \
253 pthread_mutex_lock (&_malloc_mutex); \
254 } while (0)
255 #define UNLOCK() \
256 do { \
257 if (_malloc_thread_enabled_p) \
258 pthread_mutex_unlock (&_malloc_mutex); \
259 } while (0)
260 #define LOCK_ALIGNED_BLOCKS() \
261 do { \
262 if (_malloc_thread_enabled_p) \
263 pthread_mutex_lock (&_aligned_blocks_mutex); \
264 } while (0)
265 #define UNLOCK_ALIGNED_BLOCKS() \
266 do { \
267 if (_malloc_thread_enabled_p) \
268 pthread_mutex_unlock (&_aligned_blocks_mutex); \
269 } while (0)
249 #else 270 #else
250 #define LOCK() 271 #define LOCK()
251 #define UNLOCK() 272 #define UNLOCK()
252 #define LOCK_ALIGNED_BLOCKS() 273 #define LOCK_ALIGNED_BLOCKS()
253 #define UNLOCK_ALIGNED_BLOCKS() 274 #define UNLOCK_ALIGNED_BLOCKS()
562 583
563 #ifdef USE_PTHREAD 584 #ifdef USE_PTHREAD
564 static pthread_once_t malloc_init_once_control = PTHREAD_ONCE_INIT; 585 static pthread_once_t malloc_init_once_control = PTHREAD_ONCE_INIT;
565 pthread_mutex_t _malloc_mutex = PTHREAD_MUTEX_INITIALIZER; 586 pthread_mutex_t _malloc_mutex = PTHREAD_MUTEX_INITIALIZER;
566 pthread_mutex_t _aligned_blocks_mutex = PTHREAD_MUTEX_INITIALIZER; 587 pthread_mutex_t _aligned_blocks_mutex = PTHREAD_MUTEX_INITIALIZER;
588 int _malloc_thread_enabled_p;
589
590 static void
591 malloc_atfork_handler_prepare ()
592 {
593 LOCK ();
594 LOCK_ALIGNED_BLOCKS ();
595 }
596
597 static void
598 malloc_atfork_handler_parent ()
599 {
600 UNLOCK_ALIGNED_BLOCKS ();
601 UNLOCK ();
602 }
603
604 static void
605 malloc_atfork_handler_child ()
606 {
607 UNLOCK_ALIGNED_BLOCKS ();
608 UNLOCK ();
609 }
610
611 /* Set up mutexes and make malloc etc. thread-safe. */
612 void
613 malloc_enable_thread ()
614 {
615 if (_malloc_thread_enabled_p)
616 return;
617
618 /* Some pthread implementations call malloc for statically
619 initialized mutexes when they are used first. To avoid such a
620 situation, we initialize mutexes here while their use is
621 disabled in malloc etc. */
622 pthread_mutex_init (&_malloc_mutex, NULL);
623 pthread_mutex_init (&_aligned_blocks_mutex, NULL);
624 pthread_atfork (malloc_atfork_handler_prepare,
625 malloc_atfork_handler_parent,
626 malloc_atfork_handler_child);
627 _malloc_thread_enabled_p = 1;
628 }
567 #endif 629 #endif
568 630
569 static void 631 static void
570 malloc_initialize_1 () 632 malloc_initialize_1 ()
571 { 633 {
573 mcheck (NULL); 635 mcheck (NULL);
574 #endif 636 #endif
575 637
576 if (__malloc_initialize_hook) 638 if (__malloc_initialize_hook)
577 (*__malloc_initialize_hook) (); 639 (*__malloc_initialize_hook) ();
578
579 /* We don't use recursive mutex because pthread_mutexattr_init may
580 call malloc internally. */
581 #if 0 /* defined (USE_PTHREAD) */
582 {
583 pthread_mutexattr_t attr;
584
585 pthread_mutexattr_init (&attr);
586 pthread_mutexattr_settype (&attr, PTHREAD_MUTEX_RECURSIVE);
587 pthread_mutex_init (&_malloc_mutex, &attr);
588 pthread_mutexattr_destroy (&attr);
589 }
590 #endif
591 640
592 heapsize = HEAP / BLOCKSIZE; 641 heapsize = HEAP / BLOCKSIZE;
593 _heapinfo = (malloc_info *) align (heapsize * sizeof (malloc_info)); 642 _heapinfo = (malloc_info *) align (heapsize * sizeof (malloc_info));
594 if (_heapinfo == NULL) 643 if (_heapinfo == NULL)
595 return; 644 return;