summaryrefslogtreecommitdiff
path: root/LinkedNode.py
diff options
context:
space:
mode:
Diffstat (limited to 'LinkedNode.py')
-rw-r--r--LinkedNode.py71
1 files changed, 25 insertions, 46 deletions
diff --git a/LinkedNode.py b/LinkedNode.py
index 88bc6da..f068993 100644
--- a/LinkedNode.py
+++ b/LinkedNode.py
@@ -18,12 +18,9 @@ __version__ = "1.0"
__maintainer__ = "Peter Wu"
__email__ = "uwretep@gmail.com"
-from Variables import Variables
-
class LinkedNode(object):
"""Stores nodes with a reference to the parent"""
- def __init__(self, node, parent=None, level_increment=False,
- defined_names=None):
+ def __init__(self, node, parent=None, level_increment=False):
"""Holds properties for a node
Keyword arguments:
@@ -31,8 +28,6 @@ class LinkedNode(object):
parent -- a parent LinkedNode object
level_increment -- True if the indentation level needs to be
incremented, False otherwise
- defined_names -- a list of names which will be used in the @DATA
- section. If not set, it'll be looked up in the parent
"""
self.node = node
if parent:
@@ -46,48 +41,32 @@ class LinkedNode(object):
self.variables = None
# for supporting post increment and post decrement
self.post_lines = []
- parent_variables = None
# inherit level and variables from parent
if parent:
self.level = parent.level
- self.variables = parent_variables = parent.variables
- if not defined_names:
- defined_names = parent.variables.defined_names
+ self.variables = parent.variables
- # for is added for the init part (C99)
- if self.type in ("Compound", "FileAST", "For"):
- # the node appears to have an own variable scope
- if defined_names is None:
- raise RuntimeError("No object found for storing variables")
- # pass function object for local variables allocation
- function = self.getFunctionNode()
- if function:
- function = function.function
- self.variables = Variables(parent_variables, defined_names,
- function=function)
- # Identifiers which are in use (think of variables and labels)
- self.defined_names = defined_names
- if not self.variables:
- raise RuntimeError("No variables object found")
if level_increment:
self.incrementLevel()
+
# labels are limited to function contexts
if self.type == "FuncDef":
self.goto_labels = {}
+ def setVariablesObj(self, variables_obj):
+ """Sets a new variables scope object for this node"""
+ self.variables = variables_obj
def handle_post_lines(self, lines):
"""Add post-increment lines to the lines list and clear the queue"""
lines += self.post_lines
self.post_lines = []
- def getScopeNode(self):
- """Get the nearest node which introduces a new scope.
-
- If there is no node found an exception is raised because it expects at
- least a global scope"""
- if self.local_vars is not None:
- return self
- if self.parent:
- return self.parent.getScopeNode()
- raise RuntimeError("No global variable scope was found")
+ def needNewScope(self):
+ """Returns True if a new name scope is necessary and False otherwise"""
+ if self.type == "Compound":
+ if self.parent.type not in ("For", "FuncDef"):
+ return True
+ elif self.type in ("FileAST", "For", "FuncDef"):
+ return True
+ return False
def isTypeStatement(self):
"""Returns True if the node is a statement type"""
return self.type in ("Compound", "If", "Return", "DoWhile", "While",
@@ -118,11 +97,14 @@ class LinkedNode(object):
return self.parent.getFunctionNode()
return None
def setFunction(self, function):
- """Sets the function object containing label information"""
+ """Sets the function object containing label information and a stack
+ allocation function
+ """
self.function = function
+ self.variables.setFunction(function)
def getLocation(self):
if hasattr(self.node, "coord"):
- return self.node.coord
+ return str(self.node.coord)
return "Unknown"
def setBreak(self, break_label):
"""Marks this node as a loop or switch by setting the label for break
@@ -153,9 +135,12 @@ class LinkedNode(object):
if self.parent:
return self.parent.getContinueNode()
return None
- def setLabel(self, label_name):
- """Sets the label for this node and return the label name as it appears
- in assembly
+ def setLabel(self, label_name, label_asm):
+ """Sets the label for this node
+
+ Keyword arguments:
+ label_name -- The label name as can be used in C
+ label_asm -- The label as it appears in assembly
"""
if self.parent:
function = self.parent.getFunctionNode()
@@ -164,12 +149,6 @@ class LinkedNode(object):
if label_name in function.goto_labels:
raise RuntimeError("Duplicate label '{}'".format(label_name))
- label_asm = "lbl_" + label_name
- i = 0
- while label_asm in self.defined_names:
- label_asm = "lbl_" + label_name + str(i)
- i += 1
-
function.goto_labels[label_name] = label_asm
return label_asm
def lookupLabel(self, label_name):