Properly deduplicating imported functions
Signed-off-by: Jakub Doka <jakub.doka2@gmail.com>
This commit is contained in:
parent
da5bd3d36a
commit
8aee4f2890
|
@ -17,6 +17,7 @@ use {
|
||||||
utils::{self as hbutils, Ent, EntVec},
|
utils::{self as hbutils, Ent, EntVec},
|
||||||
},
|
},
|
||||||
std::{
|
std::{
|
||||||
|
collections::HashSet,
|
||||||
fmt::{Display, Write},
|
fmt::{Display, Write},
|
||||||
ops::Range,
|
ops::Range,
|
||||||
},
|
},
|
||||||
|
@ -90,6 +91,9 @@ impl hblang::backend::Backend for Backend {
|
||||||
|
|
||||||
self.globals.shadow(types.ins.globals.len());
|
self.globals.shadow(types.ins.globals.len());
|
||||||
|
|
||||||
|
#[cfg(debug_assertions)]
|
||||||
|
let mut seen_names = HashSet::new();
|
||||||
|
|
||||||
self.asm.frontier.push(from.into());
|
self.asm.frontier.push(from.into());
|
||||||
while let Some(itm) = self.asm.frontier.pop() {
|
while let Some(itm) = self.asm.frontier.pop() {
|
||||||
match itm.expand() {
|
match itm.expand() {
|
||||||
|
@ -156,6 +160,7 @@ impl hblang::backend::Backend for Backend {
|
||||||
&mut self.ctx.func.signature,
|
&mut self.ctx.func.signature,
|
||||||
&mut vec![],
|
&mut vec![],
|
||||||
);
|
);
|
||||||
|
debug_assert!(seen_names.insert(self.asm.name.clone()), "{}", self.asm.name);
|
||||||
fuc.module_id = Some(
|
fuc.module_id = Some(
|
||||||
module
|
module
|
||||||
.declare_function(&self.asm.name, linkage, &self.ctx.func.signature)
|
.declare_function(&self.asm.name, linkage, &self.ctx.func.signature)
|
||||||
|
@ -211,7 +216,9 @@ impl hblang::backend::Backend for Backend {
|
||||||
nm.index =
|
nm.index =
|
||||||
self.globals[hbty::Global::new(nm.index as _)].module_id.unwrap().as_u32();
|
self.globals[hbty::Global::new(nm.index as _)].module_id.unwrap().as_u32();
|
||||||
}
|
}
|
||||||
|
let prev_len = self.ctx.func.params.user_named_funcs().len();
|
||||||
self.ctx.func.params.ensure_user_func_name(nm.clone());
|
self.ctx.func.params.ensure_user_func_name(nm.clone());
|
||||||
|
debug_assert_ne!(self.ctx.func.params.user_named_funcs().len(), prev_len, "{}", nm);
|
||||||
});
|
});
|
||||||
module
|
module
|
||||||
.define_function_bytes(
|
.define_function_bytes(
|
||||||
|
@ -254,7 +261,6 @@ impl hblang::backend::Backend for Backend {
|
||||||
tys: &hbty::Types,
|
tys: &hbty::Types,
|
||||||
files: &hbutils::EntSlice<hbty::Module, hblang::parser::Ast>,
|
files: &hbutils::EntSlice<hbty::Module, hblang::parser::Ast>,
|
||||||
) {
|
) {
|
||||||
self.ctx.clear();
|
|
||||||
let isa = self.module.as_ref().unwrap().isa();
|
let isa = self.module.as_ref().unwrap().isa();
|
||||||
|
|
||||||
let mut lens = vec![];
|
let mut lens = vec![];
|
||||||
|
@ -286,6 +292,7 @@ impl hblang::backend::Backend for Backend {
|
||||||
self.ctx.compile(isa, &mut self.ctrl_plane).unwrap();
|
self.ctx.compile(isa, &mut self.ctrl_plane).unwrap();
|
||||||
let code = self.ctx.compiled_code().unwrap();
|
let code = self.ctx.compiled_code().unwrap();
|
||||||
self.funcs.push(id, &self.ctx.func, &code.buffer);
|
self.funcs.push(id, &self.ctx.func, &code.buffer);
|
||||||
|
self.ctx.clear();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -229,8 +229,8 @@ impl Backend for HbvmBackend {
|
||||||
let functions = types
|
let functions = types
|
||||||
.ins
|
.ins
|
||||||
.funcs
|
.funcs
|
||||||
.iter()
|
.values()
|
||||||
.zip(self.funcs.iter())
|
.zip(self.funcs.values())
|
||||||
.filter(|(_, f)| f.offset != u32::MAX)
|
.filter(|(_, f)| f.offset != u32::MAX)
|
||||||
.map(|(f, fd)| {
|
.map(|(f, fd)| {
|
||||||
let name = if f.file != Module::default() {
|
let name = if f.file != Module::default() {
|
||||||
|
@ -245,8 +245,8 @@ impl Backend for HbvmBackend {
|
||||||
types
|
types
|
||||||
.ins
|
.ins
|
||||||
.globals
|
.globals
|
||||||
.iter()
|
.values()
|
||||||
.zip(self.globals.iter())
|
.zip(self.globals.values())
|
||||||
.filter(|(_, g)| g.offset != u32::MAX)
|
.filter(|(_, g)| g.offset != u32::MAX)
|
||||||
.map(|(g, gd)| {
|
.map(|(g, gd)| {
|
||||||
let name = if g.file == Module::default() {
|
let name = if g.file == Module::default() {
|
||||||
|
|
|
@ -4258,24 +4258,43 @@ impl<'a> Codegen<'a> {
|
||||||
"the simbol name is limmited to 63 characters, please don't import java",
|
"the simbol name is limmited to 63 characters, please don't import java",
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
name
|
name
|
||||||
} else {
|
} else {
|
||||||
name
|
name
|
||||||
};
|
};
|
||||||
|
|
||||||
let func = FuncData {
|
if let Some(f) = self
|
||||||
file: sc.file,
|
.tys
|
||||||
parent: sc.parent,
|
.ins
|
||||||
name,
|
.funcs
|
||||||
pos,
|
.values()
|
||||||
sig,
|
.find(|f| f.name == name && f.is_import && f.pos != pos)
|
||||||
expr: ExprRef::new(expr),
|
{
|
||||||
is_inline: sc.is_ct,
|
self.error_low(sc.file, pos, "second import of this symbol");
|
||||||
is_generic: false,
|
self.error_low(sc.file, f.pos, "...previous occured here");
|
||||||
is_import: true,
|
}
|
||||||
comp_state: [CompState::Compiled.into(); 2],
|
|
||||||
};
|
*self.tys.syms.get_or_insert(
|
||||||
self.tys.ins.funcs.push(func).into()
|
SymKey::Import(sc.parent, name),
|
||||||
|
&mut self.tys.ins,
|
||||||
|
|ins| {
|
||||||
|
ins.funcs
|
||||||
|
.push(FuncData {
|
||||||
|
file: sc.file,
|
||||||
|
parent: sc.parent,
|
||||||
|
name,
|
||||||
|
pos,
|
||||||
|
sig,
|
||||||
|
expr: ExprRef::new(expr),
|
||||||
|
is_inline: sc.is_ct,
|
||||||
|
is_generic: false,
|
||||||
|
is_import: true,
|
||||||
|
comp_state: [CompState::Compiled.into(); 2],
|
||||||
|
})
|
||||||
|
.into()
|
||||||
|
},
|
||||||
|
)
|
||||||
}
|
}
|
||||||
Expr::Closure { pos, args, ret, .. } if let Some(name) = sc.name => {
|
Expr::Closure { pos, args, ret, .. } if let Some(name) = sc.name => {
|
||||||
match self.try_parse_concrete_signature(pos, sc, args, ret) {
|
match self.try_parse_concrete_signature(pos, sc, args, ret) {
|
||||||
|
|
|
@ -143,6 +143,8 @@ impl crate::ctx_map::CtxEntry for Id {
|
||||||
let fc = &ctx.funcs[f];
|
let fc = &ctx.funcs[f];
|
||||||
if fc.is_generic {
|
if fc.is_generic {
|
||||||
SymKey::Type(fc.parent, fc.pos, fc.sig.args)
|
SymKey::Type(fc.parent, fc.pos, fc.sig.args)
|
||||||
|
} else if fc.is_import {
|
||||||
|
SymKey::Import(fc.parent, fc.name)
|
||||||
} else {
|
} else {
|
||||||
SymKey::Decl(fc.parent, fc.name)
|
SymKey::Decl(fc.parent, fc.name)
|
||||||
}
|
}
|
||||||
|
@ -643,6 +645,8 @@ pub enum SymKey<'a> {
|
||||||
Optional(&'a OptData),
|
Optional(&'a OptData),
|
||||||
Type(Id, Pos, List),
|
Type(Id, Pos, List),
|
||||||
Decl(Id, Ident),
|
Decl(Id, Ident),
|
||||||
|
// separate to avoid colision with decl
|
||||||
|
Import(Id, Ident),
|
||||||
Array(&'a ArrayData),
|
Array(&'a ArrayData),
|
||||||
Constant(&'a ConstData),
|
Constant(&'a ConstData),
|
||||||
}
|
}
|
||||||
|
|
|
@ -646,7 +646,7 @@ impl<K: Ent, T> EntVec<K, T> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn iter(&self) -> core::slice::Iter<T> {
|
pub fn values(&self) -> core::slice::Iter<T> {
|
||||||
self.data.iter()
|
self.data.iter()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue