Commit ae2cc948 authored by Taddeus Kroes's avatar Taddeus Kroes

Merge branch 'master' of github.com:taddeus/peephole

parents c94f0225 ff70b648
...@@ -246,14 +246,18 @@ the generated Assembly code. ...@@ -246,14 +246,18 @@ the generated Assembly code.
The writer expects a list of statements, so first the blocks have to be The writer expects a list of statements, so first the blocks have to be
concatenated again into a list. After this is done, the list is passed on to concatenated again into a list. After this is done, the list is passed on to
the writer, which writes the instructions back to Assembly and saves the file the writer, which writes the instructions back to Assembly and saves the file
so we can let xgcc compile it. We also write the original statements to a file, so we can let xgcc compile it. The original statements can also written to a
so differences in tabs, spaces and newlines do not show up when we check the file, so differences in tabs, spaces and newlines do not show up when checking
differences between the optimized and non-optimized files. the differences between the optimized and non-optimized files.
\subsection{Execution} \subsection{Execution}
To execute the optimizer, the following command can be given:\\ To execute the optimizer, the following command can be given:\\
\texttt{./main <original file> <optimized file> <rewritten original file>} \texttt{./main.py <original file> <optimized file> <rewritten original file>}\\
There is also a script available that runs the optimizer and automatically
starts the program \emph{meld}. In meld it is easy to visually compare the
original file and the optimized file. The command to execute this script is:\\
\texttt{./run <benchmark name (e.g. whet)>}\\
\section{Testing} \section{Testing}
......
...@@ -123,8 +123,25 @@ def add_lw(add, statements): ...@@ -123,8 +123,25 @@ def add_lw(add, statements):
return True return True
def remove_redundant_jumps(statements): def remove_redundant_jumps(statements):
"""Remove jump if label follows immediatly."""
old_len = -1
while old_len != len(statements):
old_len = len(statements)
while not statements.end():
s = statements.read()
# j $Lx -> $Lx:
# $Lx:
if s.is_command('j'):
following = statements.peek(2)
if following.is_label(s[0]):
statements.replace(1, [])
def remove_redundant_branch_jumps(statements):
"""Optimize statement sequences on a global level.""" """Optimize statement sequences on a global level."""
old_len = -1 old_len = -1
......
...@@ -173,71 +173,94 @@ class TestOptimize(unittest.TestCase): ...@@ -173,71 +173,94 @@ class TestOptimize(unittest.TestCase):
self.assertEquals(block2.statements, arguments2) self.assertEquals(block2.statements, arguments2)
self.assertEquals(block3.statements, arguments3) self.assertEquals(block3.statements, arguments3)
def test_remove_redundant_jumps_beq_j_true(self): def test_optimize_block_move_move_true(self):
block = B([self.foo, block = B([self.foo,
S('command', 'beq', '$regA', '$regB', '$Lx'), S('command', 'move', '$regA', '$regB'),
S('command', 'j', '$Ly'), S('command', 'move', '$regB', '$regA'),
S('label', '$Lx'),
self.bar]) self.bar])
remove_redundant_jumps(block) remove_redundancies(block)
self.assertEquals(block.statements, [self.foo, self.assertEquals(block.statements, [self.foo,
S('command', 'bne', '$regA', '$regB', '$Ly'), S('command', 'move', '$regA', '$regB'),
S('label', '$Lx'),
self.bar]) self.bar])
def test_remove_redundant_jumps_beq_j_false(self): def test_optimize_block_mov_mov_false(self):
arguments = [self.foo, \ arguments = [self.foo, \
S('command', 'beq', '$regA', '$regB', '$Lz'), \ S('command', 'move', '$regA', '$regB'), \
S('command', 'j', '$Ly'), \ S('command', 'move', '$regB', '$regC'), \
S('label', '$Lx'), \
self.bar] self.bar]
block = B(arguments) block = B(arguments)
remove_redundant_jumps(block) remove_redundancies(block)
self.assertEquals(block.statements, arguments) self.assertEquals(block.statements, arguments)
def test_remove_redundant_jumps_bne_j_true(self): def test_remove_redundant_jumps_true(self):
block = B([self.foo, block = B([self.foo,
S('command', 'bne', '$regA', '$regB', '$Lx'), S('command', 'j', '$L1'),
S('label', '$L1'),
self.bar])
remove_redundancies(block)
self.assertEqual(block.statements, B([self.foo,
S('command', 'j', '$L1'),
self.bar]))
def test_remove_redundant_jumps_false(self):
arguments = [self.foo,
S('command', 'j', '$L1'),
S('label', '$L2'),
self.bar]
block = B(arguments)
remove_redundancies(block)
self.assertEqual(block.statements, arguments)
def test_remove_redundant_branch_jumps_beq_j_true(self):
block = B([self.foo,
S('command', 'beq', '$regA', '$regB', '$Lx'),
S('command', 'j', '$Ly'), S('command', 'j', '$Ly'),
S('label', '$Lx'), S('label', '$Lx'),
self.bar]) self.bar])
remove_redundant_jumps(block) remove_redundant_branch_jumps(block)
self.assertEquals(block.statements, [self.foo, self.assertEquals(block.statements, [self.foo,
S('command', 'beq', '$regA', '$regB', '$Ly'), S('command', 'bne', '$regA', '$regB', '$Ly'),
S('label', '$Lx'), S('label', '$Lx'),
self.bar]) self.bar])
def test_remove_redundant_jumps_bne_j_false(self): def test_remove_redundant_branch_jumps_beq_j_false(self):
arguments = [self.foo, \ arguments = [self.foo, \
S('command', 'bne', '$regA', '$regB', '$Lz'), \ S('command', 'beq', '$regA', '$regB', '$Lz'), \
S('command', 'j', '$Ly'), \ S('command', 'j', '$Ly'), \
S('label', '$Lx'), \ S('label', '$Lx'), \
self.bar] self.bar]
block = B(arguments) block = B(arguments)
remove_redundant_jumps(block) remove_redundant_branch_jumps(block)
self.assertEquals(block.statements, arguments) self.assertEquals(block.statements, arguments)
def test_optimize_block_move_move_true(self): def test_remove_redundant_branch_jumps_bne_j_true(self):
block = B([self.foo, block = B([self.foo,
S('command', 'move', '$regA', '$regB'), S('command', 'bne', '$regA', '$regB', '$Lx'),
S('command', 'move', '$regB', '$regA'), S('command', 'j', '$Ly'),
S('label', '$Lx'),
self.bar]) self.bar])
remove_redundancies(block) remove_redundant_branch_jumps(block)
self.assertEquals(block.statements, [self.foo, self.assertEquals(block.statements, [self.foo,
S('command', 'move', '$regA', '$regB'), S('command', 'beq', '$regA', '$regB', '$Ly'),
S('label', '$Lx'),
self.bar]) self.bar])
def test_optimize_block_mov_mov_false(self): def test_remove_redundant_branch_jumps_bne_j_false(self):
arguments = [self.foo, \ arguments = [self.foo, \
S('command', 'move', '$regA', '$regB'), \ S('command', 'bne', '$regA', '$regB', '$Lz'), \
S('command', 'move', '$regB', '$regC'), \ S('command', 'j', '$Ly'), \
S('label', '$Lx'), \
self.bar] self.bar]
block = B(arguments) block = B(arguments)
remove_redundancies(block) remove_redundant_branch_jumps(block)
self.assertEquals(block.statements, arguments) self.assertEquals(block.statements, arguments)
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment