diff --git a/langkit/lkt_lowering.py b/langkit/lkt_lowering.py index db1cd9b16..e3fcbd28d 100644 --- a/langkit/lkt_lowering.py +++ b/langkit/lkt_lowering.py @@ -21,7 +21,7 @@ from langkit.compiled_types import ( ASTNodeType, AbstractNodeData, Argument, CompiledType, CompiledTypeOrDefer, CompiledTypeRepo, EnumNodeAlternative, EnumType, Field, StructType, T, - TypeRepo, UserField, resolve_type + TypeRepo, UserField ) from langkit.diagnostics import ( DiagnosticError, Location, check_source_language, diagnostic_context, error @@ -1354,8 +1354,9 @@ def lower_type_decl(self, decl: L.TypeDecl) -> CompiledType: try: t = self.compiled_types[decl] except KeyError: - # The type is not lowered yet: let's do it - pass + # The type is not lowered yet: let's do it. Add the sentinel to + # reject type inheritance loop during recursion. + self.compiled_types[decl] = None else: if t is None: error('Type inheritance loop detected') diff --git a/testsuite/tests/grammar/invalid_derivation_loop/test.lkt b/testsuite/tests/grammar/invalid_derivation_loop/test.lkt new file mode 100644 index 000000000..f846d26b1 --- /dev/null +++ b/testsuite/tests/grammar/invalid_derivation_loop/test.lkt @@ -0,0 +1,15 @@ +import lexer_example + +@with_lexer(foo_lexer) +grammar foo_grammar { + @main_rule main_rule <- or(N1("example") | N2("null")) +} + +@abstract class FooNode implements Node[FooNode] { +} + +class N1 : N2 { +} + +class N2 : N1 { +} diff --git a/testsuite/tests/grammar/invalid_derivation_loop/test.out b/testsuite/tests/grammar/invalid_derivation_loop/test.out new file mode 100644 index 000000000..05fce0573 --- /dev/null +++ b/testsuite/tests/grammar/invalid_derivation_loop/test.out @@ -0,0 +1,7 @@ +== test.lkt == +test.lkt:11:1: error: Type inheritance loop detected +11 | class N1 : N2 { + | ^ + + +Done diff --git a/testsuite/tests/grammar/invalid_derivation_loop/test.yaml b/testsuite/tests/grammar/invalid_derivation_loop/test.yaml new file mode 100644 index 000000000..4a499fbd3 --- /dev/null +++ b/testsuite/tests/grammar/invalid_derivation_loop/test.yaml @@ -0,0 +1 @@ +driver: lkt_compile