mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-10-18 18:42:46 +02:00
[TextAPI] Arch&Platform to Target
Summary: This is a patch for updating TextAPI/Macho to read in targets as opposed to arch/platform. This is because in previous versions tbd files only supported a single platform but that is no longer the case, so, now its tracked by unique triples. This precedes a seperate patch that will add the TBD-v4 format Reviewers: ributzka, steven_wu, plotfi, compnerd, smeenai Reviewed By: ributzka Subscribers: mgorny, hiraditya, dexonsmith, llvm-commits Tags: #llvm Differential Revision: https://reviews.llvm.org/D67527 llvm-svn: 372396
This commit is contained in:
parent
a661d2b4f2
commit
5392f0f014
@ -14,6 +14,7 @@
|
||||
#define LLVM_TEXTAPI_MACHO_ARCHITECTURE_H
|
||||
|
||||
#include "llvm/ADT/StringRef.h"
|
||||
#include "llvm/ADT/Triple.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
|
||||
namespace llvm {
|
||||
@ -39,6 +40,9 @@ StringRef getArchitectureName(Architecture Arch);
|
||||
/// Convert an architecture slice to a CPU Type and Subtype pair.
|
||||
std::pair<uint32_t, uint32_t> getCPUTypeFromArchitecture(Architecture Arch);
|
||||
|
||||
/// Convert a target to an architecture slice.
|
||||
Architecture mapToArchitecture(const llvm::Triple &Target);
|
||||
|
||||
raw_ostream &operator<<(raw_ostream &OS, Architecture Arch);
|
||||
|
||||
} // end namespace MachO.
|
||||
|
@ -59,6 +59,10 @@ public:
|
||||
|
||||
ArchSetType rawValue() const { return ArchSet; }
|
||||
|
||||
bool hasX86() const {
|
||||
return has(AK_i386) || has(AK_x86_64) || has(AK_x86_64h);
|
||||
}
|
||||
|
||||
template <typename Ty>
|
||||
class arch_iterator
|
||||
: public std::iterator<std::forward_iterator_tag, Architecture, size_t> {
|
||||
|
@ -26,21 +26,13 @@
|
||||
#include "llvm/TextAPI/MachO/Architecture.h"
|
||||
#include "llvm/TextAPI/MachO/ArchitectureSet.h"
|
||||
#include "llvm/TextAPI/MachO/PackedVersion.h"
|
||||
#include "llvm/TextAPI/MachO/Platform.h"
|
||||
#include "llvm/TextAPI/MachO/Symbol.h"
|
||||
#include "llvm/TextAPI/MachO/Target.h"
|
||||
|
||||
namespace llvm {
|
||||
namespace MachO {
|
||||
|
||||
/// Defines the list of MachO platforms.
|
||||
enum class PlatformKind : unsigned {
|
||||
unknown,
|
||||
macOS = MachO::PLATFORM_MACOS,
|
||||
iOS = MachO::PLATFORM_IOS,
|
||||
tvOS = MachO::PLATFORM_TVOS,
|
||||
watchOS = MachO::PLATFORM_WATCHOS,
|
||||
bridgeOS = MachO::PLATFORM_BRIDGEOS,
|
||||
};
|
||||
|
||||
/// Defines a list of Objective-C constraints.
|
||||
enum class ObjCConstraintType : unsigned {
|
||||
/// No constraint.
|
||||
@ -89,29 +81,42 @@ public:
|
||||
|
||||
InterfaceFileRef(StringRef InstallName) : InstallName(InstallName) {}
|
||||
|
||||
InterfaceFileRef(StringRef InstallName, ArchitectureSet Archs)
|
||||
: InstallName(InstallName), Architectures(Archs) {}
|
||||
InterfaceFileRef(StringRef InstallName, const TargetList Targets)
|
||||
: InstallName(InstallName), Targets(std::move(Targets)) {}
|
||||
|
||||
StringRef getInstallName() const { return InstallName; };
|
||||
void addArchitectures(ArchitectureSet Archs) { Architectures |= Archs; }
|
||||
ArchitectureSet getArchitectures() const { return Architectures; }
|
||||
bool hasArchitecture(Architecture Arch) const {
|
||||
return Architectures.has(Arch);
|
||||
|
||||
void addTarget(const Target &Target);
|
||||
template <typename RangeT> void addTargets(RangeT &&Targets) {
|
||||
for (const auto &Target : Targets)
|
||||
addTarget(Target(Target));
|
||||
}
|
||||
|
||||
using const_target_iterator = TargetList::const_iterator;
|
||||
using const_target_range = llvm::iterator_range<const_target_iterator>;
|
||||
const_target_range targets() const { return {Targets}; }
|
||||
|
||||
ArchitectureSet getArchitectures() const {
|
||||
return mapToArchitectureSet(Targets);
|
||||
}
|
||||
|
||||
PlatformSet getPlatforms() const { return mapToPlatformSet(Targets); }
|
||||
|
||||
bool operator==(const InterfaceFileRef &O) const {
|
||||
return std::tie(InstallName, Architectures) ==
|
||||
std::tie(O.InstallName, O.Architectures);
|
||||
return std::tie(InstallName, Targets) == std::tie(O.InstallName, O.Targets);
|
||||
}
|
||||
|
||||
bool operator!=(const InterfaceFileRef &O) const {
|
||||
return std::tie(InstallName, Targets) != std::tie(O.InstallName, O.Targets);
|
||||
}
|
||||
|
||||
bool operator<(const InterfaceFileRef &O) const {
|
||||
return std::tie(InstallName, Architectures) <
|
||||
std::tie(O.InstallName, O.Architectures);
|
||||
return std::tie(InstallName, Targets) < std::tie(O.InstallName, O.Targets);
|
||||
}
|
||||
|
||||
private:
|
||||
std::string InstallName;
|
||||
ArchitectureSet Architectures;
|
||||
TargetList Targets;
|
||||
};
|
||||
|
||||
} // end namespace MachO.
|
||||
@ -170,27 +175,43 @@ public:
|
||||
/// \return The file type.
|
||||
FileType getFileType() const { return FileKind; }
|
||||
|
||||
/// Set the platform.
|
||||
void setPlatform(PlatformKind Platform_) { Platform = Platform_; }
|
||||
|
||||
/// Get the platform.
|
||||
PlatformKind getPlatform() const { return Platform; }
|
||||
|
||||
/// Specify the set of supported architectures by this file.
|
||||
void setArchitectures(ArchitectureSet Architectures_) {
|
||||
Architectures = Architectures_;
|
||||
/// Get the architectures.
|
||||
///
|
||||
/// \return The applicable architectures.
|
||||
ArchitectureSet getArchitectures() const {
|
||||
return mapToArchitectureSet(Targets);
|
||||
}
|
||||
|
||||
/// Add the set of supported architectures by this file.
|
||||
void addArchitectures(ArchitectureSet Architectures_) {
|
||||
Architectures |= Architectures_;
|
||||
/// Get the platforms.
|
||||
///
|
||||
/// \return The applicable platforms.
|
||||
PlatformSet getPlatforms() const { return mapToPlatformSet(Targets); }
|
||||
|
||||
/// Set and add target.
|
||||
///
|
||||
/// \param Target the target to add into.
|
||||
void addTarget(const Target &Target);
|
||||
|
||||
/// Set and add targets.
|
||||
///
|
||||
/// Add the subset of llvm::triples that is supported by Tapi
|
||||
///
|
||||
/// \param Targets the collection of targets.
|
||||
template <typename RangeT> void addTargets(RangeT &&Targets) {
|
||||
for (const auto &Target_ : Targets)
|
||||
addTarget(Target(Target_));
|
||||
}
|
||||
|
||||
/// Add supported architecture by this file..
|
||||
void addArch(Architecture Arch) { Architectures.set(Arch); }
|
||||
using const_target_iterator = TargetList::const_iterator;
|
||||
using const_target_range = llvm::iterator_range<const_target_iterator>;
|
||||
const_target_range targets() const { return {Targets}; }
|
||||
|
||||
/// Get the set of supported architectures.
|
||||
ArchitectureSet getArchitectures() const { return Architectures; }
|
||||
using const_filtered_target_iterator =
|
||||
llvm::filter_iterator<const_target_iterator,
|
||||
std::function<bool(const Target &)>>;
|
||||
using const_filtered_target_range =
|
||||
llvm::iterator_range<const_filtered_target_iterator>;
|
||||
const_filtered_target_range targets(ArchitectureSet Archs) const;
|
||||
|
||||
/// Set the install name of the library.
|
||||
void setInstallName(StringRef InstallName_) { InstallName = InstallName_; }
|
||||
@ -244,11 +265,18 @@ public:
|
||||
/// Check if this file was generated during InstallAPI.
|
||||
bool isInstallAPI() const { return IsInstallAPI; }
|
||||
|
||||
/// Set the parent umbrella framework.
|
||||
void setParentUmbrella(StringRef Parent) { ParentUmbrella = Parent; }
|
||||
/// Set the parent umbrella frameworks.
|
||||
/// \param Target_ The target applicable to Parent
|
||||
/// \param Parent The name of Parent
|
||||
void addParentUmbrella(const Target &Target_, StringRef Parent);
|
||||
const std::vector<std::pair<Target, std::string>> &umbrellas() const {
|
||||
return ParentUmbrellas;
|
||||
}
|
||||
|
||||
/// Get the parent umbrella framework.
|
||||
StringRef getParentUmbrella() const { return ParentUmbrella; }
|
||||
const std::vector<std::pair<Target, std::string>> getParentUmbrellas() const {
|
||||
return ParentUmbrellas;
|
||||
}
|
||||
|
||||
/// Add an allowable client.
|
||||
///
|
||||
@ -258,8 +286,8 @@ public:
|
||||
/// linker refuses to link this library.
|
||||
///
|
||||
/// \param Name The name of the client that is allowed to link this library.
|
||||
/// \param Architectures The set of architecture for which this applies.
|
||||
void addAllowableClient(StringRef Name, ArchitectureSet Architectures);
|
||||
/// \param Target The target triple for which this applies.
|
||||
void addAllowableClient(StringRef InstallName, const Target &Target);
|
||||
|
||||
/// Get the list of allowable clients.
|
||||
///
|
||||
@ -271,9 +299,8 @@ public:
|
||||
/// Add a re-exported library.
|
||||
///
|
||||
/// \param InstallName The name of the library to re-export.
|
||||
/// \param Architectures The set of architecture for which this applies.
|
||||
void addReexportedLibrary(StringRef InstallName,
|
||||
ArchitectureSet Architectures);
|
||||
/// \param Target The target triple for which this applies.
|
||||
void addReexportedLibrary(StringRef InstallName, const Target &Target);
|
||||
|
||||
/// Get the list of re-exported libraries.
|
||||
///
|
||||
@ -282,27 +309,27 @@ public:
|
||||
return ReexportedLibraries;
|
||||
}
|
||||
|
||||
/// Add an architecture/UUID pair.
|
||||
/// Add an Target/UUID pair.
|
||||
///
|
||||
/// \param Arch The architecture for which this applies.
|
||||
/// \param Target The target triple for which this applies.
|
||||
/// \param UUID The UUID of the library for the specified architecture.
|
||||
void addUUID(Architecture Arch, StringRef UUID);
|
||||
void addUUID(const Target &Target, StringRef UUID);
|
||||
|
||||
/// Add an architecture/UUID pair.
|
||||
/// Add an Target/UUID pair.
|
||||
///
|
||||
/// \param Arch The architecture for which this applies.
|
||||
/// \param Target The target triple for which this applies.
|
||||
/// \param UUID The UUID of the library for the specified architecture.
|
||||
void addUUID(Architecture Arch, uint8_t UUID[16]);
|
||||
void addUUID(const Target &Target, uint8_t UUID[16]);
|
||||
|
||||
/// Get the list of architecture/UUID pairs.
|
||||
/// Get the list of Target/UUID pairs.
|
||||
///
|
||||
/// \return Returns a list of architecture/UUID pairs.
|
||||
const std::vector<std::pair<Architecture, std::string>> &uuids() const {
|
||||
/// \return Returns a list of Target/UUID pairs.
|
||||
const std::vector<std::pair<Target, std::string>> &uuids() const {
|
||||
return UUIDs;
|
||||
}
|
||||
|
||||
/// Add a symbol to the symbols list or extend an existing one.
|
||||
void addSymbol(SymbolKind Kind, StringRef Name, ArchitectureSet Architectures,
|
||||
void addSymbol(SymbolKind Kind, StringRef Name, const TargetList &Targets,
|
||||
SymbolFlags Flags = SymbolFlags::None);
|
||||
|
||||
using SymbolMapType = DenseMap<SymbolsMapKey, Symbol *>;
|
||||
@ -362,10 +389,9 @@ private:
|
||||
return StringRef(reinterpret_cast<const char *>(Ptr), String.size());
|
||||
}
|
||||
|
||||
TargetList Targets;
|
||||
std::string Path;
|
||||
FileType FileKind;
|
||||
PlatformKind Platform;
|
||||
ArchitectureSet Architectures;
|
||||
std::string InstallName;
|
||||
PackedVersion CurrentVersion;
|
||||
PackedVersion CompatibilityVersion;
|
||||
@ -374,10 +400,10 @@ private:
|
||||
bool IsAppExtensionSafe{false};
|
||||
bool IsInstallAPI{false};
|
||||
ObjCConstraintType ObjcConstraint = ObjCConstraintType::None;
|
||||
std::string ParentUmbrella;
|
||||
std::vector<std::pair<Target, std::string>> ParentUmbrellas;
|
||||
std::vector<InterfaceFileRef> AllowableClients;
|
||||
std::vector<InterfaceFileRef> ReexportedLibraries;
|
||||
std::vector<std::pair<Architecture, std::string>> UUIDs;
|
||||
std::vector<std::pair<Target, std::string>> UUIDs;
|
||||
SymbolMapType Symbols;
|
||||
};
|
||||
|
||||
|
40
include/llvm/TextAPI/MachO/Platform.h
Normal file
40
include/llvm/TextAPI/MachO/Platform.h
Normal file
@ -0,0 +1,40 @@
|
||||
//===- llvm/TextAPI/MachO/Platform.h - Platform -----------------*- C++ -*-===//
|
||||
//
|
||||
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
||||
// See https://llvm.org/LICENSE.txt for license information.
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// Defines the Platforms supported by Tapi and helpers.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
#ifndef LLVM_TEXTAPI_MACHO_PLATFORM_H
|
||||
#define LLVM_TEXTAPI_MACHO_PLATFORM_H
|
||||
|
||||
#include "llvm/ADT/SmallSet.h"
|
||||
#include "llvm/BinaryFormat/MachO.h"
|
||||
|
||||
namespace llvm {
|
||||
namespace MachO {
|
||||
|
||||
/// Defines the list of MachO platforms.
|
||||
enum class PlatformKind : unsigned {
|
||||
unknown,
|
||||
macOS = MachO::PLATFORM_MACOS,
|
||||
iOS = MachO::PLATFORM_IOS,
|
||||
tvOS = MachO::PLATFORM_TVOS,
|
||||
watchOS = MachO::PLATFORM_WATCHOS,
|
||||
bridgeOS = MachO::PLATFORM_BRIDGEOS
|
||||
};
|
||||
|
||||
using PlatformSet = SmallSet<PlatformKind, 3>;
|
||||
|
||||
PlatformKind mapToPlatformKind(const Triple &Target);
|
||||
PlatformSet mapToPlatformSet(ArrayRef<Triple> Targets);
|
||||
StringRef getPlatformName(PlatformKind Platform);
|
||||
|
||||
} // end namespace MachO.
|
||||
} // end namespace llvm.
|
||||
|
||||
#endif // LLVM_TEXTAPI_MACHO_PLATFORM_H
|
@ -14,6 +14,7 @@
|
||||
#include "llvm/Support/Error.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include "llvm/TextAPI/MachO/ArchitectureSet.h"
|
||||
#include "llvm/TextAPI/MachO/Target.h"
|
||||
|
||||
namespace llvm {
|
||||
namespace MachO {
|
||||
@ -49,16 +50,18 @@ enum class SymbolKind : uint8_t {
|
||||
ObjectiveCInstanceVariable,
|
||||
};
|
||||
|
||||
using TargetList = SmallVector<Target, 20>;
|
||||
class Symbol {
|
||||
public:
|
||||
constexpr Symbol(SymbolKind Kind, StringRef Name,
|
||||
ArchitectureSet Architectures, SymbolFlags Flags)
|
||||
: Name(Name), Architectures(Architectures), Kind(Kind), Flags(Flags) {}
|
||||
Symbol(SymbolKind Kind, StringRef Name, TargetList Targets, SymbolFlags Flags)
|
||||
: Name(Name), Targets(std::move(Targets)), Kind(Kind), Flags(Flags) {}
|
||||
|
||||
void addTarget(Target target) { Targets.emplace_back(target); }
|
||||
SymbolKind getKind() const { return Kind; }
|
||||
StringRef getName() const { return Name; }
|
||||
ArchitectureSet getArchitectures() const { return Architectures; }
|
||||
void addArchitectures(ArchitectureSet Archs) { Architectures |= Archs; }
|
||||
ArchitectureSet getArchitectures() const {
|
||||
return mapToArchitectureSet(Targets);
|
||||
}
|
||||
SymbolFlags getFlags() const { return Flags; }
|
||||
|
||||
bool isWeakDefined() const {
|
||||
@ -78,6 +81,17 @@ public:
|
||||
return (Flags & SymbolFlags::Undefined) == SymbolFlags::Undefined;
|
||||
}
|
||||
|
||||
using const_target_iterator = TargetList::const_iterator;
|
||||
using const_target_range = llvm::iterator_range<const_target_iterator>;
|
||||
const_target_range targets() const { return {Targets}; }
|
||||
|
||||
using const_filtered_target_iterator =
|
||||
llvm::filter_iterator<const_target_iterator,
|
||||
std::function<bool(const Target &)>>;
|
||||
using const_filtered_target_range =
|
||||
llvm::iterator_range<const_filtered_target_iterator>;
|
||||
const_filtered_target_range targets(ArchitectureSet architectures) const;
|
||||
|
||||
#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
|
||||
void dump(raw_ostream &OS) const;
|
||||
void dump() const { dump(llvm::errs()); }
|
||||
@ -85,7 +99,7 @@ public:
|
||||
|
||||
private:
|
||||
StringRef Name;
|
||||
ArchitectureSet Architectures;
|
||||
TargetList Targets;
|
||||
SymbolKind Kind;
|
||||
SymbolFlags Flags;
|
||||
};
|
||||
|
66
include/llvm/TextAPI/MachO/Target.h
Normal file
66
include/llvm/TextAPI/MachO/Target.h
Normal file
@ -0,0 +1,66 @@
|
||||
//===- llvm/TextAPI/Target.h - TAPI Target ----------------------*- C++ -*-===//
|
||||
//
|
||||
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
||||
// See https://llvm.org/LICENSE.txt for license information.
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_TEXTAPI_MACHO_TARGET_H
|
||||
#define LLVM_TEXTAPI_MACHO_TARGET_H
|
||||
|
||||
#include "llvm/ADT/Triple.h"
|
||||
#include "llvm/Support/Error.h"
|
||||
#include "llvm/TextAPI/MachO/Architecture.h"
|
||||
#include "llvm/TextAPI/MachO/ArchitectureSet.h"
|
||||
#include "llvm/TextAPI/MachO/Platform.h"
|
||||
|
||||
namespace llvm {
|
||||
namespace MachO {
|
||||
|
||||
// This is similar to a llvm Triple, but the triple doesn't have all the
|
||||
// information we need. For example there is no enum value for x86_64h. The
|
||||
// only way to get that information is to parse the triple string.
|
||||
class Target {
|
||||
public:
|
||||
Target() = default;
|
||||
Target(Architecture Arch, PlatformKind Platform)
|
||||
: Arch(Arch), Platform(Platform) {}
|
||||
explicit Target(const llvm::Triple &Triple)
|
||||
: Arch(mapToArchitecture(Triple)), Platform(mapToPlatformKind(Triple)) {}
|
||||
|
||||
operator std::string() const;
|
||||
|
||||
Architecture Arch;
|
||||
PlatformKind Platform;
|
||||
};
|
||||
|
||||
inline bool operator==(const Target &LHS, const Target &RHS) {
|
||||
return std::tie(LHS.Arch, LHS.Platform) == std::tie(RHS.Arch, RHS.Platform);
|
||||
}
|
||||
|
||||
inline bool operator!=(const Target &LHS, const Target &RHS) {
|
||||
return std::tie(LHS.Arch, LHS.Platform) != std::tie(RHS.Arch, RHS.Platform);
|
||||
}
|
||||
|
||||
inline bool operator<(const Target &LHS, const Target &RHS) {
|
||||
return std::tie(LHS.Arch, LHS.Platform) < std::tie(RHS.Arch, RHS.Platform);
|
||||
}
|
||||
|
||||
inline bool operator==(const Target &LHS, const Architecture &RHS) {
|
||||
return LHS.Arch == RHS;
|
||||
}
|
||||
|
||||
inline bool operator!=(const Target &LHS, const Architecture &RHS) {
|
||||
return LHS.Arch != RHS;
|
||||
}
|
||||
|
||||
PlatformSet mapToPlatformSet(ArrayRef<Target> Targets);
|
||||
ArchitectureSet mapToArchitectureSet(ArrayRef<Target> Targets);
|
||||
|
||||
raw_ostream &operator<<(raw_ostream &OS, const Target &Target);
|
||||
|
||||
} // namespace MachO
|
||||
} // namespace llvm
|
||||
|
||||
#endif // LLVM_TEXTAPI_MACHO_TARGET_H
|
@ -45,13 +45,13 @@ TapiFile::TapiFile(MemoryBufferRef Source, const InterfaceFile &interface,
|
||||
if (!Symbol->getArchitectures().has(Arch))
|
||||
continue;
|
||||
|
||||
auto Platform = interface.getPlatform();
|
||||
switch (Symbol->getKind()) {
|
||||
case SymbolKind::GlobalSymbol:
|
||||
Symbols.emplace_back(StringRef(), Symbol->getName(), getFlags(Symbol));
|
||||
break;
|
||||
case SymbolKind::ObjectiveCClass:
|
||||
if (Platform == PlatformKind::macOS && Arch == AK_i386) {
|
||||
if (interface.getPlatforms().count(PlatformKind::macOS) &&
|
||||
Arch == AK_i386) {
|
||||
Symbols.emplace_back(ObjC1ClassNamePrefix, Symbol->getName(),
|
||||
getFlags(Symbol));
|
||||
} else {
|
||||
|
@ -5,7 +5,9 @@ add_llvm_library(LLVMTextAPI
|
||||
MachO/ArchitectureSet.cpp
|
||||
MachO/InterfaceFile.cpp
|
||||
MachO/PackedVersion.cpp
|
||||
MachO/Platform.cpp
|
||||
MachO/Symbol.cpp
|
||||
MachO/Target.cpp
|
||||
MachO/TextStub.cpp
|
||||
MachO/TextStubCommon.cpp
|
||||
|
||||
|
@ -68,6 +68,10 @@ std::pair<uint32_t, uint32_t> getCPUTypeFromArchitecture(Architecture Arch) {
|
||||
return std::make_pair(0, 0);
|
||||
}
|
||||
|
||||
Architecture mapToArchitecture(const Triple &Target) {
|
||||
return getArchitectureFromName(Target.getArchName());
|
||||
}
|
||||
|
||||
raw_ostream &operator<<(raw_ostream &OS, Architecture Arch) {
|
||||
OS << getArchitectureName(Arch);
|
||||
return OS;
|
||||
|
@ -27,36 +27,65 @@ typename C::iterator addEntry(C &Container, StringRef InstallName) {
|
||||
|
||||
return Container.emplace(I, InstallName);
|
||||
}
|
||||
|
||||
template <typename C>
|
||||
typename C::iterator addEntry(C &Container, const Target &Target_) {
|
||||
auto Iter =
|
||||
lower_bound(Container, Target_, [](const Target &LHS, const Target &RHS) {
|
||||
return LHS < RHS;
|
||||
});
|
||||
if ((Iter != std::end(Container)) && !(Target_ < *Iter))
|
||||
return Iter;
|
||||
|
||||
return Container.insert(Iter, Target_);
|
||||
}
|
||||
} // end namespace detail.
|
||||
|
||||
void InterfaceFile::addAllowableClient(StringRef Name,
|
||||
ArchitectureSet Architectures) {
|
||||
auto Client = detail::addEntry(AllowableClients, Name);
|
||||
Client->addArchitectures(Architectures);
|
||||
void InterfaceFileRef::addTarget(const Target &Target) {
|
||||
detail::addEntry(Targets, Target);
|
||||
}
|
||||
|
||||
void InterfaceFile::addAllowableClient(StringRef InstallName,
|
||||
const Target &Target) {
|
||||
auto Client = detail::addEntry(AllowableClients, InstallName);
|
||||
Client->addTarget(Target);
|
||||
}
|
||||
|
||||
void InterfaceFile::addReexportedLibrary(StringRef InstallName,
|
||||
ArchitectureSet Architectures) {
|
||||
const Target &Target) {
|
||||
auto Lib = detail::addEntry(ReexportedLibraries, InstallName);
|
||||
Lib->addArchitectures(Architectures);
|
||||
Lib->addTarget(Target);
|
||||
}
|
||||
|
||||
void InterfaceFile::addUUID(Architecture Arch, StringRef UUID) {
|
||||
auto I = partition_point(UUIDs,
|
||||
[=](const std::pair<Architecture, std::string> &O) {
|
||||
return O.first < Arch;
|
||||
});
|
||||
void InterfaceFile::addParentUmbrella(const Target &Target_, StringRef Parent) {
|
||||
auto Iter = lower_bound(ParentUmbrellas, Target_,
|
||||
[](const std::pair<Target, std::string> &LHS,
|
||||
Target RHS) { return LHS.first < RHS; });
|
||||
|
||||
if (I != UUIDs.end() && Arch == I->first) {
|
||||
I->second = UUID;
|
||||
if ((Iter != ParentUmbrellas.end()) && !(Target_ < Iter->first)) {
|
||||
Iter->second = Parent;
|
||||
return;
|
||||
}
|
||||
|
||||
UUIDs.emplace(I, Arch, UUID);
|
||||
ParentUmbrellas.emplace(Iter, Target_, Parent);
|
||||
return;
|
||||
}
|
||||
|
||||
void InterfaceFile::addUUID(Architecture Arch, uint8_t UUID[16]) {
|
||||
void InterfaceFile::addUUID(const Target &Target_, StringRef UUID) {
|
||||
auto Iter = lower_bound(UUIDs, Target_,
|
||||
[](const std::pair<Target, std::string> &LHS,
|
||||
Target RHS) { return LHS.first < RHS; });
|
||||
|
||||
if ((Iter != UUIDs.end()) && !(Target_ < Iter->first)) {
|
||||
Iter->second = UUID;
|
||||
return;
|
||||
}
|
||||
|
||||
UUIDs.emplace(Iter, Target_, UUID);
|
||||
return;
|
||||
}
|
||||
|
||||
void InterfaceFile::addUUID(const Target &Target, uint8_t UUID[16]) {
|
||||
std::stringstream Stream;
|
||||
for (unsigned i = 0; i < 16; ++i) {
|
||||
if (i == 4 || i == 6 || i == 8 || i == 10)
|
||||
@ -64,17 +93,30 @@ void InterfaceFile::addUUID(Architecture Arch, uint8_t UUID[16]) {
|
||||
Stream << std::setfill('0') << std::setw(2) << std::uppercase << std::hex
|
||||
<< static_cast<int>(UUID[i]);
|
||||
}
|
||||
addUUID(Arch, Stream.str());
|
||||
addUUID(Target, Stream.str());
|
||||
}
|
||||
|
||||
void InterfaceFile::addTarget(const Target &Target) {
|
||||
detail::addEntry(Targets, Target);
|
||||
}
|
||||
|
||||
InterfaceFile::const_filtered_target_range
|
||||
InterfaceFile::targets(ArchitectureSet Archs) const {
|
||||
std::function<bool(const Target &)> fn = [Archs](const Target &Target_) {
|
||||
return Archs.has(Target_.Arch);
|
||||
};
|
||||
return make_filter_range(Targets, fn);
|
||||
}
|
||||
|
||||
void InterfaceFile::addSymbol(SymbolKind Kind, StringRef Name,
|
||||
ArchitectureSet Archs, SymbolFlags Flags) {
|
||||
const TargetList &Targets, SymbolFlags Flags) {
|
||||
Name = copyString(Name);
|
||||
auto result = Symbols.try_emplace(SymbolsMapKey{Kind, Name}, nullptr);
|
||||
if (result.second)
|
||||
result.first->second = new (Allocator) Symbol{Kind, Name, Archs, Flags};
|
||||
result.first->second = new (Allocator) Symbol{Kind, Name, Targets, Flags};
|
||||
else
|
||||
result.first->second->addArchitectures(Archs);
|
||||
for (const auto &Target : Targets)
|
||||
result.first->second->addTarget(Target);
|
||||
}
|
||||
|
||||
} // end namespace MachO.
|
||||
|
61
lib/TextAPI/MachO/Platform.cpp
Normal file
61
lib/TextAPI/MachO/Platform.cpp
Normal file
@ -0,0 +1,61 @@
|
||||
//===- llvm/TextAPI/MachO/Platform.cpp - Platform ---------------*- C++ -*-===//
|
||||
//
|
||||
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
||||
// See https://llvm.org/LICENSE.txt for license information.
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// Implementations of Platform Helper functions.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/ADT/ArrayRef.h"
|
||||
#include "llvm/ADT/Triple.h"
|
||||
#include "llvm/TextAPI/MachO/Platform.h"
|
||||
|
||||
namespace llvm {
|
||||
namespace MachO {
|
||||
|
||||
PlatformKind mapToPlatformKind(const Triple &Target) {
|
||||
switch (Target.getOS()) {
|
||||
default:
|
||||
return PlatformKind::unknown;
|
||||
case Triple::MacOSX:
|
||||
return PlatformKind::macOS;
|
||||
case Triple::IOS:
|
||||
return PlatformKind::iOS;
|
||||
case Triple::TvOS:
|
||||
return PlatformKind::tvOS;
|
||||
case Triple::WatchOS:
|
||||
return PlatformKind::watchOS;
|
||||
// TODO: add bridgeOS once in llvm::Triple
|
||||
}
|
||||
}
|
||||
|
||||
PlatformSet mapToPlatformSet(ArrayRef<Triple> Targets) {
|
||||
PlatformSet Result;
|
||||
for (const auto &Target : Targets)
|
||||
Result.insert(mapToPlatformKind(Target));
|
||||
return Result;
|
||||
}
|
||||
|
||||
StringRef getPlatformName(PlatformKind Platform) {
|
||||
switch (Platform) {
|
||||
case PlatformKind::unknown:
|
||||
return "unknown";
|
||||
case PlatformKind::macOS:
|
||||
return "macOS";
|
||||
case PlatformKind::iOS:
|
||||
return "iOS";
|
||||
case PlatformKind::tvOS:
|
||||
return "tvOS";
|
||||
case PlatformKind::watchOS:
|
||||
return "watchOS";
|
||||
case PlatformKind::bridgeOS:
|
||||
return "bridgeOS";
|
||||
}
|
||||
}
|
||||
|
||||
} // end namespace MachO.
|
||||
} // end namespace llvm.
|
@ -45,5 +45,14 @@ LLVM_DUMP_METHOD void Symbol::dump(raw_ostream &OS) const {
|
||||
}
|
||||
#endif
|
||||
|
||||
Symbol::const_filtered_target_range
|
||||
Symbol::targets(ArchitectureSet Architectures) const {
|
||||
std::function<bool(const Target &)> FN =
|
||||
[Architectures](const Target &Target) {
|
||||
return Architectures.has(Target.Arch);
|
||||
};
|
||||
return make_filter_range(Targets, FN);
|
||||
}
|
||||
|
||||
} // end namespace MachO.
|
||||
} // end namespace llvm.
|
||||
|
45
lib/TextAPI/MachO/Target.cpp
Normal file
45
lib/TextAPI/MachO/Target.cpp
Normal file
@ -0,0 +1,45 @@
|
||||
//===- tapi/Core/Target.cpp - Target ----------------------------*- C++ -*-===//
|
||||
//
|
||||
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
||||
// See https://llvm.org/LICENSE.txt for license information.
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/ADT/SmallString.h"
|
||||
#include "llvm/ADT/SmallVector.h"
|
||||
#include "llvm/ADT/StringExtras.h"
|
||||
#include "llvm/ADT/StringSwitch.h"
|
||||
#include "llvm/Support/Format.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include "llvm/TextAPI/MachO/Target.h"
|
||||
|
||||
namespace llvm {
|
||||
namespace MachO {
|
||||
|
||||
Target::operator std::string() const {
|
||||
return (getArchitectureName(Arch) + " (" + getPlatformName(Platform) + ")")
|
||||
.str();
|
||||
}
|
||||
|
||||
raw_ostream &operator<<(raw_ostream &OS, const Target &Target) {
|
||||
OS << std::string(Target);
|
||||
return OS;
|
||||
}
|
||||
|
||||
PlatformSet mapToPlatformSet(ArrayRef<Target> Targets) {
|
||||
PlatformSet Result;
|
||||
for (const auto &Target : Targets)
|
||||
Result.insert(Target.Platform);
|
||||
return Result;
|
||||
}
|
||||
|
||||
ArchitectureSet mapToArchitectureSet(ArrayRef<Target> Targets) {
|
||||
ArchitectureSet Result;
|
||||
for (const auto &Target : Targets)
|
||||
Result.set(Target.Arch);
|
||||
return Result;
|
||||
}
|
||||
|
||||
} // end namespace MachO.
|
||||
} // end namespace llvm.
|
@ -246,7 +246,7 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
NormalizedTBD(IO &IO, const InterfaceFile *&File) {
|
||||
Architectures = File->getArchitectures();
|
||||
UUIDs = File->uuids();
|
||||
Platform = File->getPlatform();
|
||||
Platforms = File->getPlatforms();
|
||||
InstallName = File->getInstallName();
|
||||
CurrentVersion = PackedVersion(File->getCurrentVersion());
|
||||
CompatibilityVersion = PackedVersion(File->getCompatibilityVersion());
|
||||
@ -263,7 +263,10 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
if (File->isInstallAPI())
|
||||
Flags |= TBDFlags::InstallAPI;
|
||||
|
||||
ParentUmbrella = File->getParentUmbrella();
|
||||
for (const auto &Iter : File->umbrellas()) {
|
||||
ParentUmbrella = Iter.second;
|
||||
break;
|
||||
}
|
||||
|
||||
std::set<ArchitectureSet> ArchSet;
|
||||
for (const auto &Library : File->allowableClients())
|
||||
@ -396,6 +399,17 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
}
|
||||
}
|
||||
|
||||
TargetList synthesizeTargets(ArchitectureSet Architectures,
|
||||
const PlatformSet &Platforms) {
|
||||
TargetList Targets;
|
||||
|
||||
for (auto Platform : Platforms) {
|
||||
for (const auto &&Architecture : Architectures)
|
||||
Targets.emplace_back(Architecture, Platform);
|
||||
}
|
||||
return Targets;
|
||||
}
|
||||
|
||||
const InterfaceFile *denormalize(IO &IO) {
|
||||
auto Ctx = reinterpret_cast<TextAPIContext *>(IO.getContext());
|
||||
assert(Ctx);
|
||||
@ -403,16 +417,16 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
auto *File = new InterfaceFile;
|
||||
File->setPath(Ctx->Path);
|
||||
File->setFileType(Ctx->FileKind);
|
||||
File->addTargets(synthesizeTargets(Architectures, Platforms));
|
||||
for (auto &ID : UUIDs)
|
||||
File->addUUID(ID.first, ID.second);
|
||||
File->setPlatform(Platform);
|
||||
File->setArchitectures(Architectures);
|
||||
File->setInstallName(InstallName);
|
||||
File->setCurrentVersion(CurrentVersion);
|
||||
File->setCompatibilityVersion(CompatibilityVersion);
|
||||
File->setSwiftABIVersion(SwiftABIVersion);
|
||||
File->setObjCConstraint(ObjCConstraint);
|
||||
File->setParentUmbrella(ParentUmbrella);
|
||||
for (const auto &Target : File->targets())
|
||||
File->addParentUmbrella(Target, ParentUmbrella);
|
||||
|
||||
if (Ctx->FileKind == FileType::TBD_V1) {
|
||||
File->setTwoLevelNamespace();
|
||||
@ -425,76 +439,80 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
}
|
||||
|
||||
for (const auto &Section : Exports) {
|
||||
for (const auto &Library : Section.AllowableClients)
|
||||
File->addAllowableClient(Library, Section.Architectures);
|
||||
for (const auto &Library : Section.ReexportedLibraries)
|
||||
File->addReexportedLibrary(Library, Section.Architectures);
|
||||
const auto Targets =
|
||||
synthesizeTargets(Section.Architectures, Platforms);
|
||||
|
||||
for (const auto &Lib : Section.AllowableClients)
|
||||
for (const auto &Target : Targets)
|
||||
File->addAllowableClient(Lib, Target);
|
||||
|
||||
for (const auto &Lib : Section.ReexportedLibraries)
|
||||
for (const auto &Target : Targets)
|
||||
File->addReexportedLibrary(Lib, Target);
|
||||
|
||||
for (const auto &Symbol : Section.Symbols) {
|
||||
if (Ctx->FileKind != FileType::TBD_V3 &&
|
||||
Symbol.value.startswith("_OBJC_EHTYPE_$_"))
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType,
|
||||
Symbol.value.drop_front(15), Section.Architectures);
|
||||
Symbol.value.drop_front(15), Targets);
|
||||
else
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol,
|
||||
Section.Architectures);
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol, Targets);
|
||||
}
|
||||
for (auto &Symbol : Section.Classes) {
|
||||
auto Name = Symbol.value;
|
||||
if (Ctx->FileKind != FileType::TBD_V3)
|
||||
Name = Name.drop_front();
|
||||
File->addSymbol(SymbolKind::ObjectiveCClass, Name,
|
||||
Section.Architectures);
|
||||
File->addSymbol(SymbolKind::ObjectiveCClass, Name, Targets);
|
||||
}
|
||||
for (auto &Symbol : Section.ClassEHs)
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType, Symbol,
|
||||
Section.Architectures);
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType, Symbol, Targets);
|
||||
for (auto &Symbol : Section.IVars) {
|
||||
auto Name = Symbol.value;
|
||||
if (Ctx->FileKind != FileType::TBD_V3)
|
||||
Name = Name.drop_front();
|
||||
File->addSymbol(SymbolKind::ObjectiveCInstanceVariable, Name,
|
||||
Section.Architectures);
|
||||
Targets);
|
||||
}
|
||||
for (auto &Symbol : Section.WeakDefSymbols)
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol,
|
||||
Section.Architectures, SymbolFlags::WeakDefined);
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol, Targets,
|
||||
SymbolFlags::WeakDefined);
|
||||
for (auto &Symbol : Section.TLVSymbols)
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol,
|
||||
Section.Architectures, SymbolFlags::ThreadLocalValue);
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol, Targets,
|
||||
SymbolFlags::ThreadLocalValue);
|
||||
}
|
||||
|
||||
for (const auto &Section : Undefineds) {
|
||||
const auto Targets =
|
||||
synthesizeTargets(Section.Architectures, Platforms);
|
||||
for (auto &Symbol : Section.Symbols) {
|
||||
if (Ctx->FileKind != FileType::TBD_V3 &&
|
||||
Symbol.value.startswith("_OBJC_EHTYPE_$_"))
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType,
|
||||
Symbol.value.drop_front(15), Section.Architectures,
|
||||
Symbol.value.drop_front(15), Targets,
|
||||
SymbolFlags::Undefined);
|
||||
else
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol,
|
||||
Section.Architectures, SymbolFlags::Undefined);
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol, Targets,
|
||||
SymbolFlags::Undefined);
|
||||
}
|
||||
for (auto &Symbol : Section.Classes) {
|
||||
auto Name = Symbol.value;
|
||||
if (Ctx->FileKind != FileType::TBD_V3)
|
||||
Name = Name.drop_front();
|
||||
File->addSymbol(SymbolKind::ObjectiveCClass, Name,
|
||||
Section.Architectures, SymbolFlags::Undefined);
|
||||
File->addSymbol(SymbolKind::ObjectiveCClass, Name, Targets,
|
||||
SymbolFlags::Undefined);
|
||||
}
|
||||
for (auto &Symbol : Section.ClassEHs)
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType, Symbol,
|
||||
Section.Architectures, SymbolFlags::Undefined);
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType, Symbol, Targets,
|
||||
SymbolFlags::Undefined);
|
||||
for (auto &Symbol : Section.IVars) {
|
||||
auto Name = Symbol.value;
|
||||
if (Ctx->FileKind != FileType::TBD_V3)
|
||||
Name = Name.drop_front();
|
||||
File->addSymbol(SymbolKind::ObjectiveCInstanceVariable, Name,
|
||||
Section.Architectures, SymbolFlags::Undefined);
|
||||
File->addSymbol(SymbolKind::ObjectiveCInstanceVariable, Name, Targets,
|
||||
SymbolFlags::Undefined);
|
||||
}
|
||||
for (auto &Symbol : Section.WeakRefSymbols)
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol,
|
||||
Section.Architectures,
|
||||
File->addSymbol(SymbolKind::GlobalSymbol, Symbol, Targets,
|
||||
SymbolFlags::Undefined | SymbolFlags::WeakReferenced);
|
||||
}
|
||||
|
||||
@ -513,7 +531,7 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
|
||||
std::vector<Architecture> Architectures;
|
||||
std::vector<UUID> UUIDs;
|
||||
PlatformKind Platform{PlatformKind::unknown};
|
||||
PlatformSet Platforms;
|
||||
StringRef InstallName;
|
||||
PackedVersion CurrentVersion;
|
||||
PackedVersion CompatibilityVersion;
|
||||
@ -567,7 +585,7 @@ template <> struct MappingTraits<const InterfaceFile *> {
|
||||
IO.mapRequired("archs", Keys->Architectures);
|
||||
if (Ctx->FileKind != FileType::TBD_V1)
|
||||
IO.mapOptional("uuids", Keys->UUIDs);
|
||||
IO.mapRequired("platform", Keys->Platform);
|
||||
IO.mapRequired("platform", Keys->Platforms);
|
||||
if (Ctx->FileKind != FileType::TBD_V1)
|
||||
IO.mapOptional("flags", Keys->Flags, TBDFlags::None);
|
||||
IO.mapRequired("install-name", Keys->InstallName);
|
||||
|
@ -41,9 +41,10 @@ void ScalarEnumerationTraits<ObjCConstraintType>::enumeration(
|
||||
IO.enumCase(Constraint, "gc", ObjCConstraintType::GC);
|
||||
}
|
||||
|
||||
void ScalarTraits<PlatformKind>::output(const PlatformKind &Value, void *,
|
||||
raw_ostream &OS) {
|
||||
switch (Value) {
|
||||
void ScalarTraits<PlatformSet>::output(const PlatformSet &Values, void *IO,
|
||||
raw_ostream &OS) {
|
||||
assert(Values.size() == 1U);
|
||||
switch (*Values.begin()) {
|
||||
default:
|
||||
llvm_unreachable("unexpected platform");
|
||||
break;
|
||||
@ -64,21 +65,26 @@ void ScalarTraits<PlatformKind>::output(const PlatformKind &Value, void *,
|
||||
break;
|
||||
}
|
||||
}
|
||||
StringRef ScalarTraits<PlatformKind>::input(StringRef Scalar, void *,
|
||||
PlatformKind &Value) {
|
||||
Value = StringSwitch<PlatformKind>(Scalar)
|
||||
.Case("macosx", PlatformKind::macOS)
|
||||
.Case("ios", PlatformKind::iOS)
|
||||
.Case("watchos", PlatformKind::watchOS)
|
||||
.Case("tvos", PlatformKind::tvOS)
|
||||
.Case("bridgeos", PlatformKind::bridgeOS)
|
||||
.Default(PlatformKind::unknown);
|
||||
|
||||
if (Value == PlatformKind::unknown)
|
||||
StringRef ScalarTraits<PlatformSet>::input(StringRef Scalar, void *IO,
|
||||
PlatformSet &Values) {
|
||||
auto Platform = StringSwitch<PlatformKind>(Scalar)
|
||||
.Case("unknown", PlatformKind::unknown)
|
||||
.Case("macosx", PlatformKind::macOS)
|
||||
.Case("ios", PlatformKind::iOS)
|
||||
.Case("watchos", PlatformKind::watchOS)
|
||||
.Case("tvos", PlatformKind::tvOS)
|
||||
.Case("bridgeos", PlatformKind::bridgeOS)
|
||||
.Default(PlatformKind::unknown);
|
||||
|
||||
if (Platform == PlatformKind::unknown)
|
||||
return "unknown platform";
|
||||
|
||||
Values.insert(Platform);
|
||||
return {};
|
||||
}
|
||||
QuotingType ScalarTraits<PlatformKind>::mustQuote(StringRef) {
|
||||
|
||||
QuotingType ScalarTraits<PlatformSet>::mustQuote(StringRef) {
|
||||
return QuotingType::None;
|
||||
}
|
||||
|
||||
@ -166,10 +172,11 @@ StringRef ScalarTraits<UUID>::input(StringRef Scalar, void *, UUID &Value) {
|
||||
auto UUID = Split.second.trim();
|
||||
if (UUID.empty())
|
||||
return "invalid uuid string pair";
|
||||
Value.first = getArchitectureFromName(Arch);
|
||||
Value.second = UUID;
|
||||
Value.first = Target{getArchitectureFromName(Arch), PlatformKind::unknown};
|
||||
return {};
|
||||
}
|
||||
|
||||
QuotingType ScalarTraits<UUID>::mustQuote(StringRef) {
|
||||
return QuotingType::Single;
|
||||
}
|
||||
|
@ -21,7 +21,7 @@
|
||||
#include "llvm/TextAPI/MachO/InterfaceFile.h"
|
||||
#include "llvm/TextAPI/MachO/PackedVersion.h"
|
||||
|
||||
using UUID = std::pair<llvm::MachO::Architecture, std::string>;
|
||||
using UUID = std::pair<llvm::MachO::Target, std::string>;
|
||||
|
||||
LLVM_YAML_STRONG_TYPEDEF(llvm::StringRef, FlowStringRef)
|
||||
LLVM_YAML_STRONG_TYPEDEF(uint8_t, SwiftVersion)
|
||||
@ -41,9 +41,9 @@ template <> struct ScalarEnumerationTraits<MachO::ObjCConstraintType> {
|
||||
static void enumeration(IO &, MachO::ObjCConstraintType &);
|
||||
};
|
||||
|
||||
template <> struct ScalarTraits<MachO::PlatformKind> {
|
||||
static void output(const MachO::PlatformKind &, void *, raw_ostream &);
|
||||
static StringRef input(StringRef, void *, MachO::PlatformKind &);
|
||||
template <> struct ScalarTraits<MachO::PlatformSet> {
|
||||
static void output(const MachO::PlatformSet &, void *, raw_ostream &);
|
||||
static StringRef input(StringRef, void *, MachO::PlatformSet &);
|
||||
static QuotingType mustQuote(StringRef);
|
||||
};
|
||||
|
||||
|
@ -220,21 +220,6 @@ static Expected<std::unique_ptr<IFSStub>> readInputFile(StringRef FilePath) {
|
||||
|
||||
int writeTbdStub(const llvm::Triple &T, const std::set<IFSSymbol> &Symbols,
|
||||
const StringRef Format, raw_ostream &Out) {
|
||||
auto ArchOrError =
|
||||
[](const llvm::Triple &T) -> llvm::Expected<llvm::MachO::Architecture> {
|
||||
switch (T.getArch()) {
|
||||
default:
|
||||
return createStringError(errc::not_supported, "Invalid Architecture.\n");
|
||||
case llvm::Triple::ArchType::x86:
|
||||
return AK_i386;
|
||||
case llvm::Triple::ArchType::x86_64:
|
||||
return AK_x86_64;
|
||||
case llvm::Triple::ArchType::arm:
|
||||
return AK_armv7;
|
||||
case llvm::Triple::ArchType::aarch64:
|
||||
return AK_arm64;
|
||||
}
|
||||
}(T);
|
||||
|
||||
auto PlatformKindOrError =
|
||||
[](const llvm::Triple &T) -> llvm::Expected<llvm::MachO::PlatformKind> {
|
||||
@ -256,19 +241,15 @@ int writeTbdStub(const llvm::Triple &T, const std::set<IFSSymbol> &Symbols,
|
||||
return createStringError(errc::not_supported, "Invalid Platform.\n");
|
||||
}(T);
|
||||
|
||||
if (!ArchOrError)
|
||||
return -1;
|
||||
|
||||
if (!PlatformKindOrError)
|
||||
return -1;
|
||||
|
||||
Architecture Arch = ArchOrError.get();
|
||||
PlatformKind Plat = PlatformKindOrError.get();
|
||||
TargetList Targets({Target(llvm::MachO::mapToArchitecture(T), Plat)});
|
||||
|
||||
InterfaceFile File;
|
||||
File.setFileType(FileType::TBD_V3); // Only supporting v3 for now.
|
||||
File.setArchitectures(Arch);
|
||||
File.setPlatform(Plat);
|
||||
File.addTargets(Targets);
|
||||
|
||||
for (const auto &Symbol : Symbols) {
|
||||
auto Name = Symbol.Name;
|
||||
@ -286,9 +267,9 @@ int writeTbdStub(const llvm::Triple &T, const std::set<IFSSymbol> &Symbols,
|
||||
break;
|
||||
}
|
||||
if (Symbol.Weak)
|
||||
File.addSymbol(Kind, Name, Arch, SymbolFlags::WeakDefined);
|
||||
File.addSymbol(Kind, Name, Targets, SymbolFlags::WeakDefined);
|
||||
else
|
||||
File.addSymbol(Kind, Name, Arch);
|
||||
File.addSymbol(Kind, Name, Targets);
|
||||
}
|
||||
|
||||
SmallString<4096> Buffer;
|
||||
|
@ -87,8 +87,13 @@ TEST(TBDv1, ReadFile) {
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
auto Archs = AK_armv7 | AK_armv7s | AK_armv7k | AK_arm64;
|
||||
auto Platform = PlatformKind::iOS;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : Archs)
|
||||
Targets.emplace_back(Target(arch, Platform));
|
||||
EXPECT_EQ(Archs, File->getArchitectures());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
EXPECT_EQ(std::string("Test.dylib"), File->getInstallName());
|
||||
EXPECT_EQ(PackedVersion(2, 3, 4), File->getCurrentVersion());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCompatibilityVersion());
|
||||
@ -97,8 +102,8 @@ TEST(TBDv1, ReadFile) {
|
||||
EXPECT_TRUE(File->isTwoLevelNamespace());
|
||||
EXPECT_TRUE(File->isApplicationExtensionSafe());
|
||||
EXPECT_FALSE(File->isInstallAPI());
|
||||
InterfaceFileRef client("clientA", Archs);
|
||||
InterfaceFileRef reexport("/usr/lib/libfoo.dylib", Archs);
|
||||
InterfaceFileRef client("clientA", Targets);
|
||||
InterfaceFileRef reexport("/usr/lib/libfoo.dylib", Targets);
|
||||
EXPECT_EQ(1U, File->allowableClients().size());
|
||||
EXPECT_EQ(client, File->allowableClients().front());
|
||||
EXPECT_EQ(1U, File->reexportedLibraries().size());
|
||||
@ -117,6 +122,10 @@ TEST(TBDv1, ReadFile) {
|
||||
EXPECT_EQ(sizeof(TBDv1Symbols) / sizeof(ExportedSymbol), Exports.size());
|
||||
EXPECT_TRUE(
|
||||
std::equal(Exports.begin(), Exports.end(), std::begin(TBDv1Symbols)));
|
||||
|
||||
File->addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", {Targets[1]});
|
||||
File->addSymbol(SymbolKind::ObjectiveCInstanceVariable, "Class1._ivar1",
|
||||
{Targets[1]});
|
||||
}
|
||||
|
||||
TEST(TBDv1, ReadFile2) {
|
||||
@ -131,8 +140,13 @@ TEST(TBDv1, ReadFile2) {
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
auto Archs = AK_armv7 | AK_armv7s | AK_armv7k | AK_arm64;
|
||||
auto Platform = PlatformKind::iOS;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : Archs)
|
||||
Targets.emplace_back(Target(arch, Platform));
|
||||
EXPECT_EQ(Archs, File->getArchitectures());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
EXPECT_EQ(std::string("Test.dylib"), File->getInstallName());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCurrentVersion());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCompatibilityVersion());
|
||||
@ -169,25 +183,27 @@ TEST(TBDv1, WriteFile) {
|
||||
"...\n";
|
||||
|
||||
InterfaceFile File;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : AK_i386 | AK_x86_64)
|
||||
Targets.emplace_back(Target(arch, PlatformKind::macOS));
|
||||
File.setPath("libfoo.dylib");
|
||||
File.setInstallName("/usr/lib/libfoo.dylib");
|
||||
File.setFileType(FileType::TBD_V1);
|
||||
File.setArchitectures(AK_i386 | AK_x86_64);
|
||||
File.setPlatform(PlatformKind::macOS);
|
||||
File.addTargets(Targets);
|
||||
File.setCurrentVersion(PackedVersion(1, 2, 3));
|
||||
File.setSwiftABIVersion(5);
|
||||
File.setObjCConstraint(ObjCConstraintType::Retain_Release);
|
||||
File.addAllowableClient("clientA", AK_x86_64);
|
||||
File.addReexportedLibrary("/usr/lib/libfoo.dylib", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym1", AK_i386);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym2", AK_i386,
|
||||
File.addAllowableClient("clientA", Targets[1]);
|
||||
File.addReexportedLibrary("/usr/lib/libfoo.dylib", Targets[1]);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym1", {Targets[0]});
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym2", {Targets[0]},
|
||||
SymbolFlags::WeakDefined);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym3", AK_i386,
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym3", {Targets[0]},
|
||||
SymbolFlags::ThreadLocalValue);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClass, "Class1", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClass, "Class1", {Targets[1]});
|
||||
File.addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", {Targets[1]});
|
||||
File.addSymbol(SymbolKind::ObjectiveCInstanceVariable, "Class1._ivar1",
|
||||
AK_x86_64);
|
||||
{Targets[1]});
|
||||
|
||||
SmallString<4096> Buffer;
|
||||
raw_svector_ostream OS(Buffer);
|
||||
@ -206,9 +222,11 @@ TEST(TBDv1, Platform_macOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_macos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::macOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::macOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv1, Platform_iOS) {
|
||||
@ -221,9 +239,11 @@ TEST(TBDv1, Platform_iOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_ios, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::iOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv1, Platform_watchOS) {
|
||||
@ -236,9 +256,11 @@ TEST(TBDv1, Platform_watchOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_watchos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::watchOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::watchOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv1, Platform_tvOS) {
|
||||
@ -251,9 +273,11 @@ TEST(TBDv1, Platform_tvOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_tvos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::tvOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::tvOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv1, Platform_bridgeOS) {
|
||||
@ -266,9 +290,11 @@ TEST(TBDv1, Platform_bridgeOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_bridgeos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::bridgeOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V1, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::bridgeOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv1, Swift_1_0) {
|
||||
|
@ -89,8 +89,13 @@ TEST(TBDv2, ReadFile) {
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
auto Archs = AK_armv7 | AK_armv7s | AK_armv7k | AK_arm64;
|
||||
auto Platform = PlatformKind::iOS;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : Archs)
|
||||
Targets.emplace_back(Target(arch, Platform));
|
||||
EXPECT_EQ(Archs, File->getArchitectures());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
EXPECT_EQ(std::string("Test.dylib"), File->getInstallName());
|
||||
EXPECT_EQ(PackedVersion(2, 3, 4), File->getCurrentVersion());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCompatibilityVersion());
|
||||
@ -99,8 +104,8 @@ TEST(TBDv2, ReadFile) {
|
||||
EXPECT_TRUE(File->isTwoLevelNamespace());
|
||||
EXPECT_TRUE(File->isApplicationExtensionSafe());
|
||||
EXPECT_TRUE(File->isInstallAPI());
|
||||
InterfaceFileRef client("clientA", Archs);
|
||||
InterfaceFileRef reexport("/usr/lib/libfoo.dylib", Archs);
|
||||
InterfaceFileRef client("clientA", Targets);
|
||||
InterfaceFileRef reexport("/usr/lib/libfoo.dylib", Targets);
|
||||
EXPECT_EQ(1U, File->allowableClients().size());
|
||||
EXPECT_EQ(client, File->allowableClients().front());
|
||||
EXPECT_EQ(1U, File->reexportedLibraries().size());
|
||||
@ -155,8 +160,13 @@ TEST(TBDv2, ReadFile2) {
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
auto Archs = AK_armv7 | AK_armv7s | AK_armv7k | AK_arm64;
|
||||
auto Platform = PlatformKind::iOS;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : Archs)
|
||||
Targets.emplace_back(Target(arch, Platform));
|
||||
EXPECT_EQ(Archs, File->getArchitectures());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
EXPECT_EQ(std::string("Test.dylib"), File->getInstallName());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCurrentVersion());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCompatibilityVersion());
|
||||
@ -192,27 +202,29 @@ TEST(TBDv2, WriteFile) {
|
||||
"...\n";
|
||||
|
||||
InterfaceFile File;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : AK_i386 | AK_x86_64)
|
||||
Targets.emplace_back(Target(arch, PlatformKind::macOS));
|
||||
File.setPath("libfoo.dylib");
|
||||
File.setInstallName("/usr/lib/libfoo.dylib");
|
||||
File.setFileType(FileType::TBD_V2);
|
||||
File.setArchitectures(AK_i386 | AK_x86_64);
|
||||
File.setPlatform(PlatformKind::macOS);
|
||||
File.addTargets(Targets);
|
||||
File.setCurrentVersion(PackedVersion(1, 2, 3));
|
||||
File.setTwoLevelNamespace();
|
||||
File.setApplicationExtensionSafe();
|
||||
File.setSwiftABIVersion(5);
|
||||
File.setObjCConstraint(ObjCConstraintType::Retain_Release);
|
||||
File.addAllowableClient("clientA", AK_x86_64);
|
||||
File.addReexportedLibrary("/usr/lib/libfoo.dylib", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym1", AK_i386);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym2", AK_i386,
|
||||
File.addAllowableClient("clientA", Targets[1]);
|
||||
File.addReexportedLibrary("/usr/lib/libfoo.dylib", Targets[1]);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym1", {Targets[0]});
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym2", {Targets[0]},
|
||||
SymbolFlags::WeakDefined);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym3", AK_i386,
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym3", {Targets[0]},
|
||||
SymbolFlags::ThreadLocalValue);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClass, "Class1", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClass, "Class1", {Targets[1]});
|
||||
File.addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", {Targets[1]});
|
||||
File.addSymbol(SymbolKind::ObjectiveCInstanceVariable, "Class1._ivar1",
|
||||
AK_x86_64);
|
||||
{Targets[1]});
|
||||
|
||||
SmallString<4096> Buffer;
|
||||
raw_svector_ostream OS(Buffer);
|
||||
@ -232,8 +244,10 @@ TEST(TBDv2, Platform_macOS) {
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_macos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto File = std::move(Result.get());
|
||||
auto Platform = PlatformKind::macOS;
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::macOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv2, Platform_iOS) {
|
||||
@ -246,9 +260,11 @@ TEST(TBDv2, Platform_iOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_ios, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::iOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv2, Platform_watchOS) {
|
||||
@ -261,9 +277,11 @@ TEST(TBDv2, Platform_watchOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_watchos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::watchOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::watchOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv2, Platform_tvOS) {
|
||||
@ -276,9 +294,11 @@ TEST(TBDv2, Platform_tvOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_tvos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::tvOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::tvOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv2, Platform_bridgeOS) {
|
||||
@ -291,9 +311,11 @@ TEST(TBDv2, Platform_bridgeOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_bridgeos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::bridgeOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V2, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::bridgeOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv2, Swift_1_0) {
|
||||
@ -415,7 +437,6 @@ TEST(TBDv2, UnknownArchitecture) {
|
||||
"platform: macosx\n"
|
||||
"install-name: Test.dylib\n"
|
||||
"...\n";
|
||||
|
||||
auto Result = TextAPIReader::get(
|
||||
MemoryBufferRef(tbd_v2_file_unknown_architecture, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
@ -423,9 +444,9 @@ TEST(TBDv2, UnknownArchitecture) {
|
||||
|
||||
TEST(TBDv2, UnknownPlatform) {
|
||||
static const char tbd_v2_file_unknown_platform[] = "--- !tapi-tbd-v2\n"
|
||||
"archs: [ i386 ]\n"
|
||||
"platform: newOS\n"
|
||||
"...\n";
|
||||
"archs: [ i386 ]\n"
|
||||
"platform: newOS\n"
|
||||
"...\n";
|
||||
|
||||
auto Result = TextAPIReader::get(
|
||||
MemoryBufferRef(tbd_v2_file_unknown_platform, "Test.tbd"));
|
||||
|
@ -23,7 +23,7 @@ struct ExportedSymbol {
|
||||
bool ThreadLocalValue;
|
||||
};
|
||||
using ExportedSymbolSeq = std::vector<ExportedSymbol>;
|
||||
using UUIDs = std::vector<std::pair<Architecture, std::string>>;
|
||||
using UUIDs = std::vector<std::pair<Target, std::string>>;
|
||||
|
||||
inline bool operator<(const ExportedSymbol &lhs, const ExportedSymbol &rhs) {
|
||||
return std::tie(lhs.Kind, lhs.Name) < std::tie(rhs.Kind, rhs.Name);
|
||||
@ -93,11 +93,18 @@ TEST(TBDv3, ReadFile) {
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V3, File->getFileType());
|
||||
auto Archs = AK_armv7 | AK_arm64;
|
||||
auto Platform = PlatformKind::iOS;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : Archs)
|
||||
Targets.emplace_back(Target(arch, Platform));
|
||||
EXPECT_EQ(Archs, File->getArchitectures());
|
||||
UUIDs uuids = {{AK_armv7, "00000000-0000-0000-0000-000000000000"},
|
||||
{AK_arm64, "11111111-1111-1111-1111-111111111111"}};
|
||||
EXPECT_EQ(uuids, File->uuids());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
UUIDs Uuids = {{Target(AK_armv7, PlatformKind::unknown),
|
||||
"00000000-0000-0000-0000-000000000000"},
|
||||
{Target(AK_arm64, PlatformKind::unknown),
|
||||
"11111111-1111-1111-1111-111111111111"}};
|
||||
EXPECT_EQ(Uuids, File->uuids());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
EXPECT_EQ(std::string("Test.dylib"), File->getInstallName());
|
||||
EXPECT_EQ(PackedVersion(2, 3, 4), File->getCurrentVersion());
|
||||
EXPECT_EQ(PackedVersion(1, 0, 0), File->getCompatibilityVersion());
|
||||
@ -106,8 +113,8 @@ TEST(TBDv3, ReadFile) {
|
||||
EXPECT_TRUE(File->isTwoLevelNamespace());
|
||||
EXPECT_TRUE(File->isApplicationExtensionSafe());
|
||||
EXPECT_TRUE(File->isInstallAPI());
|
||||
InterfaceFileRef client("clientA", Archs);
|
||||
InterfaceFileRef reexport("/usr/lib/libfoo.dylib", Archs);
|
||||
InterfaceFileRef client("clientA", Targets);
|
||||
InterfaceFileRef reexport("/usr/lib/libfoo.dylib", Targets);
|
||||
EXPECT_EQ(1U, File->allowableClients().size());
|
||||
EXPECT_EQ(client, File->allowableClients().front());
|
||||
EXPECT_EQ(1U, File->reexportedLibraries().size());
|
||||
@ -151,27 +158,29 @@ TEST(TBDv3, WriteFile) {
|
||||
"...\n";
|
||||
|
||||
InterfaceFile File;
|
||||
TargetList Targets;
|
||||
for (auto &&arch : AK_i386 | AK_x86_64)
|
||||
Targets.emplace_back(Target(arch, PlatformKind::macOS));
|
||||
File.setPath("libfoo.dylib");
|
||||
File.setInstallName("/usr/lib/libfoo.dylib");
|
||||
File.setFileType(FileType::TBD_V3);
|
||||
File.setArchitectures(AK_i386 | AK_x86_64);
|
||||
File.setPlatform(PlatformKind::macOS);
|
||||
File.addTargets(Targets);
|
||||
File.setCurrentVersion(PackedVersion(1, 2, 3));
|
||||
File.setTwoLevelNamespace();
|
||||
File.setApplicationExtensionSafe();
|
||||
File.setSwiftABIVersion(5);
|
||||
File.setObjCConstraint(ObjCConstraintType::Retain_Release);
|
||||
File.addAllowableClient("clientA", AK_x86_64);
|
||||
File.addReexportedLibrary("/usr/lib/libfoo.dylib", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym1", AK_i386);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym2", AK_i386,
|
||||
File.addAllowableClient("clientA", Targets[1]);
|
||||
File.addReexportedLibrary("/usr/lib/libfoo.dylib", Targets[1]);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym1", {Targets[0]});
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym2", {Targets[0]},
|
||||
SymbolFlags::WeakDefined);
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym3", AK_i386,
|
||||
File.addSymbol(SymbolKind::GlobalSymbol, "_sym3", {Targets[0]},
|
||||
SymbolFlags::ThreadLocalValue);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClass, "Class1", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", AK_x86_64);
|
||||
File.addSymbol(SymbolKind::ObjectiveCClass, "Class1", {Targets[1]});
|
||||
File.addSymbol(SymbolKind::ObjectiveCClassEHType, "Class1", {Targets[1]});
|
||||
File.addSymbol(SymbolKind::ObjectiveCInstanceVariable, "Class1._ivar1",
|
||||
AK_x86_64);
|
||||
{Targets[1]});
|
||||
|
||||
SmallString<4096> Buffer;
|
||||
raw_svector_ostream OS(Buffer);
|
||||
@ -190,9 +199,11 @@ TEST(TBDv3, Platform_macOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_macos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::macOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V3, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::macOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv3, Platform_iOS) {
|
||||
@ -205,9 +216,11 @@ TEST(TBDv3, Platform_iOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_ios, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::iOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V3, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::iOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv3, Platform_watchOS) {
|
||||
@ -220,9 +233,11 @@ TEST(TBDv3, Platform_watchOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_watchos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::watchOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V3, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::watchOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv3, Platform_tvOS) {
|
||||
@ -236,8 +251,10 @@ TEST(TBDv3, Platform_tvOS) {
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_tvos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto File = std::move(Result.get());
|
||||
auto Platform = PlatformKind::tvOS;
|
||||
EXPECT_EQ(FileType::TBD_V3, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::tvOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv3, Platform_bridgeOS) {
|
||||
@ -250,9 +267,11 @@ TEST(TBDv3, Platform_bridgeOS) {
|
||||
auto Result =
|
||||
TextAPIReader::get(MemoryBufferRef(tbd_v1_platform_bridgeos, "Test.tbd"));
|
||||
EXPECT_TRUE(!!Result);
|
||||
auto Platform = PlatformKind::bridgeOS;
|
||||
auto File = std::move(Result.get());
|
||||
EXPECT_EQ(FileType::TBD_V3, File->getFileType());
|
||||
EXPECT_EQ(PlatformKind::bridgeOS, File->getPlatform());
|
||||
EXPECT_EQ(File->getPlatforms().size(), 1U);
|
||||
EXPECT_EQ(Platform, *File->getPlatforms().begin());
|
||||
}
|
||||
|
||||
TEST(TBDv3, Swift_1_0) {
|
||||
|
Loading…
Reference in New Issue
Block a user