funcdata_go116.go (5092B)
1 //go:build go1.16 && !go1.18 2 // +build go1.16,!go1.18 3 4 /* 5 * Copyright 2021 ByteDance Inc. 6 * 7 * Licensed under the Apache License, Version 2.0 (the "License"); 8 * you may not use this file except in compliance with the License. 9 * You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, software 14 * distributed under the License is distributed on an "AS IS" BASIS, 15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 * See the License for the specific language governing permissions and 17 * limitations under the License. 18 */ 19 20 package loader 21 22 import ( 23 `unsafe` 24 ) 25 26 type _Func struct { 27 entry uintptr // start pc 28 nameoff int32 // function name 29 args int32 // in/out args size 30 deferreturn uint32 // offset of start of a deferreturn call instruction from entry, if any. 31 pcsp uint32 32 pcfile uint32 33 pcln uint32 34 npcdata uint32 35 cuOffset uint32 // runtime.cutab offset of this function's CU 36 funcID uint8 // set for certain special runtime functions 37 _ [2]byte // pad 38 nfuncdata uint8 // must be last 39 argptrs uintptr 40 localptrs uintptr 41 } 42 43 type _FuncTab struct { 44 entry uintptr 45 funcoff uintptr 46 } 47 48 type _PCHeader struct { 49 magic uint32 // 0xFFFFFFFA 50 pad1, pad2 uint8 // 0,0 51 minLC uint8 // min instruction size 52 ptrSize uint8 // size of a ptr in bytes 53 nfunc int // number of functions in the module 54 nfiles uint // number of entries in the file tab. 55 funcnameOffset uintptr // offset to the funcnametab variable from _PCHeader 56 cuOffset uintptr // offset to the cutab variable from _PCHeader 57 filetabOffset uintptr // offset to the filetab variable from _PCHeader 58 pctabOffset uintptr // offset to the pctab varible from _PCHeader 59 pclnOffset uintptr // offset to the pclntab variable from _PCHeader 60 } 61 62 type _BitVector struct { 63 n int32 // # of bits 64 bytedata *uint8 65 } 66 67 type _PtabEntry struct { 68 name int32 69 typ int32 70 } 71 72 type _TextSection struct { 73 vaddr uintptr // prelinked section vaddr 74 length uintptr // section length 75 baseaddr uintptr // relocated section address 76 } 77 78 type _ModuleData struct { 79 pcHeader *_PCHeader 80 funcnametab []byte 81 cutab []uint32 82 filetab []byte 83 pctab []byte 84 pclntable []_Func 85 ftab []_FuncTab 86 findfunctab *_FindFuncBucket 87 minpc, maxpc uintptr 88 text, etext uintptr 89 noptrdata, enoptrdata uintptr 90 data, edata uintptr 91 bss, ebss uintptr 92 noptrbss, enoptrbss uintptr 93 end, gcdata, gcbss uintptr 94 types, etypes uintptr 95 textsectmap []_TextSection 96 typelinks []int32 97 itablinks []unsafe.Pointer 98 ptab []_PtabEntry 99 pluginpath string 100 pkghashes []struct{} 101 modulename string 102 modulehashes []struct{} 103 hasmain uint8 104 gcdatamask, gcbssmask _BitVector 105 typemap map[int32]unsafe.Pointer 106 bad bool 107 next *_ModuleData 108 } 109 110 type _FindFuncBucket struct { 111 idx uint32 112 subbuckets [16]byte 113 } 114 115 var modHeader = &_PCHeader { 116 magic : 0xfffffffa, 117 minLC : 1, 118 nfunc : 1, 119 ptrSize : 4 << (^uintptr(0) >> 63), 120 } 121 122 var findFuncTab = &_FindFuncBucket { 123 idx: 1, 124 } 125 126 func makePCtab(fp int) []byte { 127 return append([]byte{0}, encodeVariant((fp + 1) << 1)...) 128 } 129 130 func registerFunction(name string, pc uintptr, textSize uintptr, fp int, args int, size uintptr, argPtrs []bool, localPtrs []bool) { 131 mod := new(_ModuleData) 132 133 minpc := pc 134 maxpc := pc + size 135 136 // cache arg and local stackmap 137 argptrs, localptrs := cacheStackmap(argPtrs, localPtrs, mod) 138 139 /* function entry */ 140 lnt := []_Func {{ 141 entry : pc, 142 nameoff : 1, 143 args : int32(args), 144 pcsp : 1, 145 nfuncdata : 2, 146 argptrs : uintptr(argptrs), 147 localptrs : uintptr(localptrs), 148 }} 149 150 /* function table */ 151 tab := []_FuncTab { 152 {entry: pc}, 153 {entry: pc}, 154 {entry: maxpc}, 155 } 156 157 /* module data */ 158 *mod = _ModuleData { 159 pcHeader : modHeader, 160 funcnametab : append(append([]byte{0}, name...), 0), 161 pctab : append(makePCtab(fp), encodeVariant(int(size))...), 162 pclntable : lnt, 163 ftab : tab, 164 findfunctab : findFuncTab, 165 minpc : minpc, 166 maxpc : maxpc, 167 modulename : name, 168 gcdata: uintptr(unsafe.Pointer(&emptyByte)), 169 gcbss: uintptr(unsafe.Pointer(&emptyByte)), 170 } 171 172 /* verify and register the new module */ 173 moduledataverify1(mod) 174 registerModule(mod) 175 }