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

Subversion Repositories or1k

[/] [or1k/] [tags/] [VER_5_3/] [gdb-5.3/] [bfd/] [elfcore.h] - Blame information for rev 1182

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

Line No. Rev Author Line
1 1181 sfurman
/* ELF core file support for BFD.
2
   Copyright 1995, 1996, 1997, 1998, 2000, 2001, 2002
3
   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 2 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
20
 
21
char*
22
elf_core_file_failing_command (abfd)
23
     bfd *abfd;
24
{
25
  return elf_tdata (abfd)->core_command;
26
}
27
 
28
int
29
elf_core_file_failing_signal (abfd)
30
     bfd *abfd;
31
{
32
  return elf_tdata (abfd)->core_signal;
33
}
34
 
35
boolean
36
elf_core_file_matches_executable_p (core_bfd, exec_bfd)
37
     bfd *core_bfd;
38
     bfd *exec_bfd;
39
{
40
  char* corename;
41
 
42
  /* xvecs must match if both are ELF files for the same target.  */
43
 
44
  if (core_bfd->xvec != exec_bfd->xvec)
45
    {
46
      bfd_set_error (bfd_error_system_call);
47
      return false;
48
    }
49
 
50
  /* See if the name in the corefile matches the executable name.  */
51
 
52
  corename = elf_tdata (core_bfd)->core_program;
53
  if (corename != NULL)
54
    {
55
      const char* execname = strrchr (exec_bfd->filename, '/');
56
      execname = execname ? execname + 1 : exec_bfd->filename;
57
 
58
      if (strcmp(execname, corename) != 0)
59
        return false;
60
    }
61
 
62
  return true;
63
}
64
 
65
/*  Core files are simply standard ELF formatted files that partition
66
    the file using the execution view of the file (program header table)
67
    rather than the linking view.  In fact, there is no section header
68
    table in a core file.
69
 
70
    The process status information (including the contents of the general
71
    register set) and the floating point register set are stored in a
72
    segment of type PT_NOTE.  We handcraft a couple of extra bfd sections
73
    that allow standard bfd access to the general registers (.reg) and the
74
    floating point registers (.reg2).
75
 
76
 */
77
 
78
const bfd_target *
79
elf_core_file_p (abfd)
80
     bfd *abfd;
81
{
82
  Elf_External_Ehdr x_ehdr;     /* Elf file header, external form */
83
  Elf_Internal_Ehdr *i_ehdrp;   /* Elf file header, internal form */
84
  Elf_Internal_Phdr *i_phdrp;   /* Elf program header, internal form */
85
  unsigned int phindex;
86
  struct elf_backend_data *ebd;
87
  struct bfd_preserve preserve;
88
  struct elf_obj_tdata *new_tdata = NULL;
89
  bfd_size_type amt;
90
 
91
  preserve.arch_info = abfd->arch_info;
92
 
93
  /* Read in the ELF header in external format.  */
94
  if (bfd_bread ((PTR) &x_ehdr, (bfd_size_type) sizeof (x_ehdr), abfd)
95
      != sizeof (x_ehdr))
96
    {
97
      if (bfd_get_error () != bfd_error_system_call)
98
        bfd_set_error (bfd_error_wrong_format);
99
      return NULL;
100
    }
101
 
102
  /* Check the magic number.  */
103
  if (! elf_file_p (&x_ehdr))
104
    goto wrong;
105
 
106
  /* FIXME: Check EI_VERSION here ! */
107
 
108
  /* Check the address size ("class").  */
109
  if (x_ehdr.e_ident[EI_CLASS] != ELFCLASS)
110
    goto wrong;
111
 
112
  /* Check the byteorder.  */
113
  switch (x_ehdr.e_ident[EI_DATA])
114
    {
115
    case ELFDATA2MSB:           /* Big-endian */
116
      if (! bfd_big_endian (abfd))
117
        goto wrong;
118
      break;
119
    case ELFDATA2LSB:           /* Little-endian */
120
      if (! bfd_little_endian (abfd))
121
        goto wrong;
122
      break;
123
    default:
124
      goto wrong;
125
    }
126
 
127
  /* Give abfd an elf_obj_tdata.  */
128
  amt = sizeof (struct elf_obj_tdata);
129
  new_tdata = (struct elf_obj_tdata *) bfd_zalloc (abfd, amt);
130
  if (new_tdata == NULL)
131
    return NULL;
132
  preserve.tdata = elf_tdata (abfd);
133
  elf_tdata (abfd) = new_tdata;
134
 
135
  /* Clear section information, since there might be a recognized bfd that
136
     we now check if we can replace, and we don't want to append to it.  */
137
  preserve.sections = abfd->sections;
138
  preserve.section_tail = abfd->section_tail;
139
  preserve.section_count = abfd->section_count;
140
  preserve.section_htab = abfd->section_htab;
141
  abfd->sections = NULL;
142
  abfd->section_tail = &abfd->sections;
143
  abfd->section_count = 0;
144
  if (!bfd_hash_table_init (&abfd->section_htab, bfd_section_hash_newfunc))
145
    goto fail;
146
 
147
  /* Swap in the rest of the header, now that we have the byte order.  */
148
  i_ehdrp = elf_elfheader (abfd);
149
  elf_swap_ehdr_in (abfd, &x_ehdr, i_ehdrp);
150
 
151
#if DEBUG & 1
152
  elf_debug_file (i_ehdrp);
153
#endif
154
 
155
  ebd = get_elf_backend_data (abfd);
156
 
157
  /* Check that the ELF e_machine field matches what this particular
158
     BFD format expects.  */
159
 
160
  if (ebd->elf_machine_code != i_ehdrp->e_machine
161
      && (ebd->elf_machine_alt1 == 0
162
          || i_ehdrp->e_machine != ebd->elf_machine_alt1)
163
      && (ebd->elf_machine_alt2 == 0
164
          || i_ehdrp->e_machine != ebd->elf_machine_alt2))
165
    {
166
      const bfd_target * const *target_ptr;
167
 
168
      if (ebd->elf_machine_code != EM_NONE)
169
        goto wrong;
170
 
171
      /* This is the generic ELF target.  Let it match any ELF target
172
         for which we do not have a specific backend.  */
173
 
174
      for (target_ptr = bfd_target_vector; *target_ptr != NULL; target_ptr++)
175
        {
176
          struct elf_backend_data *back;
177
 
178
          if ((*target_ptr)->flavour != bfd_target_elf_flavour)
179
            continue;
180
          back = (struct elf_backend_data *) (*target_ptr)->backend_data;
181
          if (back->elf_machine_code == i_ehdrp->e_machine)
182
            {
183
              /* target_ptr is an ELF backend which matches this
184
                 object file, so reject the generic ELF target.  */
185
              goto wrong;
186
            }
187
        }
188
    }
189
 
190
  /* If there is no program header, or the type is not a core file, then
191
     we are hosed.  */
192
  if (i_ehdrp->e_phoff == 0 || i_ehdrp->e_type != ET_CORE)
193
    goto wrong;
194
 
195
  /* Does BFD's idea of the phdr size match the size
196
     recorded in the file? */
197
  if (i_ehdrp->e_phentsize != sizeof (Elf_External_Phdr))
198
    goto wrong;
199
 
200
  /* Move to the start of the program headers.  */
201
  if (bfd_seek (abfd, (file_ptr) i_ehdrp->e_phoff, SEEK_SET) != 0)
202
    goto wrong;
203
 
204
  /* Allocate space for the program headers.  */
205
  amt = sizeof (*i_phdrp) * i_ehdrp->e_phnum;
206
  i_phdrp = (Elf_Internal_Phdr *) bfd_alloc (abfd, amt);
207
  if (!i_phdrp)
208
    goto fail;
209
 
210
  elf_tdata (abfd)->phdr = i_phdrp;
211
 
212
  /* Read and convert to internal form.  */
213
  for (phindex = 0; phindex < i_ehdrp->e_phnum; ++phindex)
214
    {
215
      Elf_External_Phdr x_phdr;
216
      if (bfd_bread ((PTR) &x_phdr, (bfd_size_type) sizeof (x_phdr), abfd)
217
          != sizeof (x_phdr))
218
        goto fail;
219
 
220
      elf_swap_phdr_in (abfd, &x_phdr, i_phdrp + phindex);
221
    }
222
 
223
  /* Set the machine architecture.  Do this before processing the
224
     program headers since we need to know the architecture type
225
     when processing the notes of some systems' core files.  */
226
  if (! bfd_default_set_arch_mach (abfd, ebd->arch, 0))
227
    {
228
      /* It's OK if this fails for the generic target.  */
229
      if (ebd->elf_machine_code != EM_NONE)
230
        goto fail;
231
    }
232
 
233
  /* Process each program header.  */
234
  for (phindex = 0; phindex < i_ehdrp->e_phnum; ++phindex)
235
    {
236
      if (! bfd_section_from_phdr (abfd, i_phdrp + phindex, (int) phindex))
237
        goto fail;
238
    }
239
 
240
  /* Save the entry point from the ELF header.  */
241
  bfd_get_start_address (abfd) = i_ehdrp->e_entry;
242
 
243
  /* Let the backend double check the format and override global
244
     information.  */
245
  if (ebd->elf_backend_object_p)
246
    {
247
      if (! (*ebd->elf_backend_object_p) (abfd))
248
        goto wrong;
249
    }
250
 
251
  bfd_hash_table_free (&preserve.section_htab);
252
  return abfd->xvec;
253
 
254
wrong:
255
  /* There is way too much undoing of half-known state here.  The caller,
256
     bfd_check_format_matches, really shouldn't iterate on live bfd's to
257
     check match/no-match like it does.  We have to rely on that a call to
258
     bfd_default_set_arch_mach with the previously known mach, undoes what
259
     was done by the first bfd_default_set_arch_mach (with mach 0) here.
260
     For this to work, only elf-data and the mach may be changed by the
261
     target-specific elf_backend_object_p function.  Note that saving the
262
     whole bfd here and restoring it would be even worse; the first thing
263
     you notice is that the cached bfd file position gets out of sync.  */
264
  bfd_set_error (bfd_error_wrong_format);
265
 
266
fail:
267
  abfd->arch_info = preserve.arch_info;
268
  if (new_tdata != NULL)
269
    {
270
      /* bfd_release frees all memory more recently bfd_alloc'd than
271
         its arg, as well as its arg.  */
272
      bfd_release (abfd, new_tdata);
273
      elf_tdata (abfd) = preserve.tdata;
274
      abfd->section_htab = preserve.section_htab;
275
      abfd->sections = preserve.sections;
276
      abfd->section_tail = preserve.section_tail;
277
      abfd->section_count = preserve.section_count;
278
    }
279
  return NULL;
280
}

powered by: WebSVN 2.1.0

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