Merge pull request #2307 from rtfeldman/make-tag-recursive-loop

Make tag recursive loop
This commit is contained in:
Richard Feldman 2022-01-03 21:44:50 -05:00 committed by GitHub
commit 54eb9ef669
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 73 additions and 6 deletions

View File

@ -3136,3 +3136,49 @@ fn alias_defined_out_of_order() {
RocStr
);
}
#[test]
#[cfg(any(feature = "gen-llvm"))]
fn recursively_build_effect() {
assert_evals_to!(
indoc!(
r#"
app "test" provides [ main ] to "./platform"
greeting =
hi = "Hello"
name = "World"
"\(hi), \(name)!"
main =
when nestHelp 4 is
_ -> greeting
nestHelp : I64 -> XEffect {}
nestHelp = \m ->
when m is
0 ->
always {}
_ ->
always {} |> after \_ -> nestHelp (m - 1)
XEffect a : [ @XEffect ({} -> a) ]
always : a -> XEffect a
always = \x -> @XEffect (\{} -> x)
after : XEffect a, (a -> XEffect b) -> XEffect b
after = \(@XEffect e), toB ->
@XEffect \{} ->
when toB (e {}) is
@XEffect e2 ->
e2 {}
"#
),
RocStr::from_slice(b"Hello, World!"),
RocStr
);
}

View File

@ -833,10 +833,21 @@ enum OtherTags2 {
}
fn maybe_mark_tag_union_recursive(subs: &mut Subs, tag_union_var: Variable) {
while let Err((recursive, _chain)) = subs.occurs(tag_union_var) {
'outer: while let Err((recursive, chain)) = subs.occurs(tag_union_var) {
let description = subs.get(recursive);
if let Content::Structure(FlatType::TagUnion(tags, ext_var)) = description.content {
subs.mark_tag_union_recursive(recursive, tags, ext_var);
} else {
// walk the chain till we find a tag union
for v in &chain[..chain.len() - 1] {
let description = subs.get(*v);
if let Content::Structure(FlatType::TagUnion(tags, ext_var)) = description.content {
subs.mark_tag_union_recursive(*v, tags, ext_var);
continue 'outer;
}
}
panic!("recursive loop does not contain a tag union")
}
}
}

View File

@ -677,11 +677,21 @@ impl From<&str> for RocStr {
impl fmt::Debug for RocStr {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
// RocStr { is_small_str: false, storage: Refcounted(3), elements: [ 1,2,3,4] }
f.debug_struct("RocStr")
.field("is_small_str", &self.is_small_str())
.field("storage", &self.storage())
.field("elements", &self.as_slice())
.finish()
match core::str::from_utf8(self.as_slice()) {
Ok(string) => f
.debug_struct("RocStr")
.field("is_small_str", &self.is_small_str())
.field("storage", &self.storage())
.field("string_contents", &string)
.finish(),
Err(_) => f
.debug_struct("RocStr")
.field("is_small_str", &self.is_small_str())
.field("storage", &self.storage())
.field("byte_contents", &self.as_slice())
.finish(),
}
}
}