fix reg2reg and incr decr 16 bits

This commit is contained in:
Irmen de Jong 2017-12-29 02:28:59 +01:00
parent 9bcbf29a49
commit 739f5b9659
2 changed files with 122 additions and 20 deletions

View File

@ -405,38 +405,75 @@ class CodeGenerator:
raise CodeError("only supports incr/decr by up to 255 for now") # XXX
is_incr = isinstance(stmt, ParseResult.InplaceIncrStmt)
if isinstance(stmt.what, ParseResult.RegisterValue):
reg = stmt.what.register
if is_incr:
if stmt.what.register == 'A':
if reg == 'A':
self.p("\t\tclc")
self.p("\t\tadc #{:d}".format(stmt.howmuch))
elif stmt.what.register in REGISTER_BYTES:
elif reg in REGISTER_BYTES:
# 8 bit incr
if stmt.howmuch == 1:
self.p("\t\tin{:s}".format(stmt.what.register.lower()))
self.p("\t\tin{:s}".format(reg.lower()))
else:
self.p("\t\tpha")
self.p("\t\tt{:s}a".format(stmt.what.register.lower()))
self.p("\t\tt{:s}a".format(reg.lower()))
self.p("\t\tclc")
self.p("\t\tadc #{:d}".format(stmt.howmuch))
self.p("\t\tta{:s}".format(stmt.what.register.lower()))
self.p("\t\tta{:s}".format(reg.lower()))
self.p("\t\tpla")
elif reg == "AX":
self.p("\t\tclc")
self.p("\t\tadc #1")
self.p("\t\tbne +")
self.p("\t\tinx")
self.p("+")
elif reg == "AY":
self.p("\t\tclc")
self.p("\t\tadc #1")
self.p("\t\tbne +")
self.p("\t\tiny")
self.p("+")
elif reg == "XY":
self.p("\t\tinx")
self.p("\t\tbne +")
self.p("\t\tiny")
self.p("+")
else:
raise CodeError("invalid incr/decr register")
raise CodeError("invalid incr register: " + reg)
else:
if stmt.what.register == 'A':
if reg == 'A':
self.p("\t\tsec")
self.p("\t\tsbc #{:d}".format(stmt.howmuch))
elif stmt.what.register in REGISTER_BYTES:
elif reg in REGISTER_BYTES:
# 8 bit decr
if stmt.howmuch == 1:
self.p("\t\tde{:s}".format(stmt.what.register.lower()))
self.p("\t\tde{:s}".format(reg.lower()))
else:
self.p("\t\tpha")
self.p("\t\tt{:s}a".format(stmt.what.register.lower()))
self.p("\t\tt{:s}a".format(reg.lower()))
self.p("\t\tsec")
self.p("\t\tsbc #{:d}".format(stmt.howmuch))
self.p("\t\tta{:s}".format(stmt.what.register.lower()))
self.p("\t\tta{:s}".format(reg.lower()))
self.p("\t\tpla")
elif reg == "AX":
self.p("\t\tcmp #0")
self.p("\t\tbne +")
self.p("\t\tdex")
self.p("+\t\tsec")
self.p("\t\tsbc #1")
elif reg == "AY":
self.p("\t\tcmp #0")
self.p("\t\tbne +")
self.p("\t\tdey")
self.p("+\t\tsec")
self.p("\t\tsbc #1")
elif reg == "XY":
self.p("\t\tcpx #0")
self.p("\t\tbne +")
self.p("\t\tdey")
self.p("+\t\tdex")
else:
raise CodeError("invalid incr/decr register")
raise CodeError("invalid decr register: " + reg)
elif isinstance(stmt.what, (ParseResult.MemMappedValue, ParseResult.IndirectValue)):
what = stmt.what
if isinstance(what, ParseResult.IndirectValue):
@ -768,16 +805,12 @@ class CodeGenerator:
def _generate_call_or_goto(self, stmt: ParseResult.CallStmt, branch_emitter: Callable[[str, bool, bool], None]) -> None:
def generate_param_assignments() -> None:
self.p("; param assignment") # XXX
for assign_stmt in stmt.desugared_call_arguments:
self.generate_assignment(assign_stmt)
self.p("; param assignment done") # XXX
def generate_result_assignments() -> None:
self.p("; result assignment") # XXX
for assign_stmt in stmt.desugared_output_assignments:
self.generate_assignment(assign_stmt)
self.p("; result assignment done") # XXX
def params_load_a() -> bool:
for assign_stmt in stmt.desugared_call_arguments:
@ -1510,19 +1543,21 @@ class CodeGenerator:
# y -> x, 6502 doesn't have tyx
self.p("\t\tsty ${0:02x}\n\t\tldx ${0:02x}".format(Zeropage.SCRATCH_B1))
elif lv.register == "AX" and r_register == "XY":
# x -> a, y -> x, 6502 doesn't have tyx
self.p("\t\ttxa")
# y -> x, 6502 doesn't have tyx
self.p("\t\tsty ${0:02x}\n\t\tldx ${0:02x}".format(Zeropage.SCRATCH_B1))
elif lv.register == "AY" and r_register == "AX":
# x -> y, 6502 doesn't have txy
self.p("\t\tstx ${0:02x}\n\t\tldy ${0:02x}".format(Zeropage.SCRATCH_B1))
elif lv.register == "AY" and r_register == "XY":
# x -> a
self.p("\t\ttxa")
elif lv.register == "XY" and r_register == "AX":
self.p("\t\ttax")
# x -> y, 6502 doesn't have txy
# x -> y, a -> x, 6502 doesn't have txy
self.p("\t\tstx ${0:02x}\n\t\tldy ${0:02x}".format(Zeropage.SCRATCH_B1))
self.p("\t\ttax")
elif lv.register == "XY" and r_register == "AY":
# a -> x
self.p("\t\ttax")
else:
raise CodeError("invalid register combination", lv.register, r_register)

View File

@ -10,7 +10,74 @@ import "c64lib"
var secretnumber
var attempts_left = 10
start
c64util.init_system()
XY = $0401
c64util.print_word_decimal(XY)
c64.CHROUT('\n')
XY--
c64util.print_word_decimal(XY)
c64.CHROUT('\n')
XY--
c64util.print_word_decimal(XY)
c64.CHROUT('\n')
AX = $0401
c64util.print_word_decimal(AX)
c64.CHROUT('\n')
AX--
c64util.print_word_decimal(AX)
c64.CHROUT('\n')
AX--
c64util.print_word_decimal(AX)
c64.CHROUT('\n')
AY = $0401
c64util.print_word_decimal(AY)
c64.CHROUT('\n')
AY--
c64util.print_word_decimal(AY)
c64.CHROUT('\n')
AY--
c64util.print_word_decimal(AY)
c64.CHROUT('\n')
c64.CHROUT('\n')
XY = $03ff
c64util.print_word_decimal(XY)
c64.CHROUT('\n')
XY++
c64util.print_word_decimal(XY)
c64.CHROUT('\n')
XY++
c64util.print_word_decimal(XY)
c64.CHROUT('\n')
AX = $03ff
c64util.print_word_decimal(AX)
c64.CHROUT('\n')
AX++
c64util.print_word_decimal(AX)
c64.CHROUT('\n')
AX++
c64util.print_word_decimal(AX)
c64.CHROUT('\n')
AY = $03ff
c64util.print_word_decimal(AY)
c64.CHROUT('\n')
AY++
c64util.print_word_decimal(AY)
c64.CHROUT('\n')
AY++
c64util.print_word_decimal(AY)
c64.CHROUT('\n')
c64.CHROUT('\n')
A = c64.VMCSB
A |= 2 ; @todo c64.VMCSB |= 2
c64.VMCSB = A
@ -43,7 +110,7 @@ printloop
; @todo comparison expression so we can do if attempts_left>0 ...
A = attempts_left
A --
A--
if_zero A goto ask_guess
c64util.print_string("es")
ask_guess