UnNamed discriminant unions
This may be known behavior but it appears that un-named union types fail:
struct SomeStruct
{
union switch (int v)
{
case 1:
void;
}
value;
};
outputs:
Failed: can't have unnamed type Union(Named("v", Int), [UnionCase(Const(1), Void)], None)
It doesn't look like the RFC specifies that this is needed though.
type-specifier:
[ "unsigned" ] "int"
| [ "unsigned" ] "hyper"
| "float"
| "double"
| "quadruple"
| "bool"
| enum-type-spec
| struct-type-spec
| union-type-spec
| identifier
...
union-type-spec:
"union" union-body
union-body:
"switch" "(" declaration ")" "{"
case-spec
case-spec *
[ "default" ":" declaration ";" ]
"}"
Hm, that's pretty awkward. Rust doesn't support unnamed compound types, so we'd need to make up a name for it, and you'd have to use that name to refer to the Rust enum variants.
Yes, I agree. But maybe we could use the name of the attribute it's prefixing? In the example above, there's an attribute named value and we could name the enum __Value. If we use a couple of underscores we can ensure that it doesn't interact with other types that might exist.
What do you think?
It looks like anonymous types can be arbitrarily nested though:
struct SomeStruct
{
union switch (int v)
{
case 1:
union switch (int u)
{
case 1: void;
};
}
value;
};
What name would you use for the inner one?
😱
@jsgf I suppose they would still potentially have a path though to the type. It appears that we already name cases based on their matched value. So what if we used that?
enum SomeStruct_Value_Union_Const1_Union {
Const1,
}
enum SomeStruct_Value_Union {
Const1(SomeStruct_Value_Union_Const1_Union),
}
struct SomeStruct {
value: SomeStruct_Value_Union
}
Basically, this could be a pattern like:
<StructName>_<AttributeName>_Union[_<EnumVariant>_Union]*
Not sure that maps super well, but it should be unique... It's also not pretty but we're dealing with anonymous types so perhaps we can't be too choosy.
Ok, so the challenge is that the nom spec actually does parse these unname types fine (I was able to add a test locally) but not it appears that when we try to parse it breaks on the unnamed type. Of course, the code doesn't know that it has an unnamed type until it gets to that point and it's definitely missing from Symtab (which I assume is a symbol table).
Do you think there's a way to scan for unnamed types first, like a preprocessing, and then replace the types with idents?