My code is crashing (rarely) while accessing classes retrieved by objc_getClassList
Crash message:
objc[48740]: Attempt to use unknown class 0x600000ac2640.
var numClasses: Int32 = 0
var newNumClasses = objc_getClassList(nil, 0)
var classes: UnsafeMutablePointer<AnyClass>?
while (numClasses < newNumClasses) { // calling objc_getClassList until all returned classes are fitting into the buffer
numClasses = newNumClasses
if let classes = classes {
classes.deallocate()
}
classes = UnsafeMutablePointer<AnyClass>.allocate(capacity: Int(numClasses))
let buffer = AutoreleasingUnsafeMutablePointer<AnyClass>(classes)
newNumClasses = objc_getClassList(buffer, numClasses);
}
for i in 0..<Int(newNumClasses) {
let someclass: AnyClass = classes![i]
let s = "\(someclass)" // crash happens here
// not very costly computations here
}
Mostly it happens when iteration is performed for 80% or so. Total number of classes is around 50000. It reproduces more often on slower devices/simulators. No other signs of heap corruption are present. Memory graph is fine.
Classes around the broken one looks somewhat like this: fir_420DF5A9-4BF1-468C-8919-FFAA7D864314_GDTCCTUploadOperation (this is a name of the class. Looks firebasy).
EDIT: Alternatively
var count: UInt32 = 0
guard let classList = objc_copyClassList(&count) else {
return []
}
return UnsafeBufferPointer(start: classList, count: Int(count)).filter { (type: AnyClass) in
return class_conformsToProtocol(type, protocolName)
}
Produces the same result (again, very rarely)
Please let me know if anyone has an idea how to filter out dead/inaccessible classes.
Thank you.