1*3d8817e4Smiod /* Assorted BFD support routines, only used internally.
2*3d8817e4Smiod Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3*3d8817e4Smiod 2000, 2001, 2002, 2003, 2004, 2005
4*3d8817e4Smiod Free Software Foundation, Inc.
5*3d8817e4Smiod Written by Cygnus Support.
6*3d8817e4Smiod
7*3d8817e4Smiod This file is part of BFD, the Binary File Descriptor library.
8*3d8817e4Smiod
9*3d8817e4Smiod This program is free software; you can redistribute it and/or modify
10*3d8817e4Smiod it under the terms of the GNU General Public License as published by
11*3d8817e4Smiod the Free Software Foundation; either version 2 of the License, or
12*3d8817e4Smiod (at your option) any later version.
13*3d8817e4Smiod
14*3d8817e4Smiod This program is distributed in the hope that it will be useful,
15*3d8817e4Smiod but WITHOUT ANY WARRANTY; without even the implied warranty of
16*3d8817e4Smiod MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17*3d8817e4Smiod GNU General Public License for more details.
18*3d8817e4Smiod
19*3d8817e4Smiod You should have received a copy of the GNU General Public License
20*3d8817e4Smiod along with this program; if not, write to the Free Software
21*3d8817e4Smiod Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */
22*3d8817e4Smiod
23*3d8817e4Smiod #include "bfd.h"
24*3d8817e4Smiod #include "sysdep.h"
25*3d8817e4Smiod #include "libbfd.h"
26*3d8817e4Smiod
27*3d8817e4Smiod #ifndef HAVE_GETPAGESIZE
28*3d8817e4Smiod #define getpagesize() 2048
29*3d8817e4Smiod #endif
30*3d8817e4Smiod
31*3d8817e4Smiod /*
32*3d8817e4Smiod SECTION
33*3d8817e4Smiod Implementation details
34*3d8817e4Smiod
35*3d8817e4Smiod SUBSECTION
36*3d8817e4Smiod Internal functions
37*3d8817e4Smiod
38*3d8817e4Smiod DESCRIPTION
39*3d8817e4Smiod These routines are used within BFD.
40*3d8817e4Smiod They are not intended for export, but are documented here for
41*3d8817e4Smiod completeness.
42*3d8817e4Smiod */
43*3d8817e4Smiod
44*3d8817e4Smiod /* A routine which is used in target vectors for unsupported
45*3d8817e4Smiod operations. */
46*3d8817e4Smiod
47*3d8817e4Smiod bfd_boolean
bfd_false(bfd * ignore ATTRIBUTE_UNUSED)48*3d8817e4Smiod bfd_false (bfd *ignore ATTRIBUTE_UNUSED)
49*3d8817e4Smiod {
50*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
51*3d8817e4Smiod return FALSE;
52*3d8817e4Smiod }
53*3d8817e4Smiod
54*3d8817e4Smiod /* A routine which is used in target vectors for supported operations
55*3d8817e4Smiod which do not actually do anything. */
56*3d8817e4Smiod
57*3d8817e4Smiod bfd_boolean
bfd_true(bfd * ignore ATTRIBUTE_UNUSED)58*3d8817e4Smiod bfd_true (bfd *ignore ATTRIBUTE_UNUSED)
59*3d8817e4Smiod {
60*3d8817e4Smiod return TRUE;
61*3d8817e4Smiod }
62*3d8817e4Smiod
63*3d8817e4Smiod /* A routine which is used in target vectors for unsupported
64*3d8817e4Smiod operations which return a pointer value. */
65*3d8817e4Smiod
66*3d8817e4Smiod void *
bfd_nullvoidptr(bfd * ignore ATTRIBUTE_UNUSED)67*3d8817e4Smiod bfd_nullvoidptr (bfd *ignore ATTRIBUTE_UNUSED)
68*3d8817e4Smiod {
69*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
70*3d8817e4Smiod return NULL;
71*3d8817e4Smiod }
72*3d8817e4Smiod
73*3d8817e4Smiod int
bfd_0(bfd * ignore ATTRIBUTE_UNUSED)74*3d8817e4Smiod bfd_0 (bfd *ignore ATTRIBUTE_UNUSED)
75*3d8817e4Smiod {
76*3d8817e4Smiod return 0;
77*3d8817e4Smiod }
78*3d8817e4Smiod
79*3d8817e4Smiod unsigned int
bfd_0u(bfd * ignore ATTRIBUTE_UNUSED)80*3d8817e4Smiod bfd_0u (bfd *ignore ATTRIBUTE_UNUSED)
81*3d8817e4Smiod {
82*3d8817e4Smiod return 0;
83*3d8817e4Smiod }
84*3d8817e4Smiod
85*3d8817e4Smiod long
bfd_0l(bfd * ignore ATTRIBUTE_UNUSED)86*3d8817e4Smiod bfd_0l (bfd *ignore ATTRIBUTE_UNUSED)
87*3d8817e4Smiod {
88*3d8817e4Smiod return 0;
89*3d8817e4Smiod }
90*3d8817e4Smiod
91*3d8817e4Smiod /* A routine which is used in target vectors for unsupported
92*3d8817e4Smiod operations which return -1 on error. */
93*3d8817e4Smiod
94*3d8817e4Smiod long
_bfd_n1(bfd * ignore_abfd ATTRIBUTE_UNUSED)95*3d8817e4Smiod _bfd_n1 (bfd *ignore_abfd ATTRIBUTE_UNUSED)
96*3d8817e4Smiod {
97*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
98*3d8817e4Smiod return -1;
99*3d8817e4Smiod }
100*3d8817e4Smiod
101*3d8817e4Smiod void
bfd_void(bfd * ignore ATTRIBUTE_UNUSED)102*3d8817e4Smiod bfd_void (bfd *ignore ATTRIBUTE_UNUSED)
103*3d8817e4Smiod {
104*3d8817e4Smiod }
105*3d8817e4Smiod
106*3d8817e4Smiod bfd_boolean
_bfd_nocore_core_file_matches_executable_p(bfd * ignore_core_bfd ATTRIBUTE_UNUSED,bfd * ignore_exec_bfd ATTRIBUTE_UNUSED)107*3d8817e4Smiod _bfd_nocore_core_file_matches_executable_p
108*3d8817e4Smiod (bfd *ignore_core_bfd ATTRIBUTE_UNUSED,
109*3d8817e4Smiod bfd *ignore_exec_bfd ATTRIBUTE_UNUSED)
110*3d8817e4Smiod {
111*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
112*3d8817e4Smiod return FALSE;
113*3d8817e4Smiod }
114*3d8817e4Smiod
115*3d8817e4Smiod /* Routine to handle core_file_failing_command entry point for targets
116*3d8817e4Smiod without core file support. */
117*3d8817e4Smiod
118*3d8817e4Smiod char *
_bfd_nocore_core_file_failing_command(bfd * ignore_abfd ATTRIBUTE_UNUSED)119*3d8817e4Smiod _bfd_nocore_core_file_failing_command (bfd *ignore_abfd ATTRIBUTE_UNUSED)
120*3d8817e4Smiod {
121*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
122*3d8817e4Smiod return NULL;
123*3d8817e4Smiod }
124*3d8817e4Smiod
125*3d8817e4Smiod /* Routine to handle core_file_failing_signal entry point for targets
126*3d8817e4Smiod without core file support. */
127*3d8817e4Smiod
128*3d8817e4Smiod int
_bfd_nocore_core_file_failing_signal(bfd * ignore_abfd ATTRIBUTE_UNUSED)129*3d8817e4Smiod _bfd_nocore_core_file_failing_signal (bfd *ignore_abfd ATTRIBUTE_UNUSED)
130*3d8817e4Smiod {
131*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
132*3d8817e4Smiod return 0;
133*3d8817e4Smiod }
134*3d8817e4Smiod
135*3d8817e4Smiod const bfd_target *
_bfd_dummy_target(bfd * ignore_abfd ATTRIBUTE_UNUSED)136*3d8817e4Smiod _bfd_dummy_target (bfd *ignore_abfd ATTRIBUTE_UNUSED)
137*3d8817e4Smiod {
138*3d8817e4Smiod bfd_set_error (bfd_error_wrong_format);
139*3d8817e4Smiod return 0;
140*3d8817e4Smiod }
141*3d8817e4Smiod
142*3d8817e4Smiod /* Allocate memory using malloc. */
143*3d8817e4Smiod
144*3d8817e4Smiod void *
bfd_malloc(bfd_size_type size)145*3d8817e4Smiod bfd_malloc (bfd_size_type size)
146*3d8817e4Smiod {
147*3d8817e4Smiod void *ptr;
148*3d8817e4Smiod
149*3d8817e4Smiod if (size != (size_t) size)
150*3d8817e4Smiod {
151*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
152*3d8817e4Smiod return NULL;
153*3d8817e4Smiod }
154*3d8817e4Smiod
155*3d8817e4Smiod ptr = malloc ((size_t) size);
156*3d8817e4Smiod if (ptr == NULL && (size_t) size != 0)
157*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
158*3d8817e4Smiod
159*3d8817e4Smiod return ptr;
160*3d8817e4Smiod }
161*3d8817e4Smiod
162*3d8817e4Smiod /* Allocate memory using malloc, nmemb * size with overflow checking. */
163*3d8817e4Smiod
164*3d8817e4Smiod void *
bfd_malloc2(bfd_size_type nmemb,bfd_size_type size)165*3d8817e4Smiod bfd_malloc2 (bfd_size_type nmemb, bfd_size_type size)
166*3d8817e4Smiod {
167*3d8817e4Smiod void *ptr;
168*3d8817e4Smiod
169*3d8817e4Smiod if ((nmemb | size) >= HALF_BFD_SIZE_TYPE
170*3d8817e4Smiod && size != 0
171*3d8817e4Smiod && nmemb > ~(bfd_size_type) 0 / size)
172*3d8817e4Smiod {
173*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
174*3d8817e4Smiod return NULL;
175*3d8817e4Smiod }
176*3d8817e4Smiod
177*3d8817e4Smiod size *= nmemb;
178*3d8817e4Smiod
179*3d8817e4Smiod if (size != (size_t) size)
180*3d8817e4Smiod {
181*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
182*3d8817e4Smiod return NULL;
183*3d8817e4Smiod }
184*3d8817e4Smiod
185*3d8817e4Smiod ptr = malloc ((size_t) size);
186*3d8817e4Smiod if (ptr == NULL && (size_t) size != 0)
187*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
188*3d8817e4Smiod
189*3d8817e4Smiod return ptr;
190*3d8817e4Smiod }
191*3d8817e4Smiod
192*3d8817e4Smiod /* Reallocate memory using realloc. */
193*3d8817e4Smiod
194*3d8817e4Smiod void *
bfd_realloc(void * ptr,bfd_size_type size)195*3d8817e4Smiod bfd_realloc (void *ptr, bfd_size_type size)
196*3d8817e4Smiod {
197*3d8817e4Smiod void *ret;
198*3d8817e4Smiod
199*3d8817e4Smiod if (size != (size_t) size)
200*3d8817e4Smiod {
201*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
202*3d8817e4Smiod return NULL;
203*3d8817e4Smiod }
204*3d8817e4Smiod
205*3d8817e4Smiod if (ptr == NULL)
206*3d8817e4Smiod ret = malloc ((size_t) size);
207*3d8817e4Smiod else
208*3d8817e4Smiod ret = realloc (ptr, (size_t) size);
209*3d8817e4Smiod
210*3d8817e4Smiod if (ret == NULL && (size_t) size != 0)
211*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
212*3d8817e4Smiod
213*3d8817e4Smiod return ret;
214*3d8817e4Smiod }
215*3d8817e4Smiod
216*3d8817e4Smiod /* Reallocate memory using realloc, nmemb * size with overflow checking. */
217*3d8817e4Smiod
218*3d8817e4Smiod void *
bfd_realloc2(void * ptr,bfd_size_type nmemb,bfd_size_type size)219*3d8817e4Smiod bfd_realloc2 (void *ptr, bfd_size_type nmemb, bfd_size_type size)
220*3d8817e4Smiod {
221*3d8817e4Smiod void *ret;
222*3d8817e4Smiod
223*3d8817e4Smiod if ((nmemb | size) >= HALF_BFD_SIZE_TYPE
224*3d8817e4Smiod && size != 0
225*3d8817e4Smiod && nmemb > ~(bfd_size_type) 0 / size)
226*3d8817e4Smiod {
227*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
228*3d8817e4Smiod return NULL;
229*3d8817e4Smiod }
230*3d8817e4Smiod
231*3d8817e4Smiod size *= nmemb;
232*3d8817e4Smiod
233*3d8817e4Smiod if (size != (size_t) size)
234*3d8817e4Smiod {
235*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
236*3d8817e4Smiod return NULL;
237*3d8817e4Smiod }
238*3d8817e4Smiod
239*3d8817e4Smiod if (ptr == NULL)
240*3d8817e4Smiod ret = malloc ((size_t) size);
241*3d8817e4Smiod else
242*3d8817e4Smiod ret = realloc (ptr, (size_t) size);
243*3d8817e4Smiod
244*3d8817e4Smiod if (ret == NULL && (size_t) size != 0)
245*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
246*3d8817e4Smiod
247*3d8817e4Smiod return ret;
248*3d8817e4Smiod }
249*3d8817e4Smiod
250*3d8817e4Smiod /* Allocate memory using malloc and clear it. */
251*3d8817e4Smiod
252*3d8817e4Smiod void *
bfd_zmalloc(bfd_size_type size)253*3d8817e4Smiod bfd_zmalloc (bfd_size_type size)
254*3d8817e4Smiod {
255*3d8817e4Smiod void *ptr;
256*3d8817e4Smiod
257*3d8817e4Smiod if (size != (size_t) size)
258*3d8817e4Smiod {
259*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
260*3d8817e4Smiod return NULL;
261*3d8817e4Smiod }
262*3d8817e4Smiod
263*3d8817e4Smiod ptr = malloc ((size_t) size);
264*3d8817e4Smiod
265*3d8817e4Smiod if ((size_t) size != 0)
266*3d8817e4Smiod {
267*3d8817e4Smiod if (ptr == NULL)
268*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
269*3d8817e4Smiod else
270*3d8817e4Smiod memset (ptr, 0, (size_t) size);
271*3d8817e4Smiod }
272*3d8817e4Smiod
273*3d8817e4Smiod return ptr;
274*3d8817e4Smiod }
275*3d8817e4Smiod
276*3d8817e4Smiod /* Allocate memory using malloc (nmemb * size) with overflow checking
277*3d8817e4Smiod and clear it. */
278*3d8817e4Smiod
279*3d8817e4Smiod void *
bfd_zmalloc2(bfd_size_type nmemb,bfd_size_type size)280*3d8817e4Smiod bfd_zmalloc2 (bfd_size_type nmemb, bfd_size_type size)
281*3d8817e4Smiod {
282*3d8817e4Smiod void *ptr;
283*3d8817e4Smiod
284*3d8817e4Smiod if ((nmemb | size) >= HALF_BFD_SIZE_TYPE
285*3d8817e4Smiod && size != 0
286*3d8817e4Smiod && nmemb > ~(bfd_size_type) 0 / size)
287*3d8817e4Smiod {
288*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
289*3d8817e4Smiod return NULL;
290*3d8817e4Smiod }
291*3d8817e4Smiod
292*3d8817e4Smiod size *= nmemb;
293*3d8817e4Smiod
294*3d8817e4Smiod if (size != (size_t) size)
295*3d8817e4Smiod {
296*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
297*3d8817e4Smiod return NULL;
298*3d8817e4Smiod }
299*3d8817e4Smiod
300*3d8817e4Smiod ptr = malloc ((size_t) size);
301*3d8817e4Smiod
302*3d8817e4Smiod if ((size_t) size != 0)
303*3d8817e4Smiod {
304*3d8817e4Smiod if (ptr == NULL)
305*3d8817e4Smiod bfd_set_error (bfd_error_no_memory);
306*3d8817e4Smiod else
307*3d8817e4Smiod memset (ptr, 0, (size_t) size);
308*3d8817e4Smiod }
309*3d8817e4Smiod
310*3d8817e4Smiod return ptr;
311*3d8817e4Smiod }
312*3d8817e4Smiod
313*3d8817e4Smiod /*
314*3d8817e4Smiod INTERNAL_FUNCTION
315*3d8817e4Smiod bfd_write_bigendian_4byte_int
316*3d8817e4Smiod
317*3d8817e4Smiod SYNOPSIS
318*3d8817e4Smiod bfd_boolean bfd_write_bigendian_4byte_int (bfd *, unsigned int);
319*3d8817e4Smiod
320*3d8817e4Smiod DESCRIPTION
321*3d8817e4Smiod Write a 4 byte integer @var{i} to the output BFD @var{abfd}, in big
322*3d8817e4Smiod endian order regardless of what else is going on. This is useful in
323*3d8817e4Smiod archives.
324*3d8817e4Smiod
325*3d8817e4Smiod */
326*3d8817e4Smiod bfd_boolean
bfd_write_bigendian_4byte_int(bfd * abfd,unsigned int i)327*3d8817e4Smiod bfd_write_bigendian_4byte_int (bfd *abfd, unsigned int i)
328*3d8817e4Smiod {
329*3d8817e4Smiod bfd_byte buffer[4];
330*3d8817e4Smiod bfd_putb32 ((bfd_vma) i, buffer);
331*3d8817e4Smiod return bfd_bwrite (buffer, (bfd_size_type) 4, abfd) == 4;
332*3d8817e4Smiod }
333*3d8817e4Smiod
334*3d8817e4Smiod
335*3d8817e4Smiod /** The do-it-yourself (byte) sex-change kit */
336*3d8817e4Smiod
337*3d8817e4Smiod /* The middle letter e.g. get<b>short indicates Big or Little endian
338*3d8817e4Smiod target machine. It doesn't matter what the byte order of the host
339*3d8817e4Smiod machine is; these routines work for either. */
340*3d8817e4Smiod
341*3d8817e4Smiod /* FIXME: Should these take a count argument?
342*3d8817e4Smiod Answer (gnu@cygnus.com): No, but perhaps they should be inline
343*3d8817e4Smiod functions in swap.h #ifdef __GNUC__.
344*3d8817e4Smiod Gprof them later and find out. */
345*3d8817e4Smiod
346*3d8817e4Smiod /*
347*3d8817e4Smiod FUNCTION
348*3d8817e4Smiod bfd_put_size
349*3d8817e4Smiod FUNCTION
350*3d8817e4Smiod bfd_get_size
351*3d8817e4Smiod
352*3d8817e4Smiod DESCRIPTION
353*3d8817e4Smiod These macros as used for reading and writing raw data in
354*3d8817e4Smiod sections; each access (except for bytes) is vectored through
355*3d8817e4Smiod the target format of the BFD and mangled accordingly. The
356*3d8817e4Smiod mangling performs any necessary endian translations and
357*3d8817e4Smiod removes alignment restrictions. Note that types accepted and
358*3d8817e4Smiod returned by these macros are identical so they can be swapped
359*3d8817e4Smiod around in macros---for example, @file{libaout.h} defines <<GET_WORD>>
360*3d8817e4Smiod to either <<bfd_get_32>> or <<bfd_get_64>>.
361*3d8817e4Smiod
362*3d8817e4Smiod In the put routines, @var{val} must be a <<bfd_vma>>. If we are on a
363*3d8817e4Smiod system without prototypes, the caller is responsible for making
364*3d8817e4Smiod sure that is true, with a cast if necessary. We don't cast
365*3d8817e4Smiod them in the macro definitions because that would prevent <<lint>>
366*3d8817e4Smiod or <<gcc -Wall>> from detecting sins such as passing a pointer.
367*3d8817e4Smiod To detect calling these with less than a <<bfd_vma>>, use
368*3d8817e4Smiod <<gcc -Wconversion>> on a host with 64 bit <<bfd_vma>>'s.
369*3d8817e4Smiod
370*3d8817e4Smiod .
371*3d8817e4Smiod .{* Byte swapping macros for user section data. *}
372*3d8817e4Smiod .
373*3d8817e4Smiod .#define bfd_put_8(abfd, val, ptr) \
374*3d8817e4Smiod . ((void) (*((unsigned char *) (ptr)) = (val) & 0xff))
375*3d8817e4Smiod .#define bfd_put_signed_8 \
376*3d8817e4Smiod . bfd_put_8
377*3d8817e4Smiod .#define bfd_get_8(abfd, ptr) \
378*3d8817e4Smiod . (*(unsigned char *) (ptr) & 0xff)
379*3d8817e4Smiod .#define bfd_get_signed_8(abfd, ptr) \
380*3d8817e4Smiod . (((*(unsigned char *) (ptr) & 0xff) ^ 0x80) - 0x80)
381*3d8817e4Smiod .
382*3d8817e4Smiod .#define bfd_put_16(abfd, val, ptr) \
383*3d8817e4Smiod . BFD_SEND (abfd, bfd_putx16, ((val),(ptr)))
384*3d8817e4Smiod .#define bfd_put_signed_16 \
385*3d8817e4Smiod . bfd_put_16
386*3d8817e4Smiod .#define bfd_get_16(abfd, ptr) \
387*3d8817e4Smiod . BFD_SEND (abfd, bfd_getx16, (ptr))
388*3d8817e4Smiod .#define bfd_get_signed_16(abfd, ptr) \
389*3d8817e4Smiod . BFD_SEND (abfd, bfd_getx_signed_16, (ptr))
390*3d8817e4Smiod .
391*3d8817e4Smiod .#define bfd_put_32(abfd, val, ptr) \
392*3d8817e4Smiod . BFD_SEND (abfd, bfd_putx32, ((val),(ptr)))
393*3d8817e4Smiod .#define bfd_put_signed_32 \
394*3d8817e4Smiod . bfd_put_32
395*3d8817e4Smiod .#define bfd_get_32(abfd, ptr) \
396*3d8817e4Smiod . BFD_SEND (abfd, bfd_getx32, (ptr))
397*3d8817e4Smiod .#define bfd_get_signed_32(abfd, ptr) \
398*3d8817e4Smiod . BFD_SEND (abfd, bfd_getx_signed_32, (ptr))
399*3d8817e4Smiod .
400*3d8817e4Smiod .#define bfd_put_64(abfd, val, ptr) \
401*3d8817e4Smiod . BFD_SEND (abfd, bfd_putx64, ((val), (ptr)))
402*3d8817e4Smiod .#define bfd_put_signed_64 \
403*3d8817e4Smiod . bfd_put_64
404*3d8817e4Smiod .#define bfd_get_64(abfd, ptr) \
405*3d8817e4Smiod . BFD_SEND (abfd, bfd_getx64, (ptr))
406*3d8817e4Smiod .#define bfd_get_signed_64(abfd, ptr) \
407*3d8817e4Smiod . BFD_SEND (abfd, bfd_getx_signed_64, (ptr))
408*3d8817e4Smiod .
409*3d8817e4Smiod .#define bfd_get(bits, abfd, ptr) \
410*3d8817e4Smiod . ((bits) == 8 ? (bfd_vma) bfd_get_8 (abfd, ptr) \
411*3d8817e4Smiod . : (bits) == 16 ? bfd_get_16 (abfd, ptr) \
412*3d8817e4Smiod . : (bits) == 32 ? bfd_get_32 (abfd, ptr) \
413*3d8817e4Smiod . : (bits) == 64 ? bfd_get_64 (abfd, ptr) \
414*3d8817e4Smiod . : (abort (), (bfd_vma) - 1))
415*3d8817e4Smiod .
416*3d8817e4Smiod .#define bfd_put(bits, abfd, val, ptr) \
417*3d8817e4Smiod . ((bits) == 8 ? bfd_put_8 (abfd, val, ptr) \
418*3d8817e4Smiod . : (bits) == 16 ? bfd_put_16 (abfd, val, ptr) \
419*3d8817e4Smiod . : (bits) == 32 ? bfd_put_32 (abfd, val, ptr) \
420*3d8817e4Smiod . : (bits) == 64 ? bfd_put_64 (abfd, val, ptr) \
421*3d8817e4Smiod . : (abort (), (void) 0))
422*3d8817e4Smiod .
423*3d8817e4Smiod */
424*3d8817e4Smiod
425*3d8817e4Smiod /*
426*3d8817e4Smiod FUNCTION
427*3d8817e4Smiod bfd_h_put_size
428*3d8817e4Smiod bfd_h_get_size
429*3d8817e4Smiod
430*3d8817e4Smiod DESCRIPTION
431*3d8817e4Smiod These macros have the same function as their <<bfd_get_x>>
432*3d8817e4Smiod brethren, except that they are used for removing information
433*3d8817e4Smiod for the header records of object files. Believe it or not,
434*3d8817e4Smiod some object files keep their header records in big endian
435*3d8817e4Smiod order and their data in little endian order.
436*3d8817e4Smiod .
437*3d8817e4Smiod .{* Byte swapping macros for file header data. *}
438*3d8817e4Smiod .
439*3d8817e4Smiod .#define bfd_h_put_8(abfd, val, ptr) \
440*3d8817e4Smiod . bfd_put_8 (abfd, val, ptr)
441*3d8817e4Smiod .#define bfd_h_put_signed_8(abfd, val, ptr) \
442*3d8817e4Smiod . bfd_put_8 (abfd, val, ptr)
443*3d8817e4Smiod .#define bfd_h_get_8(abfd, ptr) \
444*3d8817e4Smiod . bfd_get_8 (abfd, ptr)
445*3d8817e4Smiod .#define bfd_h_get_signed_8(abfd, ptr) \
446*3d8817e4Smiod . bfd_get_signed_8 (abfd, ptr)
447*3d8817e4Smiod .
448*3d8817e4Smiod .#define bfd_h_put_16(abfd, val, ptr) \
449*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_putx16, (val, ptr))
450*3d8817e4Smiod .#define bfd_h_put_signed_16 \
451*3d8817e4Smiod . bfd_h_put_16
452*3d8817e4Smiod .#define bfd_h_get_16(abfd, ptr) \
453*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_getx16, (ptr))
454*3d8817e4Smiod .#define bfd_h_get_signed_16(abfd, ptr) \
455*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_getx_signed_16, (ptr))
456*3d8817e4Smiod .
457*3d8817e4Smiod .#define bfd_h_put_32(abfd, val, ptr) \
458*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_putx32, (val, ptr))
459*3d8817e4Smiod .#define bfd_h_put_signed_32 \
460*3d8817e4Smiod . bfd_h_put_32
461*3d8817e4Smiod .#define bfd_h_get_32(abfd, ptr) \
462*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_getx32, (ptr))
463*3d8817e4Smiod .#define bfd_h_get_signed_32(abfd, ptr) \
464*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_getx_signed_32, (ptr))
465*3d8817e4Smiod .
466*3d8817e4Smiod .#define bfd_h_put_64(abfd, val, ptr) \
467*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_putx64, (val, ptr))
468*3d8817e4Smiod .#define bfd_h_put_signed_64 \
469*3d8817e4Smiod . bfd_h_put_64
470*3d8817e4Smiod .#define bfd_h_get_64(abfd, ptr) \
471*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_getx64, (ptr))
472*3d8817e4Smiod .#define bfd_h_get_signed_64(abfd, ptr) \
473*3d8817e4Smiod . BFD_SEND (abfd, bfd_h_getx_signed_64, (ptr))
474*3d8817e4Smiod .
475*3d8817e4Smiod .{* Aliases for the above, which should eventually go away. *}
476*3d8817e4Smiod .
477*3d8817e4Smiod .#define H_PUT_64 bfd_h_put_64
478*3d8817e4Smiod .#define H_PUT_32 bfd_h_put_32
479*3d8817e4Smiod .#define H_PUT_16 bfd_h_put_16
480*3d8817e4Smiod .#define H_PUT_8 bfd_h_put_8
481*3d8817e4Smiod .#define H_PUT_S64 bfd_h_put_signed_64
482*3d8817e4Smiod .#define H_PUT_S32 bfd_h_put_signed_32
483*3d8817e4Smiod .#define H_PUT_S16 bfd_h_put_signed_16
484*3d8817e4Smiod .#define H_PUT_S8 bfd_h_put_signed_8
485*3d8817e4Smiod .#define H_GET_64 bfd_h_get_64
486*3d8817e4Smiod .#define H_GET_32 bfd_h_get_32
487*3d8817e4Smiod .#define H_GET_16 bfd_h_get_16
488*3d8817e4Smiod .#define H_GET_8 bfd_h_get_8
489*3d8817e4Smiod .#define H_GET_S64 bfd_h_get_signed_64
490*3d8817e4Smiod .#define H_GET_S32 bfd_h_get_signed_32
491*3d8817e4Smiod .#define H_GET_S16 bfd_h_get_signed_16
492*3d8817e4Smiod .#define H_GET_S8 bfd_h_get_signed_8
493*3d8817e4Smiod .
494*3d8817e4Smiod .*/
495*3d8817e4Smiod
496*3d8817e4Smiod /* Sign extension to bfd_signed_vma. */
497*3d8817e4Smiod #define COERCE16(x) (((bfd_signed_vma) (x) ^ 0x8000) - 0x8000)
498*3d8817e4Smiod #define COERCE32(x) (((bfd_signed_vma) (x) ^ 0x80000000) - 0x80000000)
499*3d8817e4Smiod #define EIGHT_GAZILLION ((bfd_int64_t) 1 << 63)
500*3d8817e4Smiod #define COERCE64(x) \
501*3d8817e4Smiod (((bfd_int64_t) (x) ^ EIGHT_GAZILLION) - EIGHT_GAZILLION)
502*3d8817e4Smiod
503*3d8817e4Smiod bfd_vma
bfd_getb16(const void * p)504*3d8817e4Smiod bfd_getb16 (const void *p)
505*3d8817e4Smiod {
506*3d8817e4Smiod const bfd_byte *addr = p;
507*3d8817e4Smiod return (addr[0] << 8) | addr[1];
508*3d8817e4Smiod }
509*3d8817e4Smiod
510*3d8817e4Smiod bfd_vma
bfd_getl16(const void * p)511*3d8817e4Smiod bfd_getl16 (const void *p)
512*3d8817e4Smiod {
513*3d8817e4Smiod const bfd_byte *addr = p;
514*3d8817e4Smiod return (addr[1] << 8) | addr[0];
515*3d8817e4Smiod }
516*3d8817e4Smiod
517*3d8817e4Smiod bfd_signed_vma
bfd_getb_signed_16(const void * p)518*3d8817e4Smiod bfd_getb_signed_16 (const void *p)
519*3d8817e4Smiod {
520*3d8817e4Smiod const bfd_byte *addr = p;
521*3d8817e4Smiod return COERCE16 ((addr[0] << 8) | addr[1]);
522*3d8817e4Smiod }
523*3d8817e4Smiod
524*3d8817e4Smiod bfd_signed_vma
bfd_getl_signed_16(const void * p)525*3d8817e4Smiod bfd_getl_signed_16 (const void *p)
526*3d8817e4Smiod {
527*3d8817e4Smiod const bfd_byte *addr = p;
528*3d8817e4Smiod return COERCE16 ((addr[1] << 8) | addr[0]);
529*3d8817e4Smiod }
530*3d8817e4Smiod
531*3d8817e4Smiod void
bfd_putb16(bfd_vma data,void * p)532*3d8817e4Smiod bfd_putb16 (bfd_vma data, void *p)
533*3d8817e4Smiod {
534*3d8817e4Smiod bfd_byte *addr = p;
535*3d8817e4Smiod addr[0] = (data >> 8) & 0xff;
536*3d8817e4Smiod addr[1] = data & 0xff;
537*3d8817e4Smiod }
538*3d8817e4Smiod
539*3d8817e4Smiod void
bfd_putl16(bfd_vma data,void * p)540*3d8817e4Smiod bfd_putl16 (bfd_vma data, void *p)
541*3d8817e4Smiod {
542*3d8817e4Smiod bfd_byte *addr = p;
543*3d8817e4Smiod addr[0] = data & 0xff;
544*3d8817e4Smiod addr[1] = (data >> 8) & 0xff;
545*3d8817e4Smiod }
546*3d8817e4Smiod
547*3d8817e4Smiod bfd_vma
bfd_getb32(const void * p)548*3d8817e4Smiod bfd_getb32 (const void *p)
549*3d8817e4Smiod {
550*3d8817e4Smiod const bfd_byte *addr = p;
551*3d8817e4Smiod unsigned long v;
552*3d8817e4Smiod
553*3d8817e4Smiod v = (unsigned long) addr[0] << 24;
554*3d8817e4Smiod v |= (unsigned long) addr[1] << 16;
555*3d8817e4Smiod v |= (unsigned long) addr[2] << 8;
556*3d8817e4Smiod v |= (unsigned long) addr[3];
557*3d8817e4Smiod return v;
558*3d8817e4Smiod }
559*3d8817e4Smiod
560*3d8817e4Smiod bfd_vma
bfd_getl32(const void * p)561*3d8817e4Smiod bfd_getl32 (const void *p)
562*3d8817e4Smiod {
563*3d8817e4Smiod const bfd_byte *addr = p;
564*3d8817e4Smiod unsigned long v;
565*3d8817e4Smiod
566*3d8817e4Smiod v = (unsigned long) addr[0];
567*3d8817e4Smiod v |= (unsigned long) addr[1] << 8;
568*3d8817e4Smiod v |= (unsigned long) addr[2] << 16;
569*3d8817e4Smiod v |= (unsigned long) addr[3] << 24;
570*3d8817e4Smiod return v;
571*3d8817e4Smiod }
572*3d8817e4Smiod
573*3d8817e4Smiod bfd_signed_vma
bfd_getb_signed_32(const void * p)574*3d8817e4Smiod bfd_getb_signed_32 (const void *p)
575*3d8817e4Smiod {
576*3d8817e4Smiod const bfd_byte *addr = p;
577*3d8817e4Smiod unsigned long v;
578*3d8817e4Smiod
579*3d8817e4Smiod v = (unsigned long) addr[0] << 24;
580*3d8817e4Smiod v |= (unsigned long) addr[1] << 16;
581*3d8817e4Smiod v |= (unsigned long) addr[2] << 8;
582*3d8817e4Smiod v |= (unsigned long) addr[3];
583*3d8817e4Smiod return COERCE32 (v);
584*3d8817e4Smiod }
585*3d8817e4Smiod
586*3d8817e4Smiod bfd_signed_vma
bfd_getl_signed_32(const void * p)587*3d8817e4Smiod bfd_getl_signed_32 (const void *p)
588*3d8817e4Smiod {
589*3d8817e4Smiod const bfd_byte *addr = p;
590*3d8817e4Smiod unsigned long v;
591*3d8817e4Smiod
592*3d8817e4Smiod v = (unsigned long) addr[0];
593*3d8817e4Smiod v |= (unsigned long) addr[1] << 8;
594*3d8817e4Smiod v |= (unsigned long) addr[2] << 16;
595*3d8817e4Smiod v |= (unsigned long) addr[3] << 24;
596*3d8817e4Smiod return COERCE32 (v);
597*3d8817e4Smiod }
598*3d8817e4Smiod
599*3d8817e4Smiod bfd_uint64_t
bfd_getb64(const void * p ATTRIBUTE_UNUSED)600*3d8817e4Smiod bfd_getb64 (const void *p ATTRIBUTE_UNUSED)
601*3d8817e4Smiod {
602*3d8817e4Smiod #ifdef BFD_HOST_64_BIT
603*3d8817e4Smiod const bfd_byte *addr = p;
604*3d8817e4Smiod bfd_uint64_t v;
605*3d8817e4Smiod
606*3d8817e4Smiod v = addr[0]; v <<= 8;
607*3d8817e4Smiod v |= addr[1]; v <<= 8;
608*3d8817e4Smiod v |= addr[2]; v <<= 8;
609*3d8817e4Smiod v |= addr[3]; v <<= 8;
610*3d8817e4Smiod v |= addr[4]; v <<= 8;
611*3d8817e4Smiod v |= addr[5]; v <<= 8;
612*3d8817e4Smiod v |= addr[6]; v <<= 8;
613*3d8817e4Smiod v |= addr[7];
614*3d8817e4Smiod
615*3d8817e4Smiod return v;
616*3d8817e4Smiod #else
617*3d8817e4Smiod BFD_FAIL();
618*3d8817e4Smiod return 0;
619*3d8817e4Smiod #endif
620*3d8817e4Smiod }
621*3d8817e4Smiod
622*3d8817e4Smiod bfd_uint64_t
bfd_getl64(const void * p ATTRIBUTE_UNUSED)623*3d8817e4Smiod bfd_getl64 (const void *p ATTRIBUTE_UNUSED)
624*3d8817e4Smiod {
625*3d8817e4Smiod #ifdef BFD_HOST_64_BIT
626*3d8817e4Smiod const bfd_byte *addr = p;
627*3d8817e4Smiod bfd_uint64_t v;
628*3d8817e4Smiod
629*3d8817e4Smiod v = addr[7]; v <<= 8;
630*3d8817e4Smiod v |= addr[6]; v <<= 8;
631*3d8817e4Smiod v |= addr[5]; v <<= 8;
632*3d8817e4Smiod v |= addr[4]; v <<= 8;
633*3d8817e4Smiod v |= addr[3]; v <<= 8;
634*3d8817e4Smiod v |= addr[2]; v <<= 8;
635*3d8817e4Smiod v |= addr[1]; v <<= 8;
636*3d8817e4Smiod v |= addr[0];
637*3d8817e4Smiod
638*3d8817e4Smiod return v;
639*3d8817e4Smiod #else
640*3d8817e4Smiod BFD_FAIL();
641*3d8817e4Smiod return 0;
642*3d8817e4Smiod #endif
643*3d8817e4Smiod
644*3d8817e4Smiod }
645*3d8817e4Smiod
646*3d8817e4Smiod bfd_int64_t
bfd_getb_signed_64(const void * p ATTRIBUTE_UNUSED)647*3d8817e4Smiod bfd_getb_signed_64 (const void *p ATTRIBUTE_UNUSED)
648*3d8817e4Smiod {
649*3d8817e4Smiod #ifdef BFD_HOST_64_BIT
650*3d8817e4Smiod const bfd_byte *addr = p;
651*3d8817e4Smiod bfd_uint64_t v;
652*3d8817e4Smiod
653*3d8817e4Smiod v = addr[0]; v <<= 8;
654*3d8817e4Smiod v |= addr[1]; v <<= 8;
655*3d8817e4Smiod v |= addr[2]; v <<= 8;
656*3d8817e4Smiod v |= addr[3]; v <<= 8;
657*3d8817e4Smiod v |= addr[4]; v <<= 8;
658*3d8817e4Smiod v |= addr[5]; v <<= 8;
659*3d8817e4Smiod v |= addr[6]; v <<= 8;
660*3d8817e4Smiod v |= addr[7];
661*3d8817e4Smiod
662*3d8817e4Smiod return COERCE64 (v);
663*3d8817e4Smiod #else
664*3d8817e4Smiod BFD_FAIL();
665*3d8817e4Smiod return 0;
666*3d8817e4Smiod #endif
667*3d8817e4Smiod }
668*3d8817e4Smiod
669*3d8817e4Smiod bfd_int64_t
bfd_getl_signed_64(const void * p ATTRIBUTE_UNUSED)670*3d8817e4Smiod bfd_getl_signed_64 (const void *p ATTRIBUTE_UNUSED)
671*3d8817e4Smiod {
672*3d8817e4Smiod #ifdef BFD_HOST_64_BIT
673*3d8817e4Smiod const bfd_byte *addr = p;
674*3d8817e4Smiod bfd_uint64_t v;
675*3d8817e4Smiod
676*3d8817e4Smiod v = addr[7]; v <<= 8;
677*3d8817e4Smiod v |= addr[6]; v <<= 8;
678*3d8817e4Smiod v |= addr[5]; v <<= 8;
679*3d8817e4Smiod v |= addr[4]; v <<= 8;
680*3d8817e4Smiod v |= addr[3]; v <<= 8;
681*3d8817e4Smiod v |= addr[2]; v <<= 8;
682*3d8817e4Smiod v |= addr[1]; v <<= 8;
683*3d8817e4Smiod v |= addr[0];
684*3d8817e4Smiod
685*3d8817e4Smiod return COERCE64 (v);
686*3d8817e4Smiod #else
687*3d8817e4Smiod BFD_FAIL();
688*3d8817e4Smiod return 0;
689*3d8817e4Smiod #endif
690*3d8817e4Smiod }
691*3d8817e4Smiod
692*3d8817e4Smiod void
bfd_putb32(bfd_vma data,void * p)693*3d8817e4Smiod bfd_putb32 (bfd_vma data, void *p)
694*3d8817e4Smiod {
695*3d8817e4Smiod bfd_byte *addr = p;
696*3d8817e4Smiod addr[0] = (data >> 24) & 0xff;
697*3d8817e4Smiod addr[1] = (data >> 16) & 0xff;
698*3d8817e4Smiod addr[2] = (data >> 8) & 0xff;
699*3d8817e4Smiod addr[3] = data & 0xff;
700*3d8817e4Smiod }
701*3d8817e4Smiod
702*3d8817e4Smiod void
bfd_putl32(bfd_vma data,void * p)703*3d8817e4Smiod bfd_putl32 (bfd_vma data, void *p)
704*3d8817e4Smiod {
705*3d8817e4Smiod bfd_byte *addr = p;
706*3d8817e4Smiod addr[0] = data & 0xff;
707*3d8817e4Smiod addr[1] = (data >> 8) & 0xff;
708*3d8817e4Smiod addr[2] = (data >> 16) & 0xff;
709*3d8817e4Smiod addr[3] = (data >> 24) & 0xff;
710*3d8817e4Smiod }
711*3d8817e4Smiod
712*3d8817e4Smiod void
bfd_putb64(bfd_uint64_t data ATTRIBUTE_UNUSED,void * p ATTRIBUTE_UNUSED)713*3d8817e4Smiod bfd_putb64 (bfd_uint64_t data ATTRIBUTE_UNUSED, void *p ATTRIBUTE_UNUSED)
714*3d8817e4Smiod {
715*3d8817e4Smiod #ifdef BFD_HOST_64_BIT
716*3d8817e4Smiod bfd_byte *addr = p;
717*3d8817e4Smiod addr[0] = (data >> (7*8)) & 0xff;
718*3d8817e4Smiod addr[1] = (data >> (6*8)) & 0xff;
719*3d8817e4Smiod addr[2] = (data >> (5*8)) & 0xff;
720*3d8817e4Smiod addr[3] = (data >> (4*8)) & 0xff;
721*3d8817e4Smiod addr[4] = (data >> (3*8)) & 0xff;
722*3d8817e4Smiod addr[5] = (data >> (2*8)) & 0xff;
723*3d8817e4Smiod addr[6] = (data >> (1*8)) & 0xff;
724*3d8817e4Smiod addr[7] = (data >> (0*8)) & 0xff;
725*3d8817e4Smiod #else
726*3d8817e4Smiod BFD_FAIL();
727*3d8817e4Smiod #endif
728*3d8817e4Smiod }
729*3d8817e4Smiod
730*3d8817e4Smiod void
bfd_putl64(bfd_uint64_t data ATTRIBUTE_UNUSED,void * p ATTRIBUTE_UNUSED)731*3d8817e4Smiod bfd_putl64 (bfd_uint64_t data ATTRIBUTE_UNUSED, void *p ATTRIBUTE_UNUSED)
732*3d8817e4Smiod {
733*3d8817e4Smiod #ifdef BFD_HOST_64_BIT
734*3d8817e4Smiod bfd_byte *addr = p;
735*3d8817e4Smiod addr[7] = (data >> (7*8)) & 0xff;
736*3d8817e4Smiod addr[6] = (data >> (6*8)) & 0xff;
737*3d8817e4Smiod addr[5] = (data >> (5*8)) & 0xff;
738*3d8817e4Smiod addr[4] = (data >> (4*8)) & 0xff;
739*3d8817e4Smiod addr[3] = (data >> (3*8)) & 0xff;
740*3d8817e4Smiod addr[2] = (data >> (2*8)) & 0xff;
741*3d8817e4Smiod addr[1] = (data >> (1*8)) & 0xff;
742*3d8817e4Smiod addr[0] = (data >> (0*8)) & 0xff;
743*3d8817e4Smiod #else
744*3d8817e4Smiod BFD_FAIL();
745*3d8817e4Smiod #endif
746*3d8817e4Smiod }
747*3d8817e4Smiod
748*3d8817e4Smiod void
bfd_put_bits(bfd_uint64_t data,void * p,int bits,bfd_boolean big_p)749*3d8817e4Smiod bfd_put_bits (bfd_uint64_t data, void *p, int bits, bfd_boolean big_p)
750*3d8817e4Smiod {
751*3d8817e4Smiod bfd_byte *addr = p;
752*3d8817e4Smiod int i;
753*3d8817e4Smiod int bytes;
754*3d8817e4Smiod
755*3d8817e4Smiod if (bits % 8 != 0)
756*3d8817e4Smiod abort ();
757*3d8817e4Smiod
758*3d8817e4Smiod bytes = bits / 8;
759*3d8817e4Smiod for (i = 0; i < bytes; i++)
760*3d8817e4Smiod {
761*3d8817e4Smiod int index = big_p ? bytes - i - 1 : i;
762*3d8817e4Smiod
763*3d8817e4Smiod addr[index] = data & 0xff;
764*3d8817e4Smiod data >>= 8;
765*3d8817e4Smiod }
766*3d8817e4Smiod }
767*3d8817e4Smiod
768*3d8817e4Smiod bfd_uint64_t
bfd_get_bits(const void * p,int bits,bfd_boolean big_p)769*3d8817e4Smiod bfd_get_bits (const void *p, int bits, bfd_boolean big_p)
770*3d8817e4Smiod {
771*3d8817e4Smiod const bfd_byte *addr = p;
772*3d8817e4Smiod bfd_uint64_t data;
773*3d8817e4Smiod int i;
774*3d8817e4Smiod int bytes;
775*3d8817e4Smiod
776*3d8817e4Smiod if (bits % 8 != 0)
777*3d8817e4Smiod abort ();
778*3d8817e4Smiod
779*3d8817e4Smiod data = 0;
780*3d8817e4Smiod bytes = bits / 8;
781*3d8817e4Smiod for (i = 0; i < bytes; i++)
782*3d8817e4Smiod {
783*3d8817e4Smiod int index = big_p ? i : bytes - i - 1;
784*3d8817e4Smiod
785*3d8817e4Smiod data = (data << 8) | addr[index];
786*3d8817e4Smiod }
787*3d8817e4Smiod
788*3d8817e4Smiod return data;
789*3d8817e4Smiod }
790*3d8817e4Smiod
791*3d8817e4Smiod /* Default implementation */
792*3d8817e4Smiod
793*3d8817e4Smiod bfd_boolean
_bfd_generic_get_section_contents(bfd * abfd,sec_ptr section,void * location,file_ptr offset,bfd_size_type count)794*3d8817e4Smiod _bfd_generic_get_section_contents (bfd *abfd,
795*3d8817e4Smiod sec_ptr section,
796*3d8817e4Smiod void *location,
797*3d8817e4Smiod file_ptr offset,
798*3d8817e4Smiod bfd_size_type count)
799*3d8817e4Smiod {
800*3d8817e4Smiod bfd_size_type sz;
801*3d8817e4Smiod if (count == 0)
802*3d8817e4Smiod return TRUE;
803*3d8817e4Smiod
804*3d8817e4Smiod sz = section->rawsize ? section->rawsize : section->size;
805*3d8817e4Smiod if (offset + count > sz)
806*3d8817e4Smiod {
807*3d8817e4Smiod bfd_set_error (bfd_error_invalid_operation);
808*3d8817e4Smiod return FALSE;
809*3d8817e4Smiod }
810*3d8817e4Smiod
811*3d8817e4Smiod if (bfd_seek (abfd, section->filepos + offset, SEEK_SET) != 0
812*3d8817e4Smiod || bfd_bread (location, count, abfd) != count)
813*3d8817e4Smiod return FALSE;
814*3d8817e4Smiod
815*3d8817e4Smiod return TRUE;
816*3d8817e4Smiod }
817*3d8817e4Smiod
818*3d8817e4Smiod bfd_boolean
_bfd_generic_get_section_contents_in_window(bfd * abfd ATTRIBUTE_UNUSED,sec_ptr section ATTRIBUTE_UNUSED,bfd_window * w ATTRIBUTE_UNUSED,file_ptr offset ATTRIBUTE_UNUSED,bfd_size_type count ATTRIBUTE_UNUSED)819*3d8817e4Smiod _bfd_generic_get_section_contents_in_window
820*3d8817e4Smiod (bfd *abfd ATTRIBUTE_UNUSED,
821*3d8817e4Smiod sec_ptr section ATTRIBUTE_UNUSED,
822*3d8817e4Smiod bfd_window *w ATTRIBUTE_UNUSED,
823*3d8817e4Smiod file_ptr offset ATTRIBUTE_UNUSED,
824*3d8817e4Smiod bfd_size_type count ATTRIBUTE_UNUSED)
825*3d8817e4Smiod {
826*3d8817e4Smiod #ifdef USE_MMAP
827*3d8817e4Smiod bfd_size_type sz;
828*3d8817e4Smiod
829*3d8817e4Smiod if (count == 0)
830*3d8817e4Smiod return TRUE;
831*3d8817e4Smiod if (abfd->xvec->_bfd_get_section_contents
832*3d8817e4Smiod != _bfd_generic_get_section_contents)
833*3d8817e4Smiod {
834*3d8817e4Smiod /* We don't know what changes the bfd's get_section_contents
835*3d8817e4Smiod method may have to make. So punt trying to map the file
836*3d8817e4Smiod window, and let get_section_contents do its thing. */
837*3d8817e4Smiod /* @@ FIXME : If the internal window has a refcount of 1 and was
838*3d8817e4Smiod allocated with malloc instead of mmap, just reuse it. */
839*3d8817e4Smiod bfd_free_window (w);
840*3d8817e4Smiod w->i = bfd_zmalloc (sizeof (bfd_window_internal));
841*3d8817e4Smiod if (w->i == NULL)
842*3d8817e4Smiod return FALSE;
843*3d8817e4Smiod w->i->data = bfd_malloc (count);
844*3d8817e4Smiod if (w->i->data == NULL)
845*3d8817e4Smiod {
846*3d8817e4Smiod free (w->i);
847*3d8817e4Smiod w->i = NULL;
848*3d8817e4Smiod return FALSE;
849*3d8817e4Smiod }
850*3d8817e4Smiod w->i->mapped = 0;
851*3d8817e4Smiod w->i->refcount = 1;
852*3d8817e4Smiod w->size = w->i->size = count;
853*3d8817e4Smiod w->data = w->i->data;
854*3d8817e4Smiod return bfd_get_section_contents (abfd, section, w->data, offset, count);
855*3d8817e4Smiod }
856*3d8817e4Smiod sz = section->rawsize ? section->rawsize : section->size;
857*3d8817e4Smiod if (offset + count > sz
858*3d8817e4Smiod || ! bfd_get_file_window (abfd, section->filepos + offset, count, w,
859*3d8817e4Smiod TRUE))
860*3d8817e4Smiod return FALSE;
861*3d8817e4Smiod return TRUE;
862*3d8817e4Smiod #else
863*3d8817e4Smiod abort ();
864*3d8817e4Smiod #endif
865*3d8817e4Smiod }
866*3d8817e4Smiod
867*3d8817e4Smiod /* This generic function can only be used in implementations where creating
868*3d8817e4Smiod NEW sections is disallowed. It is useful in patching existing sections
869*3d8817e4Smiod in read-write files, though. See other set_section_contents functions
870*3d8817e4Smiod to see why it doesn't work for new sections. */
871*3d8817e4Smiod bfd_boolean
_bfd_generic_set_section_contents(bfd * abfd,sec_ptr section,const void * location,file_ptr offset,bfd_size_type count)872*3d8817e4Smiod _bfd_generic_set_section_contents (bfd *abfd,
873*3d8817e4Smiod sec_ptr section,
874*3d8817e4Smiod const void *location,
875*3d8817e4Smiod file_ptr offset,
876*3d8817e4Smiod bfd_size_type count)
877*3d8817e4Smiod {
878*3d8817e4Smiod if (count == 0)
879*3d8817e4Smiod return TRUE;
880*3d8817e4Smiod
881*3d8817e4Smiod if (bfd_seek (abfd, section->filepos + offset, SEEK_SET) != 0
882*3d8817e4Smiod || bfd_bwrite (location, count, abfd) != count)
883*3d8817e4Smiod return FALSE;
884*3d8817e4Smiod
885*3d8817e4Smiod return TRUE;
886*3d8817e4Smiod }
887*3d8817e4Smiod
888*3d8817e4Smiod /*
889*3d8817e4Smiod INTERNAL_FUNCTION
890*3d8817e4Smiod bfd_log2
891*3d8817e4Smiod
892*3d8817e4Smiod SYNOPSIS
893*3d8817e4Smiod unsigned int bfd_log2 (bfd_vma x);
894*3d8817e4Smiod
895*3d8817e4Smiod DESCRIPTION
896*3d8817e4Smiod Return the log base 2 of the value supplied, rounded up. E.g., an
897*3d8817e4Smiod @var{x} of 1025 returns 11. A @var{x} of 0 returns 0.
898*3d8817e4Smiod */
899*3d8817e4Smiod
900*3d8817e4Smiod unsigned int
bfd_log2(bfd_vma x)901*3d8817e4Smiod bfd_log2 (bfd_vma x)
902*3d8817e4Smiod {
903*3d8817e4Smiod unsigned int result = 0;
904*3d8817e4Smiod
905*3d8817e4Smiod while ((x = (x >> 1)) != 0)
906*3d8817e4Smiod ++result;
907*3d8817e4Smiod return result;
908*3d8817e4Smiod }
909*3d8817e4Smiod
910*3d8817e4Smiod bfd_boolean
bfd_generic_is_local_label_name(bfd * abfd,const char * name)911*3d8817e4Smiod bfd_generic_is_local_label_name (bfd *abfd, const char *name)
912*3d8817e4Smiod {
913*3d8817e4Smiod char locals_prefix = (bfd_get_symbol_leading_char (abfd) == '_') ? 'L' : '.';
914*3d8817e4Smiod
915*3d8817e4Smiod return name[0] == locals_prefix;
916*3d8817e4Smiod }
917*3d8817e4Smiod
918*3d8817e4Smiod /* Can be used from / for bfd_merge_private_bfd_data to check that
919*3d8817e4Smiod endianness matches between input and output file. Returns
920*3d8817e4Smiod TRUE for a match, otherwise returns FALSE and emits an error. */
921*3d8817e4Smiod bfd_boolean
_bfd_generic_verify_endian_match(bfd * ibfd,bfd * obfd)922*3d8817e4Smiod _bfd_generic_verify_endian_match (bfd *ibfd, bfd *obfd)
923*3d8817e4Smiod {
924*3d8817e4Smiod if (ibfd->xvec->byteorder != obfd->xvec->byteorder
925*3d8817e4Smiod && ibfd->xvec->byteorder != BFD_ENDIAN_UNKNOWN
926*3d8817e4Smiod && obfd->xvec->byteorder != BFD_ENDIAN_UNKNOWN)
927*3d8817e4Smiod {
928*3d8817e4Smiod const char *msg;
929*3d8817e4Smiod
930*3d8817e4Smiod if (bfd_big_endian (ibfd))
931*3d8817e4Smiod msg = _("%B: compiled for a big endian system and target is little endian");
932*3d8817e4Smiod else
933*3d8817e4Smiod msg = _("%B: compiled for a little endian system and target is big endian");
934*3d8817e4Smiod
935*3d8817e4Smiod (*_bfd_error_handler) (msg, ibfd);
936*3d8817e4Smiod
937*3d8817e4Smiod bfd_set_error (bfd_error_wrong_format);
938*3d8817e4Smiod return FALSE;
939*3d8817e4Smiod }
940*3d8817e4Smiod
941*3d8817e4Smiod return TRUE;
942*3d8817e4Smiod }
943*3d8817e4Smiod
944*3d8817e4Smiod /* Give a warning at runtime if someone compiles code which calls
945*3d8817e4Smiod old routines. */
946*3d8817e4Smiod
947*3d8817e4Smiod void
warn_deprecated(const char * what,const char * file,int line,const char * func)948*3d8817e4Smiod warn_deprecated (const char *what,
949*3d8817e4Smiod const char *file,
950*3d8817e4Smiod int line,
951*3d8817e4Smiod const char *func)
952*3d8817e4Smiod {
953*3d8817e4Smiod /* Poor man's tracking of functions we've already warned about. */
954*3d8817e4Smiod static size_t mask = 0;
955*3d8817e4Smiod
956*3d8817e4Smiod if (~(size_t) func & ~mask)
957*3d8817e4Smiod {
958*3d8817e4Smiod /* Note: separate sentences in order to allow
959*3d8817e4Smiod for translation into other languages. */
960*3d8817e4Smiod if (func)
961*3d8817e4Smiod fprintf (stderr, _("Deprecated %s called at %s line %d in %s\n"),
962*3d8817e4Smiod what, file, line, func);
963*3d8817e4Smiod else
964*3d8817e4Smiod fprintf (stderr, _("Deprecated %s called\n"), what);
965*3d8817e4Smiod mask |= ~(size_t) func;
966*3d8817e4Smiod }
967*3d8817e4Smiod }
968*3d8817e4Smiod
969*3d8817e4Smiod /* Helper function for reading uleb128 encoded data. */
970*3d8817e4Smiod
971*3d8817e4Smiod bfd_vma
read_unsigned_leb128(bfd * abfd ATTRIBUTE_UNUSED,bfd_byte * buf,unsigned int * bytes_read_ptr)972*3d8817e4Smiod read_unsigned_leb128 (bfd *abfd ATTRIBUTE_UNUSED,
973*3d8817e4Smiod bfd_byte *buf,
974*3d8817e4Smiod unsigned int *bytes_read_ptr)
975*3d8817e4Smiod {
976*3d8817e4Smiod bfd_vma result;
977*3d8817e4Smiod unsigned int num_read;
978*3d8817e4Smiod unsigned int shift;
979*3d8817e4Smiod unsigned char byte;
980*3d8817e4Smiod
981*3d8817e4Smiod result = 0;
982*3d8817e4Smiod shift = 0;
983*3d8817e4Smiod num_read = 0;
984*3d8817e4Smiod do
985*3d8817e4Smiod {
986*3d8817e4Smiod byte = bfd_get_8 (abfd, buf);
987*3d8817e4Smiod buf++;
988*3d8817e4Smiod num_read++;
989*3d8817e4Smiod result |= (((bfd_vma) byte & 0x7f) << shift);
990*3d8817e4Smiod shift += 7;
991*3d8817e4Smiod }
992*3d8817e4Smiod while (byte & 0x80);
993*3d8817e4Smiod *bytes_read_ptr = num_read;
994*3d8817e4Smiod return result;
995*3d8817e4Smiod }
996*3d8817e4Smiod
997*3d8817e4Smiod /* Helper function for reading sleb128 encoded data. */
998*3d8817e4Smiod
999*3d8817e4Smiod bfd_signed_vma
read_signed_leb128(bfd * abfd ATTRIBUTE_UNUSED,bfd_byte * buf,unsigned int * bytes_read_ptr)1000*3d8817e4Smiod read_signed_leb128 (bfd *abfd ATTRIBUTE_UNUSED,
1001*3d8817e4Smiod bfd_byte *buf,
1002*3d8817e4Smiod unsigned int *bytes_read_ptr)
1003*3d8817e4Smiod {
1004*3d8817e4Smiod bfd_vma result;
1005*3d8817e4Smiod unsigned int shift;
1006*3d8817e4Smiod unsigned int num_read;
1007*3d8817e4Smiod unsigned char byte;
1008*3d8817e4Smiod
1009*3d8817e4Smiod result = 0;
1010*3d8817e4Smiod shift = 0;
1011*3d8817e4Smiod num_read = 0;
1012*3d8817e4Smiod do
1013*3d8817e4Smiod {
1014*3d8817e4Smiod byte = bfd_get_8 (abfd, buf);
1015*3d8817e4Smiod buf ++;
1016*3d8817e4Smiod num_read ++;
1017*3d8817e4Smiod result |= (((bfd_vma) byte & 0x7f) << shift);
1018*3d8817e4Smiod shift += 7;
1019*3d8817e4Smiod }
1020*3d8817e4Smiod while (byte & 0x80);
1021*3d8817e4Smiod if (shift < 8 * sizeof (result) && (byte & 0x40))
1022*3d8817e4Smiod result |= (((bfd_vma) -1) << shift);
1023*3d8817e4Smiod *bytes_read_ptr = num_read;
1024*3d8817e4Smiod return result;
1025*3d8817e4Smiod }
1026*3d8817e4Smiod
1027*3d8817e4Smiod bfd_boolean
_bfd_generic_find_line(bfd * abfd ATTRIBUTE_UNUSED,asymbol ** symbols ATTRIBUTE_UNUSED,asymbol * symbol ATTRIBUTE_UNUSED,const char ** filename_ptr ATTRIBUTE_UNUSED,unsigned int * linenumber_ptr ATTRIBUTE_UNUSED)1028*3d8817e4Smiod _bfd_generic_find_line (bfd *abfd ATTRIBUTE_UNUSED,
1029*3d8817e4Smiod asymbol **symbols ATTRIBUTE_UNUSED,
1030*3d8817e4Smiod asymbol *symbol ATTRIBUTE_UNUSED,
1031*3d8817e4Smiod const char **filename_ptr ATTRIBUTE_UNUSED,
1032*3d8817e4Smiod unsigned int *linenumber_ptr ATTRIBUTE_UNUSED)
1033*3d8817e4Smiod {
1034*3d8817e4Smiod return FALSE;
1035*3d8817e4Smiod }
1036*3d8817e4Smiod
1037*3d8817e4Smiod bfd_boolean
_bfd_generic_init_private_section_data(bfd * ibfd ATTRIBUTE_UNUSED,asection * isec ATTRIBUTE_UNUSED,bfd * obfd ATTRIBUTE_UNUSED,asection * osec ATTRIBUTE_UNUSED,struct bfd_link_info * link_info ATTRIBUTE_UNUSED)1038*3d8817e4Smiod _bfd_generic_init_private_section_data (bfd *ibfd ATTRIBUTE_UNUSED,
1039*3d8817e4Smiod asection *isec ATTRIBUTE_UNUSED,
1040*3d8817e4Smiod bfd *obfd ATTRIBUTE_UNUSED,
1041*3d8817e4Smiod asection *osec ATTRIBUTE_UNUSED,
1042*3d8817e4Smiod struct bfd_link_info *link_info ATTRIBUTE_UNUSED)
1043*3d8817e4Smiod {
1044*3d8817e4Smiod return TRUE;
1045*3d8817e4Smiod }
1046