[lld][MachO] Refactor findCommand

Refactor findCommand to allow passing multiple types. NFC.

Test plan: make check-lld-macho

Differential revision: https://reviews.llvm.org/D100954
This commit is contained in:
Alexander Shaposhnikov
2021-04-21 08:18:20 -07:00
parent 55ee541653
commit b5720354ef
3 changed files with 26 additions and 22 deletions

View File

@@ -109,29 +109,31 @@ static Optional<PlatformInfo> getPlatformInfo(const InputFile *input) {
using Header = typename LP::mach_header;
auto *hdr = reinterpret_cast<const Header *>(input->mb.getBufferStart());
PlatformInfo platformInfo;
if (const auto *cmd =
findCommand<build_version_command>(hdr, LC_BUILD_VERSION)) {
platformInfo.target.Platform = static_cast<PlatformKind>(cmd->platform);
platformInfo.minimum = decodeVersion(cmd->minos);
return platformInfo;
} else if (const auto *cmd =
findCommand<version_min_command>(hdr, LC_VERSION_MIN_MACOSX)) {
platformInfo.target.Platform = PlatformKind::macOS;
platformInfo.minimum = decodeVersion(cmd->version);
return platformInfo;
} else if (const auto *cmd = findCommand<version_min_command>(
hdr, LC_VERSION_MIN_IPHONEOS)) {
platformInfo.target.Platform = PlatformKind::iOS;
platformInfo.minimum = decodeVersion(cmd->version);
return platformInfo;
} else if (const auto *cmd =
findCommand<version_min_command>(hdr, LC_VERSION_MIN_TVOS)) {
platformInfo.target.Platform = PlatformKind::tvOS;
platformInfo.minimum = decodeVersion(cmd->version);
} else if (const auto *cmd = findCommand<version_min_command>(
hdr, LC_VERSION_MIN_WATCHOS)) {
platformInfo.target.Platform = PlatformKind::watchOS;
}
if (const auto *cmd = findCommand<version_min_command>(
hdr, LC_VERSION_MIN_MACOSX, LC_VERSION_MIN_IPHONEOS,
LC_VERSION_MIN_TVOS, LC_VERSION_MIN_WATCHOS)) {
switch (cmd->cmd) {
case LC_VERSION_MIN_MACOSX:
platformInfo.target.Platform = PlatformKind::macOS;
break;
case LC_VERSION_MIN_IPHONEOS:
platformInfo.target.Platform = PlatformKind::iOS;
break;
case LC_VERSION_MIN_TVOS:
platformInfo.target.Platform = PlatformKind::tvOS;
break;
case LC_VERSION_MIN_WATCHOS:
platformInfo.target.Platform = PlatformKind::watchOS;
break;
}
platformInfo.minimum = decodeVersion(cmd->version);
return platformInfo;
}

View File

@@ -189,13 +189,15 @@ extern llvm::SetVector<InputFile *> inputFiles;
llvm::Optional<MemoryBufferRef> readFile(StringRef path);
template <class CommandType = llvm::MachO::load_command, class Header>
const CommandType *findCommand(const Header *hdr, uint32_t type) {
template <class CommandType = llvm::MachO::load_command, class Header,
class... Types>
const CommandType *findCommand(const Header *hdr, Types... types) {
std::initializer_list<uint32_t> typesList{types...};
const uint8_t *p = reinterpret_cast<const uint8_t *>(hdr) + sizeof(Header);
for (uint32_t i = 0, n = hdr->ncmds; i < n; ++i) {
auto *cmd = reinterpret_cast<const CommandType *>(p);
if (cmd->cmd == type)
if (llvm::is_contained(typesList, cmd->cmd))
return cmd;
p += cmd->cmdsize;
}

View File

@@ -23,8 +23,8 @@ template <class LP> static bool hasObjCSection(MemoryBufferRef mb) {
auto *hdr =
reinterpret_cast<const typename LP::mach_header *>(mb.getBufferStart());
if (const load_command *cmd = findCommand(hdr, LP::segmentLCType)) {
auto *c = reinterpret_cast<const typename LP::segment_command *>(cmd);
if (const auto *c =
findCommand<typename LP::segment_command>(hdr, LP::segmentLCType)) {
auto sectionHeaders =
ArrayRef<Section>{reinterpret_cast<const Section *>(c + 1), c->nsects};
for (const Section &sec : sectionHeaders) {