add logical or and logical and
This commit is contained in:
		
							
								
								
									
										4
									
								
								ir.c
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								ir.c
									
									
									
									
									
								
							@@ -14,6 +14,8 @@ const char *irinstr_str[IRInstrEnumSize] = {
 | 
				
			|||||||
	[IRLt]  = "lt",
 | 
						[IRLt]  = "lt",
 | 
				
			||||||
	[IRLe]  = "le",
 | 
						[IRLe]  = "le",
 | 
				
			||||||
	[IRNot] = "not",
 | 
						[IRNot] = "not",
 | 
				
			||||||
 | 
						[IRAnd] = "and",
 | 
				
			||||||
 | 
						[IROr]  = "or",
 | 
				
			||||||
	[IRJmp] = "jmp",
 | 
						[IRJmp] = "jmp",
 | 
				
			||||||
	[IRJnz] = "jnz",
 | 
						[IRJnz] = "jnz",
 | 
				
			||||||
	[IRCallInternal] = "calli",
 | 
						[IRCallInternal] = "calli",
 | 
				
			||||||
@@ -119,6 +121,8 @@ void print_ir(IRToks *v, const BuiltinFunc *builtin_funcs) {
 | 
				
			|||||||
			case IREq:
 | 
								case IREq:
 | 
				
			||||||
			case IRLt:
 | 
								case IRLt:
 | 
				
			||||||
			case IRLe:
 | 
								case IRLe:
 | 
				
			||||||
 | 
								case IRAnd:
 | 
				
			||||||
 | 
								case IROr:
 | 
				
			||||||
				printf(" %%%zx ", v->toks[i].Binary.addr);
 | 
									printf(" %%%zx ", v->toks[i].Binary.addr);
 | 
				
			||||||
				print_irparam(&v->toks[i].Binary.lhs);
 | 
									print_irparam(&v->toks[i].Binary.lhs);
 | 
				
			||||||
				printf(" ");
 | 
									printf(" ");
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										2
									
								
								ir.h
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								ir.h
									
									
									
									
									
								
							@@ -22,6 +22,8 @@ enum IRInstr {
 | 
				
			|||||||
	IRLt,
 | 
						IRLt,
 | 
				
			||||||
	IRLe,
 | 
						IRLe,
 | 
				
			||||||
	IRNot,
 | 
						IRNot,
 | 
				
			||||||
 | 
						IRAnd,
 | 
				
			||||||
 | 
						IROr,
 | 
				
			||||||
	IRJmp,
 | 
						IRJmp,
 | 
				
			||||||
	IRJnz,
 | 
						IRJnz,
 | 
				
			||||||
	IRCallInternal,
 | 
						IRCallInternal,
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										14
									
								
								lex.c
									
									
									
									
									
								
							
							
						
						
									
										14
									
								
								lex.c
									
									
									
									
									
								
							@@ -218,6 +218,20 @@ TokList lex(const char *s) {
 | 
				
			|||||||
					continue;
 | 
										continue;
 | 
				
			||||||
				}
 | 
									}
 | 
				
			||||||
				break;
 | 
									break;
 | 
				
			||||||
 | 
								case '&':
 | 
				
			||||||
 | 
									consume(&pos, *(s++));
 | 
				
			||||||
 | 
									if (s[0] == '&') {
 | 
				
			||||||
 | 
										emit(&toks, &pos, (Tok){ .kind = TokOp, .Op = OpAnd });
 | 
				
			||||||
 | 
									} else
 | 
				
			||||||
 | 
										continue;
 | 
				
			||||||
 | 
									break;
 | 
				
			||||||
 | 
								case '|':
 | 
				
			||||||
 | 
									consume(&pos, *(s++));
 | 
				
			||||||
 | 
									if (s[0] == '|') {
 | 
				
			||||||
 | 
										emit(&toks, &pos, (Tok){ .kind = TokOp, .Op = OpOr });
 | 
				
			||||||
 | 
									} else
 | 
				
			||||||
 | 
										continue;
 | 
				
			||||||
 | 
									break;
 | 
				
			||||||
			case '{':
 | 
								case '{':
 | 
				
			||||||
			case '}':
 | 
								case '}':
 | 
				
			||||||
			case '(':
 | 
								case '(':
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										4
									
								
								parse.c
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								parse.c
									
									
									
									
									
								
							@@ -56,6 +56,8 @@ static void set_irtok_dest_addr(IRTok *t, size_t addr) {
 | 
				
			|||||||
		case IREq:
 | 
							case IREq:
 | 
				
			||||||
		case IRLt:
 | 
							case IRLt:
 | 
				
			||||||
		case IRLe:
 | 
							case IRLe:
 | 
				
			||||||
 | 
							case IRAnd:
 | 
				
			||||||
 | 
							case IROr:
 | 
				
			||||||
			t->Binary.addr = addr;
 | 
								t->Binary.addr = addr;
 | 
				
			||||||
			break;
 | 
								break;
 | 
				
			||||||
		case IRCallInternal:
 | 
							case IRCallInternal:
 | 
				
			||||||
@@ -446,6 +448,8 @@ static ExprRet expr(IRToks *out_ir, TokList *toks, Map *funcs, Scope *parent_sc,
 | 
				
			|||||||
				case OpLe:  instr = IRLe;  break;
 | 
									case OpLe:  instr = IRLe;  break;
 | 
				
			||||||
				case OpGt:  instr = IRLt; swap_operands = true; break;
 | 
									case OpGt:  instr = IRLt; swap_operands = true; break;
 | 
				
			||||||
				case OpGe:  instr = IRLe; swap_operands = true; break;
 | 
									case OpGe:  instr = IRLe; swap_operands = true; break;
 | 
				
			||||||
 | 
									case OpAnd: instr = IRAnd; break;
 | 
				
			||||||
 | 
									case OpOr:  instr = IROr;  break;
 | 
				
			||||||
				default:
 | 
									default:
 | 
				
			||||||
					mark_err(l_op);
 | 
										mark_err(l_op);
 | 
				
			||||||
					set_err("Unknown operation: '%s'", op_str[l_op->Op]);
 | 
										set_err("Unknown operation: '%s'", op_str[l_op->Op]);
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										12
									
								
								runtime.c
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								runtime.c
									
									
									
									
									
								
							@@ -65,6 +65,18 @@ Value eval_binary(IRInstr instr, const Value *lhs, const Value *rhs) {
 | 
				
			|||||||
				.type.kind = TypeBool,
 | 
									.type.kind = TypeBool,
 | 
				
			||||||
				.Bool = res,
 | 
									.Bool = res,
 | 
				
			||||||
			};
 | 
								};
 | 
				
			||||||
 | 
							case IRAnd:
 | 
				
			||||||
 | 
								return (Value){
 | 
				
			||||||
 | 
									.type.kind = TypeBool,
 | 
				
			||||||
 | 
									.Bool = is_nonzero(lhs) && is_nonzero(rhs),
 | 
				
			||||||
 | 
								};
 | 
				
			||||||
 | 
								break;
 | 
				
			||||||
 | 
							case IROr:
 | 
				
			||||||
 | 
								return (Value){
 | 
				
			||||||
 | 
									.type.kind = TypeBool,
 | 
				
			||||||
 | 
									.Bool = is_nonzero(lhs) || is_nonzero(rhs),
 | 
				
			||||||
 | 
								};
 | 
				
			||||||
 | 
								break;
 | 
				
			||||||
		default:
 | 
							default:
 | 
				
			||||||
			ASSERT_UNREACHED();
 | 
								ASSERT_UNREACHED();
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										22
									
								
								tok.c
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								tok.c
									
									
									
									
									
								
							@@ -11,15 +11,17 @@ int8_t op_prec[OperatorEnumSize] = {
 | 
				
			|||||||
	[OpLCurl]  = PREC_DELIM,
 | 
						[OpLCurl]  = PREC_DELIM,
 | 
				
			||||||
	[OpRParen] = PREC_DELIM,
 | 
						[OpRParen] = PREC_DELIM,
 | 
				
			||||||
	[OpComma]  = PREC_DELIM,
 | 
						[OpComma]  = PREC_DELIM,
 | 
				
			||||||
	[OpEq]     = 0,
 | 
						[OpAnd]    = 0,
 | 
				
			||||||
	[OpLt]     = 0,
 | 
						[OpOr]     = 0,
 | 
				
			||||||
	[OpGt]     = 0,
 | 
						[OpEq]     = 1,
 | 
				
			||||||
	[OpLe]     = 0,
 | 
						[OpLt]     = 1,
 | 
				
			||||||
	[OpGe]     = 0,
 | 
						[OpGt]     = 1,
 | 
				
			||||||
	[OpAdd]    = 1,
 | 
						[OpLe]     = 1,
 | 
				
			||||||
	[OpSub]    = 1,
 | 
						[OpGe]     = 1,
 | 
				
			||||||
	[OpMul]    = 2,
 | 
						[OpAdd]    = 2,
 | 
				
			||||||
	[OpDiv]    = 2,
 | 
						[OpSub]    = 2,
 | 
				
			||||||
 | 
						[OpMul]    = 3,
 | 
				
			||||||
 | 
						[OpDiv]    = 3,
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const char *op_str[OperatorEnumSize] = {
 | 
					const char *op_str[OperatorEnumSize] = {
 | 
				
			||||||
@@ -40,6 +42,8 @@ const char *op_str[OperatorEnumSize] = {
 | 
				
			|||||||
	[OpGt]     = ">",
 | 
						[OpGt]     = ">",
 | 
				
			||||||
	[OpLe]     = "<=",
 | 
						[OpLe]     = "<=",
 | 
				
			||||||
	[OpGe]     = ">=",
 | 
						[OpGe]     = ">=",
 | 
				
			||||||
 | 
						[OpAnd]    = "&&",
 | 
				
			||||||
 | 
						[OpOr]     = "||",
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const char *tok_str[TokKindEnumSize] = {
 | 
					const char *tok_str[TokKindEnumSize] = {
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										2
									
								
								tok.h
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								tok.h
									
									
									
									
									
								
							@@ -47,6 +47,8 @@ enum Operator {
 | 
				
			|||||||
	OpGt,
 | 
						OpGt,
 | 
				
			||||||
	OpLe,
 | 
						OpLe,
 | 
				
			||||||
	OpGe,
 | 
						OpGe,
 | 
				
			||||||
 | 
						OpAnd,
 | 
				
			||||||
 | 
						OpOr,
 | 
				
			||||||
	OpNewLn,
 | 
						OpNewLn,
 | 
				
			||||||
	OpEOF,
 | 
						OpEOF,
 | 
				
			||||||
	OperatorEnumSize,
 | 
						OperatorEnumSize,
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										2
									
								
								vm.c
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								vm.c
									
									
									
									
									
								
							@@ -67,6 +67,8 @@ void run(const IRToks *ir, const BuiltinFunc *builtin_funcs) {
 | 
				
			|||||||
			case IREq:
 | 
								case IREq:
 | 
				
			||||||
			case IRLt:
 | 
								case IRLt:
 | 
				
			||||||
			case IRLe:
 | 
								case IRLe:
 | 
				
			||||||
 | 
								case IRAnd:
 | 
				
			||||||
 | 
								case IROr:
 | 
				
			||||||
				stack_fit(&s, instr->Binary.addr);
 | 
									stack_fit(&s, instr->Binary.addr);
 | 
				
			||||||
				TRY_ELSE(s.mem[instr->Binary.addr] = eval_binary(instr->instr,
 | 
									TRY_ELSE(s.mem[instr->Binary.addr] = eval_binary(instr->instr,
 | 
				
			||||||
					irparam_to_val(&s, &instr->Binary.lhs),
 | 
										irparam_to_val(&s, &instr->Binary.lhs),
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user