1 //===--- Relocation.cpp - Interface for object file relocations ----------===// 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 //===----------------------------------------------------------------------===// 10 11 #include "bolt/Core/Relocation.h" 12 #include "llvm/MC/MCContext.h" 13 #include "llvm/MC/MCStreamer.h" 14 #include "llvm/Object/ELF.h" 15 16 using namespace llvm; 17 using namespace bolt; 18 19 Triple::ArchType Relocation::Arch; 20 21 namespace { 22 23 bool isSupportedX86(uint64_t Type) { 24 switch (Type) { 25 default: 26 return false; 27 case ELF::R_X86_64_8: 28 case ELF::R_X86_64_16: 29 case ELF::R_X86_64_32: 30 case ELF::R_X86_64_32S: 31 case ELF::R_X86_64_64: 32 case ELF::R_X86_64_PC8: 33 case ELF::R_X86_64_PC32: 34 case ELF::R_X86_64_PC64: 35 case ELF::R_X86_64_PLT32: 36 case ELF::R_X86_64_GOTPCREL: 37 case ELF::R_X86_64_GOTTPOFF: 38 case ELF::R_X86_64_TPOFF32: 39 case ELF::R_X86_64_GOTPCRELX: 40 case ELF::R_X86_64_REX_GOTPCRELX: 41 return true; 42 } 43 } 44 45 bool isSupportedAArch64(uint64_t Type) { 46 switch (Type) { 47 default: 48 return false; 49 case ELF::R_AARCH64_CALL26: 50 case ELF::R_AARCH64_JUMP26: 51 case ELF::R_AARCH64_TSTBR14: 52 case ELF::R_AARCH64_CONDBR19: 53 case ELF::R_AARCH64_ADR_PREL_LO21: 54 case ELF::R_AARCH64_ADR_PREL_PG_HI21: 55 case ELF::R_AARCH64_ADR_PREL_PG_HI21_NC: 56 case ELF::R_AARCH64_LDST64_ABS_LO12_NC: 57 case ELF::R_AARCH64_ADD_ABS_LO12_NC: 58 case ELF::R_AARCH64_LDST128_ABS_LO12_NC: 59 case ELF::R_AARCH64_LDST32_ABS_LO12_NC: 60 case ELF::R_AARCH64_LDST16_ABS_LO12_NC: 61 case ELF::R_AARCH64_LDST8_ABS_LO12_NC: 62 case ELF::R_AARCH64_ADR_GOT_PAGE: 63 case ELF::R_AARCH64_TLSDESC_ADR_PREL21: 64 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 65 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 66 case ELF::R_AARCH64_TLSLE_ADD_TPREL_HI12: 67 case ELF::R_AARCH64_TLSLE_ADD_TPREL_LO12_NC: 68 case ELF::R_AARCH64_LD64_GOT_LO12_NC: 69 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 70 case ELF::R_AARCH64_TLSDESC_ADD_LO12: 71 case ELF::R_AARCH64_TLSDESC_CALL: 72 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: 73 case ELF::R_AARCH64_PREL32: 74 case ELF::R_AARCH64_ABS16: 75 case ELF::R_AARCH64_ABS32: 76 case ELF::R_AARCH64_ABS64: 77 case ELF::R_AARCH64_MOVW_UABS_G0: 78 case ELF::R_AARCH64_MOVW_UABS_G0_NC: 79 case ELF::R_AARCH64_MOVW_UABS_G1: 80 case ELF::R_AARCH64_MOVW_UABS_G1_NC: 81 case ELF::R_AARCH64_MOVW_UABS_G2: 82 case ELF::R_AARCH64_MOVW_UABS_G2_NC: 83 case ELF::R_AARCH64_MOVW_UABS_G3: 84 return true; 85 } 86 } 87 88 size_t getSizeForTypeX86(uint64_t Type) { 89 switch (Type) { 90 default: 91 errs() << object::getELFRelocationTypeName(ELF::EM_X86_64, Type) << '\n'; 92 llvm_unreachable("unsupported relocation type"); 93 case ELF::R_X86_64_8: 94 case ELF::R_X86_64_PC8: 95 return 1; 96 case ELF::R_X86_64_16: 97 return 2; 98 case ELF::R_X86_64_PLT32: 99 case ELF::R_X86_64_PC32: 100 case ELF::R_X86_64_32S: 101 case ELF::R_X86_64_32: 102 case ELF::R_X86_64_GOTPCREL: 103 case ELF::R_X86_64_GOTTPOFF: 104 case ELF::R_X86_64_TPOFF32: 105 case ELF::R_X86_64_GOTPCRELX: 106 case ELF::R_X86_64_REX_GOTPCRELX: 107 return 4; 108 case ELF::R_X86_64_PC64: 109 case ELF::R_X86_64_64: 110 return 8; 111 } 112 } 113 114 size_t getSizeForTypeAArch64(uint64_t Type) { 115 switch (Type) { 116 default: 117 errs() << object::getELFRelocationTypeName(ELF::EM_AARCH64, Type) << '\n'; 118 llvm_unreachable("unsupported relocation type"); 119 case ELF::R_AARCH64_ABS16: 120 return 2; 121 case ELF::R_AARCH64_CALL26: 122 case ELF::R_AARCH64_JUMP26: 123 case ELF::R_AARCH64_TSTBR14: 124 case ELF::R_AARCH64_CONDBR19: 125 case ELF::R_AARCH64_ADR_PREL_LO21: 126 case ELF::R_AARCH64_ADR_PREL_PG_HI21: 127 case ELF::R_AARCH64_ADR_PREL_PG_HI21_NC: 128 case ELF::R_AARCH64_LDST64_ABS_LO12_NC: 129 case ELF::R_AARCH64_ADD_ABS_LO12_NC: 130 case ELF::R_AARCH64_LDST128_ABS_LO12_NC: 131 case ELF::R_AARCH64_LDST32_ABS_LO12_NC: 132 case ELF::R_AARCH64_LDST16_ABS_LO12_NC: 133 case ELF::R_AARCH64_LDST8_ABS_LO12_NC: 134 case ELF::R_AARCH64_ADR_GOT_PAGE: 135 case ELF::R_AARCH64_TLSDESC_ADR_PREL21: 136 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 137 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 138 case ELF::R_AARCH64_TLSLE_ADD_TPREL_HI12: 139 case ELF::R_AARCH64_TLSLE_ADD_TPREL_LO12_NC: 140 case ELF::R_AARCH64_LD64_GOT_LO12_NC: 141 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 142 case ELF::R_AARCH64_TLSDESC_ADD_LO12: 143 case ELF::R_AARCH64_TLSDESC_CALL: 144 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: 145 case ELF::R_AARCH64_PREL32: 146 case ELF::R_AARCH64_MOVW_UABS_G0: 147 case ELF::R_AARCH64_MOVW_UABS_G0_NC: 148 case ELF::R_AARCH64_MOVW_UABS_G1: 149 case ELF::R_AARCH64_MOVW_UABS_G1_NC: 150 case ELF::R_AARCH64_MOVW_UABS_G2: 151 case ELF::R_AARCH64_MOVW_UABS_G2_NC: 152 case ELF::R_AARCH64_MOVW_UABS_G3: 153 case ELF::R_AARCH64_ABS32: 154 return 4; 155 case ELF::R_AARCH64_ABS64: 156 return 8; 157 } 158 } 159 160 bool skipRelocationProcessX86(uint64_t Type, uint64_t Contents) { 161 return false; 162 } 163 164 bool skipRelocationProcessAArch64(uint64_t Type, uint64_t Contents) { 165 auto IsMov = [](uint64_t Contents) -> bool { 166 // The bits 28-23 are 0b100101 167 if ((Contents & 0x1f800000) == 0x12800000) 168 return true; 169 return false; 170 }; 171 172 auto IsB = [](uint64_t Contents) -> bool { 173 // The bits 31-26 are 0b000101 174 if ((Contents & 0xfc000000) == 0x14000000) 175 return true; 176 return false; 177 }; 178 179 auto IsNop = [](uint64_t Contents) -> bool { return Contents == 0xd503201f; }; 180 181 // The linker might eliminate the instruction and replace it with NOP, ignore 182 if (IsNop(Contents)) 183 return true; 184 185 // The linker might perform TLS relocations relaxations, such as 186 // changed TLS access model (e.g. changed global dynamic model 187 // to initial exec), thus changing the instructions. The static 188 // relocations might be invalid at this point and we might no 189 // need to proccess these relocations anymore. 190 // More information could be found by searching 191 // elfNN_aarch64_tls_relax in bfd 192 switch (Type) { 193 default: 194 break; 195 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 196 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 197 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 198 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: { 199 if (IsMov(Contents)) 200 return true; 201 } 202 } 203 204 // The ld might replace load/store instruction with jump and 205 // veneer due to errata 843419 206 // https://documentation-service.arm.com/static/5fa29fddb209f547eebd361d 207 // Thus load/store relocations for these instructions must be ignored 208 // NOTE: We only process GOT and TLS relocations this way since the 209 // addend used in load/store instructions won't change after bolt 210 // (it is important since the instruction in veneer won't have relocation) 211 switch (Type) { 212 default: 213 break; 214 case ELF::R_AARCH64_LD64_GOT_LO12_NC: 215 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 216 case ELF::R_AARCH64_TLSDESC_LD64_LO12: { 217 if (IsB(Contents)) 218 return true; 219 } 220 } 221 222 return false; 223 } 224 225 uint64_t adjustValueX86(uint64_t Type, uint64_t Value, uint64_t PC) { 226 switch (Type) { 227 default: 228 llvm_unreachable("not supported relocation"); 229 case ELF::R_X86_64_32: 230 break; 231 case ELF::R_X86_64_PC32: 232 Value -= PC; 233 break; 234 } 235 return Value; 236 } 237 238 uint64_t adjustValueAArch64(uint64_t Type, uint64_t Value, uint64_t PC) { 239 switch (Type) { 240 default: 241 llvm_unreachable("not supported relocation"); 242 case ELF::R_AARCH64_ABS32: 243 break; 244 case ELF::R_AARCH64_PREL32: 245 Value -= PC; 246 break; 247 } 248 return Value; 249 } 250 251 uint64_t extractValueX86(uint64_t Type, uint64_t Contents, uint64_t PC) { 252 if (Type == ELF::R_X86_64_32S) 253 return SignExtend64<32>(Contents & 0xffffffff); 254 return Contents; 255 } 256 257 uint64_t extractValueAArch64(uint64_t Type, uint64_t Contents, uint64_t PC) { 258 switch (Type) { 259 default: 260 errs() << object::getELFRelocationTypeName(ELF::EM_AARCH64, Type) << '\n'; 261 llvm_unreachable("unsupported relocation type"); 262 case ELF::R_AARCH64_ABS16: 263 case ELF::R_AARCH64_ABS32: 264 case ELF::R_AARCH64_ABS64: 265 return Contents; 266 case ELF::R_AARCH64_PREL32: 267 return static_cast<int64_t>(PC) + SignExtend64<32>(Contents & 0xffffffff); 268 case ELF::R_AARCH64_TLSDESC_CALL: 269 case ELF::R_AARCH64_JUMP26: 270 case ELF::R_AARCH64_CALL26: 271 // Immediate goes in bits 25:0 of B and BL. 272 Contents &= ~0xfffffffffc000000ULL; 273 return static_cast<int64_t>(PC) + SignExtend64<28>(Contents << 2); 274 case ELF::R_AARCH64_TSTBR14: 275 // Immediate:15:2 goes in bits 18:5 of TBZ, TBNZ 276 Contents &= ~0xfffffffffff8001fULL; 277 return static_cast<int64_t>(PC) + SignExtend64<16>(Contents >> 3); 278 case ELF::R_AARCH64_CONDBR19: 279 // Immediate:20:2 goes in bits 23:5 of Bcc, CBZ, CBNZ 280 Contents &= ~0xffffffffff00001fULL; 281 return static_cast<int64_t>(PC) + SignExtend64<21>(Contents >> 3); 282 case ELF::R_AARCH64_ADR_GOT_PAGE: 283 case ELF::R_AARCH64_TLSDESC_ADR_PREL21: 284 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 285 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: 286 case ELF::R_AARCH64_ADR_PREL_LO21: 287 case ELF::R_AARCH64_ADR_PREL_PG_HI21: 288 case ELF::R_AARCH64_ADR_PREL_PG_HI21_NC: { 289 // Bits 32:12 of Symbol address goes in bits 30:29 + 23:5 of ADRP 290 // and ADR instructions 291 bool IsAdr = !!(((Contents >> 31) & 0x1) == 0); 292 Contents &= ~0xffffffff9f00001fUll; 293 uint64_t LowBits = (Contents >> 29) & 0x3; 294 uint64_t HighBits = (Contents >> 5) & 0x7ffff; 295 Contents = LowBits | (HighBits << 2); 296 if (IsAdr) 297 return static_cast<int64_t>(PC) + SignExtend64<21>(Contents); 298 299 // ADRP instruction 300 Contents = static_cast<int64_t>(PC) + SignExtend64<33>(Contents << 12); 301 Contents &= ~0xfffUll; 302 return Contents; 303 } 304 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 305 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 306 case ELF::R_AARCH64_LD64_GOT_LO12_NC: 307 case ELF::R_AARCH64_LDST64_ABS_LO12_NC: { 308 // Immediate goes in bits 21:10 of LD/ST instruction, taken 309 // from bits 11:3 of Symbol address 310 Contents &= ~0xffffffffffc003ffU; 311 return Contents >> (10 - 3); 312 } 313 case ELF::R_AARCH64_TLSLE_ADD_TPREL_HI12: 314 case ELF::R_AARCH64_TLSLE_ADD_TPREL_LO12_NC: 315 case ELF::R_AARCH64_TLSDESC_ADD_LO12: 316 case ELF::R_AARCH64_ADD_ABS_LO12_NC: { 317 // Immediate goes in bits 21:10 of ADD instruction 318 Contents &= ~0xffffffffffc003ffU; 319 return Contents >> (10 - 0); 320 } 321 case ELF::R_AARCH64_LDST128_ABS_LO12_NC: { 322 // Immediate goes in bits 21:10 of ADD instruction, taken 323 // from bits 11:4 of Symbol address 324 Contents &= ~0xffffffffffc003ffU; 325 return Contents >> (10 - 4); 326 } 327 case ELF::R_AARCH64_LDST32_ABS_LO12_NC: { 328 // Immediate goes in bits 21:10 of ADD instruction, taken 329 // from bits 11:2 of Symbol address 330 Contents &= ~0xffffffffffc003ffU; 331 return Contents >> (10 - 2); 332 } 333 case ELF::R_AARCH64_LDST16_ABS_LO12_NC: { 334 // Immediate goes in bits 21:10 of ADD instruction, taken 335 // from bits 11:1 of Symbol address 336 Contents &= ~0xffffffffffc003ffU; 337 return Contents >> (10 - 1); 338 } 339 case ELF::R_AARCH64_LDST8_ABS_LO12_NC: { 340 // Immediate goes in bits 21:10 of ADD instruction, taken 341 // from bits 11:0 of Symbol address 342 Contents &= ~0xffffffffffc003ffU; 343 return Contents >> (10 - 0); 344 } 345 case ELF::R_AARCH64_MOVW_UABS_G3: 346 case ELF::R_AARCH64_MOVW_UABS_G2_NC: 347 case ELF::R_AARCH64_MOVW_UABS_G2: 348 case ELF::R_AARCH64_MOVW_UABS_G1_NC: 349 case ELF::R_AARCH64_MOVW_UABS_G1: 350 case ELF::R_AARCH64_MOVW_UABS_G0_NC: 351 case ELF::R_AARCH64_MOVW_UABS_G0: 352 // The shift goest in bits 22:21 of MOV* instructions 353 uint8_t Shift = (Contents >> 21) & 0x3; 354 // Immediate goes in bits 20:5 355 Contents = (Contents >> 5) & 0xffff; 356 return Contents << (16 * Shift); 357 } 358 } 359 360 bool isGOTX86(uint64_t Type) { 361 switch (Type) { 362 default: 363 return false; 364 case ELF::R_X86_64_GOT32: 365 case ELF::R_X86_64_GOTPCREL: 366 case ELF::R_X86_64_GOTTPOFF: 367 case ELF::R_X86_64_GOTOFF64: 368 case ELF::R_X86_64_GOTPC32: 369 case ELF::R_X86_64_GOT64: 370 case ELF::R_X86_64_GOTPCREL64: 371 case ELF::R_X86_64_GOTPC64: 372 case ELF::R_X86_64_GOTPLT64: 373 case ELF::R_X86_64_GOTPC32_TLSDESC: 374 case ELF::R_X86_64_GOTPCRELX: 375 case ELF::R_X86_64_REX_GOTPCRELX: 376 return true; 377 } 378 } 379 380 bool isGOTAArch64(uint64_t Type) { 381 switch (Type) { 382 default: 383 return false; 384 case ELF::R_AARCH64_ADR_GOT_PAGE: 385 case ELF::R_AARCH64_LD64_GOT_LO12_NC: 386 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 387 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: 388 case ELF::R_AARCH64_TLSDESC_ADR_PREL21: 389 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 390 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 391 case ELF::R_AARCH64_TLSDESC_ADD_LO12: 392 case ELF::R_AARCH64_TLSDESC_CALL: 393 return true; 394 } 395 } 396 397 bool isTLSX86(uint64_t Type) { 398 switch (Type) { 399 default: 400 return false; 401 case ELF::R_X86_64_TPOFF32: 402 case ELF::R_X86_64_TPOFF64: 403 case ELF::R_X86_64_GOTTPOFF: 404 return true; 405 } 406 } 407 408 bool isTLSAArch64(uint64_t Type) { 409 switch (Type) { 410 default: 411 return false; 412 case ELF::R_AARCH64_TLSDESC_ADR_PREL21: 413 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 414 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 415 case ELF::R_AARCH64_TLSLE_ADD_TPREL_HI12: 416 case ELF::R_AARCH64_TLSLE_ADD_TPREL_LO12_NC: 417 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 418 case ELF::R_AARCH64_TLSDESC_ADD_LO12: 419 case ELF::R_AARCH64_TLSDESC_CALL: 420 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: 421 return true; 422 } 423 } 424 425 bool isPCRelativeX86(uint64_t Type) { 426 switch (Type) { 427 default: 428 llvm_unreachable("Unknown relocation type"); 429 case ELF::R_X86_64_64: 430 case ELF::R_X86_64_32: 431 case ELF::R_X86_64_32S: 432 case ELF::R_X86_64_16: 433 case ELF::R_X86_64_8: 434 case ELF::R_X86_64_TPOFF32: 435 return false; 436 case ELF::R_X86_64_PC8: 437 case ELF::R_X86_64_PC32: 438 case ELF::R_X86_64_PC64: 439 case ELF::R_X86_64_GOTPCREL: 440 case ELF::R_X86_64_PLT32: 441 case ELF::R_X86_64_GOTTPOFF: 442 case ELF::R_X86_64_GOTPCRELX: 443 case ELF::R_X86_64_REX_GOTPCRELX: 444 return true; 445 } 446 } 447 448 bool isPCRelativeAArch64(uint64_t Type) { 449 switch (Type) { 450 default: 451 llvm_unreachable("Unknown relocation type"); 452 case ELF::R_AARCH64_ABS16: 453 case ELF::R_AARCH64_ABS32: 454 case ELF::R_AARCH64_ABS64: 455 case ELF::R_AARCH64_LDST64_ABS_LO12_NC: 456 case ELF::R_AARCH64_ADD_ABS_LO12_NC: 457 case ELF::R_AARCH64_LDST128_ABS_LO12_NC: 458 case ELF::R_AARCH64_LDST32_ABS_LO12_NC: 459 case ELF::R_AARCH64_LDST16_ABS_LO12_NC: 460 case ELF::R_AARCH64_LDST8_ABS_LO12_NC: 461 case ELF::R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC: 462 case ELF::R_AARCH64_TLSLE_ADD_TPREL_HI12: 463 case ELF::R_AARCH64_TLSLE_ADD_TPREL_LO12_NC: 464 case ELF::R_AARCH64_LD64_GOT_LO12_NC: 465 case ELF::R_AARCH64_TLSDESC_LD64_LO12: 466 case ELF::R_AARCH64_TLSDESC_ADD_LO12: 467 case ELF::R_AARCH64_MOVW_UABS_G0: 468 case ELF::R_AARCH64_MOVW_UABS_G0_NC: 469 case ELF::R_AARCH64_MOVW_UABS_G1: 470 case ELF::R_AARCH64_MOVW_UABS_G1_NC: 471 case ELF::R_AARCH64_MOVW_UABS_G2: 472 case ELF::R_AARCH64_MOVW_UABS_G2_NC: 473 case ELF::R_AARCH64_MOVW_UABS_G3: 474 return false; 475 case ELF::R_AARCH64_TLSDESC_CALL: 476 case ELF::R_AARCH64_CALL26: 477 case ELF::R_AARCH64_JUMP26: 478 case ELF::R_AARCH64_TSTBR14: 479 case ELF::R_AARCH64_CONDBR19: 480 case ELF::R_AARCH64_ADR_PREL_LO21: 481 case ELF::R_AARCH64_ADR_PREL_PG_HI21: 482 case ELF::R_AARCH64_ADR_PREL_PG_HI21_NC: 483 case ELF::R_AARCH64_ADR_GOT_PAGE: 484 case ELF::R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21: 485 case ELF::R_AARCH64_TLSDESC_ADR_PREL21: 486 case ELF::R_AARCH64_TLSDESC_ADR_PAGE21: 487 case ELF::R_AARCH64_PREL32: 488 return true; 489 } 490 } 491 492 } // end anonymous namespace 493 494 bool Relocation::isSupported(uint64_t Type) { 495 if (Arch == Triple::aarch64) 496 return isSupportedAArch64(Type); 497 return isSupportedX86(Type); 498 } 499 500 size_t Relocation::getSizeForType(uint64_t Type) { 501 if (Arch == Triple::aarch64) 502 return getSizeForTypeAArch64(Type); 503 return getSizeForTypeX86(Type); 504 } 505 506 bool Relocation::skipRelocationProcess(uint64_t Type, uint64_t Contents) { 507 if (Arch == Triple::aarch64) 508 return skipRelocationProcessAArch64(Type, Contents); 509 return skipRelocationProcessX86(Type, Contents); 510 } 511 512 uint64_t Relocation::adjustValue(uint64_t Type, uint64_t Value, 513 uint64_t PC) { 514 if (Arch == Triple::aarch64) 515 return adjustValueAArch64(Type, Value, PC); 516 return adjustValueX86(Type, Value, PC); 517 } 518 519 uint64_t Relocation::extractValue(uint64_t Type, uint64_t Contents, 520 uint64_t PC) { 521 if (Arch == Triple::aarch64) 522 return extractValueAArch64(Type, Contents, PC); 523 return extractValueX86(Type, Contents, PC); 524 } 525 526 bool Relocation::isGOT(uint64_t Type) { 527 if (Arch == Triple::aarch64) 528 return isGOTAArch64(Type); 529 return isGOTX86(Type); 530 } 531 532 bool Relocation::isNone(uint64_t Type) { 533 if (Arch == Triple::aarch64) 534 return Type == ELF::R_AARCH64_NONE; 535 return Type == ELF::R_X86_64_NONE; 536 } 537 538 bool Relocation::isRelative(uint64_t Type) { 539 if (Arch == Triple::aarch64) 540 return Type == ELF::R_AARCH64_RELATIVE; 541 return Type == ELF::R_X86_64_RELATIVE; 542 } 543 544 bool Relocation::isIRelative(uint64_t Type) { 545 if (Arch == Triple::aarch64) 546 return Type == ELF::R_AARCH64_IRELATIVE; 547 return Type == ELF::R_X86_64_IRELATIVE; 548 } 549 550 bool Relocation::isTLS(uint64_t Type) { 551 if (Arch == Triple::aarch64) 552 return isTLSAArch64(Type); 553 return isTLSX86(Type); 554 } 555 556 bool Relocation::isPCRelative(uint64_t Type) { 557 if (Arch == Triple::aarch64) 558 return isPCRelativeAArch64(Type); 559 return isPCRelativeX86(Type); 560 } 561 562 uint64_t Relocation::getPC32() { 563 if (Arch == Triple::aarch64) 564 return ELF::R_AARCH64_PREL32; 565 return ELF::R_X86_64_PC32; 566 } 567 568 uint64_t Relocation::getPC64() { 569 if (Arch == Triple::aarch64) 570 return ELF::R_AARCH64_PREL64; 571 return ELF::R_X86_64_PC64; 572 } 573 574 size_t Relocation::emit(MCStreamer *Streamer) const { 575 const size_t Size = getSizeForType(Type); 576 MCContext &Ctx = Streamer->getContext(); 577 if (isPCRelative(Type)) { 578 MCSymbol *TempLabel = Ctx.createNamedTempSymbol(); 579 Streamer->emitLabel(TempLabel); 580 const MCExpr *Value = nullptr; 581 if (Symbol) { 582 Value = MCSymbolRefExpr::create(Symbol, Ctx); 583 if (Addend) { 584 Value = MCBinaryExpr::createAdd( 585 Value, MCConstantExpr::create(Addend, Ctx), Ctx); 586 } 587 } else { 588 Value = MCConstantExpr::create(Addend, Ctx); 589 } 590 Value = MCBinaryExpr::createSub( 591 Value, MCSymbolRefExpr::create(TempLabel, Ctx), Ctx); 592 Streamer->emitValue(Value, Size); 593 594 return Size; 595 } 596 597 if (Symbol && Addend) { 598 auto Value = 599 MCBinaryExpr::createAdd(MCSymbolRefExpr::create(Symbol, Ctx), 600 MCConstantExpr::create(Addend, Ctx), Ctx); 601 Streamer->emitValue(Value, Size); 602 } else if (Symbol) { 603 Streamer->emitSymbolValue(Symbol, Size); 604 } else { 605 Streamer->emitIntValue(Addend, Size); 606 } 607 608 return Size; 609 } 610 611 #define ELF_RELOC(name, value) #name, 612 613 void Relocation::print(raw_ostream &OS) const { 614 static const char *X86RelocNames[] = { 615 #include "llvm/BinaryFormat/ELFRelocs/x86_64.def" 616 }; 617 static const char *AArch64RelocNames[] = { 618 #include "llvm/BinaryFormat/ELFRelocs/AArch64.def" 619 }; 620 if (Arch == Triple::aarch64) 621 OS << AArch64RelocNames[Type]; 622 else 623 OS << X86RelocNames[Type]; 624 OS << ", 0x" << Twine::utohexstr(Offset); 625 if (Symbol) { 626 OS << ", " << Symbol->getName(); 627 } 628 if (int64_t(Addend) < 0) 629 OS << ", -0x" << Twine::utohexstr(-int64_t(Addend)); 630 else 631 OS << ", 0x" << Twine::utohexstr(Addend); 632 OS << ", 0x" << Twine::utohexstr(Value); 633 } 634