uboot/arch/arm/lib/reloc_arm_efi.c
<<
>>
Prefs
   1// SPDX-License-Identifier: BSD-3-Clause
   2/*
   3 * reloc_arm.c - position-independent ARM ELF shared object relocator
   4 *
   5 * Copyright (C) 2014 Linaro Ltd. <ard.biesheuvel@linaro.org>
   6 * Copyright (C) 1999 Hewlett-Packard Co.
   7 * Contributed by David Mosberger <davidm@hpl.hp.com>.
   8 *
   9 * All rights reserved.
  10 *
  11 * This file is taken and modified from the gnu-efi project.
  12 */
  13
  14#include <efi.h>
  15#include <elf.h>
  16
  17efi_status_t EFIAPI _relocate(long ldbase, Elf32_Dyn *dyn)
  18{
  19        long relsz = 0, relent = 0;
  20        Elf32_Rel *rel = 0;
  21        ulong *addr;
  22        int i;
  23
  24        for (i = 0; dyn[i].d_tag != DT_NULL; ++i) {
  25                switch (dyn[i].d_tag) {
  26                case DT_REL:
  27                        rel = (Elf32_Rel *)((ulong)dyn[i].d_un.d_ptr
  28                                        + ldbase);
  29                        break;
  30                case DT_RELSZ:
  31                        relsz = dyn[i].d_un.d_val;
  32                        break;
  33                case DT_RELENT:
  34                        relent = dyn[i].d_un.d_val;
  35                        break;
  36                default:
  37                        break;
  38                }
  39        }
  40
  41        if (!rel && relent == 0)
  42                return EFI_SUCCESS;
  43
  44        if (!rel || relent == 0)
  45                return EFI_LOAD_ERROR;
  46
  47        while (relsz > 0) {
  48                /* apply the relocs */
  49                switch (ELF32_R_TYPE(rel->r_info)) {
  50                case R_ARM_NONE:
  51                        break;
  52                case R_ARM_RELATIVE:
  53                        addr = (ulong *)(ldbase + rel->r_offset);
  54                        *addr += ldbase;
  55                        break;
  56                default:
  57                        break;
  58                }
  59                rel = (Elf32_Rel *)((char *)rel + relent);
  60                relsz -= relent;
  61        }
  62
  63        return EFI_SUCCESS;
  64}
  65