Add support for comparison operators
Signed-off-by: Slendi <slendi@socopon.com>
This commit is contained in:
parent
92c8509125
commit
71c337a3f4
@ -254,6 +254,72 @@ generate_llvm :: proc(ctx: LLVMContextRef, mod: LLVMModuleRef, builder: LLVMBuil
|
|||||||
return LLVMBuildURem(builder, lhs, rhs, "modtmp")
|
return LLVMBuildURem(builder, lhs, rhs, "modtmp")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
case .BitwiseLeftShift:
|
||||||
|
return LLVMBuildShl(builder, lhs, rhs, "shltmp")
|
||||||
|
case .BitwiseRightShift:
|
||||||
|
if is_signed {
|
||||||
|
return LLVMBuildAShr(builder, lhs, rhs, "ashrtmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildLShr(builder, lhs, rhs, "lshrtmp")
|
||||||
|
}
|
||||||
|
case .BitwiseAnd:
|
||||||
|
return LLVMBuildAnd(builder, lhs, rhs, "andtmp")
|
||||||
|
case .BitwiseOr:
|
||||||
|
return LLVMBuildOr(builder, lhs, rhs, "ortmp")
|
||||||
|
case .BitwiseXOR:
|
||||||
|
return LLVMBuildXor(builder, lhs, rhs, "xortmp")
|
||||||
|
case .Equals:
|
||||||
|
if is_float {
|
||||||
|
return LLVMBuildFCmp(builder, .LLVMRealOEQ, lhs, rhs, "eqtmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntEQ, lhs, rhs, "eqtmp")
|
||||||
|
}
|
||||||
|
case .NotEquals:
|
||||||
|
if is_float {
|
||||||
|
return LLVMBuildFCmp(builder, .LLVMRealONE, lhs, rhs, "neqtmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntNE, lhs, rhs, "neqtmp")
|
||||||
|
}
|
||||||
|
case .LessThan:
|
||||||
|
if is_float {
|
||||||
|
return LLVMBuildFCmp(builder, .LLVMRealOLT, lhs, rhs, "lttmp")
|
||||||
|
} else {
|
||||||
|
if is_signed {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntSLT, lhs, rhs, "lttmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntULT, lhs, rhs, "lttmp")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case .LessThanOrEqual:
|
||||||
|
if is_float {
|
||||||
|
return LLVMBuildFCmp(builder, .LLVMRealOLE, lhs, rhs, "letmp")
|
||||||
|
} else {
|
||||||
|
if is_signed {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntSLE, lhs, rhs, "letmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntULE, lhs, rhs, "letmp")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case .GreaterThan:
|
||||||
|
if is_float {
|
||||||
|
return LLVMBuildFCmp(builder, .LLVMRealOGT, lhs, rhs, "gttmp")
|
||||||
|
} else {
|
||||||
|
if is_signed {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntSGT, lhs, rhs, "gttmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntUGT, lhs, rhs, "gttmp")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case .GreaterThanOrEqual:
|
||||||
|
if is_float {
|
||||||
|
return LLVMBuildFCmp(builder, .LLVMRealOGE, lhs, rhs, "getmp")
|
||||||
|
} else {
|
||||||
|
if is_signed {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntSGE, lhs, rhs, "getmp")
|
||||||
|
} else {
|
||||||
|
return LLVMBuildICmp(builder, .LLVMIntUGE, lhs, rhs, "getmp")
|
||||||
|
}
|
||||||
|
}
|
||||||
case:
|
case:
|
||||||
fmt.panicf("LLVM-C: Unexpected binary expression kind: {}", op)
|
fmt.panicf("LLVM-C: Unexpected binary expression kind: {}", op)
|
||||||
}
|
}
|
||||||
@ -273,7 +339,16 @@ generate_llvm :: proc(ctx: LLVMContextRef, mod: LLVMModuleRef, builder: LLVMBuil
|
|||||||
if condition == nil {
|
if condition == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
int_32_type := LLVMInt32TypeInContext(ctx)
|
int_32_type : LLVMTypeRef
|
||||||
|
if condition_node.return_type.kind == .Float {
|
||||||
|
if condition_node.return_type.bit_size == 64 {
|
||||||
|
int_32_type = LLVMDoubleTypeInContext(ctx)
|
||||||
|
} else {
|
||||||
|
int_32_type = LLVMFloatTypeInContext(ctx)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
int_32_type = LLVMIntTypeInContext(ctx, uint(condition_node.return_type.bit_size))
|
||||||
|
}
|
||||||
comparison_res := LLVMBuildICmp(builder, .LLVMIntNE, condition, LLVMConstInt(int_32_type, 0, LLVMBool(1)), "")
|
comparison_res := LLVMBuildICmp(builder, .LLVMIntNE, condition, LLVMConstInt(int_32_type, 0, LLVMBool(1)), "")
|
||||||
|
|
||||||
true_block := LLVMAppendBasicBlockInContext(ctx, function, "")
|
true_block := LLVMAppendBasicBlockInContext(ctx, function, "")
|
||||||
|
@ -59,6 +59,25 @@ LLVMIntPredicate :: enum {
|
|||||||
LLVMIntSLE,
|
LLVMIntSLE,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
LLVMRealPredicate :: enum {
|
||||||
|
LLVMRealPredicateFalse,
|
||||||
|
LLVMRealOEQ,
|
||||||
|
LLVMRealOGT,
|
||||||
|
LLVMRealOGE,
|
||||||
|
LLVMRealOLT,
|
||||||
|
LLVMRealOLE,
|
||||||
|
LLVMRealONE,
|
||||||
|
LLVMRealORD,
|
||||||
|
LLVMRealUNO,
|
||||||
|
LLVMRealUEQ,
|
||||||
|
LLVMRealUGT,
|
||||||
|
LLVMRealUGE,
|
||||||
|
LLVMRealULT,
|
||||||
|
LLVMRealULE,
|
||||||
|
LLVMRealUNE,
|
||||||
|
LLVMRealPredicateTrue
|
||||||
|
};
|
||||||
|
|
||||||
@(default_calling_convention = "std")
|
@(default_calling_convention = "std")
|
||||||
foreign llvmc {
|
foreign llvmc {
|
||||||
LLVMContextCreate :: proc() -> LLVMContextRef ---
|
LLVMContextCreate :: proc() -> LLVMContextRef ---
|
||||||
@ -89,6 +108,8 @@ foreign llvmc {
|
|||||||
|
|
||||||
LLVMVoidTypeInContext :: proc(C: LLVMContextRef) -> LLVMTypeRef ---
|
LLVMVoidTypeInContext :: proc(C: LLVMContextRef) -> LLVMTypeRef ---
|
||||||
|
|
||||||
|
LLVMGetTypeKind :: proc(Ty: LLVMTypeRef) -> LLVMTypeKind ---
|
||||||
|
|
||||||
LLVMArrayType2 :: proc(ElementType: LLVMTypeRef, ElementCount: u64) -> LLVMTypeRef ---
|
LLVMArrayType2 :: proc(ElementType: LLVMTypeRef, ElementCount: u64) -> LLVMTypeRef ---
|
||||||
LLVMPointerType :: proc(ElementType: LLVMTypeRef, AddressSpace: uint) -> LLVMTypeRef ---
|
LLVMPointerType :: proc(ElementType: LLVMTypeRef, AddressSpace: uint) -> LLVMTypeRef ---
|
||||||
|
|
||||||
@ -128,6 +149,16 @@ foreign llvmc {
|
|||||||
LLVMBuildBr :: proc(Builder: LLVMBuilderRef, Dest: LLVMBasicBlockRef) -> LLVMValueRef ---
|
LLVMBuildBr :: proc(Builder: LLVMBuilderRef, Dest: LLVMBasicBlockRef) -> LLVMValueRef ---
|
||||||
LLVMBuildCondBr :: proc(Builder: LLVMBuilderRef, If: LLVMValueRef, Then: LLVMBasicBlockRef, Else: LLVMBasicBlockRef) -> LLVMValueRef ---
|
LLVMBuildCondBr :: proc(Builder: LLVMBuilderRef, If: LLVMValueRef, Then: LLVMBasicBlockRef, Else: LLVMBasicBlockRef) -> LLVMValueRef ---
|
||||||
LLVMBuildICmp :: proc(Builder: LLVMBuilderRef, Predicate: LLVMIntPredicate, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
LLVMBuildICmp :: proc(Builder: LLVMBuilderRef, Predicate: LLVMIntPredicate, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildFCmp :: proc(Builder: LLVMBuilderRef, Predicate: LLVMRealPredicate, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
|
||||||
|
LLVMBuildAnd :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildOr :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildXor :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildNot :: proc(Builder: LLVMBuilderRef, Val: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildShl :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildLShr :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildAShr :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
LLVMBuildShr :: proc(Builder: LLVMBuilderRef, LHS: LLVMValueRef, RHS: LLVMValueRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
|
||||||
LLVMBuildPhi :: proc(Builder: LLVMBuilderRef, Ty: LLVMTypeRef, Name: cstring) -> LLVMValueRef ---
|
LLVMBuildPhi :: proc(Builder: LLVMBuilderRef, Ty: LLVMTypeRef, Name: cstring) -> LLVMValueRef ---
|
||||||
|
|
||||||
|
@ -237,7 +237,10 @@ type_check :: proc(ast: ^Node, parent_ast: ^Node) {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ast.return_type = ast.children[0].return_type
|
||||||
|
|
||||||
if ast.value_token_kind == .Assign {
|
if ast.value_token_kind == .Assign {
|
||||||
|
ast.return_type = nil
|
||||||
if !scope_stack[len(scope_stack) - 1].variable_mutability_definitions[get_character_sum_of_dyn_arr(&ast.children[0].value.([dynamic]u8))] {
|
if !scope_stack[len(scope_stack) - 1].variable_mutability_definitions[get_character_sum_of_dyn_arr(&ast.children[0].value.([dynamic]u8))] {
|
||||||
append(&g_message_list,
|
append(&g_message_list,
|
||||||
message_create(
|
message_create(
|
||||||
@ -247,10 +250,12 @@ type_check :: proc(ast: ^Node, parent_ast: ^Node) {
|
|||||||
),
|
),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
} else if ast.value_token_kind == .Equals || ast.value_token_kind == .NotEquals ||
|
||||||
|
ast.value_token_kind == .GreaterThan || ast.value_token_kind == .GreaterThanOrEqual ||
|
||||||
|
ast.value_token_kind == .LessThan || ast.value_token_kind == .LessThanOrEqual {
|
||||||
|
ast.return_type = type_create_integer(1, true)
|
||||||
}
|
}
|
||||||
|
|
||||||
ast.return_type = ast.children[0].return_type
|
|
||||||
|
|
||||||
// FIXME: Verify that the operation is possible
|
// FIXME: Verify that the operation is possible
|
||||||
case .UnaryExpression:
|
case .UnaryExpression:
|
||||||
// FIXME: Verify that the operation is possible
|
// FIXME: Verify that the operation is possible
|
||||||
|
@ -7,16 +7,18 @@
|
|||||||
|
|
||||||
\name 123.0 456.0
|
\name 123.0 456.0
|
||||||
|
|
||||||
let arr: []i32, arr2: [69]u8, ptr: ^i32
|
\let arr: []i32, arr2: [69]u8, ptr: ^i32
|
||||||
|
|
||||||
fn put_i32(val: i32) i32
|
fn put_i32(val: i32) i32
|
||||||
|
|
||||||
let amogus := 500 + (put_i32 8008135)
|
\let amogus := 500 + (put_i32 8008135)
|
||||||
|
\
|
||||||
|
\put_i32 69 * amogus + 420
|
||||||
|
|
||||||
put_i32 69 * amogus + 420
|
let a b := 5 1
|
||||||
|
|
||||||
if 0 {
|
if a == 5 {
|
||||||
if 0 {
|
if b {
|
||||||
put_i32 123
|
put_i32 123
|
||||||
} else {
|
} else {
|
||||||
put_i32 69
|
put_i32 69
|
||||||
|
Loading…
x
Reference in New Issue
Block a user