Back to home page

LXR

 
 

    


File indexing completed on 2025-05-11 08:24:16

0001 /* SPDX-License-Identifier: BSD-2-Clause */
0002 
0003 /**
0004  *  @file
0005  *
0006  *  @ingroup
0007  *
0008  *  @brief
0009  */
0010 
0011 /*
0012  * Copyright (C) 2014 Chris Johns <chrisj@rtems.org>.
0013  *
0014  * Redistribution and use in source and binary forms, with or without
0015  * modification, are permitted provided that the following conditions
0016  * are met:
0017  * 1. Redistributions of source code must retain the above copyright
0018  *    notice, this list of conditions and the following disclaimer.
0019  * 2. Redistributions in binary form must reproduce the above copyright
0020  *    notice, this list of conditions and the following disclaimer in the
0021  *    documentation and/or other materials provided with the distribution.
0022  *
0023  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
0024  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
0025  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
0026  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
0027  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
0028  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
0029  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
0030  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
0031  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
0032  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
0033  * POSSIBILITY OF SUCH DAMAGE.
0034  */
0035 
0036 
0037 #include <sys/cdefs.h>
0038 
0039 #include <errno.h>
0040 #include <stdio.h>
0041 #include <sys/types.h>
0042 #include <sys/stat.h>
0043 
0044 #include <rtems/rtl/rtl.h>
0045 #include "rtl-elf.h"
0046 #include "rtl-error.h"
0047 #include <rtems/rtl/rtl-trace.h>
0048 #include "rtl-unwind.h"
0049 #include "rtl-unwind-dw2.h"
0050 
0051 uint32_t
0052 rtems_rtl_elf_section_flags (const rtems_rtl_obj* obj,
0053                              const Elf_Shdr*      shdr)
0054 {
0055   return 0;
0056 }
0057 
0058 uint32_t
0059 rtems_rtl_elf_arch_parse_section (const rtems_rtl_obj* obj,
0060                                   int                  section,
0061                                   const char*          name,
0062                                   const Elf_Shdr*      shdr,
0063                                   const uint32_t       flags)
0064 {
0065   (void) obj;
0066   (void) section;
0067   (void) name;
0068   (void) shdr;
0069   return flags;
0070 }
0071 
0072 bool
0073 rtems_rtl_elf_arch_section_alloc (const rtems_rtl_obj* obj,
0074                                   rtems_rtl_obj_sect*  sect)
0075 {
0076   (void) obj;
0077   (void) sect;
0078   return false;
0079 }
0080 
0081 bool
0082 rtems_rtl_elf_arch_section_free (const rtems_rtl_obj* obj,
0083                                   rtems_rtl_obj_sect*  sect)
0084 {
0085   (void) obj;
0086   (void) sect;
0087   return false;
0088 }
0089 
0090 bool
0091 rtems_rtl_elf_rel_resolve_sym (Elf_Word type)
0092 {
0093   return true;
0094 }
0095 
0096 uint32_t rtems_rtl_obj_tramp_alignment (const rtems_rtl_obj* obj)
0097 {
0098   (void) obj;
0099   return sizeof(uint32_t);
0100 }
0101 
0102 size_t
0103 rtems_rtl_elf_relocate_tramp_max_size (void)
0104 {
0105   /*
0106    * Disable by returning 0.
0107    */
0108   return 0;
0109 }
0110 
0111 rtems_rtl_elf_rel_status
0112 rtems_rtl_elf_relocate_rela_tramp (rtems_rtl_obj*            obj,
0113                                    const Elf_Rela*           rela,
0114                                    const rtems_rtl_obj_sect* sect,
0115                                    const char*               symname,
0116                                    const Elf_Byte            syminfo,
0117                                    const Elf_Word            symvalue)
0118 {
0119   (void) obj;
0120   (void) rela;
0121   (void) sect;
0122   (void) symname;
0123   (void) syminfo;
0124   (void) symvalue;
0125   return rtems_rtl_elf_rel_no_error;
0126 }
0127 
0128 rtems_rtl_elf_rel_status
0129 rtems_rtl_elf_relocate_rela (rtems_rtl_obj*            obj,
0130                              const Elf_Rela*           rela,
0131                              const rtems_rtl_obj_sect* sect,
0132                              const char*               symname,
0133                              const Elf_Byte            syminfo,
0134                              const Elf_Word            symvalue)
0135 {
0136   Elf_Addr *where;
0137   Elf_Sword tmp;
0138 
0139   where = (Elf_Addr *)(sect->base + rela->r_offset);
0140 
0141   /* Handle the not 4byte aligned address carefully */
0142 
0143   switch (ELF_R_TYPE(rela->r_info)) {
0144     case R_TYPE(NONE):
0145       break;
0146 
0147     case R_TYPE(32):
0148       *(uint16_t *)where = ((symvalue + rela->r_addend) >> 16) & 0xffff;
0149       *((uint16_t *)where + 1) = (symvalue + rela->r_addend) & 0xffff;
0150 
0151       if (rtems_rtl_trace (RTEMS_RTL_TRACE_RELOC)) {
0152           printf("*where 0x%04x%04x\n", *((uint16_t *)where + 1), *(uint16_t *)where);
0153       }
0154       break;
0155 
0156     case R_TYPE(PCREL10):
0157       /* beq, bge, bgeu, bgt, bgtu, ble, bleu, blt, bltu, bne */
0158       if (rtems_rtl_trace (RTEMS_RTL_TRACE_RELOC)) {
0159         printf("*where %x\n", *(uint16_t *)where);
0160         printf("symvalue - where %x\n", (int)(symvalue - (Elf_Word)where));
0161       }
0162       tmp = (symvalue + rela->r_addend - ((Elf_Word)where + 2)); /* pc is the next instruction */
0163       tmp = (Elf_Sword)tmp >> 1;
0164       if (((Elf32_Sword)tmp > 0x1ff) || ((Elf32_Sword)tmp < -(Elf32_Sword)0x200)){
0165         printf("Overflow for PCREL10: %ld exceed -0x200:0x1ff\n", tmp);
0166         return rtems_rtl_elf_rel_failure;
0167       }
0168 
0169       *(uint16_t *)where = (*(uint16_t *)where & 0xfc00) | (tmp & 0x3ff);
0170 
0171       if (rtems_rtl_trace (RTEMS_RTL_TRACE_RELOC)) {
0172           printf("*where 0x%04x\n",  *(uint16_t *)where);
0173       }
0174 
0175       break;
0176 
0177     default:
0178       rtems_rtl_set_error (EINVAL, "rela type record not supported");
0179       printf("Unsupported reloc types\n");
0180       return rtems_rtl_elf_rel_failure;
0181   }
0182 
0183   return rtems_rtl_elf_rel_no_error;
0184 }
0185 
0186 rtems_rtl_elf_rel_status
0187 rtems_rtl_elf_relocate_rel_tramp (rtems_rtl_obj*            obj,
0188                                   const Elf_Rel*            rel,
0189                                   const rtems_rtl_obj_sect* sect,
0190                                   const char*               symname,
0191                                   const Elf_Byte            syminfo,
0192                                   const Elf_Word            symvalue)
0193 {
0194   (void) obj;
0195   (void) rel;
0196   (void) sect;
0197   (void) symname;
0198   (void) syminfo;
0199   (void) symvalue;
0200   rtems_rtl_set_error (EINVAL, "rel type record not supported");
0201   return rtems_rtl_elf_rel_failure;
0202 }
0203 
0204 rtems_rtl_elf_rel_status
0205 rtems_rtl_elf_relocate_rel (rtems_rtl_obj*            obj,
0206                             const Elf_Rel*            rel,
0207                             const rtems_rtl_obj_sect* sect,
0208                             const char*               symname,
0209                             const Elf_Byte            syminfo,
0210                             const Elf_Word            symvalue)
0211 {
0212   (void) obj;
0213   (void) rel;
0214   (void) sect;
0215   (void) symname;
0216   (void) syminfo;
0217   (void) symvalue;
0218   rtems_rtl_set_error (EINVAL, "rel type record not supported");
0219   return rtems_rtl_elf_rel_failure;
0220 }
0221 
0222 bool
0223 rtems_rtl_elf_unwind_parse (const rtems_rtl_obj* obj,
0224                             const char*          name,
0225                             uint32_t             flags)
0226 {
0227   return rtems_rtl_elf_unwind_dw2_parse (obj, name, flags);
0228 }
0229 
0230 bool
0231 rtems_rtl_elf_unwind_register (rtems_rtl_obj* obj)
0232 {
0233   return rtems_rtl_elf_unwind_dw2_register (obj);
0234 }
0235 
0236 bool
0237 rtems_rtl_elf_unwind_deregister (rtems_rtl_obj* obj)
0238 {
0239   return rtems_rtl_elf_unwind_dw2_deregister (obj);
0240 }