Skip to content

Commit bd5637a

Browse files
committedMar 30, 2019
Fix memory leak in @synchronized.
This was actually a memory leak in the hidden class implementation, but it was mostly visible in the @synchronized implementation. Every hidden class registered a custom .cxx_destruct method, to handle cleanup of all of the hidden class structures. Unfortunately, this destructor failed to delete the reflection metadata structures associated with the class, specifically the objc_method_list containing the objc_method pointing to the destructor itself. Fixes gnustep#98
1 parent c5fbeb7 commit bd5637a

File tree

3 files changed

+14
-2
lines changed

3 files changed

+14
-2
lines changed
 

‎associate.m

+3
Original file line numberDiff line numberDiff line change
@@ -275,6 +275,9 @@ static void deallocHiddenClass(id obj, SEL _cmd)
275275
}
276276
}
277277
obj->isa = hiddenClass->super_class;
278+
// Free the introspection structures:
279+
freeMethodLists(hiddenClass);
280+
freeIvarLists(hiddenClass);
278281
// Free the class
279282
free(hiddenClass);
280283
}

‎class.h

+9
Original file line numberDiff line numberDiff line change
@@ -434,4 +434,13 @@ static inline BOOL classIsOrInherits(Class cls, Class base)
434434
return NO;
435435
}
436436

437+
/**
438+
* Free the instance variable lists associated with a class.
439+
*/
440+
void freeIvarLists(Class aClass);
441+
/**
442+
* Free the method lists associated with a class.
443+
*/
444+
void freeMethodLists(Class aClass);
445+
437446
#endif //__OBJC_CLASS_H_INCLUDED

‎runtime.c

+2-2
Original file line numberDiff line numberDiff line change
@@ -622,7 +622,7 @@ id objc_getRequiredClass(const char *name)
622622
return cls;
623623
}
624624

625-
static void freeMethodLists(Class aClass)
625+
PRIVATE void freeMethodLists(Class aClass)
626626
{
627627
struct objc_method_list *methods = aClass->methods;
628628
while(methods != NULL)
@@ -637,7 +637,7 @@ static void freeMethodLists(Class aClass)
637637
}
638638
}
639639

640-
static void freeIvarLists(Class aClass)
640+
PRIVATE void freeIvarLists(Class aClass)
641641
{
642642
struct objc_ivar_list *ivarlist = aClass->ivars;
643643
if (NULL == ivarlist) { return; }

0 commit comments

Comments
 (0)
Please sign in to comment.