1
0
mirror of https://github.com/catseye/SixtyPical.git synced 2024-11-25 23:49:17 +00:00

Implement compiling if, but we need relative addressing first.

This commit is contained in:
Chris Pressey 2015-10-17 16:34:02 +01:00
parent 479b484313
commit b6bb64528f
3 changed files with 67 additions and 10 deletions

View File

@ -7,12 +7,13 @@ from sixtypical.model import (
)
from sixtypical.emitter import Label, Byte
from sixtypical.gen6502 import (
Immediate, Absolute,
Immediate, Absolute, Relative,
LDA, LDX, LDY, STA, STX, STY,
CLC, SEC, ADC, SBC, ROL, ROR,
RTS, JSR,
INC, INX, INY, DEC, DEX, DEY,
CMP, CPX, CPY, AND, ORA, EOR,
BCC, BNE,
JMP, JSR, RTS,
)
@ -58,10 +59,8 @@ class Compiler(object):
def compile_block(self, block):
assert isinstance(block, Block)
label = self.emitter.make_label()
for instr in block.instrs:
self.compile_instr(instr)
return label
def compile_instr(self, instr):
assert isinstance(instr, Instr)
@ -168,6 +167,22 @@ class Compiler(object):
label = self.labels[instr.name]
self.emitter.emit(JSR(Absolute(label)))
elif opcode == 'if':
raise NotImplementedError
cls = {
'c': BCC,
'z': BNE,
}.get(src.name)
if cls is None:
raise UnsupportedOpcodeError(instr)
else_label = Label('else_label')
self.emitter.emit(cls(Relative(else_label)))
self.compile_block(instr.block1)
if instr.block2:
end_label = Label('end_label')
self.emitter.emit(JMP(Absolute(end_label)))
self.emitter.resolve_label(else_label)
self.compile_block(instr.block2)
self.emitter.resolve_label(end_label)
else:
self.emitter.resolve_label(else_label)
else:
raise NotImplementedError

View File

@ -8,6 +8,9 @@ class AddressingMode(object):
"""Size of the operand for the mode (not including the opcode)"""
raise NotImplementedError
def __repr__(self):
return "%s(%r)" % (self.__class__.__name__, self.value)
class Implied(AddressingMode):
def size(self):
@ -31,9 +34,6 @@ class Immediate(AddressingMode):
def serialize(self):
return self.value.serialize()
def __repr__(self):
return "%s(%r)" % (self.__class__.__name__, self.value)
class Absolute(AddressingMode):
def __init__(self, value):
@ -46,8 +46,18 @@ class Absolute(AddressingMode):
def serialize(self):
return self.value.serialize()
def __repr__(self):
return "%s(%r)" % (self.__class__.__name__, self.value)
class Relative(AddressingMode):
def __init__(self, value):
assert isinstance(value, (Byte, Label))
self.value = value
def size(self):
return 1
def serialize(self):
# HA
return chr(0xff)
class Opcode(Emittable):
@ -81,6 +91,18 @@ class AND(Opcode):
}
class BCC(Opcode):
opcodes = {
Relative: 0x90,
}
class BNE(Opcode):
opcodes = {
Relative: 0xd0,
}
class CLC(Opcode):
opcodes = {
Implied: 0x18
@ -151,6 +173,12 @@ class INY(Opcode):
}
class JMP(Opcode):
opcodes = {
Absolute: 0x4c,
}
class JSR(Opcode):
opcodes = {
Absolute: 0x20,

View File

@ -118,3 +118,17 @@ Some instructions.
| shr a
| }
= 00c0a900a200a0008d46c08e46c08c46c0381869016d46c0e901ed46c0ee46c0e8c8ce46c0ca8829ff2d46c009ff0d46c049ff4d46c0c901cd46c0e001ec46c0c001cc46c02a6a60
Compiling `if`.
| routine main
| trashes a, x, y, z, n, c, v
| {
| ld a, 0
| if z {
| ld y, 1
| } else {
| ld y, 2
| }
| }
= 00c0