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