Home | History | Annotate | Download | only in libebl
      1 /* i386 specific symbolic name handling.
      2    Copyright (C) 2000, 2001, 2002 Red Hat, Inc.
      3    Written by Ulrich Drepper <drepper (at) redhat.com>, 2000.
      4 
      5    This program is Open Source software; you can redistribute it and/or
      6    modify it under the terms of the Open Software License version 1.0 as
      7    published by the Open Source Initiative.
      8 
      9    You should have received a copy of the Open Software License along
     10    with this program; if not, you may obtain a copy of the Open Software
     11    License version 1.0 from http://www.opensource.org/licenses/osl.php or
     12    by writing the Open Source Initiative c/o Lawrence Rosen, Esq.,
     13    3001 King Ranch Road, Ukiah, CA 95482.   */
     14 
     15 #ifdef HAVE_CONFIG_H
     16 # include <config.h>
     17 #endif
     18 
     19 #include <assert.h>
     20 #include <elf.h>
     21 #include <stddef.h>
     22 
     23 #include <libebl_i386.h>
     24 
     25 
     26 /* Return of the backend.  */
     27 const char *
     28 i386_backend_name (void)
     29 {
     30   return "i386";
     31 }
     32 
     33 
     34 /* Relocation mapping table.  */
     35 static struct
     36 {
     37   const char *name;
     38   enum { both = 0, rel = 1, exec = 2 } appear;
     39 } reloc_map_table[] =
     40   {
     41     [R_386_NONE] = { "R_386_NONE", both },
     42     [R_386_32] = { "R_386_32", both },
     43     [R_386_PC32] = { "R_386_PC32", rel },
     44     [R_386_GOT32] = { "R_386_GOT32", rel },
     45     [R_386_PLT32] = { "R_386_PLT32", rel },
     46     [R_386_COPY] = { "R_386_COPY", exec },
     47     [R_386_GLOB_DAT] = { "R_386_GLOB_DAT", exec },
     48     [R_386_JMP_SLOT] = { "R_386_JMP_SLOT", exec },
     49     [R_386_RELATIVE] = { "R_386_RELATIVE", exec },
     50     [R_386_GOTOFF] = { "R_386_GOTOFF", rel },
     51     [R_386_GOTPC] = { "R_386_GOTPC", rel },
     52     [R_386_32PLT] = { "R_386_32PLT", rel },
     53     [R_386_TLS_TPOFF] = { "R_386_TLS_TPOFF", rel },
     54     [R_386_TLS_IE] = { "R_386_TLS_IE", rel },
     55     [R_386_TLS_GOTIE] = { "R_386_TLS_GOTIE", rel },
     56     [R_386_TLS_LE] = { "R_386_TLS_LE", rel },
     57     [R_386_TLS_GD] = { "R_386_TLS_GD", rel },
     58     [R_386_TLS_LDM] = { "R_386_TLS_LDM", rel },
     59     [R_386_16] = { "R_386_16", rel },
     60     [R_386_PC16] = { "R_386_PC16", rel },
     61     [R_386_8] = { "R_386_8", rel },
     62     [R_386_PC8] = { "R_386_PC8", rel },
     63     [R_386_TLS_GD_32] = { "R_386_TLS_GD_32", rel },
     64     [R_386_TLS_GD_PUSH] = { "R_386_TLS_GD_PUSH", rel },
     65     [R_386_TLS_GD_CALL] = { "R_386_TLS_GD_CALL", rel },
     66     [R_386_TLS_GD_POP] = { "R_386_TLS_GD_POP", rel },
     67     [R_386_TLS_LDM_32] = { "R_386_TLS_LDM_32", rel },
     68     [R_386_TLS_LDM_PUSH] = { "R_386_TLS_LDM_PUSH", rel },
     69     [R_386_TLS_LDM_CALL] = { "R_386_TLS_LDM_CALL", rel },
     70     [R_386_TLS_LDM_POP] = { "R_386_TLS_LDM_POP", rel },
     71     [R_386_TLS_LDO_32] = { "R_386_TLS_LDO_32", rel },
     72     [R_386_TLS_IE_32] = { "R_386_TLS_IE_32", rel },
     73     [R_386_TLS_LE_32] = { "R_386_TLS_LE_32", rel },
     74     [R_386_TLS_DTPMOD32] = { "R_386_TLS_DTPMOD32", rel },
     75     [R_386_TLS_DTPOFF32] = { "R_386_TLS_DTPOFF32", rel },
     76     [R_386_TLS_TPOFF32] = { "R_386_TLS_TPOFF32", rel }
     77   };
     78 
     79 
     80 /* Determine relocation type string for x86.  */
     81 const char *
     82 i386_reloc_type_name (int type, char *buf, size_t len)
     83 {
     84   if (type < 0 || type >= R_386_NUM)
     85     return NULL;
     86 
     87   return reloc_map_table[type].name;
     88 }
     89 
     90 
     91 /* Check for correct relocation type.  */
     92 bool
     93 i386_reloc_type_check (int type)
     94 {
     95   return (type >= R_386_NONE && type < R_386_NUM
     96 	  && reloc_map_table[type].name != NULL) ? true : false;
     97 }
     98 
     99 
    100 /* Check for correct relocation type use.  */
    101 bool
    102 i386_reloc_valid_use (Elf *elf, int type)
    103 {
    104   if (type < R_386_NONE || type >= R_386_NUM
    105       || reloc_map_table[type].name == NULL)
    106     return false;
    107 
    108   Elf32_Ehdr *ehdr = elf32_getehdr (elf);
    109   assert (ehdr != NULL);
    110 
    111   if (reloc_map_table[type].appear == rel)
    112     return ehdr->e_type == ET_REL;
    113 
    114   if (reloc_map_table[type].appear == exec)
    115     return ehdr->e_type != ET_REL;
    116 
    117   assert (reloc_map_table[type].appear == both);
    118   return true;
    119 }
    120 
    121 
    122 /* Return true if the symbol type is that referencing the GOT.  */
    123 bool
    124 i386_gotpc_reloc_check (Elf *elf, int type)
    125 {
    126   return type == R_386_GOTPC;
    127 }
    128