feat: for-in range loops in selfhost + bootstrap

- Parser: add parseRange for selfhost (.. / ..=)
- Sema: determine loop variable type from range bounds
- HIR Lower: desugar range for-in to while loop with counter
- Bootstrap sema: fix range-based for variable type (was unknown)
- Selfhost loop remains deterministic
This commit is contained in:
2026-06-09 21:53:12 +03:00
parent 6414ef236b
commit 74db8a5790
4 changed files with 194 additions and 4 deletions
+20 -1
View File
@@ -759,12 +759,31 @@ func parserParseBinary(p: *Parser) -> *Expr {
return parserParseBinaryPrec(p, 1);
}
// ---------------------------------------------------------------------------
// Range: lo .. hi or lo ..= hi
// ---------------------------------------------------------------------------
func parserParseRange(p: *Parser) -> *Expr {
var left: *Expr = parserParseBinary(p);
if parserCheck(p, tkDotDot) || parserCheck(p, tkDotDotEqual) {
let inclusive: bool = parserCheck(p, tkDotDotEqual);
let opTok: LexToken = parserAdvance(p);
let right: *Expr = parserParseBinary(p);
let e: *Expr = parserMakeExpr(ekRange, opTok.line, opTok.column);
e.child1 = left;
e.child2 = right;
e.boolValue = inclusive;
return e;
}
return left;
}
// ---------------------------------------------------------------------------
// Ternary: cond ? then : else
// ---------------------------------------------------------------------------
func parserParseTernary(p: *Parser) -> *Expr {
var left: *Expr = parserParseBinary(p);
var left: *Expr = parserParseRange(p);
if parserMatch(p, tkQuestion) {
let thenExpr: *Expr = parserParseExpr(p);
discard parserExpect(p, tkColon, "expected ':' in ternary");