Browse Source

HPCC-10942 Fix some minor bugs found while trying to simplify processing

Prevent global(global(x)) being generated, and handle it correctly in the resourcing
if it does occur.  Could possibly have occured when generating a library.

Signed-off-by: Gavin Halliday <gavin.halliday@lexisnexis.com>
Gavin Halliday 11 years ago
parent
commit
c1213bd3f9
6 changed files with 36 additions and 11 deletions
  1. 11 0
      ecl/hql/hqlexpr.cpp
  2. 1 0
      ecl/hql/hqlexpr.hpp
  3. 4 0
      ecl/hql/hqlfold.cpp
  4. 3 3
      ecl/hqlcpp/hqlcpp.cpp
  5. 13 8
      ecl/hqlcpp/hqlresource.cpp
  6. 4 0
      ecl/hqlcpp/hqlttcpp.cpp

+ 11 - 0
ecl/hql/hqlexpr.cpp

@@ -12234,6 +12234,17 @@ bool isDummySerializeDeserialize(IHqlExpression * expr)
 }
 
 
+bool isRedundantGlobalScope(IHqlExpression * expr)
+{
+    assertex(expr->getOperator() == no_globalscope);
+    IHqlExpression * child = expr->queryChild(0);
+    if (child->getOperator() != no_globalscope)
+        return false;
+    if (expr->hasAttribute(optAtom) && !child->hasAttribute(optAtom))
+        return false;
+    return true;
+}
+
 bool isIndependentOfScope(IHqlExpression * expr)
 {
     return expr->isIndependentOfScope();

+ 1 - 0
ecl/hql/hqlexpr.hpp

@@ -1534,6 +1534,7 @@ extern HQL_API IHqlExpression * expandBetween(IHqlExpression * expr);
 extern HQL_API bool isAlwaysActiveRow(IHqlExpression * expr);
 extern HQL_API bool isAlwaysNewRow(IHqlExpression * expr);
 extern HQL_API IHqlExpression * ensureActiveRow(IHqlExpression * expr);
+extern HQL_API bool isRedundantGlobalScope(IHqlExpression * expr);
 extern HQL_API bool isIndependentOfScope(IHqlExpression * expr);
 extern HQL_API bool isActivityIndependentOfScope(IHqlExpression * expr);
 extern HQL_API bool exprReferencesDataset(IHqlExpression * expr, IHqlExpression * dataset);

+ 4 - 0
ecl/hql/hqlfold.cpp

@@ -3936,6 +3936,10 @@ IHqlExpression * NullFolderMixin::foldNullDataset(IHqlExpression * expr)
                 return removeParentNode(expr);
             break;
         }
+    case no_globalscope:
+        if (isRedundantGlobalScope(expr))
+            return removeParentNode(expr);
+        break;
     }
     return NULL;
 }

+ 3 - 3
ecl/hqlcpp/hqlcpp.cpp

@@ -3222,7 +3222,7 @@ void HqlCppTranslator::buildExpr(BuildCtx & ctx, IHqlExpression * expr, CHqlBoun
         tgt.expr.set(expr);
         return;
     case no_globalscope:
-        if (options.regressionTest)
+        if (options.regressionTest && !ctx.queryMatchExpr(globalContextMarkerExpr))
             throwUnexpected();
         buildExpr(ctx, expr->queryChild(0), tgt);
         return;
@@ -8032,8 +8032,8 @@ void HqlCppTranslator::expandSimpleOrder(IHqlExpression * left, IHqlExpression *
     {
         IHqlExpression * record = left->queryRecord();
         assertex(right->isDatarow() && (record == right->queryRecord()));
-        expandRowOrder(left, record, leftValues, !isActiveRow(left));
-        expandRowOrder(right, record, rightValues, !isActiveRow(right));
+        expandRowOrder(left, record, leftValues, !isActiveRow(left) && (left->getOperator() != no_select));
+        expandRowOrder(right, record, rightValues, !isActiveRow(right) && (right->getOperator() != no_select));
     }
     else
     {

+ 13 - 8
ecl/hqlcpp/hqlresource.cpp

@@ -2056,6 +2056,16 @@ inline bool projectSelectorDatasetToField(IHqlExpression * row)
     return ((row->getOperator() == no_selectnth) && getFieldCount(row->queryRecord()) > 1);
 }
 
+static IHqlExpression * skipScalarWrappers(IHqlExpression * value)
+{
+    loop
+    {
+        node_operator op = value->getOperator();
+        if ((op != no_globalscope) && (op != no_thisnode) && (op != no_evalonce))
+            return value;
+        value = value->queryChild(0);
+    }
+}
 
 static HqlTransformerInfo eclHoistLocatorInfo("EclHoistLocator");
 class EclHoistLocator : public NewHqlTransformer
@@ -2098,6 +2108,8 @@ public:
         unsigned match = matched.findOriginal(expr);
         if (match == NotFound)
         {
+            value = skipScalarWrappers(value);
+
             OwnedHqlExpr hoisted;
             IHqlExpression * projected = NULL;
             if (value->getOperator() == no_select)
@@ -4541,15 +4553,8 @@ protected:
 
 static IHqlExpression * getScalarReplacement(CChildDependent & cur, ResourcerInfo * hoistedInfo, IHqlExpression * replacement)
 {
-    IHqlExpression * value = cur.original;
     //First skip any wrappers which are there to cause things to be hoisted.
-    loop
-    {
-        node_operator op = value->getOperator();
-        if ((op != no_globalscope) && (op != no_thisnode) && (op != no_evalonce))
-            break;
-        value = value->queryChild(0);
-    }
+    IHqlExpression * value = skipScalarWrappers(cur.original);
 
     //Now modify the spilled result depending on how the spilled result was created (see EclHoistLocator::noteScalar() above)
     if (value->getOperator() == no_select)

+ 4 - 0
ecl/hqlcpp/hqlttcpp.cpp

@@ -7706,6 +7706,10 @@ IHqlExpression * NewScopeMigrateTransformer::createTransformed(IHqlExpression *
             }
             break;
         }
+    case no_globalscope:
+        if (isRedundantGlobalScope(transformed))
+            return LINK(transformed->queryChild(0));
+        break;
     }
     return transformed.getClear();
 }