Fix variuus minor bugs reported by Andre Levy

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@20020 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Richard Frith-Macdonald 2004-09-07 14:27:14 +00:00
parent d82674f3d8
commit 5f8b76348f
5 changed files with 41 additions and 16 deletions

View file

@ -1,7 +1,10 @@
2004-09-07 Richard Frith-Macdonald <rfm@gnu.org>
* Source/NSSet.m:
* Source/NSSet.m: Fix possible stack overflows.
* Source/GSSet.m: ([allObjects]) Fix stack overflow for large sets.
* Source/NSTask.m: Fix error testing for task which has been lost.
* Source/NSArray.m: Fix possible stack overflows
Thanks to Andre Levey for reporting these.
2004-09-07 Richard Frith-Macdonald <rfm@gnu.org>

View file

@ -25,6 +25,29 @@
#include "GNUstepBase/GSObjCRuntime.h"
/**
* Macro to manage memory for chunks of code that need to work with
* arrays of items. Use this to start the block of code using
* the array and GS_ENDITEMBUF() to end it. The idea is to ensure that small
* arrays are allocated on the stack (for speed), but large arrays are
* allocated from the heap (to avoid stack overflow).
*/
#define GS_BEGINITEMBUF(P, S, T) { \
T _ibuf[(S) <= GS_MAX_OBJECTS_FROM_STACK ? (S) : 0]; \
T *_base = ((S) <= GS_MAX_OBJECTS_FROM_STACK) ? _ibuf \
: (T*)NSZoneMalloc(NSDefaultMallocZone(), (S) * sizeof(T)); \
T *(P) = _base;
/**
* Macro to manage memory for chunks of code that need to work with
* arrays of items. Use GS_BEGINITEMBUF() to start the block of code using
* the array and this macro to end it.
*/
#define GS_ENDITEMBUF() \
if (_base != _ibuf) \
NSZoneFree(NSDefaultMallocZone(), _base); \
}
/**
* Macro to manage memory for chunks of code that need to work with
* arrays of objects. Use this to start the block of code using
@ -32,21 +55,14 @@
* arrays are allocated on the stack (for speed), but large arrays are
* allocated from the heap (to avoid stack overflow).
*/
#define GS_BEGINIDBUF(P, S) { \
id _obuf[(S) <= GS_MAX_OBJECTS_FROM_STACK ? (S) : 0]; \
id *_base = ((S) <= GS_MAX_OBJECTS_FROM_STACK) ? _obuf \
: (id*)NSZoneMalloc(NSDefaultMallocZone(), (S) * sizeof(id)); \
id *(P) = _base;
#define GS_BEGINIDBUF(P, S) GS_BEGINITEMBUF(P, S, id)
/**
* Macro to manage memory for chunks of code that need to work with
* arrays of objects. Use GS_BEGINIDBUF() to start the block of code using
* the array and this macro to end it.
*/
#define GS_ENDIDBUF() \
if (_base != _obuf) \
NSZoneFree(NSDefaultMallocZone(), _base); \
}
#define GS_ENDIDBUF() GS_ENDITEMBUF()
/**
* Macro to consistently replace public accessable

View file

@ -1688,7 +1688,7 @@ compare(id elem1, id elem2, void* context)
{
if (count > 0)
{
unsigned sorted[count];
GS_BEGINITEMBUF(sorted, count, unsigned int);
unsigned to = 0;
unsigned from = 0;
unsigned i;
@ -1732,6 +1732,7 @@ compare(id elem1, id elem2, void* context)
(*rem)(self, remSel, sorted[to]);
}
}
GS_ENDITEMBUF();
}
}

View file

@ -253,7 +253,7 @@ static Class NSMutableSet_concrete_class;
[aCoder decodeValueOfObjCType: @encode(unsigned) at: &count];
if (count > 0)
{
id objs[count];
GS_BEGINIDBUF(objs, count);
unsigned i;
for (i = 0; i < count; i++)
@ -267,6 +267,7 @@ static Class NSMutableSet_concrete_class;
[objs[count] release];
}
#endif
GS_ENDIDBUF();
}
}
return self;
@ -370,10 +371,12 @@ static Class NSMutableSet_concrete_class;
}
else
{
id objs[count];
GS_BEGINIDBUF(objs, count);
[other getObjects: objs];
return [self initWithObjects: objs count: count];
self = [self initWithObjects: objs count: count];
GS_ENDIDBUF();
return self;
}
}
@ -384,8 +387,9 @@ static Class NSMutableSet_concrete_class;
- (id) initWithSet: (NSSet*)other copyItems: (BOOL)flag
{
unsigned c = [other count];
id os[c], o, e = [other objectEnumerator];
id o, e = [other objectEnumerator];
unsigned i = 0;
GS_BEGINIDBUF(os, c);
while ((o = [e nextObject]))
{
@ -401,6 +405,7 @@ static Class NSMutableSet_concrete_class;
while (i--)
[os[i] release];
#endif
GS_ENDIDBUF();
return self;
}

View file

@ -991,7 +991,7 @@ static DWORD WINAPI _threadFunction(LPVOID t)
[tasksLock lock];
task = (NSConcreteWindowsTask*)NSMapGet(activeTasks, (void*)taskId);
[tasksLock unlock];
if (t == nil)
if (task == nil)
{
return 0; // Task gone away.
}