blob: 1597d2b31d2223e92dd801ad9d7d92c059efc087 [file] [log] [blame]
Dan Gohmanf17a25c2007-07-18 16:29:46 +00001//===-- X86ELFWriterInfo.cpp - ELF Writer Info for the X86 backend --------===//
2//
3// The LLVM Compiler Infrastructure
4//
Chris Lattner081ce942007-12-29 20:36:04 +00005// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
Dan Gohmanf17a25c2007-07-18 16:29:46 +00007//
8//===----------------------------------------------------------------------===//
9//
10// This file implements ELF writer information for the X86 backend.
11//
12//===----------------------------------------------------------------------===//
13
14#include "X86ELFWriterInfo.h"
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000015#include "X86Relocations.h"
Bruno Cardoso Lopesde5fdb42009-06-11 22:13:00 +000016#include "llvm/Function.h"
Edwin Török675d5622009-07-11 20:10:48 +000017#include "llvm/Support/ErrorHandling.h"
Bruno Cardoso Lopesde5fdb42009-06-11 22:13:00 +000018#include "llvm/Target/TargetData.h"
Bruno Cardoso Lopes8c25df12009-06-11 19:16:03 +000019#include "llvm/Target/TargetMachine.h"
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000020
Dan Gohmanf17a25c2007-07-18 16:29:46 +000021using namespace llvm;
22
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000023//===----------------------------------------------------------------------===//
24// Implementation of the X86ELFWriterInfo class
25//===----------------------------------------------------------------------===//
26
Bruno Cardoso Lopes8c25df12009-06-11 19:16:03 +000027X86ELFWriterInfo::X86ELFWriterInfo(TargetMachine &TM)
28 : TargetELFWriterInfo(TM) {
29 bool is64Bit = TM.getTargetData()->getPointerSizeInBits() == 64;
30 EMachine = is64Bit ? EM_X86_64 : EM_386;
31 }
32
Dan Gohmanf17a25c2007-07-18 16:29:46 +000033X86ELFWriterInfo::~X86ELFWriterInfo() {}
Bruno Cardoso Lopes8c25df12009-06-11 19:16:03 +000034
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000035unsigned X86ELFWriterInfo::getRelocationType(unsigned MachineRelTy) const {
36 if (is64Bit) {
37 switch(MachineRelTy) {
38 case X86::reloc_pcrel_word:
39 return R_X86_64_PC32;
40 case X86::reloc_absolute_word:
41 return R_X86_64_32;
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000042 case X86::reloc_absolute_word_sext:
43 return R_X86_64_32S;
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000044 case X86::reloc_absolute_dword:
45 return R_X86_64_64;
46 case X86::reloc_picrel_word:
47 default:
Bruno Cardoso Lopes8c203922009-07-18 19:30:09 +000048 llvm_unreachable("unknown x86_64 machine relocation type");
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000049 }
50 } else {
51 switch(MachineRelTy) {
52 case X86::reloc_pcrel_word:
53 return R_386_PC32;
54 case X86::reloc_absolute_word:
55 return R_386_32;
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000056 case X86::reloc_absolute_word_sext:
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000057 case X86::reloc_absolute_dword:
58 case X86::reloc_picrel_word:
59 default:
Bruno Cardoso Lopes8c203922009-07-18 19:30:09 +000060 llvm_unreachable("unknown x86 machine relocation type");
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000061 }
62 }
63 return 0;
64}
65
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000066long int X86ELFWriterInfo::getDefaultAddendForRelTy(unsigned RelTy,
67 long int Modifier) const {
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000068 if (is64Bit) {
69 switch(RelTy) {
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000070 case R_X86_64_PC32: return Modifier - 4;
Bruno Cardoso Lopes88ac2e42009-07-21 06:51:32 +000071 case R_X86_64_32:
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000072 case R_X86_64_32S:
Bruno Cardoso Lopes88ac2e42009-07-21 06:51:32 +000073 case R_X86_64_64:
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000074 return Modifier;
Bruno Cardoso Lopes8c203922009-07-18 19:30:09 +000075 default:
76 llvm_unreachable("unknown x86_64 relocation type");
77 }
78 } else {
79 switch(RelTy) {
Bruno Cardoso Lopesb4be2152009-08-05 06:57:03 +000080 case R_386_PC32: return Modifier - 4;
81 case R_386_32: return Modifier;
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000082 default:
Edwin Törökbd448e32009-07-14 16:55:14 +000083 llvm_unreachable("unknown x86 relocation type");
Bruno Cardoso Lopes6d4086b2009-06-22 19:16:16 +000084 }
85 }
86 return 0;
87}
Bruno Cardoso Lopes8c203922009-07-18 19:30:09 +000088
89unsigned X86ELFWriterInfo::getRelocationTySize(unsigned RelTy) const {
90 if (is64Bit) {
91 switch(RelTy) {
92 case R_X86_64_PC32:
93 case R_X86_64_32:
Bruno Cardoso Lopes2c1fe1a2009-07-18 23:24:01 +000094 case R_X86_64_32S:
Bruno Cardoso Lopes8c203922009-07-18 19:30:09 +000095 return 32;
96 case R_X86_64_64:
97 return 64;
98 default:
99 llvm_unreachable("unknown x86_64 relocation type");
100 }
101 } else {
102 switch(RelTy) {
103 case R_386_PC32:
104 case R_386_32:
105 return 32;
106 default:
107 llvm_unreachable("unknown x86 relocation type");
108 }
109 }
110 return 0;
111}
112
Bruno Cardoso Lopesc4d2daf2009-07-20 08:52:02 +0000113bool X86ELFWriterInfo::isPCRelativeRel(unsigned RelTy) const {
114 if (is64Bit) {
115 switch(RelTy) {
116 case R_X86_64_PC32:
117 return true;
118 case R_X86_64_32:
119 case R_X86_64_32S:
120 case R_X86_64_64:
121 return false;
122 default:
123 llvm_unreachable("unknown x86_64 relocation type");
124 }
125 } else {
126 switch(RelTy) {
127 case R_386_PC32:
128 return true;
129 case R_386_32:
130 return false;
131 default:
132 llvm_unreachable("unknown x86 relocation type");
133 }
134 }
135 return 0;
136}
137
Bruno Cardoso Lopes530a2d32009-07-18 20:52:11 +0000138unsigned X86ELFWriterInfo::getAbsoluteLabelMachineRelTy() const {
139 return is64Bit ?
140 X86::reloc_absolute_dword : X86::reloc_absolute_word;
Bruno Cardoso Lopes8c203922009-07-18 19:30:09 +0000141}
142
Bruno Cardoso Lopesc4d2daf2009-07-20 08:52:02 +0000143long int X86ELFWriterInfo::computeRelocation(unsigned SymOffset,
144 unsigned RelOffset,
145 unsigned RelTy) const {
146
147 if (RelTy == R_X86_64_PC32 || RelTy == R_386_PC32)
148 return SymOffset - (RelOffset + 4);
149 else
150 assert("computeRelocation unknown for this relocation type");
151
152 return 0;
153}