i386lynx.c revision 1.1.1.6 1 1.1 skrll /* BFD back-end for i386 a.out binaries under LynxOS.
2 1.1.1.6 christos Copyright (C) 1990-2018 Free Software Foundation, Inc.
3 1.1 skrll
4 1.1 skrll This file is part of BFD, the Binary File Descriptor library.
5 1.1 skrll
6 1.1 skrll This program is free software; you can redistribute it and/or modify
7 1.1 skrll it under the terms of the GNU General Public License as published by
8 1.1 skrll the Free Software Foundation; either version 3 of the License, or
9 1.1 skrll (at your option) any later version.
10 1.1 skrll
11 1.1 skrll This program is distributed in the hope that it will be useful,
12 1.1 skrll but WITHOUT ANY WARRANTY; without even the implied warranty of
13 1.1 skrll MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 1.1 skrll GNU General Public License for more details.
15 1.1 skrll
16 1.1 skrll You should have received a copy of the GNU General Public License
17 1.1 skrll along with this program; if not, write to the Free Software
18 1.1 skrll Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
19 1.1 skrll MA 02110-1301, USA. */
20 1.1 skrll
21 1.1 skrll #define TEXT_START_ADDR 0
22 1.1 skrll #define TARGET_PAGE_SIZE 4096
23 1.1 skrll #define SEGMENT_SIZE TARGET_PAGE_SIZE
24 1.1 skrll #define DEFAULT_ARCH bfd_arch_i386
25 1.1 skrll
26 1.1 skrll /* Do not "beautify" the CONCAT* macro args. Traditional C will not
27 1.1 skrll remove whitespace added here, and thus will fail to concatenate
28 1.1 skrll the tokens. */
29 1.1.1.4 christos #define MY(OP) CONCAT2 (i386_aout_lynx_,OP)
30 1.1 skrll #define TARGETNAME "a.out-i386-lynx"
31 1.1 skrll
32 1.1 skrll #include "sysdep.h"
33 1.1 skrll #include "bfd.h"
34 1.1 skrll #include "libbfd.h"
35 1.1 skrll
36 1.1 skrll #ifndef WRITE_HEADERS
37 1.1 skrll #define WRITE_HEADERS(abfd, execp) \
38 1.1 skrll { \
39 1.1 skrll if (adata(abfd).magic == undecided_magic) \
40 1.1.1.5 christos NAME(aout,adjust_sizes_and_vmas) (abfd); \
41 1.1.1.6 christos \
42 1.1 skrll execp->a_syms = bfd_get_symcount (abfd) * EXTERNAL_NLIST_SIZE; \
43 1.1 skrll execp->a_entry = bfd_get_start_address (abfd); \
44 1.1.1.6 christos \
45 1.1 skrll execp->a_trsize = ((obj_textsec (abfd)->reloc_count) * \
46 1.1 skrll obj_reloc_entry_size (abfd)); \
47 1.1 skrll execp->a_drsize = ((obj_datasec (abfd)->reloc_count) * \
48 1.1 skrll obj_reloc_entry_size (abfd)); \
49 1.1 skrll NAME(aout,swap_exec_header_out) (abfd, execp, &exec_bytes); \
50 1.1 skrll \
51 1.1 skrll if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0 \
52 1.1.1.3 christos || bfd_bwrite (&exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, \
53 1.1 skrll abfd) != EXEC_BYTES_SIZE) \
54 1.1 skrll return FALSE; \
55 1.1 skrll /* Now write out reloc info, followed by syms and strings */ \
56 1.1.1.6 christos \
57 1.1.1.6 christos if (bfd_get_symcount (abfd) != 0) \
58 1.1 skrll { \
59 1.1.1.5 christos if (bfd_seek (abfd, (file_ptr) (N_SYMOFF (execp)), SEEK_SET) \
60 1.1 skrll != 0) \
61 1.1.1.6 christos return FALSE; \
62 1.1 skrll \
63 1.1 skrll if (! NAME(aout,write_syms) (abfd)) return FALSE; \
64 1.1 skrll \
65 1.1.1.5 christos if (bfd_seek (abfd, (file_ptr) (N_TRELOFF (execp)), SEEK_SET) \
66 1.1 skrll != 0) \
67 1.1.1.6 christos return FALSE; \
68 1.1 skrll \
69 1.1 skrll if (!NAME(lynx,squirt_out_relocs) (abfd, obj_textsec (abfd))) \
70 1.1 skrll return FALSE; \
71 1.1.1.5 christos if (bfd_seek (abfd, (file_ptr) (N_DRELOFF (execp)), SEEK_SET) \
72 1.1 skrll != 0) \
73 1.1.1.6 christos return 0; \
74 1.1 skrll \
75 1.1 skrll if (!NAME(lynx,squirt_out_relocs) (abfd, obj_datasec (abfd))) \
76 1.1 skrll return FALSE; \
77 1.1 skrll } \
78 1.1 skrll }
79 1.1 skrll #endif
80 1.1 skrll
81 1.1 skrll #include "libaout.h"
82 1.1 skrll #include "aout/aout64.h"
83 1.1 skrll
84 1.1 skrll
85 1.1 skrll #ifdef LYNX_CORE
86 1.1 skrll
87 1.1 skrll char *lynx_core_file_failing_command ();
88 1.1 skrll int lynx_core_file_failing_signal ();
89 1.1 skrll bfd_boolean lynx_core_file_matches_executable_p ();
90 1.1 skrll const bfd_target *lynx_core_file_p ();
91 1.1 skrll
92 1.1 skrll #define MY_core_file_failing_command lynx_core_file_failing_command
93 1.1 skrll #define MY_core_file_failing_signal lynx_core_file_failing_signal
94 1.1 skrll #define MY_core_file_matches_executable_p lynx_core_file_matches_executable_p
95 1.1 skrll #define MY_core_file_p lynx_core_file_p
96 1.1 skrll
97 1.1 skrll #endif /* LYNX_CORE */
98 1.1 skrll
99 1.1 skrll
101 1.1 skrll #define KEEPIT udata.i
102 1.1 skrll
103 1.1 skrll extern reloc_howto_type aout_32_ext_howto_table[];
104 1.1 skrll extern reloc_howto_type aout_32_std_howto_table[];
105 1.1 skrll
106 1.1 skrll /* Standard reloc stuff */
107 1.1 skrll /* Output standard relocation information to a file in target byte order. */
108 1.1.1.3 christos
109 1.1.1.3 christos static void
110 1.1.1.3 christos NAME(lynx,swap_std_reloc_out) (bfd *abfd,
111 1.1.1.3 christos arelent *g,
112 1.1 skrll struct reloc_std_external *natptr)
113 1.1 skrll {
114 1.1 skrll int r_index;
115 1.1 skrll asymbol *sym = *(g->sym_ptr_ptr);
116 1.1 skrll int r_extern;
117 1.1 skrll unsigned int r_length;
118 1.1 skrll int r_pcrel;
119 1.1 skrll int r_baserel, r_jmptable, r_relative;
120 1.1 skrll asection *output_section = sym->section->output_section;
121 1.1 skrll
122 1.1 skrll PUT_WORD (abfd, g->address, natptr->r_address);
123 1.1 skrll
124 1.1 skrll r_length = g->howto->size; /* Size as a power of two */
125 1.1 skrll r_pcrel = (int) g->howto->pc_relative; /* Relative to PC? */
126 1.1 skrll /* r_baserel, r_jmptable, r_relative??? FIXME-soon */
127 1.1 skrll r_baserel = 0;
128 1.1 skrll r_jmptable = 0;
129 1.1 skrll r_relative = 0;
130 1.1 skrll
131 1.1 skrll /* name was clobbered by aout_write_syms to be symbol index */
132 1.1 skrll
133 1.1 skrll /* If this relocation is relative to a symbol then set the
134 1.1 skrll r_index to the symbols index, and the r_extern bit.
135 1.1 skrll
136 1.1 skrll Absolute symbols can come in in two ways, either as an offset
137 1.1 skrll from the abs section, or as a symbol which has an abs value.
138 1.1 skrll check for that here
139 1.1 skrll */
140 1.1 skrll
141 1.1 skrll if (bfd_is_com_section (output_section)
142 1.1 skrll || bfd_is_abs_section (output_section)
143 1.1 skrll || bfd_is_und_section (output_section))
144 1.1 skrll {
145 1.1 skrll if (bfd_abs_section_ptr->symbol == sym)
146 1.1 skrll {
147 1.1 skrll /* Whoops, looked like an abs symbol, but is really an offset
148 1.1 skrll from the abs section */
149 1.1 skrll r_index = 0;
150 1.1 skrll r_extern = 0;
151 1.1 skrll }
152 1.1 skrll else
153 1.1 skrll {
154 1.1 skrll /* Fill in symbol */
155 1.1 skrll r_extern = 1;
156 1.1 skrll r_index = (*g->sym_ptr_ptr)->KEEPIT;
157 1.1 skrll }
158 1.1 skrll }
159 1.1 skrll else
160 1.1 skrll {
161 1.1 skrll /* Just an ordinary section */
162 1.1 skrll r_extern = 0;
163 1.1 skrll r_index = output_section->target_index;
164 1.1 skrll }
165 1.1 skrll
166 1.1 skrll /* now the fun stuff */
167 1.1 skrll if (bfd_header_big_endian (abfd))
168 1.1 skrll {
169 1.1 skrll natptr->r_index[0] = r_index >> 16;
170 1.1 skrll natptr->r_index[1] = r_index >> 8;
171 1.1 skrll natptr->r_index[2] = r_index;
172 1.1 skrll natptr->r_type[0] =
173 1.1 skrll (r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
174 1.1 skrll | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
175 1.1 skrll | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
176 1.1 skrll | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
177 1.1 skrll | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
178 1.1 skrll | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG);
179 1.1 skrll }
180 1.1 skrll else
181 1.1 skrll {
182 1.1 skrll natptr->r_index[2] = r_index >> 16;
183 1.1 skrll natptr->r_index[1] = r_index >> 8;
184 1.1 skrll natptr->r_index[0] = r_index;
185 1.1 skrll natptr->r_type[0] =
186 1.1 skrll (r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
187 1.1 skrll | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
188 1.1 skrll | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
189 1.1 skrll | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
190 1.1 skrll | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
191 1.1 skrll | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE);
192 1.1 skrll }
193 1.1 skrll }
194 1.1 skrll
195 1.1 skrll
196 1.1 skrll /* Extended stuff */
197 1.1 skrll /* Output extended relocation information to a file in target byte order. */
198 1.1.1.3 christos
199 1.1.1.3 christos static void
200 1.1.1.3 christos NAME(lynx,swap_ext_reloc_out) (bfd *abfd,
201 1.1.1.3 christos arelent *g,
202 1.1 skrll struct reloc_ext_external *natptr)
203 1.1 skrll {
204 1.1 skrll int r_index;
205 1.1 skrll int r_extern;
206 1.1 skrll unsigned int r_type;
207 1.1 skrll unsigned int r_addend;
208 1.1 skrll asymbol *sym = *(g->sym_ptr_ptr);
209 1.1 skrll asection *output_section = sym->section->output_section;
210 1.1 skrll
211 1.1 skrll PUT_WORD (abfd, g->address, natptr->r_address);
212 1.1 skrll
213 1.1 skrll r_type = (unsigned int) g->howto->type;
214 1.1 skrll
215 1.1 skrll r_addend = g->addend + (*(g->sym_ptr_ptr))->section->output_section->vma;
216 1.1 skrll
217 1.1 skrll
218 1.1 skrll /* If this relocation is relative to a symbol then set the
219 1.1 skrll r_index to the symbols index, and the r_extern bit.
220 1.1 skrll
221 1.1 skrll Absolute symbols can come in in two ways, either as an offset
222 1.1 skrll from the abs section, or as a symbol which has an abs value.
223 1.1 skrll check for that here
224 1.1 skrll */
225 1.1 skrll
226 1.1 skrll if (bfd_is_com_section (output_section)
227 1.1 skrll || bfd_is_abs_section (output_section)
228 1.1 skrll || bfd_is_und_section (output_section))
229 1.1 skrll {
230 1.1 skrll if (bfd_abs_section_ptr->symbol == sym)
231 1.1 skrll {
232 1.1 skrll /* Whoops, looked like an abs symbol, but is really an offset
233 1.1 skrll from the abs section */
234 1.1 skrll r_index = 0;
235 1.1 skrll r_extern = 0;
236 1.1 skrll }
237 1.1 skrll else
238 1.1 skrll {
239 1.1 skrll r_extern = 1;
240 1.1 skrll r_index = (*g->sym_ptr_ptr)->KEEPIT;
241 1.1 skrll }
242 1.1 skrll }
243 1.1 skrll else
244 1.1 skrll {
245 1.1 skrll /* Just an ordinary section */
246 1.1 skrll r_extern = 0;
247 1.1 skrll r_index = output_section->target_index;
248 1.1 skrll }
249 1.1 skrll
250 1.1 skrll
251 1.1 skrll /* now the fun stuff */
252 1.1 skrll if (bfd_header_big_endian (abfd))
253 1.1 skrll {
254 1.1 skrll natptr->r_index[0] = r_index >> 16;
255 1.1 skrll natptr->r_index[1] = r_index >> 8;
256 1.1 skrll natptr->r_index[2] = r_index;
257 1.1 skrll natptr->r_type[0] =
258 1.1 skrll (r_extern ? RELOC_EXT_BITS_EXTERN_BIG : 0)
259 1.1 skrll | (r_type << RELOC_EXT_BITS_TYPE_SH_BIG);
260 1.1 skrll }
261 1.1 skrll else
262 1.1 skrll {
263 1.1 skrll natptr->r_index[2] = r_index >> 16;
264 1.1 skrll natptr->r_index[1] = r_index >> 8;
265 1.1 skrll natptr->r_index[0] = r_index;
266 1.1 skrll natptr->r_type[0] =
267 1.1 skrll (r_extern ? RELOC_EXT_BITS_EXTERN_LITTLE : 0)
268 1.1 skrll | (r_type << RELOC_EXT_BITS_TYPE_SH_LITTLE);
269 1.1 skrll }
270 1.1 skrll
271 1.1 skrll PUT_WORD (abfd, r_addend, natptr->r_addend);
272 1.1 skrll }
273 1.1 skrll
274 1.1 skrll /* BFD deals internally with all things based from the section they're
275 1.1 skrll in. so, something in 10 bytes into a text section with a base of
276 1.1 skrll 50 would have a symbol (.text+10) and know .text vma was 50.
277 1.1 skrll
278 1.1 skrll Aout keeps all it's symbols based from zero, so the symbol would
279 1.1 skrll contain 60. This macro subs the base of each section from the value
280 1.1 skrll to give the true offset from the section */
281 1.1 skrll
282 1.1.1.6 christos
283 1.1.1.3 christos #define MOVE_ADDRESS(ad) \
284 1.1.1.3 christos if (r_extern) \
285 1.1 skrll { \
286 1.1 skrll /* undefined symbol */ \
287 1.1 skrll cache_ptr->sym_ptr_ptr = symbols + r_index; \
288 1.1.1.3 christos cache_ptr->addend = ad; \
289 1.1.1.3 christos } \
290 1.1.1.3 christos else \
291 1.1.1.6 christos { \
292 1.1 skrll /* defined, section relative. replace symbol with pointer to \
293 1.1 skrll symbol which points to section */ \
294 1.1 skrll switch (r_index) { \
295 1.1 skrll case N_TEXT: \
296 1.1 skrll case N_TEXT | N_EXT: \
297 1.1 skrll cache_ptr->sym_ptr_ptr = obj_textsec(abfd)->symbol_ptr_ptr; \
298 1.1 skrll cache_ptr->addend = ad - su->textsec->vma; \
299 1.1 skrll break; \
300 1.1 skrll case N_DATA: \
301 1.1 skrll case N_DATA | N_EXT: \
302 1.1 skrll cache_ptr->sym_ptr_ptr = obj_datasec(abfd)->symbol_ptr_ptr; \
303 1.1 skrll cache_ptr->addend = ad - su->datasec->vma; \
304 1.1 skrll break; \
305 1.1 skrll case N_BSS: \
306 1.1 skrll case N_BSS | N_EXT: \
307 1.1 skrll cache_ptr->sym_ptr_ptr = obj_bsssec(abfd)->symbol_ptr_ptr; \
308 1.1 skrll cache_ptr->addend = ad - su->bsssec->vma; \
309 1.1 skrll break; \
310 1.1 skrll default: \
311 1.1 skrll case N_ABS: \
312 1.1 skrll case N_ABS | N_EXT: \
313 1.1 skrll cache_ptr->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr; \
314 1.1 skrll cache_ptr->addend = ad; \
315 1.1 skrll break; \
316 1.1.1.6 christos } \
317 1.1 skrll } \
318 1.1.1.3 christos
319 1.1.1.3 christos static void
320 1.1.1.3 christos NAME(lynx,swap_ext_reloc_in) (bfd *abfd,
321 1.1.1.3 christos struct reloc_ext_external *bytes,
322 1.1.1.3 christos arelent *cache_ptr,
323 1.1.1.3 christos asymbol **symbols,
324 1.1 skrll bfd_size_type symcount ATTRIBUTE_UNUSED)
325 1.1 skrll {
326 1.1 skrll int r_index;
327 1.1 skrll int r_extern;
328 1.1 skrll unsigned int r_type;
329 1.1 skrll struct aoutdata *su = &(abfd->tdata.aout_data->a);
330 1.1 skrll
331 1.1 skrll cache_ptr->address = (GET_SWORD (abfd, bytes->r_address));
332 1.1 skrll
333 1.1 skrll r_index = bytes->r_index[1];
334 1.1 skrll r_extern = (0 != (bytes->r_index[0] & RELOC_EXT_BITS_EXTERN_BIG));
335 1.1 skrll r_type = (bytes->r_index[0] & RELOC_EXT_BITS_TYPE_BIG)
336 1.1 skrll >> RELOC_EXT_BITS_TYPE_SH_BIG;
337 1.1 skrll
338 1.1 skrll cache_ptr->howto = aout_32_ext_howto_table + r_type;
339 1.1 skrll MOVE_ADDRESS (GET_SWORD (abfd, bytes->r_addend));
340 1.1 skrll }
341 1.1.1.3 christos
342 1.1.1.3 christos static void
343 1.1.1.3 christos NAME(lynx,swap_std_reloc_in) (bfd *abfd,
344 1.1.1.3 christos struct reloc_std_external *bytes,
345 1.1.1.3 christos arelent *cache_ptr,
346 1.1.1.3 christos asymbol **symbols,
347 1.1 skrll bfd_size_type symcount ATTRIBUTE_UNUSED)
348 1.1 skrll {
349 1.1 skrll int r_index;
350 1.1 skrll int r_extern;
351 1.1 skrll unsigned int r_length;
352 1.1 skrll int r_pcrel;
353 1.1 skrll struct aoutdata *su = &(abfd->tdata.aout_data->a);
354 1.1 skrll
355 1.1 skrll cache_ptr->address = H_GET_32 (abfd, bytes->r_address);
356 1.1 skrll
357 1.1 skrll r_index = bytes->r_index[1];
358 1.1 skrll r_extern = (0 != (bytes->r_index[0] & RELOC_STD_BITS_EXTERN_BIG));
359 1.1 skrll r_pcrel = (0 != (bytes->r_index[0] & RELOC_STD_BITS_PCREL_BIG));
360 1.1 skrll r_length = (bytes->r_index[0] & RELOC_STD_BITS_LENGTH_BIG)
361 1.1 skrll >> RELOC_STD_BITS_LENGTH_SH_BIG;
362 1.1 skrll
363 1.1 skrll cache_ptr->howto = aout_32_std_howto_table + r_length + 4 * r_pcrel;
364 1.1 skrll /* FIXME-soon: Roll baserel, jmptable, relative bits into howto setting */
365 1.1 skrll
366 1.1 skrll MOVE_ADDRESS (0);
367 1.1 skrll }
368 1.1 skrll
369 1.1 skrll /* Reloc hackery */
370 1.1.1.3 christos
371 1.1.1.3 christos static bfd_boolean
372 1.1.1.3 christos NAME(lynx,slurp_reloc_table) (bfd *abfd,
373 1.1.1.3 christos sec_ptr asect,
374 1.1 skrll asymbol **symbols)
375 1.1 skrll {
376 1.1 skrll bfd_size_type count;
377 1.1.1.3 christos bfd_size_type reloc_size;
378 1.1 skrll void * relocs;
379 1.1 skrll arelent *reloc_cache;
380 1.1 skrll size_t each_size;
381 1.1 skrll
382 1.1 skrll if (asect->relocation)
383 1.1 skrll return TRUE;
384 1.1 skrll
385 1.1 skrll if (asect->flags & SEC_CONSTRUCTOR)
386 1.1 skrll return TRUE;
387 1.1 skrll
388 1.1 skrll if (asect == obj_datasec (abfd))
389 1.1 skrll {
390 1.1 skrll reloc_size = exec_hdr (abfd)->a_drsize;
391 1.1 skrll goto doit;
392 1.1 skrll }
393 1.1 skrll
394 1.1 skrll if (asect == obj_textsec (abfd))
395 1.1 skrll {
396 1.1 skrll reloc_size = exec_hdr (abfd)->a_trsize;
397 1.1 skrll goto doit;
398 1.1 skrll }
399 1.1 skrll
400 1.1 skrll bfd_set_error (bfd_error_invalid_operation);
401 1.1 skrll return FALSE;
402 1.1 skrll
403 1.1 skrll doit:
404 1.1 skrll if (bfd_seek (abfd, asect->rel_filepos, SEEK_SET) != 0)
405 1.1 skrll return FALSE;
406 1.1 skrll each_size = obj_reloc_entry_size (abfd);
407 1.1 skrll
408 1.1 skrll count = reloc_size / each_size;
409 1.1 skrll
410 1.1 skrll
411 1.1 skrll reloc_cache = (arelent *) bfd_zmalloc (count * sizeof (arelent));
412 1.1 skrll if (!reloc_cache && count != 0)
413 1.1 skrll return FALSE;
414 1.1.1.3 christos
415 1.1 skrll relocs = bfd_alloc (abfd, reloc_size);
416 1.1 skrll if (!relocs && reloc_size != 0)
417 1.1 skrll {
418 1.1 skrll free (reloc_cache);
419 1.1 skrll return FALSE;
420 1.1 skrll }
421 1.1 skrll
422 1.1 skrll if (bfd_bread (relocs, reloc_size, abfd) != reloc_size)
423 1.1 skrll {
424 1.1 skrll bfd_release (abfd, relocs);
425 1.1 skrll free (reloc_cache);
426 1.1 skrll return FALSE;
427 1.1 skrll }
428 1.1 skrll
429 1.1 skrll if (each_size == RELOC_EXT_SIZE)
430 1.1.1.3 christos {
431 1.1 skrll struct reloc_ext_external *rptr = (struct reloc_ext_external *) relocs;
432 1.1 skrll unsigned int counter = 0;
433 1.1 skrll arelent *cache_ptr = reloc_cache;
434 1.1 skrll
435 1.1 skrll for (; counter < count; counter++, rptr++, cache_ptr++)
436 1.1 skrll {
437 1.1 skrll NAME(lynx,swap_ext_reloc_in) (abfd, rptr, cache_ptr, symbols,
438 1.1 skrll (bfd_size_type) bfd_get_symcount (abfd));
439 1.1 skrll }
440 1.1 skrll }
441 1.1 skrll else
442 1.1.1.3 christos {
443 1.1 skrll struct reloc_std_external *rptr = (struct reloc_std_external *) relocs;
444 1.1 skrll unsigned int counter = 0;
445 1.1 skrll arelent *cache_ptr = reloc_cache;
446 1.1 skrll
447 1.1 skrll for (; counter < count; counter++, rptr++, cache_ptr++)
448 1.1 skrll {
449 1.1 skrll NAME(lynx,swap_std_reloc_in) (abfd, rptr, cache_ptr, symbols,
450 1.1 skrll (bfd_size_type) bfd_get_symcount (abfd));
451 1.1 skrll }
452 1.1 skrll
453 1.1 skrll }
454 1.1 skrll
455 1.1 skrll bfd_release (abfd, relocs);
456 1.1 skrll asect->relocation = reloc_cache;
457 1.1 skrll asect->reloc_count = count;
458 1.1 skrll return TRUE;
459 1.1 skrll }
460 1.1 skrll
461 1.1 skrll
462 1.1 skrll
463 1.1 skrll /* Write out a relocation section into an object file. */
464 1.1.1.3 christos
465 1.1.1.3 christos static bfd_boolean
466 1.1 skrll NAME(lynx,squirt_out_relocs) (bfd *abfd, asection *section)
467 1.1 skrll {
468 1.1 skrll arelent **generic;
469 1.1 skrll unsigned char *native, *natptr;
470 1.1 skrll size_t each_size;
471 1.1 skrll unsigned int count = section->reloc_count;
472 1.1 skrll bfd_size_type natsize;
473 1.1 skrll
474 1.1 skrll if (count == 0)
475 1.1 skrll return TRUE;
476 1.1 skrll
477 1.1 skrll each_size = obj_reloc_entry_size (abfd);
478 1.1 skrll natsize = count;
479 1.1 skrll natsize *= each_size;
480 1.1 skrll native = (unsigned char *) bfd_zalloc (abfd, natsize);
481 1.1 skrll if (!native)
482 1.1 skrll return FALSE;
483 1.1 skrll
484 1.1 skrll generic = section->orelocation;
485 1.1 skrll
486 1.1 skrll if (each_size == RELOC_EXT_SIZE)
487 1.1 skrll {
488 1.1 skrll for (natptr = native;
489 1.1 skrll count != 0;
490 1.1 skrll --count, natptr += each_size, ++generic)
491 1.1 skrll NAME(lynx,swap_ext_reloc_out) (abfd, *generic, (struct reloc_ext_external *) natptr);
492 1.1 skrll }
493 1.1 skrll else
494 1.1 skrll {
495 1.1 skrll for (natptr = native;
496 1.1 skrll count != 0;
497 1.1 skrll --count, natptr += each_size, ++generic)
498 1.1 skrll NAME(lynx,swap_std_reloc_out) (abfd, *generic, (struct reloc_std_external *) natptr);
499 1.1 skrll }
500 1.1.1.3 christos
501 1.1 skrll if (bfd_bwrite (native, natsize, abfd) != natsize)
502 1.1 skrll {
503 1.1 skrll bfd_release (abfd, native);
504 1.1 skrll return FALSE;
505 1.1 skrll }
506 1.1 skrll bfd_release (abfd, native);
507 1.1 skrll
508 1.1 skrll return TRUE;
509 1.1 skrll }
510 1.1 skrll
511 1.1.1.3 christos /* This is stupid. This function should be a boolean predicate */
512 1.1.1.3 christos static long
513 1.1.1.3 christos NAME(lynx,canonicalize_reloc) (bfd *abfd,
514 1.1.1.3 christos sec_ptr section,
515 1.1.1.3 christos arelent **relptr,
516 1.1 skrll asymbol **symbols)
517 1.1 skrll {
518 1.1 skrll arelent *tblptr = section->relocation;
519 1.1 skrll unsigned int count;
520 1.1 skrll
521 1.1 skrll if (!(tblptr || NAME(lynx,slurp_reloc_table) (abfd, section, symbols)))
522 1.1 skrll return -1;
523 1.1 skrll
524 1.1 skrll if (section->flags & SEC_CONSTRUCTOR)
525 1.1 skrll {
526 1.1 skrll arelent_chain *chain = section->constructor_chain;
527 1.1 skrll for (count = 0; count < section->reloc_count; count++)
528 1.1 skrll {
529 1.1 skrll *relptr++ = &chain->relent;
530 1.1 skrll chain = chain->next;
531 1.1 skrll }
532 1.1 skrll }
533 1.1 skrll else
534 1.1 skrll {
535 1.1 skrll tblptr = section->relocation;
536 1.1 skrll
537 1.1 skrll for (count = 0; count++ < section->reloc_count;)
538 1.1 skrll {
539 1.1 skrll *relptr++ = tblptr++;
540 1.1 skrll }
541 1.1 skrll }
542 1.1 skrll *relptr = 0;
543 1.1 skrll
544 1.1 skrll return section->reloc_count;
545 1.1 skrll }
546 1.1 skrll
547 1.1 skrll #define MY_canonicalize_reloc NAME(lynx,canonicalize_reloc)
548 1.1 skrll
549 #include "aout-target.h"
550