fixing compiler pulling function destinations out of the loops
This commit is contained in:
parent
a299bad75b
commit
29367d8f8b
|
@ -612,6 +612,30 @@ main := fn(): uint {
|
|||
|
||||
### Purely Testing Examples
|
||||
|
||||
#### null_check_in_the_loop
|
||||
```hb
|
||||
A := struct {
|
||||
x_change: u8,
|
||||
y_change: u8,
|
||||
left: u8,
|
||||
middle: u8,
|
||||
right: u8,
|
||||
}
|
||||
|
||||
return_fn := fn(): ?A {
|
||||
return A.(0, 0, 0, 0, 0)
|
||||
}
|
||||
|
||||
main := fn(): int {
|
||||
loop {
|
||||
ret := return_fn()
|
||||
if ret != null {
|
||||
return 1
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### stack_provenance
|
||||
```hb
|
||||
main := fn(): uint {
|
||||
|
|
|
@ -225,13 +225,13 @@ impl Nodes {
|
|||
return;
|
||||
}
|
||||
|
||||
let mut deepest = VOID;
|
||||
for i in 0..self[node].inputs.len() {
|
||||
let inp = self[node].inputs[i];
|
||||
let mut deepest = self[node].inputs[0];
|
||||
for &inp in self[node].inputs[1..].iter() {
|
||||
if self.idepth(inp) > self.idepth(deepest) {
|
||||
if matches!(self[inp].kind, Kind::Call { .. }) {
|
||||
deepest = inp;
|
||||
} else {
|
||||
debug_assert!(!self.is_cfg(inp));
|
||||
deepest = self.idom(inp);
|
||||
}
|
||||
}
|
||||
|
@ -256,14 +256,15 @@ impl Nodes {
|
|||
self[deepest].outputs.push(node);
|
||||
}
|
||||
|
||||
fn collect_rpo(&mut self, node: Nid, rpo: &mut Vec<Nid>, visited: &mut BitSet) {
|
||||
fn collect_rpo(&self, node: Nid, rpo: &mut Vec<Nid>, visited: &mut BitSet) {
|
||||
if !self.is_cfg(node) || !visited.set(node) {
|
||||
return;
|
||||
}
|
||||
|
||||
for i in 0..self[node].outputs.len() {
|
||||
self.collect_rpo(self[node].outputs[i], rpo, visited);
|
||||
for &n in self[node].outputs.iter() {
|
||||
self.collect_rpo(n, rpo, visited);
|
||||
}
|
||||
|
||||
rpo.push(node);
|
||||
}
|
||||
|
||||
|
@ -1251,6 +1252,8 @@ impl Nodes {
|
|||
return Some(NEVER);
|
||||
}
|
||||
|
||||
std::dbg!(&self[self[target].inputs[1]]);
|
||||
|
||||
if self[target].inputs[1] == NEVER {
|
||||
self.lock(target);
|
||||
for o in self[target].outputs.clone() {
|
||||
|
@ -2390,6 +2393,11 @@ impl<'a> Codegen<'a> {
|
|||
}
|
||||
|
||||
let (index, _) = self.ci.nodes.aclass_index(region);
|
||||
if self.ci.nodes[value].kind == Kind::Load {
|
||||
let (lindex, _) = self.ci.nodes.aclass_index(self.ci.nodes[value].inputs[1]);
|
||||
let clobber = self.ci.scope.aclasses[lindex].clobber.get();
|
||||
self.ci.scope.aclasses[index].clobber.set(clobber, &mut self.ci.nodes);
|
||||
}
|
||||
let aclass = &mut self.ci.scope.aclasses[index];
|
||||
self.ci.nodes.load_loop_aclass(index, aclass, &mut self.ci.loops);
|
||||
let vc = Vc::from([aclass.clobber.get(), value, region, aclass.last_store.get()]);
|
||||
|
@ -2416,7 +2424,7 @@ impl<'a> Codegen<'a> {
|
|||
let (index, _) = self.ci.nodes.aclass_index(region);
|
||||
let aclass = &mut self.ci.scope.aclasses[index];
|
||||
self.ci.nodes.load_loop_aclass(index, aclass, &mut self.ci.loops);
|
||||
let vc = [aclass.clobber.get(), region, aclass.last_store.get()];
|
||||
let vc = [std::dbg!(aclass.clobber.get()), region, aclass.last_store.get()];
|
||||
self.ci.nodes.new_node(ty, Kind::Load, vc)
|
||||
}
|
||||
|
||||
|
@ -2567,15 +2575,10 @@ impl<'a> Codegen<'a> {
|
|||
}
|
||||
}
|
||||
|
||||
self.ci.ctrl.set(
|
||||
self.ci.nodes.new_node_nop(ty::Id::VOID, Kind::Return, inps),
|
||||
&mut self.ci.nodes,
|
||||
);
|
||||
|
||||
self.ci.nodes[self.ci.ctrl.get()].pos = pos;
|
||||
|
||||
self.ci.nodes[NEVER].inputs.push(self.ci.ctrl.get());
|
||||
self.ci.nodes[self.ci.ctrl.get()].outputs.push(NEVER);
|
||||
let ret = self.ci.nodes.new_node_nop(ty::Id::VOID, Kind::Return, inps);
|
||||
self.ci.ctrl.set(NEVER, &mut self.ci.nodes);
|
||||
self.ci.nodes[ret].pos = pos;
|
||||
self.ci.nodes.bind(ret, NEVER);
|
||||
} else if let Some((pv, ctrl, scope)) = &mut self.ci.inline_ret {
|
||||
ctrl.set(
|
||||
self.ci
|
||||
|
@ -3164,6 +3167,7 @@ impl<'a> Codegen<'a> {
|
|||
Loc::Reg => None,
|
||||
Loc::Stack => {
|
||||
let stck = self.new_stack(func.pos(), sig.ret);
|
||||
clobbered_aliases.set(self.ci.nodes.aclass_index(stck).0 as _);
|
||||
inps.push(stck);
|
||||
Some(Value::ptr(stck).ty(sig.ret))
|
||||
}
|
||||
|
@ -4638,6 +4642,7 @@ mod tests {
|
|||
fb_driver;
|
||||
|
||||
// Purely Testing Examples;
|
||||
null_check_in_the_loop;
|
||||
stack_provenance;
|
||||
advanced_floating_point_arithmetic;
|
||||
nullable_structure;
|
||||
|
|
34
lang/tests/son_tests_null_check_in_the_loop.txt
Normal file
34
lang/tests/son_tests_null_check_in_the_loop.txt
Normal file
|
@ -0,0 +1,34 @@
|
|||
main:
|
||||
ADDI64 r254, r254, -38d
|
||||
ST r31, r254, 6a, 32h
|
||||
LI8 r32, 0b
|
||||
ADDI64 r33, r254, 0d
|
||||
2: JAL r31, r0, :return_fn
|
||||
ST r1, r254, 0a, 6h
|
||||
LD r34, r254, 0a, 1h
|
||||
ANDI r34, r34, 255d
|
||||
ANDI r32, r32, 255d
|
||||
JEQ r34, r32, :0
|
||||
LI64 r1, 1d
|
||||
JMP :1
|
||||
0: JMP :2
|
||||
1: LD r31, r254, 6a, 32h
|
||||
ADDI64 r254, r254, 38d
|
||||
JALA r0, r31, 0a
|
||||
return_fn:
|
||||
ADDI64 r254, r254, -6d
|
||||
LI8 r4, 1b
|
||||
ADDI64 r3, r254, 0d
|
||||
ST r4, r254, 0a, 1h
|
||||
LI8 r4, 0b
|
||||
ST r4, r254, 1a, 1h
|
||||
ST r4, r254, 2a, 1h
|
||||
ST r4, r254, 3a, 1h
|
||||
ST r4, r254, 4a, 1h
|
||||
ST r4, r254, 5a, 1h
|
||||
LD r1, r3, 0a, 6h
|
||||
ADDI64 r254, r254, 6d
|
||||
JALA r0, r31, 0a
|
||||
code size: 302
|
||||
ret: 1
|
||||
status: Ok(())
|
Loading…
Reference in a new issue