refine the documentation, add extra warning messages
[lunaix-os.git] / lunaix-os / scripts / build-tools / lcfg2 / rewriter.py
index 4134bce7f62447ef155ea993257aba1c364ab185..9a42447eae54e4dd7087046c7afb7f1e81b18085 100644 (file)
@@ -1,8 +1,8 @@
 import ast
 
-from lib.utils  import Schema
+from lib.utils  import Schema, SourceLogger
 from .lazy       import Lazy
-from .common     import NodeProperty
+from .common     import NodeProperty, NodeInverseDependency
 
 class RewriteRule:
     MaybeBuiltin = Schema(
@@ -33,6 +33,16 @@ class ConfigNodeASTRewriter(ast.NodeTransformer):
 
         self.__when_epxr = None
 
+    def __put_linkage(self, to_node, item):
+        node = self.__cfg_node._env.get_node(to_node)
+        link = NodeProperty.Linkage[node]
+        
+        if not link:
+            link = NodeInverseDependency()
+            NodeProperty.Linkage[node] = link
+        
+        link.add_linkage(self.__cfg_node._name, ast.unparse(item))
+
     def __subscript_accessor(self, name, ctx, token):
         return ast.Subscript(
             value=ast.Name("__lzLut__", ctx=ast.Load()),
@@ -67,7 +77,7 @@ class ConfigNodeASTRewriter(ast.NodeTransformer):
 
         if RewriteRule.WhenToggler != node:
             raise cfgn.config_error(
-                f"invalid when(...) expression: {ast.unparse(node)}")
+                f"when(...): invalid expression: {ast.unparse(node)}")
 
         if RewriteRule.WhenTogglerItem == node:
             and_list.append(node)
@@ -77,10 +87,16 @@ class ConfigNodeASTRewriter(ast.NodeTransformer):
         for i in range(len(and_list)):
             item = and_list[i]
             operator = item.ops[0]
+
+            if RewriteRule.WhenTogglerItem != item:
+                raise cfgn.config_error(
+                        f"when(...): non-trivial subclause : {ast.unparse(node)}")
             
             name = Lazy.from_type(cfgn, Lazy.NodeValue, item.left.id)
             acc = self.__subscript_accessor(name, ast.Load(), node)
             
+            self.__put_linkage(item.left.id, item)
+
             if isinstance(operator, ast.Is):
                 operator = ast.Eq()
             else:
@@ -122,7 +138,11 @@ class ConfigNodeASTRewriter(ast.NodeTransformer):
         return None
     
     def visit_Return(self, node):
-        if NodeProperty.WhenToggle[self.__cfg_node]:
+        if self.__when_epxr:
+            SourceLogger.warn(self.__cfg_node, node, 
+                              "mixed use of `return` and `when` directive. "
+                              "`when` have higher precedence than `return`. "
+                              "consider remove `return` to avoid confusion")
             return None
         return self.generic_visit(node)