""" Python 2.7.11 garbage collector bug code snippet """ import ctypes import gc my_Library_Name = "clib_filename.so" MAX_LIST_COUNT = 50 # load the c-library cdll.LoadLibrary(my_Library_Name) # define c-structure: # (please don't comment on the c-structure this was done this # way a long time ago to support something else and had to be # done this way for that particular architecture - no need to # discuss why it has to be this way) class pyStruct_cstruct1_t(ctypes.Structure): _fields_ = [ ("red_cats", c_int16), ("blu_dogs", c_int16), ("red_x", (c_int16 * 2)), ("blu_x", (c_int16 * 2)), ("red_P", (c_int16 * 4)), ("blu_P", (c_int16 * 4)), ("avar", c_int16), ("ivar", c_int16), ("s1var", c_int), ("s2var", c_int8) ] class pyStruct_cstruct2_t(ctypes.Structure): _fields_ = [ ("list", (pyStruct_cstruct1_t \ * MAX_LIST_COUNT)), ("free", (POINTER(pyStruct_cstruct1_t) \ * MAX_LIST_COUNT)), ("used", (POINTER(pyStruct_cstruct1_t) \ * MAX_LIST_COUNT)), ("free_count", c_int8), ("used_count", c_int8) ] #### temporary workaround -- allows it to work consistently # gc.disable() cvar_mystruct2 = pyStruct_cstruct2_t() cvar_mystruct1 = pyStruct_cstruct1_t() cvar_mystruct1.red_cats = my_redcat cvar_mystruct1.blu_dogs = my_bludog cvar_myother_struct1 = pyStruct_cstruct1_t() for j in range(0, len(my_other_cats)): cvar_myother_struct1 = pyStruct_cstruct1_t() cvar_myother_struct1.red_cats = c_int16(my_other_cats[j]) cvar_myother_struct1.blu_dogs = c_int16(my_other_dogs[j]) cvar_mystruct2.used[j] = pointer(cvar_myother_struct1) cvar_retstatus = c_int32(-9999) cvar_someothervar = c_int32(0) # C-library function call (gets NULL pointer - causes segmentation fault) # seems the garbage collector is cleaning house because of the local scope # of the for loop on linux platform but not on mac platform. The behavior # across platforms is not consistent. (same python version on both platforms). cvar_retstatus = ctypes.myclib.mycfunction( \ byref(cvar_mystruct1), byref(cvar_mystruct2), cvar_someothervar ) # other code that works with the result from the c-function # not included here #### temporary workaround -- allows it to work consistently # gc.enable() ##EOF##