1 // Do not edit. Bootstrap copy of /usr/local/google/buildbot/src/android/build-tools/out/obj/go/src/cmd/link/internal/ld/decodesym.go 2 3 //line /usr/local/google/buildbot/src/android/build-tools/out/obj/go/src/cmd/link/internal/ld/decodesym.go:1 4 // Copyright 2012 The Go Authors. All rights reserved. 5 // Use of this source code is governed by a BSD-style 6 // license that can be found in the LICENSE file. 7 8 package ld 9 10 import ( 11 "bootstrap/internal/obj" 12 "debug/elf" 13 ) 14 15 // Decoding the type.* symbols. This has to be in sync with 16 // ../../runtime/type.go, or more specifically, with what 17 // ../gc/reflect.c stuffs in these. 18 19 func decode_reloc(s *LSym, off int32) *Reloc { 20 for i := 0; i < len(s.R); i++ { 21 if s.R[i].Off == off { 22 return &s.R[i:][0] 23 } 24 } 25 return nil 26 } 27 28 func decode_reloc_sym(s *LSym, off int32) *LSym { 29 r := decode_reloc(s, off) 30 if r == nil { 31 return nil 32 } 33 return r.Sym 34 } 35 36 func decode_inuxi(p []byte, sz int) uint64 { 37 switch sz { 38 case 2: 39 return uint64(Ctxt.Arch.ByteOrder.Uint16(p)) 40 case 4: 41 return uint64(Ctxt.Arch.ByteOrder.Uint32(p)) 42 case 8: 43 return Ctxt.Arch.ByteOrder.Uint64(p) 44 default: 45 Exitf("dwarf: decode inuxi %d", sz) 46 panic("unreachable") 47 } 48 } 49 50 // commonsize returns the size of the common prefix for all type 51 // structures (runtime._type). 52 func commonsize() int { 53 return 8*Thearch.Ptrsize + 8 54 } 55 56 // Type.commonType.kind 57 func decodetype_kind(s *LSym) uint8 { 58 return uint8(s.P[2*Thearch.Ptrsize+7] & obj.KindMask) // 0x13 / 0x1f 59 } 60 61 // Type.commonType.kind 62 func decodetype_noptr(s *LSym) uint8 { 63 return uint8(s.P[2*Thearch.Ptrsize+7] & obj.KindNoPointers) // 0x13 / 0x1f 64 } 65 66 // Type.commonType.kind 67 func decodetype_usegcprog(s *LSym) uint8 { 68 return uint8(s.P[2*Thearch.Ptrsize+7] & obj.KindGCProg) // 0x13 / 0x1f 69 } 70 71 // Type.commonType.size 72 func decodetype_size(s *LSym) int64 { 73 return int64(decode_inuxi(s.P, Thearch.Ptrsize)) // 0x8 / 0x10 74 } 75 76 // Type.commonType.ptrdata 77 func decodetype_ptrdata(s *LSym) int64 { 78 return int64(decode_inuxi(s.P[Thearch.Ptrsize:], Thearch.Ptrsize)) // 0x8 / 0x10 79 } 80 81 // Find the elf.Section of a given shared library that contains a given address. 82 func findShlibSection(path string, addr uint64) *elf.Section { 83 for _, shlib := range Ctxt.Shlibs { 84 if shlib.Path == path { 85 for _, sect := range shlib.File.Sections { 86 if sect.Addr <= addr && addr <= sect.Addr+sect.Size { 87 return sect 88 } 89 } 90 } 91 } 92 return nil 93 } 94 95 // Type.commonType.gc 96 func decodetype_gcprog(s *LSym) []byte { 97 if s.Type == obj.SDYNIMPORT { 98 addr := decodetype_gcprog_shlib(s) 99 sect := findShlibSection(s.File, addr) 100 if sect != nil { 101 // A gcprog is a 4-byte uint32 indicating length, followed by 102 // the actual program. 103 progsize := make([]byte, 4) 104 sect.ReadAt(progsize, int64(addr-sect.Addr)) 105 progbytes := make([]byte, Ctxt.Arch.ByteOrder.Uint32(progsize)) 106 sect.ReadAt(progbytes, int64(addr-sect.Addr+4)) 107 return append(progsize, progbytes...) 108 } 109 Exitf("cannot find gcprog for %s", s.Name) 110 return nil 111 } 112 return decode_reloc_sym(s, 2*int32(Thearch.Ptrsize)+8+1*int32(Thearch.Ptrsize)).P 113 } 114 115 func decodetype_gcprog_shlib(s *LSym) uint64 { 116 return decode_inuxi(s.P[2*int32(Thearch.Ptrsize)+8+1*int32(Thearch.Ptrsize):], Thearch.Ptrsize) 117 } 118 119 func decodetype_gcmask(s *LSym) []byte { 120 if s.Type == obj.SDYNIMPORT { 121 addr := decodetype_gcprog_shlib(s) 122 ptrdata := decodetype_ptrdata(s) 123 sect := findShlibSection(s.File, addr) 124 if sect != nil { 125 r := make([]byte, ptrdata/int64(Thearch.Ptrsize)) 126 sect.ReadAt(r, int64(addr-sect.Addr)) 127 return r 128 } 129 Exitf("cannot find gcmask for %s", s.Name) 130 return nil 131 } 132 mask := decode_reloc_sym(s, 2*int32(Thearch.Ptrsize)+8+1*int32(Thearch.Ptrsize)) 133 return mask.P 134 } 135 136 // Type.ArrayType.elem and Type.SliceType.Elem 137 func decodetype_arrayelem(s *LSym) *LSym { 138 return decode_reloc_sym(s, int32(commonsize())) // 0x1c / 0x30 139 } 140 141 func decodetype_arraylen(s *LSym) int64 { 142 return int64(decode_inuxi(s.P[commonsize()+2*Thearch.Ptrsize:], Thearch.Ptrsize)) 143 } 144 145 // Type.PtrType.elem 146 func decodetype_ptrelem(s *LSym) *LSym { 147 return decode_reloc_sym(s, int32(commonsize())) // 0x1c / 0x30 148 } 149 150 // Type.MapType.key, elem 151 func decodetype_mapkey(s *LSym) *LSym { 152 return decode_reloc_sym(s, int32(commonsize())) // 0x1c / 0x30 153 } 154 155 func decodetype_mapvalue(s *LSym) *LSym { 156 return decode_reloc_sym(s, int32(commonsize())+int32(Thearch.Ptrsize)) // 0x20 / 0x38 157 } 158 159 // Type.ChanType.elem 160 func decodetype_chanelem(s *LSym) *LSym { 161 return decode_reloc_sym(s, int32(commonsize())) // 0x1c / 0x30 162 } 163 164 // Type.FuncType.dotdotdot 165 func decodetype_funcdotdotdot(s *LSym) int { 166 return int(s.P[commonsize()]) 167 } 168 169 // Type.FuncType.in.length 170 func decodetype_funcincount(s *LSym) int { 171 return int(decode_inuxi(s.P[commonsize()+2*Thearch.Ptrsize:], Thearch.Intsize)) 172 } 173 174 func decodetype_funcoutcount(s *LSym) int { 175 return int(decode_inuxi(s.P[commonsize()+3*Thearch.Ptrsize+2*Thearch.Intsize:], Thearch.Intsize)) 176 } 177 178 func decodetype_funcintype(s *LSym, i int) *LSym { 179 r := decode_reloc(s, int32(commonsize())+int32(Thearch.Ptrsize)) 180 if r == nil { 181 return nil 182 } 183 return decode_reloc_sym(r.Sym, int32(r.Add+int64(int32(i)*int32(Thearch.Ptrsize)))) 184 } 185 186 func decodetype_funcouttype(s *LSym, i int) *LSym { 187 r := decode_reloc(s, int32(commonsize())+2*int32(Thearch.Ptrsize)+2*int32(Thearch.Intsize)) 188 if r == nil { 189 return nil 190 } 191 return decode_reloc_sym(r.Sym, int32(r.Add+int64(int32(i)*int32(Thearch.Ptrsize)))) 192 } 193 194 // Type.StructType.fields.Slice::length 195 func decodetype_structfieldcount(s *LSym) int { 196 return int(decode_inuxi(s.P[commonsize()+Thearch.Ptrsize:], Thearch.Intsize)) 197 } 198 199 func structfieldsize() int { 200 return 5 * Thearch.Ptrsize 201 } 202 203 // Type.StructType.fields[]-> name, typ and offset. 204 func decodetype_structfieldname(s *LSym, i int) string { 205 // go.string."foo" 0x28 / 0x40 206 s = decode_reloc_sym(s, int32(commonsize())+int32(Thearch.Ptrsize)+2*int32(Thearch.Intsize)+int32(i)*int32(structfieldsize())) 207 208 if s == nil { // embedded structs have a nil name. 209 return "" 210 } 211 r := decode_reloc(s, 0) // s has a pointer to the string data at offset 0 212 if r == nil { // shouldn't happen. 213 return "" 214 } 215 return cstring(r.Sym.P[r.Add:]) 216 } 217 218 func decodetype_structfieldtype(s *LSym, i int) *LSym { 219 return decode_reloc_sym(s, int32(commonsize())+int32(Thearch.Ptrsize)+2*int32(Thearch.Intsize)+int32(i)*int32(structfieldsize())+2*int32(Thearch.Ptrsize)) 220 } 221 222 func decodetype_structfieldoffs(s *LSym, i int) int64 { 223 return int64(decode_inuxi(s.P[commonsize()+Thearch.Ptrsize+2*Thearch.Intsize+i*structfieldsize()+4*Thearch.Ptrsize:], Thearch.Intsize)) 224 } 225 226 // InterfaceType.methods.length 227 func decodetype_ifacemethodcount(s *LSym) int64 { 228 return int64(decode_inuxi(s.P[commonsize()+Thearch.Ptrsize:], Thearch.Intsize)) 229 } 230