169
172
if(r->sym != S && r->sym->type == SDYNIMPORT)
170
173
diag("unhandled relocation for %s (type %d rtype %d)", r->sym->name, r->sym->type, r->type);
172
if(r->sym != S && !r->sym->reachable)
175
if(r->sym != S && r->sym->type != STLSBSS && !r->sym->reachable)
173
176
diag("unreachable sym in relocation: %s %s", s->name, r->sym->name);
175
178
switch(r->type) {
178
if(archreloc(r, s, &o) < 0)
181
if(linkmode == LinkExternal || archreloc(r, s, &o) < 0)
179
182
diag("unknown reloc %d", r->type);
189
if(linkmode == LinkExternal && r->sym->type != SCONST) {
192
// set up addend for eventual relocation via outer symbol.
195
while(rs->outer != nil) {
196
r->xadd += symaddr(rs) - symaddr(rs->outer);
199
if(rs->type != SHOSTOBJ && rs->sect == nil)
200
diag("missing section for %s", rs->name);
207
} else if(HEADTYPE == Hdarwin) {
208
if(rs->type != SHOSTOBJ)
211
diag("unhandled pcrel relocation for %s", headtype);
182
215
o = symaddr(r->sym) + r->add;
185
// r->sym can be null when CALL $(constant) is transformed from absoulte PC to relative PC call.
218
// r->sym can be null when CALL $(constant) is transformed from absolute PC to relative PC call.
219
if(linkmode == LinkExternal && r->sym && r->sym->type != SCONST && r->sym->sect != cursym->sect) {
222
// set up addend for eventual relocation via outer symbol.
225
while(rs->outer != nil) {
226
r->xadd += symaddr(rs) - symaddr(rs->outer);
229
r->xadd -= r->siz; // relative to address after the relocated chunk
230
if(rs->type != SHOSTOBJ && rs->sect == nil)
231
diag("missing section for %s", rs->name);
238
} else if(HEADTYPE == Hdarwin) {
239
if(rs->type != SHOSTOBJ)
240
o += symaddr(rs) - rs->sect->vaddr;
243
diag("unhandled pcrel relocation for %s", headtype);
188
249
o += symaddr(r->sym);
189
o += r->add - (s->value + r->off + r->siz);
250
// NOTE: The (int32) cast on the next line works around a bug in Plan 9's 8c
251
// compiler. The expression s->value + r->off + r->siz is int32 + int32 +
252
// uchar, and Plan 9 8c incorrectly treats the expression as type uint32
253
// instead of int32, causing incorrect values when sign extended for adding
254
// to o. The bug only occurs on Plan 9, because this C program is compiled by
255
// the standard host compiler (gcc on most other systems).
256
o += r->add - (s->value + r->off + (int32)r->siz);
192
259
o = r->sym->size + r->add;
967
while(align > s->size && align > 1)
975
aligndatsize(vlong datsize, Sym *s)
977
return rnd(datsize, symalign(s));
980
// maxalign returns the maximum required alignment for
981
// the list of symbols s; the list stops when s->type exceeds type.
983
maxalign(Sym *s, int type)
988
for(; s != S && s->type <= type; s = s->next) {
997
gcaddsym(Sym *gc, Sym *s, vlong off)
1002
if(s->size < PtrSize)
1004
if(strcmp(s->name, ".string") == 0)
1009
//print("gcaddsym: %s %d %s\n", s->name, s->size, gotype->name);
1010
adduintxx(gc, GC_CALL, PtrSize);
1011
adduintxx(gc, off, PtrSize);
1012
addpcrelplus(gc, decodetype_gc(gotype), 3*PtrSize+4);
1014
adduintxx(gc, 0, 4);
1016
//print("gcaddsym: %s %d <unknown type>\n", s->name, s->size);
1017
for(a = -off&(PtrSize-1); a+PtrSize<=s->size; a+=PtrSize) {
1018
adduintxx(gc, GC_APTR, PtrSize);
1019
adduintxx(gc, off+a, PtrSize);
1025
growdatsize(vlong *datsizep, Sym *s)
1029
datsize = *datsizep;
1031
diag("negative size (datsize = %lld, s->size = %lld)", datsize, s->size);
1032
if(datsize + s->size < datsize)
1033
diag("symbol too large (datsize = %lld, s->size = %lld)", datsize, s->size);
1034
*datsizep = datsize + s->size;
800
Section *sect, *noptr;
801
1043
Sym *s, *last, **l;
1044
Sym *gcdata1, *gcbss1;
804
1047
Bprint(&bso, "%5.2f dodata\n", cputime());
1050
// define garbage collection symbols
1051
gcdata1 = lookup("gcdata", 0);
1052
gcdata1->type = STYPE;
1053
gcdata1->reachable = 1;
1054
gcbss1 = lookup("gcbss", 0);
1055
gcbss1->type = STYPE;
1056
gcbss1->reachable = 1;
1058
// size of .data and .bss section. the zero value is later replaced by the actual size of the section.
1059
adduintxx(gcdata1, 0, PtrSize);
1060
adduintxx(gcbss1, 0, PtrSize);
847
datap = datsort(datap);
1107
for(s=datap; s != nil; s = s->next) {
1109
s->type = SDATARELRO;
1112
datap = listsort(datap, datcmp, offsetof(Sym, next));
850
* allocate data sections. list is sorted by type,
1115
* allocate sections. list is sorted by type,
851
1116
* so we can just walk it for each piece we want to emit.
1117
* segdata is processed before segtext, because we need
1118
* to see all symbols in the .data and .bss sections in order
1119
* to generate garbage collection information.
1124
/* skip symbols belonging to segtext */
1126
for(; s != nil && s->type < SELFSECT; s = s->next)
1129
/* writable ELF sections */
1131
for(; s != nil && s->type < SNOPTRDATA; s = s->next) {
1132
sect = addsection(&segdata, s->name, 06);
1133
sect->align = symalign(s);
1134
datsize = rnd(datsize, sect->align);
1135
sect->vaddr = datsize;
1139
growdatsize(&datsize, s);
1140
sect->len = datsize - sect->vaddr;
1143
/* pointer-free data */
1144
sect = addsection(&segdata, ".noptrdata", 06);
1145
sect->align = maxalign(s, SDATARELRO-1);
1146
datsize = rnd(datsize, sect->align);
1147
sect->vaddr = datsize;
1148
lookup("noptrdata", 0)->sect = sect;
1149
lookup("enoptrdata", 0)->sect = sect;
1150
for(; s != nil && s->type < SDATARELRO; s = s->next) {
1151
datsize = aligndatsize(datsize, s);
1155
growdatsize(&datsize, s);
1157
sect->len = datsize - sect->vaddr;
1159
/* dynamic relocated rodata */
1161
sect = addsection(&segdata, ".data.rel.ro", 06);
1162
sect->align = maxalign(s, SDATARELRO);
1163
datsize = rnd(datsize, sect->align);
1164
sect->vaddr = datsize;
1165
lookup("datarelro", 0)->sect = sect;
1166
lookup("edatarelro", 0)->sect = sect;
1167
for(; s != nil && s->type == SDATARELRO; s = s->next) {
1168
datsize = aligndatsize(datsize, s);
1172
growdatsize(&datsize, s);
1174
sect->len = datsize - sect->vaddr;
1178
sect = addsection(&segdata, ".data", 06);
1179
sect->align = maxalign(s, SBSS-1);
1180
datsize = rnd(datsize, sect->align);
1181
sect->vaddr = datsize;
1182
lookup("data", 0)->sect = sect;
1183
lookup("edata", 0)->sect = sect;
1184
for(; s != nil && s->type < SBSS; s = s->next) {
1185
if(s->type == SDATARELRO) {
1187
diag("unexpected symbol type %d", s->type);
1191
datsize = aligndatsize(datsize, s);
1193
gcaddsym(gcdata1, s, datsize - sect->vaddr); // gc
1194
growdatsize(&datsize, s);
1196
sect->len = datsize - sect->vaddr;
1198
adduintxx(gcdata1, GC_END, PtrSize);
1199
setuintxx(gcdata1, 0, sect->len, PtrSize);
1202
sect = addsection(&segdata, ".bss", 06);
1203
sect->align = maxalign(s, SNOPTRBSS-1);
1204
datsize = rnd(datsize, sect->align);
1205
sect->vaddr = datsize;
1206
lookup("bss", 0)->sect = sect;
1207
lookup("ebss", 0)->sect = sect;
1208
for(; s != nil && s->type < SNOPTRBSS; s = s->next) {
1210
datsize = aligndatsize(datsize, s);
1212
gcaddsym(gcbss1, s, datsize - sect->vaddr); // gc
1213
growdatsize(&datsize, s);
1215
sect->len = datsize - sect->vaddr;
1217
adduintxx(gcbss1, GC_END, PtrSize);
1218
setuintxx(gcbss1, 0, sect->len, PtrSize);
1220
/* pointer-free bss */
1221
sect = addsection(&segdata, ".noptrbss", 06);
1222
sect->align = maxalign(s, SNOPTRBSS);
1223
datsize = rnd(datsize, sect->align);
1224
sect->vaddr = datsize;
1225
lookup("noptrbss", 0)->sect = sect;
1226
lookup("enoptrbss", 0)->sect = sect;
1227
for(; s != nil && s->type == SNOPTRBSS; s = s->next) {
1228
datsize = aligndatsize(datsize, s);
1231
growdatsize(&datsize, s);
1233
sect->len = datsize - sect->vaddr;
1234
lookup("end", 0)->sect = sect;
1236
// 6g uses 4-byte relocation offsets, so the entire segment must fit in 32 bits.
1237
if(datsize != (uint32)datsize) {
1238
diag("data or bss segment too large");
1241
if(iself && linkmode == LinkExternal && s != nil && s->type == STLSBSS && HEADTYPE != Hopenbsd) {
1242
sect = addsection(&segdata, ".tbss", 06);
1243
sect->align = PtrSize;
1246
for(; s != nil && s->type == STLSBSS; s = s->next) {
1247
datsize = aligndatsize(datsize, s);
1250
growdatsize(&datsize, s);
1252
sect->len = datsize;
1257
diag("unexpected symbol type %d for %s", s->type, s->name);
1260
/* we finished segdata, begin segtext */
854
1263
/* read-only data */
855
1264
sect = addsection(&segtext, ".rodata", 04);
1265
sect->align = maxalign(s, STYPELINK-1);
856
1266
sect->vaddr = 0;
1267
lookup("rodata", 0)->sect = sect;
1268
lookup("erodata", 0)->sect = sect;
859
for(; s != nil && s->type < SSYMTAB; s = s->next) {
861
datsize = rnd(datsize, s->align);
864
datsize += rnd(s->size, PtrSize);
1270
for(; s != nil && s->type < STYPELINK; s = s->next) {
1271
datsize = aligndatsize(datsize, s);
1275
growdatsize(&datsize, s);
1277
sect->len = datsize - sect->vaddr;
1280
sect = addsection(&segtext, ".typelink", 04);
1281
sect->align = maxalign(s, STYPELINK);
1282
datsize = rnd(datsize, sect->align);
1283
sect->vaddr = datsize;
1284
lookup("typelink", 0)->sect = sect;
1285
lookup("etypelink", 0)->sect = sect;
1286
for(; s != nil && s->type == STYPELINK; s = s->next) {
1287
datsize = aligndatsize(datsize, s);
1291
growdatsize(&datsize, s);
866
1293
sect->len = datsize - sect->vaddr;
869
1296
sect = addsection(&segtext, ".gosymtab", 04);
1297
sect->align = maxalign(s, SPCLNTAB-1);
1298
datsize = rnd(datsize, sect->align);
870
1299
sect->vaddr = datsize;
1300
lookup("symtab", 0)->sect = sect;
1301
lookup("esymtab", 0)->sect = sect;
871
1302
for(; s != nil && s->type < SPCLNTAB; s = s->next) {
1303
datsize = aligndatsize(datsize, s);
872
1305
s->type = SRODATA;
873
1306
s->value = datsize;
1307
growdatsize(&datsize, s);
876
1309
sect->len = datsize - sect->vaddr;
877
datsize = rnd(datsize, PtrSize);
880
1312
sect = addsection(&segtext, ".gopclntab", 04);
1313
sect->align = maxalign(s, SELFROSECT-1);
1314
datsize = rnd(datsize, sect->align);
881
1315
sect->vaddr = datsize;
1316
lookup("pclntab", 0)->sect = sect;
1317
lookup("epclntab", 0)->sect = sect;
882
1318
for(; s != nil && s->type < SELFROSECT; s = s->next) {
1319
datsize = aligndatsize(datsize, s);
883
1321
s->type = SRODATA;
884
1322
s->value = datsize;
1323
growdatsize(&datsize, s);
887
1325
sect->len = datsize - sect->vaddr;
888
datsize = rnd(datsize, PtrSize);
890
/* read-only ELF sections */
1327
/* read-only ELF, Mach-O sections */
891
1328
for(; s != nil && s->type < SELFSECT; s = s->next) {
892
1329
sect = addsection(&segtext, s->name, 04);
894
datsize = rnd(datsize, s->align);
1330
sect->align = symalign(s);
1331
datsize = rnd(datsize, sect->align);
895
1332
sect->vaddr = datsize;
896
1334
s->type = SRODATA;
897
1335
s->value = datsize;
898
datsize += rnd(s->size, PtrSize);
1336
growdatsize(&datsize, s);
899
1337
sect->len = datsize - sect->vaddr;
902
/* writable ELF sections */
904
for(; s != nil && s->type < SNOPTRDATA; s = s->next) {
905
sect = addsection(&segdata, s->name, 06);
907
datsize = rnd(datsize, s->align);
908
sect->vaddr = datsize;
911
datsize += rnd(s->size, PtrSize);
912
sect->len = datsize - sect->vaddr;
1340
// 6g uses 4-byte relocation offsets, so the entire segment must fit in 32 bits.
1341
if(datsize != (uint32)datsize) {
1342
diag("text segment too large");
915
/* pointer-free data, then data */
916
sect = addsection(&segdata, ".noptrdata", 06);
917
sect->vaddr = datsize;
919
for(; ; s = s->next) {
920
if((s == nil || s->type >= SDATA) && sect == noptr) {
921
// finish noptrdata, start data
922
datsize = rnd(datsize, 8);
923
sect->len = datsize - sect->vaddr;
924
sect = addsection(&segdata, ".data", 06);
925
sect->vaddr = datsize;
927
if(s == nil || s->type >= SBSS) {
929
sect->len = datsize - sect->vaddr;
939
datsize = rnd(datsize, s->align);
943
datsize = rnd(datsize, 2);
945
datsize = rnd(datsize, 4);
947
datsize = rnd(datsize, 8);
952
/* bss, then pointer-free bss */
954
sect = addsection(&segdata, ".bss", 06);
955
sect->vaddr = datsize;
956
for(; ; s = s->next) {
957
if((s == nil || s->type >= SNOPTRBSS) && noptr == nil) {
958
// finish bss, start noptrbss
959
datsize = rnd(datsize, 8);
960
sect->len = datsize - sect->vaddr;
961
sect = addsection(&segdata, ".noptrbss", 06);
962
sect->vaddr = datsize;
966
sect->len = datsize - sect->vaddr;
969
if(s->type > SNOPTRBSS) {
971
diag("unexpected symbol type %d", s->type);
979
datsize = rnd(datsize, s->align);
983
datsize = rnd(datsize, 2);
985
datsize = rnd(datsize, 4);
987
datsize = rnd(datsize, 8);
1345
/* number the sections */
1347
for(sect = segtext.sect; sect != nil; sect = sect->next)
1349
for(sect = segdata.sect; sect != nil; sect = sect->next)
993
1353
// assign addresses to text