protected virtual object CompileArrayAccess(object output)
        {
            // This is to handle the last identifier
            SetContextualIdentifierHandler(CompileLastKeyWord, output);

            object right = CompileArrowFunctionIndexer(output);

            ClearContextualIdentifierHandler();
            Require(Token.Type.ClosingArrayIndex, "] Expected");

            Func <object> rightFunc = CompilerUtility.ForceGetFunction(right, _cdata);

            if (rightFunc != null)
            {
                right = rightFunc;
            }

            Type type = CompilerUtility.GetReturnType(right);

            if (typeof(IList).IsAssignableFrom(type))
            {
                output = CreateListAccessorReference(output, right);
            }
            else
            {
                output = CreateIntAccessorReference(output, right);
            }

            return(output);
        }
        protected virtual object CompileLastKeyWord(object left)
        {
            if (LookAhead(Token.Type.Dot, Token.Type.Identifier))
            {
                if (_tokens[_index + 1].text == "last")
                {
                    Step(); Step();
                }
                Func <object> arrayFunc = CompilerUtility.ForceGetFunction(left, _cdata);

                if (arrayFunc == null)
                {
                    return((Func <int>)(() =>
                    {
                        return ((IList)left).Count - 1;
                    }));
                }
                else
                {
                    return((Func <int>)(() =>
                    {
                        return ((IList)arrayFunc()).Count - 1;
                    }));
                }
            }

            return(null);
        }
        public override Func <T> CreateGetFunction <T>(CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction <object>(_accessor, cdata);

            if (accessorFunc == null)
            {
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    IList arr = System.Array.CreateInstance(_elemType, accessorCount);
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        arr[i] = ((IList)cdata._environment[_environmentIndex].data)[(int)list[i]];
                    }
                    return (T)arr;
                });
            }
            else
            {
                return(() =>
                {
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;

                    IList arr = System.Array.CreateInstance(_elemType, accessorCount);
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        arr[i] = ((IList)cdata._environment[_environmentIndex].data)[(int)list[i]];
                    }
                    return (T)arr;
                });
            }
        }
        public override Func <T> CreateGetFunction <T>(CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction(_accessor, cdata);
            Func <object> targetFunc   = (CompilerUtility.IsFunc(_targetObject)) ? (Func <object>)_targetObject : null;

            if (targetFunc == null && accessorFunc == null)
            {
                return(() =>
                {
                    return (T)((IList)_targetObject)[(int)_accessor];
                });
            }
            else if (targetFunc == null && accessorFunc != null)
            {
                return(() =>
                {
                    return (T)((IList)_targetObject)[(int)accessorFunc()];
                });
            }
            else if (targetFunc != null && accessorFunc == null)
            {
                return(() =>
                {
                    return (T)((IList)targetFunc())[(int)_accessor];
                });
            }
            else
            {
                return(() =>
                {
                    return (T)((IList)targetFunc())[(int)accessorFunc()];
                });
            }
        }
        protected virtual object CompileWhileStatement()
        {
            Require(Token.Type.OpenParenthesis, "Parenthesis Required");
            object condition = CompileExpression();

            Require(Token.Type.ClosingParethesis, ") Expected");
            object        statement     = CompileDeclaration();
            Func <object> whileFunc     = null;
            Func <object> blockFunc     = (Func <object>)statement;
            Func <bool>   conditionFunc = CompilerUtility.ForceGetFunction <bool>(condition, _cdata);

            if (conditionFunc != null)
            {
                whileFunc = () =>
                {
                    while (conditionFunc())
                    {
                        blockFunc();
                        if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Break) != 0)
                        {
                            _cdata._runtimeFlags = 0;
                            break;
                        }
                        if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Exit) != 0)
                        {
                            return(null);
                        }
                    }
                    return(null);
                };
            }
            else
            {
                whileFunc = () =>
                {
                    while ((bool)condition)
                    {
                        blockFunc();
                        if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Break) != 0)
                        {
                            _cdata._runtimeFlags = 0;
                            break;
                        }
                        if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Exit) != 0)
                        {
                            return(null);
                        }
                    }
                    return(null);
                };
            }

            return(whileFunc);
        }
示例#6
0
        protected virtual object CompileArrayLiteral()
        {
            if (MatchToken(Token.Type.ClosingArrayIndex))
            {
                return(new object[0]);
            }
            List <object> list    = new List <object>();
            Type          arrType = null;

            do
            {
                object  elem        = CompileAddition();
                Type    elemType    = CompilerUtility.GetReturnType(elem);
                TypeDef elemTypeDef = _cdata._assembly.GetTypeDef(elemType, false);

                if (arrType == null)
                {
                    arrType = elemType;
                }
                if (elemType == typeof(float) && arrType == typeof(int))
                {
                    arrType = typeof(float);
                }

                if (arrType != elemType)
                {
                    if (!(arrType == typeof(float) && elemType == typeof(int)) && !(arrType == typeof(object) || elemType == typeof(object)))
                    {
                        throw new Exception("All elements must be the same type: " + elemType.Name + " is not " + arrType.Name);
                    }
                }

                var elemFunc = CompilerUtility.ForceGetFunction(elem, _cdata);

                if (elemFunc != null)
                {
                    elem = elemFunc;
                }
                list.Add(elem);
            } while (!isAtEnd && MatchToken(Token.Type.Comma));

            TypeDef typeDef = _assembly.GetTypeDef(arrType, false);

            for (int i = 0; i < list.Count; i += 1)
            {
                list[i] = typeDef.Cast(list[i], _cdata);
            }

            Require(Token.Type.ClosingArrayIndex, "] Expected");

            return(typeDef.CreateArrayLiteral(list.ToArray(), _cdata));
        }
        protected virtual object BuildFunctionCall(object callingFunction)
        {
            // For now, every function call is a runtime reference so we do not have to worry about the rest
            List <object> argList = new List <object>();

            if (Peek().type != Token.Type.ClosingParethesis)
            {
                do
                {
                    object        expr = CompileExpression();
                    Func <object> func = null;
                    //Type returnType = CompilerUtility.GetReturnType(expr);
                    //TypeDef typeDef = _assembly.GetTypeDef(returnType);

                    func = CompilerUtility.ForceGetFunction(expr, _cdata);
                    if (func == null)
                    {
                        func = () => { return(expr); };
                    }
                    argList.Add(func);
                } while (MatchToken(Token.Type.Comma));
            }
            if (Step().type != Token.Type.ClosingParethesis)
            {
                throw new Exception(") expected after function call arguments");
            }

            RunTimeReference callingReference = callingFunction as RunTimeReference;

            if (callingReference != null)
            {
                Func <object> targetFunc = CompilerUtility.ForceGetFunction(callingReference.targetObject, _cdata);
                if (targetFunc == null)
                {
                    return(new MethodCall(callingReference.type, callingReference.identifer, callingReference.targetObject, argList.ToArray(), _cdata, callingReference.targetType));
                }
                else
                {
                    return(new MethodCall(callingReference.type, callingReference.identifer, targetFunc, argList.ToArray(), _cdata, callingReference.targetType));
                }
            }
            CompileTimeReference compileTimeReference = callingFunction as CompileTimeReference;

            if (compileTimeReference != null)
            {
                return(new FunctionCall(compileTimeReference.type, compileTimeReference.identifer, compileTimeReference.environmentIndex, argList.ToArray(), _cdata));
            }
            return(callingFunction);
        }
        public override Func <T> CreateModifyFunction <T>(object value, CompilerData cdata, Token.Type operation)
        {
            Type rtype = CompilerUtility.GetReturnType(value);

            Operation.BinaryOperationDelegate del = cdata._assembly.GetBinaryOperation(operation, type, rtype);

            // This section was made for runtime type inference
            // May cause some weird issues, definitely check this out if there are problems
            if (del == null && type != typeof(Object) && rtype == typeof(Object))
            {
                del = cdata._assembly.GetBinaryOperation(operation, type, type);
            }

            if (del == null && type == typeof(Object) && rtype != typeof(Object))
            {
                del = cdata._assembly.GetBinaryOperation(operation, rtype, rtype);
            }

            if (del == null)
            {
                throw new CompilationException("Cannot perform the operation " + operation.ToString() + " on " + type.Name + " and " + rtype.Name);
            }

            Func <object> accessorFunc = CompilerUtility.ForceGetFunction <object>(_accessor, cdata);

            object  func          = del(this, value, cdata);
            Type    returnType    = CompilerUtility.GetReturnType(func);
            TypeDef returnTypeDef = cdata._assembly.GetTypeDef(returnType);

            if (accessorFunc == null)
            {
                return(() =>
                {
                    object ob = returnTypeDef.CallFunction(func);
                    ((IList)(cdata._environment[_environmentIndex].data))[(int)_accessor] = ob;
                    return (T)ob;
                });
            }
            else
            {
                return(() =>
                {
                    object ob = returnTypeDef.CallFunction(func);
                    ((IList)(cdata._environment[_environmentIndex].data))[(int)accessorFunc()] = ob;
                    return (T)ob;
                });
            }
        }
示例#9
0
        public override Func <T> CreateModifyFunction <T>(object value, CompilerData cdata, Token.Type operation)
        {
            Type rtype = CompilerUtility.GetReturnType(value);

            Operation.BinaryOperationDelegate del = cdata._assembly.GetBinaryOperation(operation, type, rtype);

            // This section was made for runtime type inference
            // May cause some weird issues, definitely check this out if there are problems
            if (del == null && type != typeof(Object) && rtype == typeof(Object))
            {
                del = cdata._assembly.GetBinaryOperation(operation, type, type);
            }

            if (del == null && type == typeof(Object) && rtype != typeof(Object))
            {
                del = cdata._assembly.GetBinaryOperation(operation, rtype, rtype);
            }

            if (del == null)
            {
                throw new CompilationException("Cannot perform the operation " + operation.ToString() + " on " + type.Name + " and " + rtype.Name);
            }

            Func <object> targetFunc = CompilerUtility.ForceGetFunction <object>(_targetObject, cdata);

            object  func          = del(this, value, cdata);
            Type    returnType    = CompilerUtility.GetReturnType(func);
            TypeDef returnTypeDef = cdata._assembly.GetTypeDef(returnType);

            if (targetFunc == null)
            {
                return(() =>
                {
                    object ob = returnTypeDef.CallFunction(func);
                    return (T)RunTimeUtility.SetMemberValue(_targetObject, _identifer, cdata, ob);
                });
            }
            else
            {
                return(() =>
                {
                    object ob = returnTypeDef.CallFunction(func);
                    return (T)RunTimeUtility.SetMemberValue(targetFunc(), _identifer, cdata, ob);
                });
            }
        }
        protected virtual object CompileFunctionCall()
        {
            object left   = CompileIdentifier();
            object output = null;

            while (MatchToken(Token.Type.OpenParenthesis, Token.Type.Dot, Token.Type.IfDot, Token.Type.ArrayIndexBegin))
            {
                Token.Type op   = previous.type;
                int        line = UpdateLineNumber();
                if (output == null)
                {
                    output = left;
                }
                Type leftType = CompilerUtility.GetReturnType(output);

                if (leftType == null)
                {
                    throw RuntimeException.Create("Cannot call " + previous.text + " on NULL", line);
                }

                if (op == Token.Type.OpenParenthesis)
                {
                    output = BuildFunctionCall(output);
                }
                else if (op == Token.Type.Dot)
                {
                    Token         identifier   = Require(Token.Type.Identifier, "Identifier Expected");
                    Func <object> parentGetter = CompilerUtility.ForceGetFunction(output, _cdata);
                    if (leftType != typeof(object))
                    {
                        Type t = ReflectionUtility.GetMemberDataType(leftType, identifier.text);
                        output = new RunTimeReference(t, identifier.text, parentGetter, leftType);
                    }
                    else
                    {
                        output = new RunTimeReference(typeof(object), identifier.text, parentGetter, typeof(object));
                    }
                }
                else if (op == Token.Type.ArrayIndexBegin)
                {
                    output = CompileArrayAccess(output);
                }
            }

            return((output != null) ? (object)output : left);
        }
        public override Func <T> CreateSetFunction <T>(object value, CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction(_accessor, cdata);
            Func <T>      valueFunc    = CompilerUtility.ForceGetFunction <T>(value, cdata);

            if (valueFunc == null && accessorFunc == null)
            {
                T val = (T)value;
                return(() =>
                {
                    ((IList)(cdata._environment[_environmentIndex].data))[(int)_accessor] = val;
                    return (T)val;
                });
            }
            else if (valueFunc == null && accessorFunc != null)
            {
                T val = (T)value;
                return(() =>
                {
                    ((IList)(cdata._environment[_environmentIndex].data))[(int)accessorFunc()] = val;
                    return (T)val;
                });
            }
            if (valueFunc != null && accessorFunc == null)
            {
                return(() =>
                {
                    T val = (T)valueFunc();
                    ((IList)(cdata._environment[_environmentIndex].data))[(int)_accessor] = val;
                    return (T)val;
                });
            }
            else
            {
                return(() =>
                {
                    T val = (T)valueFunc();
                    ((IList)(cdata._environment[_environmentIndex].data))[(int)accessorFunc()] = val;
                    return (T)val;
                });
            }
        }
        public override Func <T> CreateGetFunction <T>(CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction <object>(_accessor, cdata);

            if (accessorFunc != null)
            {
                Type accessorFuncType = CompilerUtility.GetReturnType(accessorFunc);

                return(() =>
                {
                    return (T)((IList)cdata._environment[_environmentIndex].data)[(int)accessorFunc()];
                });
            }
            else
            {
                return(() =>
                {
                    return (T)((IList)cdata._environment[_environmentIndex].data)[(int)_accessor];
                });
            }
        }
示例#13
0
        public override Func <T> CreateSetFunction <T>(object value, CompilerData cdata)
        {
            Func <object> targetFunc = CompilerUtility.ForceGetFunction <object>(_targetObject, cdata);
            Func <T>      valueFunc  = CompilerUtility.ForceGetFunction <T>(value, cdata);

            if (targetFunc == null && valueFunc == null)
            {
                T val = (T)value;
                return(() =>
                {
                    return (T)RunTimeUtility.SetMemberValue(_targetObject, _identifer, cdata, val);
                });
            }
            else if (targetFunc == null && valueFunc != null)
            {
                return(() =>
                {
                    return (T)RunTimeUtility.SetMemberValue(_targetObject, _identifer, cdata, valueFunc());
                });
            }
            else if (targetFunc != null && valueFunc == null)
            {
                T val = (T)value;
                return(() =>
                {
                    return (T)RunTimeUtility.SetMemberValue(targetFunc(), _identifer, cdata, val);
                });
            }
            else
            {
                return(() =>
                {
                    return (T)RunTimeUtility.SetMemberValue(targetFunc(), _identifer, cdata, valueFunc());
                });
            }
        }
        protected virtual object CompileBlockStatement()
        {
            List <Func <object> > functions = new List <Func <object> >();

            _cdata._scopeResolver.Push();
            while (!isAtEnd && Peek().type != Token.Type.CloseBlock)
            {
                object compiled = CompileDeclaration();

                Func <object> function = CompilerUtility.ForceGetFunction(compiled, _cdata);
                if (function == null)
                {
                    function = () => { return(compiled); };
                }
                functions.Add(function);
            }
            Func <object>[] funcArray = functions.ToArray();

            Func <object> block = () =>
            {
                object output = null;
                for (int mn = 0; mn < funcArray.Length; mn += 1)
                {
                    output = funcArray[mn]();
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Break) != 0)
                    {
                        break;
                    }
                }
                return(output);
            };

            Require(Token.Type.CloseBlock, "Closing } Expected");
            _cdata._scopeResolver.Pop();
            return(block);
        }
        protected virtual object CompileIfStatement()
        {
            Require(Token.Type.OpenParenthesis, "Parenthesis Required");
            object condition = CompileAssignment();

            Require(Token.Type.ClosingParethesis, ") Expected");
            object statement = CompileDeclaration();

            Func <bool> conditionFunc = CompilerUtility.ForceGetFunction <bool>(condition, _cdata);

            if (conditionFunc == null)
            {
                conditionFunc = () => { return((bool)condition); };
            }

            Func <object> statementFunc = CompilerUtility.ForceGetFunction(statement, _cdata);

            if (statementFunc == null)
            {
                statementFunc = () => { return(statement); };
            }

            Func <object> elseFunc = null;
            Func <object> ifFunc   = null;

            if (MatchToken(Token.Type.Else))
            {
                if (MatchToken(Token.Type.If))
                {
                    object elseData = CompileIfStatement();
                    if (elseData.GetType() == typeof(Func <object>))
                    {
                        elseFunc = (Func <object>)elseData;
                    }
                }
                else
                {
                    object elseData = CompileDeclaration();
                    if (elseData.GetType() == typeof(Func <object>))
                    {
                        elseFunc = (Func <object>)elseData;
                    }
                }

                ifFunc = () =>
                {
                    if (conditionFunc())
                    {
                        statementFunc();
                    }
                    else
                    {
                        elseFunc();
                    }
                    return(null);
                };
            }
            else
            {
                ifFunc = () =>
                {
                    if ((bool)conditionFunc())
                    {
                        statementFunc();
                    }
                    return(null);
                };
            }

            return(ifFunc);
        }
        public override Func <T> CreateSetFunction <T>(object value, CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction(_accessor, cdata);
            Func <object> targetFunc   = CompilerUtility.ForceGetFunction(_targetObject, cdata);
            Func <object> valueFunc    = CompilerUtility.ForceGetFunction(value, cdata);

            if (valueFunc == null && targetFunc == null && accessorFunc == null)
            {
                return(() =>
                {
                    ((IList)(_targetObject))[(int)_accessor] = value;
                    return (T)value;
                });
            }
            else if (valueFunc == null && targetFunc == null && accessorFunc != null)
            {
                return(() =>
                {
                    ((IList)(_targetObject))[(int)accessorFunc()] = value;
                    return (T)value;
                });
            }
            else if (valueFunc == null && targetFunc != null && accessorFunc == null)
            {
                return(() =>
                {
                    ((IList)(targetFunc()))[(int)_accessor] = value;
                    return (T)value;
                });
            }
            else if (valueFunc == null && targetFunc != null && accessorFunc != null)
            {
                return(() =>
                {
                    ((IList)(targetFunc()))[(int)accessorFunc()] = value;
                    return (T)value;
                });
            }
            else if (valueFunc != null && targetFunc == null && accessorFunc == null)
            {
                return(() =>
                {
                    object val = valueFunc();
                    ((IList)(_targetObject))[(int)_accessor] = val;
                    return (T)val;
                });
            }
            else if (valueFunc != null && targetFunc == null && accessorFunc != null)
            {
                return(() =>
                {
                    object val = valueFunc();
                    ((IList)(_targetObject))[(int)accessorFunc()] = val;
                    return (T)val;
                });
            }
            else if (valueFunc != null && targetFunc != null && accessorFunc == null)
            {
                return(() =>
                {
                    object val = valueFunc();
                    ((IList)(targetFunc()))[(int)_accessor] = val;
                    return (T)val;
                });
            }
            else
            {
                return(() =>
                {
                    object val = valueFunc();
                    ((IList)(targetFunc()))[(int)accessorFunc()] = val;
                    return (T)val;
                });
            }
        }
示例#17
0
        /// <summary>
        /// Compile function declaration
        /// </summary>
        /// <param name="type"></param>
        /// <param name="identifier"></param>
        /// <returns></returns>
        protected virtual object CompileFunctionDeclaration(TypeDef type, string identifier, bool isArray = false)
        {
            string tempIdentifier = identifier;

            Require(Token.Type.OpenParenthesis, "( Expected");

            // Prebind the function to support recursion
            //_cdata._environment.Add(type.Cast((Func<object>)(() => { return null; }), _cdata));
            //int refIndex = _cdata._environment.Count - 1;
            //_cdata._scopeResolver.Add(identifier, refIndex);

            // Push local function scope
            _cdata._scopeResolver.AddScopeStack(tempIdentifier);
            _cdata._scopeResolver.SetScopeByID(tempIdentifier);

            // Process arguments
            if (Peek().type != Token.Type.ClosingParethesis)
            {
                int arrCount = 0;
                do
                {
                    CompileFunctionArgumentDeclaration();
                    arrCount += 1;
                }while (MatchToken(Token.Type.Comma));
                _cdata._scopeResolver.localArgumentCount = arrCount;
            }
            else
            {
                _cdata._scopeResolver.localArgumentCount = 0;
            }

            // continue function
            Require(Token.Type.ClosingParethesis, ") Expected");
            List <Func <object> > functions = new List <Func <object> >();

            Require(Token.Type.OpenBlock, "{ Expected");
            while (!isAtEnd && Peek().type != Token.Type.CloseBlock)
            {
                object        compiled = CompileDeclaration(false);
                Func <object> function = CompilerUtility.ForceGetFunction(compiled, _cdata);
                if (function == null && compiled != null)
                {
                    function = () => { return(compiled); };
                }
                if (function != null)
                {
                    functions.Add(function);
                }
            }
            _cdata._scopeResolver.SetScopeByID(ScopeResolver.GLOBAL_ID);
            Require(Token.Type.CloseBlock, "} Expected");

            Func <object>[] funcArray = functions.ToArray();

            Func <object> block = () =>
            {
                object output = null;
                for (int mn = 0; mn < funcArray.Length; mn += 1)
                {
                    output = funcArray[mn]();
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Break) != 0)
                    {
                        break;
                    }
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Continue) != 0)
                    {
                        _cdata._runtimeFlags ^= (int)CompilerData.ControlInstruction.Continue;
                        break;
                    }
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Exit) != 0)
                    {
                        _cdata._runtimeFlags ^= (int)CompilerData.ControlInstruction.Exit;
                        return(_cdata._returnValue);
                    }
                }
                return(output);
            };

            object func;

            if (isArray)
            {
                func = type.CastArray(block, _cdata);
            }
            else
            {
                func = type.Cast(block, _cdata);
            }
            int refIndex = _cdata.AddMemoryObject(func);

            _cdata._scopeResolver.Add(identifier, refIndex);

            return(null);
        }
        public override Func <T> CreateSetFunction <T>(object value, CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction(_accessor, cdata);
            Func <T>      valueFunc    = CompilerUtility.ForceGetFunction <T>(value, cdata);

            if (valueFunc == null && accessorFunc == null)
            {
                T     val           = (T)value;
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)cdata._environment[_environmentIndex].data)[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
            else if (valueFunc == null && accessorFunc != null)
            {
                T val = (T)value;
                return(() =>
                {
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;

                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)cdata._environment[_environmentIndex].data)[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
            if (valueFunc != null && accessorFunc == null)
            {
                T     val           = valueFunc();
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)cdata._environment[_environmentIndex].data)[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
            else
            {
                return(() =>
                {
                    T val = valueFunc();
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;

                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)cdata._environment[_environmentIndex].data)[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
        }
        protected virtual object CompileDimensionalIndexer()
        {
            object left   = CompileExpression();
            object output = left;

            if (MatchToken(Token.Type.Colon))
            {
                Type leftType = CompilerUtility.GetReturnType(left);
                if (leftType != typeof(Int32) && leftType != typeof(object))
                {
                    throw new Exception("Function is not supported for type: " + leftType.Name);
                }
                List <object> integerList = new List <object>();

                object right     = CompileExpression();
                Type   rightType = CompilerUtility.GetReturnType(right);

                if (rightType != typeof(Int32) && rightType != typeof(object))
                {
                    throw new Exception("Function is not supported for type: " + rightType.Name);
                }

                Func <int> leftFunc = CompilerUtility.ForceGetFunction <int>(left, _cdata);
                if (leftFunc != null)
                {
                    left = leftFunc;
                }
                integerList.Add(left);

                Func <int> rightFunc = CompilerUtility.ForceGetFunction <int>(right, _cdata);
                if (rightFunc != null)
                {
                    right = rightFunc;
                }
                integerList.Add(right);
                while (MatchToken(Token.Type.Comma))
                {
                    left     = CompileExpression();
                    leftFunc = CompilerUtility.ForceGetFunction <int>(left, _cdata);
                    if (leftFunc != null)
                    {
                        left = leftFunc;
                    }
                    integerList.Add(left);
                    if (MatchToken(Token.Type.Colon))
                    {
                        right     = CompileExpression();
                        rightFunc = CompilerUtility.ForceGetFunction <int>(right, _cdata);
                        if (rightFunc != null)
                        {
                            right = rightFunc;
                        }
                        integerList.Add(right);
                    }
                }

                return((Func <int>)(() =>
                {
                    int total = 0;
                    int dimensionSize = 1;
                    int count = integerList.Count;
                    for (int i = 0; i < count; i += 2)
                    {
                        Func <int> lFunc = integerList[i] as Func <int>;
                        if (lFunc != null)
                        {
                            total += lFunc() * dimensionSize;
                        }
                        else
                        {
                            Debug.Log(integerList[i]);
                            total += (int)integerList[i] * dimensionSize;
                        }
                        if (i + 1 < count)
                        {
                            Func <int> rFunc = integerList[i + 1] as Func <int>;
                            if (rFunc != null)
                            {
                                dimensionSize *= rFunc();
                            }
                            else
                            {
                                dimensionSize *= (int)integerList[i + 1];
                            }
                        }
                    }
                    return total;
                }));
            }

            return(output);
        }
        protected virtual object CompileForStatement()
        {
            _cdata._scopeResolver.Push();

            Require(Token.Type.OpenParenthesis, "( Expected");
            object initializer = CompileDeclaration();
            object condition   = CompileAssignment();

            Require(Token.Type.EOS, "; Expected");
            object incrementor = CompileExpression();

            Require(Token.Type.ClosingParethesis, ") Expected");
            Require(Token.Type.OpenBlock, "{ Expected");

            Func <object> initFunction        = CompilerUtility.ForceGetFunction(initializer, _cdata);
            Func <bool>   conditionFunction   = CompilerUtility.ForceGetFunction <bool>(condition, _cdata);
            Func <object> incrementorFunction = CompilerUtility.ForceGetFunction(incrementor, _cdata);

            if (initFunction == null && initializer != null)
            {
                initFunction = () => { return(initializer); };
            }
            if (conditionFunction == null)
            {
                if (condition != null)
                {
                    conditionFunction = () => { return((bool)condition); };
                }
                else
                {
                    conditionFunction = () => { return(true); };
                }
            }
            if (incrementorFunction == null && incrementor != null)
            {
                incrementorFunction = () => { return(incrementor); };
            }

            if (CompilerUtility.GetReturnType(conditionFunction) != typeof(bool))
            {
                throw new Exception("for loop condition must be a bool");
            }

            List <Func <object> > functions = new List <Func <object> >();

            while (!isAtEnd && Peek().type != Token.Type.CloseBlock)
            {
                object        compiled = CompileDeclaration();
                Func <object> function = CompilerUtility.ForceGetFunction(compiled, _cdata);
                if (function == null && compiled != null)
                {
                    function = () => { return(compiled); };
                }
                functions.Add(function);
            }

            Func <object>[] funcArray = functions.ToArray();

            Func <object> block = () =>
            {
                object output = null;
                for (int mn = 0; mn < funcArray.Length; mn += 1)
                {
                    output = funcArray[mn]();
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Break) != 0)
                    {
                        break;
                    }
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Continue) != 0)
                    {
                        _cdata._runtimeFlags = 0;
                        break;
                    }
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Exit) != 0)
                    {
                        return(null);
                    }
                }
                return(output);
            };

            Func <object> forFunc = () =>
            {
                for (initFunction(); conditionFunction(); incrementorFunction())
                {
                    block();
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Break) != 0)
                    {
                        _cdata._runtimeFlags = 0;
                        break;
                    }
                    if ((_cdata._runtimeFlags & (int)CompilerData.ControlInstruction.Exit) != 0)
                    {
                        return(null);
                    }
                }
                return(null);
            };

            Require(Token.Type.CloseBlock, "} Expected");

            _cdata._scopeResolver.Pop();
            return(forFunc);
        }
        public override Func <T> CreateGetFunction <T>(CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction(_accessor, cdata);
            Func <object> targetFunc   = (CompilerUtility.IsFunc(_targetObject)) ? (Func <object>)_targetObject : null;

            if (targetFunc == null && accessorFunc == null)
            {
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    Type et = (_elemType != typeof(object)) ? _elemType : _targetObject.GetType().GetElementType();
                    IList arr = System.Array.CreateInstance(et, accessorCount);
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        arr[i] = ((IList)_targetObject)[(int)list[i]];
                    }
                    return (T)arr;
                });
            }
            else if (targetFunc == null && accessorFunc != null)
            {
                return(() =>
                {
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;
                    Type et = (_elemType != typeof(object)) ? _elemType : _targetObject.GetType().GetElementType();
                    IList arr = System.Array.CreateInstance(et, accessorCount);
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        arr[i] = ((IList)_targetObject)[(int)list[i]];
                    }
                    return (T)arr;
                });
            }
            else if (targetFunc != null && accessorFunc == null)
            {
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    object targetObject = targetFunc();
                    Type et = (_elemType != typeof(object)) ? _elemType : targetObject.GetType().GetElementType();
                    IList arr = System.Array.CreateInstance(et, accessorCount);
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        arr[i] = ((IList)targetObject)[(int)list[i]];
                    }
                    return (T)arr;
                });
            }
            else
            {
                return(() =>
                {
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;
                    object targetObject = targetFunc();
                    Type et = (_elemType != typeof(object)) ? _elemType : targetObject.GetType().GetElementType();
                    IList arr = System.Array.CreateInstance(et, accessorCount);
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        arr[i] = ((IList)targetObject)[(int)list[i]];
                    }
                    return (T)arr;
                });
            }
        }
        public override Func <T> CreateSetFunction <T>(object value, CompilerData cdata)
        {
            Func <object> accessorFunc = CompilerUtility.ForceGetFunction(_accessor, cdata);
            Func <object> targetFunc   = CompilerUtility.ForceGetFunction(_targetObject, cdata);
            Func <object> valueFunc    = CompilerUtility.ForceGetFunction(value, cdata);

            if (valueFunc == null && targetFunc == null && accessorFunc == null)
            {
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)_targetObject)[(int)list[i]] = value;
                    }
                    return (T)value;
                });
            }
            else if (valueFunc == null && targetFunc == null && accessorFunc != null)
            {
                return(() =>
                {
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)_targetObject)[(int)list[i]] = value;
                    }
                    return (T)value;
                });
            }
            else if (valueFunc == null && targetFunc != null && accessorFunc == null)
            {
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    IList targetObject = (IList)targetFunc();
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        targetObject[(int)list[i]] = value;
                    }
                    return (T)value;
                });
            }
            else if (valueFunc == null && targetFunc != null && accessorFunc != null)
            {
                return(() =>
                {
                    IList targetObject = (IList)targetFunc();
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        targetObject[(int)list[i]] = value;
                    }
                    return (T)value;
                });
            }
            else if (valueFunc != null && targetFunc == null && accessorFunc == null)
            {
                IList targetObject  = (IList)targetFunc();
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    T val = (T)valueFunc();
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        targetObject[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
            else if (valueFunc != null && targetFunc == null && accessorFunc != null)
            {
                return(() =>
                {
                    T val = (T)valueFunc();
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        ((IList)_targetObject)[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
            else if (valueFunc != null && targetFunc != null && accessorFunc == null)
            {
                IList targetObject  = (IList)targetFunc();
                IList list          = _accessor as IList;
                int   accessorCount = list.Count;
                return(() =>
                {
                    T val = (T)valueFunc();
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        targetObject[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
            else
            {
                return(() =>
                {
                    IList targetObject = (IList)targetFunc();
                    T val = (T)valueFunc();
                    IList list = accessorFunc() as IList;
                    int accessorCount = list.Count;
                    for (int i = 0; i < accessorCount; i += 1)
                    {
                        targetObject[(int)list[i]] = val;
                    }
                    return (T)val;
                });
            }
        }