From 1ca61190eb5bf75bc8f5aee5b805367bc2d8c995 Mon Sep 17 00:00:00 2001 From: Eduard Urbach Date: Fri, 21 Feb 2025 13:47:56 +0100 Subject: [PATCH] Fixed incorrect const values --- examples/array/array.q | 4 ++-- lib/log/number.q | 2 +- lib/mem/alloc_mac.q | 22 ---------------------- lib/mem/{alloc_linux.q => alloc_unix.q} | 10 ---------- lib/mem/alloc_windows.q | 15 ++++----------- lib/mem/const_linux.q | 9 +++++++++ lib/mem/const_mac.q | 9 +++++++++ lib/mem/const_windows.q | 9 +++++++++ lib/mem/{free.q => free_unix.q} | 0 lib/mem/free_windows.q | 7 +++++++ lib/sys/sys_linux.q | 12 ++++++------ lib/sys/sys_mac.q | 4 ++-- lib/sys/sys_windows.q | 22 ++++------------------ lib/thread/thread_linux.q | 2 +- src/core/Constant.go | 2 +- src/core/ExpressionToRegister.go | 8 +++++--- src/core/Fold.go | 2 +- src/core/PeriodToRegister.go | 10 +++++++++- src/core/ToNumber.go | 18 ++++++++++++------ src/scanner/queueDirectory.go | 4 ++++ src/scanner/scanConst.go | 8 ++++---- src/scanner/scanExtern.go | 6 +++--- 22 files changed, 93 insertions(+), 92 deletions(-) delete mode 100644 lib/mem/alloc_mac.q rename lib/mem/{alloc_linux.q => alloc_unix.q} (68%) create mode 100644 lib/mem/const_linux.q create mode 100644 lib/mem/const_mac.q create mode 100644 lib/mem/const_windows.q rename lib/mem/{free.q => free_unix.q} (100%) create mode 100644 lib/mem/free_windows.q diff --git a/examples/array/array.q b/examples/array/array.q index 4f17ef0..0000ad3 100644 --- a/examples/array/array.q +++ b/examples/array/array.q @@ -1,5 +1,5 @@ +import io import mem -import sys main() { length := 5 @@ -9,6 +9,6 @@ main() { address[2] = 'l' address[3] = 'l' address[4] = 'o' - sys.write(1, address, length) + io.write(1, address) mem.free(address) } \ No newline at end of file diff --git a/lib/log/number.q b/lib/log/number.q index 4945f93..230571c 100644 --- a/lib/log/number.q +++ b/lib/log/number.q @@ -8,7 +8,7 @@ number(x int) { mem.free(buffer) } -itoa(x int, buffer []byte) -> (*any, int) { +itoa(x int, buffer []byte) -> (*byte, int) { end := buffer + len(buffer) tmp := end digit := 0 diff --git a/lib/mem/alloc_mac.q b/lib/mem/alloc_mac.q deleted file mode 100644 index a559240..0000000 --- a/lib/mem/alloc_mac.q +++ /dev/null @@ -1,22 +0,0 @@ -import sys - -alloc(length int) -> []byte { - x := sys.mmap(0, length+8, prot.read|prot.write, map.private|map.anonymous) - - if x < 0x1000 { - return x - } - - store(x, 8, length) - return x + 8 -} - -const prot { - read 0x1 - write 0x2 -} - -const map { - private 0x02 - anonymous 0x1000 -} \ No newline at end of file diff --git a/lib/mem/alloc_linux.q b/lib/mem/alloc_unix.q similarity index 68% rename from lib/mem/alloc_linux.q rename to lib/mem/alloc_unix.q index 061693a..e12a331 100644 --- a/lib/mem/alloc_linux.q +++ b/lib/mem/alloc_unix.q @@ -9,14 +9,4 @@ alloc(length int) -> []byte { store(x, 8, length) return x + 8 -} - -const prot { - read 0x1 - write 0x2 -} - -const map { - private 0x02 - anonymous 0x20 } \ No newline at end of file diff --git a/lib/mem/alloc_windows.q b/lib/mem/alloc_windows.q index d48fe0a..3eda616 100644 --- a/lib/mem/alloc_windows.q +++ b/lib/mem/alloc_windows.q @@ -1,7 +1,9 @@ -import sys +extern kernel32 { + VirtualAlloc(address int, size uint, flags uint32, protection uint32) -> *any +} alloc(length int) -> []byte { - x := sys.mmap(0, length+8, page.readwrite, mem.commit|mem.reserve) + x := kernel32.VirtualAlloc(0, length+8, mem.commit|mem.reserve, page.readwrite) if x < 0x1000 { return x @@ -9,13 +11,4 @@ alloc(length int) -> []byte { store(x, 8, length) return x + 8 -} - -const page { - readwrite 0x0004 -} - -const mem { - commit 0x1000 - reserve 0x2000 } \ No newline at end of file diff --git a/lib/mem/const_linux.q b/lib/mem/const_linux.q new file mode 100644 index 0000000..9193a01 --- /dev/null +++ b/lib/mem/const_linux.q @@ -0,0 +1,9 @@ +const prot { + read 0x1 + write 0x2 +} + +const map { + private 0x02 + anonymous 0x20 +} \ No newline at end of file diff --git a/lib/mem/const_mac.q b/lib/mem/const_mac.q new file mode 100644 index 0000000..7aac429 --- /dev/null +++ b/lib/mem/const_mac.q @@ -0,0 +1,9 @@ +const prot { + read 0x1 + write 0x2 +} + +const map { + private 0x02 + anonymous 0x1000 +} \ No newline at end of file diff --git a/lib/mem/const_windows.q b/lib/mem/const_windows.q new file mode 100644 index 0000000..7008e67 --- /dev/null +++ b/lib/mem/const_windows.q @@ -0,0 +1,9 @@ +const page { + readwrite 0x0004 +} + +const mem { + commit 0x1000 + reserve 0x2000 + decommit 0x4000 +} \ No newline at end of file diff --git a/lib/mem/free.q b/lib/mem/free_unix.q similarity index 100% rename from lib/mem/free.q rename to lib/mem/free_unix.q diff --git a/lib/mem/free_windows.q b/lib/mem/free_windows.q new file mode 100644 index 0000000..1bb258a --- /dev/null +++ b/lib/mem/free_windows.q @@ -0,0 +1,7 @@ +extern kernel32 { + VirtualFree(address *any, size uint, type uint32) -> bool +} + +free(address []any) -> int { + return kernel32.VirtualFree(address-8, len(address)+8, mem.decommit) +} \ No newline at end of file diff --git a/lib/sys/sys_linux.q b/lib/sys/sys_linux.q index f35439b..4d82732 100644 --- a/lib/sys/sys_linux.q +++ b/lib/sys/sys_linux.q @@ -1,8 +1,8 @@ -read(fd int, buffer *any, length int) -> int { +read(fd int, buffer *byte, length int) -> int { return syscall(0, fd, buffer, length) } -write(fd int, buffer *any, length int) -> int { +write(fd int, buffer *byte, length int) -> int { return syscall(1, fd, buffer, length) } @@ -14,16 +14,16 @@ close(fd int) -> int { return syscall(3, fd) } -mmap(address int, length int, protection int, flags int) -> *any { +mmap(address int, length uint, protection int, flags int) -> *any { return syscall(9, address, length, protection, flags) } -munmap(address *any, length int) -> int { +munmap(address *any, length uint) -> int { return syscall(11, address, length) } -clone(flags int, stack *any) -> int { - return syscall(56, flags, stack) +clone(flags uint, stack *any, parent *int, child *int, tls uint) -> int { + return syscall(56, flags, stack, parent, child, tls) } fork() -> int { diff --git a/lib/sys/sys_mac.q b/lib/sys/sys_mac.q index 6c31517..aefa23e 100644 --- a/lib/sys/sys_mac.q +++ b/lib/sys/sys_mac.q @@ -1,8 +1,8 @@ -read(fd int, buffer *any, length int) -> int { +read(fd int, buffer *byte, length int) -> int { return syscall(0x2000003, fd, buffer, length) } -write(fd int, buffer *any, length int) -> int { +write(fd int, buffer *byte, length int) -> int { return syscall(0x2000004, fd, buffer, length) } diff --git a/lib/sys/sys_windows.q b/lib/sys/sys_windows.q index 1d67740..2523338 100644 --- a/lib/sys/sys_windows.q +++ b/lib/sys/sys_windows.q @@ -1,31 +1,17 @@ -read(fd int64, buffer *any, length int64) -> int64 { +read(fd int64, buffer *byte, length int64) -> int64 { fd = kernel32.GetStdHandle(-10 - fd) kernel32.ReadConsole(fd, buffer, length, 0) return length } -write(fd int64, buffer *any, length int64) -> int64 { +write(fd int64, buffer *byte, length int64) -> int64 { fd = kernel32.GetStdHandle(-10 - fd) kernel32.WriteConsoleA(fd, buffer, length, 0) return length } -mmap(address int, length int, protection int, flags int) -> *any { - return kernel32.VirtualAlloc(address, length, flags, protection) -} - -munmap(address *any, length int) -> int { - return kernel32.VirtualFree(address, length, mem.decommit) -} - -const mem { - decommit 0x4000 -} - extern kernel32 { GetStdHandle(handle int64) -> int64 - ReadConsole(fd int64, buffer *any, length uint32, written *uint32) -> bool - VirtualAlloc(address int, length int, flags int, protection int) - VirtualFree(address *any, length int, type int) -> bool - WriteConsoleA(fd int64, buffer *any, length uint32, written *uint32) -> bool + ReadConsole(fd int64, buffer *byte, length uint32, written *uint32) -> bool + WriteConsoleA(fd int64, buffer *byte, length uint32, written *uint32) -> bool } \ No newline at end of file diff --git a/lib/thread/thread_linux.q b/lib/thread/thread_linux.q index e57fa17..cf4d75a 100644 --- a/lib/thread/thread_linux.q +++ b/lib/thread/thread_linux.q @@ -19,5 +19,5 @@ create(func *any) -> int { store(stack, 8, core.exit) stack -= 8 store(stack, 8, func) - return sys.clone(clone.vm|clone.fs|clone.files|clone.sighand|clone.parent|clone.thread|clone.io, stack) + return sys.clone(clone.vm|clone.fs|clone.files|clone.sighand|clone.parent|clone.thread|clone.io, stack, 0, 0, 0) } \ No newline at end of file diff --git a/src/core/Constant.go b/src/core/Constant.go index 1156e05..5fe78cf 100644 --- a/src/core/Constant.go +++ b/src/core/Constant.go @@ -8,6 +8,6 @@ import ( // Constant registers a single value to be accessible under a descriptive name. type Constant struct { Name string - Value token.Token + Token token.Token File *fs.File } diff --git a/src/core/ExpressionToRegister.go b/src/core/ExpressionToRegister.go index 056ebe1..785cb91 100644 --- a/src/core/ExpressionToRegister.go +++ b/src/core/ExpressionToRegister.go @@ -64,14 +64,16 @@ func (f *Function) ExpressionToRegister(node *expression.Expression, register cp f.FreeRegister(register) } - _, isArray := typ.(*types.Array) + arrayType, isArray := typ.(*types.Array) if isArray { - typ = types.AnyPointer + typ = &types.Pointer{To: arrayType.Of} } else if right.Token.Kind == token.Identifier { rightVariable := f.VariableByName(right.Token.Text(f.File.Bytes)) + leftPointer, leftIsPointer := typ.(*types.Pointer) + rightPointer, rightIsPointer := rightVariable.Type.(*types.Pointer) - if typ == types.AnyPointer && rightVariable.Type == types.AnyPointer { + if leftIsPointer && rightIsPointer && leftPointer.To == rightPointer.To { typ = types.Int } } diff --git a/src/core/Fold.go b/src/core/Fold.go index eaaf0cd..0f610e8 100644 --- a/src/core/Fold.go +++ b/src/core/Fold.go @@ -38,7 +38,7 @@ func (f *Function) Fold(expr *expression.Expression) error { return nil } - value, err := f.ToNumber(constant.Value) + value, err := ToNumber(constant.Token, constant.File) expr.Value = value expr.IsFolded = true return err diff --git a/src/core/PeriodToRegister.go b/src/core/PeriodToRegister.go index d915f85..fd2123b 100644 --- a/src/core/PeriodToRegister.go +++ b/src/core/PeriodToRegister.go @@ -36,7 +36,15 @@ func (f *Function) PeriodToRegister(node *expression.Expression, register cpu.Re constant, isConst := f.Constants[f.Package+"."+leftText+"."+rightText] if isConst { - return f.TokenToRegister(constant.Value, register) + number, err := ToNumber(constant.Token, constant.File) + + if err != nil { + return nil, err + } + + f.SaveRegister(register) + f.RegisterNumber(asm.MOVE, register, number) + return types.Int, nil } uniqueName := fmt.Sprintf("%s.%s", leftText, rightText) diff --git a/src/core/ToNumber.go b/src/core/ToNumber.go index 1978939..122b04d 100644 --- a/src/core/ToNumber.go +++ b/src/core/ToNumber.go @@ -6,15 +6,21 @@ import ( "unicode/utf8" "git.akyoto.dev/cli/q/src/errors" + "git.akyoto.dev/cli/q/src/fs" "git.akyoto.dev/cli/q/src/token" ) // ToNumber tries to convert the token into a numeric value. func (f *Function) ToNumber(t token.Token) (int, error) { + return ToNumber(t, f.File) +} + +// ToNumber tries to convert the token into a numeric value. +func ToNumber(t token.Token, file *fs.File) (int, error) { switch t.Kind { case token.Number: var ( - digits = t.Text(f.File.Bytes) + digits = t.Text(file.Bytes) number int64 err error ) @@ -31,27 +37,27 @@ func (f *Function) ToNumber(t token.Token) (int, error) { } if err != nil { - return 0, errors.New(errors.InvalidNumber, f.File, t.Position) + return 0, errors.New(errors.InvalidNumber, file, t.Position) } return int(number), nil case token.Rune: - r := t.Bytes(f.File.Bytes) + r := t.Bytes(file.Bytes) r = String(r) if len(r) == 0 { - return 0, errors.New(errors.InvalidRune, f.File, t.Position+1) + return 0, errors.New(errors.InvalidRune, file, t.Position+1) } number, size := utf8.DecodeRune(r) if len(r) > size { - return 0, errors.New(errors.InvalidRune, f.File, t.Position+1) + return 0, errors.New(errors.InvalidRune, file, t.Position+1) } return int(number), nil } - return 0, errors.New(errors.InvalidNumber, f.File, t.Position) + return 0, errors.New(errors.InvalidNumber, file, t.Position) } diff --git a/src/scanner/queueDirectory.go b/src/scanner/queueDirectory.go index eebd2d3..27b1906 100644 --- a/src/scanner/queueDirectory.go +++ b/src/scanner/queueDirectory.go @@ -29,6 +29,10 @@ func (s *Scanner) queueDirectory(directory string, pkg string) { return } + if strings.HasSuffix(name, "_unix.q") && config.TargetOS != config.Linux && config.TargetOS != config.Mac { + return + } + if strings.HasSuffix(name, "_windows.q") && config.TargetOS != config.Windows { return } diff --git a/src/scanner/scanConst.go b/src/scanner/scanConst.go index f382813..801dba4 100644 --- a/src/scanner/scanConst.go +++ b/src/scanner/scanConst.go @@ -25,18 +25,18 @@ func (s *Scanner) scanConst(file *fs.File, tokens token.List, i int) (int, error i++ for i < len(tokens) { - if tokens[i].Kind == token.Identifier { + switch tokens[i].Kind { + case token.Identifier: name := tokens[i].Text(file.Bytes) i++ s.constants <- &core.Constant{ Name: file.Package + "." + groupName + "." + name, - Value: tokens[i], + Token: tokens[i], File: file, } - } - if tokens[i].Kind == token.BlockEnd { + case token.BlockEnd: return i, nil } diff --git a/src/scanner/scanExtern.go b/src/scanner/scanExtern.go index 4e4e7e8..5f4e214 100644 --- a/src/scanner/scanExtern.go +++ b/src/scanner/scanExtern.go @@ -24,7 +24,8 @@ func (s *Scanner) scanExtern(file *fs.File, tokens token.List, i int) (int, erro i++ for i < len(tokens) { - if tokens[i].Kind == token.Identifier { + switch tokens[i].Kind { + case token.Identifier: function, j, err := scanFunctionSignature(file, tokens, i, token.NewLine) if err != nil { @@ -35,9 +36,8 @@ func (s *Scanner) scanExtern(file *fs.File, tokens token.List, i int) (int, erro function.Package = dllName function.UniqueName = dllName + "." + function.Name s.functions <- function - } - if tokens[i].Kind == token.BlockEnd { + case token.BlockEnd: return i, nil }