xref: /freebsd-src/contrib/llvm-project/llvm/lib/BinaryFormat/MachO.cpp (revision 06c3fb2749bda94cb5201f81ffdb8fa6c3161b2e)
15ffd83dbSDimitry Andric //===-- llvm/BinaryFormat/MachO.cpp - The MachO file format -----*- C++/-*-===//
25ffd83dbSDimitry Andric //
35ffd83dbSDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
45ffd83dbSDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
55ffd83dbSDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
65ffd83dbSDimitry Andric //
75ffd83dbSDimitry Andric //===----------------------------------------------------------------------===//
85ffd83dbSDimitry Andric 
95ffd83dbSDimitry Andric #include "llvm/BinaryFormat/MachO.h"
10*06c3fb27SDimitry Andric #include "llvm/TargetParser/ARMTargetParser.h"
11*06c3fb27SDimitry Andric #include "llvm/TargetParser/Triple.h"
125ffd83dbSDimitry Andric 
135ffd83dbSDimitry Andric using namespace llvm;
145ffd83dbSDimitry Andric 
getX86SubType(const Triple & T)155ffd83dbSDimitry Andric static MachO::CPUSubTypeX86 getX86SubType(const Triple &T) {
165ffd83dbSDimitry Andric   assert(T.isX86());
175ffd83dbSDimitry Andric   if (T.isArch32Bit())
185ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_I386_ALL;
195ffd83dbSDimitry Andric 
205ffd83dbSDimitry Andric   assert(T.isArch64Bit());
215ffd83dbSDimitry Andric   if (T.getArchName() == "x86_64h")
225ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_X86_64_H;
235ffd83dbSDimitry Andric   return MachO::CPU_SUBTYPE_X86_64_ALL;
245ffd83dbSDimitry Andric }
255ffd83dbSDimitry Andric 
getARMSubType(const Triple & T)265ffd83dbSDimitry Andric static MachO::CPUSubTypeARM getARMSubType(const Triple &T) {
275ffd83dbSDimitry Andric   assert(T.isARM() || T.isThumb());
285ffd83dbSDimitry Andric   StringRef Arch = T.getArchName();
295ffd83dbSDimitry Andric   ARM::ArchKind AK = ARM::parseArch(Arch);
305ffd83dbSDimitry Andric   switch (AK) {
315ffd83dbSDimitry Andric   default:
325ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V7;
335ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV4T:
345ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V4T;
355ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV5T:
365ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV5TE:
375ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV5TEJ:
385ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V5;
395ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV6:
405ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV6K:
415ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V6;
425ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV7A:
435ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V7;
445ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV7S:
455ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V7S;
465ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV7K:
475ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V7K;
485ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV6M:
495ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V6M;
505ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV7M:
515ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V7M;
525ffd83dbSDimitry Andric   case ARM::ArchKind::ARMV7EM:
535ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM_V7EM;
545ffd83dbSDimitry Andric   }
555ffd83dbSDimitry Andric }
565ffd83dbSDimitry Andric 
getARM64SubType(const Triple & T)575ffd83dbSDimitry Andric static MachO::CPUSubTypeARM64 getARM64SubType(const Triple &T) {
58e8d8bef9SDimitry Andric   assert(T.isAArch64());
595ffd83dbSDimitry Andric   if (T.isArch32Bit())
605ffd83dbSDimitry Andric     return (MachO::CPUSubTypeARM64)MachO::CPU_SUBTYPE_ARM64_32_V8;
61e8d8bef9SDimitry Andric   if (T.isArm64e())
625ffd83dbSDimitry Andric     return MachO::CPU_SUBTYPE_ARM64E;
635ffd83dbSDimitry Andric 
645ffd83dbSDimitry Andric   return MachO::CPU_SUBTYPE_ARM64_ALL;
655ffd83dbSDimitry Andric }
665ffd83dbSDimitry Andric 
getPowerPCSubType(const Triple & T)675ffd83dbSDimitry Andric static MachO::CPUSubTypePowerPC getPowerPCSubType(const Triple &T) {
685ffd83dbSDimitry Andric   return MachO::CPU_SUBTYPE_POWERPC_ALL;
695ffd83dbSDimitry Andric }
705ffd83dbSDimitry Andric 
unsupported(const char * Str,const Triple & T)715ffd83dbSDimitry Andric static Error unsupported(const char *Str, const Triple &T) {
725ffd83dbSDimitry Andric   return createStringError(std::errc::invalid_argument,
735ffd83dbSDimitry Andric                            "Unsupported triple for mach-o cpu %s: %s", Str,
745ffd83dbSDimitry Andric                            T.str().c_str());
755ffd83dbSDimitry Andric }
765ffd83dbSDimitry Andric 
getCPUType(const Triple & T)775ffd83dbSDimitry Andric Expected<uint32_t> MachO::getCPUType(const Triple &T) {
785ffd83dbSDimitry Andric   if (!T.isOSBinFormatMachO())
795ffd83dbSDimitry Andric     return unsupported("type", T);
805ffd83dbSDimitry Andric   if (T.isX86() && T.isArch32Bit())
815ffd83dbSDimitry Andric     return MachO::CPU_TYPE_X86;
825ffd83dbSDimitry Andric   if (T.isX86() && T.isArch64Bit())
835ffd83dbSDimitry Andric     return MachO::CPU_TYPE_X86_64;
845ffd83dbSDimitry Andric   if (T.isARM() || T.isThumb())
855ffd83dbSDimitry Andric     return MachO::CPU_TYPE_ARM;
865ffd83dbSDimitry Andric   if (T.isAArch64())
87e8d8bef9SDimitry Andric     return T.isArch32Bit() ? MachO::CPU_TYPE_ARM64_32 : MachO::CPU_TYPE_ARM64;
885ffd83dbSDimitry Andric   if (T.getArch() == Triple::ppc)
895ffd83dbSDimitry Andric     return MachO::CPU_TYPE_POWERPC;
905ffd83dbSDimitry Andric   if (T.getArch() == Triple::ppc64)
915ffd83dbSDimitry Andric     return MachO::CPU_TYPE_POWERPC64;
925ffd83dbSDimitry Andric   return unsupported("type", T);
935ffd83dbSDimitry Andric }
945ffd83dbSDimitry Andric 
getCPUSubType(const Triple & T)955ffd83dbSDimitry Andric Expected<uint32_t> MachO::getCPUSubType(const Triple &T) {
965ffd83dbSDimitry Andric   if (!T.isOSBinFormatMachO())
975ffd83dbSDimitry Andric     return unsupported("subtype", T);
985ffd83dbSDimitry Andric   if (T.isX86())
995ffd83dbSDimitry Andric     return getX86SubType(T);
1005ffd83dbSDimitry Andric   if (T.isARM() || T.isThumb())
1015ffd83dbSDimitry Andric     return getARMSubType(T);
1025ffd83dbSDimitry Andric   if (T.isAArch64() || T.getArch() == Triple::aarch64_32)
1035ffd83dbSDimitry Andric     return getARM64SubType(T);
1045ffd83dbSDimitry Andric   if (T.getArch() == Triple::ppc || T.getArch() == Triple::ppc64)
1055ffd83dbSDimitry Andric     return getPowerPCSubType(T);
1065ffd83dbSDimitry Andric   return unsupported("subtype", T);
1075ffd83dbSDimitry Andric }
108