14
14
#include " Thunks.h"
15
15
#include " lld/Common/ErrorHandler.h"
16
16
#include " llvm/Object/ELF.h"
17
- #include " llvm/Support/Endian.h"
18
17
19
18
using namespace llvm ;
20
19
using namespace llvm ::object;
21
- using namespace llvm ::support::endian;
22
20
using namespace llvm ::ELF;
23
21
using namespace lld ;
24
22
using namespace lld ::elf;
@@ -199,7 +197,7 @@ void MIPS<ELFT>::writeGotPlt(uint8_t *buf, const Symbol &) const {
199
197
uint64_t va = in.plt ->getVA ();
200
198
if (isMicroMips ())
201
199
va |= 1 ;
202
- write32<ELFT::TargetEndianness> (buf, va);
200
+ write32 (buf, va);
203
201
}
204
202
205
203
template <endianness E> static uint32_t readShuffle (const uint8_t *loc) {
@@ -209,7 +207,7 @@ template <endianness E> static uint32_t readShuffle(const uint8_t *loc) {
209
207
// as early as possible. To do so, little-endian binaries keep 16-bit
210
208
// words in a big-endian order. That is why we have to swap these
211
209
// words to get a correct value.
212
- uint32_t v = read32<E> (loc);
210
+ uint32_t v = read32 (loc);
213
211
if (E == support::little)
214
212
return (v << 16 ) | (v >> 16 );
215
213
return v;
@@ -218,10 +216,10 @@ template <endianness E> static uint32_t readShuffle(const uint8_t *loc) {
218
216
template <endianness E>
219
217
static void writeValue (uint8_t *loc, uint64_t v, uint8_t bitsSize,
220
218
uint8_t shift) {
221
- uint32_t instr = read32<E> (loc);
219
+ uint32_t instr = read32 (loc);
222
220
uint32_t mask = 0xffffffff >> (32 - bitsSize);
223
221
uint32_t data = (instr & ~mask) | ((v >> shift) & mask);
224
- write32<E> (loc, data);
222
+ write32 (loc, data);
225
223
}
226
224
227
225
template <endianness E>
@@ -241,10 +239,10 @@ static void writeShuffleValue(uint8_t *loc, uint64_t v, uint8_t bitsSize,
241
239
template <endianness E>
242
240
static void writeMicroRelocation16 (uint8_t *loc, uint64_t v, uint8_t bitsSize,
243
241
uint8_t shift) {
244
- uint16_t instr = read16<E> (loc);
242
+ uint16_t instr = read16 (loc);
245
243
uint16_t mask = 0xffff >> (16 - bitsSize);
246
244
uint16_t data = (instr & ~mask) | ((v >> shift) & mask);
247
- write16<E> (loc, data);
245
+ write16 (loc, data);
248
246
}
249
247
250
248
template <class ELFT > void MIPS<ELFT>::writePltHeader(uint8_t *buf) const {
@@ -255,53 +253,53 @@ template <class ELFT> void MIPS<ELFT>::writePltHeader(uint8_t *buf) const {
255
253
// Overwrite trap instructions written by Writer::writeTrapInstr.
256
254
memset (buf, 0 , pltHeaderSize);
257
255
258
- write16<e> (buf, isMipsR6 () ? 0x7860 : 0x7980 ); // addiupc v1, (GOTPLT) - .
259
- write16<e> (buf + 4 , 0xff23 ); // lw $25, 0($3)
260
- write16<e> (buf + 8 , 0x0535 ); // subu16 $2, $2, $3
261
- write16<e> (buf + 10 , 0x2525 ); // srl16 $2, $2, 2
262
- write16<e> (buf + 12 , 0x3302 ); // addiu $24, $2, -2
263
- write16<e> (buf + 14 , 0xfffe );
264
- write16<e> (buf + 16 , 0x0dff ); // move $15, $31
256
+ write16 (buf, isMipsR6 () ? 0x7860 : 0x7980 ); // addiupc v1, (GOTPLT) - .
257
+ write16 (buf + 4 , 0xff23 ); // lw $25, 0($3)
258
+ write16 (buf + 8 , 0x0535 ); // subu16 $2, $2, $3
259
+ write16 (buf + 10 , 0x2525 ); // srl16 $2, $2, 2
260
+ write16 (buf + 12 , 0x3302 ); // addiu $24, $2, -2
261
+ write16 (buf + 14 , 0xfffe );
262
+ write16 (buf + 16 , 0x0dff ); // move $15, $31
265
263
if (isMipsR6 ()) {
266
- write16<e> (buf + 18 , 0x0f83 ); // move $28, $3
267
- write16<e> (buf + 20 , 0x472b ); // jalrc $25
268
- write16<e> (buf + 22 , 0x0c00 ); // nop
264
+ write16 (buf + 18 , 0x0f83 ); // move $28, $3
265
+ write16 (buf + 20 , 0x472b ); // jalrc $25
266
+ write16 (buf + 22 , 0x0c00 ); // nop
269
267
relocateOne (buf, R_MICROMIPS_PC19_S2, gotPlt - plt);
270
268
} else {
271
- write16<e> (buf + 18 , 0x45f9 ); // jalrc $25
272
- write16<e> (buf + 20 , 0x0f83 ); // move $28, $3
273
- write16<e> (buf + 22 , 0x0c00 ); // nop
269
+ write16 (buf + 18 , 0x45f9 ); // jalrc $25
270
+ write16 (buf + 20 , 0x0f83 ); // move $28, $3
271
+ write16 (buf + 22 , 0x0c00 ); // nop
274
272
relocateOne (buf, R_MICROMIPS_PC23_S2, gotPlt - plt);
275
273
}
276
274
return ;
277
275
}
278
276
279
277
if (config->mipsN32Abi ) {
280
- write32<e> (buf, 0x3c0e0000 ); // lui $14, %hi(&GOTPLT[0])
281
- write32<e> (buf + 4 , 0x8dd90000 ); // lw $25, %lo(&GOTPLT[0])($14)
282
- write32<e> (buf + 8 , 0x25ce0000 ); // addiu $14, $14, %lo(&GOTPLT[0])
283
- write32<e> (buf + 12 , 0x030ec023 ); // subu $24, $24, $14
284
- write32<e> (buf + 16 , 0x03e07825 ); // move $15, $31
285
- write32<e> (buf + 20 , 0x0018c082 ); // srl $24, $24, 2
278
+ write32 (buf, 0x3c0e0000 ); // lui $14, %hi(&GOTPLT[0])
279
+ write32 (buf + 4 , 0x8dd90000 ); // lw $25, %lo(&GOTPLT[0])($14)
280
+ write32 (buf + 8 , 0x25ce0000 ); // addiu $14, $14, %lo(&GOTPLT[0])
281
+ write32 (buf + 12 , 0x030ec023 ); // subu $24, $24, $14
282
+ write32 (buf + 16 , 0x03e07825 ); // move $15, $31
283
+ write32 (buf + 20 , 0x0018c082 ); // srl $24, $24, 2
286
284
} else if (ELFT::Is64Bits) {
287
- write32<e> (buf, 0x3c0e0000 ); // lui $14, %hi(&GOTPLT[0])
288
- write32<e> (buf + 4 , 0xddd90000 ); // ld $25, %lo(&GOTPLT[0])($14)
289
- write32<e> (buf + 8 , 0x25ce0000 ); // addiu $14, $14, %lo(&GOTPLT[0])
290
- write32<e> (buf + 12 , 0x030ec023 ); // subu $24, $24, $14
291
- write32<e> (buf + 16 , 0x03e07825 ); // move $15, $31
292
- write32<e> (buf + 20 , 0x0018c0c2 ); // srl $24, $24, 3
285
+ write32 (buf, 0x3c0e0000 ); // lui $14, %hi(&GOTPLT[0])
286
+ write32 (buf + 4 , 0xddd90000 ); // ld $25, %lo(&GOTPLT[0])($14)
287
+ write32 (buf + 8 , 0x25ce0000 ); // addiu $14, $14, %lo(&GOTPLT[0])
288
+ write32 (buf + 12 , 0x030ec023 ); // subu $24, $24, $14
289
+ write32 (buf + 16 , 0x03e07825 ); // move $15, $31
290
+ write32 (buf + 20 , 0x0018c0c2 ); // srl $24, $24, 3
293
291
} else {
294
- write32<e> (buf, 0x3c1c0000 ); // lui $28, %hi(&GOTPLT[0])
295
- write32<e> (buf + 4 , 0x8f990000 ); // lw $25, %lo(&GOTPLT[0])($28)
296
- write32<e> (buf + 8 , 0x279c0000 ); // addiu $28, $28, %lo(&GOTPLT[0])
297
- write32<e> (buf + 12 , 0x031cc023 ); // subu $24, $24, $28
298
- write32<e> (buf + 16 , 0x03e07825 ); // move $15, $31
299
- write32<e> (buf + 20 , 0x0018c082 ); // srl $24, $24, 2
292
+ write32 (buf, 0x3c1c0000 ); // lui $28, %hi(&GOTPLT[0])
293
+ write32 (buf + 4 , 0x8f990000 ); // lw $25, %lo(&GOTPLT[0])($28)
294
+ write32 (buf + 8 , 0x279c0000 ); // addiu $28, $28, %lo(&GOTPLT[0])
295
+ write32 (buf + 12 , 0x031cc023 ); // subu $24, $24, $28
296
+ write32 (buf + 16 , 0x03e07825 ); // move $15, $31
297
+ write32 (buf + 20 , 0x0018c082 ); // srl $24, $24, 2
300
298
}
301
299
302
300
uint32_t jalrInst = config->zHazardplt ? 0x0320fc09 : 0x0320f809 ;
303
- write32<e> (buf + 24 , jalrInst); // jalr.hb $25 or jalr $25
304
- write32<e> (buf + 28 , 0x2718fffe ); // subu $24, $24, 2
301
+ write32 (buf + 24 , jalrInst); // jalr.hb $25 or jalr $25
302
+ write32 (buf + 28 , 0x2718fffe ); // subu $24, $24, 2
305
303
306
304
uint64_t gotPlt = in.gotPlt ->getVA ();
307
305
writeValue<e>(buf, gotPlt + 0x8000 , 16 , 16 );
@@ -319,16 +317,16 @@ void MIPS<ELFT>::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
319
317
memset (buf, 0 , pltEntrySize);
320
318
321
319
if (isMipsR6 ()) {
322
- write16<e> (buf, 0x7840 ); // addiupc $2, (GOTPLT) - .
323
- write16<e> (buf + 4 , 0xff22 ); // lw $25, 0($2)
324
- write16<e> (buf + 8 , 0x0f02 ); // move $24, $2
325
- write16<e> (buf + 10 , 0x4723 ); // jrc $25 / jr16 $25
320
+ write16 (buf, 0x7840 ); // addiupc $2, (GOTPLT) - .
321
+ write16 (buf + 4 , 0xff22 ); // lw $25, 0($2)
322
+ write16 (buf + 8 , 0x0f02 ); // move $24, $2
323
+ write16 (buf + 10 , 0x4723 ); // jrc $25 / jr16 $25
326
324
relocateOne (buf, R_MICROMIPS_PC19_S2, gotPltEntryAddr - pltEntryAddr);
327
325
} else {
328
- write16<e> (buf, 0x7900 ); // addiupc $2, (GOTPLT) - .
329
- write16<e> (buf + 4 , 0xff22 ); // lw $25, 0($2)
330
- write16<e> (buf + 8 , 0x4599 ); // jrc $25 / jr16 $25
331
- write16<e> (buf + 10 , 0x0f02 ); // move $24, $2
326
+ write16 (buf, 0x7900 ); // addiupc $2, (GOTPLT) - .
327
+ write16 (buf + 4 , 0xff22 ); // lw $25, 0($2)
328
+ write16 (buf + 8 , 0x4599 ); // jrc $25 / jr16 $25
329
+ write16 (buf + 10 , 0x0f02 ); // move $24, $2
332
330
relocateOne (buf, R_MICROMIPS_PC23_S2, gotPltEntryAddr - pltEntryAddr);
333
331
}
334
332
return ;
@@ -339,10 +337,10 @@ void MIPS<ELFT>::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
339
337
: (config->zHazardplt ? 0x03200408 : 0x03200008 );
340
338
uint32_t addInst = ELFT::Is64Bits ? 0x65f80000 : 0x25f80000 ;
341
339
342
- write32<e> (buf, 0x3c0f0000 ); // lui $15, %hi(.got.plt entry)
343
- write32<e> (buf + 4 , loadInst); // l[wd] $25, %lo(.got.plt entry)($15)
344
- write32<e> (buf + 8 , jrInst); // jr $25 / jr.hb $25
345
- write32<e> (buf + 12 , addInst); // [d]addiu $24, $15, %lo(.got.plt entry)
340
+ write32 (buf, 0x3c0f0000 ); // lui $15, %hi(.got.plt entry)
341
+ write32 (buf + 4 , loadInst); // l[wd] $25, %lo(.got.plt entry)($15)
342
+ write32 (buf + 8 , jrInst); // jr $25 / jr.hb $25
343
+ write32 (buf + 12 , addInst); // [d]addiu $24, $15, %lo(.got.plt entry)
346
344
writeValue<e>(buf, gotPltEntryAddr + 0x8000 , 16 , 16 );
347
345
writeValue<e>(buf + 4 , gotPltEntryAddr, 16 , 0 );
348
346
writeValue<e>(buf + 12 , gotPltEntryAddr, 16 , 0 );
@@ -379,24 +377,24 @@ int64_t MIPS<ELFT>::getImplicitAddend(const uint8_t *buf, RelType type) const {
379
377
case R_MIPS_GPREL32:
380
378
case R_MIPS_TLS_DTPREL32:
381
379
case R_MIPS_TLS_TPREL32:
382
- return SignExtend64<32 >(read32<e> (buf));
380
+ return SignExtend64<32 >(read32 (buf));
383
381
case R_MIPS_26:
384
382
// FIXME (simon): If the relocation target symbol is not a PLT entry
385
383
// we should use another expression for calculation:
386
384
// ((A << 2) | (P & 0xf0000000)) >> 2
387
- return SignExtend64<28 >(read32<e> (buf) << 2 );
385
+ return SignExtend64<28 >(read32 (buf) << 2 );
388
386
case R_MIPS_GOT16:
389
387
case R_MIPS_HI16:
390
388
case R_MIPS_PCHI16:
391
- return SignExtend64<16 >(read32<e> (buf)) << 16 ;
389
+ return SignExtend64<16 >(read32 (buf)) << 16 ;
392
390
case R_MIPS_GPREL16:
393
391
case R_MIPS_LO16:
394
392
case R_MIPS_PCLO16:
395
393
case R_MIPS_TLS_DTPREL_HI16:
396
394
case R_MIPS_TLS_DTPREL_LO16:
397
395
case R_MIPS_TLS_TPREL_HI16:
398
396
case R_MIPS_TLS_TPREL_LO16:
399
- return SignExtend64<16 >(read32<e> (buf));
397
+ return SignExtend64<16 >(read32 (buf));
400
398
case R_MICROMIPS_GOT16:
401
399
case R_MICROMIPS_HI16:
402
400
return SignExtend64<16 >(readShuffle<e>(buf)) << 16 ;
@@ -410,21 +408,21 @@ int64_t MIPS<ELFT>::getImplicitAddend(const uint8_t *buf, RelType type) const {
410
408
case R_MICROMIPS_GPREL7_S2:
411
409
return SignExtend64<9 >(readShuffle<e>(buf) << 2 );
412
410
case R_MIPS_PC16:
413
- return SignExtend64<18 >(read32<e> (buf) << 2 );
411
+ return SignExtend64<18 >(read32 (buf) << 2 );
414
412
case R_MIPS_PC19_S2:
415
- return SignExtend64<21 >(read32<e> (buf) << 2 );
413
+ return SignExtend64<21 >(read32 (buf) << 2 );
416
414
case R_MIPS_PC21_S2:
417
- return SignExtend64<23 >(read32<e> (buf) << 2 );
415
+ return SignExtend64<23 >(read32 (buf) << 2 );
418
416
case R_MIPS_PC26_S2:
419
- return SignExtend64<28 >(read32<e> (buf) << 2 );
417
+ return SignExtend64<28 >(read32 (buf) << 2 );
420
418
case R_MIPS_PC32:
421
- return SignExtend64<32 >(read32<e> (buf));
419
+ return SignExtend64<32 >(read32 (buf));
422
420
case R_MICROMIPS_26_S1:
423
421
return SignExtend64<27 >(readShuffle<e>(buf) << 1 );
424
422
case R_MICROMIPS_PC7_S1:
425
- return SignExtend64<8 >(read16<e> (buf) << 1 );
423
+ return SignExtend64<8 >(read16 (buf) << 1 );
426
424
case R_MICROMIPS_PC10_S1:
427
- return SignExtend64<11 >(read16<e> (buf) << 1 );
425
+ return SignExtend64<11 >(read16 (buf) << 1 );
428
426
case R_MICROMIPS_PC16_S1:
429
427
return SignExtend64<17 >(readShuffle<e>(buf) << 1 );
430
428
case R_MICROMIPS_PC18_S3:
@@ -494,7 +492,7 @@ static uint64_t fixupCrossModeJump(uint8_t *loc, RelType type, uint64_t val) {
494
492
495
493
switch (type) {
496
494
case R_MIPS_26: {
497
- uint32_t inst = read32<e> (loc) >> 26 ;
495
+ uint32_t inst = read32 (loc) >> 26 ;
498
496
if (inst == 0x3 || inst == 0x1d ) { // JAL or JALX
499
497
writeValue<e>(loc, 0x1d << 26 , 32 , 0 );
500
498
return val;
@@ -552,12 +550,12 @@ void MIPS<ELFT>::relocateOne(uint8_t *loc, RelType type, uint64_t val) const {
552
550
case R_MIPS_GPREL32:
553
551
case R_MIPS_TLS_DTPREL32:
554
552
case R_MIPS_TLS_TPREL32:
555
- write32<e> (loc, val);
553
+ write32 (loc, val);
556
554
break ;
557
555
case R_MIPS_64:
558
556
case R_MIPS_TLS_DTPREL64:
559
557
case R_MIPS_TLS_TPREL64:
560
- write64<e> (loc, val);
558
+ write64 (loc, val);
561
559
break ;
562
560
case R_MIPS_26:
563
561
writeValue<e>(loc, val, 26 , 2 );
@@ -643,12 +641,12 @@ void MIPS<ELFT>::relocateOne(uint8_t *loc, RelType type, uint64_t val) const {
643
641
// Replace jalr/jr instructions by bal/b if the target
644
642
// offset fits into the 18-bit range.
645
643
if (isInt<18 >(val)) {
646
- switch (read32<e> (loc)) {
644
+ switch (read32 (loc)) {
647
645
case 0x0320f809 : // jalr $25 => bal sym
648
- write32<e> (loc, 0x04110000 | ((val >> 2 ) & 0xffff ));
646
+ write32 (loc, 0x04110000 | ((val >> 2 ) & 0xffff ));
649
647
break ;
650
648
case 0x03200008 : // jr $25 => b sym
651
- write32<e> (loc, 0x10000000 | ((val >> 2 ) & 0xffff ));
649
+ write32 (loc, 0x10000000 | ((val >> 2 ) & 0xffff ));
652
650
break ;
653
651
}
654
652
}
0 commit comments