fix: infinite recursion bug

This commit is contained in:
Shunsuke Shibayama 2024-09-07 14:50:47 +09:00
parent cd2a741fc6
commit d6cc5b1c2b
3 changed files with 28 additions and 12 deletions

View file

@ -9,7 +9,7 @@ use erg_common::log;
use erg_common::set::Set;
use erg_common::shared::Shared;
use erg_common::traits::{Locational, Stream};
use erg_common::{dict, fmt_vec, fn_name, option_enum_unwrap, set, Triple};
use erg_common::{dict, fmt_vec, fn_name, option_enum_unwrap, set, set_recursion_limit, Triple};
use erg_common::{ArcArray, Str};
use OpKind::*;
@ -2321,10 +2321,14 @@ impl Context {
Ok(ty) => Ok(self.complement(&ty)),
Err((ty, errs)) => Err((self.complement(&ty), errs)),
},
Type::Structural(typ) => match self.eval_t_params(*typ, level, t_loc) {
Ok(typ) => Ok(typ.structuralize()),
Err((t, errs)) => Err((t.structuralize(), errs)),
},
Type::Structural(typ) => {
// TODO: avoid infinite recursion
set_recursion_limit!(Ok(typ.structuralize()), 128);
match self.eval_t_params(*typ, level, t_loc) {
Ok(typ) => Ok(typ.structuralize()),
Err((t, errs)) => Err((t.structuralize(), errs)),
}
}
Type::Record(rec) => {
let mut fields = dict! {};
for (name, ty) in rec.into_iter() {

View file

@ -4899,7 +4899,11 @@ impl Type {
match self {
Self::FreeVar(fv) => fv.inc_undo_count(),
Self::Refinement(refine) => refine.t.inc_undo_count(),
_ => panic!("{self} is not a free variable"),
_ => {
if DEBUG_MODE {
panic!("{self} is not a free variable")
}
}
}
}

View file

@ -1589,18 +1589,22 @@ impl TyParam {
Self::Type(t) => {
if let Ok(to) = <&Type>::try_from(to) {
t.destructive_link(to);
} else {
} else if DEBUG_MODE {
panic!("{to} is not a type");
}
}
Self::Value(ValueObj::Type(t)) => {
if let Ok(to) = <&Type>::try_from(to) {
t.typ().destructive_link(to);
} else {
} else if DEBUG_MODE {
panic!("{to} is not a type");
}
}
_ => panic!("{self} is not a free variable"),
_ => {
if DEBUG_MODE {
panic!("{self} is not a free variable")
}
}
}
}
@ -1623,18 +1627,22 @@ impl TyParam {
Self::Type(t) => {
if let Ok(to) = <&Type>::try_from(to) {
t.undoable_link(to, list);
} else {
} else if DEBUG_MODE {
panic!("{to} is not a type");
}
}
Self::Value(ValueObj::Type(t)) => {
if let Ok(to) = <&Type>::try_from(to) {
t.typ().undoable_link(to, list);
} else {
} else if DEBUG_MODE {
panic!("{to} is not a type");
}
}
_ => panic!("{self} is not a free variable"),
_ => {
if DEBUG_MODE {
panic!("{self} is not a free variable")
}
}
}
}