=?UTF-8?Q?Andr=C3=A9=20Hentschel=20?=: ntdll: Implement IMAGE_REL_BASED_THUMB_MOV32 relocation on ARM.

Alexandre Julliard julliard at winehq.org
Mon Jan 21 13:52:23 CST 2013


Module: wine
Branch: master
Commit: 0993f8bb7b138063d6202e2ce4a4a61e4b9fc537
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=0993f8bb7b138063d6202e2ce4a4a61e4b9fc537

Author: André Hentschel <nerv at dawncrow.de>
Date:   Sun Jan 20 18:02:10 2013 +0100

ntdll: Implement IMAGE_REL_BASED_THUMB_MOV32 relocation on ARM.

---

 dlls/ntdll/loader.c |   38 ++++++++++++++++++++++++++++++++++++++
 include/winnt.h     |    2 ++
 2 files changed, 40 insertions(+), 0 deletions(-)

diff --git a/dlls/ntdll/loader.c b/dlls/ntdll/loader.c
index fd63e08..28ed9f4 100644
--- a/dlls/ntdll/loader.c
+++ b/dlls/ntdll/loader.c
@@ -2175,6 +2175,44 @@ IMAGE_BASE_RELOCATION * WINAPI LdrProcessRelocationBlock( void *page, UINT count
         case IMAGE_REL_BASED_DIR64:
             *(INT_PTR *)((char *)page + offset) += delta;
             break;
+#elif defined(__arm__)
+        case IMAGE_REL_BASED_THUMB_MOV32:
+        {
+            DWORD inst = *(INT_PTR *)((char *)page + offset);
+            DWORD imm16 = ((inst << 1) & 0x0800) + ((inst << 12) & 0xf000) +
+                          ((inst >> 20) & 0x0700) + ((inst >> 16) & 0x000f);
+
+            if ((inst & 0x8000fbf0) != 0x0000f240)
+                ERR("wrong Thumb2 instruction %08x, expected MOVW\n", inst);
+
+            imm16 += LOWORD(delta);
+            if (imm16 > 0xffff)
+                ERR("resulting immediate value won't fit: %08x\n", imm16);
+            *(INT_PTR *)((char *)page + offset) = (inst & 0x8f00fbf0) + ((imm16 >> 1) & 0x0400) +
+                                                  ((imm16 >> 12) & 0x000f) +
+                                                  ((imm16 << 20) & 0x70000000) +
+                                                  ((imm16 << 16) & 0x0f0000);
+
+            if (delta > 0xffff)
+            {
+                inst = *(INT_PTR *)((char *)page + offset + 4);
+                imm16 = ((inst << 1) & 0x0800) + ((inst << 12) & 0xf000) +
+                        ((inst >> 20) & 0x0700) + ((inst >> 16) & 0x000f);
+
+                if ((inst & 0x8000fbf0) != 0x0000f2c0)
+                    ERR("wrong Thumb2 instruction %08x, expected MOVT\n", inst);
+
+                imm16 += HIWORD(delta);
+                if (imm16 > 0xffff)
+                    ERR("resulting immediate value won't fit: %08x\n", imm16);
+                *(INT_PTR *)((char *)page + offset + 4) = (inst & 0x8f00fbf0) +
+                                                          ((imm16 >> 1) & 0x0400) +
+                                                          ((imm16 >> 12) & 0x000f) +
+                                                          ((imm16 << 20) & 0x70000000) +
+                                                          ((imm16 << 16) & 0x0f0000);
+            }
+        }
+            break;
 #endif
         default:
             FIXME("Unknown/unsupported fixup type %x.\n", type);
diff --git a/include/winnt.h b/include/winnt.h
index f2bf990..d4e5cb4 100644
--- a/include/winnt.h
+++ b/include/winnt.h
@@ -3101,9 +3101,11 @@ typedef struct _IMAGE_RELOCATION
 #define IMAGE_REL_BASED_HIGHADJ			4
 #define IMAGE_REL_BASED_MIPS_JMPADDR		5
 #define IMAGE_REL_BASED_ARM_MOV32A		5 /* yes, 5 too */
+#define IMAGE_REL_BASED_ARM_MOV32		5 /* yes, 5 too */
 #define IMAGE_REL_BASED_SECTION			6
 #define	IMAGE_REL_BASED_REL			7
 #define	IMAGE_REL_BASED_ARM_MOV32T		7 /* yes, 7 too */
+#define IMAGE_REL_BASED_THUMB_MOV32		7 /* yes, 7 too */
 #define IMAGE_REL_BASED_MIPS_JMPADDR16		9
 #define IMAGE_REL_BASED_IA64_IMM64		9 /* yes, 9 too */
 #define IMAGE_REL_BASED_DIR64			10




More information about the wine-cvs mailing list