memory.py (3625B)
1import sys 2 3memory_block_start = """ 4 mov UP, LEFT 5 6 mov UP, ACC 7 mov UP, LEFT 8 9 jnz is_write 10 mov LEFT, DOWN 11 mov 0, DOWN 12 mov UP, DOWN 13 mov LEFT, NIL 14 jmp wrap 15 16is_write: 17 mov LEFT, DOWN 18 mov 1, DOWN 19 mov UP, ACC 20 xor LEFT 21 mov ACC, DOWN 22 swp 23 24wrap: 25 mov DOWN, ACC 26 xor LEFT 27 mov LEFT, RIGHT 28 mov ${{addr}}, RIGHT 29 mov ${OP_ACK}, RIGHT 30 mov ACC, RIGHT 31 mov ${OP_NIL}, RIGHT 32""" 33 34memory_block_start_left = """ 35 mov RIGHT, ACC 36 swp 37 mov RIGHT, ACC 38 mov ACC, RIGHT 39 mov ACC, RIGHT 40 mov ACC, RIGHT 41 swp 42 mov ACC, RIGHT 43""" 44 45memory_block_start_right = """ 46 mov LEFT, UP 47""" 48 49code_memory_split = """ 50 mov UP, ACC 51 mov ACC, LEFT 52 mov ACC, RIGHT 53 54 mov UP, ACC 55 mov ACC, LEFT 56 mov ACC, RIGHT 57 58 mov UP, ACC 59 mov ACC, LEFT 60 mov ACC, RIGHT 61 62 mov ANY, ACC 63 add ANY 64 mov ACC, UP 65""" 66 67code_memory_split_rev = """ 68 mov UP, ACC 69 mov ACC, RIGHT 70 mov ACC, LEFT 71 72 mov UP, ACC 73 mov ACC, RIGHT 74 mov ACC, LEFT 75 76 mov UP, ACC 77 mov ACC, RIGHT 78 mov ACC, LEFT 79 80 mov ANY, ACC 81 add ANY 82 mov ACC, UP 83""" 84 85code_memory_cell = """ 86 mov 0x{val:02x}, ACC 87 sav 88start: 89 mov UP, ACC 90 xor {idx} 91 jnz skip 92 mov UP, ACC 93 jnz WRITE 94 mov UP, NIL 95 swp 96 mov ACC, UP 97 sav 98 jmp start 99write: 100 mov UP, ACC 101 swp 102 mov ACC, UP 103 jmp start 104skip: 105 mov UP, NIL 106 mov UP, NIL 107 mov 0, UP 108 jmp start 109""" 110 111code_memory_right = """ 112mov LEFT, RIGHT 113mov LEFT, RIGHT 114mov LEFT, RIGHT 115mov RIGHT, LEFT 116""" 117 118code_memory_right_corner = """ 119mov LEFT, DOWN 120mov LEFT, DOWN 121mov LEFT, DOWN 122mov DOWN, LEFT 123""" 124 125code_memory_left = """ 126mov RIGHT, LEFT 127mov RIGHT, LEFT 128mov RIGHT, LEFT 129mov LEFT, RIGHT 130""" 131 132code_memory_left_corner = """ 133mov RIGHT, DOWN 134mov RIGHT, DOWN 135mov RIGHT, DOWN 136mov DOWN, RIGHT 137""" 138 139class BlockMap(dict): 140 def __setattr__(self, key, value): 141 if key in self.__dict__: 142 raise ValueError("Already exists") 143 super().__setattr__(key, value) 144 145def gen_memory(blocks, start, idx_offset, idx, depth, contents): 146 if depth <= 0: 147 addr = idx_offset + idx 148 blocks[start] = code_memory_cell.format(idx=addr,val=addr^contents[idx]) 149 return 150 sx, sy = start 151 blocks[start] = code_memory_split_rev if depth % 2 else code_memory_split 152 sidelen = int(2**(depth-1)) 153 for i in range(1, sidelen): 154 blocks[(sx + i, sy)] = code_memory_right 155 blocks[(sx - i, sy)] = code_memory_left 156 blocks[(sx + sidelen, sy)] = code_memory_right_corner 157 blocks[(sx - sidelen, sy)] = code_memory_left_corner 158 gen_memory(blocks, (start[0] + sidelen, start[1] + 1), 159 idx_offset, idx + 2**(depth-1), depth - 1, contents) 160 gen_memory(blocks, (start[0] - sidelen, start[1] + 1), 161 idx_offset, idx, depth - 1, contents) 162 163def write_blocks(blocks, filepath, addr_tmpl): 164 with open(filepath, "w+") as f: 165 for i,(x,y) in enumerate(blocks): 166 f.write(f"tpu X{x} Y{y}\n") 167 if i == 0: 168 f.write("\t## ${" + addr_tmpl + "}\n") 169 for l in blocks[(x,y)].strip("\n").split("\n"): 170 f.write(f"{l}\n") 171 f.write(f"end\n") 172 f.write("\n") 173 174if __name__ == "__main__": 175 blocks = {} 176 blocks[(0, 0)] = memory_block_start.replace("{addr}", sys.argv[5]) 177 blocks[(-1, 0)] = memory_block_start_left 178 blocks[(1, 0)] = memory_block_start_right 179 gen_memory(blocks, (0, 1), int(sys.argv[2]), 0, int(sys.argv[3]), 180 open(sys.argv[4], "rb").read().ljust(256, b"\x00")) 181 write_blocks(blocks, sys.argv[1], sys.argv[5])