Skip to content

Commit 67fee0c

Browse files
committed
Backport support for hidden symbols for windows to 8.10
1 parent 96efeea commit 67fee0c

File tree

3 files changed

+385
-0
lines changed

3 files changed

+385
-0
lines changed

overlays/bootstrap.nix

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -291,6 +291,8 @@ in {
291291
# ++ final.lib.optional (versionAtLeast "9.6" && versionLessThan "9.9" && final.stdenv.targetPlatform.isMusl) ./patches/ghc/ghc-9.6-0005-Better-interpreter-debugging.-Needs-ghcidladdr.patch
292292
++ final.lib.optional (versionAtLeast "9.6" && versionLessThan "9.9" && (final.stdenv.targetPlatform.isWindows || final.stdenv.targetPlatform.isMusl)) ./patches/ghc/ghc-9.6-0006-Adds-support-for-Hidden-symbols.patch
293293
++ final.lib.optional (versionAtLeast "9.6" && versionLessThan "9.9" && final.stdenv.targetPlatform.isMusl) ./patches/ghc/ghc-9.6-0007-fixup-Better-pool-alignment.-We-still-hardcode-secti.patch
294+
++ final.lib.optional (versionAtLeast "8.10" && versionLessThan "8.11" && (final.stdenv.targetPlatform.isWindows)) ./patches/ghc/ghc-8.10-0006-Adds-support-for-Hidden-symbols.patch
295+
++ final.lib.optional (versionAtLeast "8.10" && versionLessThan "8.11" && (final.stdenv.targetPlatform.isWindows)) ./patches/ghc/ghc-8.10-0006-Adds-support-for-Hidden-symbols-2.patch
294296
;
295297
in ({
296298
ghc865 = final.callPackage ../compiler/ghc (traceWarnOld "8.6" {
Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
diff --git a/rts/Linker.c b/rts/Linker.c
2+
index 5b3421d..7a6e3b6 100644
3+
--- a/rts/Linker.c
4+
+++ b/rts/Linker.c
5+
@@ -267,10 +267,12 @@ int ghciInsertSymbolTable(
6+
HashTable *table,
7+
const SymbolName* key,
8+
SymbolAddr* data,
9+
- HsBool weak,
10+
- HsBool hidden,
11+
+ int flags,
12+
ObjectCode *owner)
13+
{
14+
+ HsBool weak = flags & 1;
15+
+ HsBool hidden = flags & 2;
16+
+
17+
RtsSymbolInfo *pinfo = lookupStrHashTable(table, key);
18+
if (!pinfo) /* new entry */
19+
{
20+
@@ -352,7 +354,6 @@ int ghciInsertSymbolTable(
21+
pinfo->hidden = hidden;
22+
return 1;
23+
}
24+
-
25+
pathchar* archiveName = NULL;
26+
debugBelch(
27+
"GHC runtime linker: fatal error: I found a duplicate definition for symbol\n"
28+
@@ -467,7 +468,7 @@ initLinker_ (int retain_cafs)
29+
for (sym = rtsSyms; sym->lbl != NULL; sym++) {
30+
if (! ghciInsertSymbolTable(WSTR("(GHCi built-in symbols)"),
31+
symhash, sym->lbl, sym->addr,
32+
- sym->weak, HS_BOOL_FALSE, NULL)) {
33+
+ sym->weak | (HS_BOOL_FALSE << 1), NULL)) {
34+
barf("ghciInsertSymbolTable failed");
35+
}
36+
IF_DEBUG(linker, debugBelch("initLinker: inserting rts symbol %s, %p\n", sym->lbl, sym->addr));
37+
@@ -479,7 +480,7 @@ initLinker_ (int retain_cafs)
38+
use an arbitrary (hopefully unique) address here.
39+
*/
40+
if (! ghciInsertSymbolTable(WSTR("(GHCi special symbols)"),
41+
- symhash, "__dso_handle", (void *)0x12345687, HS_BOOL_FALSE, HS_BOOL_FALSE, NULL)) {
42+
+ symhash, "__dso_handle", (void *)0x12345687, HS_BOOL_FALSE | (HS_BOOL_FALSE << 1), NULL)) {
43+
barf("ghciInsertSymbolTable failed");
44+
}
45+
46+
@@ -487,7 +488,7 @@ initLinker_ (int retain_cafs)
47+
if (! ghciInsertSymbolTable(WSTR("(GHCi built-in symbols)"), symhash,
48+
MAYBE_LEADING_UNDERSCORE_STR("newCAF"),
49+
retain_cafs ? newRetainedCAF : newGCdCAF,
50+
- HS_BOOL_FALSE, HS_BOOL_FALSE, NULL)) {
51+
+ HS_BOOL_FALSE | (HS_BOOL_FALSE << 1), NULL)) {
52+
barf("ghciInsertSymbolTable failed");
53+
}
54+
55+
@@ -860,8 +861,8 @@ HsBool removeLibrarySearchPath(HsPtr dll_path_index)
56+
*/
57+
HsInt insertSymbol(pathchar* obj_name, SymbolName* key, SymbolAddr* data)
58+
{
59+
- return ghciInsertSymbolTable(obj_name, symhash, key, data, HS_BOOL_FALSE,
60+
- HS_BOOL_FALSE, NULL);
61+
+ return ghciInsertSymbolTable(obj_name, symhash, key, data,
62+
+ HS_BOOL_FALSE | (HS_BOOL_FALSE << 1), NULL);
63+
}
64+
65+
/* -----------------------------------------------------------------------------
66+
@@ -1715,8 +1716,8 @@ int ocTryLoad (ObjectCode* oc) {
67+
if ( symbol.name
68+
&& !ghciInsertSymbolTable(oc->fileName, symhash, symbol.name,
69+
symbol.addr,
70+
- isSymbolWeak(oc, symbol.name),
71+
- HS_BOOL_FALSE, oc)) {
72+
+ isSymbolWeak(oc, symbol.name) | (HS_BOOL_FALSE << 1),
73+
+ oc)) {
74+
return 0;
75+
}
76+
}
77+
diff --git a/rts/LinkerInternals.h b/rts/LinkerInternals.h
78+
index 1bc082c..b40d14e 100644
79+
--- a/rts/LinkerInternals.h
80+
+++ b/rts/LinkerInternals.h
81+
@@ -334,8 +334,7 @@ int ghciInsertSymbolTable(
82+
HashTable *table,
83+
const SymbolName* key,
84+
SymbolAddr* data,
85+
- HsBool weak,
86+
- HsBool hidden,
87+
+ int flags,
88+
ObjectCode *owner);
89+
90+
/* Lock-free version of lookupSymbol. When 'dependent' is not NULL, adds it as a
91+
diff --git a/rts/linker/Elf.c b/rts/linker/Elf.c
92+
index 4a53687..e166e20 100644
93+
--- a/rts/linker/Elf.c
94+
+++ b/rts/linker/Elf.c
95+
@@ -976,8 +976,8 @@ ocGetNames_ELF ( ObjectCode* oc )
96+
setWeakSymbol(oc, nm);
97+
}
98+
if (!ghciInsertSymbolTable(oc->fileName, symhash,
99+
- nm, symbol->addr, isWeak,
100+
- ELF_ST_VISIBILITY(symbol->elf_sym->st_other) == STV_HIDDEN,
101+
+ nm, symbol->addr,
102+
+ isWeak | ((ELF_ST_VISIBILITY(symbol->elf_sym->st_other) == STV_HIDDEN) << 1),
103+
oc)
104+
) {
105+
goto fail;
106+
diff --git a/rts/linker/MachO.c b/rts/linker/MachO.c
107+
index 00b0dce..d633699 100644
108+
--- a/rts/linker/MachO.c
109+
+++ b/rts/linker/MachO.c
110+
@@ -1336,7 +1336,7 @@ ocGetNames_MachO(ObjectCode* oc)
111+
, symhash
112+
, nm
113+
, addr
114+
- , HS_BOOL_FALSE
115+
+ , HS_BOOL_FALSE | (HS_BOOL_FALSE << 1)
116+
, oc);
117+
118+
oc->symbols[curSymbol].name = nm;
119+
@@ -1376,7 +1376,7 @@ ocGetNames_MachO(ObjectCode* oc)
120+
121+
IF_DEBUG(linker, debugBelch("ocGetNames_MachO: inserting common symbol: %s\n", nm));
122+
ghciInsertSymbolTable(oc->fileName, symhash, nm,
123+
- (void*)commonCounter, HS_BOOL_FALSE, oc);
124+
+ (void*)commonCounter, HS_BOOL_FALSE | (HS_BOOL_FALSE << 1), oc);
125+
oc->symbols[curSymbol].name = nm;
126+
oc->symbols[curSymbol].addr = oc->info->macho_symbols[i].addr;
127+
curSymbol++;
128+
diff --git a/rts/linker/PEi386.c b/rts/linker/PEi386.c
129+
index 841faa8..d847d13 100644
130+
--- a/rts/linker/PEi386.c
131+
+++ b/rts/linker/PEi386.c
132+
@@ -292,7 +292,7 @@ const void* __rts_iob_func = (void*)&__acrt_iob_func;
133+
void initLinker_PEi386()
134+
{
135+
if (!ghciInsertSymbolTable(WSTR("(GHCi/Ld special symbols)"),
136+
- symhash, "__image_base__", __image_base, HS_BOOL_TRUE, HS_BOOL_FALSE, NULL)) {
137+
+ symhash, "__image_base__", __image_base, HS_BOOL_TRUE | (HS_BOOL_FALSE << 1), NULL)) {
138+
barf("ghciInsertSymbolTable failed");
139+
}
140+
141+
@@ -1093,7 +1093,7 @@ lookupSymbolInDLLs ( const SymbolName* lbl )
142+
/* debugBelch("look in %ls for %s\n", o_dll->name, lbl); */
143+
144+
if (wcsncmp(o_dll->name,WSTR("ucrtbase.dll"),wcslen(WSTR("ucrtbase.dll"))) == 0) {
145+
- IF_DEBUG(linker, debugBelch("warning: ignoring %s\n", o_dll->name));
146+
+ IF_DEBUG(linker, debugBelch("warning: ignoring %" PATH_FMT "\n", o_dll->name));
147+
continue;
148+
}
149+
150+
@@ -1541,7 +1541,7 @@ ocGetNames_PEi386 ( ObjectCode* oc )
151+
sname = strdup (sname);
152+
addr = strdup (addr);
153+
if (!ghciInsertSymbolTable(oc->fileName, symhash, sname,
154+
- addr, false, HS_BOOL_FALSE, oc)) {
155+
+ addr, HS_BOOL_FALSE | (HS_BOOL_FALSE << 1), oc)) {
156+
releaseOcInfo (oc);
157+
stgFree (oc->image);
158+
oc->image = NULL;
159+
@@ -1759,8 +1759,8 @@ ocGetNames_PEi386 ( ObjectCode* oc )
160+
stgFree(tmp);
161+
sname = strdup (sname);
162+
if (!ghciInsertSymbolTable(oc->fileName, symhash, sname,
163+
- addr, false,
164+
- section->info->props & IMAGE_SCN_LNK_COMDAT,
165+
+ addr,
166+
+ HS_BOOL_FALSE | ((secNumber == IMAGE_SYM_UNDEFINED) << 1),
167+
oc))
168+
return false;
169+
170+
@@ -1779,8 +1779,7 @@ ocGetNames_PEi386 ( ObjectCode* oc )
171+
setWeakSymbol(oc, sname);
172+
}
173+
if (! ghciInsertSymbolTable(oc->fileName, symhash, sname, addr,
174+
- isWeak,
175+
- section->info->props & IMAGE_SCN_LNK_COMDAT,
176+
+ isWeak | ((secNumber == IMAGE_SYM_UNDEFINED) << 1),
177+
oc))
178+
return false;
179+
} else {
Lines changed: 204 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,204 @@
1+
diff --git a/rts/Linker.c b/rts/Linker.c
2+
index 10b0764..587f16a 100644
3+
--- a/rts/Linker.c
4+
+++ b/rts/Linker.c
5+
@@ -268,6 +268,7 @@ int ghciInsertSymbolTable(
6+
const SymbolName* key,
7+
SymbolAddr* data,
8+
HsBool weak,
9+
+ HsBool hidden,
10+
ObjectCode *owner)
11+
{
12+
RtsSymbolInfo *pinfo = lookupStrHashTable(table, key);
13+
@@ -277,6 +278,7 @@ int ghciInsertSymbolTable(
14+
pinfo->value = data;
15+
pinfo->owner = owner;
16+
pinfo->weak = weak;
17+
+ pinfo->hidden = hidden;
18+
insertStrHashTable(table, key, pinfo);
19+
return 1;
20+
}
21+
@@ -340,11 +342,23 @@ int ghciInsertSymbolTable(
22+
call this function again to trigger the duplicate error. */
23+
return 1;
24+
}
25+
+ else if(pinfo->hidden && !hidden)
26+
+ {
27+
+ /* The existing symbol is hidden, let's replace it */
28+
+ pinfo->value = data;
29+
+ pinfo->owner = owner;
30+
+ pinfo->weak = weak;
31+
+
32+
+ pinfo->hidden = hidden;
33+
+ return 1;
34+
+ }
35+
36+
pathchar* archiveName = NULL;
37+
debugBelch(
38+
"GHC runtime linker: fatal error: I found a duplicate definition for symbol\n"
39+
" %s\n"
40+
+ " new symbol is hidden: %d\n"
41+
+ " old symbol is hidden: %d\n"
42+
"whilst processing object file\n"
43+
" %" PATH_FMT "\n"
44+
"The symbol was previously defined in\n"
45+
@@ -355,6 +369,8 @@ int ghciInsertSymbolTable(
46+
" * An incorrect `package.conf' entry, causing some object to be\n"
47+
" loaded twice.\n",
48+
(char*)key,
49+
+ hidden ? 1 : 0,
50+
+ pinfo->hidden ? 1 : 0,
51+
obj_name,
52+
pinfo->owner == NULL ? WSTR("(GHCi built-in symbols)") :
53+
pinfo->owner->archiveMemberName ? archiveName = mkPath(pinfo->owner->archiveMemberName)
54+
@@ -451,7 +467,7 @@ initLinker_ (int retain_cafs)
55+
for (sym = rtsSyms; sym->lbl != NULL; sym++) {
56+
if (! ghciInsertSymbolTable(WSTR("(GHCi built-in symbols)"),
57+
symhash, sym->lbl, sym->addr,
58+
- sym->weak, NULL)) {
59+
+ sym->weak, HS_BOOL_FALSE, NULL)) {
60+
barf("ghciInsertSymbolTable failed");
61+
}
62+
IF_DEBUG(linker, debugBelch("initLinker: inserting rts symbol %s, %p\n", sym->lbl, sym->addr));
63+
@@ -463,7 +479,7 @@ initLinker_ (int retain_cafs)
64+
use an arbitrary (hopefully unique) address here.
65+
*/
66+
if (! ghciInsertSymbolTable(WSTR("(GHCi special symbols)"),
67+
- symhash, "__dso_handle", (void *)0x12345687, HS_BOOL_FALSE, NULL)) {
68+
+ symhash, "__dso_handle", (void *)0x12345687, HS_BOOL_FALSE, HS_BOOL_FALSE, NULL)) {
69+
barf("ghciInsertSymbolTable failed");
70+
}
71+
72+
@@ -471,7 +487,7 @@ initLinker_ (int retain_cafs)
73+
if (! ghciInsertSymbolTable(WSTR("(GHCi built-in symbols)"), symhash,
74+
MAYBE_LEADING_UNDERSCORE_STR("newCAF"),
75+
retain_cafs ? newRetainedCAF : newGCdCAF,
76+
- HS_BOOL_FALSE, NULL)) {
77+
+ HS_BOOL_FALSE, HS_BOOL_FALSE, NULL)) {
78+
barf("ghciInsertSymbolTable failed");
79+
}
80+
81+
@@ -845,7 +861,7 @@ HsBool removeLibrarySearchPath(HsPtr dll_path_index)
82+
HsInt insertSymbol(pathchar* obj_name, SymbolName* key, SymbolAddr* data)
83+
{
84+
return ghciInsertSymbolTable(obj_name, symhash, key, data, HS_BOOL_FALSE,
85+
- NULL);
86+
+ HS_BOOL_FALSE, NULL);
87+
}
88+
89+
/* -----------------------------------------------------------------------------
90+
@@ -1699,7 +1715,8 @@ int ocTryLoad (ObjectCode* oc) {
91+
if ( symbol.name
92+
&& !ghciInsertSymbolTable(oc->fileName, symhash, symbol.name,
93+
symbol.addr,
94+
- isSymbolWeak(oc, symbol.name), oc)) {
95+
+ isSymbolWeak(oc, symbol.name),
96+
+ HS_BOOL_FALSE, oc)) {
97+
return 0;
98+
}
99+
}
100+
diff --git a/rts/LinkerInternals.h b/rts/LinkerInternals.h
101+
index f326a84..1bc082c 100644
102+
--- a/rts/LinkerInternals.h
103+
+++ b/rts/LinkerInternals.h
104+
@@ -306,6 +306,7 @@ typedef struct _RtsSymbolInfo {
105+
SymbolAddr* value;
106+
ObjectCode *owner;
107+
HsBool weak;
108+
+ HsBool hidden;
109+
} RtsSymbolInfo;
110+
111+
void exitLinker( void );
112+
@@ -334,6 +335,7 @@ int ghciInsertSymbolTable(
113+
const SymbolName* key,
114+
SymbolAddr* data,
115+
HsBool weak,
116+
+ HsBool hidden,
117+
ObjectCode *owner);
118+
119+
/* Lock-free version of lookupSymbol. When 'dependent' is not NULL, adds it as a
120+
diff --git a/rts/linker/Elf.c b/rts/linker/Elf.c
121+
index fdfe87a..4a53687 100644
122+
--- a/rts/linker/Elf.c
123+
+++ b/rts/linker/Elf.c
124+
@@ -976,7 +976,9 @@ ocGetNames_ELF ( ObjectCode* oc )
125+
setWeakSymbol(oc, nm);
126+
}
127+
if (!ghciInsertSymbolTable(oc->fileName, symhash,
128+
- nm, symbol->addr, isWeak, oc)
129+
+ nm, symbol->addr, isWeak,
130+
+ ELF_ST_VISIBILITY(symbol->elf_sym->st_other) == STV_HIDDEN,
131+
+ oc)
132+
) {
133+
goto fail;
134+
}
135+
diff --git a/rts/linker/ElfTypes.h b/rts/linker/ElfTypes.h
136+
index e5333d7..0a8e44a 100644
137+
--- a/rts/linker/ElfTypes.h
138+
+++ b/rts/linker/ElfTypes.h
139+
@@ -32,6 +32,9 @@
140+
#define Elf_Sym Elf64_Sym
141+
#define Elf_Rel Elf64_Rel
142+
#define Elf_Rela Elf64_Rela
143+
+#if !defined(ELF_ST_VISIBILITY)
144+
+#define ELF_ST_VISIBILITY ELF64_ST_VISIBILITY
145+
+#endif
146+
#if !defined(ELF_ST_TYPE)
147+
#define ELF_ST_TYPE ELF64_ST_TYPE
148+
#endif
149+
@@ -56,6 +59,9 @@
150+
#define Elf_Sym Elf32_Sym
151+
#define Elf_Rel Elf32_Rel
152+
#define Elf_Rela Elf32_Rela
153+
+#if !defined(ELF_ST_VISIBILITY)
154+
+#define ELF_ST_VISIBILITY ELF32_ST_VISIBILITY
155+
+#endif /* ELF_ST_VISIBILITY */
156+
#if !defined(ELF_ST_TYPE)
157+
#define ELF_ST_TYPE ELF32_ST_TYPE
158+
#endif /* ELF_ST_TYPE */
159+
diff --git a/rts/linker/PEi386.c b/rts/linker/PEi386.c
160+
index 6d0d417..841faa8 100644
161+
--- a/rts/linker/PEi386.c
162+
+++ b/rts/linker/PEi386.c
163+
@@ -292,7 +292,7 @@ const void* __rts_iob_func = (void*)&__acrt_iob_func;
164+
void initLinker_PEi386()
165+
{
166+
if (!ghciInsertSymbolTable(WSTR("(GHCi/Ld special symbols)"),
167+
- symhash, "__image_base__", __image_base, HS_BOOL_TRUE, NULL)) {
168+
+ symhash, "__image_base__", __image_base, HS_BOOL_TRUE, HS_BOOL_FALSE, NULL)) {
169+
barf("ghciInsertSymbolTable failed");
170+
}
171+
172+
@@ -1541,7 +1541,7 @@ ocGetNames_PEi386 ( ObjectCode* oc )
173+
sname = strdup (sname);
174+
addr = strdup (addr);
175+
if (!ghciInsertSymbolTable(oc->fileName, symhash, sname,
176+
- addr, false, oc)) {
177+
+ addr, false, HS_BOOL_FALSE, oc)) {
178+
releaseOcInfo (oc);
179+
stgFree (oc->image);
180+
oc->image = NULL;
181+
@@ -1759,7 +1759,9 @@ ocGetNames_PEi386 ( ObjectCode* oc )
182+
stgFree(tmp);
183+
sname = strdup (sname);
184+
if (!ghciInsertSymbolTable(oc->fileName, symhash, sname,
185+
- addr, false, oc))
186+
+ addr, false,
187+
+ section->info->props & IMAGE_SCN_LNK_COMDAT,
188+
+ oc))
189+
return false;
190+
191+
break;
192+
@@ -1776,9 +1778,10 @@ ocGetNames_PEi386 ( ObjectCode* oc )
193+
if (isWeak) {
194+
setWeakSymbol(oc, sname);
195+
}
196+
-
197+
if (! ghciInsertSymbolTable(oc->fileName, symhash, sname, addr,
198+
- isWeak, oc))
199+
+ isWeak,
200+
+ section->info->props & IMAGE_SCN_LNK_COMDAT,
201+
+ oc))
202+
return false;
203+
} else {
204+
/* We're skipping the symbol, but if we ever load this

0 commit comments

Comments
 (0)