DAG-execplan: add a test case, but more tests are required
diff --git a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionBlock.java b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionBlock.java
index 378726b..250b842 100644
--- a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionBlock.java
+++ b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionBlock.java
@@ -54,7 +54,11 @@
   }
 
   public void setPlan(LogicalNode plan) {
-    executionPlan.setPlan(plan);
+    try {
+      executionPlan.setPlan((LogicalNode) plan.clone());
+    } catch (CloneNotSupportedException e) {
+
+    }
   }
 
   public void setPlan(ExecutionPlan plan) {
diff --git a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionPlan.java b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionPlan.java
index 84780c6..f199be7 100644
--- a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionPlan.java
+++ b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/ExecutionPlan.java
@@ -88,20 +88,29 @@
     public LogicalNode toLinkedLogicalNode() {
       LogicalNode[] nodes = this.nodes.toArray(new LogicalNode[this.nodes.size()]);
 
-      for (int i = 0; i < nodes.length;) {
+      toLinkedLogicalNode(nodes, 0);
+      return nodes[0];
+    }
+
+    private int toLinkedLogicalNode(LogicalNode[] nodes, int i) {
+      if (i < nodes.length) {
         if (nodes[i] instanceof UnaryNode) {
-          ((UnaryNode)nodes[i]).setChild(nodes[++i]);
+          ((UnaryNode)nodes[i]).setChild(nodes[i+1]);
+          return toLinkedLogicalNode(nodes, i + 1);
         } else if (nodes[i] instanceof BinaryNode) {
           ((BinaryNode)nodes[i]).setLeftChild(nodes[i+1]);
-          ((BinaryNode)nodes[i]).setRightChild(nodes[i+2]);
-          i += 2;
+          int rightChildIndex = toLinkedLogicalNode(nodes, i+1);
+          ((BinaryNode)nodes[i]).setRightChild(nodes[rightChildIndex]);
+          return toLinkedLogicalNode(nodes, rightChildIndex);
         } else if (nodes[i] instanceof TableSubQueryNode) {
-          ((TableSubQueryNode)nodes[i]).setSubQuery(nodes[++i]);
+          ((TableSubQueryNode)nodes[i]).setSubQuery(nodes[i+1]);
+          return toLinkedLogicalNode(nodes, i+1);
         } else {
-          i++;
+          return i+1;
         }
+      } else {
+        return -1;
       }
-      return nodes[0];
     }
 
     public LogicalNode getRootNode() {
diff --git a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/GlobalPlanner.java b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/GlobalPlanner.java
index fe7d177..b9206a1 100644
--- a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/GlobalPlanner.java
+++ b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/global/GlobalPlanner.java
@@ -579,11 +579,11 @@
 
     private LogicalNode handleUnaryNode(GlobalPlanContext context, LogicalNode child, LogicalNode node) {
       ExecutionBlock execBlock = context.execBlockMap.remove(child.getPID());
-      if (node instanceof UnaryNode) {
-        ((UnaryNode)node).setChild(execBlock.getPlan().getFirstPlanGroup().toLinkedLogicalNode());
-      } else if (node instanceof TableSubQueryNode) {
-        ((TableSubQueryNode) node).setSubQuery(execBlock.getPlan().getFirstPlanGroup().toLinkedLogicalNode());
-      }
+//      if (node instanceof UnaryNode) {
+//        ((UnaryNode)node).setChild(execBlock.getPlan().getFirstPlanGroup().toLinkedLogicalNode());
+//      } else if (node instanceof TableSubQueryNode) {
+//        ((TableSubQueryNode) node).setSubQuery(execBlock.getPlan().getFirstPlanGroup().toLinkedLogicalNode());
+//      }
       execBlock.setPlan(node);
       context.execBlockMap.put(node.getPID(), execBlock);
 
diff --git a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/logical/TableSubQueryNode.java b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/logical/TableSubQueryNode.java
index 49a4b68..bf93f99 100644
--- a/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/logical/TableSubQueryNode.java
+++ b/tajo-core/tajo-core-backend/src/main/java/org/apache/tajo/engine/planner/logical/TableSubQueryNode.java
@@ -24,6 +24,7 @@
 import org.apache.tajo.engine.planner.PlanString;
 import org.apache.tajo.engine.planner.PlannerUtil;
 import org.apache.tajo.engine.planner.Target;
+import org.apache.tajo.util.TUtil;
 
 public class TableSubQueryNode extends RelationNode implements Projectable {
   @Expose private String tableName;
@@ -97,15 +98,26 @@
   public boolean equals(Object object) {
     if (object instanceof TableSubQueryNode) {
       TableSubQueryNode another = (TableSubQueryNode) object;
-      return tableName.equals(another.tableName) && subQuery.equals(another.subQuery);
+      return tableName.equals(another.tableName) && TUtil.checkEquals(this.targets, another.targets);
+//          && subQuery.equals(another.subQuery);
     }
 
     return false;
   }
 
   @Override
+  public boolean deepEquals(Object o) {
+    if (o instanceof TableSubQueryNode) {
+      TableSubQueryNode other = (TableSubQueryNode) o;
+      return equals(o) && subQuery.deepEquals(other.subQuery);
+    }
+    return false;
+  }
+
+  @Override
   public Object clone() throws CloneNotSupportedException {
     TableSubQueryNode newTableSubQueryNode = (TableSubQueryNode) super.clone();
+    newTableSubQueryNode.subQuery = this.subQuery == null ? null : (LogicalNode) this.subQuery.clone();
     newTableSubQueryNode.tableName = tableName;
     return newTableSubQueryNode;
   }
diff --git a/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/planner/global/TestExecutionPlan.java b/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/planner/global/TestExecutionPlan.java
index 71d5a9c..981bf9a 100644
--- a/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/planner/global/TestExecutionPlan.java
+++ b/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/planner/global/TestExecutionPlan.java
@@ -102,4 +102,34 @@
     assertEquals(3, plan.getParentCount(scanNode));
 
   }
+
+  @Test
+  public void testToLinkedLogicalNode() throws CloneNotSupportedException {
+    Schema schema = new Schema();
+    schema.addColumn("id", Type.INT4);
+    schema.addColumn("name", Type.TEXT);
+    schema.addColumn("age", Type.INT2);
+    PIDFactory pidFactory = new PIDFactory();
+
+    LogicalRootNode root1 = new LogicalRootNode(pidFactory.newPID());
+    GroupbyNode groupbyNode = new GroupbyNode(pidFactory.newPID(),
+        new Column[]{schema.getColumn(1), schema.getColumn(2)});
+    ScanNode scanNode = new ScanNode(pidFactory.newPID(),
+        CatalogUtil.newTableDesc("in", schema, CatalogUtil.newTableMeta(StoreType.CSV), new Path("in")));
+    ScanNode scanNode2 = new ScanNode(pidFactory.newPID(),
+        CatalogUtil.newTableDesc("in", schema, CatalogUtil.newTableMeta(StoreType.CSV), new Path("in")));
+    UnionNode unionNode = new UnionNode(pidFactory.newPID(), groupbyNode, scanNode2);
+    unionNode.setOutSchema(schema);
+    unionNode.setInSchema(schema);
+    TableSubQueryNode tableSubQueryNode = new TableSubQueryNode(pidFactory.newPID(), "test", unionNode);
+    root1.setChild(tableSubQueryNode);
+    groupbyNode.setChild(scanNode);
+
+    LogicalRootNode clone = (LogicalRootNode) root1.clone();
+
+    ExecutionPlan plan = new ExecutionPlan(pidFactory);
+    plan.addPlan(root1);
+
+    assertTrue(clone.getChild().deepEquals(plan.getFirstPlanGroup().toLinkedLogicalNode()));
+  }
 }
diff --git a/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/query/TestCaseByCases.java b/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/query/TestCaseByCases.java
index 5885f10..e3e29c2 100644
--- a/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/query/TestCaseByCases.java
+++ b/tajo-core/tajo-core-backend/src/test/java/org/apache/tajo/engine/query/TestCaseByCases.java
@@ -79,4 +79,32 @@
       res.close();
     }
   }
+
+  @Test
+  public final void testTAJO266Case() throws Exception {
+    ResultSet res = tpch.execute(FileUtil.readTextFile(new File("src/test/queries/tajo266_case.sql")));
+    try {
+      assertTrue(res.next());
+      assertEquals("1", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("1", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("1", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("1", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("2", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("3", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("3", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("3", res.getString(1));
+      assertTrue(res.next());
+      assertEquals("3", res.getString(1));
+      assertFalse(res.next());
+    } finally {
+      res.close();
+    }
+  }
 }
diff --git a/tajo-core/tajo-core-backend/src/test/queries/tajo266_case.sql b/tajo-core/tajo-core-backend/src/test/queries/tajo266_case.sql
new file mode 100644
index 0000000..5434291
--- /dev/null
+++ b/tajo-core/tajo-core-backend/src/test/queries/tajo266_case.sql
@@ -0,0 +1,9 @@
+SELECT
+  l1.l_orderkey
+
+FROM
+  lineitem AS l1
+
+  INNER JOIN lineitem AS l2
+
+  ON l1.l_orderkey = l2.l_orderkey;
\ No newline at end of file