/* Subroutine for function pointer canonicalization on PA-RISC with ELF32.
   Copyright (C) 2002-2025 Free Software Foundation, Inc.
   Contributed by John David Anglin (dave.anglin@nrc.ca).

This file is part of GCC.

GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.

GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
for more details.

Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.

You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
<http://www.gnu.org/licenses/>.  */


/* WARNING: The code is this function depends on internal and undocumented
   details of the GNU linker and dynamic loader as implemented for parisc
   linux.  */

/* This MUST match the defines sysdeps/hppa/dl-machine.h and
   bfd/elf32-hppa.c.  */
#define GOT_FROM_PLT_STUB (4*4)

/* List of byte offsets in _dl_runtime_resolve to search for "bl" branches.
   The first "bl" branch instruction found MUST be a call to fixup.  See
   the define for TRAMPOLINE_TEMPLATE in sysdeps/hppa/dl-machine.h.  If
   the trampoline template is changed, the list must be appropriately
   updated.  The offset of -4 allows for a magic branch at the start of
   the template should it be necessary to change the current branch
   position.  */
#define NOFFSETS 2
static int fixup_branch_offset[NOFFSETS] = { -4, 32 };

#define GET_FIELD(X, FROM, TO) \
  ((X) >> (31 - (TO)) & ((1 << ((TO) - (FROM) + 1)) - 1))
#define SIGN_EXTEND(VAL,BITS) \
  ((int) ((VAL) >> ((BITS) - 1) ? ((unsigned)(-1) << (BITS)) | (VAL) : (VAL)))

struct link_map;
typedef int (*fptr_t) (void);
typedef int (*fixup_t) (struct link_map *, unsigned int);
extern unsigned int _GLOBAL_OFFSET_TABLE_;

static inline int
_dl_read_access_allowed (unsigned int addr)
{
  int result;

  asm ("proberi (%1),3,%0" : "=r" (result) : "r" (addr) : );

  return result;
}

#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Warray-bounds"

/* __canonicalize_funcptr_for_compare must be hidden so that it is not
   placed in the dynamic symbol table.  Like millicode functions, it
   must be linked into all binaries in order access the got table of
   that binary.  However, we don't use the millicode calling convention
   and the routine must be a normal function so that it can be compiled
   as pic code.  */
unsigned int __canonicalize_funcptr_for_compare (fptr_t)
      __attribute__ ((visibility ("hidden")));

unsigned int
__canonicalize_funcptr_for_compare (fptr_t fptr)
{
  static unsigned int fixup_plabel[2] __attribute__((used));
  fixup_t fixup;
  volatile unsigned int *plabel;
  unsigned int *got, *iptr, reloc_offset;
  int i;

  /* -1 and page 0 are special.  -1 is used in crtend to mark the end of
     a list of function pointers.  Also return immediately if the plabel
     bit is not set in the function pointer.  In this case, the function
     pointer points directly to the function.  */
  if ((int) fptr == -1 || (unsigned int) fptr < 4096 || !((int) fptr & 2))
    return (unsigned int) fptr;

  /* The function pointer points to a function descriptor (plabel).  If
     the plabel hasn't been resolved, the first word of the plabel points
     to the entry of the PLT stub just before the global offset table.
     The second word in the plabel contains the relocation offset for the
     function.  */
  plabel = (volatile unsigned int *) ((unsigned int) fptr & ~3);
  if (!_dl_read_access_allowed ((unsigned int)plabel))
    return (unsigned int) fptr;

  /* Load first word of candidate descriptor.  It should be a pointer
     with word alignment and point to memory that can be read.  */
  got = (unsigned int *) plabel[0];
  if (((unsigned int) got & 3) != 0
      || !_dl_read_access_allowed ((unsigned int)got))
    return (unsigned int) fptr;

  /* We need to load the relocation offset before the function address.  */
  reloc_offset = plabel[1];
  __sync_synchronize();
  got = (unsigned int *) (plabel[0] + GOT_FROM_PLT_STUB);

  /* Return the address of the function if the plabel has been resolved.  */
  if (got !=  &_GLOBAL_OFFSET_TABLE_)
    return plabel[0];

  /* Find the first "bl" branch in the offset search list.  This is a
     call to _dl_fixup or a magic branch to fixup at the beginning of the
     trampoline template.  The fixup function does the actual runtime
     resolution of function descriptors.  We only look for "bl" branches
     with a 17-bit pc-relative displacement.  */
  for (i = 0; i < NOFFSETS; i++)
    {
      iptr = (unsigned int *) (got[-2] + fixup_branch_offset[i]);
      if ((*iptr & 0xfc00e000) == 0xe8000000)
	break;
    }

  /* This should not happen... */
  if (i == NOFFSETS)
    return ~0;

  /* Extract the 17-bit displacement from the instruction.  */
  iptr += SIGN_EXTEND (GET_FIELD (*iptr, 19, 28) |
		       GET_FIELD (*iptr, 29, 29) << 10 |
		       GET_FIELD (*iptr, 11, 15) << 11 |
		       GET_FIELD (*iptr, 31, 31) << 16, 17);

  /* Build a plabel for an indirect call to _dl_fixup.  */
  fixup_plabel[0] = (unsigned int) iptr + 8;	/* address of fixup */
  fixup_plabel[1] = got[-1];			/* ltp for fixup */
  fixup = (fixup_t) ((int) fixup_plabel | 2);

  /* Call fixup to resolve the function address.  got[1] contains the
     link_map pointer and plabel[1] the relocation offset.  */
  fixup ((struct link_map *) got[1], reloc_offset);

  return plabel[0];
}

#pragma GCC diagnostic pop
