Implemented addition
This commit is contained in:
parent
41f5dcbe62
commit
597cb9abed
@ -5,8 +5,11 @@ main() {
|
|||||||
hello() {
|
hello() {
|
||||||
write := 1
|
write := 1
|
||||||
stdout := 1
|
stdout := 1
|
||||||
address := 4194305
|
address := 4194304
|
||||||
length := 3
|
length := 0
|
||||||
|
|
||||||
|
address += 1
|
||||||
|
length += 3
|
||||||
|
|
||||||
loop {
|
loop {
|
||||||
syscall(write, stdout, address, length)
|
syscall(write, stdout, address, length)
|
||||||
|
@ -113,6 +113,16 @@ func (f *Function) CompileInstruction(line token.List) error {
|
|||||||
return f.CompileFunctionCall(expr)
|
return f.CompileFunctionCall(expr)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if expr.Token.Kind == token.Operator {
|
||||||
|
switch expr.Token.Text() {
|
||||||
|
case "+=":
|
||||||
|
name := expr.Children[0].Token.Text()
|
||||||
|
number, _ := strconv.Atoi(expr.Children[1].Token.Text())
|
||||||
|
f.Assembler.AddRegisterNumber(f.Variables[name].Register, uint64(number))
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return errors.New(&errors.InvalidInstruction{Instruction: expr.Token.Text()}, f.File, expr.Token.Position)
|
return errors.New(&errors.InvalidInstruction{Instruction: expr.Token.Text()}, f.File, expr.Token.Position)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
18
src/build/arch/x64/Add.go
Normal file
18
src/build/arch/x64/Add.go
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
package x64
|
||||||
|
|
||||||
|
import "git.akyoto.dev/cli/q/src/build/cpu"
|
||||||
|
|
||||||
|
// AddRegNum8 adds a byte to the given register.
|
||||||
|
func AddRegNum8(code []byte, destination cpu.Register, number uint8) []byte {
|
||||||
|
if destination >= 8 {
|
||||||
|
code = append(code, REX(0, 0, 0, 1))
|
||||||
|
destination -= 8
|
||||||
|
}
|
||||||
|
|
||||||
|
return append(
|
||||||
|
code,
|
||||||
|
0x83,
|
||||||
|
ModRM(0b11, 0b000, byte(destination)),
|
||||||
|
byte(number),
|
||||||
|
)
|
||||||
|
}
|
@ -27,21 +27,15 @@ func (a *Assembler) Finalize() ([]byte, []byte) {
|
|||||||
|
|
||||||
for _, x := range a.Instructions {
|
for _, x := range a.Instructions {
|
||||||
switch x.Mnemonic {
|
switch x.Mnemonic {
|
||||||
case MOVE:
|
case ADD:
|
||||||
switch operands := x.Data.(type) {
|
switch operands := x.Data.(type) {
|
||||||
case *RegisterNumber:
|
case *RegisterNumber:
|
||||||
code = x64.MoveRegNum32(code, operands.Register, uint32(operands.Number))
|
code = x64.AddRegNum8(code, operands.Register, uint8(operands.Number))
|
||||||
|
|
||||||
case *RegisterRegister:
|
case *RegisterRegister:
|
||||||
code = x64.MoveRegReg64(code, operands.Destination, operands.Source)
|
// code = x64.AddRegReg64(code, operands.Destination, operands.Source)
|
||||||
}
|
}
|
||||||
|
|
||||||
case RETURN:
|
|
||||||
code = x64.Return(code)
|
|
||||||
|
|
||||||
case SYSCALL:
|
|
||||||
code = x64.Syscall(code)
|
|
||||||
|
|
||||||
case CALL:
|
case CALL:
|
||||||
code = x64.Call(code, 0x00_00_00_00)
|
code = x64.Call(code, 0x00_00_00_00)
|
||||||
size := 4
|
size := 4
|
||||||
@ -77,6 +71,21 @@ func (a *Assembler) Finalize() ([]byte, []byte) {
|
|||||||
case LABEL:
|
case LABEL:
|
||||||
labels[x.Data.(*Label).Name] = Address(len(code))
|
labels[x.Data.(*Label).Name] = Address(len(code))
|
||||||
|
|
||||||
|
case MOVE:
|
||||||
|
switch operands := x.Data.(type) {
|
||||||
|
case *RegisterNumber:
|
||||||
|
code = x64.MoveRegNum32(code, operands.Register, uint32(operands.Number))
|
||||||
|
|
||||||
|
case *RegisterRegister:
|
||||||
|
code = x64.MoveRegReg64(code, operands.Destination, operands.Source)
|
||||||
|
}
|
||||||
|
|
||||||
|
case RETURN:
|
||||||
|
code = x64.Return(code)
|
||||||
|
|
||||||
|
case SYSCALL:
|
||||||
|
code = x64.Syscall(code)
|
||||||
|
|
||||||
default:
|
default:
|
||||||
panic("Unknown mnemonic: " + x.Mnemonic.String())
|
panic("Unknown mnemonic: " + x.Mnemonic.String())
|
||||||
}
|
}
|
||||||
|
@ -2,6 +2,17 @@ package asm
|
|||||||
|
|
||||||
import "git.akyoto.dev/cli/q/src/build/cpu"
|
import "git.akyoto.dev/cli/q/src/build/cpu"
|
||||||
|
|
||||||
|
// AddRegisterNumber adds a number to the given register.
|
||||||
|
func (a *Assembler) AddRegisterNumber(reg cpu.Register, number uint64) {
|
||||||
|
a.Instructions = append(a.Instructions, Instruction{
|
||||||
|
Mnemonic: ADD,
|
||||||
|
Data: &RegisterNumber{
|
||||||
|
Register: reg,
|
||||||
|
Number: number,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
// MoveRegisterNumber moves a number into the given register.
|
// MoveRegisterNumber moves a number into the given register.
|
||||||
func (a *Assembler) MoveRegisterNumber(reg cpu.Register, number uint64) {
|
func (a *Assembler) MoveRegisterNumber(reg cpu.Register, number uint64) {
|
||||||
a.Instructions = append(a.Instructions, Instruction{
|
a.Instructions = append(a.Instructions, Instruction{
|
||||||
|
@ -4,17 +4,30 @@ type Mnemonic uint8
|
|||||||
|
|
||||||
const (
|
const (
|
||||||
NONE Mnemonic = iota
|
NONE Mnemonic = iota
|
||||||
|
ADD
|
||||||
|
CALL
|
||||||
|
JUMP
|
||||||
|
LABEL
|
||||||
MOVE
|
MOVE
|
||||||
RETURN
|
RETURN
|
||||||
SYSCALL
|
SYSCALL
|
||||||
LABEL
|
|
||||||
CALL
|
|
||||||
JUMP
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// String returns a human readable version.
|
// String returns a human readable version.
|
||||||
func (m Mnemonic) String() string {
|
func (m Mnemonic) String() string {
|
||||||
switch m {
|
switch m {
|
||||||
|
case ADD:
|
||||||
|
return "add"
|
||||||
|
|
||||||
|
case CALL:
|
||||||
|
return "call"
|
||||||
|
|
||||||
|
case JUMP:
|
||||||
|
return "jump"
|
||||||
|
|
||||||
|
case LABEL:
|
||||||
|
return "label"
|
||||||
|
|
||||||
case MOVE:
|
case MOVE:
|
||||||
return "move"
|
return "move"
|
||||||
|
|
||||||
@ -23,15 +36,6 @@ func (m Mnemonic) String() string {
|
|||||||
|
|
||||||
case SYSCALL:
|
case SYSCALL:
|
||||||
return "syscall"
|
return "syscall"
|
||||||
|
|
||||||
case LABEL:
|
|
||||||
return "label"
|
|
||||||
|
|
||||||
case CALL:
|
|
||||||
return "call"
|
|
||||||
|
|
||||||
case JUMP:
|
|
||||||
return "jump"
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return "NONE"
|
return "NONE"
|
||||||
|
Loading…
Reference in New Issue
Block a user