Index: trunk/src/VBox/Storage/testcase/VDScript.cpp
===================================================================
--- trunk/src/VBox/Storage/testcase/VDScript.cpp	(revision 44842)
+++ trunk/src/VBox/Storage/testcase/VDScript.cpp	(revision 44855)
@@ -2366,4 +2366,6 @@
                         rc = vdScriptParserError(pThis, VERR_INVALID_PARAMETER, RT_SRC_POS, "Parser: Expected \";\", got ...\n");
                 }
+                else
+                    pAstNodeStmt->pExpr = NULL; /* No expression for return. */
             }
             else
Index: trunk/src/VBox/Storage/testcase/VDScriptAst.cpp
===================================================================
--- trunk/src/VBox/Storage/testcase/VDScriptAst.cpp	(revision 44842)
+++ trunk/src/VBox/Storage/testcase/VDScriptAst.cpp	(revision 44855)
@@ -24,36 +24,233 @@
 #include "VDScriptAst.h"
 
+/**
+ * Put all child nodes of the given expression AST node onto the given to free list.
+ *
+ * @returns nothing.
+ * @param   pList    The free list to append everything to.
+ * @param   pAstNode The expression node to free.
+ */
+static void vdScriptAStNodeExpressionPutOnFreeList(PRTLISTANCHOR pList, PVDSCRIPTASTCORE pAstNode)
+{
+    AssertMsgReturnVoid(pAstNode->enmClass == VDSCRIPTASTCLASS_EXPRESSION,
+                        ("Given AST node is not a statement\n"));
+
+    PVDSCRIPTASTEXPR pExpr = (PVDSCRIPTASTEXPR)pAstNode;
+    switch (pExpr->enmType)
+    {
+        case VDSCRIPTEXPRTYPE_PRIMARY_NUMCONST:
+        case VDSCRIPTEXPRTYPE_PRIMARY_STRINGCONST:
+        case VDSCRIPTEXPRTYPE_PRIMARY_IDENTIFIER:
+        case VDSCRIPTEXPRTYPE_ASSIGNMENT_LIST:
+        case VDSCRIPTEXPRTYPE_POSTFIX_INCREMENT:
+        case VDSCRIPTEXPRTYPE_POSTFIX_DECREMENT:
+        case VDSCRIPTEXPRTYPE_POSTFIX_FNCALL:
+        case VDSCRIPTEXPRTYPE_UNARY_INCREMENT:
+        case VDSCRIPTEXPRTYPE_UNARY_DECREMENT:
+        case VDSCRIPTEXPRTYPE_UNARY_POSSIGN:
+        case VDSCRIPTEXPRTYPE_UNARY_NEGSIGN:
+        case VDSCRIPTEXPRTYPE_UNARY_INVERT:
+        case VDSCRIPTEXPRTYPE_UNARY_NEGATE:
+        case VDSCRIPTEXPRTYPE_MULTIPLICATION:
+        case VDSCRIPTEXPRTYPE_DIVISION:
+        case VDSCRIPTEXPRTYPE_MODULUS:
+        case VDSCRIPTEXPRTYPE_ADDITION:
+        case VDSCRIPTEXPRTYPE_SUBTRACTION:
+        case VDSCRIPTEXPRTYPE_LSR:
+        case VDSCRIPTEXPRTYPE_LSL:
+        case VDSCRIPTEXPRTYPE_LOWER:
+        case VDSCRIPTEXPRTYPE_HIGHER:
+        case VDSCRIPTEXPRTYPE_LOWEREQUAL:
+        case VDSCRIPTEXPRTYPE_HIGHEREQUAL:
+        case VDSCRIPTEXPRTYPE_EQUAL:
+        case VDSCRIPTEXPRTYPE_NOTEQUAL:
+        case VDSCRIPTEXPRTYPE_BITWISE_AND:
+        case VDSCRIPTEXPRTYPE_BITWISE_XOR:
+        case VDSCRIPTEXPRTYPE_BITWISE_OR:
+        case VDSCRIPTEXPRTYPE_LOGICAL_AND:
+        case VDSCRIPTEXPRTYPE_LOGICAL_OR:
+        case VDSCRIPTEXPRTYPE_ASSIGN:
+        case VDSCRIPTEXPRTYPE_ASSIGN_MULT:
+        case VDSCRIPTEXPRTYPE_ASSIGN_DIV:
+        case VDSCRIPTEXPRTYPE_ASSIGN_MOD:
+        case VDSCRIPTEXPRTYPE_ASSIGN_ADD:
+        case VDSCRIPTEXPRTYPE_ASSIGN_SUB:
+        case VDSCRIPTEXPRTYPE_ASSIGN_LSL:
+        case VDSCRIPTEXPRTYPE_ASSIGN_LSR:
+        case VDSCRIPTEXPRTYPE_ASSIGN_AND:
+        case VDSCRIPTEXPRTYPE_ASSIGN_XOR:
+        case VDSCRIPTEXPRTYPE_ASSIGN_OR:
+        case VDSCRIPTEXPRTYPE_INVALID:
+        default:
+            AssertMsgFailedReturnVoid(("Invalid AST node expression type %d\n",
+                                       pExpr->enmType));
+    }
+}
+
+/**
+ * Free a given statement AST node and put everything on the given to free list.
+ *
+ * @returns nothing.
+ * @param   pList    The free list to append everything to.
+ * @param   pAstNode The statement node to free.
+ */
+static void vdScriptAstNodeStatmentPutOnFreeList(PRTLISTANCHOR pList, PVDSCRIPTASTCORE pAstNode)
+{
+    AssertMsgReturnVoid(pAstNode->enmClass == VDSCRIPTASTCLASS_STATEMENT,
+                        ("Given AST node is not a statement\n"));
+
+    PVDSCRIPTASTSTMT pStmt = (PVDSCRIPTASTSTMT)pAstNode;
+    switch (pStmt->enmStmtType)
+    {
+        case VDSCRIPTSTMTTYPE_COMPOUND:
+        {
+            /* Put all declarations on the to free list. */
+            while (!RTListIsEmpty(&pStmt->Compound.ListDecls))
+            {
+                PVDSCRIPTASTCORE pNode = RTListGetFirst(&pStmt->Compound.ListDecls, VDSCRIPTASTCORE, ListNode);
+                RTListNodeRemove(&pNode->ListNode);
+                RTListAppend(pList, &pNode->ListNode);
+            }
+
+            /* Put all statements on the to free list. */
+            while (!RTListIsEmpty(&pStmt->Compound.ListStmts))
+            {
+                PVDSCRIPTASTCORE pNode = RTListGetFirst(&pStmt->Compound.ListDecls, VDSCRIPTASTCORE, ListNode);
+                RTListNodeRemove(&pNode->ListNode);
+                RTListAppend(pList, &pNode->ListNode);
+            }
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_EXPRESSION:
+        {
+            RTListAppend(pList, &pStmt->pExpr->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_IF:
+        {
+            RTListAppend(pList, &pStmt->If.pCond->Core.ListNode);
+            RTListAppend(pList, &pStmt->If.pTrueStmt->Core.ListNode);
+            if (pStmt->If.pElseStmt)
+                RTListAppend(pList, &pStmt->If.pElseStmt->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_SWITCH:
+        {
+            RTListAppend(pList, &pStmt->Switch.pCond->Core.ListNode);
+            RTListAppend(pList, &pStmt->Switch.pStmt->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_WHILE:
+        {
+            RTListAppend(pList, &pStmt->While.pCond->Core.ListNode);
+            RTListAppend(pList, &pStmt->While.pStmt->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_FOR:
+        {
+            RTListAppend(pList, &pStmt->For.pExprStart->Core.ListNode);
+            RTListAppend(pList, &pStmt->For.pExprCond->Core.ListNode);
+            RTListAppend(pList, &pStmt->For.pExpr3->Core.ListNode);
+            RTListAppend(pList, &pStmt->For.pStmt->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_RETURN:
+        {
+            if (pStmt->pExpr)
+                RTListAppend(pList, &pStmt->pExpr->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_CASE:
+        {
+            RTListAppend(pList, &pStmt->Case.pExpr->Core.ListNode);
+            RTListAppend(pList, &pStmt->Case.pStmt->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_DEFAULT:
+        {
+            RTListAppend(pList, &pStmt->Case.pStmt->Core.ListNode);
+            break;
+        }
+        case VDSCRIPTSTMTTYPE_CONTINUE:
+        case VDSCRIPTSTMTTYPE_BREAK:
+            break;
+        case VDSCRIPTSTMTTYPE_INVALID:
+        default:
+            AssertMsgFailedReturnVoid(("Invalid AST node statement type %d\n",
+                                       pStmt->enmStmtType));
+    } 
+}
+
 DECLHIDDEN(void) vdScriptAstNodeFree(PVDSCRIPTASTCORE pAstNode)
 {
-    switch (pAstNode->enmClass)
-    {
-        case VDSCRIPTASTCLASS_FUNCTION:
-        {
-            /** @todo. */
-            break;
-        }
-        case VDSCRIPTASTCLASS_FUNCTIONARG:
-        {
-            PVDSCRIPTASTFNARG pAstNodeArg = (PVDSCRIPTASTFNARG)pAstNode;
-            if (pAstNodeArg->pType)
-                vdScriptAstNodeFree(&pAstNodeArg->pType->Core);
-            if (pAstNodeArg->pArgIde)
-                vdScriptAstNodeFree(&pAstNodeArg->pArgIde->Core);
-            break;
-        }
-        case VDSCRIPTASTCLASS_IDENTIFIER:
-            break;
-        case VDSCRIPTASTCLASS_DECLARATION:
-            break;
-        case VDSCRIPTASTCLASS_STATEMENT:
-            break;
-        case VDSCRIPTASTCLASS_EXPRESSION:
-            break;
-        case VDSCRIPTASTCLASS_INVALID:
-        default:
-            AssertMsgFailedReturnVoid(("Invalid AST node class given %d\n", pAstNode->enmClass));
-    }
-
-    RTMemFree(pAstNode);
+    RTLISTANCHOR ListFree;
+
+    /*
+     * The node is not allowed to be part of a list because we need it
+     * for the nodes to free list.
+     */
+    Assert(RTListIsEmpty(&pAstNode->ListNode));
+    RTListInit(&ListFree);
+    RTListAppend(&ListFree, &pAstNode->ListNode);
+
+    do
+    {
+        pAstNode = RTListGetFirst(&ListFree, VDSCRIPTASTCORE, ListNode);
+        RTListNodeRemove(&pAstNode->ListNode);
+
+        switch (pAstNode->enmClass)
+        {
+            case VDSCRIPTASTCLASS_FUNCTION:
+            {
+                PVDSCRIPTASTFN pFn = (PVDSCRIPTASTFN)pAstNode;
+
+                if (pFn->pRetType)
+                    RTListAppend(&ListFree, &pFn->pRetType->Core.ListNode);
+                if (pFn->pFnIde)
+                    RTListAppend(&ListFree, &pFn->pFnIde->Core.ListNode);
+
+                /* Put argument list on the to free list. */
+                while (!RTListIsEmpty(&pFn->ListArgs))
+                {
+                    PVDSCRIPTASTCORE pArg = RTListGetFirst(&pFn->ListArgs, VDSCRIPTASTCORE, ListNode);
+                    RTListNodeRemove(&pArg->ListNode);
+                    RTListAppend(&ListFree, &pArg->ListNode);
+                }
+
+                /* Put compound statement onto the list. */
+                RTListAppend(&ListFree, &pFn->pCompoundStmts->Core.ListNode);
+                break;
+            }
+            case VDSCRIPTASTCLASS_FUNCTIONARG:
+            {
+                PVDSCRIPTASTFNARG pAstNodeArg = (PVDSCRIPTASTFNARG)pAstNode;
+                if (pAstNodeArg->pType)
+                    RTListAppend(&ListFree, &pAstNodeArg->pType->Core.ListNode);
+                if (pAstNodeArg->pArgIde)
+                    RTListAppend(&ListFree, &pAstNodeArg->pArgIde->Core.ListNode);
+                break;
+            }
+            case VDSCRIPTASTCLASS_IDENTIFIER:
+                break;
+            case VDSCRIPTASTCLASS_DECLARATION:
+                break;
+            case VDSCRIPTASTCLASS_STATEMENT:
+            {
+                vdScriptAstNodeStatmentPutOnFreeList(&ListFree, pAstNode);
+                break;
+            }
+            case VDSCRIPTASTCLASS_EXPRESSION:
+            {
+                vdScriptAStNodeExpressionPutOnFreeList(&ListFree, pAstNode);
+                break;
+            }
+            case VDSCRIPTASTCLASS_INVALID:
+            default:
+                AssertMsgFailedReturnVoid(("Invalid AST node class given %d\n", pAstNode->enmClass));
+        }
+
+        RTMemFree(pAstNode);
+    } while (!RTListIsEmpty(&ListFree));
+
 }
 
Index: trunk/src/VBox/Storage/testcase/VDScriptAst.h
===================================================================
--- trunk/src/VBox/Storage/testcase/VDScriptAst.h	(revision 44842)
+++ trunk/src/VBox/Storage/testcase/VDScriptAst.h	(revision 44855)
@@ -121,8 +121,6 @@
     /** Identifier. */
     VDSCRIPTEXPRTYPE_PRIMARY_IDENTIFIER,
-    /** List of assignment expressions. */
+    /** List of assignment expressions as in a = b = c = ... . */
     VDSCRIPTEXPRTYPE_ASSIGNMENT_LIST,
-    /** Assignment expression. */
-    VDSCRIPTEXPRTYPE_ASSIGNMENT,
     /** Postfix increment expression. */
     VDSCRIPTEXPRTYPE_POSTFIX_INCREMENT,
@@ -315,6 +313,4 @@
     /** Invalid. */
     VDSCRIPTSTMTTYPE_INVALID = 0,
-    /** Labeled statement. */
-    VDSCRIPTSTMTTYPE_LABELED,
     /** Compound statement. */
     VDSCRIPTSTMTTYPE_COMPOUND,
@@ -357,12 +353,4 @@
     union
     {
-        /** Labeled statement (case, default). */
-        struct
-        {
-            /** Conditional expression, if NULL this is a statement for "default" */
-            PVDSCRIPTASTEXPR   pCondExpr;
-            /** Statement to execute. */
-            PVDSCRIPTASTSTMT   pExec;
-        } Labeled;
         /** Compound statement. */
         struct
@@ -373,5 +361,5 @@
             RTLISTANCHOR       ListStmts;
         } Compound;
-        /** case statement. */
+        /** case, default statement. */
         struct
         {
