1 //===-- ARMMCAsmInfo.cpp - ARM asm properties -----------------------------===// 2 // 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 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file contains the declarations of the ARMMCAsmInfo properties. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "ARMMCAsmInfo.h" 14 #include "llvm/MC/MCExpr.h" 15 #include "llvm/Support/raw_ostream.h" 16 #include "llvm/TargetParser/Triple.h" 17 18 using namespace llvm; 19 20 const MCAsmInfo::AtSpecifier atSpecifiers[] = { 21 {ARM::S_GOT_PREL, "GOT_PREL"}, 22 {ARM::S_ARM_NONE, "none"}, 23 {ARM::S_PREL31, "prel31"}, 24 {ARM::S_SBREL, "sbrel"}, 25 {ARM::S_TARGET1, "target1"}, 26 {ARM::S_TARGET2, "target2"}, 27 {ARM::S_TLSLDO, "TLSLDO"}, 28 {MCSymbolRefExpr::VK_COFF_IMGREL32, "imgrel"}, 29 {ARM::S_FUNCDESC, "FUNCDESC"}, 30 {ARM::S_GOT, "GOT"}, 31 {ARM::S_GOTFUNCDESC, "GOTFUNCDESC"}, 32 {ARM::S_GOTOFF, "GOTOFF"}, 33 {ARM::S_GOTOFFFUNCDESC, "GOTOFFFUNCDESC"}, 34 {ARM::S_GOTTPOFF, "GOTTPOFF"}, 35 {ARM::S_GOTTPOFF_FDPIC, "gottpoff_fdpic"}, 36 {ARM::S_PLT, "PLT"}, 37 {ARM::S_COFF_SECREL, "SECREL32"}, 38 {ARM::S_TLSCALL, "tlscall"}, 39 {ARM::S_TLSDESC, "tlsdesc"}, 40 {ARM::S_TLSGD, "TLSGD"}, 41 {ARM::S_TLSGD_FDPIC, "tlsgd_fdpic"}, 42 {ARM::S_TLSLDM, "TLSLDM"}, 43 {ARM::S_TLSLDM_FDPIC, "tlsldm_fdpic"}, 44 {ARM::S_TPOFF, "TPOFF"}, 45 }; 46 47 void ARMMCAsmInfoDarwin::anchor() { } 48 49 ARMMCAsmInfoDarwin::ARMMCAsmInfoDarwin(const Triple &TheTriple) { 50 if ((TheTriple.getArch() == Triple::armeb) || 51 (TheTriple.getArch() == Triple::thumbeb)) 52 IsLittleEndian = false; 53 54 Data64bitsDirective = nullptr; 55 CommentString = "@"; 56 AllowDollarAtStartOfIdentifier = false; 57 UseDataRegionDirectives = true; 58 59 SupportsDebugInformation = true; 60 61 // Conditional Thumb 4-byte instructions can have an implicit IT. 62 MaxInstLength = 6; 63 64 // Exceptions handling 65 ExceptionsType = (TheTriple.isOSDarwin() && !TheTriple.isWatchABI()) 66 ? ExceptionHandling::SjLj 67 : ExceptionHandling::DwarfCFI; 68 69 initializeAtSpecifiers(atSpecifiers); 70 } 71 72 void ARMELFMCAsmInfo::anchor() { } 73 74 ARMELFMCAsmInfo::ARMELFMCAsmInfo(const Triple &TheTriple) { 75 if ((TheTriple.getArch() == Triple::armeb) || 76 (TheTriple.getArch() == Triple::thumbeb)) 77 IsLittleEndian = false; 78 79 // ".comm align is in bytes but .align is pow-2." 80 AlignmentIsInBytes = false; 81 82 Data64bitsDirective = nullptr; 83 CommentString = "@"; 84 AllowDollarAtStartOfIdentifier = false; 85 86 SupportsDebugInformation = true; 87 88 // Conditional Thumb 4-byte instructions can have an implicit IT. 89 MaxInstLength = 6; 90 91 // Exceptions handling 92 switch (TheTriple.getOS()) { 93 case Triple::NetBSD: 94 ExceptionsType = ExceptionHandling::DwarfCFI; 95 break; 96 default: 97 ExceptionsType = ExceptionHandling::ARM; 98 break; 99 } 100 101 // foo(plt) instead of foo@plt 102 UseAtForSpecifier = false; 103 UseParensForSpecifier = true; 104 105 initializeAtSpecifiers(atSpecifiers); 106 } 107 108 void ARMELFMCAsmInfo::setUseIntegratedAssembler(bool Value) { 109 UseIntegratedAssembler = Value; 110 if (!UseIntegratedAssembler) { 111 // gas doesn't handle VFP register names in cfi directives, 112 // so don't use register names with external assembler. 113 // See https://sourceware.org/bugzilla/show_bug.cgi?id=16694 114 DwarfRegNumForCFI = true; 115 } 116 } 117 118 void ARMCOFFMCAsmInfoMicrosoft::anchor() { } 119 120 ARMCOFFMCAsmInfoMicrosoft::ARMCOFFMCAsmInfoMicrosoft() { 121 AlignmentIsInBytes = false; 122 SupportsDebugInformation = true; 123 ExceptionsType = ExceptionHandling::WinEH; 124 WinEHEncodingType = WinEH::EncodingType::Itanium; 125 PrivateGlobalPrefix = "$M"; 126 PrivateLabelPrefix = "$M"; 127 CommentString = "@"; 128 129 // Conditional Thumb 4-byte instructions can have an implicit IT. 130 MaxInstLength = 6; 131 132 initializeAtSpecifiers(atSpecifiers); 133 } 134 135 void ARMCOFFMCAsmInfoGNU::anchor() { } 136 137 ARMCOFFMCAsmInfoGNU::ARMCOFFMCAsmInfoGNU() { 138 AlignmentIsInBytes = false; 139 HasSingleParameterDotFile = true; 140 141 CommentString = "@"; 142 AllowDollarAtStartOfIdentifier = false; 143 PrivateGlobalPrefix = ".L"; 144 PrivateLabelPrefix = ".L"; 145 146 SupportsDebugInformation = true; 147 ExceptionsType = ExceptionHandling::WinEH; 148 WinEHEncodingType = WinEH::EncodingType::Itanium; 149 UseAtForSpecifier = false; 150 UseParensForSpecifier = true; 151 152 DwarfRegNumForCFI = false; 153 154 // Conditional Thumb 4-byte instructions can have an implicit IT. 155 MaxInstLength = 6; 156 157 initializeAtSpecifiers(atSpecifiers); 158 } 159 160 void ARM::printSpecifierExpr(const MCAsmInfo &MAI, raw_ostream &OS, 161 const MCSpecifierExpr &Expr) { 162 switch (Expr.getSpecifier()) { 163 default: 164 llvm_unreachable("Invalid kind!"); 165 case ARM::S_HI16: 166 OS << ":upper16:"; 167 break; 168 case ARM::S_LO16: 169 OS << ":lower16:"; 170 break; 171 case ARM::S_HI_8_15: 172 OS << ":upper8_15:"; 173 break; 174 case ARM::S_HI_0_7: 175 OS << ":upper0_7:"; 176 break; 177 case ARM::S_LO_8_15: 178 OS << ":lower8_15:"; 179 break; 180 case ARM::S_LO_0_7: 181 OS << ":lower0_7:"; 182 break; 183 } 184 185 const MCExpr *Sub = Expr.getSubExpr(); 186 if (Sub->getKind() != MCExpr::SymbolRef) 187 OS << '('; 188 MAI.printExpr(OS, *Sub); 189 if (Sub->getKind() != MCExpr::SymbolRef) 190 OS << ')'; 191 } 192 193 const MCSpecifierExpr *ARM::createUpper16(const MCExpr *Expr, MCContext &Ctx) { 194 return MCSpecifierExpr::create(Expr, ARM::S_HI16, Ctx); 195 } 196 197 const MCSpecifierExpr *ARM::createLower16(const MCExpr *Expr, MCContext &Ctx) { 198 return MCSpecifierExpr::create(Expr, ARM::S_LO16, Ctx); 199 } 200 201 const MCSpecifierExpr *ARM::createUpper8_15(const MCExpr *Expr, 202 MCContext &Ctx) { 203 return MCSpecifierExpr::create(Expr, ARM::S_HI_8_15, Ctx); 204 } 205 206 const MCSpecifierExpr *ARM::createUpper0_7(const MCExpr *Expr, MCContext &Ctx) { 207 return MCSpecifierExpr::create(Expr, ARM::S_HI_0_7, Ctx); 208 } 209 210 const MCSpecifierExpr *ARM::createLower8_15(const MCExpr *Expr, 211 MCContext &Ctx) { 212 return MCSpecifierExpr::create(Expr, ARM::S_LO_8_15, Ctx); 213 } 214 215 const MCSpecifierExpr *ARM::createLower0_7(const MCExpr *Expr, MCContext &Ctx) { 216 return MCSpecifierExpr::create(Expr, ARM::S_LO_0_7, Ctx); 217 } 218