def getVariables(): # get all variable nodes from 'members' and (pot.) 'construct' variables = [] if "members" in classMap: variables.extend([node for node in treeutil.nodeIterator(classMap["members"], ["variable"])]) if "construct" in classMap: variables.extend([node for node in treeutil.nodeIterator(classMap["construct"], ["variable"])]) return variables
def checkRequiredBlocks(self): for node in treeutil.nodeIterator(self.tree, "loop"): block = treeutil.selectNode(node, "statement/block") if not block: self.log(node, "The statement of loops and conditions should be enclosed by a block in braces '{}'") for node in treeutil.nodeIterator(self.tree, "elseStatement"): block = treeutil.selectNode(node, "block") if not block: block = treeutil.selectNode(node, "loop[@loopType='IF']") if not block: self.log(node, "The statement of loops and conditions should be enclosed by a block in braces '{}'")
def getVariables(): # get all variable nodes from 'members' and (pot.) 'construct' variables = [] if "members" in classMap: variables.extend([ node for node in treeutil.nodeIterator( classMap["members"], ["variable"]) ]) if "construct" in classMap: variables.extend([ node for node in treeutil.nodeIterator( classMap["construct"], ["variable"]) ]) return variables
def findVariables(rootNode): variables = [] for node in treeutil.nodeIterator(rootNode, ["assignment", "call"]): if node.type == "assignment": variables.append(node.getChild("left")) elif node.type == "call": variables.append(node.getChild("operand")) return variables
def checkRequiredBlocks(self): for node in treeutil.nodeIterator(self.tree, "loop"): block = treeutil.selectNode(node, "statement/block") if not block: self.log( node, "The statement of loops and conditions should be enclosed by a block in braces '{}'" ) for node in treeutil.nodeIterator(self.tree, "elseStatement"): block = treeutil.selectNode(node, "block") if not block: block = treeutil.selectNode(node, "loop[@loopType='IF']") if not block: self.log( node, "The statement of loops and conditions should be enclosed by a block in braces '{}'" )
def _buildScopes(self): scopes = [] self.globalScope = Scope(self.root, self) scopes.append((self.root, self.globalScope)) for node in treeutil.nodeIterator(self.root, ["function", "catch"]): scope = Scope(node, self) scopes.append((node, scope)) return scopes
def checkMaps(self): for node in treeutil.nodeIterator(self.tree, "map"): knownkeys = {} if node.hasChildren(): for child in node.children: if child.type == "keyvalue": key = child.get("key") if key in knownkeys: self.log(child, "Map key '%s' redefined." % key) else: knownkeys[key] = child
def reduceOperation(literalNode): resultNode = None treeModified = False # can only reduce with constants if literalNode.type != "constant": return literalNode, False else: literalValue = constNodeToPyValue(literalNode) # check if we're in an operation ngParent = nextNongroupParent(literalNode) # could be "first", "second" etc. in ops if not ngParent or not ngParent.parent or ngParent.parent.type != "operation": return literalNode, False else: operationNode = ngParent.parent # get operator operator = operationNode.get("operator") # normalize expression noperationNode = normalizeExpression(operationNode) # re-gain knownn literal node for node in treeutil.nodeIterator(noperationNode, [literalNode.type]): if literalNode.attributes == node.attributes: nliteralNode = node break # equal, unequal if operator in ["EQ", "SHEQ", "NE", "SHNE"]: otherOperand, _ = getOtherOperand(noperationNode, nliteralNode) if otherOperand.type != "constant": return literalNode, False if operator in ["EQ", "SHEQ"]: cmpFcn = operators.eq elif operator in ["NE", "SHNE"]: cmpFcn = operators.ne operands = [literalValue] otherVal = constNodeToPyValue(otherOperand) operands.append(otherVal) result = cmpFcn(operands[0],operands[1]) resultNode = tree.Node("constant") resultNode.set("constantType","boolean") resultNode.set("value", str(result).lower()) resultNode.set("line", noperationNode.get("line")) # order compares <, =<, ... elif operator in ["LT", "LE", "GT", "GE"]: otherOperand, otherPosition = getOtherOperand(noperationNode, nliteralNode) if otherOperand.type != "constant": return literalNode, False if operator == "LT": cmpFcn = operators.lt elif operator == "LE": cmpFcn = operators.le elif operator == "GT": cmpFcn = operators.gt elif operator == "GE": cmpFcn = operators.ge operands = {} operands[1 - otherPosition] = literalValue otherVal = constNodeToPyValue(otherOperand) operands[otherPosition] = otherVal result = cmpFcn(operands[0], operands[1]) resultNode = tree.Node("constant") resultNode.set("constantType","boolean") resultNode.set("value", str(result).lower()) resultNode.set("line", noperationNode.get("line")) # logical ! (not) elif operator in ["NOT"]: result = not literalValue resultNode = tree.Node("constant") resultNode.set("constantType","boolean") resultNode.set("value", str(result).lower()) resultNode.set("line", noperationNode.get("line")) # logical operators &&, || -- Currently disabled, s. bug#4856 elif False and operator in ["AND", "OR"]: result = None otherOperand, otherPosition = getOtherOperand(noperationNode, nliteralNode) if operator == "AND": #if otherPosition==1 and not literalValue: # short circuit # result = False #else: cmpFcn = (lambda x,y: x and y) elif operator == "OR": #if otherPosition==1 and literalValue: # short circuit # result = True #else: cmpFcn = (lambda x,y: x or y) if result == None: if otherOperand.type != "constant": return literalNode, False operands = {} operands[1 - otherPosition] = literalValue otherVal = constNodeToPyValue(otherOperand) operands[otherPosition] = otherVal result = cmpFcn(operands[0], operands[1]) resultNode = {literalValue:literalNode, otherVal:otherOperand}[result] # hook ?: operator elif operator in ["HOOK"]: if ngParent.type == "first": # optimize a literal condition if bool(literalValue): resultNode = treeutil.selectNode(noperationNode, "second/1", True) else: resultNode = treeutil.selectNode(noperationNode, "third/1", True) # unsupported operation else: pass if resultNode != None: #print "optimizing: operation" operationNode.parent.replaceChild(operationNode, resultNode) treeModified = True else: resultNode = literalNode treeModified = False return resultNode, treeModified
def reduceOperation(literalNode): resultNode = None treeModified = False # can only reduce with constants if literalNode.type != "constant": return literalNode, False else: literalValue = constNodeToPyValue(literalNode) # check if we're in an operation ngParent = nextNongroupParent( literalNode) # could be "first", "second" etc. in ops if not ngParent or not ngParent.parent or ngParent.parent.type != "operation": return literalNode, False else: operationNode = ngParent.parent # get operator operator = operationNode.get("operator") # normalize expression noperationNode = normalizeExpression(operationNode) # re-gain knownn literal node for node in treeutil.nodeIterator(noperationNode, [literalNode.type]): if literalNode.attributes == node.attributes: nliteralNode = node break # equal, unequal if operator in ["EQ", "SHEQ", "NE", "SHNE"]: otherOperand, _ = getOtherOperand(noperationNode, nliteralNode) if otherOperand.type != "constant": return literalNode, False if operator in ["EQ", "SHEQ"]: cmpFcn = operators.eq elif operator in ["NE", "SHNE"]: cmpFcn = operators.ne operands = [literalValue] otherVal = constNodeToPyValue(otherOperand) operands.append(otherVal) result = cmpFcn(operands[0], operands[1]) resultNode = tree.Node("constant") resultNode.set("constantType", "boolean") resultNode.set("value", str(result).lower()) resultNode.set("line", noperationNode.get("line")) # order compares <, =<, ... elif operator in ["LT", "LE", "GT", "GE"]: otherOperand, otherPosition = getOtherOperand(noperationNode, nliteralNode) if otherOperand.type != "constant": return literalNode, False if operator == "LT": cmpFcn = operators.lt elif operator == "LE": cmpFcn = operators.le elif operator == "GT": cmpFcn = operators.gt elif operator == "GE": cmpFcn = operators.ge operands = {} operands[1 - otherPosition] = literalValue otherVal = constNodeToPyValue(otherOperand) operands[otherPosition] = otherVal result = cmpFcn(operands[0], operands[1]) resultNode = tree.Node("constant") resultNode.set("constantType", "boolean") resultNode.set("value", str(result).lower()) resultNode.set("line", noperationNode.get("line")) # logical ! (not) elif operator in ["NOT"]: result = not literalValue resultNode = tree.Node("constant") resultNode.set("constantType", "boolean") resultNode.set("value", str(result).lower()) resultNode.set("line", noperationNode.get("line")) # logical operators &&, || -- Currently disabled, s. bug#4856 elif False and operator in ["AND", "OR"]: result = None otherOperand, otherPosition = getOtherOperand(noperationNode, nliteralNode) if operator == "AND": #if otherPosition==1 and not literalValue: # short circuit # result = False #else: cmpFcn = (lambda x, y: x and y) elif operator == "OR": #if otherPosition==1 and literalValue: # short circuit # result = True #else: cmpFcn = (lambda x, y: x or y) if result == None: if otherOperand.type != "constant": return literalNode, False operands = {} operands[1 - otherPosition] = literalValue otherVal = constNodeToPyValue(otherOperand) operands[otherPosition] = otherVal result = cmpFcn(operands[0], operands[1]) resultNode = { literalValue: literalNode, otherVal: otherOperand }[result] # hook ?: operator elif operator in ["HOOK"]: if ngParent.type == "first": # optimize a literal condition if bool(literalValue): resultNode = treeutil.selectNode(noperationNode, "second/1", True) else: resultNode = treeutil.selectNode(noperationNode, "third/1", True) # unsupported operation else: pass if resultNode != None: #print "optimizing: operation" operationNode.parent.replaceChild(operationNode, resultNode) treeModified = True else: resultNode = literalNode treeModified = False return resultNode, treeModified