svn commit: trunk/uClibc/ldso/ldso/arm

kraj at uclibc.org kraj at uclibc.org
Tue Nov 21 02:50:42 UTC 2006


Author: kraj
Date: 2006-11-20 18:50:42 -0800 (Mon, 20 Nov 2006)
New Revision: 16599

Log:
Use constant pool instead of and adr 
instruction in unoptimized builds and thumb: thanks Paul Brook

Modified:
   trunk/uClibc/ldso/ldso/arm/dl-sysdep.h


Changeset:
Modified: trunk/uClibc/ldso/ldso/arm/dl-sysdep.h
===================================================================
--- trunk/uClibc/ldso/ldso/arm/dl-sysdep.h	2006-11-21 00:55:46 UTC (rev 16598)
+++ trunk/uClibc/ldso/ldso/arm/dl-sysdep.h	2006-11-21 02:50:42 UTC (rev 16599)
@@ -110,24 +110,20 @@
 	extern void __dl_start asm ("_dl_start");
 	Elf32_Addr got_addr = (Elf32_Addr) &__dl_start;
 	Elf32_Addr pcrel_addr;
-#if !defined __thumb__
+#if defined __OPTIMIZE__ && !defined __thumb__
 	asm ("adr %0, _dl_start" : "=r" (pcrel_addr));
 #else
+	/* A simple adr does not work in Thumb mode because the offset is
+	   negative, and for debug builds may be too large.  */
 	int tmp;
-	/* The above adr will not work on thumb because it
-	 * is negative.  The only safe way is to temporarily
-	 * swap to arm.
-	 */
-	asm(   ".align	2\n"
-	"	bx	pc\n"
-	"	nop	\n"
-	"	.arm	\n"
-	"	adr	%0, _dl_start\n"
-	"	.align	2\n"
-	"	orr	%1, pc, #1\n"
-	"	bx	%1\n"
-	"	.force_thumb\n"
-	: "=r" (pcrel_addr), "=&r" (tmp));
+	asm ("adr %1, 1f\n\t"
+		 "ldr %0, [%1]\n\t"
+		 "add %0, %0, %1\n\t"
+		 "b 2f\n\t"
+		 ".align 2\n\t"
+		 "1: .word _dl_start - 1b\n\t"
+		 "2:"
+		 : "=r" (pcrel_addr), "=r" (tmp));
 #endif
 	return pcrel_addr - got_addr;
 }




More information about the uClibc-cvs mailing list