Author: gonzo
Date: Sat Feb 11 00:54:57 2012
New Revision: 231491
URL: http://svn.freebsd.org/changeset/base/231491

Log:
  Add handlers for TLS-related relocation entries

Modified:
  head/libexec/rtld-elf/mips/reloc.c
  head/libexec/rtld-elf/mips/rtld_machdep.h

Modified: head/libexec/rtld-elf/mips/reloc.c
==============================================================================
--- head/libexec/rtld-elf/mips/reloc.c  Sat Feb 11 00:54:24 2012        
(r231490)
+++ head/libexec/rtld-elf/mips/reloc.c  Sat Feb 11 00:54:57 2012        
(r231491)
@@ -446,6 +446,89 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry 
                        break;
                }
 
+#ifdef __mips_n64
+               case R_TYPE(TLS_DTPMOD64):
+#else
+               case R_TYPE(TLS_DTPMOD32): 
+#endif
+               {
+
+                       const size_t rlen = sizeof(Elf_Addr);
+                       Elf_Addr old = load_ptr(where, rlen);
+                       Elf_Addr val = old;
+
+                       def = find_symdef(r_symndx, obj, &defobj, false, NULL,
+                               lockstate);
+                       if (def == NULL)
+                               return -1;
+
+                       val += (Elf_Addr)defobj->tlsindex;
+
+                       store_ptr(where, val, rlen);
+                       dbg("DTPMOD %s in %s %p --> %p in %s",
+                           obj->strtab + obj->symtab[r_symndx].st_name,
+                           obj->path, (void *)old, (void*)val, defobj->path);
+                       break;
+               }
+
+#ifdef __mips_n64
+               case R_TYPE(TLS_DTPREL64):
+#else
+               case R_TYPE(TLS_DTPREL32):
+#endif
+               {
+                       const size_t rlen = sizeof(Elf_Addr);
+                       Elf_Addr old = load_ptr(where, rlen);
+                       Elf_Addr val = old;
+
+                       def = find_symdef(r_symndx, obj, &defobj, false, NULL,
+                               lockstate);
+                       if (def == NULL)
+                               return -1;
+
+                       if (!defobj->tls_done && allocate_tls_offset(obj))
+                               return -1;
+
+                       val += (Elf_Addr)def->st_value - TLS_DTP_OFFSET;
+                       store_ptr(where, val, rlen);
+
+                       dbg("DTPREL %s in %s %p --> %p in %s",
+                           obj->strtab + obj->symtab[r_symndx].st_name,
+                           obj->path, (void*)old, (void *)val, defobj->path);
+                       break;
+               }
+
+#ifdef __mips_n64
+               case R_TYPE(TLS_TPREL64):
+#else
+               case R_TYPE(TLS_TPREL32):
+#endif
+               {
+                       const size_t rlen = sizeof(Elf_Addr);
+                       Elf_Addr old = load_ptr(where, rlen);
+                       Elf_Addr val = old;
+
+                       def = find_symdef(r_symndx, obj, &defobj, false, NULL,
+                               lockstate);
+
+                       if (def == NULL)
+                               return -1;
+
+                       if (!defobj->tls_done && allocate_tls_offset(obj))
+                               return -1;
+
+                       val += (Elf_Addr)(def->st_value + defobj->tlsoffset
+                           - TLS_TP_OFFSET - TLS_TCB_SIZE);
+                       store_ptr(where, val, rlen);
+
+                       dbg("TPREL %s in %s %p --> %p in %s",
+                           obj->strtab + obj->symtab[r_symndx].st_name,
+                           obj->path, (void*)old, (void *)val, defobj->path);
+                       break;
+               }
+
+
+
                default:
                        dbg("sym = %lu, type = %lu, offset = %p, "
                            "contents = %p, symbol = %s",
@@ -554,7 +637,7 @@ __tls_get_addr(tls_index* ti)
        sysarch(MIPS_GET_TLS, &tls);
 
        p = tls_get_addr_common((Elf_Addr**)((Elf_Addr)tls - TLS_TP_OFFSET 
-           - TLS_TCB_SIZE), ti->ti_module, ti->ti_offset);
+           - TLS_TCB_SIZE), ti->ti_module, ti->ti_offset + TLS_DTP_OFFSET);
 
-       return (p + TLS_DTV_OFFSET);
+       return (p);
 }

Modified: head/libexec/rtld-elf/mips/rtld_machdep.h
==============================================================================
--- head/libexec/rtld-elf/mips/rtld_machdep.h   Sat Feb 11 00:54:24 2012        
(r231490)
+++ head/libexec/rtld-elf/mips/rtld_machdep.h   Sat Feb 11 00:54:57 2012        
(r231491)
@@ -53,7 +53,8 @@ Elf_Addr reloc_jmpslot(Elf_Addr *where, 
  */
 
 #define TLS_TP_OFFSET  0x7000
-#define TLS_DTV_OFFSET 0x8000
+#define TLS_DTP_OFFSET 0x8000
+
 #ifdef __mips_n64
 #define TLS_TCB_SIZE   16
 #else
_______________________________________________
svn-src-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"

Reply via email to