Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(60)

Side by Side Diff: llvm/tools/llc/StubMaker.cpp

Issue 10151020: llvm: stubbed st_size does matter for copy-relocs/bss (Closed)
Patch Set: comment Created 8 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Create a high-level representation of the needed library. 1 // Create a high-level representation of the needed library.
2 2
3 #include "StubMaker.h" 3 #include "StubMaker.h"
4 4
5 #include "llvm/ADT/StringMap.h" 5 #include "llvm/ADT/StringMap.h"
6 #include "llvm/ADT/StringRef.h" 6 #include "llvm/ADT/StringRef.h"
7 #include "llvm/ADT/Triple.h" 7 #include "llvm/ADT/Triple.h"
8 #include "llvm/DerivedTypes.h" 8 #include "llvm/DerivedTypes.h"
9 #include "llvm/Support/ELF.h" 9 #include "llvm/Support/ELF.h"
10 #include "llvm/Support/ErrorHandling.h" 10 #include "llvm/Support/ErrorHandling.h"
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
81 81
82 static unsigned char GetELFVisibility(const GlobalValue *GV) { 82 static unsigned char GetELFVisibility(const GlobalValue *GV) {
83 switch (GV->getVisibility()) { 83 switch (GV->getVisibility()) {
84 case GlobalValue::DefaultVisibility: return ELF::STV_DEFAULT; 84 case GlobalValue::DefaultVisibility: return ELF::STV_DEFAULT;
85 case GlobalValue::HiddenVisibility: return ELF::STV_HIDDEN; 85 case GlobalValue::HiddenVisibility: return ELF::STV_HIDDEN;
86 case GlobalValue::ProtectedVisibility: return ELF::STV_PROTECTED; 86 case GlobalValue::ProtectedVisibility: return ELF::STV_PROTECTED;
87 } 87 }
88 llvm_unreachable("Unknown visibility in GETELFVisibility"); 88 llvm_unreachable("Unknown visibility in GETELFVisibility");
89 } 89 }
90 90
91 // Return a value for the symbol table's st_size, which is the number of bytes 91 static ELF::Elf32_Word GetElfSizeForType(const GlobalValue *GV,
92 // in a data object. This may be 0 if the size is unknown. 92 const Type *ElemType) {
93 static ELF::Elf32_Word GetELFSize(const GlobalValue *GV) {
94 const class PointerType *PT = GV->getType();
95 const Type *ElemType = PT->getElementType();
96 unsigned bit_size = ElemType->getPrimitiveSizeInBits(); 93 unsigned bit_size = ElemType->getPrimitiveSizeInBits();
97 if (bit_size != 0) { 94 if (bit_size != 0) {
98 return bit_size / 8; 95 return bit_size / 8;
99 } 96 }
97 if (isa<PointerType>(ElemType)) {
98 // Pointers are 32-bit for NaCl.
99 return 4;
100 }
101 if (isa<FunctionType>(ElemType)) {
102 // This is not a data object, so just say unknown (0).
103 return 0;
104 }
100 if (const ArrayType *ATy = dyn_cast<ArrayType>(ElemType)) { 105 if (const ArrayType *ATy = dyn_cast<ArrayType>(ElemType)) {
101 unsigned elem_bit_size = ATy->getElementType()->getPrimitiveSizeInBits(); 106 unsigned elem_bit_size = GetElfSizeForType(GV, ATy->getElementType());
102 if (elem_bit_size != 0) { 107 if (elem_bit_size != 0) {
103 unsigned num_elems = ATy->getNumElements(); 108 unsigned num_elems = ATy->getNumElements();
104 if (num_elems != 0) { 109 if (num_elems != 0) {
105 return elem_bit_size * num_elems / 8; 110 return elem_bit_size * num_elems / 8;
106 } 111 }
107 } 112 }
108 } 113 }
109 // For other cases, claim that we don't know the size (0). 114 if (const VectorType *VTy = dyn_cast<VectorType>(ElemType)) {
115 unsigned bit_width = VTy->getBitWidth();
116 if (bit_width) {
117 return bit_width / 8;
118 } else {
119 // It's a vector of pointers, and pointers are 32-bit in NaCl
120 return VTy->getNumElements() * 4;
121 }
122 }
123 if (const StructType *STy = dyn_cast<StructType>(ElemType)) {
124 // Alignment padding should have been added to the type in the front-end.
125 unsigned size_so_far = 0;
126 for (unsigned i = 0; i < STy->getNumElements(); ++i) {
127 size_so_far += GetElfSizeForType(GV, STy->getElementType(i));
128 }
129 return size_so_far;
130 }
131 // Unknown type!
132 DEBUG({
133 dbgs() << "Unknown GetELFSize for var=";
134 GV->dump();
135 dbgs() << " type= ";
136 ElemType->dump();
137 dbgs() << "\n";
138 });
139 llvm_unreachable("Unhandled type for GetELFSize");
110 return 0; 140 return 0;
111 } 141 }
112 142
143 // Return a value for the symbol table's st_size, which is the number of bytes
144 // in a data object. Functions may report unknown size 0 (not data objects).
145 // This is known to be important for symbols that may sit in BSS
146 // with copy relocations (to know how much to copy).
147 static ELF::Elf32_Word GetELFSize(const GlobalValue *GV) {
148 const class PointerType *PT = GV->getType();
149 const Type *ElemType = PT->getElementType();
150 return GetElfSizeForType(GV, ElemType);
151 }
152
113 static unsigned char GetELFType(const GlobalValue *GV) { 153 static unsigned char GetELFType(const GlobalValue *GV) {
114 if (const GlobalVariable *GVar = dyn_cast<GlobalVariable>(GV)) { 154 if (const GlobalVariable *GVar = dyn_cast<GlobalVariable>(GV)) {
115 return GVar->isThreadLocal() ? ELF::STT_TLS : ELF::STT_OBJECT; 155 return GVar->isThreadLocal() ? ELF::STT_TLS : ELF::STT_OBJECT;
116 } else if (isa<Function>(GV)) { 156 } else if (isa<Function>(GV)) {
117 // TODO(pdox): Handle STT_GNU_IFUNC 157 // TODO(pdox): Handle STT_GNU_IFUNC
118 return ELF::STT_FUNC; 158 return ELF::STT_FUNC;
119 } 159 }
120 // TODO(pdox): Do we need to resolve GlobalAliases? 160 // TODO(pdox): Do we need to resolve GlobalAliases?
121 llvm_unreachable("Unknown GlobalValue type in GetELFType!"); 161 llvm_unreachable("Unknown GlobalValue type in GetELFType!");
122 } 162 }
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
180 } 220 }
181 221
182 void FreeStubList(llvm::SmallVectorImpl<ELFStub*> *StubList) { 222 void FreeStubList(llvm::SmallVectorImpl<ELFStub*> *StubList) {
183 for (unsigned i = 0; i < StubList->size(); ++i) { 223 for (unsigned i = 0; i < StubList->size(); ++i) {
184 delete (*StubList)[i]; 224 delete (*StubList)[i];
185 } 225 }
186 StubList->clear(); 226 StubList->clear();
187 } 227 }
188 228
189 } // namespace 229 } // namespace
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698