OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [binutils-2.20.1/] [bfd/] [nlm32-sparc.c] - Blame information for rev 271

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 205 julius
/* Support for 32-bit SPARC NLM (NetWare Loadable Module)
2
   Copyright 1993, 1994, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006,
3
   2007 Free Software Foundation, Inc.
4
 
5
   This file is part of BFD, the Binary File Descriptor library.
6
 
7
   This program is free software; you can redistribute it and/or modify
8
   it under the terms of the GNU General Public License as published by
9
   the Free Software Foundation; either version 3 of the License, or
10
   (at your option) any later version.
11
 
12
   This program is distributed in the hope that it will be useful,
13
   but WITHOUT ANY WARRANTY; without even the implied warranty of
14
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
   GNU General Public License for more details.
16
 
17
   You should have received a copy of the GNU General Public License
18
   along with this program; if not, write to the Free Software
19
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20
   MA 02110-1301, USA.  */
21
 
22
#include "sysdep.h"
23
#include "bfd.h"
24
#include "libbfd.h"
25
 
26
#define ARCH_SIZE 32
27
 
28
#include "nlm/sparc32-ext.h"
29
#define Nlm_External_Fixed_Header       Nlm32_sparc_External_Fixed_Header
30
 
31
#include "libnlm.h"
32
 
33
enum reloc_type
34
{
35
  R_SPARC_NONE = 0,
36
  R_SPARC_8,            R_SPARC_16,             R_SPARC_32,
37
  R_SPARC_DISP8,        R_SPARC_DISP16,         R_SPARC_DISP32,
38
  R_SPARC_WDISP30,      R_SPARC_WDISP22,
39
  R_SPARC_HI22,         R_SPARC_22,
40
  R_SPARC_13,           R_SPARC_LO10,
41
  R_SPARC_GOT10,        R_SPARC_GOT13,          R_SPARC_GOT22,
42
  R_SPARC_PC10,         R_SPARC_PC22,
43
  R_SPARC_WPLT30,
44
  R_SPARC_COPY,
45
  R_SPARC_GLOB_DAT,     R_SPARC_JMP_SLOT,
46
  R_SPARC_RELATIVE,
47
  R_SPARC_UA32,
48
  R_SPARC_max
49
};
50
 
51
static reloc_howto_type nlm32_sparc_howto_table[] =
52
{
53
  HOWTO (R_SPARC_NONE,    0,0, 0,FALSE,0,complain_overflow_dont,    0,"R_SPARC_NONE",    FALSE,0,0x00000000,TRUE),
54
  HOWTO (R_SPARC_8,       0,0, 8,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_8",       FALSE,0,0x000000ff,TRUE),
55
  HOWTO (R_SPARC_16,      0,1,16,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_16",      FALSE,0,0x0000ffff,TRUE),
56
  HOWTO (R_SPARC_32,      0,2,32,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_32",      FALSE,0,0xffffffff,TRUE),
57
  HOWTO (R_SPARC_DISP8,   0,0, 8,TRUE, 0,complain_overflow_signed,  0,"R_SPARC_DISP8",   FALSE,0,0x000000ff,TRUE),
58
  HOWTO (R_SPARC_DISP16,  0,1,16,TRUE, 0,complain_overflow_signed,  0,"R_SPARC_DISP16",  FALSE,0,0x0000ffff,TRUE),
59
  HOWTO (R_SPARC_DISP32,  0,2,32,TRUE, 0,complain_overflow_signed,  0,"R_SPARC_DISP32",  FALSE,0,0x00ffffff,TRUE),
60
  HOWTO (R_SPARC_WDISP30, 2,2,30,TRUE, 0,complain_overflow_signed,  0,"R_SPARC_WDISP30", FALSE,0,0x3fffffff,TRUE),
61
  HOWTO (R_SPARC_WDISP22, 2,2,22,TRUE, 0,complain_overflow_signed,  0,"R_SPARC_WDISP22", FALSE,0,0x003fffff,TRUE),
62
  HOWTO (R_SPARC_HI22,   10,2,22,FALSE,0,complain_overflow_dont,    0,"R_SPARC_HI22",    FALSE,0,0x003fffff,TRUE),
63
  HOWTO (R_SPARC_22,      0,2,22,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_22",      FALSE,0,0x003fffff,TRUE),
64
  HOWTO (R_SPARC_13,      0,2,13,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_13",      FALSE,0,0x00001fff,TRUE),
65
  HOWTO (R_SPARC_LO10,    0,2,10,FALSE,0,complain_overflow_dont,    0,"R_SPARC_LO10",    FALSE,0,0x000003ff,TRUE),
66
  HOWTO (R_SPARC_GOT10,   0,2,10,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_GOT10",   FALSE,0,0x000003ff,TRUE),
67
  HOWTO (R_SPARC_GOT13,   0,2,13,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_GOT13",   FALSE,0,0x00001fff,TRUE),
68
  HOWTO (R_SPARC_GOT22,  10,2,22,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_GOT22",   FALSE,0,0x003fffff,TRUE),
69
  HOWTO (R_SPARC_PC10,    0,2,10,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_PC10",    FALSE,0,0x000003ff,TRUE),
70
  HOWTO (R_SPARC_PC22,    0,2,22,FALSE,0,complain_overflow_bitfield,0,"R_SPARC_PC22",    FALSE,0,0x003fffff,TRUE),
71
  HOWTO (R_SPARC_WPLT30,  0,0,00,FALSE,0,complain_overflow_dont,    0,"R_SPARC_WPLT30",  FALSE,0,0x00000000,TRUE),
72
  HOWTO (R_SPARC_COPY,    0,0,00,FALSE,0,complain_overflow_dont,    0,"R_SPARC_COPY",    FALSE,0,0x00000000,TRUE),
73
  HOWTO (R_SPARC_GLOB_DAT,0,0,00,FALSE,0,complain_overflow_dont,    0,"R_SPARC_GLOB_DAT",FALSE,0,0x00000000,TRUE),
74
  HOWTO (R_SPARC_JMP_SLOT,0,0,00,FALSE,0,complain_overflow_dont,    0,"R_SPARC_JMP_SLOT",FALSE,0,0x00000000,TRUE),
75
  HOWTO (R_SPARC_RELATIVE,0,0,00,FALSE,0,complain_overflow_dont,    0,"R_SPARC_RELATIVE",FALSE,0,0x00000000,TRUE),
76
  HOWTO (R_SPARC_UA32,    0,0,00,FALSE,0,complain_overflow_dont,    0,"R_SPARC_UA32",    FALSE,0,0x00000000,TRUE),
77
};
78
 
79
/* Read a NetWare sparc reloc.  */
80
 
81
struct nlm32_sparc_reloc_ext
82
{
83
  unsigned char offset[4];
84
  unsigned char addend[4];
85
  unsigned char type[1];
86
  unsigned char pad1[3];
87
};
88
 
89
static bfd_boolean
90
nlm_sparc_read_reloc (bfd *abfd,
91
                      nlmNAME (symbol_type) *sym ATTRIBUTE_UNUSED,
92
                      asection **secp,
93
                      arelent *rel)
94
{
95
  bfd_vma val, addend;
96
  unsigned int index;
97
  unsigned int type;
98
  struct nlm32_sparc_reloc_ext tmp_reloc;
99
  asection *code_sec, *data_sec;
100
 
101
  if (bfd_bread (&tmp_reloc, (bfd_size_type) 12, abfd) != 12)
102
    return FALSE;
103
 
104
  code_sec = bfd_get_section_by_name (abfd, NLM_CODE_NAME);
105
  data_sec = bfd_get_section_by_name (abfd, NLM_INITIALIZED_DATA_NAME);
106
 
107
  *secp = code_sec;
108
 
109
  val = bfd_get_32 (abfd, tmp_reloc.offset);
110
  addend = bfd_get_32 (abfd, tmp_reloc.addend);
111
  type = bfd_get_8 (abfd, tmp_reloc.type);
112
 
113
  rel->address = val;
114
  rel->addend = addend;
115
  rel->howto = NULL;
116
 
117
  for (index = 0;
118
       index < sizeof (nlm32_sparc_howto_table) / sizeof (reloc_howto_type);
119
       index++)
120
    if (nlm32_sparc_howto_table[index].type == type)
121
      {
122
        rel->howto = &nlm32_sparc_howto_table[index];
123
        break;
124
      }
125
 
126
#ifdef DEBUG
127
  fprintf (stderr, "%s:  address = %08lx, addend = %08lx, type = %u, howto = %p\n",
128
           __FUNCTION__, (unsigned long) rel->address,
129
           (unsigned long) rel->addend, type, rel->howto);
130
#endif
131
  return TRUE;
132
 
133
}
134
 
135
/* Write a NetWare sparc reloc.  */
136
 
137
static bfd_boolean
138
nlm_sparc_write_reloc (bfd * abfd, asection * sec, arelent * rel)
139
{
140
  bfd_vma val;
141
  struct nlm32_sparc_reloc_ext tmp_reloc;
142
  unsigned int index;
143
  int type = -1;
144
  reloc_howto_type *tmp;
145
 
146
  for (index = 0;
147
       index < sizeof (nlm32_sparc_howto_table) / sizeof (reloc_howto_type);
148
       index++)
149
    {
150
      tmp = &nlm32_sparc_howto_table[index];
151
 
152
      if (tmp->rightshift == rel->howto->rightshift
153
          && tmp->size == rel->howto->size
154
          && tmp->bitsize == rel->howto->bitsize
155
          && tmp->pc_relative == rel->howto->pc_relative
156
          && tmp->bitpos == rel->howto->bitpos
157
          && tmp->src_mask == rel->howto->src_mask
158
          && tmp->dst_mask == rel->howto->dst_mask)
159
        {
160
          type = tmp->type;
161
          break;
162
        }
163
    }
164
  if (type == -1)
165
    abort ();
166
 
167
  /* Netware wants a list of relocs for each address.
168
     Format is:
169
        long    offset
170
        long    addend
171
        char    type
172
     That should be it.  */
173
 
174
  /* The value we write out is the offset into the appropriate
175
     segment.  This offset is the section vma, adjusted by the vma of
176
     the lowest section in that segment, plus the address of the
177
     relocation.  */
178
  val = bfd_get_section_vma (abfd, sec) + rel->address;
179
 
180
#ifdef DEBUG
181
  fprintf (stderr, "%s:  val = %08lx, addend = %08lx, type = %u\n",
182
           __FUNCTION__, (unsigned long) val, (unsigned long) rel->addend,
183
           rel->howto->type);
184
#endif
185
  bfd_put_32 (abfd, val, tmp_reloc.offset);
186
  bfd_put_32 (abfd, rel->addend, tmp_reloc.addend);
187
  bfd_put_8 (abfd, (short) (rel->howto->type), tmp_reloc.type);
188
 
189
  if (bfd_bwrite (&tmp_reloc, (bfd_size_type) 12, abfd) != 12)
190
    return FALSE;
191
 
192
  return TRUE;
193
}
194
 
195
/* Mangle relocs for SPARC NetWare.  We can just use the standard
196
   SPARC relocs.  */
197
 
198
static bfd_boolean
199
nlm_sparc_mangle_relocs (bfd *abfd ATTRIBUTE_UNUSED,
200
                         asection *sec ATTRIBUTE_UNUSED,
201
                         const void * data ATTRIBUTE_UNUSED,
202
                         bfd_vma offset ATTRIBUTE_UNUSED,
203
                         bfd_size_type count ATTRIBUTE_UNUSED)
204
{
205
  return TRUE;
206
}
207
 
208
/* Read a NetWare sparc import record.  */
209
 
210
static bfd_boolean
211
nlm_sparc_read_import (bfd *abfd, nlmNAME (symbol_type) *sym)
212
{
213
  struct nlm_relent *nlm_relocs;        /* Relocation records for symbol.  */
214
  bfd_size_type rcount;                 /* Number of relocs.  */
215
  bfd_byte temp[NLM_TARGET_LONG_SIZE];  /* Temporary 32-bit value.  */
216
  unsigned char symlength;              /* Length of symbol name.  */
217
  char *name;
218
 
219
  /* First, read in the number of relocation
220
     entries for this symbol.  */
221
  if (bfd_bread (temp, (bfd_size_type) 4, abfd) != 4)
222
    return FALSE;
223
 
224
  rcount = bfd_get_32 (abfd, temp);
225
 
226
  /* Next, read in the length of the symbol.  */
227
  if (bfd_bread (& symlength, (bfd_size_type) sizeof (symlength), abfd)
228
      != sizeof (symlength))
229
    return FALSE;
230
  sym -> symbol.the_bfd = abfd;
231
  name = bfd_alloc (abfd, (bfd_size_type) symlength + 1);
232
  if (name == NULL)
233
    return FALSE;
234
 
235
  /* Then read in the symbol.  */
236
  if (bfd_bread (name, (bfd_size_type) symlength, abfd) != symlength)
237
    return FALSE;
238
  name[symlength] = '\0';
239
  sym -> symbol.name = name;
240
  sym -> symbol.flags = 0;
241
  sym -> symbol.value = 0;
242
  sym -> symbol.section = bfd_und_section_ptr;
243
 
244
  /* Next, start reading in the relocs.  */
245
  nlm_relocs = bfd_alloc (abfd, rcount * sizeof (struct nlm_relent));
246
  if (!nlm_relocs)
247
    return FALSE;
248
  sym -> relocs = nlm_relocs;
249
  sym -> rcnt = 0;
250
  while (sym -> rcnt < rcount)
251
    {
252
      asection *section;
253
 
254
      if (! nlm_sparc_read_reloc (abfd, sym, &section, &nlm_relocs -> reloc))
255
        return FALSE;
256
      nlm_relocs -> section = section;
257
      nlm_relocs++;
258
      sym -> rcnt++;
259
    }
260
 
261
  return TRUE;
262
}
263
 
264
static bfd_boolean
265
nlm_sparc_write_import (bfd * abfd, asection * sec, arelent * rel)
266
{
267
  char temp[4];
268
  asection *code, *data, *bss, *symsec;
269
  bfd_vma base;
270
 
271
  code = bfd_get_section_by_name (abfd, NLM_CODE_NAME);
272
  data = bfd_get_section_by_name (abfd, NLM_INITIALIZED_DATA_NAME);
273
  bss = bfd_get_section_by_name (abfd, NLM_UNINITIALIZED_DATA_NAME);
274
  symsec = (*rel->sym_ptr_ptr)->section;
275
 
276
  if (symsec == code)
277
    base = 0;
278
  else if (symsec == data)
279
    base = code->size;
280
  else if (symsec == bss)
281
    base = code->size + data->size;
282
  else
283
    base = 0;
284
 
285
#ifdef DEBUG
286
  fprintf (stderr, "%s:  <%lx, 1>\n\t",
287
           __FUNCTION__, (unsigned long) (base + (*rel->sym_ptr_ptr)->value));
288
#endif
289
  bfd_put_32 (abfd, base + (*rel->sym_ptr_ptr)->value, temp);
290
  if (bfd_bwrite (temp, (bfd_size_type) 4, abfd) != 4)
291
    return FALSE;
292
  bfd_put_32 (abfd, (bfd_vma) 1, temp);
293
  if (bfd_bwrite (temp, (bfd_size_type) 4, abfd) != 4)
294
    return FALSE;
295
  if (! nlm_sparc_write_reloc (abfd, sec, rel))
296
    return FALSE;
297
  return TRUE;
298
}
299
 
300
/* Write out an external reference.  */
301
 
302
static bfd_boolean
303
nlm_sparc_write_external (bfd *abfd,
304
                          bfd_size_type count,
305
                          asymbol *sym,
306
                          struct reloc_and_sec *relocs)
307
{
308
  unsigned int i;
309
  bfd_byte len;
310
  unsigned char temp[NLM_TARGET_LONG_SIZE];
311
 
312
  bfd_put_32 (abfd, count, temp);
313
  if (bfd_bwrite (temp, (bfd_size_type) sizeof (temp), abfd) != sizeof (temp))
314
    return FALSE;
315
 
316
  len = strlen (sym->name);
317
  if ((bfd_bwrite (&len, (bfd_size_type) sizeof (bfd_byte), abfd)
318
       != sizeof (bfd_byte))
319
      || bfd_bwrite (sym->name, (bfd_size_type) len, abfd) != len)
320
    return FALSE;
321
 
322
  for (i = 0; i < count; i++)
323
    if (! nlm_sparc_write_reloc (abfd, relocs[i].sec, relocs[i].rel))
324
      return FALSE;
325
 
326
  return TRUE;
327
}
328
 
329
static bfd_boolean
330
nlm_sparc_write_export (bfd * abfd, asymbol * sym, bfd_vma value)
331
{
332
  bfd_byte len;
333
  bfd_byte temp[4];
334
 
335
#ifdef DEBUG
336
  fprintf (stderr, "%s: <%lx, %u, %s>\n",
337
           __FUNCTION__, (unsigned long) value, strlen (sym->name), sym->name);
338
#endif
339
  bfd_put_32 (abfd, value, temp);
340
  len = strlen (sym->name);
341
 
342
  if (bfd_bwrite (temp, (bfd_size_type) 4, abfd) != 4
343
      || bfd_bwrite (&len, (bfd_size_type) 1, abfd) != 1
344
      || bfd_bwrite (sym->name, (bfd_size_type) len, abfd) != len)
345
    return FALSE;
346
 
347
  return TRUE;
348
}
349
 
350
#undef nlm_swap_fixed_header_in
351
#undef nlm_swap_fixed_header_out
352
 
353
#include "nlmswap.h"
354
 
355
static const struct nlm_backend_data nlm32_sparc_backend =
356
{
357
  "NetWare SPARC Module   \032",
358
  sizeof (Nlm32_sparc_External_Fixed_Header),
359
  0,     /* Optional_prefix_size.  */
360
  bfd_arch_sparc,
361
  0,
362
  FALSE,
363
  0,     /* Backend_object_p.  */
364
  0,     /* Write_prefix_func.  */
365
  nlm_sparc_read_reloc,
366
  nlm_sparc_mangle_relocs,
367
  nlm_sparc_read_import,
368
  nlm_sparc_write_import,
369
  0,     /* Set_public_section.  */
370
  0,     /* Get_public_offset.  */
371
  nlm_swap_fixed_header_in,
372
  nlm_swap_fixed_header_out,
373
  nlm_sparc_write_external,
374
  nlm_sparc_write_export
375
};
376
 
377
#define TARGET_BIG_NAME         "nlm32-sparc"
378
#define TARGET_BIG_SYM          nlmNAME (sparc_vec)
379
#define TARGET_BACKEND_DATA     & nlm32_sparc_backend
380
 
381
#include "nlm-target.h"

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.