aboutsummaryrefslogtreecommitdiffhomepage
path: root/ir/ir.c
diff options
context:
space:
mode:
author lemon<lsof@mailbox.org>2025-12-13 14:21:22 +0100
committer lemon<lsof@mailbox.org>2025-12-13 14:24:30 +0100
commit854df54e1839c8b96d1aaa9aeaa32c2ebbf535f8 (patch)
treeba0d2d8b79300d0af2a53aeccd628111733ae7e8 /ir/ir.c
parent17e5a9f573b1a60e12ed60948f45f5992914d324 (diff)
fix position independent loads of function symbols.
For `extern int x[1];`, can use PCREL32 for &x. But for `extern int x(int)`, must use GOTREL, when not being called directly (that's PLT). Therefore the type of an external symbol (actually just whether it denotes a function) matters when deciding what kind of relocation to emit, so keep that information.
Diffstat (limited to 'ir/ir.c')
-rw-r--r--ir/ir.c6
1 files changed, 3 insertions, 3 deletions
diff --git a/ir/ir.c b/ir/ir.c
index dbd6206..cd93992 100644
--- a/ir/ir.c
+++ b/ir/ir.c
@@ -94,7 +94,7 @@ addcon(const struct xcon *con)
{
uint h = hashb(0, con, sizeof *con);
uint i = h, n = countof(conht);
- assert(con->issym || con->isdat || con->cls);
+ assert((con->issym ^ con->isdat && !(con->isdat && con->isfunc)) || con->cls);
for (;; ++i) {
i &= countof(conht) - 1;
if (!conht[i].issym && !conht[i].isdat && !conht[i].cls) {
@@ -138,9 +138,9 @@ mkfltcon(enum irclass k, double f)
}
union ref
-mksymref(const char *s)
+mksymref(const char *s, bool isfunc)
{
- struct xcon con = { .issym = 1, .sym = s };
+ struct xcon con = { .issym = 1, .sym = s, .isfunc = isfunc };
return mkref(RXCON, addcon(&con));
}