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