github.com/kdevb0x/go@v0.0.0-20180115030120-39687051e9e7/src/cmd/link/internal/ld/data.go (about) 1 // Derived from Inferno utils/6l/obj.c and utils/6l/span.c 2 // https://bitbucket.org/inferno-os/inferno-os/src/default/utils/6l/obj.c 3 // https://bitbucket.org/inferno-os/inferno-os/src/default/utils/6l/span.c 4 // 5 // Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved. 6 // Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net) 7 // Portions Copyright © 1997-1999 Vita Nuova Limited 8 // Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com) 9 // Portions Copyright © 2004,2006 Bruce Ellis 10 // Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net) 11 // Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others 12 // Portions Copyright © 2009 The Go Authors. All rights reserved. 13 // 14 // Permission is hereby granted, free of charge, to any person obtaining a copy 15 // of this software and associated documentation files (the "Software"), to deal 16 // in the Software without restriction, including without limitation the rights 17 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 18 // copies of the Software, and to permit persons to whom the Software is 19 // furnished to do so, subject to the following conditions: 20 // 21 // The above copyright notice and this permission notice shall be included in 22 // all copies or substantial portions of the Software. 23 // 24 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 25 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 26 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 27 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 28 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 29 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 30 // THE SOFTWARE. 31 32 package ld 33 34 import ( 35 "cmd/internal/gcprog" 36 "cmd/internal/objabi" 37 "cmd/internal/sys" 38 "cmd/link/internal/sym" 39 "fmt" 40 "log" 41 "os" 42 "sort" 43 "strconv" 44 "strings" 45 "sync" 46 ) 47 48 // isRuntimeDepPkg returns whether pkg is the runtime package or its dependency 49 func isRuntimeDepPkg(pkg string) bool { 50 switch pkg { 51 case "runtime", 52 "sync/atomic": // runtime may call to sync/atomic, due to go:linkname 53 return true 54 } 55 return strings.HasPrefix(pkg, "runtime/internal/") && !strings.HasSuffix(pkg, "_test") 56 } 57 58 // Estimate the max size needed to hold any new trampolines created for this function. This 59 // is used to determine when the section can be split if it becomes too large, to ensure that 60 // the trampolines are in the same section as the function that uses them. 61 func maxSizeTrampolinesPPC64(s *sym.Symbol, isTramp bool) uint64 { 62 // If Thearch.Trampoline is nil, then trampoline support is not available on this arch. 63 // A trampoline does not need any dependent trampolines. 64 if Thearch.Trampoline == nil || isTramp { 65 return 0 66 } 67 68 n := uint64(0) 69 for ri := range s.R { 70 r := &s.R[ri] 71 if r.Type.IsDirectJump() { 72 n++ 73 } 74 } 75 // Trampolines in ppc64 are 4 instructions. 76 return n * 16 77 } 78 79 // detect too-far jumps in function s, and add trampolines if necessary 80 // ARM, PPC64 & PPC64LE support trampoline insertion for internal and external linking 81 // On PPC64 & PPC64LE the text sections might be split but will still insert trampolines 82 // where necessary. 83 func trampoline(ctxt *Link, s *sym.Symbol) { 84 if Thearch.Trampoline == nil { 85 return // no need or no support of trampolines on this arch 86 } 87 88 for ri := range s.R { 89 r := &s.R[ri] 90 if !r.Type.IsDirectJump() { 91 continue 92 } 93 if Symaddr(r.Sym) == 0 && r.Sym.Type != sym.SDYNIMPORT { 94 if r.Sym.File != s.File { 95 if !isRuntimeDepPkg(s.File) || !isRuntimeDepPkg(r.Sym.File) { 96 Errorf(s, "unresolved inter-package jump to %s(%s)", r.Sym, r.Sym.File) 97 } 98 // runtime and its dependent packages may call to each other. 99 // they are fine, as they will be laid down together. 100 } 101 continue 102 } 103 104 Thearch.Trampoline(ctxt, r, s) 105 } 106 107 } 108 109 // resolve relocations in s. 110 func relocsym(ctxt *Link, s *sym.Symbol) { 111 for ri := int32(0); ri < int32(len(s.R)); ri++ { 112 r := &s.R[ri] 113 if r.Done { 114 // Relocation already processed by an earlier phase. 115 continue 116 } 117 r.Done = true 118 off := r.Off 119 siz := int32(r.Siz) 120 if off < 0 || off+siz > int32(len(s.P)) { 121 rname := "" 122 if r.Sym != nil { 123 rname = r.Sym.Name 124 } 125 Errorf(s, "invalid relocation %s: %d+%d not in [%d,%d)", rname, off, siz, 0, len(s.P)) 126 continue 127 } 128 129 if r.Sym != nil && ((r.Sym.Type == 0 && !r.Sym.Attr.VisibilityHidden()) || r.Sym.Type == sym.SXREF) { 130 // When putting the runtime but not main into a shared library 131 // these symbols are undefined and that's OK. 132 if ctxt.BuildMode == BuildModeShared { 133 if r.Sym.Name == "main.main" || r.Sym.Name == "main.init" { 134 r.Sym.Type = sym.SDYNIMPORT 135 } else if strings.HasPrefix(r.Sym.Name, "go.info.") { 136 // Skip go.info symbols. They are only needed to communicate 137 // DWARF info between the compiler and linker. 138 continue 139 } 140 } else { 141 Errorf(s, "relocation target %s not defined", r.Sym.Name) 142 continue 143 } 144 } 145 146 if r.Type >= 256 { 147 continue 148 } 149 if r.Siz == 0 { // informational relocation - no work to do 150 continue 151 } 152 if r.Type == objabi.R_DWARFFILEREF { 153 // These should have been processed previously during 154 // line table writing. 155 Errorf(s, "orphan R_DWARFFILEREF reloc to %v", r.Sym.Name) 156 continue 157 } 158 159 // We need to be able to reference dynimport symbols when linking against 160 // shared libraries, and Solaris needs it always 161 if ctxt.HeadType != objabi.Hsolaris && r.Sym != nil && r.Sym.Type == sym.SDYNIMPORT && !ctxt.DynlinkingGo() && !r.Sym.Attr.SubSymbol() { 162 if !(ctxt.Arch.Family == sys.PPC64 && ctxt.LinkMode == LinkExternal && r.Sym.Name == ".TOC.") { 163 Errorf(s, "unhandled relocation for %s (type %d (%s) rtype %d (%s))", r.Sym.Name, r.Sym.Type, r.Sym.Type, r.Type, sym.RelocName(ctxt.Arch, r.Type)) 164 } 165 } 166 if r.Sym != nil && r.Sym.Type != sym.STLSBSS && r.Type != objabi.R_WEAKADDROFF && !r.Sym.Attr.Reachable() { 167 Errorf(s, "unreachable sym in relocation: %s", r.Sym.Name) 168 } 169 170 // TODO(mundaym): remove this special case - see issue 14218. 171 if ctxt.Arch.Family == sys.S390X { 172 switch r.Type { 173 case objabi.R_PCRELDBL: 174 r.Type = objabi.R_PCREL 175 r.Variant = sym.RV_390_DBL 176 case objabi.R_CALL: 177 r.Variant = sym.RV_390_DBL 178 } 179 } 180 181 var o int64 182 switch r.Type { 183 default: 184 switch siz { 185 default: 186 Errorf(s, "bad reloc size %#x for %s", uint32(siz), r.Sym.Name) 187 case 1: 188 o = int64(s.P[off]) 189 case 2: 190 o = int64(ctxt.Arch.ByteOrder.Uint16(s.P[off:])) 191 case 4: 192 o = int64(ctxt.Arch.ByteOrder.Uint32(s.P[off:])) 193 case 8: 194 o = int64(ctxt.Arch.ByteOrder.Uint64(s.P[off:])) 195 } 196 if !Thearch.Archreloc(ctxt, r, s, &o) { 197 Errorf(s, "unknown reloc to %v: %d (%s)", r.Sym.Name, r.Type, sym.RelocName(ctxt.Arch, r.Type)) 198 } 199 case objabi.R_TLS_LE: 200 isAndroidX86 := objabi.GOOS == "android" && (ctxt.Arch.InFamily(sys.AMD64, sys.I386)) 201 202 if ctxt.LinkMode == LinkExternal && ctxt.IsELF && !isAndroidX86 { 203 r.Done = false 204 if r.Sym == nil { 205 r.Sym = ctxt.Tlsg 206 } 207 r.Xsym = r.Sym 208 r.Xadd = r.Add 209 o = 0 210 if ctxt.Arch.Family != sys.AMD64 { 211 o = r.Add 212 } 213 break 214 } 215 216 if ctxt.IsELF && ctxt.Arch.Family == sys.ARM { 217 // On ELF ARM, the thread pointer is 8 bytes before 218 // the start of the thread-local data block, so add 8 219 // to the actual TLS offset (r->sym->value). 220 // This 8 seems to be a fundamental constant of 221 // ELF on ARM (or maybe Glibc on ARM); it is not 222 // related to the fact that our own TLS storage happens 223 // to take up 8 bytes. 224 o = 8 + r.Sym.Value 225 } else if ctxt.IsELF || ctxt.HeadType == objabi.Hplan9 || ctxt.HeadType == objabi.Hdarwin || isAndroidX86 { 226 o = int64(ctxt.Tlsoffset) + r.Add 227 } else if ctxt.HeadType == objabi.Hwindows { 228 o = r.Add 229 } else { 230 log.Fatalf("unexpected R_TLS_LE relocation for %v", ctxt.HeadType) 231 } 232 case objabi.R_TLS_IE: 233 isAndroidX86 := objabi.GOOS == "android" && (ctxt.Arch.InFamily(sys.AMD64, sys.I386)) 234 235 if ctxt.LinkMode == LinkExternal && ctxt.IsELF && !isAndroidX86 { 236 r.Done = false 237 if r.Sym == nil { 238 r.Sym = ctxt.Tlsg 239 } 240 r.Xsym = r.Sym 241 r.Xadd = r.Add 242 o = 0 243 if ctxt.Arch.Family != sys.AMD64 { 244 o = r.Add 245 } 246 break 247 } 248 if ctxt.BuildMode == BuildModePIE && ctxt.IsELF { 249 // We are linking the final executable, so we 250 // can optimize any TLS IE relocation to LE. 251 if Thearch.TLSIEtoLE == nil { 252 log.Fatalf("internal linking of TLS IE not supported on %v", ctxt.Arch.Family) 253 } 254 Thearch.TLSIEtoLE(s, int(off), int(r.Siz)) 255 o = int64(ctxt.Tlsoffset) 256 // TODO: o += r.Add when ctxt.Arch.Family != sys.AMD64? 257 // Why do we treat r.Add differently on AMD64? 258 // Is the external linker using Xadd at all? 259 } else { 260 log.Fatalf("cannot handle R_TLS_IE (sym %s) when linking internally", s.Name) 261 } 262 case objabi.R_ADDR: 263 if ctxt.LinkMode == LinkExternal && r.Sym.Type != sym.SCONST { 264 r.Done = false 265 266 // set up addend for eventual relocation via outer symbol. 267 rs := r.Sym 268 269 r.Xadd = r.Add 270 for rs.Outer != nil { 271 r.Xadd += Symaddr(rs) - Symaddr(rs.Outer) 272 rs = rs.Outer 273 } 274 275 if rs.Type != sym.SHOSTOBJ && rs.Type != sym.SDYNIMPORT && rs.Sect == nil { 276 Errorf(s, "missing section for relocation target %s", rs.Name) 277 } 278 r.Xsym = rs 279 280 o = r.Xadd 281 if ctxt.IsELF { 282 if ctxt.Arch.Family == sys.AMD64 { 283 o = 0 284 } 285 } else if ctxt.HeadType == objabi.Hdarwin { 286 // ld64 for arm64 has a bug where if the address pointed to by o exists in the 287 // symbol table (dynid >= 0), or is inside a symbol that exists in the symbol 288 // table, then it will add o twice into the relocated value. 289 // The workaround is that on arm64 don't ever add symaddr to o and always use 290 // extern relocation by requiring rs->dynid >= 0. 291 if rs.Type != sym.SHOSTOBJ { 292 if ctxt.Arch.Family == sys.ARM64 && rs.Dynid < 0 { 293 Errorf(s, "R_ADDR reloc to %s+%d is not supported on darwin/arm64", rs.Name, o) 294 } 295 if ctxt.Arch.Family != sys.ARM64 { 296 o += Symaddr(rs) 297 } 298 } 299 } else if ctxt.HeadType == objabi.Hwindows { 300 // nothing to do 301 } else { 302 Errorf(s, "unhandled pcrel relocation to %s on %v", rs.Name, ctxt.HeadType) 303 } 304 305 break 306 } 307 308 o = Symaddr(r.Sym) + r.Add 309 310 // On amd64, 4-byte offsets will be sign-extended, so it is impossible to 311 // access more than 2GB of static data; fail at link time is better than 312 // fail at runtime. See https://golang.org/issue/7980. 313 // Instead of special casing only amd64, we treat this as an error on all 314 // 64-bit architectures so as to be future-proof. 315 if int32(o) < 0 && ctxt.Arch.PtrSize > 4 && siz == 4 { 316 Errorf(s, "non-pc-relative relocation address for %s is too big: %#x (%#x + %#x)", r.Sym.Name, uint64(o), Symaddr(r.Sym), r.Add) 317 errorexit() 318 } 319 case objabi.R_DWARFSECREF: 320 if r.Sym.Sect == nil { 321 Errorf(s, "missing DWARF section for relocation target %s", r.Sym.Name) 322 } 323 324 if ctxt.LinkMode == LinkExternal { 325 r.Done = false 326 327 // On most platforms, the external linker needs to adjust DWARF references 328 // as it combines DWARF sections. However, on Darwin, dsymutil does the 329 // DWARF linking, and it understands how to follow section offsets. 330 // Leaving in the relocation records confuses it (see 331 // https://golang.org/issue/22068) so drop them for Darwin. 332 if ctxt.HeadType == objabi.Hdarwin { 333 r.Done = true 334 } 335 336 // PE code emits IMAGE_REL_I386_SECREL and IMAGE_REL_AMD64_SECREL 337 // for R_DWARFSECREF relocations, while R_ADDR is replaced with 338 // IMAGE_REL_I386_DIR32, IMAGE_REL_AMD64_ADDR64 and IMAGE_REL_AMD64_ADDR32. 339 // Do not replace R_DWARFSECREF with R_ADDR for windows - 340 // let PE code emit correct relocations. 341 if ctxt.HeadType != objabi.Hwindows { 342 r.Type = objabi.R_ADDR 343 } 344 345 r.Xsym = ctxt.Syms.ROLookup(r.Sym.Sect.Name, 0) 346 r.Xadd = r.Add + Symaddr(r.Sym) - int64(r.Sym.Sect.Vaddr) 347 348 o = r.Xadd 349 if ctxt.IsELF && ctxt.Arch.Family == sys.AMD64 { 350 o = 0 351 } 352 break 353 } 354 o = Symaddr(r.Sym) + r.Add - int64(r.Sym.Sect.Vaddr) 355 case objabi.R_WEAKADDROFF: 356 if !r.Sym.Attr.Reachable() { 357 continue 358 } 359 fallthrough 360 case objabi.R_ADDROFF: 361 // The method offset tables using this relocation expect the offset to be relative 362 // to the start of the first text section, even if there are multiple. 363 364 if r.Sym.Sect.Name == ".text" { 365 o = Symaddr(r.Sym) - int64(Segtext.Sections[0].Vaddr) + r.Add 366 } else { 367 o = Symaddr(r.Sym) - int64(r.Sym.Sect.Vaddr) + r.Add 368 } 369 370 case objabi.R_ADDRCUOFF: 371 // debug_range and debug_loc elements use this relocation type to get an 372 // offset from the start of the compile unit. 373 o = Symaddr(r.Sym) + r.Add - Symaddr(r.Sym.Lib.Textp[0]) 374 375 // r->sym can be null when CALL $(constant) is transformed from absolute PC to relative PC call. 376 case objabi.R_GOTPCREL: 377 if ctxt.DynlinkingGo() && ctxt.HeadType == objabi.Hdarwin && r.Sym != nil && r.Sym.Type != sym.SCONST { 378 r.Done = false 379 r.Xadd = r.Add 380 r.Xadd -= int64(r.Siz) // relative to address after the relocated chunk 381 r.Xsym = r.Sym 382 383 o = r.Xadd 384 o += int64(r.Siz) 385 break 386 } 387 fallthrough 388 case objabi.R_CALL, objabi.R_PCREL: 389 if ctxt.LinkMode == LinkExternal && r.Sym != nil && r.Sym.Type != sym.SCONST && (r.Sym.Sect != s.Sect || r.Type == objabi.R_GOTPCREL) { 390 r.Done = false 391 392 // set up addend for eventual relocation via outer symbol. 393 rs := r.Sym 394 395 r.Xadd = r.Add 396 for rs.Outer != nil { 397 r.Xadd += Symaddr(rs) - Symaddr(rs.Outer) 398 rs = rs.Outer 399 } 400 401 r.Xadd -= int64(r.Siz) // relative to address after the relocated chunk 402 if rs.Type != sym.SHOSTOBJ && rs.Type != sym.SDYNIMPORT && rs.Sect == nil { 403 Errorf(s, "missing section for relocation target %s", rs.Name) 404 } 405 r.Xsym = rs 406 407 o = r.Xadd 408 if ctxt.IsELF { 409 if ctxt.Arch.Family == sys.AMD64 { 410 o = 0 411 } 412 } else if ctxt.HeadType == objabi.Hdarwin { 413 if r.Type == objabi.R_CALL { 414 if rs.Type != sym.SHOSTOBJ { 415 o += int64(uint64(Symaddr(rs)) - rs.Sect.Vaddr) 416 } 417 o -= int64(r.Off) // relative to section offset, not symbol 418 } else if ctxt.Arch.Family == sys.ARM { 419 // see ../arm/asm.go:/machoreloc1 420 o += Symaddr(rs) - int64(s.Value) - int64(r.Off) 421 } else { 422 o += int64(r.Siz) 423 } 424 } else if ctxt.HeadType == objabi.Hwindows && ctxt.Arch.Family == sys.AMD64 { // only amd64 needs PCREL 425 // PE/COFF's PC32 relocation uses the address after the relocated 426 // bytes as the base. Compensate by skewing the addend. 427 o += int64(r.Siz) 428 } else { 429 Errorf(s, "unhandled pcrel relocation to %s on %v", rs.Name, ctxt.HeadType) 430 } 431 432 break 433 } 434 435 o = 0 436 if r.Sym != nil { 437 o += Symaddr(r.Sym) 438 } 439 440 o += r.Add - (s.Value + int64(r.Off) + int64(r.Siz)) 441 case objabi.R_SIZE: 442 o = r.Sym.Size + r.Add 443 } 444 445 if r.Variant != sym.RV_NONE { 446 o = Thearch.Archrelocvariant(ctxt, r, s, o) 447 } 448 449 if false { 450 nam := "<nil>" 451 if r.Sym != nil { 452 nam = r.Sym.Name 453 } 454 fmt.Printf("relocate %s %#x (%#x+%#x, size %d) => %s %#x +%#x [type %d (%s)/%d, %x]\n", s.Name, s.Value+int64(off), s.Value, r.Off, r.Siz, nam, Symaddr(r.Sym), r.Add, r.Type, sym.RelocName(ctxt.Arch, r.Type), r.Variant, o) 455 } 456 switch siz { 457 default: 458 Errorf(s, "bad reloc size %#x for %s", uint32(siz), r.Sym.Name) 459 fallthrough 460 461 // TODO(rsc): Remove. 462 case 1: 463 s.P[off] = byte(int8(o)) 464 case 2: 465 if o != int64(int16(o)) { 466 Errorf(s, "relocation address for %s is too big: %#x", r.Sym.Name, o) 467 } 468 i16 := int16(o) 469 ctxt.Arch.ByteOrder.PutUint16(s.P[off:], uint16(i16)) 470 case 4: 471 if r.Type == objabi.R_PCREL || r.Type == objabi.R_CALL { 472 if o != int64(int32(o)) { 473 Errorf(s, "pc-relative relocation address for %s is too big: %#x", r.Sym.Name, o) 474 } 475 } else { 476 if o != int64(int32(o)) && o != int64(uint32(o)) { 477 Errorf(s, "non-pc-relative relocation address for %s is too big: %#x", r.Sym.Name, uint64(o)) 478 } 479 } 480 481 fl := int32(o) 482 ctxt.Arch.ByteOrder.PutUint32(s.P[off:], uint32(fl)) 483 case 8: 484 ctxt.Arch.ByteOrder.PutUint64(s.P[off:], uint64(o)) 485 } 486 } 487 } 488 489 func (ctxt *Link) reloc() { 490 if ctxt.Debugvlog != 0 { 491 ctxt.Logf("%5.2f reloc\n", Cputime()) 492 } 493 494 for _, s := range ctxt.Textp { 495 relocsym(ctxt, s) 496 } 497 for _, s := range datap { 498 relocsym(ctxt, s) 499 } 500 for _, s := range dwarfp { 501 relocsym(ctxt, s) 502 } 503 } 504 505 func windynrelocsym(ctxt *Link, s *sym.Symbol) { 506 rel := ctxt.Syms.Lookup(".rel", 0) 507 if s == rel { 508 return 509 } 510 for ri := 0; ri < len(s.R); ri++ { 511 r := &s.R[ri] 512 targ := r.Sym 513 if targ == nil { 514 continue 515 } 516 if !targ.Attr.Reachable() { 517 if r.Type == objabi.R_WEAKADDROFF { 518 continue 519 } 520 Errorf(s, "dynamic relocation to unreachable symbol %s", targ.Name) 521 } 522 if r.Sym.Plt == -2 && r.Sym.Got != -2 { // make dynimport JMP table for PE object files. 523 targ.Plt = int32(rel.Size) 524 r.Sym = rel 525 r.Add = int64(targ.Plt) 526 527 // jmp *addr 528 if ctxt.Arch.Family == sys.I386 { 529 rel.AddUint8(0xff) 530 rel.AddUint8(0x25) 531 rel.AddAddr(ctxt.Arch, targ) 532 rel.AddUint8(0x90) 533 rel.AddUint8(0x90) 534 } else { 535 rel.AddUint8(0xff) 536 rel.AddUint8(0x24) 537 rel.AddUint8(0x25) 538 rel.AddAddrPlus4(targ, 0) 539 rel.AddUint8(0x90) 540 } 541 } else if r.Sym.Plt >= 0 { 542 r.Sym = rel 543 r.Add = int64(targ.Plt) 544 } 545 } 546 } 547 548 func dynrelocsym(ctxt *Link, s *sym.Symbol) { 549 if ctxt.HeadType == objabi.Hwindows { 550 if ctxt.LinkMode == LinkInternal { 551 windynrelocsym(ctxt, s) 552 } 553 return 554 } 555 556 for ri := 0; ri < len(s.R); ri++ { 557 r := &s.R[ri] 558 if ctxt.BuildMode == BuildModePIE && ctxt.LinkMode == LinkInternal { 559 // It's expected that some relocations will be done 560 // later by relocsym (R_TLS_LE, R_ADDROFF), so 561 // don't worry if Adddynrel returns false. 562 Thearch.Adddynrel(ctxt, s, r) 563 continue 564 } 565 if r.Sym != nil && r.Sym.Type == sym.SDYNIMPORT || r.Type >= 256 { 566 if r.Sym != nil && !r.Sym.Attr.Reachable() { 567 Errorf(s, "dynamic relocation to unreachable symbol %s", r.Sym.Name) 568 } 569 if !Thearch.Adddynrel(ctxt, s, r) { 570 Errorf(s, "unsupported dynamic relocation for symbol %s (type=%d (%s) stype=%d (%s))", r.Sym.Name, r.Type, sym.RelocName(ctxt.Arch, r.Type), r.Sym.Type, r.Sym.Type) 571 } 572 } 573 } 574 } 575 576 func dynreloc(ctxt *Link, data *[sym.SXREF][]*sym.Symbol) { 577 // -d suppresses dynamic loader format, so we may as well not 578 // compute these sections or mark their symbols as reachable. 579 if *FlagD && ctxt.HeadType != objabi.Hwindows { 580 return 581 } 582 if ctxt.Debugvlog != 0 { 583 ctxt.Logf("%5.2f dynreloc\n", Cputime()) 584 } 585 586 for _, s := range ctxt.Textp { 587 dynrelocsym(ctxt, s) 588 } 589 for _, syms := range data { 590 for _, s := range syms { 591 dynrelocsym(ctxt, s) 592 } 593 } 594 if ctxt.IsELF { 595 elfdynhash(ctxt) 596 } 597 } 598 599 func Codeblk(ctxt *Link, addr int64, size int64) { 600 CodeblkPad(ctxt, addr, size, zeros[:]) 601 } 602 func CodeblkPad(ctxt *Link, addr int64, size int64, pad []byte) { 603 if *flagA { 604 ctxt.Logf("codeblk [%#x,%#x) at offset %#x\n", addr, addr+size, ctxt.Out.Offset()) 605 } 606 607 blk(ctxt, ctxt.Textp, addr, size, pad) 608 609 /* again for printing */ 610 if !*flagA { 611 return 612 } 613 614 syms := ctxt.Textp 615 for i, s := range syms { 616 if !s.Attr.Reachable() { 617 continue 618 } 619 if s.Value >= addr { 620 syms = syms[i:] 621 break 622 } 623 } 624 625 eaddr := addr + size 626 var q []byte 627 for _, s := range syms { 628 if !s.Attr.Reachable() { 629 continue 630 } 631 if s.Value >= eaddr { 632 break 633 } 634 635 if addr < s.Value { 636 ctxt.Logf("%-20s %.8x|", "_", uint64(addr)) 637 for ; addr < s.Value; addr++ { 638 ctxt.Logf(" %.2x", 0) 639 } 640 ctxt.Logf("\n") 641 } 642 643 ctxt.Logf("%.6x\t%-20s\n", uint64(addr), s.Name) 644 q = s.P 645 646 for len(q) >= 16 { 647 ctxt.Logf("%.6x\t% x\n", uint64(addr), q[:16]) 648 addr += 16 649 q = q[16:] 650 } 651 652 if len(q) > 0 { 653 ctxt.Logf("%.6x\t% x\n", uint64(addr), q) 654 addr += int64(len(q)) 655 } 656 } 657 658 if addr < eaddr { 659 ctxt.Logf("%-20s %.8x|", "_", uint64(addr)) 660 for ; addr < eaddr; addr++ { 661 ctxt.Logf(" %.2x", 0) 662 } 663 } 664 } 665 666 func blk(ctxt *Link, syms []*sym.Symbol, addr, size int64, pad []byte) { 667 for i, s := range syms { 668 if !s.Attr.SubSymbol() && s.Value >= addr { 669 syms = syms[i:] 670 break 671 } 672 } 673 674 eaddr := addr + size 675 for _, s := range syms { 676 if s.Attr.SubSymbol() { 677 continue 678 } 679 if s.Value >= eaddr { 680 break 681 } 682 if s.Value < addr { 683 Errorf(s, "phase error: addr=%#x but sym=%#x type=%d", addr, s.Value, s.Type) 684 errorexit() 685 } 686 if addr < s.Value { 687 ctxt.Out.WriteStringPad("", int(s.Value-addr), pad) 688 addr = s.Value 689 } 690 ctxt.Out.Write(s.P) 691 addr += int64(len(s.P)) 692 if addr < s.Value+s.Size { 693 ctxt.Out.WriteStringPad("", int(s.Value+s.Size-addr), pad) 694 addr = s.Value + s.Size 695 } 696 if addr != s.Value+s.Size { 697 Errorf(s, "phase error: addr=%#x value+size=%#x", addr, s.Value+s.Size) 698 errorexit() 699 } 700 if s.Value+s.Size >= eaddr { 701 break 702 } 703 } 704 705 if addr < eaddr { 706 ctxt.Out.WriteStringPad("", int(eaddr-addr), pad) 707 } 708 ctxt.Out.Flush() 709 } 710 711 func Datblk(ctxt *Link, addr int64, size int64) { 712 if *flagA { 713 ctxt.Logf("datblk [%#x,%#x) at offset %#x\n", addr, addr+size, ctxt.Out.Offset()) 714 } 715 716 blk(ctxt, datap, addr, size, zeros[:]) 717 718 /* again for printing */ 719 if !*flagA { 720 return 721 } 722 723 syms := datap 724 for i, sym := range syms { 725 if sym.Value >= addr { 726 syms = syms[i:] 727 break 728 } 729 } 730 731 eaddr := addr + size 732 for _, sym := range syms { 733 if sym.Value >= eaddr { 734 break 735 } 736 if addr < sym.Value { 737 ctxt.Logf("\t%.8x| 00 ...\n", uint64(addr)) 738 addr = sym.Value 739 } 740 741 ctxt.Logf("%s\n\t%.8x|", sym.Name, uint64(addr)) 742 for i, b := range sym.P { 743 if i > 0 && i%16 == 0 { 744 ctxt.Logf("\n\t%.8x|", uint64(addr)+uint64(i)) 745 } 746 ctxt.Logf(" %.2x", b) 747 } 748 749 addr += int64(len(sym.P)) 750 for ; addr < sym.Value+sym.Size; addr++ { 751 ctxt.Logf(" %.2x", 0) 752 } 753 ctxt.Logf("\n") 754 755 if ctxt.LinkMode != LinkExternal { 756 continue 757 } 758 for _, r := range sym.R { 759 rsname := "" 760 if r.Sym != nil { 761 rsname = r.Sym.Name 762 } 763 typ := "?" 764 switch r.Type { 765 case objabi.R_ADDR: 766 typ = "addr" 767 case objabi.R_PCREL: 768 typ = "pcrel" 769 case objabi.R_CALL: 770 typ = "call" 771 } 772 ctxt.Logf("\treloc %.8x/%d %s %s+%#x [%#x]\n", uint(sym.Value+int64(r.Off)), r.Siz, typ, rsname, r.Add, r.Sym.Value+r.Add) 773 } 774 } 775 776 if addr < eaddr { 777 ctxt.Logf("\t%.8x| 00 ...\n", uint(addr)) 778 } 779 ctxt.Logf("\t%.8x|\n", uint(eaddr)) 780 } 781 782 func Dwarfblk(ctxt *Link, addr int64, size int64) { 783 if *flagA { 784 ctxt.Logf("dwarfblk [%#x,%#x) at offset %#x\n", addr, addr+size, ctxt.Out.Offset()) 785 } 786 787 blk(ctxt, dwarfp, addr, size, zeros[:]) 788 } 789 790 var zeros [512]byte 791 792 var ( 793 strdata = make(map[string]string) 794 strnames []string 795 ) 796 797 func addstrdata1(ctxt *Link, arg string) { 798 eq := strings.Index(arg, "=") 799 dot := strings.LastIndex(arg[:eq+1], ".") 800 if eq < 0 || dot < 0 { 801 Exitf("-X flag requires argument of the form importpath.name=value") 802 } 803 pkg := arg[:dot] 804 if ctxt.BuildMode == BuildModePlugin && pkg == "main" { 805 pkg = *flagPluginPath 806 } 807 pkg = objabi.PathToPrefix(pkg) 808 name := pkg + arg[dot:eq] 809 value := arg[eq+1:] 810 if _, ok := strdata[name]; !ok { 811 strnames = append(strnames, name) 812 } 813 strdata[name] = value 814 } 815 816 func addstrdata(ctxt *Link, name, value string) { 817 s := ctxt.Syms.ROLookup(name, 0) 818 if s == nil || s.Gotype == nil { 819 // Not defined in the loaded packages. 820 return 821 } 822 if s.Gotype.Name != "type.string" { 823 Errorf(s, "cannot set with -X: not a var of type string (%s)", s.Gotype.Name) 824 return 825 } 826 if s.Type == sym.SBSS { 827 s.Type = sym.SDATA 828 } 829 830 p := fmt.Sprintf("%s.str", s.Name) 831 sp := ctxt.Syms.Lookup(p, 0) 832 833 Addstring(sp, value) 834 sp.Type = sym.SRODATA 835 836 s.Size = 0 837 s.P = s.P[:0] 838 s.R = s.R[:0] 839 reachable := s.Attr.Reachable() 840 s.AddAddr(ctxt.Arch, sp) 841 s.AddUint(ctxt.Arch, uint64(len(value))) 842 843 // addstring, addaddr, etc., mark the symbols as reachable. 844 // In this case that is not necessarily true, so stick to what 845 // we know before entering this function. 846 s.Attr.Set(sym.AttrReachable, reachable) 847 848 sp.Attr.Set(sym.AttrReachable, reachable) 849 } 850 851 func (ctxt *Link) dostrdata() { 852 for _, name := range strnames { 853 addstrdata(ctxt, name, strdata[name]) 854 } 855 } 856 857 func Addstring(s *sym.Symbol, str string) int64 { 858 if s.Type == 0 { 859 s.Type = sym.SNOPTRDATA 860 } 861 s.Attr |= sym.AttrReachable 862 r := s.Size 863 if s.Name == ".shstrtab" { 864 elfsetstring(s, str, int(r)) 865 } 866 s.P = append(s.P, str...) 867 s.P = append(s.P, 0) 868 s.Size = int64(len(s.P)) 869 return r 870 } 871 872 // addgostring adds str, as a Go string value, to s. symname is the name of the 873 // symbol used to define the string data and must be unique per linked object. 874 func addgostring(ctxt *Link, s *sym.Symbol, symname, str string) { 875 sdata := ctxt.Syms.Lookup(symname, 0) 876 if sdata.Type != sym.Sxxx { 877 Errorf(s, "duplicate symname in addgostring: %s", symname) 878 } 879 sdata.Attr |= sym.AttrReachable 880 sdata.Attr |= sym.AttrLocal 881 sdata.Type = sym.SRODATA 882 sdata.Size = int64(len(str)) 883 sdata.P = []byte(str) 884 s.AddAddr(ctxt.Arch, sdata) 885 s.AddUint(ctxt.Arch, uint64(len(str))) 886 } 887 888 func addinitarrdata(ctxt *Link, s *sym.Symbol) { 889 p := s.Name + ".ptr" 890 sp := ctxt.Syms.Lookup(p, 0) 891 sp.Type = sym.SINITARR 892 sp.Size = 0 893 sp.Attr |= sym.AttrDuplicateOK 894 sp.AddAddr(ctxt.Arch, s) 895 } 896 897 func dosymtype(ctxt *Link) { 898 switch ctxt.BuildMode { 899 case BuildModeCArchive, BuildModeCShared: 900 for _, s := range ctxt.Syms.Allsym { 901 // Create a new entry in the .init_array section that points to the 902 // library initializer function. 903 if s.Name == *flagEntrySymbol { 904 addinitarrdata(ctxt, s) 905 } 906 } 907 } 908 } 909 910 // symalign returns the required alignment for the given symbol s. 911 func symalign(s *sym.Symbol) int32 { 912 min := int32(Thearch.Minalign) 913 if s.Align >= min { 914 return s.Align 915 } else if s.Align != 0 { 916 return min 917 } 918 if strings.HasPrefix(s.Name, "go.string.") || strings.HasPrefix(s.Name, "type..namedata.") { 919 // String data is just bytes. 920 // If we align it, we waste a lot of space to padding. 921 return min 922 } 923 align := int32(Thearch.Maxalign) 924 for int64(align) > s.Size && align > min { 925 align >>= 1 926 } 927 return align 928 } 929 930 func aligndatsize(datsize int64, s *sym.Symbol) int64 { 931 return Rnd(datsize, int64(symalign(s))) 932 } 933 934 const debugGCProg = false 935 936 type GCProg struct { 937 ctxt *Link 938 sym *sym.Symbol 939 w gcprog.Writer 940 } 941 942 func (p *GCProg) Init(ctxt *Link, name string) { 943 p.ctxt = ctxt 944 p.sym = ctxt.Syms.Lookup(name, 0) 945 p.w.Init(p.writeByte(ctxt)) 946 if debugGCProg { 947 fmt.Fprintf(os.Stderr, "ld: start GCProg %s\n", name) 948 p.w.Debug(os.Stderr) 949 } 950 } 951 952 func (p *GCProg) writeByte(ctxt *Link) func(x byte) { 953 return func(x byte) { 954 p.sym.AddUint8(x) 955 } 956 } 957 958 func (p *GCProg) End(size int64) { 959 p.w.ZeroUntil(size / int64(p.ctxt.Arch.PtrSize)) 960 p.w.End() 961 if debugGCProg { 962 fmt.Fprintf(os.Stderr, "ld: end GCProg\n") 963 } 964 } 965 966 func (p *GCProg) AddSym(s *sym.Symbol) { 967 typ := s.Gotype 968 // Things without pointers should be in sym.SNOPTRDATA or sym.SNOPTRBSS; 969 // everything we see should have pointers and should therefore have a type. 970 if typ == nil { 971 switch s.Name { 972 case "runtime.data", "runtime.edata", "runtime.bss", "runtime.ebss": 973 // Ignore special symbols that are sometimes laid out 974 // as real symbols. See comment about dyld on darwin in 975 // the address function. 976 return 977 } 978 Errorf(s, "missing Go type information for global symbol: size %d", s.Size) 979 return 980 } 981 982 ptrsize := int64(p.ctxt.Arch.PtrSize) 983 nptr := decodetypePtrdata(p.ctxt.Arch, typ) / ptrsize 984 985 if debugGCProg { 986 fmt.Fprintf(os.Stderr, "gcprog sym: %s at %d (ptr=%d+%d)\n", s.Name, s.Value, s.Value/ptrsize, nptr) 987 } 988 989 if decodetypeUsegcprog(p.ctxt.Arch, typ) == 0 { 990 // Copy pointers from mask into program. 991 mask := decodetypeGcmask(p.ctxt, typ) 992 for i := int64(0); i < nptr; i++ { 993 if (mask[i/8]>>uint(i%8))&1 != 0 { 994 p.w.Ptr(s.Value/ptrsize + i) 995 } 996 } 997 return 998 } 999 1000 // Copy program. 1001 prog := decodetypeGcprog(p.ctxt, typ) 1002 p.w.ZeroUntil(s.Value / ptrsize) 1003 p.w.Append(prog[4:], nptr) 1004 } 1005 1006 // dataSortKey is used to sort a slice of data symbol *sym.Symbol pointers. 1007 // The sort keys are kept inline to improve cache behavior while sorting. 1008 type dataSortKey struct { 1009 size int64 1010 name string 1011 sym *sym.Symbol 1012 } 1013 1014 type bySizeAndName []dataSortKey 1015 1016 func (d bySizeAndName) Len() int { return len(d) } 1017 func (d bySizeAndName) Swap(i, j int) { d[i], d[j] = d[j], d[i] } 1018 func (d bySizeAndName) Less(i, j int) bool { 1019 s1, s2 := d[i], d[j] 1020 if s1.size != s2.size { 1021 return s1.size < s2.size 1022 } 1023 return s1.name < s2.name 1024 } 1025 1026 // cutoff is the maximum data section size permitted by the linker 1027 // (see issue #9862). 1028 const cutoff = 2e9 // 2 GB (or so; looks better in errors than 2^31) 1029 1030 func checkdatsize(ctxt *Link, datsize int64, symn sym.SymKind) { 1031 if datsize > cutoff { 1032 Errorf(nil, "too much data in section %v (over %v bytes)", symn, cutoff) 1033 } 1034 } 1035 1036 // datap is a collection of reachable data symbols in address order. 1037 // Generated by dodata. 1038 var datap []*sym.Symbol 1039 1040 func (ctxt *Link) dodata() { 1041 if ctxt.Debugvlog != 0 { 1042 ctxt.Logf("%5.2f dodata\n", Cputime()) 1043 } 1044 1045 if ctxt.DynlinkingGo() && ctxt.HeadType == objabi.Hdarwin { 1046 // The values in moduledata are filled out by relocations 1047 // pointing to the addresses of these special symbols. 1048 // Typically these symbols have no size and are not laid 1049 // out with their matching section. 1050 // 1051 // However on darwin, dyld will find the special symbol 1052 // in the first loaded module, even though it is local. 1053 // 1054 // (An hypothesis, formed without looking in the dyld sources: 1055 // these special symbols have no size, so their address 1056 // matches a real symbol. The dynamic linker assumes we 1057 // want the normal symbol with the same address and finds 1058 // it in the other module.) 1059 // 1060 // To work around this we lay out the symbls whose 1061 // addresses are vital for multi-module programs to work 1062 // as normal symbols, and give them a little size. 1063 bss := ctxt.Syms.Lookup("runtime.bss", 0) 1064 bss.Size = 8 1065 bss.Attr.Set(sym.AttrSpecial, false) 1066 1067 ctxt.Syms.Lookup("runtime.ebss", 0).Attr.Set(sym.AttrSpecial, false) 1068 1069 data := ctxt.Syms.Lookup("runtime.data", 0) 1070 data.Size = 8 1071 data.Attr.Set(sym.AttrSpecial, false) 1072 1073 ctxt.Syms.Lookup("runtime.edata", 0).Attr.Set(sym.AttrSpecial, false) 1074 1075 types := ctxt.Syms.Lookup("runtime.types", 0) 1076 types.Type = sym.STYPE 1077 types.Size = 8 1078 types.Attr.Set(sym.AttrSpecial, false) 1079 1080 etypes := ctxt.Syms.Lookup("runtime.etypes", 0) 1081 etypes.Type = sym.SFUNCTAB 1082 etypes.Attr.Set(sym.AttrSpecial, false) 1083 } 1084 1085 // Collect data symbols by type into data. 1086 var data [sym.SXREF][]*sym.Symbol 1087 for _, s := range ctxt.Syms.Allsym { 1088 if !s.Attr.Reachable() || s.Attr.Special() || s.Attr.SubSymbol() { 1089 continue 1090 } 1091 if s.Type <= sym.STEXT || s.Type >= sym.SXREF { 1092 continue 1093 } 1094 data[s.Type] = append(data[s.Type], s) 1095 } 1096 1097 // Now that we have the data symbols, but before we start 1098 // to assign addresses, record all the necessary 1099 // dynamic relocations. These will grow the relocation 1100 // symbol, which is itself data. 1101 // 1102 // On darwin, we need the symbol table numbers for dynreloc. 1103 if ctxt.HeadType == objabi.Hdarwin { 1104 machosymorder(ctxt) 1105 } 1106 dynreloc(ctxt, &data) 1107 1108 if ctxt.UseRelro() { 1109 // "read only" data with relocations needs to go in its own section 1110 // when building a shared library. We do this by boosting objects of 1111 // type SXXX with relocations to type SXXXRELRO. 1112 for _, symnro := range sym.ReadOnly { 1113 symnrelro := sym.RelROMap[symnro] 1114 1115 ro := []*sym.Symbol{} 1116 relro := data[symnrelro] 1117 1118 for _, s := range data[symnro] { 1119 isRelro := len(s.R) > 0 1120 switch s.Type { 1121 case sym.STYPE, sym.STYPERELRO, sym.SGOFUNCRELRO: 1122 // Symbols are not sorted yet, so it is possible 1123 // that an Outer symbol has been changed to a 1124 // relro Type before it reaches here. 1125 isRelro = true 1126 } 1127 if isRelro { 1128 s.Type = symnrelro 1129 if s.Outer != nil { 1130 s.Outer.Type = s.Type 1131 } 1132 relro = append(relro, s) 1133 } else { 1134 ro = append(ro, s) 1135 } 1136 } 1137 1138 // Check that we haven't made two symbols with the same .Outer into 1139 // different types (because references two symbols with non-nil Outer 1140 // become references to the outer symbol + offset it's vital that the 1141 // symbol and the outer end up in the same section). 1142 for _, s := range relro { 1143 if s.Outer != nil && s.Outer.Type != s.Type { 1144 Errorf(s, "inconsistent types for symbol and its Outer %s (%v != %v)", 1145 s.Outer.Name, s.Type, s.Outer.Type) 1146 } 1147 } 1148 1149 data[symnro] = ro 1150 data[symnrelro] = relro 1151 } 1152 } 1153 1154 // Sort symbols. 1155 var dataMaxAlign [sym.SXREF]int32 1156 var wg sync.WaitGroup 1157 for symn := range data { 1158 symn := sym.SymKind(symn) 1159 wg.Add(1) 1160 go func() { 1161 data[symn], dataMaxAlign[symn] = dodataSect(ctxt, symn, data[symn]) 1162 wg.Done() 1163 }() 1164 } 1165 wg.Wait() 1166 1167 // Allocate sections. 1168 // Data is processed before segtext, because we need 1169 // to see all symbols in the .data and .bss sections in order 1170 // to generate garbage collection information. 1171 datsize := int64(0) 1172 1173 // Writable data sections that do not need any specialized handling. 1174 writable := []sym.SymKind{ 1175 sym.SELFSECT, 1176 sym.SMACHO, 1177 sym.SMACHOGOT, 1178 sym.SWINDOWS, 1179 } 1180 for _, symn := range writable { 1181 for _, s := range data[symn] { 1182 sect := addsection(ctxt.Arch, &Segdata, s.Name, 06) 1183 sect.Align = symalign(s) 1184 datsize = Rnd(datsize, int64(sect.Align)) 1185 sect.Vaddr = uint64(datsize) 1186 s.Sect = sect 1187 s.Type = sym.SDATA 1188 s.Value = int64(uint64(datsize) - sect.Vaddr) 1189 datsize += s.Size 1190 sect.Length = uint64(datsize) - sect.Vaddr 1191 } 1192 checkdatsize(ctxt, datsize, symn) 1193 } 1194 1195 // .got (and .toc on ppc64) 1196 if len(data[sym.SELFGOT]) > 0 { 1197 sect := addsection(ctxt.Arch, &Segdata, ".got", 06) 1198 sect.Align = dataMaxAlign[sym.SELFGOT] 1199 datsize = Rnd(datsize, int64(sect.Align)) 1200 sect.Vaddr = uint64(datsize) 1201 var toc *sym.Symbol 1202 for _, s := range data[sym.SELFGOT] { 1203 datsize = aligndatsize(datsize, s) 1204 s.Sect = sect 1205 s.Type = sym.SDATA 1206 s.Value = int64(uint64(datsize) - sect.Vaddr) 1207 1208 // Resolve .TOC. symbol for this object file (ppc64) 1209 toc = ctxt.Syms.ROLookup(".TOC.", int(s.Version)) 1210 if toc != nil { 1211 toc.Sect = sect 1212 toc.Outer = s 1213 toc.Sub = s.Sub 1214 s.Sub = toc 1215 1216 toc.Value = 0x8000 1217 } 1218 1219 datsize += s.Size 1220 } 1221 checkdatsize(ctxt, datsize, sym.SELFGOT) 1222 sect.Length = uint64(datsize) - sect.Vaddr 1223 } 1224 1225 /* pointer-free data */ 1226 sect := addsection(ctxt.Arch, &Segdata, ".noptrdata", 06) 1227 sect.Align = dataMaxAlign[sym.SNOPTRDATA] 1228 datsize = Rnd(datsize, int64(sect.Align)) 1229 sect.Vaddr = uint64(datsize) 1230 ctxt.Syms.Lookup("runtime.noptrdata", 0).Sect = sect 1231 ctxt.Syms.Lookup("runtime.enoptrdata", 0).Sect = sect 1232 for _, s := range data[sym.SNOPTRDATA] { 1233 datsize = aligndatsize(datsize, s) 1234 s.Sect = sect 1235 s.Type = sym.SDATA 1236 s.Value = int64(uint64(datsize) - sect.Vaddr) 1237 datsize += s.Size 1238 } 1239 checkdatsize(ctxt, datsize, sym.SNOPTRDATA) 1240 sect.Length = uint64(datsize) - sect.Vaddr 1241 1242 hasinitarr := ctxt.linkShared 1243 1244 /* shared library initializer */ 1245 switch ctxt.BuildMode { 1246 case BuildModeCArchive, BuildModeCShared, BuildModeShared, BuildModePlugin: 1247 hasinitarr = true 1248 } 1249 if hasinitarr { 1250 sect := addsection(ctxt.Arch, &Segdata, ".init_array", 06) 1251 sect.Align = dataMaxAlign[sym.SINITARR] 1252 datsize = Rnd(datsize, int64(sect.Align)) 1253 sect.Vaddr = uint64(datsize) 1254 for _, s := range data[sym.SINITARR] { 1255 datsize = aligndatsize(datsize, s) 1256 s.Sect = sect 1257 s.Value = int64(uint64(datsize) - sect.Vaddr) 1258 datsize += s.Size 1259 } 1260 sect.Length = uint64(datsize) - sect.Vaddr 1261 checkdatsize(ctxt, datsize, sym.SINITARR) 1262 } 1263 1264 /* data */ 1265 sect = addsection(ctxt.Arch, &Segdata, ".data", 06) 1266 sect.Align = dataMaxAlign[sym.SDATA] 1267 datsize = Rnd(datsize, int64(sect.Align)) 1268 sect.Vaddr = uint64(datsize) 1269 ctxt.Syms.Lookup("runtime.data", 0).Sect = sect 1270 ctxt.Syms.Lookup("runtime.edata", 0).Sect = sect 1271 var gc GCProg 1272 gc.Init(ctxt, "runtime.gcdata") 1273 for _, s := range data[sym.SDATA] { 1274 s.Sect = sect 1275 s.Type = sym.SDATA 1276 datsize = aligndatsize(datsize, s) 1277 s.Value = int64(uint64(datsize) - sect.Vaddr) 1278 gc.AddSym(s) 1279 datsize += s.Size 1280 } 1281 checkdatsize(ctxt, datsize, sym.SDATA) 1282 sect.Length = uint64(datsize) - sect.Vaddr 1283 gc.End(int64(sect.Length)) 1284 1285 /* bss */ 1286 sect = addsection(ctxt.Arch, &Segdata, ".bss", 06) 1287 sect.Align = dataMaxAlign[sym.SBSS] 1288 datsize = Rnd(datsize, int64(sect.Align)) 1289 sect.Vaddr = uint64(datsize) 1290 ctxt.Syms.Lookup("runtime.bss", 0).Sect = sect 1291 ctxt.Syms.Lookup("runtime.ebss", 0).Sect = sect 1292 gc = GCProg{} 1293 gc.Init(ctxt, "runtime.gcbss") 1294 for _, s := range data[sym.SBSS] { 1295 s.Sect = sect 1296 datsize = aligndatsize(datsize, s) 1297 s.Value = int64(uint64(datsize) - sect.Vaddr) 1298 gc.AddSym(s) 1299 datsize += s.Size 1300 } 1301 checkdatsize(ctxt, datsize, sym.SBSS) 1302 sect.Length = uint64(datsize) - sect.Vaddr 1303 gc.End(int64(sect.Length)) 1304 1305 /* pointer-free bss */ 1306 sect = addsection(ctxt.Arch, &Segdata, ".noptrbss", 06) 1307 sect.Align = dataMaxAlign[sym.SNOPTRBSS] 1308 datsize = Rnd(datsize, int64(sect.Align)) 1309 sect.Vaddr = uint64(datsize) 1310 ctxt.Syms.Lookup("runtime.noptrbss", 0).Sect = sect 1311 ctxt.Syms.Lookup("runtime.enoptrbss", 0).Sect = sect 1312 for _, s := range data[sym.SNOPTRBSS] { 1313 datsize = aligndatsize(datsize, s) 1314 s.Sect = sect 1315 s.Value = int64(uint64(datsize) - sect.Vaddr) 1316 datsize += s.Size 1317 } 1318 1319 sect.Length = uint64(datsize) - sect.Vaddr 1320 ctxt.Syms.Lookup("runtime.end", 0).Sect = sect 1321 checkdatsize(ctxt, datsize, sym.SNOPTRBSS) 1322 1323 if len(data[sym.STLSBSS]) > 0 { 1324 var sect *sym.Section 1325 if ctxt.IsELF && (ctxt.LinkMode == LinkExternal || !*FlagD) { 1326 sect = addsection(ctxt.Arch, &Segdata, ".tbss", 06) 1327 sect.Align = int32(ctxt.Arch.PtrSize) 1328 sect.Vaddr = 0 1329 } 1330 datsize = 0 1331 1332 for _, s := range data[sym.STLSBSS] { 1333 datsize = aligndatsize(datsize, s) 1334 s.Sect = sect 1335 s.Value = datsize 1336 datsize += s.Size 1337 } 1338 checkdatsize(ctxt, datsize, sym.STLSBSS) 1339 1340 if sect != nil { 1341 sect.Length = uint64(datsize) 1342 } 1343 } 1344 1345 /* 1346 * We finished data, begin read-only data. 1347 * Not all systems support a separate read-only non-executable data section. 1348 * ELF systems do. 1349 * OS X and Plan 9 do not. 1350 * Windows PE may, but if so we have not implemented it. 1351 * And if we're using external linking mode, the point is moot, 1352 * since it's not our decision; that code expects the sections in 1353 * segtext. 1354 */ 1355 var segro *sym.Segment 1356 if ctxt.IsELF && ctxt.LinkMode == LinkInternal { 1357 segro = &Segrodata 1358 } else { 1359 segro = &Segtext 1360 } 1361 1362 datsize = 0 1363 1364 /* read-only executable ELF, Mach-O sections */ 1365 if len(data[sym.STEXT]) != 0 { 1366 Errorf(nil, "dodata found an sym.STEXT symbol: %s", data[sym.STEXT][0].Name) 1367 } 1368 for _, s := range data[sym.SELFRXSECT] { 1369 sect := addsection(ctxt.Arch, &Segtext, s.Name, 04) 1370 sect.Align = symalign(s) 1371 datsize = Rnd(datsize, int64(sect.Align)) 1372 sect.Vaddr = uint64(datsize) 1373 s.Sect = sect 1374 s.Type = sym.SRODATA 1375 s.Value = int64(uint64(datsize) - sect.Vaddr) 1376 datsize += s.Size 1377 sect.Length = uint64(datsize) - sect.Vaddr 1378 checkdatsize(ctxt, datsize, sym.SELFRXSECT) 1379 } 1380 1381 /* read-only data */ 1382 sect = addsection(ctxt.Arch, segro, ".rodata", 04) 1383 1384 sect.Vaddr = 0 1385 ctxt.Syms.Lookup("runtime.rodata", 0).Sect = sect 1386 ctxt.Syms.Lookup("runtime.erodata", 0).Sect = sect 1387 if !ctxt.UseRelro() { 1388 ctxt.Syms.Lookup("runtime.types", 0).Sect = sect 1389 ctxt.Syms.Lookup("runtime.etypes", 0).Sect = sect 1390 } 1391 for _, symn := range sym.ReadOnly { 1392 align := dataMaxAlign[symn] 1393 if sect.Align < align { 1394 sect.Align = align 1395 } 1396 } 1397 datsize = Rnd(datsize, int64(sect.Align)) 1398 for _, symn := range sym.ReadOnly { 1399 for _, s := range data[symn] { 1400 datsize = aligndatsize(datsize, s) 1401 s.Sect = sect 1402 s.Type = sym.SRODATA 1403 s.Value = int64(uint64(datsize) - sect.Vaddr) 1404 datsize += s.Size 1405 } 1406 checkdatsize(ctxt, datsize, symn) 1407 } 1408 sect.Length = uint64(datsize) - sect.Vaddr 1409 1410 /* read-only ELF, Mach-O sections */ 1411 for _, s := range data[sym.SELFROSECT] { 1412 sect = addsection(ctxt.Arch, segro, s.Name, 04) 1413 sect.Align = symalign(s) 1414 datsize = Rnd(datsize, int64(sect.Align)) 1415 sect.Vaddr = uint64(datsize) 1416 s.Sect = sect 1417 s.Type = sym.SRODATA 1418 s.Value = int64(uint64(datsize) - sect.Vaddr) 1419 datsize += s.Size 1420 sect.Length = uint64(datsize) - sect.Vaddr 1421 } 1422 checkdatsize(ctxt, datsize, sym.SELFROSECT) 1423 1424 for _, s := range data[sym.SMACHOPLT] { 1425 sect = addsection(ctxt.Arch, segro, s.Name, 04) 1426 sect.Align = symalign(s) 1427 datsize = Rnd(datsize, int64(sect.Align)) 1428 sect.Vaddr = uint64(datsize) 1429 s.Sect = sect 1430 s.Type = sym.SRODATA 1431 s.Value = int64(uint64(datsize) - sect.Vaddr) 1432 datsize += s.Size 1433 sect.Length = uint64(datsize) - sect.Vaddr 1434 } 1435 checkdatsize(ctxt, datsize, sym.SMACHOPLT) 1436 1437 // There is some data that are conceptually read-only but are written to by 1438 // relocations. On GNU systems, we can arrange for the dynamic linker to 1439 // mprotect sections after relocations are applied by giving them write 1440 // permissions in the object file and calling them ".data.rel.ro.FOO". We 1441 // divide the .rodata section between actual .rodata and .data.rel.ro.rodata, 1442 // but for the other sections that this applies to, we just write a read-only 1443 // .FOO section or a read-write .data.rel.ro.FOO section depending on the 1444 // situation. 1445 // TODO(mwhudson): It would make sense to do this more widely, but it makes 1446 // the system linker segfault on darwin. 1447 addrelrosection := func(suffix string) *sym.Section { 1448 return addsection(ctxt.Arch, segro, suffix, 04) 1449 } 1450 1451 if ctxt.UseRelro() { 1452 addrelrosection = func(suffix string) *sym.Section { 1453 seg := &Segrelrodata 1454 if ctxt.LinkMode == LinkExternal { 1455 // Using a separate segment with an external 1456 // linker results in some programs moving 1457 // their data sections unexpectedly, which 1458 // corrupts the moduledata. So we use the 1459 // rodata segment and let the external linker 1460 // sort out a rel.ro segment. 1461 seg = &Segrodata 1462 } 1463 return addsection(ctxt.Arch, seg, ".data.rel.ro"+suffix, 06) 1464 } 1465 /* data only written by relocations */ 1466 sect = addrelrosection("") 1467 1468 sect.Vaddr = 0 1469 ctxt.Syms.Lookup("runtime.types", 0).Sect = sect 1470 ctxt.Syms.Lookup("runtime.etypes", 0).Sect = sect 1471 for _, symnro := range sym.ReadOnly { 1472 symn := sym.RelROMap[symnro] 1473 align := dataMaxAlign[symn] 1474 if sect.Align < align { 1475 sect.Align = align 1476 } 1477 } 1478 datsize = Rnd(datsize, int64(sect.Align)) 1479 for _, symnro := range sym.ReadOnly { 1480 symn := sym.RelROMap[symnro] 1481 for _, s := range data[symn] { 1482 datsize = aligndatsize(datsize, s) 1483 if s.Outer != nil && s.Outer.Sect != nil && s.Outer.Sect != sect { 1484 Errorf(s, "s.Outer (%s) in different section from s, %s != %s", s.Outer.Name, s.Outer.Sect.Name, sect.Name) 1485 } 1486 s.Sect = sect 1487 s.Type = sym.SRODATA 1488 s.Value = int64(uint64(datsize) - sect.Vaddr) 1489 datsize += s.Size 1490 } 1491 checkdatsize(ctxt, datsize, symn) 1492 } 1493 1494 sect.Length = uint64(datsize) - sect.Vaddr 1495 } 1496 1497 /* typelink */ 1498 sect = addrelrosection(".typelink") 1499 sect.Align = dataMaxAlign[sym.STYPELINK] 1500 datsize = Rnd(datsize, int64(sect.Align)) 1501 sect.Vaddr = uint64(datsize) 1502 typelink := ctxt.Syms.Lookup("runtime.typelink", 0) 1503 typelink.Sect = sect 1504 typelink.Type = sym.SRODATA 1505 datsize += typelink.Size 1506 checkdatsize(ctxt, datsize, sym.STYPELINK) 1507 sect.Length = uint64(datsize) - sect.Vaddr 1508 1509 /* itablink */ 1510 sect = addrelrosection(".itablink") 1511 sect.Align = dataMaxAlign[sym.SITABLINK] 1512 datsize = Rnd(datsize, int64(sect.Align)) 1513 sect.Vaddr = uint64(datsize) 1514 ctxt.Syms.Lookup("runtime.itablink", 0).Sect = sect 1515 ctxt.Syms.Lookup("runtime.eitablink", 0).Sect = sect 1516 for _, s := range data[sym.SITABLINK] { 1517 datsize = aligndatsize(datsize, s) 1518 s.Sect = sect 1519 s.Type = sym.SRODATA 1520 s.Value = int64(uint64(datsize) - sect.Vaddr) 1521 datsize += s.Size 1522 } 1523 checkdatsize(ctxt, datsize, sym.SITABLINK) 1524 sect.Length = uint64(datsize) - sect.Vaddr 1525 1526 /* gosymtab */ 1527 sect = addrelrosection(".gosymtab") 1528 sect.Align = dataMaxAlign[sym.SSYMTAB] 1529 datsize = Rnd(datsize, int64(sect.Align)) 1530 sect.Vaddr = uint64(datsize) 1531 ctxt.Syms.Lookup("runtime.symtab", 0).Sect = sect 1532 ctxt.Syms.Lookup("runtime.esymtab", 0).Sect = sect 1533 for _, s := range data[sym.SSYMTAB] { 1534 datsize = aligndatsize(datsize, s) 1535 s.Sect = sect 1536 s.Type = sym.SRODATA 1537 s.Value = int64(uint64(datsize) - sect.Vaddr) 1538 datsize += s.Size 1539 } 1540 checkdatsize(ctxt, datsize, sym.SSYMTAB) 1541 sect.Length = uint64(datsize) - sect.Vaddr 1542 1543 /* gopclntab */ 1544 sect = addrelrosection(".gopclntab") 1545 sect.Align = dataMaxAlign[sym.SPCLNTAB] 1546 datsize = Rnd(datsize, int64(sect.Align)) 1547 sect.Vaddr = uint64(datsize) 1548 ctxt.Syms.Lookup("runtime.pclntab", 0).Sect = sect 1549 ctxt.Syms.Lookup("runtime.epclntab", 0).Sect = sect 1550 for _, s := range data[sym.SPCLNTAB] { 1551 datsize = aligndatsize(datsize, s) 1552 s.Sect = sect 1553 s.Type = sym.SRODATA 1554 s.Value = int64(uint64(datsize) - sect.Vaddr) 1555 datsize += s.Size 1556 } 1557 checkdatsize(ctxt, datsize, sym.SRODATA) 1558 sect.Length = uint64(datsize) - sect.Vaddr 1559 1560 // 6g uses 4-byte relocation offsets, so the entire segment must fit in 32 bits. 1561 if datsize != int64(uint32(datsize)) { 1562 Errorf(nil, "read-only data segment too large: %d", datsize) 1563 } 1564 1565 for symn := sym.SELFRXSECT; symn < sym.SXREF; symn++ { 1566 datap = append(datap, data[symn]...) 1567 } 1568 1569 dwarfgeneratedebugsyms(ctxt) 1570 1571 var i int 1572 for ; i < len(dwarfp); i++ { 1573 s := dwarfp[i] 1574 if s.Type != sym.SDWARFSECT { 1575 break 1576 } 1577 1578 sect = addsection(ctxt.Arch, &Segdwarf, s.Name, 04) 1579 sect.Align = 1 1580 datsize = Rnd(datsize, int64(sect.Align)) 1581 sect.Vaddr = uint64(datsize) 1582 s.Sect = sect 1583 s.Type = sym.SRODATA 1584 s.Value = int64(uint64(datsize) - sect.Vaddr) 1585 datsize += s.Size 1586 sect.Length = uint64(datsize) - sect.Vaddr 1587 } 1588 checkdatsize(ctxt, datsize, sym.SDWARFSECT) 1589 1590 for i < len(dwarfp) { 1591 curType := dwarfp[i].Type 1592 var sect *sym.Section 1593 switch curType { 1594 case sym.SDWARFINFO: 1595 sect = addsection(ctxt.Arch, &Segdwarf, ".debug_info", 04) 1596 case sym.SDWARFRANGE: 1597 sect = addsection(ctxt.Arch, &Segdwarf, ".debug_ranges", 04) 1598 case sym.SDWARFLOC: 1599 sect = addsection(ctxt.Arch, &Segdwarf, ".debug_loc", 04) 1600 default: 1601 Errorf(dwarfp[i], "unknown DWARF section %v", curType) 1602 } 1603 1604 sect.Align = 1 1605 datsize = Rnd(datsize, int64(sect.Align)) 1606 sect.Vaddr = uint64(datsize) 1607 for ; i < len(dwarfp); i++ { 1608 s := dwarfp[i] 1609 if s.Type != curType { 1610 break 1611 } 1612 s.Sect = sect 1613 s.Type = sym.SRODATA 1614 s.Value = int64(uint64(datsize) - sect.Vaddr) 1615 s.Attr |= sym.AttrLocal 1616 datsize += s.Size 1617 } 1618 sect.Length = uint64(datsize) - sect.Vaddr 1619 checkdatsize(ctxt, datsize, curType) 1620 } 1621 1622 /* number the sections */ 1623 n := int32(1) 1624 1625 for _, sect := range Segtext.Sections { 1626 sect.Extnum = int16(n) 1627 n++ 1628 } 1629 for _, sect := range Segrodata.Sections { 1630 sect.Extnum = int16(n) 1631 n++ 1632 } 1633 for _, sect := range Segrelrodata.Sections { 1634 sect.Extnum = int16(n) 1635 n++ 1636 } 1637 for _, sect := range Segdata.Sections { 1638 sect.Extnum = int16(n) 1639 n++ 1640 } 1641 for _, sect := range Segdwarf.Sections { 1642 sect.Extnum = int16(n) 1643 n++ 1644 } 1645 } 1646 1647 func dodataSect(ctxt *Link, symn sym.SymKind, syms []*sym.Symbol) (result []*sym.Symbol, maxAlign int32) { 1648 if ctxt.HeadType == objabi.Hdarwin { 1649 // Some symbols may no longer belong in syms 1650 // due to movement in machosymorder. 1651 newSyms := make([]*sym.Symbol, 0, len(syms)) 1652 for _, s := range syms { 1653 if s.Type == symn { 1654 newSyms = append(newSyms, s) 1655 } 1656 } 1657 syms = newSyms 1658 } 1659 1660 var head, tail *sym.Symbol 1661 symsSort := make([]dataSortKey, 0, len(syms)) 1662 for _, s := range syms { 1663 if s.Attr.OnList() { 1664 log.Fatalf("symbol %s listed multiple times", s.Name) 1665 } 1666 s.Attr |= sym.AttrOnList 1667 switch { 1668 case s.Size < int64(len(s.P)): 1669 Errorf(s, "initialize bounds (%d < %d)", s.Size, len(s.P)) 1670 case s.Size < 0: 1671 Errorf(s, "negative size (%d bytes)", s.Size) 1672 case s.Size > cutoff: 1673 Errorf(s, "symbol too large (%d bytes)", s.Size) 1674 } 1675 1676 // If the usually-special section-marker symbols are being laid 1677 // out as regular symbols, put them either at the beginning or 1678 // end of their section. 1679 if ctxt.DynlinkingGo() && ctxt.HeadType == objabi.Hdarwin { 1680 switch s.Name { 1681 case "runtime.text", "runtime.bss", "runtime.data", "runtime.types": 1682 head = s 1683 continue 1684 case "runtime.etext", "runtime.ebss", "runtime.edata", "runtime.etypes": 1685 tail = s 1686 continue 1687 } 1688 } 1689 1690 key := dataSortKey{ 1691 size: s.Size, 1692 name: s.Name, 1693 sym: s, 1694 } 1695 1696 switch s.Type { 1697 case sym.SELFGOT: 1698 // For ppc64, we want to interleave the .got and .toc sections 1699 // from input files. Both are type sym.SELFGOT, so in that case 1700 // we skip size comparison and fall through to the name 1701 // comparison (conveniently, .got sorts before .toc). 1702 key.size = 0 1703 } 1704 1705 symsSort = append(symsSort, key) 1706 } 1707 1708 sort.Sort(bySizeAndName(symsSort)) 1709 1710 off := 0 1711 if head != nil { 1712 syms[0] = head 1713 off++ 1714 } 1715 for i, symSort := range symsSort { 1716 syms[i+off] = symSort.sym 1717 align := symalign(symSort.sym) 1718 if maxAlign < align { 1719 maxAlign = align 1720 } 1721 } 1722 if tail != nil { 1723 syms[len(syms)-1] = tail 1724 } 1725 1726 if ctxt.IsELF && symn == sym.SELFROSECT { 1727 // Make .rela and .rela.plt contiguous, the ELF ABI requires this 1728 // and Solaris actually cares. 1729 reli, plti := -1, -1 1730 for i, s := range syms { 1731 switch s.Name { 1732 case ".rel.plt", ".rela.plt": 1733 plti = i 1734 case ".rel", ".rela": 1735 reli = i 1736 } 1737 } 1738 if reli >= 0 && plti >= 0 && plti != reli+1 { 1739 var first, second int 1740 if plti > reli { 1741 first, second = reli, plti 1742 } else { 1743 first, second = plti, reli 1744 } 1745 rel, plt := syms[reli], syms[plti] 1746 copy(syms[first+2:], syms[first+1:second]) 1747 syms[first+0] = rel 1748 syms[first+1] = plt 1749 1750 // Make sure alignment doesn't introduce a gap. 1751 // Setting the alignment explicitly prevents 1752 // symalign from basing it on the size and 1753 // getting it wrong. 1754 rel.Align = int32(ctxt.Arch.RegSize) 1755 plt.Align = int32(ctxt.Arch.RegSize) 1756 } 1757 } 1758 1759 return syms, maxAlign 1760 } 1761 1762 // Add buildid to beginning of text segment, on non-ELF systems. 1763 // Non-ELF binary formats are not always flexible enough to 1764 // give us a place to put the Go build ID. On those systems, we put it 1765 // at the very beginning of the text segment. 1766 // This ``header'' is read by cmd/go. 1767 func (ctxt *Link) textbuildid() { 1768 if ctxt.IsELF || ctxt.BuildMode == BuildModePlugin || *flagBuildid == "" { 1769 return 1770 } 1771 1772 s := ctxt.Syms.Lookup("go.buildid", 0) 1773 s.Attr |= sym.AttrReachable 1774 // The \xff is invalid UTF-8, meant to make it less likely 1775 // to find one of these accidentally. 1776 data := "\xff Go build ID: " + strconv.Quote(*flagBuildid) + "\n \xff" 1777 s.Type = sym.STEXT 1778 s.P = []byte(data) 1779 s.Size = int64(len(s.P)) 1780 1781 ctxt.Textp = append(ctxt.Textp, nil) 1782 copy(ctxt.Textp[1:], ctxt.Textp) 1783 ctxt.Textp[0] = s 1784 } 1785 1786 // assign addresses to text 1787 func (ctxt *Link) textaddress() { 1788 addsection(ctxt.Arch, &Segtext, ".text", 05) 1789 1790 // Assign PCs in text segment. 1791 // Could parallelize, by assigning to text 1792 // and then letting threads copy down, but probably not worth it. 1793 sect := Segtext.Sections[0] 1794 1795 sect.Align = int32(Funcalign) 1796 1797 text := ctxt.Syms.Lookup("runtime.text", 0) 1798 text.Sect = sect 1799 1800 if ctxt.DynlinkingGo() && ctxt.HeadType == objabi.Hdarwin { 1801 etext := ctxt.Syms.Lookup("runtime.etext", 0) 1802 etext.Sect = sect 1803 1804 ctxt.Textp = append(ctxt.Textp, etext, nil) 1805 copy(ctxt.Textp[1:], ctxt.Textp) 1806 ctxt.Textp[0] = text 1807 } 1808 1809 va := uint64(*FlagTextAddr) 1810 n := 1 1811 sect.Vaddr = va 1812 ntramps := 0 1813 for _, s := range ctxt.Textp { 1814 sect, n, va = assignAddress(ctxt, sect, n, s, va, false) 1815 1816 trampoline(ctxt, s) // resolve jumps, may add trampolines if jump too far 1817 1818 // lay down trampolines after each function 1819 for ; ntramps < len(ctxt.tramps); ntramps++ { 1820 tramp := ctxt.tramps[ntramps] 1821 sect, n, va = assignAddress(ctxt, sect, n, tramp, va, true) 1822 } 1823 } 1824 1825 sect.Length = va - sect.Vaddr 1826 ctxt.Syms.Lookup("runtime.etext", 0).Sect = sect 1827 1828 // merge tramps into Textp, keeping Textp in address order 1829 if ntramps != 0 { 1830 newtextp := make([]*sym.Symbol, 0, len(ctxt.Textp)+ntramps) 1831 i := 0 1832 for _, s := range ctxt.Textp { 1833 for ; i < ntramps && ctxt.tramps[i].Value < s.Value; i++ { 1834 newtextp = append(newtextp, ctxt.tramps[i]) 1835 } 1836 newtextp = append(newtextp, s) 1837 } 1838 newtextp = append(newtextp, ctxt.tramps[i:ntramps]...) 1839 1840 ctxt.Textp = newtextp 1841 } 1842 } 1843 1844 // assigns address for a text symbol, returns (possibly new) section, its number, and the address 1845 // Note: once we have trampoline insertion support for external linking, this function 1846 // will not need to create new text sections, and so no need to return sect and n. 1847 func assignAddress(ctxt *Link, sect *sym.Section, n int, s *sym.Symbol, va uint64, isTramp bool) (*sym.Section, int, uint64) { 1848 s.Sect = sect 1849 if s.Attr.SubSymbol() { 1850 return sect, n, va 1851 } 1852 if s.Align != 0 { 1853 va = uint64(Rnd(int64(va), int64(s.Align))) 1854 } else { 1855 va = uint64(Rnd(int64(va), int64(Funcalign))) 1856 } 1857 s.Value = 0 1858 for sub := s; sub != nil; sub = sub.Sub { 1859 sub.Value += int64(va) 1860 } 1861 1862 funcsize := uint64(MINFUNC) // spacing required for findfunctab 1863 if s.Size > MINFUNC { 1864 funcsize = uint64(s.Size) 1865 } 1866 1867 // On ppc64x a text section should not be larger than 2^26 bytes due to the size of 1868 // call target offset field in the bl instruction. Splitting into smaller text 1869 // sections smaller than this limit allows the GNU linker to modify the long calls 1870 // appropriately. The limit allows for the space needed for tables inserted by the linker. 1871 1872 // If this function doesn't fit in the current text section, then create a new one. 1873 1874 // Only break at outermost syms. 1875 1876 if ctxt.Arch.InFamily(sys.PPC64) && s.Outer == nil && ctxt.IsELF && ctxt.LinkMode == LinkExternal && va-sect.Vaddr+funcsize+maxSizeTrampolinesPPC64(s, isTramp) > 0x1c00000 { 1877 1878 // Set the length for the previous text section 1879 sect.Length = va - sect.Vaddr 1880 1881 // Create new section, set the starting Vaddr 1882 sect = addsection(ctxt.Arch, &Segtext, ".text", 05) 1883 sect.Vaddr = va 1884 s.Sect = sect 1885 1886 // Create a symbol for the start of the secondary text sections 1887 ctxt.Syms.Lookup(fmt.Sprintf("runtime.text.%d", n), 0).Sect = sect 1888 n++ 1889 } 1890 va += funcsize 1891 1892 return sect, n, va 1893 } 1894 1895 // assign addresses 1896 func (ctxt *Link) address() { 1897 va := uint64(*FlagTextAddr) 1898 Segtext.Rwx = 05 1899 Segtext.Vaddr = va 1900 Segtext.Fileoff = uint64(HEADR) 1901 for _, s := range Segtext.Sections { 1902 va = uint64(Rnd(int64(va), int64(s.Align))) 1903 s.Vaddr = va 1904 va += s.Length 1905 } 1906 1907 Segtext.Length = va - uint64(*FlagTextAddr) 1908 Segtext.Filelen = Segtext.Length 1909 if ctxt.HeadType == objabi.Hnacl { 1910 va += 32 // room for the "halt sled" 1911 } 1912 1913 if len(Segrodata.Sections) > 0 { 1914 // align to page boundary so as not to mix 1915 // rodata and executable text. 1916 // 1917 // Note: gold or GNU ld will reduce the size of the executable 1918 // file by arranging for the relro segment to end at a page 1919 // boundary, and overlap the end of the text segment with the 1920 // start of the relro segment in the file. The PT_LOAD segments 1921 // will be such that the last page of the text segment will be 1922 // mapped twice, once r-x and once starting out rw- and, after 1923 // relocation processing, changed to r--. 1924 // 1925 // Ideally the last page of the text segment would not be 1926 // writable even for this short period. 1927 va = uint64(Rnd(int64(va), int64(*FlagRound))) 1928 1929 Segrodata.Rwx = 04 1930 Segrodata.Vaddr = va 1931 Segrodata.Fileoff = va - Segtext.Vaddr + Segtext.Fileoff 1932 Segrodata.Filelen = 0 1933 for _, s := range Segrodata.Sections { 1934 va = uint64(Rnd(int64(va), int64(s.Align))) 1935 s.Vaddr = va 1936 va += s.Length 1937 } 1938 1939 Segrodata.Length = va - Segrodata.Vaddr 1940 Segrodata.Filelen = Segrodata.Length 1941 } 1942 if len(Segrelrodata.Sections) > 0 { 1943 // align to page boundary so as not to mix 1944 // rodata, rel-ro data, and executable text. 1945 va = uint64(Rnd(int64(va), int64(*FlagRound))) 1946 1947 Segrelrodata.Rwx = 06 1948 Segrelrodata.Vaddr = va 1949 Segrelrodata.Fileoff = va - Segrodata.Vaddr + Segrodata.Fileoff 1950 Segrelrodata.Filelen = 0 1951 for _, s := range Segrelrodata.Sections { 1952 va = uint64(Rnd(int64(va), int64(s.Align))) 1953 s.Vaddr = va 1954 va += s.Length 1955 } 1956 1957 Segrelrodata.Length = va - Segrelrodata.Vaddr 1958 Segrelrodata.Filelen = Segrelrodata.Length 1959 } 1960 1961 va = uint64(Rnd(int64(va), int64(*FlagRound))) 1962 Segdata.Rwx = 06 1963 Segdata.Vaddr = va 1964 Segdata.Fileoff = va - Segtext.Vaddr + Segtext.Fileoff 1965 Segdata.Filelen = 0 1966 if ctxt.HeadType == objabi.Hwindows { 1967 Segdata.Fileoff = Segtext.Fileoff + uint64(Rnd(int64(Segtext.Length), PEFILEALIGN)) 1968 } 1969 if ctxt.HeadType == objabi.Hplan9 { 1970 Segdata.Fileoff = Segtext.Fileoff + Segtext.Filelen 1971 } 1972 var data *sym.Section 1973 var noptr *sym.Section 1974 var bss *sym.Section 1975 var noptrbss *sym.Section 1976 for i, s := range Segdata.Sections { 1977 if ctxt.IsELF && s.Name == ".tbss" { 1978 continue 1979 } 1980 vlen := int64(s.Length) 1981 if i+1 < len(Segdata.Sections) && !(ctxt.IsELF && Segdata.Sections[i+1].Name == ".tbss") { 1982 vlen = int64(Segdata.Sections[i+1].Vaddr - s.Vaddr) 1983 } 1984 s.Vaddr = va 1985 va += uint64(vlen) 1986 Segdata.Length = va - Segdata.Vaddr 1987 if s.Name == ".data" { 1988 data = s 1989 } 1990 if s.Name == ".noptrdata" { 1991 noptr = s 1992 } 1993 if s.Name == ".bss" { 1994 bss = s 1995 } 1996 if s.Name == ".noptrbss" { 1997 noptrbss = s 1998 } 1999 } 2000 2001 Segdata.Filelen = bss.Vaddr - Segdata.Vaddr 2002 2003 va = uint64(Rnd(int64(va), int64(*FlagRound))) 2004 Segdwarf.Rwx = 06 2005 Segdwarf.Vaddr = va 2006 Segdwarf.Fileoff = Segdata.Fileoff + uint64(Rnd(int64(Segdata.Filelen), int64(*FlagRound))) 2007 Segdwarf.Filelen = 0 2008 if ctxt.HeadType == objabi.Hwindows { 2009 Segdwarf.Fileoff = Segdata.Fileoff + uint64(Rnd(int64(Segdata.Filelen), int64(PEFILEALIGN))) 2010 } 2011 for i, s := range Segdwarf.Sections { 2012 vlen := int64(s.Length) 2013 if i+1 < len(Segdwarf.Sections) { 2014 vlen = int64(Segdwarf.Sections[i+1].Vaddr - s.Vaddr) 2015 } 2016 s.Vaddr = va 2017 va += uint64(vlen) 2018 if ctxt.HeadType == objabi.Hwindows { 2019 va = uint64(Rnd(int64(va), PEFILEALIGN)) 2020 } 2021 Segdwarf.Length = va - Segdwarf.Vaddr 2022 } 2023 2024 Segdwarf.Filelen = va - Segdwarf.Vaddr 2025 2026 var ( 2027 text = Segtext.Sections[0] 2028 rodata = ctxt.Syms.Lookup("runtime.rodata", 0).Sect 2029 itablink = ctxt.Syms.Lookup("runtime.itablink", 0).Sect 2030 symtab = ctxt.Syms.Lookup("runtime.symtab", 0).Sect 2031 pclntab = ctxt.Syms.Lookup("runtime.pclntab", 0).Sect 2032 types = ctxt.Syms.Lookup("runtime.types", 0).Sect 2033 ) 2034 lasttext := text 2035 // Could be multiple .text sections 2036 for _, sect := range Segtext.Sections { 2037 if sect.Name == ".text" { 2038 lasttext = sect 2039 } 2040 } 2041 2042 for _, s := range datap { 2043 if s.Sect != nil { 2044 s.Value += int64(s.Sect.Vaddr) 2045 } 2046 for sub := s.Sub; sub != nil; sub = sub.Sub { 2047 sub.Value += s.Value 2048 } 2049 } 2050 2051 for _, s := range dwarfp { 2052 if s.Sect != nil { 2053 s.Value += int64(s.Sect.Vaddr) 2054 } 2055 for sub := s.Sub; sub != nil; sub = sub.Sub { 2056 sub.Value += s.Value 2057 } 2058 } 2059 2060 if ctxt.BuildMode == BuildModeShared { 2061 s := ctxt.Syms.Lookup("go.link.abihashbytes", 0) 2062 sectSym := ctxt.Syms.Lookup(".note.go.abihash", 0) 2063 s.Sect = sectSym.Sect 2064 s.Value = int64(sectSym.Sect.Vaddr + 16) 2065 } 2066 2067 ctxt.xdefine("runtime.text", sym.STEXT, int64(text.Vaddr)) 2068 ctxt.xdefine("runtime.etext", sym.STEXT, int64(lasttext.Vaddr+lasttext.Length)) 2069 2070 // If there are multiple text sections, create runtime.text.n for 2071 // their section Vaddr, using n for index 2072 n := 1 2073 for _, sect := range Segtext.Sections[1:] { 2074 if sect.Name != ".text" { 2075 break 2076 } 2077 symname := fmt.Sprintf("runtime.text.%d", n) 2078 ctxt.xdefine(symname, sym.STEXT, int64(sect.Vaddr)) 2079 n++ 2080 } 2081 2082 ctxt.xdefine("runtime.rodata", sym.SRODATA, int64(rodata.Vaddr)) 2083 ctxt.xdefine("runtime.erodata", sym.SRODATA, int64(rodata.Vaddr+rodata.Length)) 2084 ctxt.xdefine("runtime.types", sym.SRODATA, int64(types.Vaddr)) 2085 ctxt.xdefine("runtime.etypes", sym.SRODATA, int64(types.Vaddr+types.Length)) 2086 ctxt.xdefine("runtime.itablink", sym.SRODATA, int64(itablink.Vaddr)) 2087 ctxt.xdefine("runtime.eitablink", sym.SRODATA, int64(itablink.Vaddr+itablink.Length)) 2088 2089 s := ctxt.Syms.Lookup("runtime.gcdata", 0) 2090 s.Attr |= sym.AttrLocal 2091 ctxt.xdefine("runtime.egcdata", sym.SRODATA, Symaddr(s)+s.Size) 2092 ctxt.Syms.Lookup("runtime.egcdata", 0).Sect = s.Sect 2093 2094 s = ctxt.Syms.Lookup("runtime.gcbss", 0) 2095 s.Attr |= sym.AttrLocal 2096 ctxt.xdefine("runtime.egcbss", sym.SRODATA, Symaddr(s)+s.Size) 2097 ctxt.Syms.Lookup("runtime.egcbss", 0).Sect = s.Sect 2098 2099 ctxt.xdefine("runtime.symtab", sym.SRODATA, int64(symtab.Vaddr)) 2100 ctxt.xdefine("runtime.esymtab", sym.SRODATA, int64(symtab.Vaddr+symtab.Length)) 2101 ctxt.xdefine("runtime.pclntab", sym.SRODATA, int64(pclntab.Vaddr)) 2102 ctxt.xdefine("runtime.epclntab", sym.SRODATA, int64(pclntab.Vaddr+pclntab.Length)) 2103 ctxt.xdefine("runtime.noptrdata", sym.SNOPTRDATA, int64(noptr.Vaddr)) 2104 ctxt.xdefine("runtime.enoptrdata", sym.SNOPTRDATA, int64(noptr.Vaddr+noptr.Length)) 2105 ctxt.xdefine("runtime.bss", sym.SBSS, int64(bss.Vaddr)) 2106 ctxt.xdefine("runtime.ebss", sym.SBSS, int64(bss.Vaddr+bss.Length)) 2107 ctxt.xdefine("runtime.data", sym.SDATA, int64(data.Vaddr)) 2108 ctxt.xdefine("runtime.edata", sym.SDATA, int64(data.Vaddr+data.Length)) 2109 ctxt.xdefine("runtime.noptrbss", sym.SNOPTRBSS, int64(noptrbss.Vaddr)) 2110 ctxt.xdefine("runtime.enoptrbss", sym.SNOPTRBSS, int64(noptrbss.Vaddr+noptrbss.Length)) 2111 ctxt.xdefine("runtime.end", sym.SBSS, int64(Segdata.Vaddr+Segdata.Length)) 2112 } 2113 2114 // add a trampoline with symbol s (to be laid down after the current function) 2115 func (ctxt *Link) AddTramp(s *sym.Symbol) { 2116 s.Type = sym.STEXT 2117 s.Attr |= sym.AttrReachable 2118 s.Attr |= sym.AttrOnList 2119 ctxt.tramps = append(ctxt.tramps, s) 2120 if *FlagDebugTramp > 0 && ctxt.Debugvlog > 0 { 2121 ctxt.Logf("trampoline %s inserted\n", s) 2122 } 2123 }