Skip to content
This repository was archived by the owner on Jun 10, 2024. It is now read-only.

Commit 5eb61c0

Browse files
committed
fix: crt fails to link if atom/dispatch tables are empty
1 parent bb03f97 commit 5eb61c0

File tree

1 file changed

+20
-0
lines changed

1 file changed

+20
-0
lines changed

compiler/driver/src/compiler/passes/bytecode/lower_bytecode.rs

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -179,15 +179,18 @@ impl Pass for LowerBytecode {
179179
global
180180
};
181181

182+
let mut is_empty = true;
182183
for function in module.functions.iter() {
183184
match function {
184185
Function::Bytecode {
185186
is_nif: true, mfa, ..
186187
} => {
188+
is_empty = false;
187189
insert_dispatch_table_entry(mfa);
188190
}
189191
Function::Bytecode { .. } => continue,
190192
Function::Bif { mfa, .. } => {
193+
is_empty = false;
191194
insert_dispatch_table_entry(mfa);
192195
}
193196
Function::Native { name, .. } => {
@@ -196,6 +199,23 @@ impl Pass for LowerBytecode {
196199
}
197200
}
198201

202+
// Make sure we have at least one function in the dispatch table
203+
//
204+
// This is very much an edge case, but linking will fail for the crt crate
205+
// on platforms other than macOS if we don't have anything in the section
206+
if is_empty {
207+
// We choose to use `erlang:display/1` here, since:
208+
//
209+
// * It is a BIF
210+
// * It is always natively-implemented
211+
// * It is almost always in real programs anyway
212+
insert_dispatch_table_entry(&ModuleFunctionArity {
213+
module: "erlang".into(),
214+
function: "display".into(),
215+
arity: 1,
216+
});
217+
}
218+
199219
// Insert a global constant value containing the size of the bytecode in bytes
200220
let constant = builder.build_constant_uint(usize_type, buffer.len() as u64);
201221
let gv_len = builder

0 commit comments

Comments
 (0)