mirror of
https://github.com/gnustep/libs-base.git
synced 2025-05-29 16:01:38 +00:00
Apply patch to switch completely to using pthreads
git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@29367 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
parent
3110312b36
commit
b662140e16
8 changed files with 174 additions and 197 deletions
|
@ -40,6 +40,7 @@
|
|||
|
||||
#include "GNUstepBase/GCObject.h"
|
||||
#include "GNUstepBase/GSCategories.h"
|
||||
#include <pthread.h>
|
||||
|
||||
/*
|
||||
* The head of a linked list of all garbage collecting objects is a
|
||||
|
@ -70,18 +71,25 @@ static BOOL isCollecting = NO;
|
|||
|
||||
#ifdef NeXT_RUNTIME
|
||||
static void *allocationLock = NULL;
|
||||
#define objc_mutex_allocate() NULL
|
||||
#define objc_mutex_lock(lock)
|
||||
#define objc_mutex_unlock(lock)
|
||||
#define pthread_mutex_lock(lock)
|
||||
#define pthread_mutex_unlock(lock)
|
||||
#else
|
||||
static objc_mutex_t allocationLock = NULL;
|
||||
static pthread_mutex_t *allocationLock = NULL;
|
||||
#endif
|
||||
|
||||
+ (void) _becomeMultiThreaded: (NSNotification *)aNotification
|
||||
{
|
||||
if (allocationLock == 0)
|
||||
if (allocationLock == NULL)
|
||||
{
|
||||
allocationLock = objc_mutex_allocate();
|
||||
# ifndef NeXT_RUNTIME
|
||||
allocationLock = malloc(sizeof(pthread_mutex_t));
|
||||
if (allocationLock == NULL)
|
||||
{
|
||||
abort();
|
||||
}
|
||||
|
||||
pthread_mutex_init(allocationLock, NULL);
|
||||
# endif
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -95,7 +103,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
o->gc.next = allObjects;
|
||||
o->gc.previous = allObjects->gc.previous;
|
||||
|
@ -104,7 +112,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
o->gc.flags.refCount = 1;
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
|
||||
return o;
|
||||
|
@ -145,13 +153,13 @@ static objc_mutex_t allocationLock = NULL;
|
|||
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
if (isCollecting == YES)
|
||||
{
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
return; // Don't allow recursion.
|
||||
}
|
||||
|
@ -211,7 +219,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
isCollecting = NO;
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -261,7 +269,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
// p = anObject->gc.previous;
|
||||
// n = anObject->gc.next;
|
||||
|
@ -273,7 +281,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
[n gcSetPreviousObject: p];
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -288,7 +296,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
o->gc.next = allObjects;
|
||||
o->gc.previous = allObjects->gc.previous;
|
||||
|
@ -297,7 +305,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
o->gc.flags.refCount = 1;
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
return o;
|
||||
}
|
||||
|
@ -315,7 +323,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
// p = anObject->gc.previous;
|
||||
// n = anObject->gc.next;
|
||||
|
@ -327,7 +335,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
[n gcSetPreviousObject: p];
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
[super dealloc];
|
||||
}
|
||||
|
@ -410,7 +418,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
{
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
if (gc.flags.refCount > 0 && gc.flags.refCount-- == 1)
|
||||
{
|
||||
|
@ -419,7 +427,7 @@ static objc_mutex_t allocationLock = NULL;
|
|||
}
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -430,12 +438,12 @@ static objc_mutex_t allocationLock = NULL;
|
|||
{
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_lock(allocationLock);
|
||||
pthread_mutex_lock(allocationLock);
|
||||
}
|
||||
gc.flags.refCount++;
|
||||
if (allocationLock != 0)
|
||||
{
|
||||
objc_mutex_unlock(allocationLock);
|
||||
pthread_mutex_unlock(allocationLock);
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
|
|
@ -58,6 +58,10 @@
|
|||
|
||||
#include <string.h>
|
||||
|
||||
#ifndef NeXT_RUNTIME
|
||||
#include <pthread.h>
|
||||
#endif
|
||||
|
||||
#ifdef NeXT_Foundation_LIBRARY
|
||||
@interface NSObject (MissingFromMacOSX)
|
||||
+ (IMP) methodForSelector: (SEL)aSelector;
|
||||
|
@ -67,59 +71,6 @@
|
|||
#define BDBGPrintf(format, args...) \
|
||||
do { if (behavior_debug) { fprintf(stderr, (format) , ## args); } } while (0)
|
||||
|
||||
static objc_mutex_t local_lock = NULL;
|
||||
|
||||
/* This class it intended soley for thread safe / +load safe
|
||||
initialization of the local lock.
|
||||
It's a root class so it won't trigger the initialization
|
||||
of any other class. */
|
||||
@interface _GSObjCRuntimeInitializer /* Root Class */
|
||||
{
|
||||
Class isa;
|
||||
}
|
||||
+ (Class)class;
|
||||
@end
|
||||
@implementation _GSObjCRuntimeInitializer
|
||||
+ (void)initialize
|
||||
{
|
||||
if (local_lock == NULL)
|
||||
{
|
||||
local_lock = objc_mutex_allocate();
|
||||
}
|
||||
}
|
||||
+ (Class)class
|
||||
{
|
||||
return self;
|
||||
}
|
||||
@end
|
||||
|
||||
void
|
||||
GSAllocateMutexAt(objc_mutex_t *request)
|
||||
{
|
||||
if (request == NULL)
|
||||
{
|
||||
/* This could be called very early in process
|
||||
initialization so many things may not have
|
||||
been setup correctly yet. */
|
||||
fprintf(stderr,
|
||||
"Error: GSAllocateMutexAt() called with NULL pointer.\n");
|
||||
abort();
|
||||
}
|
||||
|
||||
if (local_lock == NULL)
|
||||
{
|
||||
/* Initialize in a thread safe way. */
|
||||
[_GSObjCRuntimeInitializer class];
|
||||
}
|
||||
|
||||
objc_mutex_lock(local_lock);
|
||||
if (*request == NULL)
|
||||
{
|
||||
*request = objc_mutex_allocate();
|
||||
}
|
||||
objc_mutex_unlock(local_lock);
|
||||
}
|
||||
|
||||
/**
|
||||
* This function is used to locate information about the instance
|
||||
* variable of obj called name. It returns YES if the variable
|
||||
|
@ -310,15 +261,10 @@ GSClassList(Class *buffer, unsigned int max, BOOL clearCache)
|
|||
#else
|
||||
static Class *cache = 0;
|
||||
static unsigned cacheClassCount = 0;
|
||||
static volatile objc_mutex_t cache_lock = NULL;
|
||||
static pthread_mutex_t cache_lock = PTHREAD_MUTEX_INITIALIZER;
|
||||
unsigned int num;
|
||||
|
||||
if (cache_lock == NULL)
|
||||
{
|
||||
GSAllocateMutexAt((void*)&cache_lock);
|
||||
}
|
||||
|
||||
objc_mutex_lock(cache_lock);
|
||||
pthread_mutex_lock(&cache_lock);
|
||||
|
||||
if (clearCache)
|
||||
{
|
||||
|
@ -369,7 +315,7 @@ GSClassList(Class *buffer, unsigned int max, BOOL clearCache)
|
|||
num = (max > cacheClassCount) ? 0 : (cacheClassCount - max);
|
||||
}
|
||||
|
||||
objc_mutex_unlock(cache_lock);
|
||||
pthread_mutex_unlock(&cache_lock);
|
||||
|
||||
#endif
|
||||
|
||||
|
@ -1267,26 +1213,22 @@ gs_find_protocol_named(const char *name)
|
|||
|
||||
static GSIMapTable_t protocol_by_name;
|
||||
static BOOL protocol_by_name_init = NO;
|
||||
static volatile objc_mutex_t protocol_by_name_lock = NULL;
|
||||
static pthread_mutex_t protocol_by_name_lock = PTHREAD_MUTEX_INITIALIZER;
|
||||
|
||||
/* Not sure about the semantics of inlining
|
||||
functions with static variables. */
|
||||
static void
|
||||
gs_init_protocol_lock(void)
|
||||
{
|
||||
if (protocol_by_name_lock == NULL)
|
||||
{
|
||||
GSAllocateMutexAt((void *)&protocol_by_name_lock);
|
||||
objc_mutex_lock(protocol_by_name_lock);
|
||||
if (protocol_by_name_init == NO)
|
||||
{
|
||||
pthread_mutex_lock(&protocol_by_name_lock);
|
||||
if (protocol_by_name_init == NO)
|
||||
{
|
||||
GSIMapInitWithZoneAndCapacity (&protocol_by_name,
|
||||
NSDefaultMallocZone(),
|
||||
128);
|
||||
protocol_by_name_init = YES;
|
||||
}
|
||||
objc_mutex_unlock(protocol_by_name_lock);
|
||||
}
|
||||
pthread_mutex_unlock(&protocol_by_name_lock);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1303,7 +1245,7 @@ GSRegisterProtocol(Protocol *proto)
|
|||
pcl p;
|
||||
|
||||
p = (pcl)proto;
|
||||
objc_mutex_lock(protocol_by_name_lock);
|
||||
pthread_mutex_lock(&protocol_by_name_lock);
|
||||
node = GSIMapNodeForKey(&protocol_by_name,
|
||||
(GSIMapKey) p->protocol_name);
|
||||
if (node == 0)
|
||||
|
@ -1312,7 +1254,7 @@ GSRegisterProtocol(Protocol *proto)
|
|||
(GSIMapKey) (void *) p->protocol_name,
|
||||
(GSIMapVal) (void *) p);
|
||||
}
|
||||
objc_mutex_unlock(protocol_by_name_lock);
|
||||
pthread_mutex_unlock(&protocol_by_name_lock);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1334,7 +1276,7 @@ GSProtocolFromName(const char *name)
|
|||
}
|
||||
else
|
||||
{
|
||||
objc_mutex_lock(protocol_by_name_lock);
|
||||
pthread_mutex_lock(&protocol_by_name_lock);
|
||||
node = GSIMapNodeForKey(&protocol_by_name, (GSIMapKey) name);
|
||||
|
||||
if (node)
|
||||
|
@ -1353,7 +1295,7 @@ GSProtocolFromName(const char *name)
|
|||
(GSIMapVal) (void *) p);
|
||||
}
|
||||
}
|
||||
objc_mutex_unlock(protocol_by_name_lock);
|
||||
pthread_mutex_unlock(&protocol_by_name_lock);
|
||||
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue