Implement bitwise not

This commit is contained in:
Daniel M 2022-01-29 21:26:14 +01:00
parent 8a1debabe9
commit 1079eb1671
4 changed files with 15 additions and 2 deletions

View File

@ -30,7 +30,7 @@
- [x] Bitwise AND `X&Y` - [x] Bitwise AND `X&Y`
- [x] Bitwise OR `X|Y` - [x] Bitwise OR `X|Y`
- [x] Bitwise XOR `X^Y` - [x] Bitwise XOR `X^Y`
- [ ] Bitwise NOT `~X` - [x] Bitwise NOT `~X`
- [x] Bitwise left shift `X<<Y` - [x] Bitwise left shift `X<<Y`
- [x] Bitwise right shift `X>>Y` - [x] Bitwise right shift `X>>Y`
- [ ] Variables - [ ] Variables

View File

@ -33,6 +33,7 @@ impl Interpreter {
match (operand, uo) { match (operand, uo) {
(Value::I64(val), UnOpType::Negate) => Value::I64(-val), (Value::I64(val), UnOpType::Negate) => Value::I64(-val),
(Value::I64(val), UnOpType::BNot) => Value::I64(!val),
// _ => panic!("Value type is not compatible with unary operation"), // _ => panic!("Value type is not compatible with unary operation"),
} }
} }

View File

@ -43,6 +43,9 @@ pub enum Token {
/// Shift Right (>>) /// Shift Right (>>)
Shr, Shr,
/// Tilde (~)
Tilde,
/// End of file /// End of file
EoF, EoF,
} }
@ -107,6 +110,7 @@ impl<'a> Lexer<'a> {
'^' => tokens.push(Token::BXor), '^' => tokens.push(Token::BXor),
'(' => tokens.push(Token::LParen), '(' => tokens.push(Token::LParen),
')' => tokens.push(Token::RParen), ')' => tokens.push(Token::RParen),
'~' => tokens.push(Token::Tilde),
//TODO: Don't panic, keep calm //TODO: Don't panic, keep calm
_ => panic!("Lexer encountered unexpected char: '{}'", ch), _ => panic!("Lexer encountered unexpected char: '{}'", ch),

View File

@ -40,6 +40,9 @@ pub enum BinOpType {
pub enum UnOpType { pub enum UnOpType {
/// Unary Negate /// Unary Negate
Negate, Negate,
/// Bitwise Not
BNot,
} }
#[derive(Debug, PartialEq, Eq, Clone)] #[derive(Debug, PartialEq, Eq, Clone)]
@ -55,7 +58,7 @@ pub enum Ast {
/* /*
## Grammar ## Grammar
### Expressions ### Expressions
expr_primary = LITERAL | "(" expr p | "-" expr_primary expr_primary = LITERAL | "(" expr p | "-" expr_primary | "~" expr_primary
expr_mul = expr_primary (("*" | "/" | "%") expr_primary)* expr_mul = expr_primary (("*" | "/" | "%") expr_primary)*
expr_add = expr_mul (("+" | "-") expr_mul)* expr_add = expr_mul (("+" | "-") expr_mul)*
expr_shift = expr_add ((">>" | "<<") expr_add)* expr_shift = expr_add ((">>" | "<<") expr_add)*
@ -137,6 +140,11 @@ impl<T: Iterator<Item = Token>> Parser<T> {
Ast::UnOp(UnOpType::Negate, operand.into()) Ast::UnOp(UnOpType::Negate, operand.into())
} }
Token::Tilde => {
let operand = self.parse_primary();
Ast::UnOp(UnOpType::BNot, operand.into())
}
tok => panic!("Error parsing primary expr: Unexpected Token '{:?}'", tok), tok => panic!("Error parsing primary expr: Unexpected Token '{:?}'", tok),
} }
} }