1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32 package obj
33
34 import (
35 "cmd/internal/objabi"
36 "log"
37 "math"
38 )
39
40
41 func (s *LSym) Grow(lsiz int64) {
42 siz := int(lsiz)
43 if int64(siz) != lsiz {
44 log.Fatalf("LSym.Grow size %d too long", lsiz)
45 }
46 if len(s.P) >= siz {
47 return
48 }
49 s.P = append(s.P, make([]byte, siz-len(s.P))...)
50 }
51
52
53 func (s *LSym) GrowCap(c int64) {
54 if int64(cap(s.P)) >= c {
55 return
56 }
57 if s.P == nil {
58 s.P = make([]byte, 0, c)
59 return
60 }
61 b := make([]byte, len(s.P), c)
62 copy(b, s.P)
63 s.P = b
64 }
65
66
67 func (s *LSym) prepwrite(ctxt *Link, off int64, siz int) {
68 if off < 0 || siz < 0 || off >= 1<<30 {
69 ctxt.Diag("prepwrite: bad off=%d siz=%d s=%v", off, siz, s)
70 }
71 switch s.Type {
72 case objabi.Sxxx, objabi.SBSS:
73 s.Type = objabi.SDATA
74 s.setFIPSType(ctxt)
75 case objabi.SNOPTRBSS:
76 s.Type = objabi.SNOPTRDATA
77 s.setFIPSType(ctxt)
78 case objabi.STLSBSS:
79 ctxt.Diag("cannot supply data for %v var %v", s.Type, s.Name)
80 }
81 l := off + int64(siz)
82 s.Grow(l)
83 if l > s.Size {
84 s.Size = l
85 }
86 }
87
88
89 func (s *LSym) WriteFloat32(ctxt *Link, off int64, f float32) {
90 s.prepwrite(ctxt, off, 4)
91 ctxt.Arch.ByteOrder.PutUint32(s.P[off:], math.Float32bits(f))
92 }
93
94
95 func (s *LSym) WriteFloat64(ctxt *Link, off int64, f float64) {
96 s.prepwrite(ctxt, off, 8)
97 ctxt.Arch.ByteOrder.PutUint64(s.P[off:], math.Float64bits(f))
98 }
99
100
101 func (s *LSym) WriteInt(ctxt *Link, off int64, siz int, i int64) {
102 s.prepwrite(ctxt, off, siz)
103 switch siz {
104 default:
105 ctxt.Diag("WriteInt: bad integer size: %d", siz)
106 case 1:
107 s.P[off] = byte(i)
108 case 2:
109 ctxt.Arch.ByteOrder.PutUint16(s.P[off:], uint16(i))
110 case 4:
111 ctxt.Arch.ByteOrder.PutUint32(s.P[off:], uint32(i))
112 case 8:
113 ctxt.Arch.ByteOrder.PutUint64(s.P[off:], uint64(i))
114 }
115 }
116
117 func (s *LSym) writeAddr(ctxt *Link, off int64, siz int, rsym *LSym, roff int64, rtype objabi.RelocType) {
118
119 if siz != ctxt.Arch.PtrSize && siz != 4 {
120 ctxt.Diag("WriteAddr: bad address size %d in %s", siz, s.Name)
121 }
122 s.prepwrite(ctxt, off, siz)
123 if int64(int32(off)) != off {
124 ctxt.Diag("WriteAddr: off overflow %d in %s", off, s.Name)
125 }
126 s.AddRel(ctxt, Reloc{
127 Type: rtype,
128 Off: int32(off),
129 Siz: uint8(siz),
130 Sym: rsym,
131 Add: roff,
132 })
133 }
134
135
136
137 func (s *LSym) WriteAddr(ctxt *Link, off int64, siz int, rsym *LSym, roff int64) {
138 s.writeAddr(ctxt, off, siz, rsym, roff, objabi.R_ADDR)
139 }
140
141
142
143
144 func (s *LSym) WriteWeakAddr(ctxt *Link, off int64, siz int, rsym *LSym, roff int64) {
145 s.writeAddr(ctxt, off, siz, rsym, roff, objabi.R_WEAKADDR)
146 }
147
148
149
150
151
152 func (s *LSym) WriteCURelativeAddr(ctxt *Link, off int64, rsym *LSym, roff int64) {
153 s.writeAddr(ctxt, off, ctxt.Arch.PtrSize, rsym, roff, objabi.R_ADDRCUOFF)
154 }
155
156
157
158
159 func (s *LSym) WriteOff(ctxt *Link, off int64, rsym *LSym, roff int64) {
160 s.prepwrite(ctxt, off, 4)
161 if int64(int32(off)) != off {
162 ctxt.Diag("WriteOff: off overflow %d in %s", off, s.Name)
163 }
164 s.AddRel(ctxt, Reloc{
165 Type: objabi.R_ADDROFF,
166 Off: int32(off),
167 Siz: 4,
168 Sym: rsym,
169 Add: roff,
170 })
171 }
172
173
174
175
176 func (s *LSym) WriteWeakOff(ctxt *Link, off int64, rsym *LSym, roff int64) {
177 s.prepwrite(ctxt, off, 4)
178 if int64(int32(off)) != off {
179 ctxt.Diag("WriteWeakOff: off overflow %d in %s", off, s.Name)
180 }
181 s.AddRel(ctxt, Reloc{
182 Type: objabi.R_WEAKADDROFF,
183 Off: int32(off),
184 Siz: 4,
185 Sym: rsym,
186 Add: roff,
187 })
188 }
189
190
191 func (s *LSym) WriteString(ctxt *Link, off int64, siz int, str string) {
192 if siz < len(str) {
193 ctxt.Diag("WriteString: bad string size: %d < %d", siz, len(str))
194 }
195 s.prepwrite(ctxt, off, siz)
196 copy(s.P[off:off+int64(siz)], str)
197 }
198
199
200 func (s *LSym) WriteBytes(ctxt *Link, off int64, b []byte) int64 {
201 s.prepwrite(ctxt, off, len(b))
202 copy(s.P[off:], b)
203 return off + int64(len(b))
204 }
205
206
207 func (s *LSym) AddRel(ctxt *Link, rel Reloc) {
208 if s.Type.IsFIPS() {
209 s.checkFIPSReloc(ctxt, rel)
210 }
211 s.R = append(s.R, rel)
212 }
213
View as plain text