Logical or/and

This commit is contained in:
nub31
2025-09-09 16:29:42 +02:00
parent e86571d1a2
commit aad41fbcbb
8 changed files with 45 additions and 21 deletions

View File

@@ -5,7 +5,7 @@ func main(args: []cstring): i64
{
let x: u32 = 23
if x == 23 && true
if x == 11 || false
{
puts("yes")
}

View File

@@ -725,13 +725,13 @@ public class QBEGenerator
var outputName = TmpName();
var instruction = BinaryInstructionFor(binaryExpression.Operator, binaryExpression.Left.Type);
var instruction = EmitBinaryInstructionForOperator(binaryExpression.Operator, binaryExpression.Left.Type);
_writer.Indented($"{outputName} {QBEAssign(binaryExpression.Left.Type)} {instruction} {left}, {right}");
return outputName;
}
private string BinaryInstructionFor(BinaryOperator op, TypeNode type)
private static string EmitBinaryInstructionForOperator(BinaryOperator op, TypeNode type)
{
return op switch
{
@@ -881,6 +881,9 @@ public class QBEGenerator
},
_ => throw new NotSupportedException($"Greater than or equal comparison not supported for type '{type}'")
},
// todo(nub31): Implement short circuiting
BinaryOperator.LogicalAnd => "and",
BinaryOperator.LogicalOr => "or",
_ => throw new ArgumentOutOfRangeException(nameof(op))
};
}

View File

@@ -344,31 +344,34 @@ public sealed class Parser
return left;
}
private int GetBinaryOperatorPrecedence(BinaryOperatorSyntax operatorSyntax)
private static int GetBinaryOperatorPrecedence(BinaryOperatorSyntax operatorSyntax)
{
return operatorSyntax switch
{
BinaryOperatorSyntax.Multiply => 6,
BinaryOperatorSyntax.Divide => 6,
BinaryOperatorSyntax.Modulo => 6,
BinaryOperatorSyntax.Multiply => 10,
BinaryOperatorSyntax.Divide => 10,
BinaryOperatorSyntax.Modulo => 10,
BinaryOperatorSyntax.Plus => 5,
BinaryOperatorSyntax.Minus => 5,
BinaryOperatorSyntax.Plus => 9,
BinaryOperatorSyntax.Minus => 9,
BinaryOperatorSyntax.LeftShift => 4,
BinaryOperatorSyntax.RightShift => 4,
BinaryOperatorSyntax.LeftShift => 8,
BinaryOperatorSyntax.RightShift => 8,
BinaryOperatorSyntax.GreaterThan => 3,
BinaryOperatorSyntax.GreaterThanOrEqual => 3,
BinaryOperatorSyntax.LessThan => 3,
BinaryOperatorSyntax.LessThanOrEqual => 3,
BinaryOperatorSyntax.GreaterThan => 7,
BinaryOperatorSyntax.GreaterThanOrEqual => 7,
BinaryOperatorSyntax.LessThan => 7,
BinaryOperatorSyntax.LessThanOrEqual => 7,
BinaryOperatorSyntax.Equal => 2,
BinaryOperatorSyntax.NotEqual => 2,
BinaryOperatorSyntax.Equal => 7,
BinaryOperatorSyntax.NotEqual => 7,
BinaryOperatorSyntax.BitwiseAnd => 1,
BinaryOperatorSyntax.BitwiseXor => 0,
BinaryOperatorSyntax.BitwiseOr => -1,
BinaryOperatorSyntax.BitwiseAnd => 6,
BinaryOperatorSyntax.BitwiseXor => 5,
BinaryOperatorSyntax.BitwiseOr => 4,
BinaryOperatorSyntax.LogicalAnd => 3,
BinaryOperatorSyntax.LogicalOr => 2,
_ => throw new ArgumentOutOfRangeException(nameof(operatorSyntax), operatorSyntax, null)
};
@@ -396,6 +399,12 @@ public sealed class Parser
case Symbol.GreaterThanOrEqual:
binaryExpressionOperator = BinaryOperatorSyntax.GreaterThanOrEqual;
return true;
case Symbol.And:
binaryExpressionOperator = BinaryOperatorSyntax.LogicalAnd;
return true;
case Symbol.Or:
binaryExpressionOperator = BinaryOperatorSyntax.LogicalOr;
return true;
case Symbol.Plus:
binaryExpressionOperator = BinaryOperatorSyntax.Plus;
return true;

View File

@@ -16,6 +16,8 @@ public enum BinaryOperatorSyntax
GreaterThanOrEqual,
LessThan,
LessThanOrEqual,
LogicalAnd,
LogicalOr,
Plus,
Minus,
Multiply,
@@ -25,7 +27,7 @@ public enum BinaryOperatorSyntax
RightShift,
BitwiseAnd,
BitwiseXor,
BitwiseOr
BitwiseOr,
}
public abstract record ExpressionSyntax(IEnumerable<Token> Tokens) : SyntaxNode(Tokens);

View File

@@ -74,4 +74,6 @@ public enum Symbol
LeftShift,
RightShift,
Pipe,
And,
Or,
}

View File

@@ -30,6 +30,8 @@ public sealed class Tokenizer
[['>', '=']] = Symbol.GreaterThanOrEqual,
[['<', '<']] = Symbol.LeftShift,
[['>', '>']] = Symbol.RightShift,
[['&', '&']] = Symbol.And,
[['|', '|']] = Symbol.Or,
[[':']] = Symbol.Colon,
[['(']] = Symbol.OpenParen,
[[')']] = Symbol.CloseParen,

View File

@@ -16,6 +16,8 @@ public enum BinaryOperator
GreaterThanOrEqual,
LessThan,
LessThanOrEqual,
LogicalAnd,
LogicalOr,
Plus,
Minus,
Multiply,

View File

@@ -364,6 +364,8 @@ public sealed class TypeChecker
BinaryOperatorSyntax.BitwiseAnd => BinaryOperator.BitwiseAnd,
BinaryOperatorSyntax.BitwiseXor => BinaryOperator.BitwiseXor,
BinaryOperatorSyntax.BitwiseOr => BinaryOperator.BitwiseOr,
BinaryOperatorSyntax.LogicalAnd => BinaryOperator.LogicalAnd,
BinaryOperatorSyntax.LogicalOr => BinaryOperator.LogicalOr,
_ => throw new ArgumentOutOfRangeException(nameof(expression.Operator), expression.Operator, null)
};
@@ -375,6 +377,8 @@ public sealed class TypeChecker
BinaryOperator.GreaterThanOrEqual => new BoolTypeNode(),
BinaryOperator.LessThan => new BoolTypeNode(),
BinaryOperator.LessThanOrEqual => new BoolTypeNode(),
BinaryOperator.LogicalAnd => new BoolTypeNode(),
BinaryOperator.LogicalOr => new BoolTypeNode(),
BinaryOperator.Plus => boundLeft.Type,
BinaryOperator.Minus => boundLeft.Type,
BinaryOperator.Multiply => boundLeft.Type,