diff -r ca1ce1e0fcff -r 382f89c11e27 eric6/Plugins/CheckerPlugins/CodeStyleChecker/Security/SecurityNodeVisitor.py --- a/eric6/Plugins/CheckerPlugins/CodeStyleChecker/Security/SecurityNodeVisitor.py Mon Jun 08 08:17:14 2020 +0200 +++ b/eric6/Plugins/CheckerPlugins/CodeStyleChecker/Security/SecurityNodeVisitor.py Mon Jun 08 20:08:27 2020 +0200 @@ -18,6 +18,16 @@ Class implementing an AST node visitor for security checks. """ def __init__(self, checker, secCheckers, filename): + """ + Constructor + + @param checker reference to the main security checker object + @type SecurityChecker + @param secCheckers dictionary containing the available checker routines + @type dict + @param filename name of the checked file + @type str + """ self.__checker = checker self.__securityCheckers = secCheckers @@ -36,6 +46,9 @@ def __runChecks(self, checkType): """ Private method to run all enabled checks for a given check type. + + @param checkType type of checks to be run + @type str """ if checkType in self.__securityCheckers: for check in self.__securityCheckers[checkType]: @@ -97,12 +110,108 @@ self.__context['name'] = name self.__runChecks("Call") + def visit_Import(self, node): + """ + Public method defining a visitor for AST Import nodes. + + @param node reference to the node being inspected + @type ast.Import + """ + for nodename in node.names: + if nodename.asname: + self.import_aliases[nodename.asname] = nodename.name + self.imports.add(nodename.name) + self.__context['module'] = nodename.name + self.__runChecks("Import") + + def visit_ImportFrom(self, node): + """ + Public method defining a visitor for AST Import nodes. + + This adds relevant information about the node to + the context for use in tests which inspect imports. + + @param node reference to the node being inspected + @type ast.ImportFrom + """ + module = node.module + if module is None: + self.visit_Import(node) + return + + for nodename in node.names: + if nodename.asname: + self.import_aliases[nodename.asname] = ( + module + "." + nodename.name + ) + else: + # Even if import is not aliased we need an entry that maps + # name to module.name. For example, with 'from a import b' + # b should be aliased to the qualified name a.b + self.import_aliases[nodename.name] = ( + module + '.' + nodename.name) + self.imports.add(module + "." + nodename.name) + self.__context['module'] = module + self.__context['name'] = nodename.name + self.__runChecks("ImportFrom") + + def visit_Constant(self, node): + """ + Public method defining a visitor for Constant nodes. + + This calls the appropriate method for the node type. + It maintains compatibility with <3.6 and 3.8+ + + @param node reference to the node being inspected + @type ast.Constant + """ + if isinstance(node.value, str): + self.visit_Str(node) + elif isinstance(node.value, bytes): + self.visit_Bytes(node) + + def visit_Str(self, node): + """ + Public method defining a visitor for String nodes. + + This adds relevant information about node to + the context for use in tests which inspect strings. + + @param node reference to the node being inspected + @type ast.Str + """ + self.__context['str'] = node.s + if not isinstance(node._securityParent, ast.Expr): # docstring + self.__context['linerange'] = SecurityUtils.linerange_fix( + node._securityParent + ) + self.__runChecks("Str") + + def visit_Bytes(self, node): + """ + Public method defining a visitor for Bytes nodes. + + This adds relevant information about node to + the context for use in tests which inspect strings. + + @param node reference to the node being inspected + @type ast.Bytes + """ + self.__context['bytes'] = node.s + if not isinstance(node._securityParent, ast.Expr): # docstring + self.__context['linerange'] = SecurityUtils.linerange_fix( + node._securityParent + ) + self.__runChecks("Bytes") + def __preVisit(self, node): """ Private method to set up a context for the visit method. @param node node to base the context on @type ast.AST + @return flag indicating to visit the node + @rtype bool """ self.__context = {} self.__context['imports'] = self.imports @@ -110,7 +219,7 @@ if hasattr(node, 'lineno'): self.__context['lineno'] = node.lineno -## +## ## if node.lineno in self.nosec_lines: ## LOG.debug("skipped, nosec") ## self.metrics.note_nosec()