Skip to content

Commit ff759d3

Browse files
committed
SB and JUMP working
1 parent d9bebd9 commit ff759d3

File tree

7 files changed

+36
-34
lines changed

7 files changed

+36
-34
lines changed
Binary file not shown.
Binary file not shown.
Binary file not shown.

src/riscv_assembler/instr_arr.py

Lines changed: 19 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
__all__ = [
66
'R_instr', 'I_instr', 'S_instr',
7-
'SB_instr', 'U_instr', 'UJ_instr','pseudo_instr',
7+
'SB_instr', 'U_instr', 'UJ_instr','pseudo_instr', 'JUMP',
88
'R', 'I', 'S', 'SB', 'U', 'UJ',
99
'Rp', 'Ip', 'Sp', 'SBp', 'Up', 'UJp', 'Psp']
1010

@@ -69,7 +69,8 @@ def compute_instr(self, instr, rs1, imm, rd):
6969
@staticmethod
7070
def immediate(imm):
7171
#return int(imm) - ((int(imm)>>12)<<12) # imm[11:0]
72-
return format(int(imm), '012b')
72+
return format(((1 << 12) - 1) & int(imm), '012b')
73+
#return format(int(imm), '012b')
7374

7475
class _S(Instruction):
7576
def __repr__(self):
@@ -97,7 +98,7 @@ def immediate(imm, n):
9798
mod_imm_2 = int(imm) - ((int(imm) >> 5) << 5) # imm[4:0]
9899
99100
return mod_imm, mod_imm_2'''
100-
mod_imm = format(((1 << 13) - 1) & int(imm), '013b')
101+
mod_imm = format(((1 << 12) - 1) & int(imm), '012b')
101102
if n == 1:
102103
return mod_imm[0] + mod_imm[12-10 : 12-4]
103104
return mod_imm[12-4 : 12 - 0] + mod_imm[1]
@@ -127,8 +128,8 @@ def compute_instr(self, instr, rs1, rs2, imm):
127128
def immediate(imm, n):
128129
mod_imm = format(((1 << 13) - 1) & int(imm), '013b')
129130
if n == 1:
130-
return mod_imm[12-12] + mod_imm[12-10:12-5]
131-
return mod_imm[12-4:12-1] + mod_imm[12-11]
131+
return mod_imm[12-12] + mod_imm[12-11:12-5]
132+
return mod_imm[12-4:12-0] + mod_imm[12-11]
132133

133134
class _U(Instruction):
134135
def __repr__(self):
@@ -201,10 +202,11 @@ def __str__(self):
201202
return "I Parser"
202203

203204
def organize(self, tokens):
205+
line_num, code = tokens[-2], tokens[-1]
204206
instr, rs1, imm, rd = tokens[0], None, None, None
205207
if instr == "jalr":
206208
if len(tokens) == 4:
207-
rs1, imm, rd = reg_map[tokens[2]], JUMP(tokens[3]), reg_map[tokens[1]]
209+
rs1, imm, rd = reg_map[tokens[2]], JUMP(tokens[3], line_num, code), reg_map[tokens[1]]
208210
else:
209211
rs1, imm, rd = reg_map[tokens[1]], 0, reg_map["x1"]
210212
elif instr == "lw":
@@ -235,7 +237,8 @@ def __str__(self):
235237
return "SB Parser"
236238

237239
def organize(self, tokens):
238-
instr, rs1, rs2, imm = tokens[0], reg_map[tokens[1]], reg_map[tokens[2]], JUMP(tokens[3])
240+
line_num, code = tokens[-2], tokens[-1]
241+
instr, rs1, rs2, imm = tokens[0], reg_map[tokens[1]], reg_map[tokens[2]], JUMP(tokens[3], line_num, code)
239242
return SB(instr, rs1, rs2, imm)
240243

241244
class _U_parse(InstructionParser):
@@ -259,11 +262,12 @@ def __str__(self):
259262
return "UJ Parser"
260263

261264
def organize(self, tokens):
265+
line_num, code = tokens[-2], tokens[-1]
262266
instr, imm, rd = tokens[0], None, None
263267
if len(tokens) == 3:
264-
imm, rd = JUMP(tokens[2]), reg_map[tokens[1]]
268+
imm, rd = JUMP(tokens[2], line_num, code), reg_map[tokens[1]]
265269
else:
266-
imm, rd = JUMP(tokens[1]), reg_map["x1"]
270+
imm, rd = JUMP(tokens[1], line_num, code), reg_map["x1"]
267271

268272
return UJ(instr, imm, rd)
269273

@@ -292,27 +296,25 @@ def organize(self, tokens):
292296

293297
return BadInstructionError()
294298

295-
def JUMP(x : str, line_num : int) -> int:
296-
raise NotImplementedError()
297-
299+
def JUMP(x : str, line_num : int, code: list) -> int:
298300
# search forward
299301
skip_labels = 0
300-
for i in range(line_num, len(self.code)):
301-
if x+":" == self.code[i]:
302+
for i in range(line_num, len(code)):
303+
if x+":" == code[i]:
302304
jump_size = (i - line_num - skip_labels) * 4 # how many instructions to jump ahead
303305
return jump_size
304306

305-
if self.code[i][-1] == ':':
307+
if code[i][-1] == ':':
306308
skip_labels += 1
307309

308310
# search backward
309311
skip_labels = 0
310312
for i in range(line_num, -1, -1):
311313
# substruct correct label itself
312-
if self.code[i][-1] == ':':
314+
if code[i][-1] == ':':
313315
skip_labels += 1
314316

315-
if x+":" == self.code[i]:
317+
if x+":" == code[i]:
316318
jump_size = (i - line_num + skip_labels) * 4 # how many instructions to jump behind
317319
return jump_size
318320

src/riscv_assembler/parse.py

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
from riscv_assembler.instr_arr import *
22
from types import FunctionType as function
3+
from os.path import exists
34
__all__ = ['Parser']
45

56
class _Parser:
@@ -18,13 +19,12 @@ class _Parser:
1819
'''
1920

2021
def __call__(self, *args) -> list:
21-
if _Parser.is_file(*args):
22-
return _Parser.interpret_file(_Parser.read_file(*args))
23-
return [_Parser.interpret(_Parser.tokenize(x)) for x in args[0].split("\n") if len(_Parser.tokenize(x)) > 0]
24-
25-
@staticmethod
26-
def is_file(x : str) -> bool:
27-
return True if '.s' in x or '/' in x else False
22+
if exists(*args):
23+
return _Parser.interpret_arr(_Parser.read_file(*args))
24+
#return [_Parser.interpret(_Parser.tokenize(x)) for x in args[0].split("\n") if len(_Parser.tokenize(x)) > 0]
25+
elif type(args[0]) == str:
26+
return _Parser.interpret_arr(args[0].split('\n'))
27+
return _Parser.interpret_arr(*args)
2828

2929
'''
3030
In read_file(), Check if the inputted line is appropriate before
@@ -35,7 +35,7 @@ def valid_line(x : str, allow_colon : bool = False) -> bool:
3535
if x[0][0] == "#" or x[0][0] == "\n" or x[0][0] == "" or x[0][0] == ".":
3636
return False
3737

38-
if not allow_colon and x[0][-1] == ":" :
38+
if not allow_colon and x[-1] == ":" :
3939
return False
4040
return True
4141

@@ -76,13 +76,13 @@ def read_file(file : str) -> list:
7676
file.close()
7777
return code'''
7878
with open(file) as f:
79-
return f.readlines()
79+
return [x.strip() for x in f.readlines() if x != '\n']
8080

8181
@staticmethod
82-
def interpret_file(code : list) -> list:
82+
def interpret_arr(code : list) -> list:
8383
int_code = []
84-
for line in code:
85-
tokens = _Parser.tokenize(line)
84+
for line_num, line in enumerate(code):
85+
tokens = _Parser.tokenize(line, line_num, code)
8686
int_code += [_Parser.interpret(tokens) for _ in range(1) if len(tokens) != 0]
8787

8888
return int_code
@@ -91,12 +91,12 @@ def interpret_file(code : list) -> list:
9191
Tokenize a given line
9292
'''
9393
@staticmethod
94-
def tokenize(line : str) -> list:
94+
def tokenize(line : str, line_num: int = None, code : list = None) -> list:
9595
line = line.strip()
96-
if len(line) > 0 and _Parser.valid_line(line, True):
96+
if len(line) > 0 and _Parser.valid_line(line):
9797
tokens = _Parser.handle_inline_comments(line).split()
9898
tokens = _Parser.handle_specific_instr(tokens)
99-
return tokens
99+
return tokens + [line_num, code] if line_num != None and code != None else tokens
100100
return []
101101

102102
'''
Binary file not shown.

tests/test_class.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -155,8 +155,8 @@ def test_11():
155155
assert func11() == []
156156

157157
# Test file test2.s, need to implement JUMP
158-
#def test_12():
159-
# assert func12() == ['0x00a00413', '0x00a00493', '0x00848263', '0xfe040493']
158+
def test_12():
159+
assert func12() == ['0x00a00413', '0x00a00493', '0x00848263', '0xfe040493']
160160

161161
def test_13():
162162
assert func13() == ['0x00812023']

0 commit comments

Comments
 (0)