diff --git a/depell/src/index.js b/depell/src/index.js index 92a0955e..46e47321 100644 --- a/depell/src/index.js +++ b/depell/src/index.js @@ -286,7 +286,7 @@ async function bindCodeEdit(target) { if (minified_size) { codeSize.textContent = (MAX_CODE_SIZE - minified_size) + ""; const perc = Math.min(100, Math.floor(100 * (minified_size / MAX_CODE_SIZE))); - codeSize.style.color = `color-mix(in srgb, white, var(--error) ${perc}%)`; + codeSize.style.color = `color-mix(in srgb, light-dark(black, white), var(--error) ${perc}%)`; } timeout = 0; }; diff --git a/lang/src/lib.rs b/lang/src/lib.rs index be6f58a9..19e67161 100644 --- a/lang/src/lib.rs +++ b/lang/src/lib.rs @@ -433,6 +433,10 @@ pub mod ty { } pub fn try_upcast(self, ob: Self) -> Option { + self.try_upcast_low(ob, false) + } + + pub fn try_upcast_low(self, ob: Self, coerce_pointer: bool) -> Option { let (oa, ob) = (Self(self.0.min(ob.0)), Self(self.0.max(ob.0))); let (a, b) = (oa.strip_pointer(), ob.strip_pointer()); Some(match () { @@ -444,7 +448,7 @@ pub mod ty { _ if a.is_signed() && b.is_signed() || a.is_unsigned() && b.is_unsigned() => ob, _ if a.is_unsigned() && b.is_signed() && a.repr() - U8 < b.repr() - I8 => ob, _ if a.is_unsigned() && b.is_signed() && a.repr() - U8 > b.repr() - I8 => oa, - _ if oa.is_integer() && ob.is_pointer() => ob, + _ if oa.is_integer() && ob.is_pointer() && coerce_pointer => ob, _ => return None, }) } diff --git a/lang/src/son.rs b/lang/src/son.rs index 6807a6ed..41394a46 100644 --- a/lang/src/son.rs +++ b/lang/src/son.rs @@ -666,7 +666,9 @@ impl Nodes { let id = self.new_node_nop(ty, kind, inps); if let Some(opt) = self.peephole(id, tys) { debug_assert_ne!(opt, id); - self.queued_peeps.clear(); + for peep in mem::take(&mut self.queued_peeps) { + self.unlock(peep); + } self.lock(opt); self.remove(id); self.unlock(opt); @@ -733,7 +735,9 @@ impl Nodes { fn late_peephole(&mut self, target: Nid, tys: &Types) -> Option { if let Some(id) = self.peephole(target, tys) { - self.queued_peeps.clear(); + for peep in mem::take(&mut self.queued_peeps) { + self.unlock(peep); + } self.replace(target, id); return None; } @@ -742,6 +746,7 @@ impl Nodes { fn iter_peeps(&mut self, mut fuel: usize, stack: &mut Vec, tys: &Types) { debug_assert!(stack.is_empty()); + debug_assert!(self.queued_peeps.is_empty()); self.iter() .filter_map(|(id, node)| node.kind.is_peeped().then_some(id)) @@ -758,18 +763,21 @@ impl Nodes { } if let Some(new) = self.peephole(node, tys) { - stack.append(&mut self.queued_peeps); self.replace(node, new); self.push_adjacent_nodes(new, stack); } + stack.append(&mut self.queued_peeps); - //debug_assert_matches!( - // self.iter() - // .find(|(i, n)| n.lock_rc != 0 && n.kind.is_peeped() && !stack.contains(i)), - // None - //); + debug_assert_matches!( + self.iter().find(|(i, n)| n.lock_rc.get() != 0 + && n.kind.is_peeped() + && !stack.contains(i)), + None + ); } + debug_assert!(self.queued_peeps.is_empty()); + stack.drain(..).for_each(|s| _ = self.unlock_remove(s)); } @@ -995,9 +1003,11 @@ impl Nodes { for i in self[target].outputs.clone() { if self[i].kind == Kind::Phi { for o in self[i].outputs.clone() { - self.lock(o); + if self.is_unlocked(o) { + self.lock(o); + self.queued_peeps.push(o); + } } - self.queued_peeps.extend(self[i].outputs.clone()); self.replace(i, self[i].inputs[side]); } } @@ -1271,8 +1281,10 @@ impl Nodes { inps[2] = region; inps[3] = prev_store; prev_store = self.new_node_nop(self[oper].ty, Kind::Stre, inps); - self.lock(prev_store); - self.queued_peeps.push(prev_store); + if self.is_unlocked(prev_store) { + self.lock(prev_store); + self.queued_peeps.push(prev_store); + } } return Some(prev_store); @@ -1385,9 +1397,11 @@ impl Nodes { self.unlock(o); for o in self[o].outputs.clone() { - self.lock(o); + if self.is_unlocked(o) { + self.lock(o); + self.queued_peeps.push(o); + } } - self.queued_peeps.extend(self[o].outputs.clone()); self.replace(o, self[o].inputs[1]); } } @@ -4774,7 +4788,7 @@ impl<'a> Codegen<'a> { rhs: &mut Value, op: TokenKind, ) -> (ty::Id, Nid) { - if let Some(upcasted) = lhs.ty.try_upcast(rhs.ty) { + if let Some(upcasted) = lhs.ty.try_upcast_low(rhs.ty, true) { let to_correct = if lhs.ty != upcasted { Some((lhs, rhs)) } else if rhs.ty != upcasted { @@ -4928,7 +4942,6 @@ impl<'a> Codegen<'a> { ) -> bool { if let Some(upcasted) = src.ty.try_upcast(expected) && upcasted == expected - && upcasted.is_pointer() == src.ty.is_pointer() { if src.ty.is_never() { return true;