about summary refs log tree commit diff
path: root/ports/sysdeps/ia64
diff options
context:
space:
mode:
authorMike Frysinger <vapier@gentoo.org>2013-03-10 11:49:29 +0000
committerMike Frysinger <vapier@gentoo.org>2013-03-12 06:00:05 -0400
commitc5abd7ce01539dc5224f7533c9d1048900992317 (patch)
treecca3fe48d201c7078fd530f55913ce9ce01eec83 /ports/sysdeps/ia64
parentb7845b638818f32401070f00a61d3b42595ab223 (diff)
downloadglibc-c5abd7ce01539dc5224f7533c9d1048900992317.tar.gz
glibc-c5abd7ce01539dc5224f7533c9d1048900992317.tar.xz
glibc-c5abd7ce01539dc5224f7533c9d1048900992317.zip
ia64: fix strict aliasing warnings with func descriptors
Function pointers on ia64 are like parisc -- they're plabels.  While
the parisc port enjoys a gcc builtin for extracting the address here,
ia64 has no such luck.

Casting & dereferencing in one go triggers a strict aliasing warning.
Use a union to fix that.

Signed-off-by: Mike Frysinger <vapier@gentoo.org>
Diffstat (limited to 'ports/sysdeps/ia64')
-rw-r--r--ports/sysdeps/ia64/dl-fptr.h10
-rw-r--r--ports/sysdeps/ia64/dl-machine.h4
-rw-r--r--ports/sysdeps/ia64/entry.h5
3 files changed, 16 insertions, 3 deletions
diff --git a/ports/sysdeps/ia64/dl-fptr.h b/ports/sysdeps/ia64/dl-fptr.h
index c2bef6c288..447c098aff 100644
--- a/ports/sysdeps/ia64/dl-fptr.h
+++ b/ports/sysdeps/ia64/dl-fptr.h
@@ -32,4 +32,14 @@
 #define ELF_MACHINE_LOAD_ADDRESS(var, symbol)	\
   asm ("movl %0 = @gprel (" #symbol ");; add %0 = %0, gp" : "=&r" (var));
 
+/* We don't have a gcc helper to extract the plabel info.  */
+#define ELF_PTR_TO_FDESC(ptr) \
+  ({ union { \
+       void *_ptr; \
+       struct fdesc *_fdesc; \
+     } _u; \
+     _u._ptr = ptr; \
+     _u._fdesc; \
+  })
+
 #endif /* !dl_ia64_fptr_h */
diff --git a/ports/sysdeps/ia64/dl-machine.h b/ports/sysdeps/ia64/dl-machine.h
index 2eb80d752f..dd469d7a73 100644
--- a/ports/sysdeps/ia64/dl-machine.h
+++ b/ports/sysdeps/ia64/dl-machine.h
@@ -119,7 +119,7 @@ elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
 
       /* This function will be called to perform the relocation.  */
       if (!profile)
-	doit = (Elf64_Addr) ((struct fdesc *) &_dl_runtime_resolve)->ip;
+	doit = (Elf64_Addr) ELF_PTR_TO_FDESC (&_dl_runtime_resolve)->ip;
       else
 	{
 	  if (GLRO(dl_profile) != NULL
@@ -129,7 +129,7 @@ elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
 		 want profiling and the timers are started.  */
 	      GL(dl_profile_map) = l;
 	    }
-	  doit = (Elf64_Addr) ((struct fdesc *) &_dl_runtime_profile)->ip;
+	  doit = (Elf64_Addr) ELF_PTR_TO_FDESC (&_dl_runtime_profile)->ip;
 	}
 
       reserve[1] = doit;
diff --git a/ports/sysdeps/ia64/entry.h b/ports/sysdeps/ia64/entry.h
index b93e1b6a57..e11b49fc53 100644
--- a/ports/sysdeps/ia64/entry.h
+++ b/ports/sysdeps/ia64/entry.h
@@ -1,10 +1,13 @@
+#include <link.h>
+#include <dl-fptr.h>
+
 #ifndef __ASSEMBLY__
 extern void _start (void);
 #endif
 
 /* The function's entry point is stored in the first word of the
    function descriptor (plabel) of _start().  */
-#define ENTRY_POINT (((long int *) _start)[0])
+#define ENTRY_POINT ELF_PTR_TO_FDESC (_start)->ip
 
 /* We have to provide a special declaration.  */
 #define ENTRY_POINT_DECL(class) class void _start (void);