diff --git a/HandyJSON.xcodeproj/project.pbxproj b/HandyJSON.xcodeproj/project.pbxproj index 7913ee0..507a225 100644 --- a/HandyJSON.xcodeproj/project.pbxproj +++ b/HandyJSON.xcodeproj/project.pbxproj @@ -1323,7 +1323,7 @@ ENABLE_BITCODE = NO; INFOPLIST_FILE = "$(SRCROOT)/Source/Info-iOS.plist"; INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks"; - IPHONEOS_DEPLOYMENT_TARGET = 8.0; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; PRODUCT_BUNDLE_IDENTIFIER = com.aliyun.app.HandyJSON; PRODUCT_NAME = "$(PROJECT_NAME)"; @@ -1347,7 +1347,7 @@ ENABLE_BITCODE = NO; INFOPLIST_FILE = "$(SRCROOT)/Source/Info-iOS.plist"; INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks"; - IPHONEOS_DEPLOYMENT_TARGET = 8.0; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; PRODUCT_BUNDLE_IDENTIFIER = com.aliyun.app.HandyJSON; PRODUCT_NAME = "$(PROJECT_NAME)"; @@ -1366,7 +1366,7 @@ DEVELOPMENT_TEAM = QBMN2BBW3K; ENABLE_BITCODE = NO; INFOPLIST_FILE = HandyJSONDemo/Info.plist; - IPHONEOS_DEPLOYMENT_TARGET = 8.0; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; PRODUCT_BUNDLE_IDENTIFIER = com.aliyun.app.HandyJSONDemo; PRODUCT_NAME = "$(TARGET_NAME)"; @@ -1386,7 +1386,7 @@ DEVELOPMENT_TEAM = QBMN2BBW3K; ENABLE_BITCODE = NO; INFOPLIST_FILE = HandyJSONDemo/Info.plist; - IPHONEOS_DEPLOYMENT_TARGET = 8.0; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; PRODUCT_BUNDLE_IDENTIFIER = com.aliyun.app.HandyJSONDemo; PRODUCT_NAME = "$(TARGET_NAME)"; @@ -1402,7 +1402,7 @@ BUNDLE_LOADER = "$(TEST_HOST)"; DEVELOPMENT_TEAM = ""; INFOPLIST_FILE = "Tests/HandyJSONTests/Info-iOS.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 8.0; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; PRODUCT_BUNDLE_IDENTIFIER = com.aliyun.app.HandyJSONTests; PRODUCT_NAME = "$(TARGET_NAME)"; @@ -1417,7 +1417,7 @@ BUNDLE_LOADER = "$(TEST_HOST)"; DEVELOPMENT_TEAM = ""; INFOPLIST_FILE = "Tests/HandyJSONTests/Info-iOS.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 8.0; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; PRODUCT_BUNDLE_IDENTIFIER = com.aliyun.app.HandyJSONTests; PRODUCT_NAME = "$(TARGET_NAME)"; diff --git a/Source/Metadata.swift b/Source/Metadata.swift index 35d78b3..55d1a61 100755 --- a/Source/Metadata.swift +++ b/Source/Metadata.swift @@ -186,7 +186,20 @@ extension Metadata { } func _propertyDescriptionsAndStartPoint() -> ([Property.Description], Int32?)? { - let instanceStart = pointer.pointee.class_rw_t()?.pointee.class_ro_t()?.pointee.instanceStart + // swift/include/swift/Remote/MetadataReader.h + guard let flags = pointer.pointee.flags() else { + return nil + } + let RO_REALIZED: UInt32 = 0x80000000 + let isRealized = (flags & RO_REALIZED) != 0 + var ro: UnsafePointer<_class_ro_t>? + if isRealized { + ro = pointer.pointee.class_rw_t()?.pointee.class_ro_t() + } else { + ro = pointer.pointee.class_ro_t() + } + + let instanceStart = ro?.pointee.instanceStart var result: [Property.Description] = [] if let fieldOffsets = self.fieldOffsets, let fieldRecords = self.reflectionFieldDescriptor?.fieldRecords { class NameAndType { @@ -256,6 +269,27 @@ extension _Metadata { return UnsafePointer<_class_rw_t>(bitPattern: self.rodataPointer & 0xfffffffc) } } + + /// Read the flags, which is a 32-bit header on both formats. + func flags() -> UInt32? { + if MemoryLayout.size == MemoryLayout.size { + let fast_data_mask: UInt64 = 0x00007ffffffffff8 + let databits_t: UInt64 = UInt64(self.rodataPointer) + return UnsafePointer(bitPattern: UInt(databits_t & fast_data_mask))?.pointee + } else { + return UnsafePointer(bitPattern: self.rodataPointer & 0xfffffffc)?.pointee + } + } + + func class_ro_t() -> UnsafePointer<_class_ro_t>? { + if MemoryLayout.size == MemoryLayout.size { + let fast_data_mask: UInt64 = 0x00007ffffffffff8 + let databits_t: UInt64 = UInt64(self.rodataPointer) + return UnsafePointer<_class_ro_t>(bitPattern: UInt(databits_t & fast_data_mask)) + } else { + return UnsafePointer<_class_ro_t>(bitPattern: self.rodataPointer & 0xfffffffc) + } + } } } @@ -290,11 +324,14 @@ extension Metadata { var name: String? var type: Any.Type? } - for i in 0.. Any.Type?] = [ + "function": { _getTypeByMangledNameInContext(cMangledTypeName, getMangledTypeNameSize(cMangledTypeName), genericContext: self.contextDescriptorPointer, genericArguments: self.genericArgumentVector) } + ] + if let function = functionMap["function"],let fieldType = function() { result.append(Property.Description(key: name, type: fieldType, offset: fieldOffsets[i])) } }