xcframework_converter 0.3.1 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 2df06815d507bcbbd8d8ea83882fe3c55463dcc9532063d4566f8d196e378ada
4
- data.tar.gz: f49c4301fb89b90b1e30e77cbee37e175ea1d432a1c104f62131d689857d0a58
3
+ metadata.gz: 8ed138cd025eb265a64d714f9342520dd10ca44c9d78120a20eb6695623f1e86
4
+ data.tar.gz: 870d95ae53553761641a9572a6e08f58103435f4312035749794353c2d34979c
5
5
  SHA512:
6
- metadata.gz: bdcc77aeb67f7eb84dbb8c469186e27a730616f9fa2c51a9e6a7e9ca91f800b4563858c18fd3c93a91298b911241aad577f9e0ba8086ba198f19932368868701
7
- data.tar.gz: ea641b22490269b45530b719ca48435092055ed5515b8cce8fe7b9ddc866567a418bdb16d6b463b3482319c664cabd49253f963864a16bfa705fa5dd6ab4faf6
6
+ metadata.gz: f5f9e9d85f7385b2a1f7406b5942741c7060c9263e751a9e59bdeb13c234e117c0ba1f58a3f3f2c0f509d797b76c9b51afbb12131fde7bdfefe9940a29e4ac4d
7
+ data.tar.gz: a2201235913e84433ee593288511da552b23cdf9e0e09ca0efdcc525f82ebd2e884d9d134b71f7323ed07a7b1ea88d70d49406492c51e2834afa3af02c1071e9
@@ -0,0 +1,28 @@
1
+ // swift-tools-version:5.3
2
+ import PackageDescription
3
+
4
+ let package = Package(
5
+ name: "arm64-to-sim",
6
+ platforms: [
7
+ .macOS(.v11)
8
+ ],
9
+ products: [
10
+ .executable(name: "arm64-to-sim", targets: ["arm64-to-sim"])
11
+ ],
12
+ dependencies: [
13
+ ],
14
+ targets: [
15
+ .target(
16
+ name: "arm64-to-sim",
17
+ dependencies: [ "Arm64ToSimLib" ]),
18
+ .target(
19
+ name: "Arm64ToSimLib",
20
+ dependencies: []),
21
+ .testTarget(
22
+ name: "Tests",
23
+ dependencies: ["Arm64ToSimLib"],
24
+ resources: [
25
+ .copy("TestResources"),
26
+ ])
27
+ ]
28
+ )
@@ -7,12 +7,12 @@ extension Data {
7
7
  let lc: load_command = withUnsafeBytes { $0.load(as: load_command.self) }
8
8
  return lc.cmd
9
9
  }
10
-
10
+
11
11
  var commandSize: Int {
12
12
  let lc: load_command = withUnsafeBytes { $0.load(as: load_command.self) }
13
13
  return Int(lc.cmdsize)
14
14
  }
15
-
15
+
16
16
  func asStruct<T>(fromByteOffset offset: Int = 0) -> T {
17
17
  return withUnsafeBytes { $0.load(fromByteOffset: offset, as: T.self) }
18
18
  }
@@ -35,63 +35,75 @@ extension FileHandle {
35
35
  }
36
36
  }
37
37
 
38
- enum Transmogrifier {
39
- private static func readBinary(atPath path: String) -> (Data, [Data], Data) {
38
+ public enum Transmogrifier {
39
+ private static func readBinary(atPath path: String, isDynamic: Bool = false) -> (Data, [Data], Data) {
40
40
  guard let handle = FileHandle(forReadingAtPath: path) else {
41
41
  fatalError("Cannot open a handle for the file at \(path). Aborting.")
42
42
  }
43
-
43
+
44
44
  // chop up the file into a relevant number of segments
45
45
  let headerData = try! handle.read(upToCount: MemoryLayout<mach_header_64>.stride)!
46
-
46
+
47
47
  let header: mach_header_64 = headerData.asStruct()
48
48
  if header.magic != MH_MAGIC_64 || header.cputype != CPU_TYPE_ARM64 {
49
49
  fatalError("The file is not a correct arm64 binary. Try thinning (via lipo) or unarchiving (via ar) first.")
50
50
  }
51
-
51
+
52
52
  let loadCommandsData: [Data] = (0..<header.ncmds).map { _ in
53
53
  let loadCommandPeekData = try! handle.peek(upToCount: MemoryLayout<load_command>.stride)
54
54
  return try! handle.read(upToCount: Int(loadCommandPeekData!.commandSize))!
55
55
  }
56
-
56
+
57
+ if isDynamic {
58
+ let bytesToDiscard = abs(MemoryLayout<build_version_command>.stride - MemoryLayout<version_min_command>.stride)
59
+ _ = handle.readData(ofLength: bytesToDiscard)
60
+ }
61
+
57
62
  let programData = try! handle.readToEnd()!
58
-
63
+
59
64
  try! handle.close()
60
-
65
+
61
66
  return (headerData, loadCommandsData, programData)
62
67
  }
63
-
68
+
64
69
  private static func updateSegment64(_ data: Data, _ offset: UInt32) -> Data {
65
70
  // decode both the segment_command_64 and the subsequent section_64s
66
71
  var segment: segment_command_64 = data.asStruct()
67
-
72
+
68
73
  let sections: [section_64] = (0..<Int(segment.nsects)).map { index in
69
74
  let offset = MemoryLayout<segment_command_64>.stride + index * MemoryLayout<section_64>.stride
70
75
  return data.asStruct(fromByteOffset: offset)
71
76
  }
72
-
77
+
73
78
  // shift segment information by the offset
74
79
  segment.fileoff += UInt64(offset)
75
80
  segment.filesize += UInt64(offset)
76
81
  segment.vmsize += UInt64(offset)
77
-
82
+
78
83
  let offsetSections = sections.map { section -> section_64 in
84
+ let sectionType = section.flags & UInt32(SECTION_TYPE)
85
+ switch Int32(sectionType) {
86
+ case S_ZEROFILL, S_GB_ZEROFILL, S_THREAD_LOCAL_ZEROFILL:
87
+ return section
88
+ case _: break
89
+ }
90
+
79
91
  var section = section
80
92
  section.offset += UInt32(offset)
81
93
  section.reloff += section.reloff > 0 ? UInt32(offset) : 0
82
94
  return section
83
95
  }
84
-
96
+
85
97
  var datas = [Data]()
86
98
  datas.append(Data(bytes: &segment, count: MemoryLayout<segment_command_64>.stride))
87
99
  datas.append(contentsOf: offsetSections.map { section in
88
100
  var section = section
89
101
  return Data(bytes: &section, count: MemoryLayout<section_64>.stride)
90
102
  })
91
-
103
+
92
104
  return datas.merge()
93
105
  }
94
-
106
+
95
107
  private static func updateVersionMin(_ data: Data, _ offset: UInt32, minos: UInt32, sdk: UInt32) -> Data {
96
108
  var command = build_version_command(cmd: UInt32(LC_BUILD_VERSION),
97
109
  cmdsize: UInt32(MemoryLayout<build_version_command>.stride),
@@ -99,68 +111,124 @@ enum Transmogrifier {
99
111
  minos: minos << 16 | 0 << 8 | 0,
100
112
  sdk: sdk << 16 | 0 << 8 | 0,
101
113
  ntools: 0)
102
-
114
+
103
115
  return Data(bytes: &command, count: MemoryLayout<build_version_command>.stride)
104
116
  }
105
-
117
+
106
118
  private static func updateDataInCode(_ data: Data, _ offset: UInt32) -> Data {
107
119
  var command: linkedit_data_command = data.asStruct()
108
120
  command.dataoff += offset
109
121
  return Data(bytes: &command, count: data.commandSize)
110
122
  }
111
-
123
+
112
124
  private static func updateSymTab(_ data: Data, _ offset: UInt32) -> Data {
113
125
  var command: symtab_command = data.asStruct()
114
126
  command.stroff += offset
115
127
  command.symoff += offset
116
128
  return Data(bytes: &command, count: data.commandSize)
117
129
  }
118
-
119
- static func processBinary(atPath path: String, minos: UInt32 = 13, sdk: UInt32 = 13) {
120
- guard CommandLine.arguments.count > 1 else {
121
- fatalError("Please add a path to command!")
122
- }
123
- let (headerData, loadCommandsData, programData) = readBinary(atPath: path)
124
-
125
- // `offset` is kind of a magic number here, since we know that's the only meaningful change to binary size
126
- // having a dynamic `offset` requires two passes over the load commands and is left as an exercise to the reader
127
- let offset = UInt32(abs(MemoryLayout<build_version_command>.stride - MemoryLayout<version_min_command>.stride))
128
-
130
+
131
+ private static func computeLoadCommandsEditor(_ loadCommandsData: [Data], isDynamic: Bool) -> ((Data, UInt32, UInt32) -> Data) {
132
+
133
+ if isDynamic {
134
+ return updateDylibFile
135
+ }
136
+
137
+ var contains_LC_VERSION_MIN_IPHONEOS = false
138
+ var contains_LC_BUILD_VERSION = false
139
+ for lc in loadCommandsData {
140
+ let loadCommand = UInt32(lc.loadCommand)
141
+ if loadCommand == LC_VERSION_MIN_IPHONEOS {
142
+ contains_LC_VERSION_MIN_IPHONEOS = true
143
+ } else if loadCommand == LC_BUILD_VERSION {
144
+ contains_LC_BUILD_VERSION = true
145
+ }
146
+ }
147
+
148
+ if contains_LC_VERSION_MIN_IPHONEOS == contains_LC_BUILD_VERSION {
149
+ if contains_LC_BUILD_VERSION == true {
150
+ fatalError("Bad Mach-O Object file: Both LC_VERSION_MIN_IPHONEOS and LC_BUILD_VERSION are present.\nEither one of them should be present")
151
+ } else {
152
+ fatalError("Bad Mach-O Object file: does not contain LC_VERSION_MIN_IPHONEOS or LC_BUILD_VERSION.\nEither one of them should be present")
153
+ }
154
+ }
155
+
156
+ if contains_LC_VERSION_MIN_IPHONEOS {
157
+ // `offset` is kind of a magic number here, since we know that's the only meaningful change to binary size
158
+ // having a dynamic `offset` requires two passes over the load commands and is left as an exercise to the reader
159
+ return updatePreiOS12ObjectFile
160
+ } else {
161
+ return updatePostiOS12ObjectFile
162
+ }
163
+ }
164
+
165
+
166
+ static func updatePostiOS12ObjectFile(lc: Data, minos: UInt32, sdk: UInt32) -> Data {
167
+ let cmd = Int32(bitPattern: lc.loadCommand)
168
+ switch cmd {
169
+ case LC_BUILD_VERSION:
170
+ return updateVersionMin(lc, 0, minos: minos, sdk: sdk)
171
+ default:
172
+ return lc
173
+ }
174
+ }
175
+
176
+ static func updatePreiOS12ObjectFile(lc: Data, minos: UInt32, sdk: UInt32) -> Data {
177
+ // `offset` is kind of a magic number here, since we know that's the only meaningful change to binary size
178
+ // having a dynamic `offset` requires two passes over the load commands and is left as an exercise to the reader
179
+ let offset = UInt32(abs(MemoryLayout<build_version_command>.stride - MemoryLayout<version_min_command>.stride))
180
+ let cmd = Int32(bitPattern: lc.loadCommand)
181
+ switch cmd {
182
+ case LC_SEGMENT_64:
183
+ return updateSegment64(lc, offset)
184
+ case LC_VERSION_MIN_IPHONEOS:
185
+ return updateVersionMin(lc, offset, minos: minos, sdk: sdk)
186
+ case LC_DATA_IN_CODE, LC_LINKER_OPTIMIZATION_HINT:
187
+ return updateDataInCode(lc, offset)
188
+ case LC_SYMTAB:
189
+ return updateSymTab(lc, offset)
190
+ case LC_BUILD_VERSION:
191
+ return updateVersionMin(lc, offset, minos: minos, sdk: sdk)
192
+ default:
193
+ return lc
194
+ }
195
+ }
196
+
197
+ static func updateDylibFile(lc: Data, minos: UInt32, sdk: UInt32) -> Data {
198
+ // `offset` is kind of a magic number here, since we know that's the only meaningful change to binary size
199
+ // having a dynamic `offset` requires two passes over the load commands and is left as an exercise to the reader
200
+ let offset = UInt32(abs(MemoryLayout<build_version_command>.stride - MemoryLayout<version_min_command>.stride))
201
+ let cmd = Int32(bitPattern: lc.loadCommand)
202
+ guard cmd != LC_BUILD_VERSION else {
203
+ fatalError("This arm64 binary already contains an LC_BUILD_VERSION load command!")
204
+ }
205
+ if cmd == LC_VERSION_MIN_IPHONEOS {
206
+ return updateVersionMin(lc, offset, minos: minos, sdk: sdk)
207
+ }
208
+ return lc
209
+ }
210
+
211
+
212
+ public static func processBinary(atPath path: String, minos: UInt32 = 13, sdk: UInt32 = 13, isDynamic: Bool = false) {
213
+ let (headerData, loadCommandsData, programData) = readBinary(atPath: path, isDynamic: isDynamic)
214
+
215
+ let editor = computeLoadCommandsEditor(loadCommandsData, isDynamic: isDynamic)
216
+
129
217
  let editedCommandsData = loadCommandsData
130
- .map { (lc) -> Data in
131
- switch Int32(lc.loadCommand) {
132
- case LC_SEGMENT_64:
133
- return updateSegment64(lc, offset)
134
- case LC_VERSION_MIN_IPHONEOS:
135
- return updateVersionMin(lc, offset, minos: minos, sdk: sdk)
136
- case LC_DATA_IN_CODE, LC_LINKER_OPTIMIZATION_HINT:
137
- return updateDataInCode(lc, offset)
138
- case LC_SYMTAB:
139
- return updateSymTab(lc, offset)
140
- case LC_BUILD_VERSION:
141
- fatalError("This arm64 binary already contains an LC_BUILD_VERSION load command!")
142
- default:
143
- return lc
144
- }
145
- }
146
- .merge()
147
-
218
+ .map { return editor($0, minos, sdk) }
219
+ .merge()
220
+
148
221
  var header: mach_header_64 = headerData.asStruct()
149
222
  header.sizeofcmds = UInt32(editedCommandsData.count)
150
-
223
+
151
224
  // reassemble the binary
152
225
  let reworkedData = [
153
226
  Data(bytes: &header, count: MemoryLayout<mach_header_64>.stride),
154
227
  editedCommandsData,
155
228
  programData
156
229
  ].merge()
157
-
230
+
158
231
  // save back to disk
159
232
  try! reworkedData.write(to: URL(fileURLWithPath: path))
160
233
  }
161
234
  }
162
-
163
- let binaryPath = CommandLine.arguments[1]
164
- let minos = UInt32(CommandLine.arguments[2]) ?? 13
165
- let sdk = UInt32(CommandLine.arguments[3]) ?? 13
166
- Transmogrifier.processBinary(atPath: binaryPath, minos: minos, sdk: sdk)
@@ -0,0 +1,73 @@
1
+ import Foundation
2
+ import XCTest
3
+ import Arm64ToSimLib
4
+
5
+ class Arm64ToSimTestCase: XCTestCase {
6
+
7
+
8
+ var tempDir: URL!
9
+ override func setUp() {
10
+ self.tempDir = FileManager.default.temporaryDirectory.appendingPathComponent(UUID.init().uuidString)
11
+ try! FileManager.default.createDirectory(at: self.tempDir, withIntermediateDirectories: false, attributes: nil)
12
+ copyFixtures()
13
+ }
14
+
15
+ override func tearDown() {
16
+ try! FileManager.default.removeItem(at: self.tempDir)
17
+ }
18
+
19
+ private func copyFixtures() {
20
+ let testResourcesPath = Bundle.module.resourcePath!.appending("/TestResources")
21
+ if let files = try? FileManager.default.contentsOfDirectory(atPath: testResourcesPath){
22
+ for file in files {
23
+ var isDir : ObjCBool = false
24
+ let fileURL = URL(fileURLWithPath: testResourcesPath).appendingPathComponent(file)
25
+ if FileManager.default.fileExists(atPath: fileURL.path, isDirectory: &isDir) {
26
+ if !isDir.boolValue {
27
+ try! FileManager.default.copyItem(at: fileURL, to: tempDir.appendingPathComponent(fileURL.lastPathComponent.replacingOccurrences(of: ".fixture", with: "")))
28
+ }
29
+ }
30
+ }
31
+ }
32
+ }
33
+
34
+ @discardableResult func runCommand(args: [String]) -> (String, Int32) {
35
+ let task = Process()
36
+ task.executableURL = URL(fileURLWithPath: args[0])
37
+ task.arguments = Array(args.dropFirst())
38
+ task.currentDirectoryURL = tempDir
39
+ let pipe = Pipe()
40
+ task.standardOutput = pipe
41
+ task.standardError = pipe
42
+ task.launch()
43
+ task.waitUntilExit()
44
+ let data = pipe.fileHandleForReading.readDataToEndOfFile()
45
+ let output = String(data: data, encoding: .utf8)?.trimmingCharacters(in: .whitespacesAndNewlines)
46
+ return (output!, task.terminationStatus)
47
+ }
48
+
49
+ private func testConvert(deviceTarget: String, simulatorTarget:String, file: StaticString = #file, line: UInt = #line) {
50
+ let (sysroot, _) = runCommand(args: ["/usr/bin/xcrun", "--show-sdk-path", "--sdk", "iphonesimulator"])
51
+ runCommand(args: ["/usr/bin/clang", "-isysroot", sysroot, "-target", simulatorTarget, "-c", "main.c", "-o", "main.arm64.ios.simulator.o"])
52
+ runCommand(args: ["/usr/bin/clang", "-isysroot", sysroot, "-target", deviceTarget, "-c", "return2.c", "-o", "return2.ios.device.o"])
53
+ let (loadCommandsOutput, _) = runCommand(args: ["/usr/bin/otool", "-l", "return2.ios.device.o" ])
54
+ print("LOAD_COMMANDS:")
55
+ for lc in loadCommandsOutput.split(separator: "\n").filter({$0.contains("cmd")}) {
56
+ print(lc)
57
+ }
58
+ let (_, link_status_failing) = runCommand(args: ["/usr/bin/clang", "-isysroot", sysroot, "-target", deviceTarget, "main.arm64.ios.simulator.o", "return2.ios.device.o"])
59
+ XCTAssert(link_status_failing != 0)
60
+ Transmogrifier.processBinary(atPath: tempDir.appendingPathComponent("return2.ios.device.o").path, minos: 13, sdk: 13, isDynamic: false)
61
+ let (_, link_status_success) = runCommand(args: ["/usr/bin/clang", "-isysroot", sysroot, "-target", "arm64-apple-ios-simulator", "main.arm64.ios.simulator.o", "return2.ios.device.o"])
62
+ XCTAssert(link_status_success == 0)
63
+ }
64
+
65
+ func testConvertPreiOS12FileFormatToSim() {
66
+ testConvert(deviceTarget: "arm64-apple-ios11", simulatorTarget: "arm64-apple-ios12-simulator")
67
+ }
68
+
69
+ func testConvertNewObjectFileFormatToSim() {
70
+ testConvert(deviceTarget: "arm64-apple-ios12", simulatorTarget: "arm64-apple-ios12-simulator")
71
+ }
72
+
73
+ }
@@ -0,0 +1,16 @@
1
+ import Foundation
2
+ import Arm64ToSimLib
3
+
4
+ guard CommandLine.arguments.count > 1 else {
5
+ fatalError("Please add a path to command!")
6
+ }
7
+
8
+ let binaryPath = CommandLine.arguments[1]
9
+ let minos = (CommandLine.arguments.count > 2 ? UInt32(CommandLine.arguments[2]) : nil) ?? 12
10
+ let sdk = (CommandLine.arguments.count > 3 ? UInt32(CommandLine.arguments[3]) : nil) ?? 13
11
+ let isDynamic = (CommandLine.arguments.count > 4 ? Bool(CommandLine.arguments[4]) : nil) ?? false
12
+ if isDynamic {
13
+ print("[arm64-to-sim] notice: running in dynamic framework mode")
14
+ }
15
+
16
+ Transmogrifier.processBinary(atPath: binaryPath, minos: minos, sdk: sdk, isDynamic: isDynamic)
@@ -42,8 +42,18 @@ module XCFrameworkConverter
42
42
  extracted_path.rmtree
43
43
  end
44
44
 
45
+ def gem_path(fragment)
46
+ Pathname.new(__FILE__).dirname.join('../..').join(fragment)
47
+ end
48
+
45
49
  def arm2sim_path
46
- Pathname.new(__FILE__).dirname.join('../arm2sim.swift')
50
+ @arm2sim_path ||= begin
51
+ warn 'Pre-building `arm64-to-sim` with SwiftPM'
52
+ Dir.chdir gem_path('lib/arm64-to-sim') do
53
+ system 'xcrun swift build -c release --arch arm64 --arch x86_64'
54
+ end
55
+ gem_path('lib/arm64-to-sim/.build/apple/Products/Release/arm64-to-sim')
56
+ end
47
57
  end
48
58
 
49
59
  def patch_arm_binary_static(slice)
@@ -55,8 +65,10 @@ module XCFrameworkConverter
55
65
  Dir[extracted_path_dir.join('*.o')].each do |object_file|
56
66
  file = MachO::MachOFile.new(object_file)
57
67
  sdk_version = file[:LC_VERSION_MIN_IPHONEOS].first.version_string.to_i
58
- `xcrun swift \"#{arm2sim_path}\" \"#{object_file}\" \"#{sdk_version}\" \"#{sdk_version}\"`
68
+ `\"#{arm2sim_path}\" \"#{object_file}\" \"#{sdk_version}\" \"#{sdk_version}\"`
69
+ $stderr.printf '.'
59
70
  end
71
+ $stderr.puts
60
72
  `cd \"#{extracted_path_dir}\" ; ar crv \"#{extracted_path}\" *.o`
61
73
 
62
74
  `xcrun lipo \"#{slice.binary_path}\" -replace arm64 \"#{extracted_path}\" -output \"#{slice.binary_path}\"`
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module XCFrameworkConverter
4
- VERSION = '0.3.1'
4
+ VERSION = '0.4.0'
5
5
  end
@@ -44,8 +44,12 @@ module XCFrameworkConverter
44
44
 
45
45
  convert_xcframeworks_if_present(frameworks_to_convert)
46
46
 
47
+ remember_spec_as_patched(spec) unless frameworks_to_convert.empty?
48
+
47
49
  remove_troublesome_xcconfig_items(spec)
48
50
  end
51
+
52
+ warn "Specs with patched XCFrameworks: #{@patched_specs.sort.join(', ')}"
49
53
  end
50
54
 
51
55
  def convert_xcframeworks_if_present(frameworks_to_convert)
@@ -61,12 +65,27 @@ module XCFrameworkConverter
61
65
  end
62
66
 
63
67
  def remove_troublesome_xcconfig_items(spec)
64
- # some pods put these as a way to NOT support arm64 sim
65
- # may stop working if a pod decides to put these in a platform proxy
66
- spec.attributes_hash['pod_target_xcconfig']&.delete('EXCLUDED_ARCHS[sdk=iphonesimulator*]')
67
- spec.attributes_hash['user_target_xcconfig']&.delete('EXCLUDED_ARCHS[sdk=iphonesimulator*]')
68
- spec.attributes_hash['pod_target_xcconfig']&.delete('VALID_ARCHS[sdk=iphonesimulator*]')
69
- spec.attributes_hash['user_target_xcconfig']&.delete('VALID_ARCHS[sdk=iphonesimulator*]')
68
+ xcconfigs = %w[
69
+ pod_target_xcconfig
70
+ user_target_xcconfig
71
+ ].map { |key| spec.attributes_hash[key] }.compact
72
+
73
+ xcconfigs.each do |xcconfig|
74
+ # some pods put these as a way to NOT support arm64 sim
75
+ # may stop working if a pod decides to put these in a platform proxy
76
+ excluded_arm = xcconfig['EXCLUDED_ARCHS[sdk=iphonesimulator*]']&.include?('arm64')
77
+ not_inlcuded_arm = xcconfig['VALID_ARCHS[sdk=iphonesimulator*]'] && !xcconfig['VALID_ARCHS[sdk=iphonesimulator*]'].include?('arm64')
78
+
79
+ remember_spec_as_patched(spec) if excluded_arm || not_inlcuded_arm
80
+
81
+ xcconfig.delete('EXCLUDED_ARCHS[sdk=iphonesimulator*]')
82
+ xcconfig.delete('VALID_ARCHS[sdk=iphonesimulator*]')
83
+ end
84
+ end
85
+
86
+ def remember_spec_as_patched(spec)
87
+ @patched_specs ||= Set.new
88
+ @patched_specs << spec.root.name
70
89
  end
71
90
  end
72
91
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: xcframework_converter
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.1
4
+ version: 0.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Igor Makarov
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-01-18 00:00:00.000000000 Z
11
+ date: 2022-05-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: cocoapods
@@ -51,7 +51,10 @@ files:
51
51
  - README.md
52
52
  - bin/xcfconvert
53
53
  - bin/xcfpatch
54
- - lib/arm2sim.swift
54
+ - lib/arm64-to-sim/Package.swift
55
+ - lib/arm64-to-sim/Sources/Arm64ToSimLib/Transmogrifier.swift
56
+ - lib/arm64-to-sim/Sources/Tests/Arm64ToSimTestCase.swift
57
+ - lib/arm64-to-sim/Sources/arm64-to-sim/main.swift
55
58
  - lib/xcframework_converter.rb
56
59
  - lib/xcframework_converter/arm_patcher.rb
57
60
  - lib/xcframework_converter/creation.rb