src/eric7/Plugins/CheckerPlugins/CodeStyleChecker/Security/SecurityUtils.py

branch
eric7
changeset 10507
d1c6608155ef
parent 10439
21c28b0f9e41
child 11090
f5f5f5803935
--- a/src/eric7/Plugins/CheckerPlugins/CodeStyleChecker/Security/SecurityUtils.py	Tue Jan 16 14:35:46 2024 +0100
+++ b/src/eric7/Plugins/CheckerPlugins/CodeStyleChecker/Security/SecurityUtils.py	Tue Jan 16 18:24:06 2024 +0100
@@ -183,6 +183,33 @@
     return obj
 
 
+def calcLineRange(node):
+    """
+    Function to calculate the line range for a subtree.
+
+    @param node node to calculate the line range for
+    @type ast.AST
+    @return tuple containing the start and end line of the subtree
+    @rtype tuple of (int, int)
+    """
+    if hasattr(node, "_securityLineRange"):
+        return node._securityLineRange
+
+    lines_min = 9999999999
+    lines_max = -1
+    if hasattr(node, "lineno"):
+        lines_min = node.lineno
+        lines_max = node.lineno
+    for n in ast.iter_child_nodes(node):
+        lines_minmax = calcLineRange(n)
+        lines_min = min(lines_min, lines_minmax[0])
+        lines_max = max(lines_max, lines_minmax[1])
+
+    node._securityLineRange = (lines_min, lines_max)
+
+    return (lines_min, lines_max)
+
+
 def linerange(node):
     """
     Function to get line number range from a node.
@@ -192,48 +219,55 @@
     @return list containing the line number range
     @rtype list of int
     """
-    strip = {"body": None, "orelse": None, "handlers": None, "finalbody": None}
-    for key in strip:
-        if hasattr(node, key):
-            strip[key] = getattr(node, key)
-            node.key = []
+    if hasattr(node, "lineno") and hasattr(node, "end_lineno"):
+        return list(range(node.lineno, node.end_lineno + 1))
+    else:
+        if hasattr(node, "_securityLineRangeStripped"):
+            lines_minmax = node._securityLineRangeStripped
+            return list(range(lines_minmax[0], lines_minmax[1] + 1))
 
-    lines_min = 9999999999
-    lines_max = -1
-    for n in ast.walk(node):
-        if hasattr(n, "lineno"):
-            lines_min = min(lines_min, n.lineno)
-            lines_max = max(lines_max, n.lineno)
-
-    for key in strip:
-        if strip[key] is not None:
-            node.key = strip[key]
-
-    if lines_max > -1:
-        return list(range(lines_min, lines_max + 1))
+        strip = {
+            "body": None,
+            "orelse": None,
+            "handlers": None,
+            "finalbody": None,
+        }
+        for key in strip:
+            if hasattr(node, key):
+                strip[key] = getattr(node, key)
+                setattr(node, key, [])
 
-    return [0, 1]
-
+        lines_min = 9999999999
+        lines_max = -1
+        if hasattr(node, "lineno"):
+            lines_min = node.lineno
+            lines_max = node.lineno
+        for n in ast.iter_child_nodes(node):
+            lines_minmax = calcLineRange(n)
+            lines_min = min(lines_min, lines_minmax[0])
+            lines_max = max(lines_max, lines_minmax[1])
 
-def linerange_fix(node):
-    """
-    Function to get a line number range working around a known Python bug
-    with multi-line strings.
+        for key in strip:
+            if strip[key] is not None:
+                setattr(node, key, strip[key])
 
-    @param node node to extract a line range from
-    @type ast.AST
-    @return list containing the line number range
-    @rtype list of int
-    """
-    # deal with multiline strings lineno behavior (Python issue #16806)
-    lines = linerange(node)
-    if hasattr(node, "_securitySibling") and hasattr(node._securitySibling, "lineno"):
-        start = min(lines)
-        delta = node._securitySibling.lineno - start
-        if delta > 1:
-            return list(range(start, node._securitySibling.lineno))
+        if lines_max == -1:
+            lines_min = 0
+            lines_max = 1
+
+        node._securityLineRangeStripped = (lines_min, lines_max)
 
-    return lines
+        lines = list(range(lines_min, lines_max + 1))
+        # deal with multi-line strings lineno behavior (Python issue #16806)
+        if hasattr(node, "_securitySibling") and hasattr(
+            node._securitySibling, "lineno"
+        ):
+            start = min(lines)
+            delta = node._securitySibling.lineno - start
+            if delta > 1:
+                return list(range(start, node._securitySibling.lineno))
+
+        return lines
 
 
 def escapedBytesRepresentation(b):

eric ide

mercurial