You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Rust and Go output doesn't compile for mixed numeric operands or implicit widening: x * 2 on an f64, a + b on i64/i32, long f(int b) { return b; } #238
The AST follows C-family numeric semantics: an int mixed with a long or a double is widened implicitly, and an int value can be assigned to, returned as, or passed as a long or double.
StandardLanguageGenerator already computes the promoted type. Promoted() is at Coder/Languages/StandardLanguageGenerator.cs:398, and StaticType uses it at :345/:356 (since #152 / PR #220). But that type is only used for inference:
GenerateBinary (StandardLanguageGenerator.cs:~1184) writes both operands exactly as they are.
Assignments, initialisers and returns do the same.
Rust and Go do no implicit numeric conversion, so the output does not compile in either. C, C++, C#, JavaScript and Python accept the same AST.
varhalffloat64=b// cannot use b (variable of type int) as float64 valuereturn (a+b) // invalid operation: a + b (mismatched types int64 and int)
Go accepts x * 2 because 2 is an untyped constant; Rust has no such rule.
#152 fixed the inferred type of mixed expressions, but the emitted operands were never converted.
Suggested fix / acceptance criteria
When a binary expression's operands have different known numeric static types, the Rust and Go generators convert the narrower operand to the Promoted type: b as i64 / int64(b), x as f64 / float64(x).
An integer literal next to a floating operand is written as a floating literal (2.0) or converted.
The same conversion applies wherever a known narrower numeric type meets a declared wider type:
a typed VariableDeclaration/FieldDeclaration initialiser
an AssignmentStatement value
a ReturnStatement against the function's return type
a call argument against a known parameter type
Narrowing (e.g. double to int) is left as it is; the AST never makes it implicit.
RustGeneratedSourceCompilesTests and GoGeneratedSourceCompilesTests compile cases covering:
Priority: High. Very ordinary ASTs (x * 2 on a double, long + int, returning an int as long) produce Rust and Go that fail to compile, so those two targets are unusable for most numeric code.
Area:Coder/Languages/StandardLanguageGenerator.cs (GenerateBinary, assignments, initialisers, returns, call arguments), plus the Rust and Go generators' conversion syntax
Suggested assignment: Owner of the Rust/Go generators
Notes: Add one hook such as ConvertTo(expr, fromType, toType) that defaults to identity and is overridden for Rust (as) and Go (T(x)), then call it at each site where a known narrower type meets a wider one. That keeps the other five targets unchanged. Start with the binary-operand case, since x * 2 on an f64 is the most common failure.
Activity
matt-edmondson commentedon Oct 17, 2026
Triage
x * 2on a double,long + int, returning anintaslong) produce Rust and Go that fail to compile, so those two targets are unusable for most numeric code.Coder/Languages/StandardLanguageGenerator.cs(GenerateBinary, assignments, initialisers, returns, call arguments), plus the Rust and Go generators' conversion syntaxready ? 1 : 2.5orx := 1 + 0.5fails to compile #152 / PR Promote mixed int and float operands to the wider type [patch] #220, which fixed only the inferred type. No open PR covers it (fix(PythonGenerator): map 'long' type to 'int' (#109) #124 is the Pythonlongmapping).Notes: Add one hook such as
ConvertTo(expr, fromType, toType)that defaults to identity and is overridden for Rust (as) and Go (T(x)), then call it at each site where a known narrower type meets a wider one. That keeps the other five targets unchanged. Start with the binary-operand case, sincex * 2on anf64is the most common failure.Generated by Claude Code