From d4f9071ee45cb1a01a840456c474bf7420b8a6ff Mon Sep 17 00:00:00 2001 From: Eduard Urbach Date: Wed, 5 Feb 2025 23:16:18 +0100 Subject: [PATCH] Renamed x64 to x86 --- docs/todo.md | 2 +- src/asm/Finalize.go | 114 ++++----- src/compiler/Result.go | 22 +- src/core/CompileAssignDivision.go | 6 +- src/core/CompileCall.go | 4 +- src/core/ExecuteRegisterNumber.go | 10 +- src/core/ExecuteRegisterRegister.go | 10 +- src/core/NewFunction.go | 14 +- src/core/ResolveTypes.go | 4 +- src/readme.md | 2 +- src/x64/Add_test.go | 88 ------- src/x64/And_test.go | 88 ------- src/x64/Compare_test.go | 88 ------- src/x64/Div_test.go | 39 --- src/x64/Load_test.go | 157 ------------ src/x64/Move_test.go | 108 --------- src/x64/Mul_test.go | 88 ------- src/x64/Negate_test.go | 39 --- src/x64/Or_test.go | 88 ------- src/x64/Pop_test.go | 39 --- src/x64/Push_test.go | 39 --- src/x64/Registers_test.go | 12 - src/x64/Shift_test.go | 71 ------ src/x64/StoreDynamic_test.go | 171 ------------- src/x64/Store_test.go | 305 ------------------------ src/x64/Sub_test.go | 88 ------- src/x64/Xor_test.go | 88 ------- src/x64/x64_test.go | 19 -- src/{x64 => x86}/Add.go | 2 +- src/x86/Add_test.go | 88 +++++++ src/{x64 => x86}/AlignStack.go | 2 +- src/{x64 => x86}/And.go | 2 +- src/x86/And_test.go | 88 +++++++ src/{x64 => x86}/Call.go | 2 +- src/{x64 => x86}/Compare.go | 2 +- src/x86/Compare_test.go | 88 +++++++ src/{x64 => x86}/Div.go | 2 +- src/x86/Div_test.go | 39 +++ src/{x64 => x86}/ExtendRAXToRDX.go | 2 +- src/{x64 => x86}/Jump.go | 2 +- src/{x64 => x86}/Jump_test.go | 18 +- src/{x64 => x86}/Load.go | 2 +- src/x86/Load_test.go | 157 ++++++++++++ src/{x64 => x86}/ModRM.go | 2 +- src/{x64 => x86}/ModRM_test.go | 6 +- src/{x64 => x86}/Move.go | 2 +- src/x86/Move_test.go | 108 +++++++++ src/{x64 => x86}/Mul.go | 2 +- src/x86/Mul_test.go | 88 +++++++ src/{x64 => x86}/Negate.go | 2 +- src/x86/Negate_test.go | 39 +++ src/{x64 => x86}/Or.go | 2 +- src/x86/Or_test.go | 88 +++++++ src/{x64 => x86}/Pop.go | 2 +- src/x86/Pop_test.go | 39 +++ src/{x64 => x86}/Push.go | 2 +- src/x86/Push_test.go | 39 +++ src/{x64 => x86}/REX.go | 2 +- src/{x64 => x86}/REX_test.go | 6 +- src/{x64 => x86}/Registers.go | 2 +- src/x86/Registers_test.go | 12 + src/{x64 => x86}/Return.go | 2 +- src/{x64 => x86}/SIB.go | 2 +- src/{x64 => x86}/SIB_test.go | 6 +- src/{x64 => x86}/Shift.go | 2 +- src/x86/Shift_test.go | 71 ++++++ src/{x64 => x86}/Store.go | 2 +- src/{x64 => x86}/StoreDynamic.go | 2 +- src/x86/StoreDynamic_test.go | 171 +++++++++++++ src/x86/Store_test.go | 305 ++++++++++++++++++++++++ src/{x64 => x86}/Sub.go | 2 +- src/x86/Sub_test.go | 88 +++++++ src/{x64 => x86}/Syscall.go | 2 +- src/{x64 => x86}/Xor.go | 2 +- src/x86/Xor_test.go | 88 +++++++ src/{x64 => x86}/encode.go | 2 +- src/{x64 => x86}/encodeNum.go | 2 +- src/{x64 => x86}/memoryAccess.go | 2 +- src/{x64 => x86}/memoryAccessDynamic.go | 2 +- src/x86/x64_test.go | 19 ++ 80 files changed, 1757 insertions(+), 1757 deletions(-) delete mode 100644 src/x64/Add_test.go delete mode 100644 src/x64/And_test.go delete mode 100644 src/x64/Compare_test.go delete mode 100644 src/x64/Div_test.go delete mode 100644 src/x64/Load_test.go delete mode 100644 src/x64/Move_test.go delete mode 100644 src/x64/Mul_test.go delete mode 100644 src/x64/Negate_test.go delete mode 100644 src/x64/Or_test.go delete mode 100644 src/x64/Pop_test.go delete mode 100644 src/x64/Push_test.go delete mode 100644 src/x64/Registers_test.go delete mode 100644 src/x64/Shift_test.go delete mode 100644 src/x64/StoreDynamic_test.go delete mode 100644 src/x64/Store_test.go delete mode 100644 src/x64/Sub_test.go delete mode 100644 src/x64/Xor_test.go delete mode 100644 src/x64/x64_test.go rename src/{x64 => x86}/Add.go (97%) create mode 100644 src/x86/Add_test.go rename src/{x64 => x86}/AlignStack.go (91%) rename src/{x64 => x86}/And.go (97%) create mode 100644 src/x86/And_test.go rename src/{x64 => x86}/Call.go (98%) rename src/{x64 => x86}/Compare.go (97%) create mode 100644 src/x86/Compare_test.go rename src/{x64 => x86}/Div.go (96%) create mode 100644 src/x86/Div_test.go rename src/{x64 => x86}/ExtendRAXToRDX.go (93%) rename src/{x64 => x86}/Jump.go (98%) rename src/{x64 => x86}/Jump_test.go (56%) rename src/{x64 => x86}/Load.go (95%) create mode 100644 src/x86/Load_test.go rename src/{x64 => x86}/ModRM.go (97%) rename src/{x64 => x86}/ModRM_test.go (90%) rename src/{x64 => x86}/Move.go (99%) create mode 100644 src/x86/Move_test.go rename src/{x64 => x86}/Mul.go (97%) create mode 100644 src/x86/Mul_test.go rename src/{x64 => x86}/Negate.go (94%) create mode 100644 src/x86/Negate_test.go rename src/{x64 => x86}/Or.go (97%) create mode 100644 src/x86/Or_test.go rename src/{x64 => x86}/Pop.go (96%) create mode 100644 src/x86/Pop_test.go rename src/{x64 => x86}/Push.go (96%) create mode 100644 src/x86/Push_test.go rename src/{x64 => x86}/REX.go (93%) rename src/{x64 => x86}/REX_test.go (87%) rename src/{x64 => x86}/Registers.go (98%) create mode 100644 src/x86/Registers_test.go rename src/{x64 => x86}/Return.go (94%) rename src/{x64 => x86}/SIB.go (97%) rename src/{x64 => x86}/SIB_test.go (89%) rename src/{x64 => x86}/Shift.go (97%) create mode 100644 src/x86/Shift_test.go rename src/{x64 => x86}/Store.go (98%) rename src/{x64 => x86}/StoreDynamic.go (98%) create mode 100644 src/x86/StoreDynamic_test.go create mode 100644 src/x86/Store_test.go rename src/{x64 => x86}/Sub.go (97%) create mode 100644 src/x86/Sub_test.go rename src/{x64 => x86}/Syscall.go (91%) rename src/{x64 => x86}/Xor.go (97%) create mode 100644 src/x86/Xor_test.go rename src/{x64 => x86}/encode.go (98%) rename src/{x64 => x86}/encodeNum.go (97%) rename src/{x64 => x86}/memoryAccess.go (98%) rename src/{x64 => x86}/memoryAccessDynamic.go (98%) create mode 100644 src/x86/x64_test.go diff --git a/docs/todo.md b/docs/todo.md index b8655f1..19132e0 100644 --- a/docs/todo.md +++ b/docs/todo.md @@ -71,7 +71,7 @@ - [ ] arm64 - [ ] riscv -- [x] x64 +- [x] x86 ### Platform diff --git a/src/asm/Finalize.go b/src/asm/Finalize.go index 0915e6b..5ea281c 100644 --- a/src/asm/Finalize.go +++ b/src/asm/Finalize.go @@ -6,7 +6,7 @@ import ( "git.akyoto.dev/cli/q/src/config" "git.akyoto.dev/cli/q/src/dll" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // Finalize generates the final machine code. @@ -27,67 +27,67 @@ func (a Assembler) Finalize(dlls dll.List) ([]byte, []byte) { case ADD: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.AddRegisterNumber(code, operands.Register, operands.Number) + code = x86.AddRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.AddRegisterRegister(code, operands.Destination, operands.Source) + code = x86.AddRegisterRegister(code, operands.Destination, operands.Source) } case AND: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.AndRegisterNumber(code, operands.Register, operands.Number) + code = x86.AndRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.AndRegisterRegister(code, operands.Destination, operands.Source) + code = x86.AndRegisterRegister(code, operands.Destination, operands.Source) } case SUB: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.SubRegisterNumber(code, operands.Register, operands.Number) + code = x86.SubRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.SubRegisterRegister(code, operands.Destination, operands.Source) + code = x86.SubRegisterRegister(code, operands.Destination, operands.Source) } case MUL: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.MulRegisterNumber(code, operands.Register, operands.Number) + code = x86.MulRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.MulRegisterRegister(code, operands.Destination, operands.Source) + code = x86.MulRegisterRegister(code, operands.Destination, operands.Source) } case DIV: switch operands := x.Data.(type) { case *RegisterRegister: - if operands.Destination != x64.RAX { - code = x64.MoveRegisterRegister(code, x64.RAX, operands.Destination) + if operands.Destination != x86.RAX { + code = x86.MoveRegisterRegister(code, x86.RAX, operands.Destination) } - code = x64.ExtendRAXToRDX(code) - code = x64.DivRegister(code, operands.Source) + code = x86.ExtendRAXToRDX(code) + code = x86.DivRegister(code, operands.Source) - if operands.Destination != x64.RAX { - code = x64.MoveRegisterRegister(code, operands.Destination, x64.RAX) + if operands.Destination != x86.RAX { + code = x86.MoveRegisterRegister(code, operands.Destination, x86.RAX) } } case MODULO: switch operands := x.Data.(type) { case *RegisterRegister: - if operands.Destination != x64.RAX { - code = x64.MoveRegisterRegister(code, x64.RAX, operands.Destination) + if operands.Destination != x86.RAX { + code = x86.MoveRegisterRegister(code, x86.RAX, operands.Destination) } - code = x64.ExtendRAXToRDX(code) - code = x64.DivRegister(code, operands.Source) + code = x86.ExtendRAXToRDX(code) + code = x86.DivRegister(code, operands.Source) - if operands.Destination != x64.RDX { - code = x64.MoveRegisterRegister(code, operands.Destination, x64.RDX) + if operands.Destination != x86.RDX { + code = x86.MoveRegisterRegister(code, operands.Destination, x86.RDX) } } case CALL: - code = x64.Call(code, 0x00_00_00_00) + code = x86.Call(code, 0x00_00_00_00) size := 4 label := x.Data.(*Label) @@ -116,20 +116,20 @@ func (a Assembler) Finalize(dlls dll.List) ([]byte, []byte) { case COMPARE: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.CompareRegisterNumber(code, operands.Register, operands.Number) + code = x86.CompareRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.CompareRegisterRegister(code, operands.Destination, operands.Source) + code = x86.CompareRegisterRegister(code, operands.Destination, operands.Source) } case DLLCALL: size := 4 // TODO: R15 could be in use. - code = x64.MoveRegisterRegister(code, x64.R15, x64.RSP) - code = x64.AlignStack(code) - code = x64.SubRegisterNumber(code, x64.RSP, 32) - code = x64.CallAtAddress(code, 0x00_00_00_00) + code = x86.MoveRegisterRegister(code, x86.R15, x86.RSP) + code = x86.AlignStack(code) + code = x86.SubRegisterNumber(code, x86.RSP, 32) + code = x86.CallAtAddress(code, 0x00_00_00_00) position := len(code) - size - code = x64.MoveRegisterRegister(code, x64.RSP, x64.R15) + code = x86.MoveRegisterRegister(code, x86.RSP, x86.R15) label := x.Data.(*Label) pointer := &pointer{ @@ -156,19 +156,19 @@ func (a Assembler) Finalize(dlls dll.List) ([]byte, []byte) { case JE, JNE, JG, JGE, JL, JLE, JUMP: switch x.Mnemonic { case JE: - code = x64.Jump8IfEqual(code, 0x00) + code = x86.Jump8IfEqual(code, 0x00) case JNE: - code = x64.Jump8IfNotEqual(code, 0x00) + code = x86.Jump8IfNotEqual(code, 0x00) case JG: - code = x64.Jump8IfGreater(code, 0x00) + code = x86.Jump8IfGreater(code, 0x00) case JGE: - code = x64.Jump8IfGreaterOrEqual(code, 0x00) + code = x86.Jump8IfGreaterOrEqual(code, 0x00) case JL: - code = x64.Jump8IfLess(code, 0x00) + code = x86.Jump8IfLess(code, 0x00) case JLE: - code = x64.Jump8IfLessOrEqual(code, 0x00) + code = x86.Jump8IfLessOrEqual(code, 0x00) case JUMP: - code = x64.Jump8(code, 0x00) + code = x86.Jump8(code, 0x00) } size := 1 @@ -199,20 +199,20 @@ func (a Assembler) Finalize(dlls dll.List) ([]byte, []byte) { case LOAD: switch operands := x.Data.(type) { case *MemoryRegister: - code = x64.LoadRegister(code, operands.Register, operands.Address.Offset, operands.Address.Length, operands.Address.Base) + code = x86.LoadRegister(code, operands.Register, operands.Address.Offset, operands.Address.Length, operands.Address.Base) } case MOVE: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.MoveRegisterNumber(code, operands.Register, operands.Number) + code = x86.MoveRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.MoveRegisterRegister(code, operands.Destination, operands.Source) + code = x86.MoveRegisterRegister(code, operands.Destination, operands.Source) case *RegisterLabel: start := len(code) - code = x64.MoveRegisterNumber(code, operands.Register, 0x00_00_00_00) + code = x86.MoveRegisterNumber(code, operands.Register, 0x00_00_00_00) size := 4 opSize := len(code) - size - start regLabel := x.Data.(*RegisterLabel) @@ -253,59 +253,59 @@ func (a Assembler) Finalize(dlls dll.List) ([]byte, []byte) { case NEGATE: switch operands := x.Data.(type) { case *Register: - code = x64.NegateRegister(code, operands.Register) + code = x86.NegateRegister(code, operands.Register) } case OR: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.OrRegisterNumber(code, operands.Register, operands.Number) + code = x86.OrRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.OrRegisterRegister(code, operands.Destination, operands.Source) + code = x86.OrRegisterRegister(code, operands.Destination, operands.Source) } case POP: switch operands := x.Data.(type) { case *Register: - code = x64.PopRegister(code, operands.Register) + code = x86.PopRegister(code, operands.Register) } case PUSH: switch operands := x.Data.(type) { case *Register: - code = x64.PushRegister(code, operands.Register) + code = x86.PushRegister(code, operands.Register) } case RETURN: - code = x64.Return(code) + code = x86.Return(code) case SHIFTL: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.ShiftLeftNumber(code, operands.Register, byte(operands.Number)&0b111111) + code = x86.ShiftLeftNumber(code, operands.Register, byte(operands.Number)&0b111111) } case SHIFTRS: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.ShiftRightSignedNumber(code, operands.Register, byte(operands.Number)&0b111111) + code = x86.ShiftRightSignedNumber(code, operands.Register, byte(operands.Number)&0b111111) } case STORE: switch operands := x.Data.(type) { case *MemoryNumber: if operands.Address.OffsetRegister == math.MaxUint8 { - code = x64.StoreNumber(code, operands.Address.Base, operands.Address.Offset, operands.Address.Length, operands.Number) + code = x86.StoreNumber(code, operands.Address.Base, operands.Address.Offset, operands.Address.Length, operands.Number) } else { - code = x64.StoreDynamicNumber(code, operands.Address.Base, operands.Address.OffsetRegister, operands.Address.Length, operands.Number) + code = x86.StoreDynamicNumber(code, operands.Address.Base, operands.Address.OffsetRegister, operands.Address.Length, operands.Number) } case *MemoryLabel: start := len(code) if operands.Address.OffsetRegister == math.MaxUint8 { - code = x64.StoreNumber(code, operands.Address.Base, operands.Address.Offset, operands.Address.Length, 0b00_00_00_00) + code = x86.StoreNumber(code, operands.Address.Base, operands.Address.Offset, operands.Address.Length, 0b00_00_00_00) } else { - code = x64.StoreDynamicNumber(code, operands.Address.Base, operands.Address.OffsetRegister, operands.Address.Length, 0b00_00_00_00) + code = x86.StoreDynamicNumber(code, operands.Address.Base, operands.Address.OffsetRegister, operands.Address.Length, 0b00_00_00_00) } size := 4 @@ -328,21 +328,21 @@ func (a Assembler) Finalize(dlls dll.List) ([]byte, []byte) { }) case *MemoryRegister: if operands.Address.OffsetRegister == math.MaxUint8 { - code = x64.StoreRegister(code, operands.Address.Base, operands.Address.Offset, operands.Address.Length, operands.Register) + code = x86.StoreRegister(code, operands.Address.Base, operands.Address.Offset, operands.Address.Length, operands.Register) } else { - code = x64.StoreDynamicRegister(code, operands.Address.Base, operands.Address.OffsetRegister, operands.Address.Length, operands.Register) + code = x86.StoreDynamicRegister(code, operands.Address.Base, operands.Address.OffsetRegister, operands.Address.Length, operands.Register) } } case SYSCALL: - code = x64.Syscall(code) + code = x86.Syscall(code) case XOR: switch operands := x.Data.(type) { case *RegisterNumber: - code = x64.XorRegisterNumber(code, operands.Register, operands.Number) + code = x86.XorRegisterNumber(code, operands.Register, operands.Number) case *RegisterRegister: - code = x64.XorRegisterRegister(code, operands.Destination, operands.Source) + code = x86.XorRegisterRegister(code, operands.Destination, operands.Source) } default: diff --git a/src/compiler/Result.go b/src/compiler/Result.go index c4d739f..6d01851 100644 --- a/src/compiler/Result.go +++ b/src/compiler/Result.go @@ -13,7 +13,7 @@ import ( "git.akyoto.dev/cli/q/src/elf" "git.akyoto.dev/cli/q/src/macho" "git.akyoto.dev/cli/q/src/pe" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" "git.akyoto.dev/go/color/ansi" ) @@ -43,15 +43,15 @@ func (r *Result) finalize() { switch config.TargetOS { case config.Linux: - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[0], LinuxExit) - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[1], 0) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[0], LinuxExit) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[1], 0) final.Syscall() case config.Mac: - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[0], MacExit) - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[1], 0) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[0], MacExit) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[1], 0) final.Syscall() case config.Windows: - final.RegisterNumber(asm.MOVE, x64.WindowsInputRegisters[0], 0) + final.RegisterNumber(asm.MOVE, x86.WindowsInputRegisters[0], 0) final.DLLCall("kernel32.ExitProcess") } @@ -75,15 +75,15 @@ func (r *Result) finalize() { switch config.TargetOS { case config.Linux: - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[0], LinuxExit) - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[1], 1) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[0], LinuxExit) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[1], 1) final.Syscall() case config.Mac: - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[0], MacExit) - final.RegisterNumber(asm.MOVE, x64.SyscallInputRegisters[1], 1) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[0], MacExit) + final.RegisterNumber(asm.MOVE, x86.SyscallInputRegisters[1], 1) final.Syscall() case config.Windows: - final.RegisterNumber(asm.MOVE, x64.WindowsInputRegisters[0], 1) + final.RegisterNumber(asm.MOVE, x86.WindowsInputRegisters[0], 1) final.DLLCall("kernel32.ExitProcess") } diff --git a/src/core/CompileAssignDivision.go b/src/core/CompileAssignDivision.go index e169827..d9f5f5c 100644 --- a/src/core/CompileAssignDivision.go +++ b/src/core/CompileAssignDivision.go @@ -4,7 +4,7 @@ import ( "git.akyoto.dev/cli/q/src/asm" "git.akyoto.dev/cli/q/src/ast" "git.akyoto.dev/cli/q/src/errors" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // CompileAssignDivision compiles an assign statement that has quotient and remainder on the left side and division on the right. @@ -37,8 +37,8 @@ func (f *Function) CompileAssignDivision(node *ast.Assign) error { divisor := right.Children[1] err = f.Execute(right.Token, dividendRegister, divisor) - f.RegisterRegister(asm.MOVE, quotientVariable.Register, x64.RAX) - f.RegisterRegister(asm.MOVE, remainderVariable.Register, x64.RDX) + f.RegisterRegister(asm.MOVE, quotientVariable.Register, x86.RAX) + f.RegisterRegister(asm.MOVE, remainderVariable.Register, x86.RDX) if isTemporary { f.FreeRegister(dividendRegister) diff --git a/src/core/CompileCall.go b/src/core/CompileCall.go index c88ec87..5ce42f1 100644 --- a/src/core/CompileCall.go +++ b/src/core/CompileCall.go @@ -6,7 +6,7 @@ import ( "git.akyoto.dev/cli/q/src/errors" "git.akyoto.dev/cli/q/src/expression" "git.akyoto.dev/cli/q/src/types" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // CompileCall executes a function call. @@ -50,7 +50,7 @@ func (f *Function) CompileCall(root *expression.Expression) (*Function, error) { if pkg == "kernel32" || pkg == "user32" || pkg == "gdi32" || pkg == "comctl32" { parameters := root.Children[1:] - registers := x64.WindowsInputRegisters[:len(parameters)] + registers := x86.WindowsInputRegisters[:len(parameters)] for i := len(parameters) - 1; i >= 0; i-- { _, err := f.ExpressionToRegister(parameters[i], registers[i]) diff --git a/src/core/ExecuteRegisterNumber.go b/src/core/ExecuteRegisterNumber.go index 0714751..f26f1a3 100644 --- a/src/core/ExecuteRegisterNumber.go +++ b/src/core/ExecuteRegisterNumber.go @@ -5,7 +5,7 @@ import ( "git.akyoto.dev/cli/q/src/cpu" "git.akyoto.dev/cli/q/src/errors" "git.akyoto.dev/cli/q/src/token" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // ExecuteRegisterNumber performs an operation on a register and a number. @@ -25,16 +25,16 @@ func (f *Function) ExecuteRegisterNumber(operation token.Token, register cpu.Reg f.RegisterNumber(asm.MUL, register, number) case token.Div, token.DivAssign: - f.SaveRegister(x64.RAX) - f.SaveRegister(x64.RDX) + f.SaveRegister(x86.RAX) + f.SaveRegister(x86.RDX) tmp := f.NewRegister() f.RegisterNumber(asm.MOVE, tmp, number) f.RegisterRegister(asm.DIV, register, tmp) f.FreeRegister(tmp) case token.Mod, token.ModAssign: - f.SaveRegister(x64.RAX) - f.SaveRegister(x64.RDX) + f.SaveRegister(x86.RAX) + f.SaveRegister(x86.RDX) tmp := f.NewRegister() f.RegisterNumber(asm.MOVE, tmp, number) f.RegisterRegister(asm.MODULO, register, tmp) diff --git a/src/core/ExecuteRegisterRegister.go b/src/core/ExecuteRegisterRegister.go index 3add7ef..ebb6811 100644 --- a/src/core/ExecuteRegisterRegister.go +++ b/src/core/ExecuteRegisterRegister.go @@ -5,7 +5,7 @@ import ( "git.akyoto.dev/cli/q/src/cpu" "git.akyoto.dev/cli/q/src/errors" "git.akyoto.dev/cli/q/src/token" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // ExecuteRegisterRegister performs an operation on two registers. @@ -25,13 +25,13 @@ func (f *Function) ExecuteRegisterRegister(operation token.Token, register cpu.R f.RegisterRegister(asm.MUL, register, operand) case token.Div, token.DivAssign: - f.SaveRegister(x64.RAX) - f.SaveRegister(x64.RDX) + f.SaveRegister(x86.RAX) + f.SaveRegister(x86.RDX) f.RegisterRegister(asm.DIV, register, operand) case token.Mod, token.ModAssign: - f.SaveRegister(x64.RAX) - f.SaveRegister(x64.RDX) + f.SaveRegister(x86.RAX) + f.SaveRegister(x86.RDX) f.RegisterRegister(asm.MODULO, register, operand) case token.And, token.AndAssign: diff --git a/src/core/NewFunction.go b/src/core/NewFunction.go index 5e5a4ae..e2d93d2 100644 --- a/src/core/NewFunction.go +++ b/src/core/NewFunction.go @@ -7,7 +7,7 @@ import ( "git.akyoto.dev/cli/q/src/register" "git.akyoto.dev/cli/q/src/scope" "git.akyoto.dev/cli/q/src/token" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // NewFunction creates a new function. @@ -26,12 +26,12 @@ func NewFunction(pkg string, name string, file *fs.File, body []token.Token) *Fu Scopes: []*scope.Scope{{}}, }, CPU: cpu.CPU{ - All: x64.AllRegisters, - General: x64.GeneralRegisters, - Input: x64.InputRegisters, - Output: x64.OutputRegisters, - SyscallInput: x64.SyscallInputRegisters, - SyscallOutput: x64.SyscallOutputRegisters, + All: x86.AllRegisters, + General: x86.GeneralRegisters, + Input: x86.InputRegisters, + Output: x86.OutputRegisters, + SyscallInput: x86.SyscallInputRegisters, + SyscallOutput: x86.SyscallOutputRegisters, }, }, } diff --git a/src/core/ResolveTypes.go b/src/core/ResolveTypes.go index c508073..c779c13 100644 --- a/src/core/ResolveTypes.go +++ b/src/core/ResolveTypes.go @@ -4,7 +4,7 @@ import ( "git.akyoto.dev/cli/q/src/errors" "git.akyoto.dev/cli/q/src/scope" "git.akyoto.dev/cli/q/src/token" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" ) // ResolveTypes parses the input and output types. @@ -27,7 +27,7 @@ func (f *Function) ResolveTypes() error { f.AddVariable(&scope.Variable{ Name: param.Name, Type: param.Type, - Register: x64.InputRegisters[i], + Register: x86.InputRegisters[i], Alive: uses, }) } diff --git a/src/readme.md b/src/readme.md index 6483efc..4ee22a5 100644 --- a/src/readme.md +++ b/src/readme.md @@ -24,4 +24,4 @@ - [sizeof](sizeof) - Calculates the byte size of numbers - [token](token) - Converts a file to tokens with the `Tokenize` function - [types](types) - Type system (w.i.p.) -- [x64](x64) - x86-64 implementation +- [x86](x86) - x86-64 implementation diff --git a/src/x64/Add_test.go b/src/x64/Add_test.go deleted file mode 100644 index 134e09e..0000000 --- a/src/x64/Add_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestAddRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x83, 0xC0, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x83, 0xC1, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x83, 0xC2, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x83, 0xC3, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x83, 0xC4, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x83, 0xC5, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x83, 0xC6, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x83, 0xC7, 0x01}}, - {x64.R8, 1, []byte{0x49, 0x83, 0xC0, 0x01}}, - {x64.R9, 1, []byte{0x49, 0x83, 0xC1, 0x01}}, - {x64.R10, 1, []byte{0x49, 0x83, 0xC2, 0x01}}, - {x64.R11, 1, []byte{0x49, 0x83, 0xC3, 0x01}}, - {x64.R12, 1, []byte{0x49, 0x83, 0xC4, 0x01}}, - {x64.R13, 1, []byte{0x49, 0x83, 0xC5, 0x01}}, - {x64.R14, 1, []byte{0x49, 0x83, 0xC6, 0x01}}, - {x64.R15, 1, []byte{0x49, 0x83, 0xC7, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC1, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC3, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC5, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC7, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC1, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC3, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC5, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC7, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("add %s, %x", pattern.Register, pattern.Number) - code := x64.AddRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestAddRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x01, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x01, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x01, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x01, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x01, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x01, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x01, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x01, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x01, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x01, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x01, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x01, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x01, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x01, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x01, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x01, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("add %s, %s", pattern.Left, pattern.Right) - code := x64.AddRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/And_test.go b/src/x64/And_test.go deleted file mode 100644 index 249d7b8..0000000 --- a/src/x64/And_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestAndRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x83, 0xE0, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x83, 0xE1, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x83, 0xE2, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x83, 0xE3, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x83, 0xE4, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x83, 0xE5, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x83, 0xE6, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x83, 0xE7, 0x01}}, - {x64.R8, 1, []byte{0x49, 0x83, 0xE0, 0x01}}, - {x64.R9, 1, []byte{0x49, 0x83, 0xE1, 0x01}}, - {x64.R10, 1, []byte{0x49, 0x83, 0xE2, 0x01}}, - {x64.R11, 1, []byte{0x49, 0x83, 0xE3, 0x01}}, - {x64.R12, 1, []byte{0x49, 0x83, 0xE4, 0x01}}, - {x64.R13, 1, []byte{0x49, 0x83, 0xE5, 0x01}}, - {x64.R14, 1, []byte{0x49, 0x83, 0xE6, 0x01}}, - {x64.R15, 1, []byte{0x49, 0x83, 0xE7, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE1, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE3, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE5, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE7, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE1, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE3, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE5, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE7, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("and %s, %x", pattern.Register, pattern.Number) - code := x64.AndRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestAndRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x21, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x21, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x21, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x21, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x21, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x21, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x21, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x21, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x21, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x21, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x21, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x21, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x21, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x21, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x21, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x21, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("and %s, %s", pattern.Left, pattern.Right) - code := x64.AndRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Compare_test.go b/src/x64/Compare_test.go deleted file mode 100644 index 0105ed0..0000000 --- a/src/x64/Compare_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestCompareRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x83, 0xF8, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x83, 0xF9, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x83, 0xFA, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x83, 0xFB, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x83, 0xFC, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x83, 0xFD, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x83, 0xFE, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x83, 0xFF, 0x01}}, - {x64.R8, 1, []byte{0x49, 0x83, 0xF8, 0x01}}, - {x64.R9, 1, []byte{0x49, 0x83, 0xF9, 0x01}}, - {x64.R10, 1, []byte{0x49, 0x83, 0xFA, 0x01}}, - {x64.R11, 1, []byte{0x49, 0x83, 0xFB, 0x01}}, - {x64.R12, 1, []byte{0x49, 0x83, 0xFC, 0x01}}, - {x64.R13, 1, []byte{0x49, 0x83, 0xFD, 0x01}}, - {x64.R14, 1, []byte{0x49, 0x83, 0xFE, 0x01}}, - {x64.R15, 1, []byte{0x49, 0x83, 0xFF, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFD, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFD, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("cmp %s, %x", pattern.Register, pattern.Number) - code := x64.CompareRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestCompareRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x39, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x39, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x39, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x39, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x39, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x39, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x39, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x39, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x39, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x39, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x39, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x39, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x39, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x39, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x39, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x39, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("cmp %s, %s", pattern.Left, pattern.Right) - code := x64.CompareRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Div_test.go b/src/x64/Div_test.go deleted file mode 100644 index de684b4..0000000 --- a/src/x64/Div_test.go +++ /dev/null @@ -1,39 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestDivRegister(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Code []byte - }{ - {x64.RAX, []byte{0x48, 0xF7, 0xF8}}, - {x64.RCX, []byte{0x48, 0xF7, 0xF9}}, - {x64.RDX, []byte{0x48, 0xF7, 0xFA}}, - {x64.RBX, []byte{0x48, 0xF7, 0xFB}}, - {x64.RSP, []byte{0x48, 0xF7, 0xFC}}, - {x64.RBP, []byte{0x48, 0xF7, 0xFD}}, - {x64.RSI, []byte{0x48, 0xF7, 0xFE}}, - {x64.RDI, []byte{0x48, 0xF7, 0xFF}}, - {x64.R8, []byte{0x49, 0xF7, 0xF8}}, - {x64.R9, []byte{0x49, 0xF7, 0xF9}}, - {x64.R10, []byte{0x49, 0xF7, 0xFA}}, - {x64.R11, []byte{0x49, 0xF7, 0xFB}}, - {x64.R12, []byte{0x49, 0xF7, 0xFC}}, - {x64.R13, []byte{0x49, 0xF7, 0xFD}}, - {x64.R14, []byte{0x49, 0xF7, 0xFE}}, - {x64.R15, []byte{0x49, 0xF7, 0xFF}}, - } - - for _, pattern := range usagePatterns { - t.Logf("idiv %s", pattern.Register) - code := x64.DivRegister(nil, pattern.Register) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Load_test.go b/src/x64/Load_test.go deleted file mode 100644 index 9585f15..0000000 --- a/src/x64/Load_test.go +++ /dev/null @@ -1,157 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestLoadRegister(t *testing.T) { - usagePatterns := []struct { - Destination cpu.Register - Source cpu.Register - Offset byte - Length byte - Code []byte - }{ - // No offset - {x64.RAX, x64.R15, 0, 8, []byte{0x49, 0x8B, 0x07}}, - {x64.RAX, x64.R15, 0, 4, []byte{0x41, 0x8B, 0x07}}, - {x64.RAX, x64.R15, 0, 2, []byte{0x66, 0x41, 0x8B, 0x07}}, - {x64.RAX, x64.R15, 0, 1, []byte{0x41, 0x8A, 0x07}}, - {x64.RCX, x64.R14, 0, 8, []byte{0x49, 0x8B, 0x0E}}, - {x64.RCX, x64.R14, 0, 4, []byte{0x41, 0x8B, 0x0E}}, - {x64.RCX, x64.R14, 0, 2, []byte{0x66, 0x41, 0x8B, 0x0E}}, - {x64.RCX, x64.R14, 0, 1, []byte{0x41, 0x8A, 0x0E}}, - {x64.RDX, x64.R13, 0, 8, []byte{0x49, 0x8B, 0x55, 0x00}}, - {x64.RDX, x64.R13, 0, 4, []byte{0x41, 0x8B, 0x55, 0x00}}, - {x64.RDX, x64.R13, 0, 2, []byte{0x66, 0x41, 0x8B, 0x55, 0x00}}, - {x64.RDX, x64.R13, 0, 1, []byte{0x41, 0x8A, 0x55, 0x00}}, - {x64.RBX, x64.R12, 0, 8, []byte{0x49, 0x8B, 0x1C, 0x24}}, - {x64.RBX, x64.R12, 0, 4, []byte{0x41, 0x8B, 0x1C, 0x24}}, - {x64.RBX, x64.R12, 0, 2, []byte{0x66, 0x41, 0x8B, 0x1C, 0x24}}, - {x64.RBX, x64.R12, 0, 1, []byte{0x41, 0x8A, 0x1C, 0x24}}, - {x64.RSP, x64.R11, 0, 8, []byte{0x49, 0x8B, 0x23}}, - {x64.RSP, x64.R11, 0, 4, []byte{0x41, 0x8B, 0x23}}, - {x64.RSP, x64.R11, 0, 2, []byte{0x66, 0x41, 0x8B, 0x23}}, - {x64.RSP, x64.R11, 0, 1, []byte{0x41, 0x8A, 0x23}}, - {x64.RBP, x64.R10, 0, 8, []byte{0x49, 0x8B, 0x2A}}, - {x64.RBP, x64.R10, 0, 4, []byte{0x41, 0x8B, 0x2A}}, - {x64.RBP, x64.R10, 0, 2, []byte{0x66, 0x41, 0x8B, 0x2A}}, - {x64.RBP, x64.R10, 0, 1, []byte{0x41, 0x8A, 0x2A}}, - {x64.RSI, x64.R9, 0, 8, []byte{0x49, 0x8B, 0x31}}, - {x64.RSI, x64.R9, 0, 4, []byte{0x41, 0x8B, 0x31}}, - {x64.RSI, x64.R9, 0, 2, []byte{0x66, 0x41, 0x8B, 0x31}}, - {x64.RSI, x64.R9, 0, 1, []byte{0x41, 0x8A, 0x31}}, - {x64.RDI, x64.R8, 0, 8, []byte{0x49, 0x8B, 0x38}}, - {x64.RDI, x64.R8, 0, 4, []byte{0x41, 0x8B, 0x38}}, - {x64.RDI, x64.R8, 0, 2, []byte{0x66, 0x41, 0x8B, 0x38}}, - {x64.RDI, x64.R8, 0, 1, []byte{0x41, 0x8A, 0x38}}, - {x64.R8, x64.RDI, 0, 8, []byte{0x4C, 0x8B, 0x07}}, - {x64.R8, x64.RDI, 0, 4, []byte{0x44, 0x8B, 0x07}}, - {x64.R8, x64.RDI, 0, 2, []byte{0x66, 0x44, 0x8B, 0x07}}, - {x64.R8, x64.RDI, 0, 1, []byte{0x44, 0x8A, 0x07}}, - {x64.R9, x64.RSI, 0, 8, []byte{0x4C, 0x8B, 0x0E}}, - {x64.R9, x64.RSI, 0, 4, []byte{0x44, 0x8B, 0x0E}}, - {x64.R9, x64.RSI, 0, 2, []byte{0x66, 0x44, 0x8B, 0x0E}}, - {x64.R9, x64.RSI, 0, 1, []byte{0x44, 0x8A, 0x0E}}, - {x64.R10, x64.RBP, 0, 8, []byte{0x4C, 0x8B, 0x55, 0x00}}, - {x64.R10, x64.RBP, 0, 4, []byte{0x44, 0x8B, 0x55, 0x00}}, - {x64.R10, x64.RBP, 0, 2, []byte{0x66, 0x44, 0x8B, 0x55, 0x00}}, - {x64.R10, x64.RBP, 0, 1, []byte{0x44, 0x8A, 0x55, 0x00}}, - {x64.R11, x64.RSP, 0, 8, []byte{0x4C, 0x8B, 0x1C, 0x24}}, - {x64.R11, x64.RSP, 0, 4, []byte{0x44, 0x8B, 0x1C, 0x24}}, - {x64.R11, x64.RSP, 0, 2, []byte{0x66, 0x44, 0x8B, 0x1C, 0x24}}, - {x64.R11, x64.RSP, 0, 1, []byte{0x44, 0x8A, 0x1C, 0x24}}, - {x64.R12, x64.RBX, 0, 8, []byte{0x4C, 0x8B, 0x23}}, - {x64.R12, x64.RBX, 0, 4, []byte{0x44, 0x8B, 0x23}}, - {x64.R12, x64.RBX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x23}}, - {x64.R12, x64.RBX, 0, 1, []byte{0x44, 0x8A, 0x23}}, - {x64.R13, x64.RDX, 0, 8, []byte{0x4C, 0x8B, 0x2A}}, - {x64.R13, x64.RDX, 0, 4, []byte{0x44, 0x8B, 0x2A}}, - {x64.R13, x64.RDX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x2A}}, - {x64.R13, x64.RDX, 0, 1, []byte{0x44, 0x8A, 0x2A}}, - {x64.R14, x64.RCX, 0, 8, []byte{0x4C, 0x8B, 0x31}}, - {x64.R14, x64.RCX, 0, 4, []byte{0x44, 0x8B, 0x31}}, - {x64.R14, x64.RCX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x31}}, - {x64.R14, x64.RCX, 0, 1, []byte{0x44, 0x8A, 0x31}}, - {x64.R15, x64.RAX, 0, 8, []byte{0x4C, 0x8B, 0x38}}, - {x64.R15, x64.RAX, 0, 4, []byte{0x44, 0x8B, 0x38}}, - {x64.R15, x64.RAX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x38}}, - {x64.R15, x64.RAX, 0, 1, []byte{0x44, 0x8A, 0x38}}, - - // Offset of 1 - {x64.RAX, x64.R15, 1, 8, []byte{0x49, 0x8B, 0x47, 0x01}}, - {x64.RAX, x64.R15, 1, 4, []byte{0x41, 0x8B, 0x47, 0x01}}, - {x64.RAX, x64.R15, 1, 2, []byte{0x66, 0x41, 0x8B, 0x47, 0x01}}, - {x64.RAX, x64.R15, 1, 1, []byte{0x41, 0x8A, 0x47, 0x01}}, - {x64.RCX, x64.R14, 1, 8, []byte{0x49, 0x8B, 0x4E, 0x01}}, - {x64.RCX, x64.R14, 1, 4, []byte{0x41, 0x8B, 0x4E, 0x01}}, - {x64.RCX, x64.R14, 1, 2, []byte{0x66, 0x41, 0x8B, 0x4E, 0x01}}, - {x64.RCX, x64.R14, 1, 1, []byte{0x41, 0x8A, 0x4E, 0x01}}, - {x64.RDX, x64.R13, 1, 8, []byte{0x49, 0x8B, 0x55, 0x01}}, - {x64.RDX, x64.R13, 1, 4, []byte{0x41, 0x8B, 0x55, 0x01}}, - {x64.RDX, x64.R13, 1, 2, []byte{0x66, 0x41, 0x8B, 0x55, 0x01}}, - {x64.RDX, x64.R13, 1, 1, []byte{0x41, 0x8A, 0x55, 0x01}}, - {x64.RBX, x64.R12, 1, 8, []byte{0x49, 0x8B, 0x5C, 0x24, 0x01}}, - {x64.RBX, x64.R12, 1, 4, []byte{0x41, 0x8B, 0x5C, 0x24, 0x01}}, - {x64.RBX, x64.R12, 1, 2, []byte{0x66, 0x41, 0x8B, 0x5C, 0x24, 0x01}}, - {x64.RBX, x64.R12, 1, 1, []byte{0x41, 0x8A, 0x5C, 0x24, 0x01}}, - {x64.RSP, x64.R11, 1, 8, []byte{0x49, 0x8B, 0x63, 0x01}}, - {x64.RSP, x64.R11, 1, 4, []byte{0x41, 0x8B, 0x63, 0x01}}, - {x64.RSP, x64.R11, 1, 2, []byte{0x66, 0x41, 0x8B, 0x63, 0x01}}, - {x64.RSP, x64.R11, 1, 1, []byte{0x41, 0x8A, 0x63, 0x01}}, - {x64.RBP, x64.R10, 1, 8, []byte{0x49, 0x8B, 0x6A, 0x01}}, - {x64.RBP, x64.R10, 1, 4, []byte{0x41, 0x8B, 0x6A, 0x01}}, - {x64.RBP, x64.R10, 1, 2, []byte{0x66, 0x41, 0x8B, 0x6A, 0x01}}, - {x64.RBP, x64.R10, 1, 1, []byte{0x41, 0x8A, 0x6A, 0x01}}, - {x64.RSI, x64.R9, 1, 8, []byte{0x49, 0x8B, 0x71, 0x01}}, - {x64.RSI, x64.R9, 1, 4, []byte{0x41, 0x8B, 0x71, 0x01}}, - {x64.RSI, x64.R9, 1, 2, []byte{0x66, 0x41, 0x8B, 0x71, 0x01}}, - {x64.RSI, x64.R9, 1, 1, []byte{0x41, 0x8A, 0x71, 0x01}}, - {x64.RDI, x64.R8, 1, 8, []byte{0x49, 0x8B, 0x78, 0x01}}, - {x64.RDI, x64.R8, 1, 4, []byte{0x41, 0x8B, 0x78, 0x01}}, - {x64.RDI, x64.R8, 1, 2, []byte{0x66, 0x41, 0x8B, 0x78, 0x01}}, - {x64.RDI, x64.R8, 1, 1, []byte{0x41, 0x8A, 0x78, 0x01}}, - {x64.R8, x64.RDI, 1, 8, []byte{0x4C, 0x8B, 0x47, 0x01}}, - {x64.R8, x64.RDI, 1, 4, []byte{0x44, 0x8B, 0x47, 0x01}}, - {x64.R8, x64.RDI, 1, 2, []byte{0x66, 0x44, 0x8B, 0x47, 0x01}}, - {x64.R8, x64.RDI, 1, 1, []byte{0x44, 0x8A, 0x47, 0x01}}, - {x64.R9, x64.RSI, 1, 8, []byte{0x4C, 0x8B, 0x4E, 0x01}}, - {x64.R9, x64.RSI, 1, 4, []byte{0x44, 0x8B, 0x4E, 0x01}}, - {x64.R9, x64.RSI, 1, 2, []byte{0x66, 0x44, 0x8B, 0x4E, 0x01}}, - {x64.R9, x64.RSI, 1, 1, []byte{0x44, 0x8A, 0x4E, 0x01}}, - {x64.R10, x64.RBP, 1, 8, []byte{0x4C, 0x8B, 0x55, 0x01}}, - {x64.R10, x64.RBP, 1, 4, []byte{0x44, 0x8B, 0x55, 0x01}}, - {x64.R10, x64.RBP, 1, 2, []byte{0x66, 0x44, 0x8B, 0x55, 0x01}}, - {x64.R10, x64.RBP, 1, 1, []byte{0x44, 0x8A, 0x55, 0x01}}, - {x64.R11, x64.RSP, 1, 8, []byte{0x4C, 0x8B, 0x5C, 0x24, 0x01}}, - {x64.R11, x64.RSP, 1, 4, []byte{0x44, 0x8B, 0x5C, 0x24, 0x01}}, - {x64.R11, x64.RSP, 1, 2, []byte{0x66, 0x44, 0x8B, 0x5C, 0x24, 0x01}}, - {x64.R11, x64.RSP, 1, 1, []byte{0x44, 0x8A, 0x5C, 0x24, 0x01}}, - {x64.R12, x64.RBX, 1, 8, []byte{0x4C, 0x8B, 0x63, 0x01}}, - {x64.R12, x64.RBX, 1, 4, []byte{0x44, 0x8B, 0x63, 0x01}}, - {x64.R12, x64.RBX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x63, 0x01}}, - {x64.R12, x64.RBX, 1, 1, []byte{0x44, 0x8A, 0x63, 0x01}}, - {x64.R13, x64.RDX, 1, 8, []byte{0x4C, 0x8B, 0x6A, 0x01}}, - {x64.R13, x64.RDX, 1, 4, []byte{0x44, 0x8B, 0x6A, 0x01}}, - {x64.R13, x64.RDX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x6A, 0x01}}, - {x64.R13, x64.RDX, 1, 1, []byte{0x44, 0x8A, 0x6A, 0x01}}, - {x64.R14, x64.RCX, 1, 8, []byte{0x4C, 0x8B, 0x71, 0x01}}, - {x64.R14, x64.RCX, 1, 4, []byte{0x44, 0x8B, 0x71, 0x01}}, - {x64.R14, x64.RCX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x71, 0x01}}, - {x64.R14, x64.RCX, 1, 1, []byte{0x44, 0x8A, 0x71, 0x01}}, - {x64.R15, x64.RAX, 1, 8, []byte{0x4C, 0x8B, 0x78, 0x01}}, - {x64.R15, x64.RAX, 1, 4, []byte{0x44, 0x8B, 0x78, 0x01}}, - {x64.R15, x64.RAX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x78, 0x01}}, - {x64.R15, x64.RAX, 1, 1, []byte{0x44, 0x8A, 0x78, 0x01}}, - } - - for _, pattern := range usagePatterns { - t.Logf("load %dB %s, [%s+%d]", pattern.Length, pattern.Destination, pattern.Source, pattern.Offset) - code := x64.LoadRegister(nil, pattern.Destination, pattern.Offset, pattern.Length, pattern.Source) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Move_test.go b/src/x64/Move_test.go deleted file mode 100644 index 071e05b..0000000 --- a/src/x64/Move_test.go +++ /dev/null @@ -1,108 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestMoveRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - // 32 bits - {x64.RAX, 0x7FFFFFFF, []byte{0xB8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0xB9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0xBA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0xBB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0xBC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0xBD, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0xBE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0xBF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x41, 0xB8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x41, 0xB9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x41, 0xBA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x41, 0xBB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x41, 0xBC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x41, 0xBD, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x41, 0xBE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x41, 0xBF, 0xFF, 0xFF, 0xFF, 0x7F}}, - - // 64 bits - {x64.RAX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xB8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xB9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBA, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xB8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xB9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBA, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - - // Negative numbers - {x64.RAX, -1, []byte{0x48, 0xC7, 0xC0, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RCX, -1, []byte{0x48, 0xC7, 0xC1, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RDX, -1, []byte{0x48, 0xC7, 0xC2, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RBX, -1, []byte{0x48, 0xC7, 0xC3, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RSP, -1, []byte{0x48, 0xC7, 0xC4, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RBP, -1, []byte{0x48, 0xC7, 0xC5, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RSI, -1, []byte{0x48, 0xC7, 0xC6, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.RDI, -1, []byte{0x48, 0xC7, 0xC7, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R8, -1, []byte{0x49, 0xC7, 0xC0, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R9, -1, []byte{0x49, 0xC7, 0xC1, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R10, -1, []byte{0x49, 0xC7, 0xC2, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R11, -1, []byte{0x49, 0xC7, 0xC3, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R12, -1, []byte{0x49, 0xC7, 0xC4, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R13, -1, []byte{0x49, 0xC7, 0xC5, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R14, -1, []byte{0x49, 0xC7, 0xC6, 0xFF, 0xFF, 0xFF, 0xFF}}, - {x64.R15, -1, []byte{0x49, 0xC7, 0xC7, 0xFF, 0xFF, 0xFF, 0xFF}}, - } - - for _, pattern := range usagePatterns { - t.Logf("mov %s, %x", pattern.Register, pattern.Number) - code := x64.MoveRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestMoveRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x89, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x89, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x89, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x89, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x89, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x89, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x89, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x89, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x89, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x89, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x89, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x89, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x89, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x89, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x89, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x89, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("mov %s, %s", pattern.Left, pattern.Right) - code := x64.MoveRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Mul_test.go b/src/x64/Mul_test.go deleted file mode 100644 index 03ffae1..0000000 --- a/src/x64/Mul_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestMulRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x6B, 0xC0, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x6B, 0xC9, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x6B, 0xD2, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x6B, 0xDB, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x6B, 0xE4, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x6B, 0xED, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x6B, 0xF6, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x6B, 0xFF, 0x01}}, - {x64.R8, 1, []byte{0x4D, 0x6B, 0xC0, 0x01}}, - {x64.R9, 1, []byte{0x4D, 0x6B, 0xC9, 0x01}}, - {x64.R10, 1, []byte{0x4D, 0x6B, 0xD2, 0x01}}, - {x64.R11, 1, []byte{0x4D, 0x6B, 0xDB, 0x01}}, - {x64.R12, 1, []byte{0x4D, 0x6B, 0xE4, 0x01}}, - {x64.R13, 1, []byte{0x4D, 0x6B, 0xED, 0x01}}, - {x64.R14, 1, []byte{0x4D, 0x6B, 0xF6, 0x01}}, - {x64.R15, 1, []byte{0x4D, 0x6B, 0xFF, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xD2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xDB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x69, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x69, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x69, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x69, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xD2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xDB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("mul %s, %x", pattern.Register, pattern.Number) - code := x64.MulRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestMulRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x49, 0x0F, 0xAF, 0xC7}}, - {x64.RCX, x64.R14, []byte{0x49, 0x0F, 0xAF, 0xCE}}, - {x64.RDX, x64.R13, []byte{0x49, 0x0F, 0xAF, 0xD5}}, - {x64.RBX, x64.R12, []byte{0x49, 0x0F, 0xAF, 0xDC}}, - {x64.RSP, x64.R11, []byte{0x49, 0x0F, 0xAF, 0xE3}}, - {x64.RBP, x64.R10, []byte{0x49, 0x0F, 0xAF, 0xEA}}, - {x64.RSI, x64.R9, []byte{0x49, 0x0F, 0xAF, 0xF1}}, - {x64.RDI, x64.R8, []byte{0x49, 0x0F, 0xAF, 0xF8}}, - {x64.R8, x64.RDI, []byte{0x4C, 0x0F, 0xAF, 0xC7}}, - {x64.R9, x64.RSI, []byte{0x4C, 0x0F, 0xAF, 0xCE}}, - {x64.R10, x64.RBP, []byte{0x4C, 0x0F, 0xAF, 0xD5}}, - {x64.R11, x64.RSP, []byte{0x4C, 0x0F, 0xAF, 0xDC}}, - {x64.R12, x64.RBX, []byte{0x4C, 0x0F, 0xAF, 0xE3}}, - {x64.R13, x64.RDX, []byte{0x4C, 0x0F, 0xAF, 0xEA}}, - {x64.R14, x64.RCX, []byte{0x4C, 0x0F, 0xAF, 0xF1}}, - {x64.R15, x64.RAX, []byte{0x4C, 0x0F, 0xAF, 0xF8}}, - } - - for _, pattern := range usagePatterns { - t.Logf("mul %s, %s", pattern.Left, pattern.Right) - code := x64.MulRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Negate_test.go b/src/x64/Negate_test.go deleted file mode 100644 index 625e601..0000000 --- a/src/x64/Negate_test.go +++ /dev/null @@ -1,39 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestNegateRegister(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Code []byte - }{ - {x64.RAX, []byte{0x48, 0xF7, 0xD8}}, - {x64.RCX, []byte{0x48, 0xF7, 0xD9}}, - {x64.RDX, []byte{0x48, 0xF7, 0xDA}}, - {x64.RBX, []byte{0x48, 0xF7, 0xDB}}, - {x64.RSP, []byte{0x48, 0xF7, 0xDC}}, - {x64.RBP, []byte{0x48, 0xF7, 0xDD}}, - {x64.RSI, []byte{0x48, 0xF7, 0xDE}}, - {x64.RDI, []byte{0x48, 0xF7, 0xDF}}, - {x64.R8, []byte{0x49, 0xF7, 0xD8}}, - {x64.R9, []byte{0x49, 0xF7, 0xD9}}, - {x64.R10, []byte{0x49, 0xF7, 0xDA}}, - {x64.R11, []byte{0x49, 0xF7, 0xDB}}, - {x64.R12, []byte{0x49, 0xF7, 0xDC}}, - {x64.R13, []byte{0x49, 0xF7, 0xDD}}, - {x64.R14, []byte{0x49, 0xF7, 0xDE}}, - {x64.R15, []byte{0x49, 0xF7, 0xDF}}, - } - - for _, pattern := range usagePatterns { - t.Logf("neg %s", pattern.Register) - code := x64.NegateRegister(nil, pattern.Register) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Or_test.go b/src/x64/Or_test.go deleted file mode 100644 index d85065a..0000000 --- a/src/x64/Or_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestOrRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x83, 0xC8, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x83, 0xC9, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x83, 0xCA, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x83, 0xCB, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x83, 0xCC, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x83, 0xCD, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x83, 0xCE, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x83, 0xCF, 0x01}}, - {x64.R8, 1, []byte{0x49, 0x83, 0xC8, 0x01}}, - {x64.R9, 1, []byte{0x49, 0x83, 0xC9, 0x01}}, - {x64.R10, 1, []byte{0x49, 0x83, 0xCA, 0x01}}, - {x64.R11, 1, []byte{0x49, 0x83, 0xCB, 0x01}}, - {x64.R12, 1, []byte{0x49, 0x83, 0xCC, 0x01}}, - {x64.R13, 1, []byte{0x49, 0x83, 0xCD, 0x01}}, - {x64.R14, 1, []byte{0x49, 0x83, 0xCE, 0x01}}, - {x64.R15, 1, []byte{0x49, 0x83, 0xCF, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCD, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCD, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCF, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("or %s, %x", pattern.Register, pattern.Number) - code := x64.OrRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestOrRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x09, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x09, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x09, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x09, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x09, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x09, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x09, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x09, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x09, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x09, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x09, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x09, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x09, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x09, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x09, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x09, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("or %s, %s", pattern.Left, pattern.Right) - code := x64.OrRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Pop_test.go b/src/x64/Pop_test.go deleted file mode 100644 index 446eebe..0000000 --- a/src/x64/Pop_test.go +++ /dev/null @@ -1,39 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestPopRegister(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Code []byte - }{ - {x64.RAX, []byte{0x58}}, - {x64.RCX, []byte{0x59}}, - {x64.RDX, []byte{0x5A}}, - {x64.RBX, []byte{0x5B}}, - {x64.RSP, []byte{0x5C}}, - {x64.RBP, []byte{0x5D}}, - {x64.RSI, []byte{0x5E}}, - {x64.RDI, []byte{0x5F}}, - {x64.R8, []byte{0x41, 0x58}}, - {x64.R9, []byte{0x41, 0x59}}, - {x64.R10, []byte{0x41, 0x5A}}, - {x64.R11, []byte{0x41, 0x5B}}, - {x64.R12, []byte{0x41, 0x5C}}, - {x64.R13, []byte{0x41, 0x5D}}, - {x64.R14, []byte{0x41, 0x5E}}, - {x64.R15, []byte{0x41, 0x5F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("pop %s", pattern.Register) - code := x64.PopRegister(nil, pattern.Register) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Push_test.go b/src/x64/Push_test.go deleted file mode 100644 index a49095d..0000000 --- a/src/x64/Push_test.go +++ /dev/null @@ -1,39 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestPushRegister(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Code []byte - }{ - {x64.RAX, []byte{0x50}}, - {x64.RCX, []byte{0x51}}, - {x64.RDX, []byte{0x52}}, - {x64.RBX, []byte{0x53}}, - {x64.RSP, []byte{0x54}}, - {x64.RBP, []byte{0x55}}, - {x64.RSI, []byte{0x56}}, - {x64.RDI, []byte{0x57}}, - {x64.R8, []byte{0x41, 0x50}}, - {x64.R9, []byte{0x41, 0x51}}, - {x64.R10, []byte{0x41, 0x52}}, - {x64.R11, []byte{0x41, 0x53}}, - {x64.R12, []byte{0x41, 0x54}}, - {x64.R13, []byte{0x41, 0x55}}, - {x64.R14, []byte{0x41, 0x56}}, - {x64.R15, []byte{0x41, 0x57}}, - } - - for _, pattern := range usagePatterns { - t.Logf("push %s", pattern.Register) - code := x64.PushRegister(nil, pattern.Register) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Registers_test.go b/src/x64/Registers_test.go deleted file mode 100644 index 626bb84..0000000 --- a/src/x64/Registers_test.go +++ /dev/null @@ -1,12 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestRegisters(t *testing.T) { - assert.NotContains(t, x64.GeneralRegisters, x64.RSP) -} diff --git a/src/x64/Shift_test.go b/src/x64/Shift_test.go deleted file mode 100644 index dc95cf2..0000000 --- a/src/x64/Shift_test.go +++ /dev/null @@ -1,71 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestShiftLeftNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0xC1, 0xE0, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0xC1, 0xE1, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0xC1, 0xE2, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0xC1, 0xE3, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0xC1, 0xE4, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0xC1, 0xE5, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0xC1, 0xE6, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0xC1, 0xE7, 0x01}}, - {x64.R8, 1, []byte{0x49, 0xC1, 0xE0, 0x01}}, - {x64.R9, 1, []byte{0x49, 0xC1, 0xE1, 0x01}}, - {x64.R10, 1, []byte{0x49, 0xC1, 0xE2, 0x01}}, - {x64.R11, 1, []byte{0x49, 0xC1, 0xE3, 0x01}}, - {x64.R12, 1, []byte{0x49, 0xC1, 0xE4, 0x01}}, - {x64.R13, 1, []byte{0x49, 0xC1, 0xE5, 0x01}}, - {x64.R14, 1, []byte{0x49, 0xC1, 0xE6, 0x01}}, - {x64.R15, 1, []byte{0x49, 0xC1, 0xE7, 0x01}}, - } - - for _, pattern := range usagePatterns { - t.Logf("shl %s, %x", pattern.Register, pattern.Number) - code := x64.ShiftLeftNumber(nil, pattern.Register, byte(pattern.Number)) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestShiftRightSignedNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0xC1, 0xF8, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0xC1, 0xF9, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0xC1, 0xFA, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0xC1, 0xFB, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0xC1, 0xFC, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0xC1, 0xFD, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0xC1, 0xFE, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0xC1, 0xFF, 0x01}}, - {x64.R8, 1, []byte{0x49, 0xC1, 0xF8, 0x01}}, - {x64.R9, 1, []byte{0x49, 0xC1, 0xF9, 0x01}}, - {x64.R10, 1, []byte{0x49, 0xC1, 0xFA, 0x01}}, - {x64.R11, 1, []byte{0x49, 0xC1, 0xFB, 0x01}}, - {x64.R12, 1, []byte{0x49, 0xC1, 0xFC, 0x01}}, - {x64.R13, 1, []byte{0x49, 0xC1, 0xFD, 0x01}}, - {x64.R14, 1, []byte{0x49, 0xC1, 0xFE, 0x01}}, - {x64.R15, 1, []byte{0x49, 0xC1, 0xFF, 0x01}}, - } - - for _, pattern := range usagePatterns { - t.Logf("sar %s, %x", pattern.Register, pattern.Number) - code := x64.ShiftRightSignedNumber(nil, pattern.Register, byte(pattern.Number)) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/StoreDynamic_test.go b/src/x64/StoreDynamic_test.go deleted file mode 100644 index 0ff1f82..0000000 --- a/src/x64/StoreDynamic_test.go +++ /dev/null @@ -1,171 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestStoreDynamicNumber(t *testing.T) { - usagePatterns := []struct { - RegisterTo cpu.Register - Offset cpu.Register - Length byte - Number int - Code []byte - }{ - {x64.RAX, x64.R15, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RAX, x64.R15, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RAX, x64.R15, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x38, 0x7F, 0x00}}, - {x64.RAX, x64.R15, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x38, 0x7F}}, - {x64.RCX, x64.R14, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RCX, x64.R14, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RCX, x64.R14, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x31, 0x7F, 0x00}}, - {x64.RCX, x64.R14, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x31, 0x7F}}, - {x64.RDX, x64.R13, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDX, x64.R13, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDX, x64.R13, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x2A, 0x7F, 0x00}}, - {x64.RDX, x64.R13, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x2A, 0x7F}}, - {x64.RBX, x64.R12, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x23, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBX, x64.R12, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x23, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBX, x64.R12, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x23, 0x7F, 0x00}}, - {x64.RBX, x64.R12, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x23, 0x7F}}, - {x64.RSP, x64.R11, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSP, x64.R11, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSP, x64.R11, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00}}, - {x64.RSP, x64.R11, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x1C, 0x7F}}, - {x64.RBP, x64.R10, 8, 0x7F, []byte{0x4A, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBP, x64.R10, 4, 0x7F, []byte{0x42, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBP, x64.R10, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00}}, - {x64.RBP, x64.R10, 1, 0x7F, []byte{0x42, 0xC6, 0x44, 0x15, 0x00, 0x7F}}, - {x64.RSI, x64.R9, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSI, x64.R9, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSI, x64.R9, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x0E, 0x7F, 0x00}}, - {x64.RSI, x64.R9, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x0E, 0x7F}}, - {x64.RDI, x64.R8, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDI, x64.R8, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDI, x64.R8, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x07, 0x7F, 0x00}}, - {x64.RDI, x64.R8, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x07, 0x7F}}, - {x64.R8, x64.RDI, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R8, x64.RDI, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R8, x64.RDI, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x38, 0x7F, 0x00}}, - {x64.R8, x64.RDI, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x38, 0x7F}}, - {x64.R9, x64.RSI, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R9, x64.RSI, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R9, x64.RSI, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x31, 0x7F, 0x00}}, - {x64.R9, x64.RSI, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x31, 0x7F}}, - {x64.R10, x64.RBP, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R10, x64.RBP, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R10, x64.RBP, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x2A, 0x7F, 0x00}}, - {x64.R10, x64.RBP, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x2A, 0x7F}}, - {x64.R11, x64.RSP, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R11, x64.RSP, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R11, x64.RSP, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00}}, - {x64.R11, x64.RSP, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x1C, 0x7F}}, - {x64.R12, x64.RBX, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R12, x64.RBX, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R12, x64.RBX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x1C, 0x7F, 0x00}}, - {x64.R12, x64.RBX, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x1C, 0x7F}}, - {x64.R13, x64.RDX, 8, 0x7F, []byte{0x49, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R13, x64.RDX, 4, 0x7F, []byte{0x41, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R13, x64.RDX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00}}, - {x64.R13, x64.RDX, 1, 0x7F, []byte{0x41, 0xC6, 0x44, 0x15, 0x00, 0x7F}}, - {x64.R14, x64.RCX, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R14, x64.RCX, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R14, x64.RCX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x0E, 0x7F, 0x00}}, - {x64.R14, x64.RCX, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x0E, 0x7F}}, - {x64.R15, x64.RAX, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R15, x64.RAX, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R15, x64.RAX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x07, 0x7F, 0x00}}, - {x64.R15, x64.RAX, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x07, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("store %dB [%s+%s], %d", pattern.Length, pattern.RegisterTo, pattern.Offset, pattern.Number) - code := x64.StoreDynamicNumber(nil, pattern.RegisterTo, pattern.Offset, pattern.Length, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestStoreDynamicRegister(t *testing.T) { - usagePatterns := []struct { - RegisterTo cpu.Register - Offset cpu.Register - Length byte - RegisterFrom cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, 8, x64.R15, []byte{0x4E, 0x89, 0x3C, 0x38}}, - {x64.RAX, x64.R15, 4, x64.R15, []byte{0x46, 0x89, 0x3C, 0x38}}, - {x64.RAX, x64.R15, 2, x64.R15, []byte{0x66, 0x46, 0x89, 0x3C, 0x38}}, - {x64.RAX, x64.R15, 1, x64.R15, []byte{0x46, 0x88, 0x3C, 0x38}}, - {x64.RCX, x64.R14, 8, x64.R14, []byte{0x4E, 0x89, 0x34, 0x31}}, - {x64.RCX, x64.R14, 4, x64.R14, []byte{0x46, 0x89, 0x34, 0x31}}, - {x64.RCX, x64.R14, 2, x64.R14, []byte{0x66, 0x46, 0x89, 0x34, 0x31}}, - {x64.RCX, x64.R14, 1, x64.R14, []byte{0x46, 0x88, 0x34, 0x31}}, - {x64.RDX, x64.R13, 8, x64.R13, []byte{0x4E, 0x89, 0x2C, 0x2A}}, - {x64.RDX, x64.R13, 4, x64.R13, []byte{0x46, 0x89, 0x2C, 0x2A}}, - {x64.RDX, x64.R13, 2, x64.R13, []byte{0x66, 0x46, 0x89, 0x2C, 0x2A}}, - {x64.RDX, x64.R13, 1, x64.R13, []byte{0x46, 0x88, 0x2C, 0x2A}}, - {x64.RBX, x64.R12, 8, x64.R12, []byte{0x4E, 0x89, 0x24, 0x23}}, - {x64.RBX, x64.R12, 4, x64.R12, []byte{0x46, 0x89, 0x24, 0x23}}, - {x64.RBX, x64.R12, 2, x64.R12, []byte{0x66, 0x46, 0x89, 0x24, 0x23}}, - {x64.RBX, x64.R12, 1, x64.R12, []byte{0x46, 0x88, 0x24, 0x23}}, - {x64.RSP, x64.R11, 8, x64.R11, []byte{0x4E, 0x89, 0x1C, 0x1C}}, - {x64.RSP, x64.R11, 4, x64.R11, []byte{0x46, 0x89, 0x1C, 0x1C}}, - {x64.RSP, x64.R11, 2, x64.R11, []byte{0x66, 0x46, 0x89, 0x1C, 0x1C}}, - {x64.RSP, x64.R11, 1, x64.R11, []byte{0x46, 0x88, 0x1C, 0x1C}}, - {x64.RBP, x64.R10, 8, x64.R10, []byte{0x4E, 0x89, 0x54, 0x15, 0x00}}, - {x64.RBP, x64.R10, 4, x64.R10, []byte{0x46, 0x89, 0x54, 0x15, 0x00}}, - {x64.RBP, x64.R10, 2, x64.R10, []byte{0x66, 0x46, 0x89, 0x54, 0x15, 0x00}}, - {x64.RBP, x64.R10, 1, x64.R10, []byte{0x46, 0x88, 0x54, 0x15, 0x00}}, - {x64.RSI, x64.R9, 8, x64.R9, []byte{0x4E, 0x89, 0x0C, 0x0E}}, - {x64.RSI, x64.R9, 4, x64.R9, []byte{0x46, 0x89, 0x0C, 0x0E}}, - {x64.RSI, x64.R9, 2, x64.R9, []byte{0x66, 0x46, 0x89, 0x0C, 0x0E}}, - {x64.RSI, x64.R9, 1, x64.R9, []byte{0x46, 0x88, 0x0C, 0x0E}}, - {x64.RDI, x64.R8, 8, x64.R8, []byte{0x4E, 0x89, 0x04, 0x07}}, - {x64.RDI, x64.R8, 4, x64.R8, []byte{0x46, 0x89, 0x04, 0x07}}, - {x64.RDI, x64.R8, 2, x64.R8, []byte{0x66, 0x46, 0x89, 0x04, 0x07}}, - {x64.RDI, x64.R8, 1, x64.R8, []byte{0x46, 0x88, 0x04, 0x07}}, - {x64.R8, x64.RDI, 8, x64.RDI, []byte{0x49, 0x89, 0x3C, 0x38}}, - {x64.R8, x64.RDI, 4, x64.RDI, []byte{0x41, 0x89, 0x3C, 0x38}}, - {x64.R8, x64.RDI, 2, x64.RDI, []byte{0x66, 0x41, 0x89, 0x3C, 0x38}}, - {x64.R8, x64.RDI, 1, x64.RDI, []byte{0x41, 0x88, 0x3C, 0x38}}, - {x64.R9, x64.RSI, 8, x64.RSI, []byte{0x49, 0x89, 0x34, 0x31}}, - {x64.R9, x64.RSI, 4, x64.RSI, []byte{0x41, 0x89, 0x34, 0x31}}, - {x64.R9, x64.RSI, 2, x64.RSI, []byte{0x66, 0x41, 0x89, 0x34, 0x31}}, - {x64.R9, x64.RSI, 1, x64.RSI, []byte{0x41, 0x88, 0x34, 0x31}}, - {x64.R10, x64.RBP, 8, x64.RBP, []byte{0x49, 0x89, 0x2C, 0x2A}}, - {x64.R10, x64.RBP, 4, x64.RBP, []byte{0x41, 0x89, 0x2C, 0x2A}}, - {x64.R10, x64.RBP, 2, x64.RBP, []byte{0x66, 0x41, 0x89, 0x2C, 0x2A}}, - {x64.R10, x64.RBP, 1, x64.RBP, []byte{0x41, 0x88, 0x2C, 0x2A}}, - {x64.R11, x64.RSP, 8, x64.RSP, []byte{0x4A, 0x89, 0x24, 0x1C}}, - {x64.R11, x64.RSP, 4, x64.RSP, []byte{0x42, 0x89, 0x24, 0x1C}}, - {x64.R11, x64.RSP, 2, x64.RSP, []byte{0x66, 0x42, 0x89, 0x24, 0x1C}}, - {x64.R11, x64.RSP, 1, x64.RSP, []byte{0x42, 0x88, 0x24, 0x1C}}, - {x64.R12, x64.RBX, 8, x64.RBX, []byte{0x49, 0x89, 0x1C, 0x1C}}, - {x64.R12, x64.RBX, 4, x64.RBX, []byte{0x41, 0x89, 0x1C, 0x1C}}, - {x64.R12, x64.RBX, 2, x64.RBX, []byte{0x66, 0x41, 0x89, 0x1C, 0x1C}}, - {x64.R12, x64.RBX, 1, x64.RBX, []byte{0x41, 0x88, 0x1C, 0x1C}}, - {x64.R13, x64.RDX, 8, x64.RDX, []byte{0x49, 0x89, 0x54, 0x15, 0x00}}, - {x64.R13, x64.RDX, 4, x64.RDX, []byte{0x41, 0x89, 0x54, 0x15, 0x00}}, - {x64.R13, x64.RDX, 2, x64.RDX, []byte{0x66, 0x41, 0x89, 0x54, 0x15, 0x00}}, - {x64.R13, x64.RDX, 1, x64.RDX, []byte{0x41, 0x88, 0x54, 0x15, 0x00}}, - {x64.R14, x64.RCX, 8, x64.RCX, []byte{0x49, 0x89, 0x0C, 0x0E}}, - {x64.R14, x64.RCX, 4, x64.RCX, []byte{0x41, 0x89, 0x0C, 0x0E}}, - {x64.R14, x64.RCX, 2, x64.RCX, []byte{0x66, 0x41, 0x89, 0x0C, 0x0E}}, - {x64.R14, x64.RCX, 1, x64.RCX, []byte{0x41, 0x88, 0x0C, 0x0E}}, - {x64.R15, x64.RAX, 8, x64.RAX, []byte{0x49, 0x89, 0x04, 0x07}}, - {x64.R15, x64.RAX, 4, x64.RAX, []byte{0x41, 0x89, 0x04, 0x07}}, - {x64.R15, x64.RAX, 2, x64.RAX, []byte{0x66, 0x41, 0x89, 0x04, 0x07}}, - {x64.R15, x64.RAX, 1, x64.RAX, []byte{0x41, 0x88, 0x04, 0x07}}, - } - - for _, pattern := range usagePatterns { - t.Logf("store %dB [%s+%s], %s", pattern.Length, pattern.RegisterTo, pattern.Offset, pattern.RegisterFrom) - code := x64.StoreDynamicRegister(nil, pattern.RegisterTo, pattern.Offset, pattern.Length, pattern.RegisterFrom) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Store_test.go b/src/x64/Store_test.go deleted file mode 100644 index 3f4bd05..0000000 --- a/src/x64/Store_test.go +++ /dev/null @@ -1,305 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestStoreNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Offset byte - Length byte - Number int - Code []byte - }{ - // No offset - {x64.RAX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RAX, 0, 4, 0x7F, []byte{0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RAX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x00, 0x7F, 0x00}}, - {x64.RAX, 0, 1, 0x7F, []byte{0xC6, 0x00, 0x7F}}, - {x64.RCX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RCX, 0, 4, 0x7F, []byte{0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RCX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x01, 0x7F, 0x00}}, - {x64.RCX, 0, 1, 0x7F, []byte{0xC6, 0x01, 0x7F}}, - {x64.RDX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDX, 0, 4, 0x7F, []byte{0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x02, 0x7F, 0x00}}, - {x64.RDX, 0, 1, 0x7F, []byte{0xC6, 0x02, 0x7F}}, - {x64.RBX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBX, 0, 4, 0x7F, []byte{0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x03, 0x7F, 0x00}}, - {x64.RBX, 0, 1, 0x7F, []byte{0xC6, 0x03, 0x7F}}, - {x64.RSP, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSP, 0, 4, 0x7F, []byte{0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSP, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x04, 0x24, 0x7F, 0x00}}, - {x64.RSP, 0, 1, 0x7F, []byte{0xC6, 0x04, 0x24, 0x7F}}, - {x64.RBP, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBP, 0, 4, 0x7F, []byte{0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBP, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x45, 0x00, 0x7F, 0x00}}, - {x64.RBP, 0, 1, 0x7F, []byte{0xC6, 0x45, 0x00, 0x7F}}, - {x64.RSI, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSI, 0, 4, 0x7F, []byte{0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSI, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x06, 0x7F, 0x00}}, - {x64.RSI, 0, 1, 0x7F, []byte{0xC6, 0x06, 0x7F}}, - {x64.RDI, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDI, 0, 4, 0x7F, []byte{0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDI, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x07, 0x7F, 0x00}}, - {x64.RDI, 0, 1, 0x7F, []byte{0xC6, 0x07, 0x7F}}, - {x64.R8, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R8, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R8, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x00, 0x7F, 0x00}}, - {x64.R8, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x00, 0x7F}}, - {x64.R9, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R9, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R9, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x01, 0x7F, 0x00}}, - {x64.R9, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x01, 0x7F}}, - {x64.R10, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R10, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R10, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x02, 0x7F, 0x00}}, - {x64.R10, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x02, 0x7F}}, - {x64.R11, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R11, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R11, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x03, 0x7F, 0x00}}, - {x64.R11, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x03, 0x7F}}, - {x64.R12, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R12, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R12, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x24, 0x7F, 0x00}}, - {x64.R12, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x24, 0x7F}}, - {x64.R13, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R13, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R13, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x45, 0x00, 0x7F, 0x00}}, - {x64.R13, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x45, 0x00, 0x7F}}, - {x64.R14, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R14, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R14, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x06, 0x7F, 0x00}}, - {x64.R14, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x06, 0x7F}}, - {x64.R15, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R15, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R15, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x07, 0x7F, 0x00}}, - {x64.R15, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x07, 0x7F}}, - - // Offset of 1 - {x64.RAX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RAX, 1, 4, 0x7F, []byte{0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RAX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x40, 0x01, 0x7F, 0x00}}, - {x64.RAX, 1, 1, 0x7F, []byte{0xC6, 0x40, 0x01, 0x7F}}, - {x64.RCX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RCX, 1, 4, 0x7F, []byte{0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RCX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x41, 0x01, 0x7F, 0x00}}, - {x64.RCX, 1, 1, 0x7F, []byte{0xC6, 0x41, 0x01, 0x7F}}, - {x64.RDX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDX, 1, 4, 0x7F, []byte{0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x42, 0x01, 0x7F, 0x00}}, - {x64.RDX, 1, 1, 0x7F, []byte{0xC6, 0x42, 0x01, 0x7F}}, - {x64.RBX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBX, 1, 4, 0x7F, []byte{0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x43, 0x01, 0x7F, 0x00}}, - {x64.RBX, 1, 1, 0x7F, []byte{0xC6, 0x43, 0x01, 0x7F}}, - {x64.RSP, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSP, 1, 4, 0x7F, []byte{0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSP, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00}}, - {x64.RSP, 1, 1, 0x7F, []byte{0xC6, 0x44, 0x24, 0x01, 0x7F}}, - {x64.RBP, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBP, 1, 4, 0x7F, []byte{0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RBP, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x45, 0x01, 0x7F, 0x00}}, - {x64.RBP, 1, 1, 0x7F, []byte{0xC6, 0x45, 0x01, 0x7F}}, - {x64.RSI, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSI, 1, 4, 0x7F, []byte{0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RSI, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x46, 0x01, 0x7F, 0x00}}, - {x64.RSI, 1, 1, 0x7F, []byte{0xC6, 0x46, 0x01, 0x7F}}, - {x64.RDI, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDI, 1, 4, 0x7F, []byte{0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.RDI, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x47, 0x01, 0x7F, 0x00}}, - {x64.RDI, 1, 1, 0x7F, []byte{0xC6, 0x47, 0x01, 0x7F}}, - {x64.R8, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R8, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R8, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x40, 0x01, 0x7F, 0x00}}, - {x64.R8, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x40, 0x01, 0x7F}}, - {x64.R9, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R9, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R9, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x41, 0x01, 0x7F, 0x00}}, - {x64.R9, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x41, 0x01, 0x7F}}, - {x64.R10, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R10, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R10, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x42, 0x01, 0x7F, 0x00}}, - {x64.R10, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x42, 0x01, 0x7F}}, - {x64.R11, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R11, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R11, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x43, 0x01, 0x7F, 0x00}}, - {x64.R11, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x43, 0x01, 0x7F}}, - {x64.R12, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R12, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R12, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00}}, - {x64.R12, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x44, 0x24, 0x01, 0x7F}}, - {x64.R13, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R13, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R13, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x45, 0x01, 0x7F, 0x00}}, - {x64.R13, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x45, 0x01, 0x7F}}, - {x64.R14, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R14, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R14, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x46, 0x01, 0x7F, 0x00}}, - {x64.R14, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x46, 0x01, 0x7F}}, - {x64.R15, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R15, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, - {x64.R15, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x47, 0x01, 0x7F, 0x00}}, - {x64.R15, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x47, 0x01, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("store %dB [%s+%d], %d", pattern.Length, pattern.Register, pattern.Offset, pattern.Number) - code := x64.StoreNumber(nil, pattern.Register, pattern.Offset, pattern.Length, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestStoreRegister(t *testing.T) { - usagePatterns := []struct { - RegisterTo cpu.Register - Offset byte - Length byte - RegisterFrom cpu.Register - Code []byte - }{ - // No offset - {x64.RAX, 0, 8, x64.R15, []byte{0x4C, 0x89, 0x38}}, - {x64.RAX, 0, 4, x64.R15, []byte{0x44, 0x89, 0x38}}, - {x64.RAX, 0, 2, x64.R15, []byte{0x66, 0x44, 0x89, 0x38}}, - {x64.RAX, 0, 1, x64.R15, []byte{0x44, 0x88, 0x38}}, - {x64.RCX, 0, 8, x64.R14, []byte{0x4C, 0x89, 0x31}}, - {x64.RCX, 0, 4, x64.R14, []byte{0x44, 0x89, 0x31}}, - {x64.RCX, 0, 2, x64.R14, []byte{0x66, 0x44, 0x89, 0x31}}, - {x64.RCX, 0, 1, x64.R14, []byte{0x44, 0x88, 0x31}}, - {x64.RDX, 0, 8, x64.R13, []byte{0x4C, 0x89, 0x2A}}, - {x64.RDX, 0, 4, x64.R13, []byte{0x44, 0x89, 0x2A}}, - {x64.RDX, 0, 2, x64.R13, []byte{0x66, 0x44, 0x89, 0x2A}}, - {x64.RDX, 0, 1, x64.R13, []byte{0x44, 0x88, 0x2A}}, - {x64.RBX, 0, 8, x64.R12, []byte{0x4C, 0x89, 0x23}}, - {x64.RBX, 0, 4, x64.R12, []byte{0x44, 0x89, 0x23}}, - {x64.RBX, 0, 2, x64.R12, []byte{0x66, 0x44, 0x89, 0x23}}, - {x64.RBX, 0, 1, x64.R12, []byte{0x44, 0x88, 0x23}}, - {x64.RSP, 0, 8, x64.R11, []byte{0x4C, 0x89, 0x1C, 0x24}}, - {x64.RSP, 0, 4, x64.R11, []byte{0x44, 0x89, 0x1C, 0x24}}, - {x64.RSP, 0, 2, x64.R11, []byte{0x66, 0x44, 0x89, 0x1C, 0x24}}, - {x64.RSP, 0, 1, x64.R11, []byte{0x44, 0x88, 0x1C, 0x24}}, - {x64.RBP, 0, 8, x64.R10, []byte{0x4C, 0x89, 0x55, 0x00}}, - {x64.RBP, 0, 4, x64.R10, []byte{0x44, 0x89, 0x55, 0x00}}, - {x64.RBP, 0, 2, x64.R10, []byte{0x66, 0x44, 0x89, 0x55, 0x00}}, - {x64.RBP, 0, 1, x64.R10, []byte{0x44, 0x88, 0x55, 0x00}}, - {x64.RSI, 0, 8, x64.R9, []byte{0x4C, 0x89, 0x0E}}, - {x64.RSI, 0, 4, x64.R9, []byte{0x44, 0x89, 0x0E}}, - {x64.RSI, 0, 2, x64.R9, []byte{0x66, 0x44, 0x89, 0x0E}}, - {x64.RSI, 0, 1, x64.R9, []byte{0x44, 0x88, 0x0E}}, - {x64.RDI, 0, 8, x64.R8, []byte{0x4C, 0x89, 0x07}}, - {x64.RDI, 0, 4, x64.R8, []byte{0x44, 0x89, 0x07}}, - {x64.RDI, 0, 2, x64.R8, []byte{0x66, 0x44, 0x89, 0x07}}, - {x64.RDI, 0, 1, x64.R8, []byte{0x44, 0x88, 0x07}}, - {x64.R8, 0, 8, x64.RDI, []byte{0x49, 0x89, 0x38}}, - {x64.R8, 0, 4, x64.RDI, []byte{0x41, 0x89, 0x38}}, - {x64.R8, 0, 2, x64.RDI, []byte{0x66, 0x41, 0x89, 0x38}}, - {x64.R8, 0, 1, x64.RDI, []byte{0x41, 0x88, 0x38}}, - {x64.R9, 0, 8, x64.RSI, []byte{0x49, 0x89, 0x31}}, - {x64.R9, 0, 4, x64.RSI, []byte{0x41, 0x89, 0x31}}, - {x64.R9, 0, 2, x64.RSI, []byte{0x66, 0x41, 0x89, 0x31}}, - {x64.R9, 0, 1, x64.RSI, []byte{0x41, 0x88, 0x31}}, - {x64.R10, 0, 8, x64.RBP, []byte{0x49, 0x89, 0x2A}}, - {x64.R10, 0, 4, x64.RBP, []byte{0x41, 0x89, 0x2A}}, - {x64.R10, 0, 2, x64.RBP, []byte{0x66, 0x41, 0x89, 0x2A}}, - {x64.R10, 0, 1, x64.RBP, []byte{0x41, 0x88, 0x2A}}, - {x64.R11, 0, 8, x64.RSP, []byte{0x49, 0x89, 0x23}}, - {x64.R11, 0, 4, x64.RSP, []byte{0x41, 0x89, 0x23}}, - {x64.R11, 0, 2, x64.RSP, []byte{0x66, 0x41, 0x89, 0x23}}, - {x64.R11, 0, 1, x64.RSP, []byte{0x41, 0x88, 0x23}}, - {x64.R12, 0, 8, x64.RBX, []byte{0x49, 0x89, 0x1C, 0x24}}, - {x64.R12, 0, 4, x64.RBX, []byte{0x41, 0x89, 0x1C, 0x24}}, - {x64.R12, 0, 2, x64.RBX, []byte{0x66, 0x41, 0x89, 0x1C, 0x24}}, - {x64.R12, 0, 1, x64.RBX, []byte{0x41, 0x88, 0x1C, 0x24}}, - {x64.R13, 0, 8, x64.RDX, []byte{0x49, 0x89, 0x55, 0x00}}, - {x64.R13, 0, 4, x64.RDX, []byte{0x41, 0x89, 0x55, 0x00}}, - {x64.R13, 0, 2, x64.RDX, []byte{0x66, 0x41, 0x89, 0x55, 0x00}}, - {x64.R13, 0, 1, x64.RDX, []byte{0x41, 0x88, 0x55, 0x00}}, - {x64.R14, 0, 8, x64.RCX, []byte{0x49, 0x89, 0x0E}}, - {x64.R14, 0, 4, x64.RCX, []byte{0x41, 0x89, 0x0E}}, - {x64.R14, 0, 2, x64.RCX, []byte{0x66, 0x41, 0x89, 0x0E}}, - {x64.R14, 0, 1, x64.RCX, []byte{0x41, 0x88, 0x0E}}, - {x64.R15, 0, 8, x64.RAX, []byte{0x49, 0x89, 0x07}}, - {x64.R15, 0, 4, x64.RAX, []byte{0x41, 0x89, 0x07}}, - {x64.R15, 0, 2, x64.RAX, []byte{0x66, 0x41, 0x89, 0x07}}, - {x64.R15, 0, 1, x64.RAX, []byte{0x41, 0x88, 0x07}}, - - // Offset of 1 - {x64.RAX, 1, 8, x64.R15, []byte{0x4C, 0x89, 0x78, 0x01}}, - {x64.RAX, 1, 4, x64.R15, []byte{0x44, 0x89, 0x78, 0x01}}, - {x64.RAX, 1, 2, x64.R15, []byte{0x66, 0x44, 0x89, 0x78, 0x01}}, - {x64.RAX, 1, 1, x64.R15, []byte{0x44, 0x88, 0x78, 0x01}}, - {x64.RCX, 1, 8, x64.R14, []byte{0x4C, 0x89, 0x71, 0x01}}, - {x64.RCX, 1, 4, x64.R14, []byte{0x44, 0x89, 0x71, 0x01}}, - {x64.RCX, 1, 2, x64.R14, []byte{0x66, 0x44, 0x89, 0x71, 0x01}}, - {x64.RCX, 1, 1, x64.R14, []byte{0x44, 0x88, 0x71, 0x01}}, - {x64.RDX, 1, 8, x64.R13, []byte{0x4C, 0x89, 0x6A, 0x01}}, - {x64.RDX, 1, 4, x64.R13, []byte{0x44, 0x89, 0x6A, 0x01}}, - {x64.RDX, 1, 2, x64.R13, []byte{0x66, 0x44, 0x89, 0x6A, 0x01}}, - {x64.RDX, 1, 1, x64.R13, []byte{0x44, 0x88, 0x6A, 0x01}}, - {x64.RBX, 1, 8, x64.R12, []byte{0x4C, 0x89, 0x63, 0x01}}, - {x64.RBX, 1, 4, x64.R12, []byte{0x44, 0x89, 0x63, 0x01}}, - {x64.RBX, 1, 2, x64.R12, []byte{0x66, 0x44, 0x89, 0x63, 0x01}}, - {x64.RBX, 1, 1, x64.R12, []byte{0x44, 0x88, 0x63, 0x01}}, - {x64.RSP, 1, 8, x64.R11, []byte{0x4C, 0x89, 0x5C, 0x24, 0x01}}, - {x64.RSP, 1, 4, x64.R11, []byte{0x44, 0x89, 0x5C, 0x24, 0x01}}, - {x64.RSP, 1, 2, x64.R11, []byte{0x66, 0x44, 0x89, 0x5C, 0x24, 0x01}}, - {x64.RSP, 1, 1, x64.R11, []byte{0x44, 0x88, 0x5C, 0x24, 0x01}}, - {x64.RBP, 1, 8, x64.R10, []byte{0x4C, 0x89, 0x55, 0x01}}, - {x64.RBP, 1, 4, x64.R10, []byte{0x44, 0x89, 0x55, 0x01}}, - {x64.RBP, 1, 2, x64.R10, []byte{0x66, 0x44, 0x89, 0x55, 0x01}}, - {x64.RBP, 1, 1, x64.R10, []byte{0x44, 0x88, 0x55, 0x01}}, - {x64.RSI, 1, 8, x64.R9, []byte{0x4C, 0x89, 0x4E, 0x01}}, - {x64.RSI, 1, 4, x64.R9, []byte{0x44, 0x89, 0x4E, 0x01}}, - {x64.RSI, 1, 2, x64.R9, []byte{0x66, 0x44, 0x89, 0x4E, 0x01}}, - {x64.RSI, 1, 1, x64.R9, []byte{0x44, 0x88, 0x4E, 0x01}}, - {x64.RDI, 1, 8, x64.R8, []byte{0x4C, 0x89, 0x47, 0x01}}, - {x64.RDI, 1, 4, x64.R8, []byte{0x44, 0x89, 0x47, 0x01}}, - {x64.RDI, 1, 2, x64.R8, []byte{0x66, 0x44, 0x89, 0x47, 0x01}}, - {x64.RDI, 1, 1, x64.R8, []byte{0x44, 0x88, 0x47, 0x01}}, - {x64.R8, 1, 8, x64.RDI, []byte{0x49, 0x89, 0x78, 0x01}}, - {x64.R8, 1, 4, x64.RDI, []byte{0x41, 0x89, 0x78, 0x01}}, - {x64.R8, 1, 2, x64.RDI, []byte{0x66, 0x41, 0x89, 0x78, 0x01}}, - {x64.R8, 1, 1, x64.RDI, []byte{0x41, 0x88, 0x78, 0x01}}, - {x64.R9, 1, 8, x64.RSI, []byte{0x49, 0x89, 0x71, 0x01}}, - {x64.R9, 1, 4, x64.RSI, []byte{0x41, 0x89, 0x71, 0x01}}, - {x64.R9, 1, 2, x64.RSI, []byte{0x66, 0x41, 0x89, 0x71, 0x01}}, - {x64.R9, 1, 1, x64.RSI, []byte{0x41, 0x88, 0x71, 0x01}}, - {x64.R10, 1, 8, x64.RBP, []byte{0x49, 0x89, 0x6A, 0x01}}, - {x64.R10, 1, 4, x64.RBP, []byte{0x41, 0x89, 0x6A, 0x01}}, - {x64.R10, 1, 2, x64.RBP, []byte{0x66, 0x41, 0x89, 0x6A, 0x01}}, - {x64.R10, 1, 1, x64.RBP, []byte{0x41, 0x88, 0x6A, 0x01}}, - {x64.R11, 1, 8, x64.RSP, []byte{0x49, 0x89, 0x63, 0x01}}, - {x64.R11, 1, 4, x64.RSP, []byte{0x41, 0x89, 0x63, 0x01}}, - {x64.R11, 1, 2, x64.RSP, []byte{0x66, 0x41, 0x89, 0x63, 0x01}}, - {x64.R11, 1, 1, x64.RSP, []byte{0x41, 0x88, 0x63, 0x01}}, - {x64.R12, 1, 8, x64.RBX, []byte{0x49, 0x89, 0x5C, 0x24, 0x01}}, - {x64.R12, 1, 4, x64.RBX, []byte{0x41, 0x89, 0x5C, 0x24, 0x01}}, - {x64.R12, 1, 2, x64.RBX, []byte{0x66, 0x41, 0x89, 0x5C, 0x24, 0x01}}, - {x64.R12, 1, 1, x64.RBX, []byte{0x41, 0x88, 0x5C, 0x24, 01}}, - {x64.R13, 1, 8, x64.RDX, []byte{0x49, 0x89, 0x55, 0x01}}, - {x64.R13, 1, 4, x64.RDX, []byte{0x41, 0x89, 0x55, 0x01}}, - {x64.R13, 1, 2, x64.RDX, []byte{0x66, 0x41, 0x89, 0x55, 0x01}}, - {x64.R13, 1, 1, x64.RDX, []byte{0x41, 0x88, 0x55, 0x01}}, - {x64.R14, 1, 8, x64.RCX, []byte{0x49, 0x89, 0x4E, 0x01}}, - {x64.R14, 1, 4, x64.RCX, []byte{0x41, 0x89, 0x4E, 0x01}}, - {x64.R14, 1, 2, x64.RCX, []byte{0x66, 0x41, 0x89, 0x4E, 0x01}}, - {x64.R14, 1, 1, x64.RCX, []byte{0x41, 0x88, 0x4E, 0x01}}, - {x64.R15, 1, 8, x64.RAX, []byte{0x49, 0x89, 0x47, 0x01}}, - {x64.R15, 1, 4, x64.RAX, []byte{0x41, 0x89, 0x47, 0x01}}, - {x64.R15, 1, 2, x64.RAX, []byte{0x66, 0x41, 0x89, 0x47, 0x01}}, - {x64.R15, 1, 1, x64.RAX, []byte{0x41, 0x88, 0x47, 0x01}}, - } - - for _, pattern := range usagePatterns { - t.Logf("store %dB [%s+%d], %s", pattern.Length, pattern.RegisterTo, pattern.Offset, pattern.RegisterFrom) - code := x64.StoreRegister(nil, pattern.RegisterTo, pattern.Offset, pattern.Length, pattern.RegisterFrom) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Sub_test.go b/src/x64/Sub_test.go deleted file mode 100644 index 7f03b53..0000000 --- a/src/x64/Sub_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestSubRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x83, 0xE8, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x83, 0xE9, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x83, 0xEA, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x83, 0xEB, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x83, 0xEC, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x83, 0xED, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x83, 0xEE, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x83, 0xEF, 0x01}}, - {x64.R8, 1, []byte{0x49, 0x83, 0xE8, 0x01}}, - {x64.R9, 1, []byte{0x49, 0x83, 0xE9, 0x01}}, - {x64.R10, 1, []byte{0x49, 0x83, 0xEA, 0x01}}, - {x64.R11, 1, []byte{0x49, 0x83, 0xEB, 0x01}}, - {x64.R12, 1, []byte{0x49, 0x83, 0xEC, 0x01}}, - {x64.R13, 1, []byte{0x49, 0x83, 0xED, 0x01}}, - {x64.R14, 1, []byte{0x49, 0x83, 0xEE, 0x01}}, - {x64.R15, 1, []byte{0x49, 0x83, 0xEF, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEF, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE8, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE9, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEA, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEB, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEC, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEE, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEF, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("sub %s, %x", pattern.Register, pattern.Number) - code := x64.SubRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestSubRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x29, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x29, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x29, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x29, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x29, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x29, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x29, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x29, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x29, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x29, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x29, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x29, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x29, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x29, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x29, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x29, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("sub %s, %s", pattern.Left, pattern.Right) - code := x64.SubRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/Xor_test.go b/src/x64/Xor_test.go deleted file mode 100644 index 1a2b629..0000000 --- a/src/x64/Xor_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/cpu" - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestXorRegisterNumber(t *testing.T) { - usagePatterns := []struct { - Register cpu.Register - Number int - Code []byte - }{ - {x64.RAX, 1, []byte{0x48, 0x83, 0xF0, 0x01}}, - {x64.RCX, 1, []byte{0x48, 0x83, 0xF1, 0x01}}, - {x64.RDX, 1, []byte{0x48, 0x83, 0xF2, 0x01}}, - {x64.RBX, 1, []byte{0x48, 0x83, 0xF3, 0x01}}, - {x64.RSP, 1, []byte{0x48, 0x83, 0xF4, 0x01}}, - {x64.RBP, 1, []byte{0x48, 0x83, 0xF5, 0x01}}, - {x64.RSI, 1, []byte{0x48, 0x83, 0xF6, 0x01}}, - {x64.RDI, 1, []byte{0x48, 0x83, 0xF7, 0x01}}, - {x64.R8, 1, []byte{0x49, 0x83, 0xF0, 0x01}}, - {x64.R9, 1, []byte{0x49, 0x83, 0xF1, 0x01}}, - {x64.R10, 1, []byte{0x49, 0x83, 0xF2, 0x01}}, - {x64.R11, 1, []byte{0x49, 0x83, 0xF3, 0x01}}, - {x64.R12, 1, []byte{0x49, 0x83, 0xF4, 0x01}}, - {x64.R13, 1, []byte{0x49, 0x83, 0xF5, 0x01}}, - {x64.R14, 1, []byte{0x49, 0x83, 0xF6, 0x01}}, - {x64.R15, 1, []byte{0x49, 0x83, 0xF7, 0x01}}, - - {x64.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF1, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF3, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF5, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF7, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF0, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF1, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF2, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF3, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF4, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF5, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, - {x64.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF7, 0xFF, 0xFF, 0xFF, 0x7F}}, - } - - for _, pattern := range usagePatterns { - t.Logf("xor %s, %x", pattern.Register, pattern.Number) - code := x64.XorRegisterNumber(nil, pattern.Register, pattern.Number) - assert.DeepEqual(t, code, pattern.Code) - } -} - -func TestXorRegisterRegister(t *testing.T) { - usagePatterns := []struct { - Left cpu.Register - Right cpu.Register - Code []byte - }{ - {x64.RAX, x64.R15, []byte{0x4C, 0x31, 0xF8}}, - {x64.RCX, x64.R14, []byte{0x4C, 0x31, 0xF1}}, - {x64.RDX, x64.R13, []byte{0x4C, 0x31, 0xEA}}, - {x64.RBX, x64.R12, []byte{0x4C, 0x31, 0xE3}}, - {x64.RSP, x64.R11, []byte{0x4C, 0x31, 0xDC}}, - {x64.RBP, x64.R10, []byte{0x4C, 0x31, 0xD5}}, - {x64.RSI, x64.R9, []byte{0x4C, 0x31, 0xCE}}, - {x64.RDI, x64.R8, []byte{0x4C, 0x31, 0xC7}}, - {x64.R8, x64.RDI, []byte{0x49, 0x31, 0xF8}}, - {x64.R9, x64.RSI, []byte{0x49, 0x31, 0xF1}}, - {x64.R10, x64.RBP, []byte{0x49, 0x31, 0xEA}}, - {x64.R11, x64.RSP, []byte{0x49, 0x31, 0xE3}}, - {x64.R12, x64.RBX, []byte{0x49, 0x31, 0xDC}}, - {x64.R13, x64.RDX, []byte{0x49, 0x31, 0xD5}}, - {x64.R14, x64.RCX, []byte{0x49, 0x31, 0xCE}}, - {x64.R15, x64.RAX, []byte{0x49, 0x31, 0xC7}}, - } - - for _, pattern := range usagePatterns { - t.Logf("xor %s, %s", pattern.Left, pattern.Right) - code := x64.XorRegisterRegister(nil, pattern.Left, pattern.Right) - assert.DeepEqual(t, code, pattern.Code) - } -} diff --git a/src/x64/x64_test.go b/src/x64/x64_test.go deleted file mode 100644 index 8216f1a..0000000 --- a/src/x64/x64_test.go +++ /dev/null @@ -1,19 +0,0 @@ -package x64_test - -import ( - "testing" - - "git.akyoto.dev/cli/q/src/x64" - "git.akyoto.dev/go/assert" -) - -func TestX64(t *testing.T) { - assert.DeepEqual(t, x64.AlignStack(nil), []byte{0x48, 0x83, 0xE4, 0xF0}) - assert.DeepEqual(t, x64.Call(nil, 1), []byte{0xE8, 0x01, 0x00, 0x00, 0x00}) - assert.DeepEqual(t, x64.CallAtAddress(nil, 1), []byte{0xFF, 0x15, 0x01, 0x00, 0x00, 0x00}) - assert.DeepEqual(t, x64.ExtendRAXToRDX(nil), []byte{0x48, 0x99}) - assert.DeepEqual(t, x64.MoveRegisterNumber(nil, 0, 1), []byte{0xB8, 0x01, 0x00, 0x00, 0x00}) - assert.DeepEqual(t, x64.MoveRegisterNumber(nil, 1, 1), []byte{0xB9, 0x01, 0x00, 0x00, 0x00}) - assert.DeepEqual(t, x64.Return(nil), []byte{0xC3}) - assert.DeepEqual(t, x64.Syscall(nil), []byte{0x0F, 0x05}) -} diff --git a/src/x64/Add.go b/src/x86/Add.go similarity index 97% rename from src/x64/Add.go rename to src/x86/Add.go index fb70735..9569a56 100644 --- a/src/x64/Add.go +++ b/src/x86/Add.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Add_test.go b/src/x86/Add_test.go new file mode 100644 index 0000000..4aa285e --- /dev/null +++ b/src/x86/Add_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestAddRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x83, 0xC0, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x83, 0xC1, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x83, 0xC2, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x83, 0xC3, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x83, 0xC4, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x83, 0xC5, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x83, 0xC6, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x83, 0xC7, 0x01}}, + {x86.R8, 1, []byte{0x49, 0x83, 0xC0, 0x01}}, + {x86.R9, 1, []byte{0x49, 0x83, 0xC1, 0x01}}, + {x86.R10, 1, []byte{0x49, 0x83, 0xC2, 0x01}}, + {x86.R11, 1, []byte{0x49, 0x83, 0xC3, 0x01}}, + {x86.R12, 1, []byte{0x49, 0x83, 0xC4, 0x01}}, + {x86.R13, 1, []byte{0x49, 0x83, 0xC5, 0x01}}, + {x86.R14, 1, []byte{0x49, 0x83, 0xC6, 0x01}}, + {x86.R15, 1, []byte{0x49, 0x83, 0xC7, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC1, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC3, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC5, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC7, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC1, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC3, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC5, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC7, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("add %s, %x", pattern.Register, pattern.Number) + code := x86.AddRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestAddRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x01, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x01, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x01, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x01, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x01, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x01, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x01, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x01, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x01, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x01, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x01, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x01, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x01, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x01, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x01, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x01, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("add %s, %s", pattern.Left, pattern.Right) + code := x86.AddRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/AlignStack.go b/src/x86/AlignStack.go similarity index 91% rename from src/x64/AlignStack.go rename to src/x86/AlignStack.go index d3199e1..b2ce237 100644 --- a/src/x64/AlignStack.go +++ b/src/x86/AlignStack.go @@ -1,4 +1,4 @@ -package x64 +package x86 // AlignStack aligns RSP on a 16-byte boundary. func AlignStack(code []byte) []byte { diff --git a/src/x64/And.go b/src/x86/And.go similarity index 97% rename from src/x64/And.go rename to src/x86/And.go index 8556507..39da3a8 100644 --- a/src/x64/And.go +++ b/src/x86/And.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/And_test.go b/src/x86/And_test.go new file mode 100644 index 0000000..a4dbd58 --- /dev/null +++ b/src/x86/And_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestAndRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x83, 0xE0, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x83, 0xE1, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x83, 0xE2, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x83, 0xE3, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x83, 0xE4, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x83, 0xE5, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x83, 0xE6, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x83, 0xE7, 0x01}}, + {x86.R8, 1, []byte{0x49, 0x83, 0xE0, 0x01}}, + {x86.R9, 1, []byte{0x49, 0x83, 0xE1, 0x01}}, + {x86.R10, 1, []byte{0x49, 0x83, 0xE2, 0x01}}, + {x86.R11, 1, []byte{0x49, 0x83, 0xE3, 0x01}}, + {x86.R12, 1, []byte{0x49, 0x83, 0xE4, 0x01}}, + {x86.R13, 1, []byte{0x49, 0x83, 0xE5, 0x01}}, + {x86.R14, 1, []byte{0x49, 0x83, 0xE6, 0x01}}, + {x86.R15, 1, []byte{0x49, 0x83, 0xE7, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE1, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE3, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE5, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE7, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE1, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE3, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE5, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE7, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("and %s, %x", pattern.Register, pattern.Number) + code := x86.AndRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestAndRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x21, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x21, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x21, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x21, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x21, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x21, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x21, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x21, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x21, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x21, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x21, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x21, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x21, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x21, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x21, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x21, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("and %s, %s", pattern.Left, pattern.Right) + code := x86.AndRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Call.go b/src/x86/Call.go similarity index 98% rename from src/x64/Call.go rename to src/x86/Call.go index 6c37d7b..812b484 100644 --- a/src/x64/Call.go +++ b/src/x86/Call.go @@ -1,4 +1,4 @@ -package x64 +package x86 // Call places the return address on the top of the stack and continues // program flow at the new address. diff --git a/src/x64/Compare.go b/src/x86/Compare.go similarity index 97% rename from src/x64/Compare.go rename to src/x86/Compare.go index 3c48dcf..6b67aaa 100644 --- a/src/x64/Compare.go +++ b/src/x86/Compare.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Compare_test.go b/src/x86/Compare_test.go new file mode 100644 index 0000000..dbf6795 --- /dev/null +++ b/src/x86/Compare_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestCompareRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x83, 0xF8, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x83, 0xF9, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x83, 0xFA, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x83, 0xFB, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x83, 0xFC, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x83, 0xFD, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x83, 0xFE, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x83, 0xFF, 0x01}}, + {x86.R8, 1, []byte{0x49, 0x83, 0xF8, 0x01}}, + {x86.R9, 1, []byte{0x49, 0x83, 0xF9, 0x01}}, + {x86.R10, 1, []byte{0x49, 0x83, 0xFA, 0x01}}, + {x86.R11, 1, []byte{0x49, 0x83, 0xFB, 0x01}}, + {x86.R12, 1, []byte{0x49, 0x83, 0xFC, 0x01}}, + {x86.R13, 1, []byte{0x49, 0x83, 0xFD, 0x01}}, + {x86.R14, 1, []byte{0x49, 0x83, 0xFE, 0x01}}, + {x86.R15, 1, []byte{0x49, 0x83, 0xFF, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFD, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFD, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("cmp %s, %x", pattern.Register, pattern.Number) + code := x86.CompareRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestCompareRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x39, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x39, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x39, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x39, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x39, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x39, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x39, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x39, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x39, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x39, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x39, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x39, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x39, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x39, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x39, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x39, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("cmp %s, %s", pattern.Left, pattern.Right) + code := x86.CompareRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Div.go b/src/x86/Div.go similarity index 96% rename from src/x64/Div.go rename to src/x86/Div.go index 26439d1..b6c5ebf 100644 --- a/src/x64/Div.go +++ b/src/x86/Div.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Div_test.go b/src/x86/Div_test.go new file mode 100644 index 0000000..2af2bda --- /dev/null +++ b/src/x86/Div_test.go @@ -0,0 +1,39 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestDivRegister(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Code []byte + }{ + {x86.RAX, []byte{0x48, 0xF7, 0xF8}}, + {x86.RCX, []byte{0x48, 0xF7, 0xF9}}, + {x86.RDX, []byte{0x48, 0xF7, 0xFA}}, + {x86.RBX, []byte{0x48, 0xF7, 0xFB}}, + {x86.RSP, []byte{0x48, 0xF7, 0xFC}}, + {x86.RBP, []byte{0x48, 0xF7, 0xFD}}, + {x86.RSI, []byte{0x48, 0xF7, 0xFE}}, + {x86.RDI, []byte{0x48, 0xF7, 0xFF}}, + {x86.R8, []byte{0x49, 0xF7, 0xF8}}, + {x86.R9, []byte{0x49, 0xF7, 0xF9}}, + {x86.R10, []byte{0x49, 0xF7, 0xFA}}, + {x86.R11, []byte{0x49, 0xF7, 0xFB}}, + {x86.R12, []byte{0x49, 0xF7, 0xFC}}, + {x86.R13, []byte{0x49, 0xF7, 0xFD}}, + {x86.R14, []byte{0x49, 0xF7, 0xFE}}, + {x86.R15, []byte{0x49, 0xF7, 0xFF}}, + } + + for _, pattern := range usagePatterns { + t.Logf("idiv %s", pattern.Register) + code := x86.DivRegister(nil, pattern.Register) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/ExtendRAXToRDX.go b/src/x86/ExtendRAXToRDX.go similarity index 93% rename from src/x64/ExtendRAXToRDX.go rename to src/x86/ExtendRAXToRDX.go index 2f03963..7d97a86 100644 --- a/src/x64/ExtendRAXToRDX.go +++ b/src/x86/ExtendRAXToRDX.go @@ -1,4 +1,4 @@ -package x64 +package x86 // ExtendRAXToRDX doubles the size of RAX by sign-extending it to RDX. // This is also known as CQO. diff --git a/src/x64/Jump.go b/src/x86/Jump.go similarity index 98% rename from src/x64/Jump.go rename to src/x86/Jump.go index 1174f58..27b1ef4 100644 --- a/src/x64/Jump.go +++ b/src/x86/Jump.go @@ -1,4 +1,4 @@ -package x64 +package x86 // Jump continues program flow at the new address. // The address is relative to the next instruction. diff --git a/src/x64/Jump_test.go b/src/x86/Jump_test.go similarity index 56% rename from src/x64/Jump_test.go rename to src/x86/Jump_test.go index 4dde162..b2df363 100644 --- a/src/x64/Jump_test.go +++ b/src/x86/Jump_test.go @@ -1,9 +1,9 @@ -package x64_test +package x86_test import ( "testing" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" "git.akyoto.dev/go/assert" ) @@ -25,16 +25,16 @@ func TestJump(t *testing.T) { for _, pattern := range usagePatterns { t.Logf("jmp %x", pattern.Offset) - code := x64.Jump8(nil, pattern.Offset) + code := x86.Jump8(nil, pattern.Offset) assert.DeepEqual(t, code, pattern.Code) } } func TestConditionalJump(t *testing.T) { - assert.DeepEqual(t, x64.Jump8IfEqual(nil, 1), []byte{0x74, 0x01}) - assert.DeepEqual(t, x64.Jump8IfNotEqual(nil, 1), []byte{0x75, 0x01}) - assert.DeepEqual(t, x64.Jump8IfLess(nil, 1), []byte{0x7C, 0x01}) - assert.DeepEqual(t, x64.Jump8IfGreaterOrEqual(nil, 1), []byte{0x7D, 0x01}) - assert.DeepEqual(t, x64.Jump8IfLessOrEqual(nil, 1), []byte{0x7E, 0x01}) - assert.DeepEqual(t, x64.Jump8IfGreater(nil, 1), []byte{0x7F, 0x01}) + assert.DeepEqual(t, x86.Jump8IfEqual(nil, 1), []byte{0x74, 0x01}) + assert.DeepEqual(t, x86.Jump8IfNotEqual(nil, 1), []byte{0x75, 0x01}) + assert.DeepEqual(t, x86.Jump8IfLess(nil, 1), []byte{0x7C, 0x01}) + assert.DeepEqual(t, x86.Jump8IfGreaterOrEqual(nil, 1), []byte{0x7D, 0x01}) + assert.DeepEqual(t, x86.Jump8IfLessOrEqual(nil, 1), []byte{0x7E, 0x01}) + assert.DeepEqual(t, x86.Jump8IfGreater(nil, 1), []byte{0x7F, 0x01}) } diff --git a/src/x64/Load.go b/src/x86/Load.go similarity index 95% rename from src/x64/Load.go rename to src/x86/Load.go index eb5ac51..ae32daa 100644 --- a/src/x64/Load.go +++ b/src/x86/Load.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Load_test.go b/src/x86/Load_test.go new file mode 100644 index 0000000..2633e09 --- /dev/null +++ b/src/x86/Load_test.go @@ -0,0 +1,157 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestLoadRegister(t *testing.T) { + usagePatterns := []struct { + Destination cpu.Register + Source cpu.Register + Offset byte + Length byte + Code []byte + }{ + // No offset + {x86.RAX, x86.R15, 0, 8, []byte{0x49, 0x8B, 0x07}}, + {x86.RAX, x86.R15, 0, 4, []byte{0x41, 0x8B, 0x07}}, + {x86.RAX, x86.R15, 0, 2, []byte{0x66, 0x41, 0x8B, 0x07}}, + {x86.RAX, x86.R15, 0, 1, []byte{0x41, 0x8A, 0x07}}, + {x86.RCX, x86.R14, 0, 8, []byte{0x49, 0x8B, 0x0E}}, + {x86.RCX, x86.R14, 0, 4, []byte{0x41, 0x8B, 0x0E}}, + {x86.RCX, x86.R14, 0, 2, []byte{0x66, 0x41, 0x8B, 0x0E}}, + {x86.RCX, x86.R14, 0, 1, []byte{0x41, 0x8A, 0x0E}}, + {x86.RDX, x86.R13, 0, 8, []byte{0x49, 0x8B, 0x55, 0x00}}, + {x86.RDX, x86.R13, 0, 4, []byte{0x41, 0x8B, 0x55, 0x00}}, + {x86.RDX, x86.R13, 0, 2, []byte{0x66, 0x41, 0x8B, 0x55, 0x00}}, + {x86.RDX, x86.R13, 0, 1, []byte{0x41, 0x8A, 0x55, 0x00}}, + {x86.RBX, x86.R12, 0, 8, []byte{0x49, 0x8B, 0x1C, 0x24}}, + {x86.RBX, x86.R12, 0, 4, []byte{0x41, 0x8B, 0x1C, 0x24}}, + {x86.RBX, x86.R12, 0, 2, []byte{0x66, 0x41, 0x8B, 0x1C, 0x24}}, + {x86.RBX, x86.R12, 0, 1, []byte{0x41, 0x8A, 0x1C, 0x24}}, + {x86.RSP, x86.R11, 0, 8, []byte{0x49, 0x8B, 0x23}}, + {x86.RSP, x86.R11, 0, 4, []byte{0x41, 0x8B, 0x23}}, + {x86.RSP, x86.R11, 0, 2, []byte{0x66, 0x41, 0x8B, 0x23}}, + {x86.RSP, x86.R11, 0, 1, []byte{0x41, 0x8A, 0x23}}, + {x86.RBP, x86.R10, 0, 8, []byte{0x49, 0x8B, 0x2A}}, + {x86.RBP, x86.R10, 0, 4, []byte{0x41, 0x8B, 0x2A}}, + {x86.RBP, x86.R10, 0, 2, []byte{0x66, 0x41, 0x8B, 0x2A}}, + {x86.RBP, x86.R10, 0, 1, []byte{0x41, 0x8A, 0x2A}}, + {x86.RSI, x86.R9, 0, 8, []byte{0x49, 0x8B, 0x31}}, + {x86.RSI, x86.R9, 0, 4, []byte{0x41, 0x8B, 0x31}}, + {x86.RSI, x86.R9, 0, 2, []byte{0x66, 0x41, 0x8B, 0x31}}, + {x86.RSI, x86.R9, 0, 1, []byte{0x41, 0x8A, 0x31}}, + {x86.RDI, x86.R8, 0, 8, []byte{0x49, 0x8B, 0x38}}, + {x86.RDI, x86.R8, 0, 4, []byte{0x41, 0x8B, 0x38}}, + {x86.RDI, x86.R8, 0, 2, []byte{0x66, 0x41, 0x8B, 0x38}}, + {x86.RDI, x86.R8, 0, 1, []byte{0x41, 0x8A, 0x38}}, + {x86.R8, x86.RDI, 0, 8, []byte{0x4C, 0x8B, 0x07}}, + {x86.R8, x86.RDI, 0, 4, []byte{0x44, 0x8B, 0x07}}, + {x86.R8, x86.RDI, 0, 2, []byte{0x66, 0x44, 0x8B, 0x07}}, + {x86.R8, x86.RDI, 0, 1, []byte{0x44, 0x8A, 0x07}}, + {x86.R9, x86.RSI, 0, 8, []byte{0x4C, 0x8B, 0x0E}}, + {x86.R9, x86.RSI, 0, 4, []byte{0x44, 0x8B, 0x0E}}, + {x86.R9, x86.RSI, 0, 2, []byte{0x66, 0x44, 0x8B, 0x0E}}, + {x86.R9, x86.RSI, 0, 1, []byte{0x44, 0x8A, 0x0E}}, + {x86.R10, x86.RBP, 0, 8, []byte{0x4C, 0x8B, 0x55, 0x00}}, + {x86.R10, x86.RBP, 0, 4, []byte{0x44, 0x8B, 0x55, 0x00}}, + {x86.R10, x86.RBP, 0, 2, []byte{0x66, 0x44, 0x8B, 0x55, 0x00}}, + {x86.R10, x86.RBP, 0, 1, []byte{0x44, 0x8A, 0x55, 0x00}}, + {x86.R11, x86.RSP, 0, 8, []byte{0x4C, 0x8B, 0x1C, 0x24}}, + {x86.R11, x86.RSP, 0, 4, []byte{0x44, 0x8B, 0x1C, 0x24}}, + {x86.R11, x86.RSP, 0, 2, []byte{0x66, 0x44, 0x8B, 0x1C, 0x24}}, + {x86.R11, x86.RSP, 0, 1, []byte{0x44, 0x8A, 0x1C, 0x24}}, + {x86.R12, x86.RBX, 0, 8, []byte{0x4C, 0x8B, 0x23}}, + {x86.R12, x86.RBX, 0, 4, []byte{0x44, 0x8B, 0x23}}, + {x86.R12, x86.RBX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x23}}, + {x86.R12, x86.RBX, 0, 1, []byte{0x44, 0x8A, 0x23}}, + {x86.R13, x86.RDX, 0, 8, []byte{0x4C, 0x8B, 0x2A}}, + {x86.R13, x86.RDX, 0, 4, []byte{0x44, 0x8B, 0x2A}}, + {x86.R13, x86.RDX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x2A}}, + {x86.R13, x86.RDX, 0, 1, []byte{0x44, 0x8A, 0x2A}}, + {x86.R14, x86.RCX, 0, 8, []byte{0x4C, 0x8B, 0x31}}, + {x86.R14, x86.RCX, 0, 4, []byte{0x44, 0x8B, 0x31}}, + {x86.R14, x86.RCX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x31}}, + {x86.R14, x86.RCX, 0, 1, []byte{0x44, 0x8A, 0x31}}, + {x86.R15, x86.RAX, 0, 8, []byte{0x4C, 0x8B, 0x38}}, + {x86.R15, x86.RAX, 0, 4, []byte{0x44, 0x8B, 0x38}}, + {x86.R15, x86.RAX, 0, 2, []byte{0x66, 0x44, 0x8B, 0x38}}, + {x86.R15, x86.RAX, 0, 1, []byte{0x44, 0x8A, 0x38}}, + + // Offset of 1 + {x86.RAX, x86.R15, 1, 8, []byte{0x49, 0x8B, 0x47, 0x01}}, + {x86.RAX, x86.R15, 1, 4, []byte{0x41, 0x8B, 0x47, 0x01}}, + {x86.RAX, x86.R15, 1, 2, []byte{0x66, 0x41, 0x8B, 0x47, 0x01}}, + {x86.RAX, x86.R15, 1, 1, []byte{0x41, 0x8A, 0x47, 0x01}}, + {x86.RCX, x86.R14, 1, 8, []byte{0x49, 0x8B, 0x4E, 0x01}}, + {x86.RCX, x86.R14, 1, 4, []byte{0x41, 0x8B, 0x4E, 0x01}}, + {x86.RCX, x86.R14, 1, 2, []byte{0x66, 0x41, 0x8B, 0x4E, 0x01}}, + {x86.RCX, x86.R14, 1, 1, []byte{0x41, 0x8A, 0x4E, 0x01}}, + {x86.RDX, x86.R13, 1, 8, []byte{0x49, 0x8B, 0x55, 0x01}}, + {x86.RDX, x86.R13, 1, 4, []byte{0x41, 0x8B, 0x55, 0x01}}, + {x86.RDX, x86.R13, 1, 2, []byte{0x66, 0x41, 0x8B, 0x55, 0x01}}, + {x86.RDX, x86.R13, 1, 1, []byte{0x41, 0x8A, 0x55, 0x01}}, + {x86.RBX, x86.R12, 1, 8, []byte{0x49, 0x8B, 0x5C, 0x24, 0x01}}, + {x86.RBX, x86.R12, 1, 4, []byte{0x41, 0x8B, 0x5C, 0x24, 0x01}}, + {x86.RBX, x86.R12, 1, 2, []byte{0x66, 0x41, 0x8B, 0x5C, 0x24, 0x01}}, + {x86.RBX, x86.R12, 1, 1, []byte{0x41, 0x8A, 0x5C, 0x24, 0x01}}, + {x86.RSP, x86.R11, 1, 8, []byte{0x49, 0x8B, 0x63, 0x01}}, + {x86.RSP, x86.R11, 1, 4, []byte{0x41, 0x8B, 0x63, 0x01}}, + {x86.RSP, x86.R11, 1, 2, []byte{0x66, 0x41, 0x8B, 0x63, 0x01}}, + {x86.RSP, x86.R11, 1, 1, []byte{0x41, 0x8A, 0x63, 0x01}}, + {x86.RBP, x86.R10, 1, 8, []byte{0x49, 0x8B, 0x6A, 0x01}}, + {x86.RBP, x86.R10, 1, 4, []byte{0x41, 0x8B, 0x6A, 0x01}}, + {x86.RBP, x86.R10, 1, 2, []byte{0x66, 0x41, 0x8B, 0x6A, 0x01}}, + {x86.RBP, x86.R10, 1, 1, []byte{0x41, 0x8A, 0x6A, 0x01}}, + {x86.RSI, x86.R9, 1, 8, []byte{0x49, 0x8B, 0x71, 0x01}}, + {x86.RSI, x86.R9, 1, 4, []byte{0x41, 0x8B, 0x71, 0x01}}, + {x86.RSI, x86.R9, 1, 2, []byte{0x66, 0x41, 0x8B, 0x71, 0x01}}, + {x86.RSI, x86.R9, 1, 1, []byte{0x41, 0x8A, 0x71, 0x01}}, + {x86.RDI, x86.R8, 1, 8, []byte{0x49, 0x8B, 0x78, 0x01}}, + {x86.RDI, x86.R8, 1, 4, []byte{0x41, 0x8B, 0x78, 0x01}}, + {x86.RDI, x86.R8, 1, 2, []byte{0x66, 0x41, 0x8B, 0x78, 0x01}}, + {x86.RDI, x86.R8, 1, 1, []byte{0x41, 0x8A, 0x78, 0x01}}, + {x86.R8, x86.RDI, 1, 8, []byte{0x4C, 0x8B, 0x47, 0x01}}, + {x86.R8, x86.RDI, 1, 4, []byte{0x44, 0x8B, 0x47, 0x01}}, + {x86.R8, x86.RDI, 1, 2, []byte{0x66, 0x44, 0x8B, 0x47, 0x01}}, + {x86.R8, x86.RDI, 1, 1, []byte{0x44, 0x8A, 0x47, 0x01}}, + {x86.R9, x86.RSI, 1, 8, []byte{0x4C, 0x8B, 0x4E, 0x01}}, + {x86.R9, x86.RSI, 1, 4, []byte{0x44, 0x8B, 0x4E, 0x01}}, + {x86.R9, x86.RSI, 1, 2, []byte{0x66, 0x44, 0x8B, 0x4E, 0x01}}, + {x86.R9, x86.RSI, 1, 1, []byte{0x44, 0x8A, 0x4E, 0x01}}, + {x86.R10, x86.RBP, 1, 8, []byte{0x4C, 0x8B, 0x55, 0x01}}, + {x86.R10, x86.RBP, 1, 4, []byte{0x44, 0x8B, 0x55, 0x01}}, + {x86.R10, x86.RBP, 1, 2, []byte{0x66, 0x44, 0x8B, 0x55, 0x01}}, + {x86.R10, x86.RBP, 1, 1, []byte{0x44, 0x8A, 0x55, 0x01}}, + {x86.R11, x86.RSP, 1, 8, []byte{0x4C, 0x8B, 0x5C, 0x24, 0x01}}, + {x86.R11, x86.RSP, 1, 4, []byte{0x44, 0x8B, 0x5C, 0x24, 0x01}}, + {x86.R11, x86.RSP, 1, 2, []byte{0x66, 0x44, 0x8B, 0x5C, 0x24, 0x01}}, + {x86.R11, x86.RSP, 1, 1, []byte{0x44, 0x8A, 0x5C, 0x24, 0x01}}, + {x86.R12, x86.RBX, 1, 8, []byte{0x4C, 0x8B, 0x63, 0x01}}, + {x86.R12, x86.RBX, 1, 4, []byte{0x44, 0x8B, 0x63, 0x01}}, + {x86.R12, x86.RBX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x63, 0x01}}, + {x86.R12, x86.RBX, 1, 1, []byte{0x44, 0x8A, 0x63, 0x01}}, + {x86.R13, x86.RDX, 1, 8, []byte{0x4C, 0x8B, 0x6A, 0x01}}, + {x86.R13, x86.RDX, 1, 4, []byte{0x44, 0x8B, 0x6A, 0x01}}, + {x86.R13, x86.RDX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x6A, 0x01}}, + {x86.R13, x86.RDX, 1, 1, []byte{0x44, 0x8A, 0x6A, 0x01}}, + {x86.R14, x86.RCX, 1, 8, []byte{0x4C, 0x8B, 0x71, 0x01}}, + {x86.R14, x86.RCX, 1, 4, []byte{0x44, 0x8B, 0x71, 0x01}}, + {x86.R14, x86.RCX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x71, 0x01}}, + {x86.R14, x86.RCX, 1, 1, []byte{0x44, 0x8A, 0x71, 0x01}}, + {x86.R15, x86.RAX, 1, 8, []byte{0x4C, 0x8B, 0x78, 0x01}}, + {x86.R15, x86.RAX, 1, 4, []byte{0x44, 0x8B, 0x78, 0x01}}, + {x86.R15, x86.RAX, 1, 2, []byte{0x66, 0x44, 0x8B, 0x78, 0x01}}, + {x86.R15, x86.RAX, 1, 1, []byte{0x44, 0x8A, 0x78, 0x01}}, + } + + for _, pattern := range usagePatterns { + t.Logf("load %dB %s, [%s+%d]", pattern.Length, pattern.Destination, pattern.Source, pattern.Offset) + code := x86.LoadRegister(nil, pattern.Destination, pattern.Offset, pattern.Length, pattern.Source) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/ModRM.go b/src/x86/ModRM.go similarity index 97% rename from src/x64/ModRM.go rename to src/x86/ModRM.go index bb6852e..1ab4393 100644 --- a/src/x64/ModRM.go +++ b/src/x86/ModRM.go @@ -1,4 +1,4 @@ -package x64 +package x86 // AddressMode encodes the addressing mode. type AddressMode = byte diff --git a/src/x64/ModRM_test.go b/src/x86/ModRM_test.go similarity index 90% rename from src/x64/ModRM_test.go rename to src/x86/ModRM_test.go index 09f72eb..fd1151a 100644 --- a/src/x64/ModRM_test.go +++ b/src/x86/ModRM_test.go @@ -1,9 +1,9 @@ -package x64_test +package x86_test import ( "testing" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" "git.akyoto.dev/go/assert" ) @@ -28,7 +28,7 @@ func TestModRM(t *testing.T) { } for _, test := range testData { - modRM := x64.ModRM(test.mod, test.reg, test.rm) + modRM := x86.ModRM(test.mod, test.reg, test.rm) assert.Equal(t, modRM, test.expected) } } diff --git a/src/x64/Move.go b/src/x86/Move.go similarity index 99% rename from src/x64/Move.go rename to src/x86/Move.go index 48edc79..2c38ca5 100644 --- a/src/x64/Move.go +++ b/src/x86/Move.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "encoding/binary" diff --git a/src/x86/Move_test.go b/src/x86/Move_test.go new file mode 100644 index 0000000..5c074ae --- /dev/null +++ b/src/x86/Move_test.go @@ -0,0 +1,108 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestMoveRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + // 32 bits + {x86.RAX, 0x7FFFFFFF, []byte{0xB8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0xB9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0xBA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0xBB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0xBC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0xBD, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0xBE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0xBF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x41, 0xB8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x41, 0xB9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x41, 0xBA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x41, 0xBB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x41, 0xBC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x41, 0xBD, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x41, 0xBE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x41, 0xBF, 0xFF, 0xFF, 0xFF, 0x7F}}, + + // 64 bits + {x86.RAX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xB8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xB9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBA, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFFFFFFFFFF, []byte{0x48, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xB8, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xB9, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBA, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBC, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFFFFFFFFFF, []byte{0x49, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + + // Negative numbers + {x86.RAX, -1, []byte{0x48, 0xC7, 0xC0, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RCX, -1, []byte{0x48, 0xC7, 0xC1, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RDX, -1, []byte{0x48, 0xC7, 0xC2, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RBX, -1, []byte{0x48, 0xC7, 0xC3, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RSP, -1, []byte{0x48, 0xC7, 0xC4, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RBP, -1, []byte{0x48, 0xC7, 0xC5, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RSI, -1, []byte{0x48, 0xC7, 0xC6, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.RDI, -1, []byte{0x48, 0xC7, 0xC7, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R8, -1, []byte{0x49, 0xC7, 0xC0, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R9, -1, []byte{0x49, 0xC7, 0xC1, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R10, -1, []byte{0x49, 0xC7, 0xC2, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R11, -1, []byte{0x49, 0xC7, 0xC3, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R12, -1, []byte{0x49, 0xC7, 0xC4, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R13, -1, []byte{0x49, 0xC7, 0xC5, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R14, -1, []byte{0x49, 0xC7, 0xC6, 0xFF, 0xFF, 0xFF, 0xFF}}, + {x86.R15, -1, []byte{0x49, 0xC7, 0xC7, 0xFF, 0xFF, 0xFF, 0xFF}}, + } + + for _, pattern := range usagePatterns { + t.Logf("mov %s, %x", pattern.Register, pattern.Number) + code := x86.MoveRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestMoveRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x89, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x89, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x89, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x89, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x89, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x89, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x89, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x89, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x89, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x89, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x89, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x89, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x89, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x89, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x89, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x89, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("mov %s, %s", pattern.Left, pattern.Right) + code := x86.MoveRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Mul.go b/src/x86/Mul.go similarity index 97% rename from src/x64/Mul.go rename to src/x86/Mul.go index 1d11da3..f2b4dbb 100644 --- a/src/x64/Mul.go +++ b/src/x86/Mul.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Mul_test.go b/src/x86/Mul_test.go new file mode 100644 index 0000000..46618fe --- /dev/null +++ b/src/x86/Mul_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestMulRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x6B, 0xC0, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x6B, 0xC9, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x6B, 0xD2, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x6B, 0xDB, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x6B, 0xE4, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x6B, 0xED, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x6B, 0xF6, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x6B, 0xFF, 0x01}}, + {x86.R8, 1, []byte{0x4D, 0x6B, 0xC0, 0x01}}, + {x86.R9, 1, []byte{0x4D, 0x6B, 0xC9, 0x01}}, + {x86.R10, 1, []byte{0x4D, 0x6B, 0xD2, 0x01}}, + {x86.R11, 1, []byte{0x4D, 0x6B, 0xDB, 0x01}}, + {x86.R12, 1, []byte{0x4D, 0x6B, 0xE4, 0x01}}, + {x86.R13, 1, []byte{0x4D, 0x6B, 0xED, 0x01}}, + {x86.R14, 1, []byte{0x4D, 0x6B, 0xF6, 0x01}}, + {x86.R15, 1, []byte{0x4D, 0x6B, 0xFF, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xD2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x69, 0xDB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x69, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x69, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x69, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x69, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xC0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xD2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xDB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xE4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x4D, 0x69, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("mul %s, %x", pattern.Register, pattern.Number) + code := x86.MulRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestMulRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x49, 0x0F, 0xAF, 0xC7}}, + {x86.RCX, x86.R14, []byte{0x49, 0x0F, 0xAF, 0xCE}}, + {x86.RDX, x86.R13, []byte{0x49, 0x0F, 0xAF, 0xD5}}, + {x86.RBX, x86.R12, []byte{0x49, 0x0F, 0xAF, 0xDC}}, + {x86.RSP, x86.R11, []byte{0x49, 0x0F, 0xAF, 0xE3}}, + {x86.RBP, x86.R10, []byte{0x49, 0x0F, 0xAF, 0xEA}}, + {x86.RSI, x86.R9, []byte{0x49, 0x0F, 0xAF, 0xF1}}, + {x86.RDI, x86.R8, []byte{0x49, 0x0F, 0xAF, 0xF8}}, + {x86.R8, x86.RDI, []byte{0x4C, 0x0F, 0xAF, 0xC7}}, + {x86.R9, x86.RSI, []byte{0x4C, 0x0F, 0xAF, 0xCE}}, + {x86.R10, x86.RBP, []byte{0x4C, 0x0F, 0xAF, 0xD5}}, + {x86.R11, x86.RSP, []byte{0x4C, 0x0F, 0xAF, 0xDC}}, + {x86.R12, x86.RBX, []byte{0x4C, 0x0F, 0xAF, 0xE3}}, + {x86.R13, x86.RDX, []byte{0x4C, 0x0F, 0xAF, 0xEA}}, + {x86.R14, x86.RCX, []byte{0x4C, 0x0F, 0xAF, 0xF1}}, + {x86.R15, x86.RAX, []byte{0x4C, 0x0F, 0xAF, 0xF8}}, + } + + for _, pattern := range usagePatterns { + t.Logf("mul %s, %s", pattern.Left, pattern.Right) + code := x86.MulRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Negate.go b/src/x86/Negate.go similarity index 94% rename from src/x64/Negate.go rename to src/x86/Negate.go index 479c143..141d105 100644 --- a/src/x64/Negate.go +++ b/src/x86/Negate.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Negate_test.go b/src/x86/Negate_test.go new file mode 100644 index 0000000..0fcaeea --- /dev/null +++ b/src/x86/Negate_test.go @@ -0,0 +1,39 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestNegateRegister(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Code []byte + }{ + {x86.RAX, []byte{0x48, 0xF7, 0xD8}}, + {x86.RCX, []byte{0x48, 0xF7, 0xD9}}, + {x86.RDX, []byte{0x48, 0xF7, 0xDA}}, + {x86.RBX, []byte{0x48, 0xF7, 0xDB}}, + {x86.RSP, []byte{0x48, 0xF7, 0xDC}}, + {x86.RBP, []byte{0x48, 0xF7, 0xDD}}, + {x86.RSI, []byte{0x48, 0xF7, 0xDE}}, + {x86.RDI, []byte{0x48, 0xF7, 0xDF}}, + {x86.R8, []byte{0x49, 0xF7, 0xD8}}, + {x86.R9, []byte{0x49, 0xF7, 0xD9}}, + {x86.R10, []byte{0x49, 0xF7, 0xDA}}, + {x86.R11, []byte{0x49, 0xF7, 0xDB}}, + {x86.R12, []byte{0x49, 0xF7, 0xDC}}, + {x86.R13, []byte{0x49, 0xF7, 0xDD}}, + {x86.R14, []byte{0x49, 0xF7, 0xDE}}, + {x86.R15, []byte{0x49, 0xF7, 0xDF}}, + } + + for _, pattern := range usagePatterns { + t.Logf("neg %s", pattern.Register) + code := x86.NegateRegister(nil, pattern.Register) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Or.go b/src/x86/Or.go similarity index 97% rename from src/x64/Or.go rename to src/x86/Or.go index fa5b440..9ed61c4 100644 --- a/src/x64/Or.go +++ b/src/x86/Or.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Or_test.go b/src/x86/Or_test.go new file mode 100644 index 0000000..f26e4e7 --- /dev/null +++ b/src/x86/Or_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestOrRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x83, 0xC8, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x83, 0xC9, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x83, 0xCA, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x83, 0xCB, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x83, 0xCC, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x83, 0xCD, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x83, 0xCE, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x83, 0xCF, 0x01}}, + {x86.R8, 1, []byte{0x49, 0x83, 0xC8, 0x01}}, + {x86.R9, 1, []byte{0x49, 0x83, 0xC9, 0x01}}, + {x86.R10, 1, []byte{0x49, 0x83, 0xCA, 0x01}}, + {x86.R11, 1, []byte{0x49, 0x83, 0xCB, 0x01}}, + {x86.R12, 1, []byte{0x49, 0x83, 0xCC, 0x01}}, + {x86.R13, 1, []byte{0x49, 0x83, 0xCD, 0x01}}, + {x86.R14, 1, []byte{0x49, 0x83, 0xCE, 0x01}}, + {x86.R15, 1, []byte{0x49, 0x83, 0xCF, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCD, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xCF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xC9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCD, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xCF, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("or %s, %x", pattern.Register, pattern.Number) + code := x86.OrRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestOrRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x09, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x09, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x09, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x09, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x09, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x09, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x09, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x09, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x09, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x09, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x09, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x09, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x09, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x09, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x09, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x09, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("or %s, %s", pattern.Left, pattern.Right) + code := x86.OrRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Pop.go b/src/x86/Pop.go similarity index 96% rename from src/x64/Pop.go rename to src/x86/Pop.go index b97182f..5b23719 100644 --- a/src/x64/Pop.go +++ b/src/x86/Pop.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Pop_test.go b/src/x86/Pop_test.go new file mode 100644 index 0000000..268dcfc --- /dev/null +++ b/src/x86/Pop_test.go @@ -0,0 +1,39 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestPopRegister(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Code []byte + }{ + {x86.RAX, []byte{0x58}}, + {x86.RCX, []byte{0x59}}, + {x86.RDX, []byte{0x5A}}, + {x86.RBX, []byte{0x5B}}, + {x86.RSP, []byte{0x5C}}, + {x86.RBP, []byte{0x5D}}, + {x86.RSI, []byte{0x5E}}, + {x86.RDI, []byte{0x5F}}, + {x86.R8, []byte{0x41, 0x58}}, + {x86.R9, []byte{0x41, 0x59}}, + {x86.R10, []byte{0x41, 0x5A}}, + {x86.R11, []byte{0x41, 0x5B}}, + {x86.R12, []byte{0x41, 0x5C}}, + {x86.R13, []byte{0x41, 0x5D}}, + {x86.R14, []byte{0x41, 0x5E}}, + {x86.R15, []byte{0x41, 0x5F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("pop %s", pattern.Register) + code := x86.PopRegister(nil, pattern.Register) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Push.go b/src/x86/Push.go similarity index 96% rename from src/x64/Push.go rename to src/x86/Push.go index bdae334..b9c82b0 100644 --- a/src/x64/Push.go +++ b/src/x86/Push.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Push_test.go b/src/x86/Push_test.go new file mode 100644 index 0000000..29cedac --- /dev/null +++ b/src/x86/Push_test.go @@ -0,0 +1,39 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestPushRegister(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Code []byte + }{ + {x86.RAX, []byte{0x50}}, + {x86.RCX, []byte{0x51}}, + {x86.RDX, []byte{0x52}}, + {x86.RBX, []byte{0x53}}, + {x86.RSP, []byte{0x54}}, + {x86.RBP, []byte{0x55}}, + {x86.RSI, []byte{0x56}}, + {x86.RDI, []byte{0x57}}, + {x86.R8, []byte{0x41, 0x50}}, + {x86.R9, []byte{0x41, 0x51}}, + {x86.R10, []byte{0x41, 0x52}}, + {x86.R11, []byte{0x41, 0x53}}, + {x86.R12, []byte{0x41, 0x54}}, + {x86.R13, []byte{0x41, 0x55}}, + {x86.R14, []byte{0x41, 0x56}}, + {x86.R15, []byte{0x41, 0x57}}, + } + + for _, pattern := range usagePatterns { + t.Logf("push %s", pattern.Register) + code := x86.PushRegister(nil, pattern.Register) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/REX.go b/src/x86/REX.go similarity index 93% rename from src/x64/REX.go rename to src/x86/REX.go index 36d7e58..554140e 100644 --- a/src/x64/REX.go +++ b/src/x86/REX.go @@ -1,4 +1,4 @@ -package x64 +package x86 // REX is used to generate a REX prefix. // w, r, x and b can only be set to either 0 or 1. diff --git a/src/x64/REX_test.go b/src/x86/REX_test.go similarity index 87% rename from src/x64/REX_test.go rename to src/x86/REX_test.go index c754354..73f2290 100644 --- a/src/x64/REX_test.go +++ b/src/x86/REX_test.go @@ -1,9 +1,9 @@ -package x64_test +package x86_test import ( "testing" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" "git.akyoto.dev/go/assert" ) @@ -28,7 +28,7 @@ func TestREX(t *testing.T) { } for _, test := range testData { - rex := x64.REX(test.w, test.r, test.x, test.b) + rex := x86.REX(test.w, test.r, test.x, test.b) assert.Equal(t, rex, test.expected) } } diff --git a/src/x64/Registers.go b/src/x86/Registers.go similarity index 98% rename from src/x64/Registers.go rename to src/x86/Registers.go index 57d4e8b..0ed7c5f 100644 --- a/src/x64/Registers.go +++ b/src/x86/Registers.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Registers_test.go b/src/x86/Registers_test.go new file mode 100644 index 0000000..54eb4d2 --- /dev/null +++ b/src/x86/Registers_test.go @@ -0,0 +1,12 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestRegisters(t *testing.T) { + assert.NotContains(t, x86.GeneralRegisters, x86.RSP) +} diff --git a/src/x64/Return.go b/src/x86/Return.go similarity index 94% rename from src/x64/Return.go rename to src/x86/Return.go index a64d39f..4ac2301 100644 --- a/src/x64/Return.go +++ b/src/x86/Return.go @@ -1,4 +1,4 @@ -package x64 +package x86 // Return transfers program control to a return address located on the top of the stack. // The address is usually placed on the stack by a Call instruction. diff --git a/src/x64/SIB.go b/src/x86/SIB.go similarity index 97% rename from src/x64/SIB.go rename to src/x86/SIB.go index 438024d..4b75714 100644 --- a/src/x64/SIB.go +++ b/src/x86/SIB.go @@ -1,4 +1,4 @@ -package x64 +package x86 // ScaleFactor encodes the scale factor. type ScaleFactor = byte diff --git a/src/x64/SIB_test.go b/src/x86/SIB_test.go similarity index 89% rename from src/x64/SIB_test.go rename to src/x86/SIB_test.go index 911b133..c6dcb4b 100644 --- a/src/x64/SIB_test.go +++ b/src/x86/SIB_test.go @@ -1,9 +1,9 @@ -package x64_test +package x86_test import ( "testing" - "git.akyoto.dev/cli/q/src/x64" + "git.akyoto.dev/cli/q/src/x86" "git.akyoto.dev/go/assert" ) @@ -28,7 +28,7 @@ func TestSIB(t *testing.T) { } for _, test := range testData { - sib := x64.SIB(test.scale, test.index, test.base) + sib := x86.SIB(test.scale, test.index, test.base) assert.Equal(t, sib, test.expected) } } diff --git a/src/x64/Shift.go b/src/x86/Shift.go similarity index 97% rename from src/x64/Shift.go rename to src/x86/Shift.go index 6fa2251..428e7aa 100644 --- a/src/x64/Shift.go +++ b/src/x86/Shift.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Shift_test.go b/src/x86/Shift_test.go new file mode 100644 index 0000000..2e80741 --- /dev/null +++ b/src/x86/Shift_test.go @@ -0,0 +1,71 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestShiftLeftNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0xC1, 0xE0, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0xC1, 0xE1, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0xC1, 0xE2, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0xC1, 0xE3, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0xC1, 0xE4, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0xC1, 0xE5, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0xC1, 0xE6, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0xC1, 0xE7, 0x01}}, + {x86.R8, 1, []byte{0x49, 0xC1, 0xE0, 0x01}}, + {x86.R9, 1, []byte{0x49, 0xC1, 0xE1, 0x01}}, + {x86.R10, 1, []byte{0x49, 0xC1, 0xE2, 0x01}}, + {x86.R11, 1, []byte{0x49, 0xC1, 0xE3, 0x01}}, + {x86.R12, 1, []byte{0x49, 0xC1, 0xE4, 0x01}}, + {x86.R13, 1, []byte{0x49, 0xC1, 0xE5, 0x01}}, + {x86.R14, 1, []byte{0x49, 0xC1, 0xE6, 0x01}}, + {x86.R15, 1, []byte{0x49, 0xC1, 0xE7, 0x01}}, + } + + for _, pattern := range usagePatterns { + t.Logf("shl %s, %x", pattern.Register, pattern.Number) + code := x86.ShiftLeftNumber(nil, pattern.Register, byte(pattern.Number)) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestShiftRightSignedNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0xC1, 0xF8, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0xC1, 0xF9, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0xC1, 0xFA, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0xC1, 0xFB, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0xC1, 0xFC, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0xC1, 0xFD, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0xC1, 0xFE, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0xC1, 0xFF, 0x01}}, + {x86.R8, 1, []byte{0x49, 0xC1, 0xF8, 0x01}}, + {x86.R9, 1, []byte{0x49, 0xC1, 0xF9, 0x01}}, + {x86.R10, 1, []byte{0x49, 0xC1, 0xFA, 0x01}}, + {x86.R11, 1, []byte{0x49, 0xC1, 0xFB, 0x01}}, + {x86.R12, 1, []byte{0x49, 0xC1, 0xFC, 0x01}}, + {x86.R13, 1, []byte{0x49, 0xC1, 0xFD, 0x01}}, + {x86.R14, 1, []byte{0x49, 0xC1, 0xFE, 0x01}}, + {x86.R15, 1, []byte{0x49, 0xC1, 0xFF, 0x01}}, + } + + for _, pattern := range usagePatterns { + t.Logf("sar %s, %x", pattern.Register, pattern.Number) + code := x86.ShiftRightSignedNumber(nil, pattern.Register, byte(pattern.Number)) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Store.go b/src/x86/Store.go similarity index 98% rename from src/x64/Store.go rename to src/x86/Store.go index 01bdfc6..0bf06e0 100644 --- a/src/x64/Store.go +++ b/src/x86/Store.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "encoding/binary" diff --git a/src/x64/StoreDynamic.go b/src/x86/StoreDynamic.go similarity index 98% rename from src/x64/StoreDynamic.go rename to src/x86/StoreDynamic.go index 3a214c9..2cedf7e 100644 --- a/src/x64/StoreDynamic.go +++ b/src/x86/StoreDynamic.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "encoding/binary" diff --git a/src/x86/StoreDynamic_test.go b/src/x86/StoreDynamic_test.go new file mode 100644 index 0000000..f5a957f --- /dev/null +++ b/src/x86/StoreDynamic_test.go @@ -0,0 +1,171 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestStoreDynamicNumber(t *testing.T) { + usagePatterns := []struct { + RegisterTo cpu.Register + Offset cpu.Register + Length byte + Number int + Code []byte + }{ + {x86.RAX, x86.R15, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RAX, x86.R15, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RAX, x86.R15, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x38, 0x7F, 0x00}}, + {x86.RAX, x86.R15, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x38, 0x7F}}, + {x86.RCX, x86.R14, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RCX, x86.R14, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RCX, x86.R14, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x31, 0x7F, 0x00}}, + {x86.RCX, x86.R14, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x31, 0x7F}}, + {x86.RDX, x86.R13, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDX, x86.R13, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDX, x86.R13, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x2A, 0x7F, 0x00}}, + {x86.RDX, x86.R13, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x2A, 0x7F}}, + {x86.RBX, x86.R12, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x23, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBX, x86.R12, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x23, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBX, x86.R12, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x23, 0x7F, 0x00}}, + {x86.RBX, x86.R12, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x23, 0x7F}}, + {x86.RSP, x86.R11, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSP, x86.R11, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSP, x86.R11, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00}}, + {x86.RSP, x86.R11, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x1C, 0x7F}}, + {x86.RBP, x86.R10, 8, 0x7F, []byte{0x4A, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBP, x86.R10, 4, 0x7F, []byte{0x42, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBP, x86.R10, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00}}, + {x86.RBP, x86.R10, 1, 0x7F, []byte{0x42, 0xC6, 0x44, 0x15, 0x00, 0x7F}}, + {x86.RSI, x86.R9, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSI, x86.R9, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSI, x86.R9, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x0E, 0x7F, 0x00}}, + {x86.RSI, x86.R9, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x0E, 0x7F}}, + {x86.RDI, x86.R8, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDI, x86.R8, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDI, x86.R8, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x07, 0x7F, 0x00}}, + {x86.RDI, x86.R8, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x07, 0x7F}}, + {x86.R8, x86.RDI, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R8, x86.RDI, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x38, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R8, x86.RDI, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x38, 0x7F, 0x00}}, + {x86.R8, x86.RDI, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x38, 0x7F}}, + {x86.R9, x86.RSI, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R9, x86.RSI, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x31, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R9, x86.RSI, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x31, 0x7F, 0x00}}, + {x86.R9, x86.RSI, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x31, 0x7F}}, + {x86.R10, x86.RBP, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R10, x86.RBP, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x2A, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R10, x86.RBP, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x2A, 0x7F, 0x00}}, + {x86.R10, x86.RBP, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x2A, 0x7F}}, + {x86.R11, x86.RSP, 8, 0x7F, []byte{0x4A, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R11, x86.RSP, 4, 0x7F, []byte{0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R11, x86.RSP, 2, 0x7F, []byte{0x66, 0x42, 0xC7, 0x04, 0x1C, 0x7F, 0x00}}, + {x86.R11, x86.RSP, 1, 0x7F, []byte{0x42, 0xC6, 0x04, 0x1C, 0x7F}}, + {x86.R12, x86.RBX, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R12, x86.RBX, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x1C, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R12, x86.RBX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x1C, 0x7F, 0x00}}, + {x86.R12, x86.RBX, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x1C, 0x7F}}, + {x86.R13, x86.RDX, 8, 0x7F, []byte{0x49, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R13, x86.RDX, 4, 0x7F, []byte{0x41, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R13, x86.RDX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x44, 0x15, 0x00, 0x7F, 0x00}}, + {x86.R13, x86.RDX, 1, 0x7F, []byte{0x41, 0xC6, 0x44, 0x15, 0x00, 0x7F}}, + {x86.R14, x86.RCX, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R14, x86.RCX, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x0E, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R14, x86.RCX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x0E, 0x7F, 0x00}}, + {x86.R14, x86.RCX, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x0E, 0x7F}}, + {x86.R15, x86.RAX, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R15, x86.RAX, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R15, x86.RAX, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x07, 0x7F, 0x00}}, + {x86.R15, x86.RAX, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x07, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("store %dB [%s+%s], %d", pattern.Length, pattern.RegisterTo, pattern.Offset, pattern.Number) + code := x86.StoreDynamicNumber(nil, pattern.RegisterTo, pattern.Offset, pattern.Length, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestStoreDynamicRegister(t *testing.T) { + usagePatterns := []struct { + RegisterTo cpu.Register + Offset cpu.Register + Length byte + RegisterFrom cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, 8, x86.R15, []byte{0x4E, 0x89, 0x3C, 0x38}}, + {x86.RAX, x86.R15, 4, x86.R15, []byte{0x46, 0x89, 0x3C, 0x38}}, + {x86.RAX, x86.R15, 2, x86.R15, []byte{0x66, 0x46, 0x89, 0x3C, 0x38}}, + {x86.RAX, x86.R15, 1, x86.R15, []byte{0x46, 0x88, 0x3C, 0x38}}, + {x86.RCX, x86.R14, 8, x86.R14, []byte{0x4E, 0x89, 0x34, 0x31}}, + {x86.RCX, x86.R14, 4, x86.R14, []byte{0x46, 0x89, 0x34, 0x31}}, + {x86.RCX, x86.R14, 2, x86.R14, []byte{0x66, 0x46, 0x89, 0x34, 0x31}}, + {x86.RCX, x86.R14, 1, x86.R14, []byte{0x46, 0x88, 0x34, 0x31}}, + {x86.RDX, x86.R13, 8, x86.R13, []byte{0x4E, 0x89, 0x2C, 0x2A}}, + {x86.RDX, x86.R13, 4, x86.R13, []byte{0x46, 0x89, 0x2C, 0x2A}}, + {x86.RDX, x86.R13, 2, x86.R13, []byte{0x66, 0x46, 0x89, 0x2C, 0x2A}}, + {x86.RDX, x86.R13, 1, x86.R13, []byte{0x46, 0x88, 0x2C, 0x2A}}, + {x86.RBX, x86.R12, 8, x86.R12, []byte{0x4E, 0x89, 0x24, 0x23}}, + {x86.RBX, x86.R12, 4, x86.R12, []byte{0x46, 0x89, 0x24, 0x23}}, + {x86.RBX, x86.R12, 2, x86.R12, []byte{0x66, 0x46, 0x89, 0x24, 0x23}}, + {x86.RBX, x86.R12, 1, x86.R12, []byte{0x46, 0x88, 0x24, 0x23}}, + {x86.RSP, x86.R11, 8, x86.R11, []byte{0x4E, 0x89, 0x1C, 0x1C}}, + {x86.RSP, x86.R11, 4, x86.R11, []byte{0x46, 0x89, 0x1C, 0x1C}}, + {x86.RSP, x86.R11, 2, x86.R11, []byte{0x66, 0x46, 0x89, 0x1C, 0x1C}}, + {x86.RSP, x86.R11, 1, x86.R11, []byte{0x46, 0x88, 0x1C, 0x1C}}, + {x86.RBP, x86.R10, 8, x86.R10, []byte{0x4E, 0x89, 0x54, 0x15, 0x00}}, + {x86.RBP, x86.R10, 4, x86.R10, []byte{0x46, 0x89, 0x54, 0x15, 0x00}}, + {x86.RBP, x86.R10, 2, x86.R10, []byte{0x66, 0x46, 0x89, 0x54, 0x15, 0x00}}, + {x86.RBP, x86.R10, 1, x86.R10, []byte{0x46, 0x88, 0x54, 0x15, 0x00}}, + {x86.RSI, x86.R9, 8, x86.R9, []byte{0x4E, 0x89, 0x0C, 0x0E}}, + {x86.RSI, x86.R9, 4, x86.R9, []byte{0x46, 0x89, 0x0C, 0x0E}}, + {x86.RSI, x86.R9, 2, x86.R9, []byte{0x66, 0x46, 0x89, 0x0C, 0x0E}}, + {x86.RSI, x86.R9, 1, x86.R9, []byte{0x46, 0x88, 0x0C, 0x0E}}, + {x86.RDI, x86.R8, 8, x86.R8, []byte{0x4E, 0x89, 0x04, 0x07}}, + {x86.RDI, x86.R8, 4, x86.R8, []byte{0x46, 0x89, 0x04, 0x07}}, + {x86.RDI, x86.R8, 2, x86.R8, []byte{0x66, 0x46, 0x89, 0x04, 0x07}}, + {x86.RDI, x86.R8, 1, x86.R8, []byte{0x46, 0x88, 0x04, 0x07}}, + {x86.R8, x86.RDI, 8, x86.RDI, []byte{0x49, 0x89, 0x3C, 0x38}}, + {x86.R8, x86.RDI, 4, x86.RDI, []byte{0x41, 0x89, 0x3C, 0x38}}, + {x86.R8, x86.RDI, 2, x86.RDI, []byte{0x66, 0x41, 0x89, 0x3C, 0x38}}, + {x86.R8, x86.RDI, 1, x86.RDI, []byte{0x41, 0x88, 0x3C, 0x38}}, + {x86.R9, x86.RSI, 8, x86.RSI, []byte{0x49, 0x89, 0x34, 0x31}}, + {x86.R9, x86.RSI, 4, x86.RSI, []byte{0x41, 0x89, 0x34, 0x31}}, + {x86.R9, x86.RSI, 2, x86.RSI, []byte{0x66, 0x41, 0x89, 0x34, 0x31}}, + {x86.R9, x86.RSI, 1, x86.RSI, []byte{0x41, 0x88, 0x34, 0x31}}, + {x86.R10, x86.RBP, 8, x86.RBP, []byte{0x49, 0x89, 0x2C, 0x2A}}, + {x86.R10, x86.RBP, 4, x86.RBP, []byte{0x41, 0x89, 0x2C, 0x2A}}, + {x86.R10, x86.RBP, 2, x86.RBP, []byte{0x66, 0x41, 0x89, 0x2C, 0x2A}}, + {x86.R10, x86.RBP, 1, x86.RBP, []byte{0x41, 0x88, 0x2C, 0x2A}}, + {x86.R11, x86.RSP, 8, x86.RSP, []byte{0x4A, 0x89, 0x24, 0x1C}}, + {x86.R11, x86.RSP, 4, x86.RSP, []byte{0x42, 0x89, 0x24, 0x1C}}, + {x86.R11, x86.RSP, 2, x86.RSP, []byte{0x66, 0x42, 0x89, 0x24, 0x1C}}, + {x86.R11, x86.RSP, 1, x86.RSP, []byte{0x42, 0x88, 0x24, 0x1C}}, + {x86.R12, x86.RBX, 8, x86.RBX, []byte{0x49, 0x89, 0x1C, 0x1C}}, + {x86.R12, x86.RBX, 4, x86.RBX, []byte{0x41, 0x89, 0x1C, 0x1C}}, + {x86.R12, x86.RBX, 2, x86.RBX, []byte{0x66, 0x41, 0x89, 0x1C, 0x1C}}, + {x86.R12, x86.RBX, 1, x86.RBX, []byte{0x41, 0x88, 0x1C, 0x1C}}, + {x86.R13, x86.RDX, 8, x86.RDX, []byte{0x49, 0x89, 0x54, 0x15, 0x00}}, + {x86.R13, x86.RDX, 4, x86.RDX, []byte{0x41, 0x89, 0x54, 0x15, 0x00}}, + {x86.R13, x86.RDX, 2, x86.RDX, []byte{0x66, 0x41, 0x89, 0x54, 0x15, 0x00}}, + {x86.R13, x86.RDX, 1, x86.RDX, []byte{0x41, 0x88, 0x54, 0x15, 0x00}}, + {x86.R14, x86.RCX, 8, x86.RCX, []byte{0x49, 0x89, 0x0C, 0x0E}}, + {x86.R14, x86.RCX, 4, x86.RCX, []byte{0x41, 0x89, 0x0C, 0x0E}}, + {x86.R14, x86.RCX, 2, x86.RCX, []byte{0x66, 0x41, 0x89, 0x0C, 0x0E}}, + {x86.R14, x86.RCX, 1, x86.RCX, []byte{0x41, 0x88, 0x0C, 0x0E}}, + {x86.R15, x86.RAX, 8, x86.RAX, []byte{0x49, 0x89, 0x04, 0x07}}, + {x86.R15, x86.RAX, 4, x86.RAX, []byte{0x41, 0x89, 0x04, 0x07}}, + {x86.R15, x86.RAX, 2, x86.RAX, []byte{0x66, 0x41, 0x89, 0x04, 0x07}}, + {x86.R15, x86.RAX, 1, x86.RAX, []byte{0x41, 0x88, 0x04, 0x07}}, + } + + for _, pattern := range usagePatterns { + t.Logf("store %dB [%s+%s], %s", pattern.Length, pattern.RegisterTo, pattern.Offset, pattern.RegisterFrom) + code := x86.StoreDynamicRegister(nil, pattern.RegisterTo, pattern.Offset, pattern.Length, pattern.RegisterFrom) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x86/Store_test.go b/src/x86/Store_test.go new file mode 100644 index 0000000..e9e1e26 --- /dev/null +++ b/src/x86/Store_test.go @@ -0,0 +1,305 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestStoreNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Offset byte + Length byte + Number int + Code []byte + }{ + // No offset + {x86.RAX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RAX, 0, 4, 0x7F, []byte{0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RAX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x00, 0x7F, 0x00}}, + {x86.RAX, 0, 1, 0x7F, []byte{0xC6, 0x00, 0x7F}}, + {x86.RCX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RCX, 0, 4, 0x7F, []byte{0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RCX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x01, 0x7F, 0x00}}, + {x86.RCX, 0, 1, 0x7F, []byte{0xC6, 0x01, 0x7F}}, + {x86.RDX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDX, 0, 4, 0x7F, []byte{0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x02, 0x7F, 0x00}}, + {x86.RDX, 0, 1, 0x7F, []byte{0xC6, 0x02, 0x7F}}, + {x86.RBX, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBX, 0, 4, 0x7F, []byte{0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBX, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x03, 0x7F, 0x00}}, + {x86.RBX, 0, 1, 0x7F, []byte{0xC6, 0x03, 0x7F}}, + {x86.RSP, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSP, 0, 4, 0x7F, []byte{0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSP, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x04, 0x24, 0x7F, 0x00}}, + {x86.RSP, 0, 1, 0x7F, []byte{0xC6, 0x04, 0x24, 0x7F}}, + {x86.RBP, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBP, 0, 4, 0x7F, []byte{0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBP, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x45, 0x00, 0x7F, 0x00}}, + {x86.RBP, 0, 1, 0x7F, []byte{0xC6, 0x45, 0x00, 0x7F}}, + {x86.RSI, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSI, 0, 4, 0x7F, []byte{0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSI, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x06, 0x7F, 0x00}}, + {x86.RSI, 0, 1, 0x7F, []byte{0xC6, 0x06, 0x7F}}, + {x86.RDI, 0, 8, 0x7F, []byte{0x48, 0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDI, 0, 4, 0x7F, []byte{0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDI, 0, 2, 0x7F, []byte{0x66, 0xC7, 0x07, 0x7F, 0x00}}, + {x86.RDI, 0, 1, 0x7F, []byte{0xC6, 0x07, 0x7F}}, + {x86.R8, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R8, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R8, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x00, 0x7F, 0x00}}, + {x86.R8, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x00, 0x7F}}, + {x86.R9, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R9, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R9, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x01, 0x7F, 0x00}}, + {x86.R9, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x01, 0x7F}}, + {x86.R10, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R10, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x02, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R10, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x02, 0x7F, 0x00}}, + {x86.R10, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x02, 0x7F}}, + {x86.R11, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R11, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x03, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R11, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x03, 0x7F, 0x00}}, + {x86.R11, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x03, 0x7F}}, + {x86.R12, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R12, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x04, 0x24, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R12, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x04, 0x24, 0x7F, 0x00}}, + {x86.R12, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x04, 0x24, 0x7F}}, + {x86.R13, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R13, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x45, 0x00, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R13, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x45, 0x00, 0x7F, 0x00}}, + {x86.R13, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x45, 0x00, 0x7F}}, + {x86.R14, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R14, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x06, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R14, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x06, 0x7F, 0x00}}, + {x86.R14, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x06, 0x7F}}, + {x86.R15, 0, 8, 0x7F, []byte{0x49, 0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R15, 0, 4, 0x7F, []byte{0x41, 0xC7, 0x07, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R15, 0, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x07, 0x7F, 0x00}}, + {x86.R15, 0, 1, 0x7F, []byte{0x41, 0xC6, 0x07, 0x7F}}, + + // Offset of 1 + {x86.RAX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RAX, 1, 4, 0x7F, []byte{0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RAX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x40, 0x01, 0x7F, 0x00}}, + {x86.RAX, 1, 1, 0x7F, []byte{0xC6, 0x40, 0x01, 0x7F}}, + {x86.RCX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RCX, 1, 4, 0x7F, []byte{0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RCX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x41, 0x01, 0x7F, 0x00}}, + {x86.RCX, 1, 1, 0x7F, []byte{0xC6, 0x41, 0x01, 0x7F}}, + {x86.RDX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDX, 1, 4, 0x7F, []byte{0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x42, 0x01, 0x7F, 0x00}}, + {x86.RDX, 1, 1, 0x7F, []byte{0xC6, 0x42, 0x01, 0x7F}}, + {x86.RBX, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBX, 1, 4, 0x7F, []byte{0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBX, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x43, 0x01, 0x7F, 0x00}}, + {x86.RBX, 1, 1, 0x7F, []byte{0xC6, 0x43, 0x01, 0x7F}}, + {x86.RSP, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSP, 1, 4, 0x7F, []byte{0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSP, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00}}, + {x86.RSP, 1, 1, 0x7F, []byte{0xC6, 0x44, 0x24, 0x01, 0x7F}}, + {x86.RBP, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBP, 1, 4, 0x7F, []byte{0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RBP, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x45, 0x01, 0x7F, 0x00}}, + {x86.RBP, 1, 1, 0x7F, []byte{0xC6, 0x45, 0x01, 0x7F}}, + {x86.RSI, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSI, 1, 4, 0x7F, []byte{0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RSI, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x46, 0x01, 0x7F, 0x00}}, + {x86.RSI, 1, 1, 0x7F, []byte{0xC6, 0x46, 0x01, 0x7F}}, + {x86.RDI, 1, 8, 0x7F, []byte{0x48, 0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDI, 1, 4, 0x7F, []byte{0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.RDI, 1, 2, 0x7F, []byte{0x66, 0xC7, 0x47, 0x01, 0x7F, 0x00}}, + {x86.RDI, 1, 1, 0x7F, []byte{0xC6, 0x47, 0x01, 0x7F}}, + {x86.R8, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R8, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x40, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R8, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x40, 0x01, 0x7F, 0x00}}, + {x86.R8, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x40, 0x01, 0x7F}}, + {x86.R9, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R9, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x41, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R9, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x41, 0x01, 0x7F, 0x00}}, + {x86.R9, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x41, 0x01, 0x7F}}, + {x86.R10, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R10, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x42, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R10, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x42, 0x01, 0x7F, 0x00}}, + {x86.R10, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x42, 0x01, 0x7F}}, + {x86.R11, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R11, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x43, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R11, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x43, 0x01, 0x7F, 0x00}}, + {x86.R11, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x43, 0x01, 0x7F}}, + {x86.R12, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R12, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R12, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x44, 0x24, 0x01, 0x7F, 0x00}}, + {x86.R12, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x44, 0x24, 0x01, 0x7F}}, + {x86.R13, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R13, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x45, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R13, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x45, 0x01, 0x7F, 0x00}}, + {x86.R13, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x45, 0x01, 0x7F}}, + {x86.R14, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R14, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x46, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R14, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x46, 0x01, 0x7F, 0x00}}, + {x86.R14, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x46, 0x01, 0x7F}}, + {x86.R15, 1, 8, 0x7F, []byte{0x49, 0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R15, 1, 4, 0x7F, []byte{0x41, 0xC7, 0x47, 0x01, 0x7F, 0x00, 0x00, 0x00}}, + {x86.R15, 1, 2, 0x7F, []byte{0x66, 0x41, 0xC7, 0x47, 0x01, 0x7F, 0x00}}, + {x86.R15, 1, 1, 0x7F, []byte{0x41, 0xC6, 0x47, 0x01, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("store %dB [%s+%d], %d", pattern.Length, pattern.Register, pattern.Offset, pattern.Number) + code := x86.StoreNumber(nil, pattern.Register, pattern.Offset, pattern.Length, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestStoreRegister(t *testing.T) { + usagePatterns := []struct { + RegisterTo cpu.Register + Offset byte + Length byte + RegisterFrom cpu.Register + Code []byte + }{ + // No offset + {x86.RAX, 0, 8, x86.R15, []byte{0x4C, 0x89, 0x38}}, + {x86.RAX, 0, 4, x86.R15, []byte{0x44, 0x89, 0x38}}, + {x86.RAX, 0, 2, x86.R15, []byte{0x66, 0x44, 0x89, 0x38}}, + {x86.RAX, 0, 1, x86.R15, []byte{0x44, 0x88, 0x38}}, + {x86.RCX, 0, 8, x86.R14, []byte{0x4C, 0x89, 0x31}}, + {x86.RCX, 0, 4, x86.R14, []byte{0x44, 0x89, 0x31}}, + {x86.RCX, 0, 2, x86.R14, []byte{0x66, 0x44, 0x89, 0x31}}, + {x86.RCX, 0, 1, x86.R14, []byte{0x44, 0x88, 0x31}}, + {x86.RDX, 0, 8, x86.R13, []byte{0x4C, 0x89, 0x2A}}, + {x86.RDX, 0, 4, x86.R13, []byte{0x44, 0x89, 0x2A}}, + {x86.RDX, 0, 2, x86.R13, []byte{0x66, 0x44, 0x89, 0x2A}}, + {x86.RDX, 0, 1, x86.R13, []byte{0x44, 0x88, 0x2A}}, + {x86.RBX, 0, 8, x86.R12, []byte{0x4C, 0x89, 0x23}}, + {x86.RBX, 0, 4, x86.R12, []byte{0x44, 0x89, 0x23}}, + {x86.RBX, 0, 2, x86.R12, []byte{0x66, 0x44, 0x89, 0x23}}, + {x86.RBX, 0, 1, x86.R12, []byte{0x44, 0x88, 0x23}}, + {x86.RSP, 0, 8, x86.R11, []byte{0x4C, 0x89, 0x1C, 0x24}}, + {x86.RSP, 0, 4, x86.R11, []byte{0x44, 0x89, 0x1C, 0x24}}, + {x86.RSP, 0, 2, x86.R11, []byte{0x66, 0x44, 0x89, 0x1C, 0x24}}, + {x86.RSP, 0, 1, x86.R11, []byte{0x44, 0x88, 0x1C, 0x24}}, + {x86.RBP, 0, 8, x86.R10, []byte{0x4C, 0x89, 0x55, 0x00}}, + {x86.RBP, 0, 4, x86.R10, []byte{0x44, 0x89, 0x55, 0x00}}, + {x86.RBP, 0, 2, x86.R10, []byte{0x66, 0x44, 0x89, 0x55, 0x00}}, + {x86.RBP, 0, 1, x86.R10, []byte{0x44, 0x88, 0x55, 0x00}}, + {x86.RSI, 0, 8, x86.R9, []byte{0x4C, 0x89, 0x0E}}, + {x86.RSI, 0, 4, x86.R9, []byte{0x44, 0x89, 0x0E}}, + {x86.RSI, 0, 2, x86.R9, []byte{0x66, 0x44, 0x89, 0x0E}}, + {x86.RSI, 0, 1, x86.R9, []byte{0x44, 0x88, 0x0E}}, + {x86.RDI, 0, 8, x86.R8, []byte{0x4C, 0x89, 0x07}}, + {x86.RDI, 0, 4, x86.R8, []byte{0x44, 0x89, 0x07}}, + {x86.RDI, 0, 2, x86.R8, []byte{0x66, 0x44, 0x89, 0x07}}, + {x86.RDI, 0, 1, x86.R8, []byte{0x44, 0x88, 0x07}}, + {x86.R8, 0, 8, x86.RDI, []byte{0x49, 0x89, 0x38}}, + {x86.R8, 0, 4, x86.RDI, []byte{0x41, 0x89, 0x38}}, + {x86.R8, 0, 2, x86.RDI, []byte{0x66, 0x41, 0x89, 0x38}}, + {x86.R8, 0, 1, x86.RDI, []byte{0x41, 0x88, 0x38}}, + {x86.R9, 0, 8, x86.RSI, []byte{0x49, 0x89, 0x31}}, + {x86.R9, 0, 4, x86.RSI, []byte{0x41, 0x89, 0x31}}, + {x86.R9, 0, 2, x86.RSI, []byte{0x66, 0x41, 0x89, 0x31}}, + {x86.R9, 0, 1, x86.RSI, []byte{0x41, 0x88, 0x31}}, + {x86.R10, 0, 8, x86.RBP, []byte{0x49, 0x89, 0x2A}}, + {x86.R10, 0, 4, x86.RBP, []byte{0x41, 0x89, 0x2A}}, + {x86.R10, 0, 2, x86.RBP, []byte{0x66, 0x41, 0x89, 0x2A}}, + {x86.R10, 0, 1, x86.RBP, []byte{0x41, 0x88, 0x2A}}, + {x86.R11, 0, 8, x86.RSP, []byte{0x49, 0x89, 0x23}}, + {x86.R11, 0, 4, x86.RSP, []byte{0x41, 0x89, 0x23}}, + {x86.R11, 0, 2, x86.RSP, []byte{0x66, 0x41, 0x89, 0x23}}, + {x86.R11, 0, 1, x86.RSP, []byte{0x41, 0x88, 0x23}}, + {x86.R12, 0, 8, x86.RBX, []byte{0x49, 0x89, 0x1C, 0x24}}, + {x86.R12, 0, 4, x86.RBX, []byte{0x41, 0x89, 0x1C, 0x24}}, + {x86.R12, 0, 2, x86.RBX, []byte{0x66, 0x41, 0x89, 0x1C, 0x24}}, + {x86.R12, 0, 1, x86.RBX, []byte{0x41, 0x88, 0x1C, 0x24}}, + {x86.R13, 0, 8, x86.RDX, []byte{0x49, 0x89, 0x55, 0x00}}, + {x86.R13, 0, 4, x86.RDX, []byte{0x41, 0x89, 0x55, 0x00}}, + {x86.R13, 0, 2, x86.RDX, []byte{0x66, 0x41, 0x89, 0x55, 0x00}}, + {x86.R13, 0, 1, x86.RDX, []byte{0x41, 0x88, 0x55, 0x00}}, + {x86.R14, 0, 8, x86.RCX, []byte{0x49, 0x89, 0x0E}}, + {x86.R14, 0, 4, x86.RCX, []byte{0x41, 0x89, 0x0E}}, + {x86.R14, 0, 2, x86.RCX, []byte{0x66, 0x41, 0x89, 0x0E}}, + {x86.R14, 0, 1, x86.RCX, []byte{0x41, 0x88, 0x0E}}, + {x86.R15, 0, 8, x86.RAX, []byte{0x49, 0x89, 0x07}}, + {x86.R15, 0, 4, x86.RAX, []byte{0x41, 0x89, 0x07}}, + {x86.R15, 0, 2, x86.RAX, []byte{0x66, 0x41, 0x89, 0x07}}, + {x86.R15, 0, 1, x86.RAX, []byte{0x41, 0x88, 0x07}}, + + // Offset of 1 + {x86.RAX, 1, 8, x86.R15, []byte{0x4C, 0x89, 0x78, 0x01}}, + {x86.RAX, 1, 4, x86.R15, []byte{0x44, 0x89, 0x78, 0x01}}, + {x86.RAX, 1, 2, x86.R15, []byte{0x66, 0x44, 0x89, 0x78, 0x01}}, + {x86.RAX, 1, 1, x86.R15, []byte{0x44, 0x88, 0x78, 0x01}}, + {x86.RCX, 1, 8, x86.R14, []byte{0x4C, 0x89, 0x71, 0x01}}, + {x86.RCX, 1, 4, x86.R14, []byte{0x44, 0x89, 0x71, 0x01}}, + {x86.RCX, 1, 2, x86.R14, []byte{0x66, 0x44, 0x89, 0x71, 0x01}}, + {x86.RCX, 1, 1, x86.R14, []byte{0x44, 0x88, 0x71, 0x01}}, + {x86.RDX, 1, 8, x86.R13, []byte{0x4C, 0x89, 0x6A, 0x01}}, + {x86.RDX, 1, 4, x86.R13, []byte{0x44, 0x89, 0x6A, 0x01}}, + {x86.RDX, 1, 2, x86.R13, []byte{0x66, 0x44, 0x89, 0x6A, 0x01}}, + {x86.RDX, 1, 1, x86.R13, []byte{0x44, 0x88, 0x6A, 0x01}}, + {x86.RBX, 1, 8, x86.R12, []byte{0x4C, 0x89, 0x63, 0x01}}, + {x86.RBX, 1, 4, x86.R12, []byte{0x44, 0x89, 0x63, 0x01}}, + {x86.RBX, 1, 2, x86.R12, []byte{0x66, 0x44, 0x89, 0x63, 0x01}}, + {x86.RBX, 1, 1, x86.R12, []byte{0x44, 0x88, 0x63, 0x01}}, + {x86.RSP, 1, 8, x86.R11, []byte{0x4C, 0x89, 0x5C, 0x24, 0x01}}, + {x86.RSP, 1, 4, x86.R11, []byte{0x44, 0x89, 0x5C, 0x24, 0x01}}, + {x86.RSP, 1, 2, x86.R11, []byte{0x66, 0x44, 0x89, 0x5C, 0x24, 0x01}}, + {x86.RSP, 1, 1, x86.R11, []byte{0x44, 0x88, 0x5C, 0x24, 0x01}}, + {x86.RBP, 1, 8, x86.R10, []byte{0x4C, 0x89, 0x55, 0x01}}, + {x86.RBP, 1, 4, x86.R10, []byte{0x44, 0x89, 0x55, 0x01}}, + {x86.RBP, 1, 2, x86.R10, []byte{0x66, 0x44, 0x89, 0x55, 0x01}}, + {x86.RBP, 1, 1, x86.R10, []byte{0x44, 0x88, 0x55, 0x01}}, + {x86.RSI, 1, 8, x86.R9, []byte{0x4C, 0x89, 0x4E, 0x01}}, + {x86.RSI, 1, 4, x86.R9, []byte{0x44, 0x89, 0x4E, 0x01}}, + {x86.RSI, 1, 2, x86.R9, []byte{0x66, 0x44, 0x89, 0x4E, 0x01}}, + {x86.RSI, 1, 1, x86.R9, []byte{0x44, 0x88, 0x4E, 0x01}}, + {x86.RDI, 1, 8, x86.R8, []byte{0x4C, 0x89, 0x47, 0x01}}, + {x86.RDI, 1, 4, x86.R8, []byte{0x44, 0x89, 0x47, 0x01}}, + {x86.RDI, 1, 2, x86.R8, []byte{0x66, 0x44, 0x89, 0x47, 0x01}}, + {x86.RDI, 1, 1, x86.R8, []byte{0x44, 0x88, 0x47, 0x01}}, + {x86.R8, 1, 8, x86.RDI, []byte{0x49, 0x89, 0x78, 0x01}}, + {x86.R8, 1, 4, x86.RDI, []byte{0x41, 0x89, 0x78, 0x01}}, + {x86.R8, 1, 2, x86.RDI, []byte{0x66, 0x41, 0x89, 0x78, 0x01}}, + {x86.R8, 1, 1, x86.RDI, []byte{0x41, 0x88, 0x78, 0x01}}, + {x86.R9, 1, 8, x86.RSI, []byte{0x49, 0x89, 0x71, 0x01}}, + {x86.R9, 1, 4, x86.RSI, []byte{0x41, 0x89, 0x71, 0x01}}, + {x86.R9, 1, 2, x86.RSI, []byte{0x66, 0x41, 0x89, 0x71, 0x01}}, + {x86.R9, 1, 1, x86.RSI, []byte{0x41, 0x88, 0x71, 0x01}}, + {x86.R10, 1, 8, x86.RBP, []byte{0x49, 0x89, 0x6A, 0x01}}, + {x86.R10, 1, 4, x86.RBP, []byte{0x41, 0x89, 0x6A, 0x01}}, + {x86.R10, 1, 2, x86.RBP, []byte{0x66, 0x41, 0x89, 0x6A, 0x01}}, + {x86.R10, 1, 1, x86.RBP, []byte{0x41, 0x88, 0x6A, 0x01}}, + {x86.R11, 1, 8, x86.RSP, []byte{0x49, 0x89, 0x63, 0x01}}, + {x86.R11, 1, 4, x86.RSP, []byte{0x41, 0x89, 0x63, 0x01}}, + {x86.R11, 1, 2, x86.RSP, []byte{0x66, 0x41, 0x89, 0x63, 0x01}}, + {x86.R11, 1, 1, x86.RSP, []byte{0x41, 0x88, 0x63, 0x01}}, + {x86.R12, 1, 8, x86.RBX, []byte{0x49, 0x89, 0x5C, 0x24, 0x01}}, + {x86.R12, 1, 4, x86.RBX, []byte{0x41, 0x89, 0x5C, 0x24, 0x01}}, + {x86.R12, 1, 2, x86.RBX, []byte{0x66, 0x41, 0x89, 0x5C, 0x24, 0x01}}, + {x86.R12, 1, 1, x86.RBX, []byte{0x41, 0x88, 0x5C, 0x24, 01}}, + {x86.R13, 1, 8, x86.RDX, []byte{0x49, 0x89, 0x55, 0x01}}, + {x86.R13, 1, 4, x86.RDX, []byte{0x41, 0x89, 0x55, 0x01}}, + {x86.R13, 1, 2, x86.RDX, []byte{0x66, 0x41, 0x89, 0x55, 0x01}}, + {x86.R13, 1, 1, x86.RDX, []byte{0x41, 0x88, 0x55, 0x01}}, + {x86.R14, 1, 8, x86.RCX, []byte{0x49, 0x89, 0x4E, 0x01}}, + {x86.R14, 1, 4, x86.RCX, []byte{0x41, 0x89, 0x4E, 0x01}}, + {x86.R14, 1, 2, x86.RCX, []byte{0x66, 0x41, 0x89, 0x4E, 0x01}}, + {x86.R14, 1, 1, x86.RCX, []byte{0x41, 0x88, 0x4E, 0x01}}, + {x86.R15, 1, 8, x86.RAX, []byte{0x49, 0x89, 0x47, 0x01}}, + {x86.R15, 1, 4, x86.RAX, []byte{0x41, 0x89, 0x47, 0x01}}, + {x86.R15, 1, 2, x86.RAX, []byte{0x66, 0x41, 0x89, 0x47, 0x01}}, + {x86.R15, 1, 1, x86.RAX, []byte{0x41, 0x88, 0x47, 0x01}}, + } + + for _, pattern := range usagePatterns { + t.Logf("store %dB [%s+%d], %s", pattern.Length, pattern.RegisterTo, pattern.Offset, pattern.RegisterFrom) + code := x86.StoreRegister(nil, pattern.RegisterTo, pattern.Offset, pattern.Length, pattern.RegisterFrom) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Sub.go b/src/x86/Sub.go similarity index 97% rename from src/x64/Sub.go rename to src/x86/Sub.go index 57332fd..40bb4ac 100644 --- a/src/x64/Sub.go +++ b/src/x86/Sub.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Sub_test.go b/src/x86/Sub_test.go new file mode 100644 index 0000000..7577b65 --- /dev/null +++ b/src/x86/Sub_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestSubRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x83, 0xE8, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x83, 0xE9, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x83, 0xEA, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x83, 0xEB, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x83, 0xEC, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x83, 0xED, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x83, 0xEE, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x83, 0xEF, 0x01}}, + {x86.R8, 1, []byte{0x49, 0x83, 0xE8, 0x01}}, + {x86.R9, 1, []byte{0x49, 0x83, 0xE9, 0x01}}, + {x86.R10, 1, []byte{0x49, 0x83, 0xEA, 0x01}}, + {x86.R11, 1, []byte{0x49, 0x83, 0xEB, 0x01}}, + {x86.R12, 1, []byte{0x49, 0x83, 0xEC, 0x01}}, + {x86.R13, 1, []byte{0x49, 0x83, 0xED, 0x01}}, + {x86.R14, 1, []byte{0x49, 0x83, 0xEE, 0x01}}, + {x86.R15, 1, []byte{0x49, 0x83, 0xEF, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xE9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xEF, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE8, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xE9, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEA, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEB, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEC, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xED, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEE, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xEF, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("sub %s, %x", pattern.Register, pattern.Number) + code := x86.SubRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestSubRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x29, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x29, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x29, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x29, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x29, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x29, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x29, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x29, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x29, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x29, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x29, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x29, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x29, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x29, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x29, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x29, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("sub %s, %s", pattern.Left, pattern.Right) + code := x86.SubRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/Syscall.go b/src/x86/Syscall.go similarity index 91% rename from src/x64/Syscall.go rename to src/x86/Syscall.go index 31e2b96..2e2005a 100644 --- a/src/x64/Syscall.go +++ b/src/x86/Syscall.go @@ -1,4 +1,4 @@ -package x64 +package x86 // Syscall is the primary way to communicate with the OS kernel. func Syscall(code []byte) []byte { diff --git a/src/x64/Xor.go b/src/x86/Xor.go similarity index 97% rename from src/x64/Xor.go rename to src/x86/Xor.go index c36a805..5c50ee6 100644 --- a/src/x64/Xor.go +++ b/src/x86/Xor.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/Xor_test.go b/src/x86/Xor_test.go new file mode 100644 index 0000000..dcf6afa --- /dev/null +++ b/src/x86/Xor_test.go @@ -0,0 +1,88 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/cpu" + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestXorRegisterNumber(t *testing.T) { + usagePatterns := []struct { + Register cpu.Register + Number int + Code []byte + }{ + {x86.RAX, 1, []byte{0x48, 0x83, 0xF0, 0x01}}, + {x86.RCX, 1, []byte{0x48, 0x83, 0xF1, 0x01}}, + {x86.RDX, 1, []byte{0x48, 0x83, 0xF2, 0x01}}, + {x86.RBX, 1, []byte{0x48, 0x83, 0xF3, 0x01}}, + {x86.RSP, 1, []byte{0x48, 0x83, 0xF4, 0x01}}, + {x86.RBP, 1, []byte{0x48, 0x83, 0xF5, 0x01}}, + {x86.RSI, 1, []byte{0x48, 0x83, 0xF6, 0x01}}, + {x86.RDI, 1, []byte{0x48, 0x83, 0xF7, 0x01}}, + {x86.R8, 1, []byte{0x49, 0x83, 0xF0, 0x01}}, + {x86.R9, 1, []byte{0x49, 0x83, 0xF1, 0x01}}, + {x86.R10, 1, []byte{0x49, 0x83, 0xF2, 0x01}}, + {x86.R11, 1, []byte{0x49, 0x83, 0xF3, 0x01}}, + {x86.R12, 1, []byte{0x49, 0x83, 0xF4, 0x01}}, + {x86.R13, 1, []byte{0x49, 0x83, 0xF5, 0x01}}, + {x86.R14, 1, []byte{0x49, 0x83, 0xF6, 0x01}}, + {x86.R15, 1, []byte{0x49, 0x83, 0xF7, 0x01}}, + + {x86.RAX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RCX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF1, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBX, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF3, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RBP, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF5, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RSI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.RDI, 0x7FFFFFFF, []byte{0x48, 0x81, 0xF7, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R8, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF0, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R9, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF1, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R10, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF2, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R11, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF3, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R12, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF4, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R13, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF5, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R14, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF6, 0xFF, 0xFF, 0xFF, 0x7F}}, + {x86.R15, 0x7FFFFFFF, []byte{0x49, 0x81, 0xF7, 0xFF, 0xFF, 0xFF, 0x7F}}, + } + + for _, pattern := range usagePatterns { + t.Logf("xor %s, %x", pattern.Register, pattern.Number) + code := x86.XorRegisterNumber(nil, pattern.Register, pattern.Number) + assert.DeepEqual(t, code, pattern.Code) + } +} + +func TestXorRegisterRegister(t *testing.T) { + usagePatterns := []struct { + Left cpu.Register + Right cpu.Register + Code []byte + }{ + {x86.RAX, x86.R15, []byte{0x4C, 0x31, 0xF8}}, + {x86.RCX, x86.R14, []byte{0x4C, 0x31, 0xF1}}, + {x86.RDX, x86.R13, []byte{0x4C, 0x31, 0xEA}}, + {x86.RBX, x86.R12, []byte{0x4C, 0x31, 0xE3}}, + {x86.RSP, x86.R11, []byte{0x4C, 0x31, 0xDC}}, + {x86.RBP, x86.R10, []byte{0x4C, 0x31, 0xD5}}, + {x86.RSI, x86.R9, []byte{0x4C, 0x31, 0xCE}}, + {x86.RDI, x86.R8, []byte{0x4C, 0x31, 0xC7}}, + {x86.R8, x86.RDI, []byte{0x49, 0x31, 0xF8}}, + {x86.R9, x86.RSI, []byte{0x49, 0x31, 0xF1}}, + {x86.R10, x86.RBP, []byte{0x49, 0x31, 0xEA}}, + {x86.R11, x86.RSP, []byte{0x49, 0x31, 0xE3}}, + {x86.R12, x86.RBX, []byte{0x49, 0x31, 0xDC}}, + {x86.R13, x86.RDX, []byte{0x49, 0x31, 0xD5}}, + {x86.R14, x86.RCX, []byte{0x49, 0x31, 0xCE}}, + {x86.R15, x86.RAX, []byte{0x49, 0x31, 0xC7}}, + } + + for _, pattern := range usagePatterns { + t.Logf("xor %s, %s", pattern.Left, pattern.Right) + code := x86.XorRegisterRegister(nil, pattern.Left, pattern.Right) + assert.DeepEqual(t, code, pattern.Code) + } +} diff --git a/src/x64/encode.go b/src/x86/encode.go similarity index 98% rename from src/x64/encode.go rename to src/x86/encode.go index 6e872b5..1306d52 100644 --- a/src/x64/encode.go +++ b/src/x86/encode.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x64/encodeNum.go b/src/x86/encodeNum.go similarity index 97% rename from src/x64/encodeNum.go rename to src/x86/encodeNum.go index c6db324..1611604 100644 --- a/src/x64/encodeNum.go +++ b/src/x86/encodeNum.go @@ -1,4 +1,4 @@ -package x64 +package x86 import ( "encoding/binary" diff --git a/src/x64/memoryAccess.go b/src/x86/memoryAccess.go similarity index 98% rename from src/x64/memoryAccess.go rename to src/x86/memoryAccess.go index c1c658c..b1dd605 100644 --- a/src/x64/memoryAccess.go +++ b/src/x86/memoryAccess.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x64/memoryAccessDynamic.go b/src/x86/memoryAccessDynamic.go similarity index 98% rename from src/x64/memoryAccessDynamic.go rename to src/x86/memoryAccessDynamic.go index c9e323c..d47988e 100644 --- a/src/x64/memoryAccessDynamic.go +++ b/src/x86/memoryAccessDynamic.go @@ -1,4 +1,4 @@ -package x64 +package x86 import "git.akyoto.dev/cli/q/src/cpu" diff --git a/src/x86/x64_test.go b/src/x86/x64_test.go new file mode 100644 index 0000000..f9e88e4 --- /dev/null +++ b/src/x86/x64_test.go @@ -0,0 +1,19 @@ +package x86_test + +import ( + "testing" + + "git.akyoto.dev/cli/q/src/x86" + "git.akyoto.dev/go/assert" +) + +func TestX64(t *testing.T) { + assert.DeepEqual(t, x86.AlignStack(nil), []byte{0x48, 0x83, 0xE4, 0xF0}) + assert.DeepEqual(t, x86.Call(nil, 1), []byte{0xE8, 0x01, 0x00, 0x00, 0x00}) + assert.DeepEqual(t, x86.CallAtAddress(nil, 1), []byte{0xFF, 0x15, 0x01, 0x00, 0x00, 0x00}) + assert.DeepEqual(t, x86.ExtendRAXToRDX(nil), []byte{0x48, 0x99}) + assert.DeepEqual(t, x86.MoveRegisterNumber(nil, 0, 1), []byte{0xB8, 0x01, 0x00, 0x00, 0x00}) + assert.DeepEqual(t, x86.MoveRegisterNumber(nil, 1, 1), []byte{0xB9, 0x01, 0x00, 0x00, 0x00}) + assert.DeepEqual(t, x86.Return(nil), []byte{0xC3}) + assert.DeepEqual(t, x86.Syscall(nil), []byte{0x0F, 0x05}) +}