I'm trying to use some of the data in a class's rodata to look at the class's objc mangled name, but it seems that the rodata structure I get is incorrect.
I'm doing the following to try and retrieve it:
struct ClassMetadata {
let metaclass: UnsafePointer<ClassMetaclass>
let superclass: Any.Type?
let reserved: (Int, Int)
let rodata: Int
}
struct ClassMetaclass {
let superclass0: Any.Type?
let superclass1: Any.Type?
let reserved: (Int, Int)
let metaclassData: UnsafeRawPointer
}
struct ROData {
let flags: UInt32
let instanceStart: UInt32
let instanceSize: UInt32
let reserved: UInt32
let ivarLayout: UnsafeRawPointer
let name: UnsafePointer<CChar>
let methodList: UnsafeRawPointer
let protocolList: UnsafeRawPointer
let ivarList: UnsafeRawPointer
let weakIvarLayout: UnsafeRawPointer
let propertyList: UnsafeRawPointer
}
func printObjCMangledName(for type: AnyObject.Type) {
let metadata = unsafeBitCast(
type,
to: UnsafePointer<ClassMetadata>.self
).pointee
// We're assuming a target who's using Swift in the OS.
let rodataAddress = metadata.rodata & ~0x2
let rodata = UnsafePointer<ROData>(
bitPattern: rodataAddress
)!.pointee
print(String(cString: rodata.name))
}
When I look at other fields of the metadata they're correct (the superclasses all register as SwiftObject
), but the rodata just doesn't seem correct because the name that get's printed is not what's being emitted (-emit-assembly
). Is the ObjC runtime altering some of these values? (I don't know much about ObjC, so I don't know if it changes any of the emitted data structures the Swift compiler emits.)