1 //===-- TextStubV4Tests.cpp - TBD V4 File Test ----------------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===-----------------------------------------------------------------------===/
8 #include "llvm/TextAPI/MachO/InterfaceFile.h"
9 #include "llvm/TextAPI/MachO/TextAPIReader.h"
10 #include "llvm/TextAPI/MachO/TextAPIWriter.h"
11 #include "gtest/gtest.h"
16 using namespace llvm::MachO
;
18 struct ExampleSymbol
{
22 bool ThreadLocalValue
;
24 using ExampleSymbolSeq
= std::vector
<ExampleSymbol
>;
25 using UUIDs
= std::vector
<std::pair
<Target
, std::string
>>;
27 inline bool operator<(const ExampleSymbol
&LHS
, const ExampleSymbol
&RHS
) {
28 return std::tie(LHS
.Kind
, LHS
.Name
) < std::tie(RHS
.Kind
, RHS
.Name
);
31 inline bool operator==(const ExampleSymbol
&LHS
, const ExampleSymbol
&RHS
) {
32 return std::tie(LHS
.Kind
, LHS
.Name
, LHS
.WeakDefined
, LHS
.ThreadLocalValue
) ==
33 std::tie(RHS
.Kind
, RHS
.Name
, RHS
.WeakDefined
, RHS
.ThreadLocalValue
);
36 static ExampleSymbol TBDv4ExportedSymbols
[] = {
37 {SymbolKind::GlobalSymbol
, "_symA", false, false},
38 {SymbolKind::GlobalSymbol
, "_symAB", false, false},
39 {SymbolKind::GlobalSymbol
, "_symB", false, false},
42 static ExampleSymbol TBDv4ReexportedSymbols
[] = {
43 {SymbolKind::GlobalSymbol
, "_symC", false, false},
46 static ExampleSymbol TBDv4UndefinedSymbols
[] = {
47 {SymbolKind::GlobalSymbol
, "_symD", false, false},
52 TEST(TBDv4
, ReadFile
) {
53 static const char tbd_v4_file
[] =
56 "targets: [ i386-macos, x86_64-macos, x86_64-ios ]\n"
58 " - target: i386-macos\n"
59 " value: 00000000-0000-0000-0000-000000000000\n"
60 " - target: x86_64-macos\n"
61 " value: 11111111-1111-1111-1111-111111111111\n"
62 " - target: x86_64-ios\n"
63 " value: 11111111-1111-1111-1111-111111111111\n"
64 "flags: [ flat_namespace, installapi ]\n"
65 "install-name: Umbrella.framework/Umbrella\n"
66 "current-version: 1.2.3\n"
67 "compatibility-version: 1.2\n"
68 "swift-abi-version: 5\n"
70 " - targets: [ i386-macos, x86_64-macos, x86_64-ios ]\n"
72 "allowable-clients:\n"
73 " - targets: [ i386-macos, x86_64-macos, x86_64-ios ]\n"
74 " clients: [ ClientA ]\n"
75 "reexported-libraries:\n"
76 " - targets: [ i386-macos ]\n"
77 " libraries: [ /System/Library/Frameworks/A.framework/A ]\n"
79 " - targets: [ i386-macos ]\n"
80 " symbols: [ _symA ]\n"
82 " objc-eh-types: []\n"
85 " thread-local-symbols: []\n"
86 " - targets: [ x86_64-ios ]\n"
88 " - targets: [ x86_64-macos, x86_64-ios ]\n"
89 " symbols: [_symAB]\n"
91 " - targets: [ i386-macos ]\n"
94 " objc-eh-types: []\n"
97 " thread-local-symbols: []\n"
99 " - targets: [ i386-macos ]\n"
100 " symbols: [ _symD ]\n"
101 " objc-classes: []\n"
102 " objc-eh-types: []\n"
104 " weak-symbols: []\n"
105 " thread-local-symbols: []\n"
108 auto Result
= TextAPIReader::get(MemoryBufferRef(tbd_v4_file
, "Test.tbd"));
109 EXPECT_TRUE(!!Result
);
110 auto File
= std::move(Result
.get());
111 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
112 PlatformSet Platforms
;
113 Platforms
.insert(PlatformKind::macOS
);
114 Platforms
.insert(PlatformKind::iOS
);
115 auto Archs
= AK_i386
| AK_x86_64
;
116 TargetList Targets
= {
117 Target(AK_i386
, PlatformKind::macOS
),
118 Target(AK_x86_64
, PlatformKind::macOS
),
119 Target(AK_x86_64
, PlatformKind::iOS
),
121 UUIDs uuids
= {{Targets
[0], "00000000-0000-0000-0000-000000000000"},
122 {Targets
[1], "11111111-1111-1111-1111-111111111111"},
123 {Targets
[2], "11111111-1111-1111-1111-111111111111"}};
124 EXPECT_EQ(Archs
, File
->getArchitectures());
125 EXPECT_EQ(uuids
, File
->uuids());
126 EXPECT_EQ(Platforms
.size(), File
->getPlatforms().size());
127 for (auto Platform
: File
->getPlatforms())
128 EXPECT_EQ(Platforms
.count(Platform
), 1U);
129 EXPECT_EQ(std::string("Umbrella.framework/Umbrella"), File
->getInstallName());
130 EXPECT_EQ(PackedVersion(1, 2, 3), File
->getCurrentVersion());
131 EXPECT_EQ(PackedVersion(1, 2, 0), File
->getCompatibilityVersion());
132 EXPECT_EQ(5U, File
->getSwiftABIVersion());
133 EXPECT_FALSE(File
->isTwoLevelNamespace());
134 EXPECT_TRUE(File
->isApplicationExtensionSafe());
135 EXPECT_TRUE(File
->isInstallAPI());
136 InterfaceFileRef
client("ClientA", Targets
);
137 InterfaceFileRef
reexport("/System/Library/Frameworks/A.framework/A",
139 EXPECT_EQ(1U, File
->allowableClients().size());
140 EXPECT_EQ(client
, File
->allowableClients().front());
141 EXPECT_EQ(1U, File
->reexportedLibraries().size());
142 EXPECT_EQ(reexport
, File
->reexportedLibraries().front());
144 ExampleSymbolSeq Exports
, Reexports
, Undefineds
;
146 for (const auto *Sym
: File
->symbols()) {
147 temp
= ExampleSymbol
{Sym
->getKind(), Sym
->getName(), Sym
->isWeakDefined(),
148 Sym
->isThreadLocalValue()};
149 EXPECT_FALSE(Sym
->isWeakReferenced());
150 if (Sym
->isUndefined())
151 Undefineds
.emplace_back(std::move(temp
));
153 Sym
->isReexported() ? Reexports
.emplace_back(std::move(temp
))
154 : Exports
.emplace_back(std::move(temp
));
156 llvm::sort(Exports
.begin(), Exports
.end());
157 llvm::sort(Reexports
.begin(), Reexports
.end());
158 llvm::sort(Undefineds
.begin(), Undefineds
.end());
160 EXPECT_EQ(sizeof(TBDv4ExportedSymbols
) / sizeof(ExampleSymbol
),
162 EXPECT_EQ(sizeof(TBDv4ReexportedSymbols
) / sizeof(ExampleSymbol
),
164 EXPECT_EQ(sizeof(TBDv4UndefinedSymbols
) / sizeof(ExampleSymbol
),
166 EXPECT_TRUE(std::equal(Exports
.begin(), Exports
.end(),
167 std::begin(TBDv4ExportedSymbols
)));
168 EXPECT_TRUE(std::equal(Reexports
.begin(), Reexports
.end(),
169 std::begin(TBDv4ReexportedSymbols
)));
170 EXPECT_TRUE(std::equal(Undefineds
.begin(), Undefineds
.end(),
171 std::begin(TBDv4UndefinedSymbols
)));
174 TEST(TBDv4
, WriteFile
) {
175 static const char tbd_v4_file
[] =
178 "targets: [ i386-macos, x86_64-ios-simulator ]\n"
180 " - target: i386-macos\n"
181 " value: 00000000-0000-0000-0000-000000000000\n"
182 " - target: x86_64-ios-simulator\n"
183 " value: 11111111-1111-1111-1111-111111111111\n"
184 "flags: [ installapi ]\n"
185 "install-name: 'Umbrella.framework/Umbrella'\n"
186 "current-version: 1.2.3\n"
187 "compatibility-version: 0\n"
188 "swift-abi-version: 5\n"
190 " - targets: [ i386-macos, x86_64-ios-simulator ]\n"
191 " umbrella: System\n"
192 "allowable-clients:\n"
193 " - targets: [ i386-macos ]\n"
194 " clients: [ ClientA ]\n"
196 " - targets: [ i386-macos ]\n"
197 " symbols: [ _symA ]\n"
198 " objc-classes: [ Class1 ]\n"
199 " weak-symbols: [ _symC ]\n"
200 " - targets: [ x86_64-ios-simulator ]\n"
201 " symbols: [ _symB ]\n"
205 TargetList Targets
= {
206 Target(AK_i386
, PlatformKind::macOS
),
207 Target(AK_x86_64
, PlatformKind::iOSSimulator
),
209 UUIDs uuids
= {{Targets
[0], "00000000-0000-0000-0000-000000000000"},
210 {Targets
[1], "11111111-1111-1111-1111-111111111111"}};
211 File
.setInstallName("Umbrella.framework/Umbrella");
212 File
.setFileType(FileType::TBD_V4
);
213 File
.addTargets(Targets
);
214 File
.addUUID(uuids
[0].first
, uuids
[0].second
);
215 File
.addUUID(uuids
[1].first
, uuids
[1].second
);
216 File
.setCurrentVersion(PackedVersion(1, 2, 3));
217 File
.setTwoLevelNamespace();
218 File
.setInstallAPI(true);
219 File
.setApplicationExtensionSafe(true);
220 File
.setSwiftABIVersion(5);
221 File
.addAllowableClient("ClientA", Targets
[0]);
222 File
.addParentUmbrella(Targets
[0], "System");
223 File
.addParentUmbrella(Targets
[1], "System");
224 File
.addSymbol(SymbolKind::GlobalSymbol
, "_symA", {Targets
[0]});
225 File
.addSymbol(SymbolKind::GlobalSymbol
, "_symB", {Targets
[1]});
226 File
.addSymbol(SymbolKind::GlobalSymbol
, "_symC", {Targets
[0]},
227 SymbolFlags::WeakDefined
);
228 File
.addSymbol(SymbolKind::ObjectiveCClass
, "Class1", {Targets
[0]});
230 SmallString
<4096> Buffer
;
231 raw_svector_ostream
OS(Buffer
);
232 auto Result
= TextAPIWriter::writeToStream(OS
, File
);
233 EXPECT_FALSE(Result
);
234 EXPECT_STREQ(tbd_v4_file
, Buffer
.c_str());
237 TEST(TBDv4
, MultipleTargets
) {
238 static const char tbd_multiple_targets
[] =
241 "targets: [ i386-maccatalyst, x86_64-tvos, arm64-ios ]\n"
242 "install-name: Test.dylib\n"
246 TextAPIReader::get(MemoryBufferRef(tbd_multiple_targets
, "Test.tbd"));
247 EXPECT_TRUE(!!Result
);
248 PlatformSet Platforms
;
249 Platforms
.insert(PlatformKind::macCatalyst
);
250 Platforms
.insert(PlatformKind::tvOS
);
251 Platforms
.insert(PlatformKind::iOS
);
252 auto File
= std::move(Result
.get());
253 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
254 EXPECT_EQ(AK_x86_64
| AK_arm64
| AK_i386
, File
->getArchitectures());
255 EXPECT_EQ(Platforms
.size(), File
->getPlatforms().size());
256 for (auto Platform
: File
->getPlatforms())
257 EXPECT_EQ(Platforms
.count(Platform
), 1U);
260 TEST(TBDv4
, MultipleTargetsSameArch
) {
261 static const char tbd_targets_same_arch
[] =
264 "targets: [ x86_64-maccatalyst, x86_64-tvos ]\n"
265 "install-name: Test.dylib\n"
269 TextAPIReader::get(MemoryBufferRef(tbd_targets_same_arch
, "Test.tbd"));
270 EXPECT_TRUE(!!Result
);
271 PlatformSet Platforms
;
272 Platforms
.insert(PlatformKind::tvOS
);
273 Platforms
.insert(PlatformKind::macCatalyst
);
274 auto File
= std::move(Result
.get());
275 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
276 EXPECT_EQ(ArchitectureSet(AK_x86_64
), File
->getArchitectures());
277 EXPECT_EQ(Platforms
.size(), File
->getPlatforms().size());
278 for (auto Platform
: File
->getPlatforms())
279 EXPECT_EQ(Platforms
.count(Platform
), 1U);
282 TEST(TBDv4
, MultipleTargetsSamePlatform
) {
283 static const char tbd_multiple_targets_same_platform
[] =
286 "targets: [ arm64-ios, armv7k-ios ]\n"
287 "install-name: Test.dylib\n"
290 auto Result
= TextAPIReader::get(
291 MemoryBufferRef(tbd_multiple_targets_same_platform
, "Test.tbd"));
292 EXPECT_TRUE(!!Result
);
293 auto File
= std::move(Result
.get());
294 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
295 EXPECT_EQ(AK_arm64
| AK_armv7k
, File
->getArchitectures());
296 EXPECT_EQ(File
->getPlatforms().size(), 1U);
297 EXPECT_EQ(PlatformKind::iOS
, *File
->getPlatforms().begin());
300 TEST(TBDv4
, Target_maccatalyst
) {
301 static const char tbd_target_maccatalyst
[] =
304 "targets: [ x86_64-maccatalyst ]\n"
305 "install-name: Test.dylib\n"
309 TextAPIReader::get(MemoryBufferRef(tbd_target_maccatalyst
, "Test.tbd"));
310 EXPECT_TRUE(!!Result
);
311 auto File
= std::move(Result
.get());
312 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
313 EXPECT_EQ(ArchitectureSet(AK_x86_64
), File
->getArchitectures());
314 EXPECT_EQ(File
->getPlatforms().size(), 1U);
315 EXPECT_EQ(PlatformKind::macCatalyst
, *File
->getPlatforms().begin());
318 TEST(TBDv4
, Target_x86_ios
) {
319 static const char tbd_target_x86_ios
[] = "--- !tapi-tbd\n"
321 "targets: [ x86_64-ios ]\n"
322 "install-name: Test.dylib\n"
326 TextAPIReader::get(MemoryBufferRef(tbd_target_x86_ios
, "Test.tbd"));
327 EXPECT_TRUE(!!Result
);
328 auto File
= std::move(Result
.get());
329 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
330 EXPECT_EQ(ArchitectureSet(AK_x86_64
), File
->getArchitectures());
331 EXPECT_EQ(File
->getPlatforms().size(), 1U);
332 EXPECT_EQ(PlatformKind::iOS
, *File
->getPlatforms().begin());
335 TEST(TBDv4
, Target_arm_bridgeOS
) {
336 static const char tbd_platform_bridgeos
[] = "--- !tapi-tbd\n"
338 "targets: [ armv7k-bridgeos ]\n"
339 "install-name: Test.dylib\n"
343 TextAPIReader::get(MemoryBufferRef(tbd_platform_bridgeos
, "Test.tbd"));
344 EXPECT_TRUE(!!Result
);
345 auto File
= std::move(Result
.get());
346 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
347 EXPECT_EQ(File
->getPlatforms().size(), 1U);
348 EXPECT_EQ(PlatformKind::bridgeOS
, *File
->getPlatforms().begin());
349 EXPECT_EQ(ArchitectureSet(AK_armv7k
), File
->getArchitectures());
352 TEST(TBDv4
, Target_x86_macos
) {
353 static const char tbd_x86_macos
[] = "--- !tapi-tbd\n"
355 "targets: [ x86_64-macos ]\n"
356 "install-name: Test.dylib\n"
359 auto Result
= TextAPIReader::get(MemoryBufferRef(tbd_x86_macos
, "Test.tbd"));
360 EXPECT_TRUE(!!Result
);
361 auto File
= std::move(Result
.get());
362 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
363 EXPECT_EQ(ArchitectureSet(AK_x86_64
), File
->getArchitectures());
364 EXPECT_EQ(File
->getPlatforms().size(), 1U);
365 EXPECT_EQ(PlatformKind::macOS
, *File
->getPlatforms().begin());
368 TEST(TBDv4
, Target_x86_ios_simulator
) {
369 static const char tbd_x86_ios_sim
[] = "--- !tapi-tbd\n"
371 "targets: [ x86_64-ios-simulator ]\n"
372 "install-name: Test.dylib\n"
376 TextAPIReader::get(MemoryBufferRef(tbd_x86_ios_sim
, "Test.tbd"));
377 EXPECT_TRUE(!!Result
);
378 auto File
= std::move(Result
.get());
379 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
380 EXPECT_EQ(ArchitectureSet(AK_x86_64
), File
->getArchitectures());
381 EXPECT_EQ(File
->getPlatforms().size(), 1U);
382 EXPECT_EQ(PlatformKind::iOSSimulator
, *File
->getPlatforms().begin());
385 TEST(TBDv4
, Target_x86_tvos_simulator
) {
386 static const char tbd_x86_tvos_sim
[] =
389 "targets: [ x86_64-tvos-simulator ]\n"
390 "install-name: Test.dylib\n"
394 TextAPIReader::get(MemoryBufferRef(tbd_x86_tvos_sim
, "Test.tbd"));
395 EXPECT_TRUE(!!Result
);
396 auto File
= std::move(Result
.get());
397 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
398 EXPECT_EQ(ArchitectureSet(AK_x86_64
), File
->getArchitectures());
399 EXPECT_EQ(File
->getPlatforms().size(), 1U);
400 EXPECT_EQ(PlatformKind::tvOSSimulator
, *File
->getPlatforms().begin());
403 TEST(TBDv4
, Target_i386_watchos_simulator
) {
404 static const char tbd_i386_watchos_sim
[] =
407 "targets: [ i386-watchos-simulator ]\n"
408 "install-name: Test.dylib\n"
412 TextAPIReader::get(MemoryBufferRef(tbd_i386_watchos_sim
, "Test.tbd"));
413 EXPECT_TRUE(!!Result
);
414 auto File
= std::move(Result
.get());
415 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
416 EXPECT_EQ(ArchitectureSet(AK_i386
), File
->getArchitectures());
417 EXPECT_EQ(File
->getPlatforms().size(), 1U);
418 EXPECT_EQ(PlatformKind::watchOSSimulator
, *File
->getPlatforms().begin());
421 TEST(TBDv4
, Swift_1
) {
422 static const char tbd_swift_1
[] = "--- !tapi-tbd\n"
424 "targets: [ x86_64-macos ]\n"
425 "install-name: Test.dylib\n"
426 "swift-abi-version: 1\n"
429 auto Result
= TextAPIReader::get(MemoryBufferRef(tbd_swift_1
, "Test.tbd"));
430 EXPECT_TRUE(!!Result
);
431 auto File
= std::move(Result
.get());
432 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
433 EXPECT_EQ(1U, File
->getSwiftABIVersion());
436 TEST(TBDv4
, Swift_2
) {
437 static const char tbd_v1_swift_2
[] = "--- !tapi-tbd\n"
439 "targets: [ x86_64-macos ]\n"
440 "install-name: Test.dylib\n"
441 "swift-abi-version: 2\n"
444 auto Result
= TextAPIReader::get(MemoryBufferRef(tbd_v1_swift_2
, "Test.tbd"));
445 EXPECT_TRUE(!!Result
);
446 auto File
= std::move(Result
.get());
447 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
448 EXPECT_EQ(2U, File
->getSwiftABIVersion());
451 TEST(TBDv4
, Swift_5
) {
452 static const char tbd_swift_5
[] = "--- !tapi-tbd\n"
454 "targets: [ x86_64-macos ]\n"
455 "install-name: Test.dylib\n"
456 "swift-abi-version: 5\n"
459 auto Result
= TextAPIReader::get(MemoryBufferRef(tbd_swift_5
, "Test.tbd"));
460 EXPECT_TRUE(!!Result
);
461 auto File
= std::move(Result
.get());
462 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
463 EXPECT_EQ(5U, File
->getSwiftABIVersion());
466 TEST(TBDv4
, Swift_99
) {
467 static const char tbd_swift_99
[] = "--- !tapi-tbd\n"
469 "targets: [ x86_64-macos ]\n"
470 "install-name: Test.dylib\n"
471 "swift-abi-version: 99\n"
474 auto Result
= TextAPIReader::get(MemoryBufferRef(tbd_swift_99
, "Test.tbd"));
475 EXPECT_TRUE(!!Result
);
476 auto File
= std::move(Result
.get());
477 EXPECT_EQ(FileType::TBD_V4
, File
->getFileType());
478 EXPECT_EQ(99U, File
->getSwiftABIVersion());
481 TEST(TBDv4
, InvalidArchitecture
) {
482 static const char tbd_file_unknown_architecture
[] =
485 "targets: [ foo-macos ]\n"
486 "install-name: Test.dylib\n"
489 auto Result
= TextAPIReader::get(
490 MemoryBufferRef(tbd_file_unknown_architecture
, "Test.tbd"));
491 EXPECT_FALSE(!!Result
);
492 auto errorMessage
= toString(Result
.takeError());
493 EXPECT_EQ("malformed file\nTest.tbd:3:12: error: unknown "
494 "architecture\ntargets: [ foo-macos ]\n"
499 TEST(TBDv4
, InvalidPlatform
) {
500 static const char tbd_file_invalid_platform
[] = "--- !tapi-tbd\n"
502 "targets: [ x86_64-maos ]\n"
503 "install-name: Test.dylib\n"
506 auto Result
= TextAPIReader::get(
507 MemoryBufferRef(tbd_file_invalid_platform
, "Test.tbd"));
508 EXPECT_FALSE(!!Result
);
509 auto errorMessage
= toString(Result
.takeError());
510 EXPECT_EQ("malformed file\nTest.tbd:3:12: error: unknown platform\ntargets: "
516 TEST(TBDv4
, MalformedFile1
) {
517 static const char malformed_file1
[] = "--- !tapi-tbd\n"
522 TextAPIReader::get(MemoryBufferRef(malformed_file1
, "Test.tbd"));
523 EXPECT_FALSE(!!Result
);
524 auto errorMessage
= toString(Result
.takeError());
525 ASSERT_EQ("malformed file\nTest.tbd:2:1: error: missing required key "
526 "'targets'\ntbd-version: 4\n^\n",
530 TEST(TBDv4
, MalformedFile2
) {
531 static const char malformed_file2
[] = "--- !tapi-tbd\n"
533 "targets: [ x86_64-macos ]\n"
534 "install-name: Test.dylib\n"
535 "foobar: \"unsupported key\"\n";
538 TextAPIReader::get(MemoryBufferRef(malformed_file2
, "Test.tbd"));
539 EXPECT_FALSE(!!Result
);
540 auto errorMessage
= toString(Result
.takeError());
542 "malformed file\nTest.tbd:5:9: error: unknown key 'foobar'\nfoobar: "
543 "\"unsupported key\"\n ^~~~~~~~~~~~~~~~~\n",
547 TEST(TBDv4
, MalformedFile3
) {
548 static const char tbd_v1_swift_1_1
[] = "--- !tapi-tbd\n"
550 "targets: [ x86_64-macos ]\n"
551 "install-name: Test.dylib\n"
552 "swift-abi-version: 1.1\n"
556 TextAPIReader::get(MemoryBufferRef(tbd_v1_swift_1_1
, "Test.tbd"));
557 EXPECT_FALSE(!!Result
);
558 auto errorMessage
= toString(Result
.takeError());
559 EXPECT_EQ("malformed file\nTest.tbd:5:20: error: invalid Swift ABI "
560 "version.\nswift-abi-version: 1.1\n ^~~\n",
564 } // end namespace TBDv4