Implement binary in the lexer

Signed-off-by: Slendi <slendi@socopon.com>
This commit is contained in:
Slendi 2024-02-28 16:34:40 +02:00
parent 9521ba6f5f
commit 7ab94d4ed5
4 changed files with 58 additions and 4 deletions

View File

@ -369,10 +369,10 @@ lexer_read_number :: proc(lexer: ^Lexer) -> Token {
end = lexer.position,
}
// FIXME: Implement binary
ReadMode :: enum {
Normal,
Hex,
Binary,
}
read_mode := ReadMode.Normal
@ -381,6 +381,11 @@ lexer_read_number :: proc(lexer: ^Lexer) -> Token {
lexer_advance(lexer)
crange.end = lexer.position
lexer_advance(lexer)
} else if lexer.char == '0' && lexer.next == 'b' {
read_mode = .Binary
lexer_advance(lexer)
crange.end = lexer.position
lexer_advance(lexer)
}
whole_part: u64 = 0
@ -402,6 +407,12 @@ lexer_read_number :: proc(lexer: ^Lexer) -> Token {
lexer_advance(lexer)
}
whole_part = whole_part >> 4
} else if read_mode == .Binary {
for lexer.char == '0' || lexer.char == '1' {
whole_part = (whole_part << 1) + u64(lexer.char) - '0'
crange.end = lexer.position
lexer_advance(lexer)
}
}
if lexer.char == '.' {
@ -435,6 +446,20 @@ lexer_read_number :: proc(lexer: ^Lexer) -> Token {
lexer_advance(lexer)
}
fractional_part = fractional_part / 16
} else if read_mode == .Binary {
append(
&g_message_list,
message_create(
.Error,
"Binary floating point numbers are not supported yet",
crange,
),
)
for lexer.char == '0' || lexer.char == '1' {
fractional_part = (fractional_part << 1) + u64(lexer.char) - '0'
crange.end = lexer.position
lexer_advance(lexer)
}
}
fractional_part_clone := fractional_part

View File

@ -3,12 +3,17 @@ package main
TypeKind :: enum {
Integer,
Float,
Pointer,
Array,
}
Type :: struct {
kind: TypeKind,
bit_size: u8,
is_signed: bool,
pointer_to: ^Type,
array_of: ^Type,
array_size: u64,
}
FunctionType :: struct {
@ -19,6 +24,15 @@ FunctionType :: struct {
compare_types :: proc(a: ^Type, b: ^Type) -> (ret: bool) {
ret = a != nil && b != nil && a.kind == b.kind && a.bit_size == b.bit_size && a.is_signed == b.is_signed
if ret == false {
return
}
if a.kind == .Pointer {
ret = compare_types(a.pointer_to, b.pointer_to)
} else if a.kind == .Array {
ret = a.array_size == b.array_size && compare_types(a.array_of, b.array_of)
}
return
}
@ -55,3 +69,18 @@ type_create_float :: proc(bit_size: u8) -> (ret: ^Type) {
ret.is_signed = true
return
}
type_create_pointer :: proc(to: ^Type) -> (ret: ^Type) {
ret = new(Type)
ret.kind = .Pointer
ret.pointer_to = to
return
}
type_create_array :: proc(of: ^Type, size: u64) -> (ret: ^Type) {
ret = new(Type)
ret.kind = .Array
ret.array_of = of
ret.array_size = size
return
}

View File

@ -16,7 +16,7 @@ infer_type :: proc(parent: ^Node, child: ^Node) {
#partial switch child.kind {
case .Integer: child.return_type = type_create_integer(32, true)
case .Float: child.return_type = type_create_float(32)
case .String: panic("FIXME: Add support for arrays")
case .String: child.return_type = type_create_array(type_create_integer(32, false), 0)
case .Character: child.return_type = type_create_integer(32, false)
}
} else {

View File

@ -1,8 +1,8 @@
let asdf := 123.0
let asdf := 0b1101 as f32
let poop :: 12.0 + 2.0 * asdf
fn name(a b: f32) i32 {
ret (a + b) as i32
}
name 123 456.0
name 123.0 456.0