コード例 #1
0
        //////////////////////////////////////////////

        private static Boolean ExitCurrentContext(
            PainContext PainContext,
            Object Result)
        {
            PainState context = PainContext.CurrentState;

            context.CurrentLineID = Guid.Empty;

            // jeśli został tylko ostatni główny context
            if (PainContext.Stack.Count == 1)
            {
                PainContext.Result     = Result;
                PainContext.IsFinished = true;
            }
            else
            {
                PainContext.PopContext();
                if (PainContext.CurrentExpressionState != null)
                {
                    PainContext.CurrentExpressionState.PushValue(Result);
                }
            }

            return(true);
        }
コード例 #2
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
        public static Object Eval(
            this PainContext PainContext)
        {
            while (true)
            {
                if (PainContext.IsFinished)
                {
                    if (PainContext.Error != null)
                    {
                        throw PainContext.Error;
                    }
                    break;
                }

                try
                {
                    Boolean result = PainLineRunner.
                                     ExecuteNext(PainContext);

                    if (PainContext.BreakEveryLine && result)
                    {
                        break;
                    }
                }
                catch
                {
                    throw;
                }
            }
            return(PainContext.Result);
        }
コード例 #3
0
        private static Boolean ExitCurrentContext(
            PainContext PainContext)
        {
            PainState state = PainContext.CurrentState;

            state.CurrentLineID = Guid.Empty;

            Object result = null;

            if (state != null &&
                state.ContextType == PainContextType.CLASS)
            {
                result = state.Object;
            }

            // jeśli został tylko ostatni główny context
            if (PainContext.Stack.Count == 1)
            {
                PainContext.Result     = result;
                PainContext.IsFinished = true;
            }
            else
            {
                PainContext.PopContext();
                if (PainContext.CurrentExpressionState != null)
                {
                    PainContext.CurrentExpressionState.PushValue(result);
                }
            }

            return(true);
        }
コード例 #4
0
        public static Boolean NextStep(
            PainContext PainContext)
        {
            if (PainContext == null || PainContext.CurrentState == null)
            {
                return(true);
            }

            ExpressionContext curExpressionContext = PainContext.
                                                     CurrentState.
                                                     ExpressionContext;

            ExpressionGroup curExpressionGroup = curExpressionContext.
                                                 ExpressionGroup;

            if (curExpressionContext == null ||
                curExpressionContext.IsFinished ||
                curExpressionContext.Current == null)
            {
                return(true);
            }

            if (curExpressionContext.Current.Expression.IsOnpExecution)
            {
                return(ExpressionRunnerOnp.EvaluateOnp(
                           PainContext));
            }
            else
            {
                return(ExpressionRunnerQueue.EvaluateQueue(
                           PainContext));
            }
        }
コード例 #5
0
 public static Boolean EvaluateValue(
     String FieldOrMethodName,
     PainContext PainContext)
 {
     return(EvaluateValueOrMethod(
                null,
                FieldOrMethodName,
                -1,
                PainContext));
 }
コード例 #6
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
 public static Object EvalStep(
     this PainProgram Program,
     IDictionary <String, Object> Parameters   = null,
     IDictionary <String, Object> StaticValues = null)
 {
     using (PainContext context = CreateContext(Program, Parameters, StaticValues, true))
     {
         return(Eval(context));
     }
 }
コード例 #7
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
        ////////////////////////////////////////////////////////////////////

        public static PainObject Exec(
            this PainProgram Program,
            IDictionary <String, Object> Parameters   = null,
            IDictionary <String, Object> StaticValues = null)
        {
            using (PainContext context = CreateContext(Program, Parameters, StaticValues, false))
            {
                return(Exec(context));
            }
        }
コード例 #8
0
        //////////////////////////////

        public Expression FindExpression(String VariableName, PainContext PainContext)
        {
            Expression foundExpression = null;

            if (Expressions != null)
            {
                Expressions.TryGetValue(VariableName, out foundExpression);
            }

            return(foundExpression);
        }
コード例 #9
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
 public static PainContext InvokeMethodGetContext(
     this PainContext PainContext,
     String Method,
     IList <Object> MethodParameters,
     IDictionary <String, Object> StaticValues = null)
 {
     return(InvokeMethodGetContext(
                Method,
                MethodParameters,
                PainContext != null && PainContext.GlobalObject != null ? PainContext.GlobalObject.DynamicValues : null,
                StaticValues));
 }
コード例 #10
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
 public static Object InvokeMethod(
     String Method,
     IList <Object> MethodParameters,
     IDictionary <String, Object> Values       = null,
     IDictionary <String, Object> StaticValues = null)
 {
     using (PainContext context = InvokeMethodGetContext(
                Method,
                MethodParameters,
                Values,
                StaticValues))
     {
         return(context.Eval());
     }
 }
コード例 #11
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
 public static Object InvokeObjectMethod(
     this PainContext PainContext,
     PainObject Object,
     String Method,
     IList <Object> MethodParameters,
     IDictionary <String, Object> StaticValues = null)
 {
     using (PainContext context = InvokeObjectMethodGetContext(
                Object,
                Method,
                MethodParameters,
                PainContext != null && PainContext.GlobalObject != null ? PainContext.GlobalObject.DynamicValues : null,
                StaticValues))
     {
         return(context.Eval());
     }
 }
コード例 #12
0
        ////////////////////////////////////////////////////////////////////////

        public static ExpressionMethodResult Execute(PainContext EvaluateContext, IList <Object> Parameters)
        {
            String variableName = UniConvert.ToUniString(Parameters != null && Parameters.Count > 0 ? Parameters[0] : null);
            Object value        = Parameters != null && Parameters.Count > 1 ? Parameters[1] : null;

            if (EvaluateContext != null)
            {
                Boolean isValueSet = EvaluateContext.SetValue(
                    EvaluateContext,
                    variableName,
                    value);

                if (isValueSet)
                {
                    return(new ExpressionMethodResult(value));
                }
            }
            return(null);
        }
コード例 #13
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
        public static PainObject Exec(
            this PainContext PainContext)
        {
            while (true)
            {
                if (PainContext.IsFinished)
                {
                    break;
                }

                Boolean result = PainLineRunner.ExecuteNext(PainContext);

                if (PainContext.BreakEveryLine && result)
                {
                    break;
                }
            }
            return(PainContext.GlobalObject);
        }
コード例 #14
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
        private static PainContext CreateContext(
            PainCodeLines Lines,
            IDictionary <String, Object> Values,
            IDictionary <String, Object> StaticValues,
            Boolean BreakEveryLine = false,
            Boolean CopyParameters = false)
        {
            PainContext runContext = new PainContext(
                new PainProgram()
            {
                ID    = Guid.Empty,
                Lines = Lines
            });

            runContext.BreakEveryLine = BreakEveryLine;

            if (runContext.CurrentState.Program.Lines.Count > 0)
            {
                runContext.CurrentState.CurrentLineID = runContext.CurrentState.Program.Lines[0].ID;
            }

            if (Values != null)
            {
                if (CopyParameters)
                {
                    if (Values is ICloneShallow)
                    {
                        runContext.CurrentState.Object.DynamicValues = (IDictionary <String, Object>)((ICloneShallow)Values).CloneShallow();
                    }
                    else
                    {
                        runContext.CurrentState.Object.DynamicValues = new MyDictionary <String, Object>(Values);
                    }
                }
                else
                {
                    runContext.CurrentState.Object.DynamicValues = Values;
                }
            }
            runContext.CurrentState.Object.StaticValues = StaticValues;

            return(runContext);
        }
コード例 #15
0
        private static Boolean?ExecuteCalculations(
            PainContext PainContext,
            PainState currentState,
            out Object Result)
        {
            Result = null;
            PainCodeLines lines       = currentState.GetCurrentLines();
            PainCodeLine  currentLine = currentState.GetCurrentLine();

            // wykonanie kalkulacji
            if (currentLine.ContainsAnyExpressions() &&
                currentLine.OperatorType != EOperatorType.ELSE)
            {
                if (PainContext.CurrentState.ExpressionContext == null)
                {
                    PainContext.CurrentState.ExpressionContext = new ExpressionContext(currentLine.ExpressionGroup);
                }

                if (PainContext.CurrentState.ExpressionContext != null &&
                    PainContext.CurrentState.ExpressionContext.IsFinished)
                {
                    Result = PainContext.CurrentState.ExpressionContext.Result;
                    PainContext.CurrentState.ExpressionContext = null;
                }
                else
                {
                    try
                    {
                        Boolean result = ExpressionRunner.NextStep(
                            PainContext);

                        return(result);
                    }
                    catch
                    {
                        throw;
                    }
                }
            }

            return(null);
        }
コード例 #16
0
        ////////////////////////////////////////////////////////////////////////

        public static Object Execute(PainContext EvaluateContext, Object obj, IList <Object> Parameters)
        {
            Boolean isValueSet = false;

            String propertyPath = UniConvert.ToUniString(Parameters != null && Parameters.Count > 0 ? Parameters[0] : null);
            Object value        = (Parameters != null && Parameters.Count > 1 ? Parameters[1] : null);

            if (obj is IDictionary)
            {
                IDictionary dict = obj as IDictionary;
                dict[propertyPath] = value;
                isValueSet         = true;
            }

            if (obj is PainObject)
            {
                propertyPath = propertyPath.ToUpper();
                PainObject painObj = obj as PainObject;
                painObj[propertyPath] = value;
                return(null);
            }

            if (!isValueSet)
            {
                isValueSet = RefSensitiveHelper.I.SetValue(obj, propertyPath, value);
            }

            if (!isValueSet)
            {
                isValueSet = RefUnsensitiveHelper.I.SetValue(obj, propertyPath, value);
            }

            if (isValueSet)
            {
                return(value);
            }

            return(null);
        }
コード例 #17
0
        private static Boolean?CheckIfFinishedOrEmptyLine(
            PainContext PainContext,
            PainState currentState)
        {
            if (currentState == null || PainContext.IsFinished)
            {
                PainContext.IsFinished = true;
                return(true);
            }

            PainCodeLines lines       = currentState.GetCurrentLines();
            PainCodeLine  currentLine = currentState.GetCurrentLine();

            if (currentLine == null)
            {
                return(ExitCurrentContext(
                           PainContext));
            }

            // jeśli linia jest pusta to przechodzimy do nastepnej
            if (currentLine.IsLineEmpty)
            {
                PainCodeLine nextLine = lines.NextLine(currentLine);
                if (nextLine == null)
                {
                    return(ExitCurrentContext(
                               PainContext));
                }
                else
                {
                    currentState.CurrentLineID = nextLine.ID;
                }
                return(true);
            }
            return(null);
        }
コード例 #18
0
        ////////////////////////////////////////////////////////////////////////

        public static Object Execute(PainContext EvaluateContext, Object obj, IList <Object> Parameters)
        {
            Object Collection = obj;
            Object Key        = Parameters == null ? null : Parameters.FirstOrDefault();

            if (Collection == null)
            {
                return(null);
            }

            if (Collection is String)
            {
                Int32?index = UniConvert.ToInt32N(Key);
                if (index == null || index < 0)
                {
                    return(null);
                }

                String str = (String)Collection;
                if (index >= str.Length)
                {
                    return(null);
                }

                return(str[index.Value]);
            }

            if (Collection is PainObject)
            {
                PainObject painObj = Collection as PainObject;

                if (painObj.TotalCount == 0)
                {
                    return(null);
                }

                /*IDictionary<String, Object> dict = ((PainObject)Collection).Values;
                 * if (dict.Count == 0)
                 *  return null;*/

                String finalKey = ((String)(Key.GetType() == typeof(String) ? Key :
                                            Convert.ChangeType(Key, typeof(String), System.Globalization.CultureInfo.InvariantCulture)));

                return(painObj[finalKey]);
            }

            if (Collection is IDictionary)
            {
                IDictionary dict = (IDictionary)Collection;
                if (dict.Count == 0)
                {
                    return(null);
                }

                Type[] arguments = dict.GetType().GetGenericArguments();
                Type   keyType   = arguments[0];

                Object finalKey = Key.GetType() == keyType ? Key :
                                  Convert.ChangeType(Key, keyType, System.Globalization.CultureInfo.InvariantCulture);

                return(dict[finalKey]);
            }

            if (Collection is IList)
            {
                Int32?index = UniConvert.ToInt32N(Key);
                if (index == null || index < 0)
                {
                    return(null);
                }

                IList list = (IList)Collection;
                if (index >= list.Count)
                {
                    return(null);
                }

                return(list[index.Value]);
            }

            if (Collection is IEnumerable)
            {
                Int32?index = UniConvert.ToInt32N(Key);
                if (index == null || index < 0)
                {
                    return(null);
                }

                Int32 i = -1;
                foreach (Object item in ((IEnumerable)Collection))
                {
                    i++;
                    if (i == index.Value)
                    {
                        return(item);
                    }
                }
            }

            return(null);
        }
コード例 #19
0
        public static Boolean EvaluateValueOrMethod(
            Object Obj,
            String FieldOrMethodName,
            Int32 ParametersCount,
            PainContext PainContext)
        {
            Boolean seekInObject = (Obj != null && !(Obj is EmptyObject));

            if (seekInObject)
            {
                Boolean foundValue = false;

                Object value = GetValueFromObject(
                    Obj,
                    FieldOrMethodName,
                    ParametersCount,
                    out foundValue);

                if (foundValue)
                {
                    if (value is MethodInfo)
                    {
                        OnpMethodInfo methodInfo = new OnpMethodInfo();
                        methodInfo.Obj  = Obj;
                        methodInfo.Name = FieldOrMethodName;
                        PainContext.CurrentExpressionState.PushValue(methodInfo);
                        return(false);
                    }
                    else
                    {
                        PainContext.CurrentExpressionState.PushValue(value);
                        return(false);
                    }
                }
            }

            ExpressionValue expressionValue = null;
            Expression      expression      = null;

            expression = PainContext.
                         CurrentExpressionGroup.
                         FindExpression(FieldOrMethodName, PainContext);

            if (expression == null)
            {
                expressionValue = PainContext.GetValue(
                    PainContext,
                    FieldOrMethodName,
                    seekInObject,
                    !seekInObject,
                    !seekInObject);
            }

            if (expression == null)
            {
                Object value = expressionValue == null ?
                               null :
                               expressionValue.Value;

                value = InternalTypeConverter.ToInner(
                    value);

                PainContext.CurrentExpressionState.PushValue(value);
                return(false);
            }
            else
            {
                ExpressionState newExpressionState = new ExpressionState();
                newExpressionState.Expression = expression;

                PainContext.CurrentExpressionContext.Stack.Add(newExpressionState);
                return(false);
            }
        }
コード例 #20
0
        private static Boolean GotoCatch(
            PainContext PainContext,
            Exception exception)
        {
            while (true)
            {
                PainState currentState = PainContext.
                                         CurrentState;

                // reset dla kontekstu obliczeń, ponieważ przechodzimy do catch'a
                currentState.ExpressionContext = null;

                PainCodeLines lines       = currentState.GetCurrentLines();
                PainCodeLine  currentLine = currentState.GetCurrentLine();

                // poszukanie poprzedniego catch'a
                PainCodeLine prevCatch = lines.
                                         PrevLineWithLessDepth(currentLine, l => l.OperatorType == EOperatorType.CATCH);

                // poszukanie poprzedniego try'a
                PainCodeLine prevTry = lines.
                                       PrevLineWithLessDepth(currentLine, l => l.OperatorType == EOperatorType.TRY);

                if (prevTry == null)
                {
                    ExitCurrentContext(
                        PainContext);

                    if (PainContext.IsFinished)
                    {
                        break;
                    }
                }
                // jeśli znalazł try'a i nie jesteśmy w catch'u
                else if (prevTry.Depth < currentLine.Depth &&
                         (prevCatch == null || lines.IndexOf(prevCatch) < lines.IndexOf(prevTry)))
                {
                    PainCodeLine nextCatch = lines.NextOnSameOrLower(
                        prevTry,
                        i => i.OperatorType == EOperatorType.CATCH);

                    if (nextCatch != null)
                    {
                        ExpressionToken variableForException =
                            nextCatch.ExpressionGroup != null &&
                            nextCatch.ExpressionGroup.MainExpression != null &&
                            nextCatch.ExpressionGroup.MainExpression.Tokens != null &&
                            nextCatch.ExpressionGroup.MainExpression.Tokens.Count > 0 ?
                            nextCatch.
                            ExpressionGroup.
                            MainExpression.
                            Tokens.
                            FirstOrDefault(i => i.TokenType != TokenType.BRACKET_BEGIN) :
                            null;

                        currentState.CurrentLineID = nextCatch.ID;

                        if (variableForException != null && !String.IsNullOrEmpty(variableForException.TokenName))
                        {
                            currentState.Object[variableForException.TokenName] = exception;
                        }

                        break;
                    }
                    else
                    {
                        ExitCurrentContext(
                            PainContext);

                        if (PainContext.IsFinished)
                        {
                            break;
                        }
                    }
                }
                else
                {
                    ExitCurrentContext(
                        PainContext);

                    if (PainContext.IsFinished)
                    {
                        break;
                    }
                }
            }
            return(false);
        }
コード例 #21
0
        public static Boolean EvaluateQueue(
            PainContext PainContext)
        {
            ExpressionState   expState   = PainContext.CurrentExpressionState;
            ExpressionContext expContext = PainContext.CurrentExpressionContext;

            // policzenie nastepnego parametru
            if (expState.AreParametersCalculating)
            {
                expState.ParameterIndex++;
                if (expState.ParameterIndex < expState.ParameterTokens.Count)
                {
                    Boolean result = false;

                    ExpressionToken parameterToken = expState.ParameterTokens[expState.ParameterIndex];
                    if (parameterToken.TokenType == TokenType.VARIABLE)
                    {
                        result = ObjectValueGetter.EvaluateValue(
                            parameterToken.TokenName,
                            PainContext);
                    }
                    else if (parameterToken.TokenType == TokenType.VALUE)
                    {
                        ExpressionValue operationValue = StringHelper.
                                                         GetValueFromText(parameterToken.TokenChars);

                        Object value = (
                            operationValue == null ? null : operationValue.Value);

                        expState.Parameters.Add(value);
                    }
                    else
                    {
                        throw new PainIncorrectExpressionFormatException();
                    }

                    return(result);
                }
            }

            // czy zakończyć i zapisać wynik
            if (expState.TokenIndex >= expState.Expression.Tokens.Count)
            {
                Object finResult = null;
                if (expState.ValueStack.Count > 0)
                {
                    finResult = expState.ValueStack.Pop();
                }

                expState.ValueStack.Clear();
                expState.Finished = true;
                expState.Result   = InternalTypeConverter.ToOuter(finResult);

                expContext.Stack.Pop();

                if (expContext.Current != null)
                {
                    expContext.Current.PushValue(InternalTypeConverter.ToOuter(finResult));
                    return(false);
                }
                else
                {
                    expContext.Result     = InternalTypeConverter.ToOuter(finResult);
                    expContext.IsFinished = true;
                    return(true);
                }
            }

            Boolean         isFirstToken = expState.TokenIndex == 0;
            ExpressionToken token        = expState.
                                           Expression.
                                           Tokens[expState.TokenIndex];

            ExpressionTokens sequence = new ExpressionTokens(
                new TokenizerQueue().
                GetNextTokensOnSameLevel(expState.Expression.Tokens, expState.TokenIndex));

            Int32 originalSequenceCount = sequence.Count;

            sequence.RemoveBrackets();

            // wykonanie następnej operacji
            if (token.TokenType == TokenType.BRACKET_BEGIN)
            {
                IList <ExpressionToken> prevSequenceTokens = new TokenizerQueue().
                                                             GetPrevTokensOnSameLevel(expState.Expression.Tokens, expState.TokenIndex - 1);

                ExpressionTokens prev_sequence = prevSequenceTokens == null ?
                                                 null : new ExpressionTokens(prevSequenceTokens);

                // jeśli poprzedni operator to @
                if (
                    prev_sequence != null && prev_sequence.Count == 1 &&
                    OnpOnpTokenHelper.IsFunctionOperatorToken(prev_sequence[0]))
                {
                    Boolean result = false;

                    if (sequence.Count == 0 || expState.AreParametersCalculated)
                    {
                        Object obj = expState.ValueStack.Count == 1 ?
                                     new EmptyObject() :
                                     expState.ValueStack.Peek(1);

                        Object methodObject = expState.
                                              ValueStack.
                                              Peek(0);

                        result = EvaluatorForMethods.EvaluateMethod(
                            obj,
                            methodObject,
                            expState.Parameters,
                            PainContext);

                        expState.CleanParametersState();

                        expState.TokenIndex += originalSequenceCount;
                    }
                    else
                    {
                        expState.ParameterTokens = GetParameterTokens(sequence);
                        expState.ParameterIndex  = -1;
                        expState.Parameters      = new List <Object>();
                        result = false;
                    }

                    return(result);
                }
                // jeśli poprzedni operator to .
                else if (
                    prev_sequence != null && prev_sequence.Count == 1 &&
                    OnpOnpTokenHelper.IsPropertyOperatorToken(prev_sequence[0]))
                {
                    throw new PainIncorrectExpressionFormatException();
                }
                // jeśli brak poprzedniego operatora
                else if (
                    prev_sequence == null &&
                    sequence.Count == 1)
                {
                    Boolean result = false;

                    if (sequence[0].TokenType == TokenType.VARIABLE)
                    {
                        result = ObjectValueGetter.EvaluateValue(
                            sequence[0].TokenName,
                            PainContext);
                    }
                    else if (sequence[0].TokenType == TokenType.VALUE)
                    {
                        ExpressionValue operationValue = StringHelper.
                                                         GetValueFromText(sequence[0].TokenChars);

                        Object value = (
                            operationValue == null ? null : operationValue.Value);

                        expState.PushValue(value);
                    }
                    else
                    {
                        throw new PainIncorrectExpressionFormatException();
                    }

                    expState.TokenIndex += originalSequenceCount; // -1;
                    return(result);
                }
                else
                {
                    throw new PainInvalidExpressionException("Incorrect expression " + expState.Expression.Tokens.JoinToString(expState.TokenIndex) + "!");
                }
            }
            else if (token.TokenType == TokenType.VALUE)
            {
                ExpressionValue operationValue = StringHelper.
                                                 GetValueFromText(token.TokenChars);

                Object value = (
                    operationValue == null ? null : operationValue.Value);

                if (isFirstToken)
                {
                    expState.PushValue(value);
                }
                else
                {
                    Object prevValue = expState.ValueStack.Peek();

                    Object method = ObjectValueGetter.GetValueFromObject(
                        prevValue,
                        UniConvert.ToString(value));

                    expState.PushValue(method);
                }

                expState.TokenIndex += originalSequenceCount; // -1
            }
            else if (token.TokenType == TokenType.PROPERTY_NAME)
            {
                if (isFirstToken)
                {
                    throw new PainIncorrectExpressionFormatException();
                }
                else
                {
                    Object prevValue = expState.ValueStack.Peek();

                    Object value = ObjectValueGetter.GetValueFromObject(
                        prevValue,
                        token.TokenName);

                    expState.PushValue(value);
                }

                expState.TokenIndex += originalSequenceCount; // -1
            }
            else if (token.TokenType == TokenType.VARIABLE)
            {
                Boolean result = false;

                ExpressionToken next_token = expState.TokenIndex + 1 < expState.Expression.Tokens.Count ?
                                             expState.Expression.Tokens[expState.TokenIndex + 1] :
                                             null;

                Object prevValue = null;
                if (isFirstToken)
                {
                    prevValue = new EmptyObject();

                    /*result = ObjectValueGetter.EvaluateValueOrMethod(
                     *  new EMPTY_OBJECT(),
                     *  sequence[0].TokenName,
                     *  -1,
                     *  PainContext);*/
                }
                else
                {
                    prevValue = (
                        expState.ValueStack.Count == 0 ?
                        null :
                        expState.ValueStack.Peek());
                }

                Int32 paramCount = -1;

                // jeśli następny operator to operator wołania funkcji @ to pobieramy z niego liczbę parametrów dla funkcji
                if (OnpOnpTokenHelper.IsFunctionOperatorToken(next_token) &&
                    next_token.TokenData != null &&
                    next_token.TokenData.FunctionParametersCount != null)
                {
                    paramCount = next_token.TokenData.FunctionParametersCount.Value;
                }
                else
                {
                    paramCount = -1;
                }

                result = ObjectValueGetter.EvaluateValueOrMethod(
                    prevValue,
                    sequence[0].TokenName,
                    paramCount,
                    PainContext);

                if (PainContext.CurrentExpressionState.ValueStack.Peek() == null)
                {
                    ExpressionToken next_next_token = expState.TokenIndex + 2 < expState.Expression.Tokens.Count ?
                                                      expState.Expression.Tokens[expState.TokenIndex + 2] :
                                                      null;

                    if (next_token.TokenType == TokenType.OPERATOR &&
                        OnpOnpTokenHelper.IsPropertyOperatorToken(next_token) &&
                        next_next_token != null)
                    {
                    }
                    else
                    {
                        next_next_token = null;
                    }

                    if (paramCount < 0)
                    {
                        if (next_next_token != null)
                        {
                            ExpressionToken next_next_next_next_next_token = expState.TokenIndex + 5 < expState.Expression.Tokens.Count ?
                                                                             expState.Expression.Tokens[expState.TokenIndex + 5] :
                                                                             null;

                            if (next_next_token.TokenName == "__EXT_SET" && next_next_next_next_next_token != null)
                            {
                                throw new PainMethodNotFoundException("Cannot find property " + next_next_next_next_next_token.TokenName + " in undefined object '" + sequence[0].TokenName + "'");
                            }
                            else
                            {
                                throw new PainMethodNotFoundException("Cannot call method '" + next_next_token.TokenName + "' in undefined object '" + sequence[0].TokenName + "'");
                            }
                        }
                        else
                        {
                            throw new PainMethodNotFoundException("Undefined object '" + sequence[0].TokenName + "'");
                        }
                    }
                    else
                    {
                        throw new PainMethodNotFoundException("Undefined method '" + sequence[0].TokenName + "'!");
                    }
                }

                expState.TokenIndex += originalSequenceCount; // -1
                return(result);
            }
            else if (token.TokenType == TokenType.OPERATOR)
            {
                if (!OnpOnpTokenHelper.IsFunctionOperatorToken(token) &&
                    !OnpOnpTokenHelper.IsPropertyOperatorToken(token))
                {
                    throw new PainIncorrectExpressionFormatException();
                }

                expState.TokenIndex += originalSequenceCount; // -1
            }

            if (expState.ValueStack.Peek() == null)
            {
                return(false);
            }

            return(false);
        }
コード例 #22
0
        //////////////////////////////////////////////

        private static Boolean GotoNextLine(
            PainContext PainContext,
            PainState currentState,
            Object currentValue)
        {
            try
            {
                PainCodeLines lines       = currentState.GetCurrentLines();
                PainCodeLine  currentLine = currentState.GetCurrentLine();

                // jesli return to konczymy
                if (currentLine.OperatorType == EOperatorType.RETURN)
                {
                    return(ExitCurrentContext(
                               PainContext,
                               currentValue));
                }
                // throw błędu
                else if (currentLine.OperatorType == EOperatorType.THROW)
                {
                    if (currentValue is Exception)
                    {
                        throw (Exception)currentValue;
                    }
                    else
                    {
                        String message = UniConvert.ToString(currentValue ?? "");
                        throw String.IsNullOrEmpty(message) ? new Exception() : new Exception(message);
                    }

                    /*return ExitCurrentContext(
                     *  PainContext,
                     *  new Exception(message));*/
                }

                if (currentLine.OperatorType == EOperatorType.WHILE ||
                    currentLine.OperatorType == EOperatorType.IF ||
                    currentLine.OperatorType == EOperatorType.ELIF)
                {
                    Boolean conditionResult = currentValue.IfTrue();
                    if (conditionResult)
                    {
                        PainCodeLine nextLine = lines.NextOnSameOrHigher(currentLine);
                        if (nextLine != null)
                        {
                            currentState.CurrentLineID = nextLine.ID;
                        }
                        else
                        {
                            throw new NotImplementedException();
                        }
                    }
                    else
                    {
                        PainCodeLine nextLine = lines.NextOnSameOrLower(currentLine);
                        if (nextLine == null)
                        {
                            return(ExitCurrentContext(
                                       PainContext));
                        }
                        else
                        {
                            if (nextLine.Depth < currentLine.Depth)
                            {
                                while (
                                    nextLine != null &
                                    (nextLine.OperatorType == EOperatorType.ELSE ||
                                     nextLine.OperatorType == EOperatorType.ELIF /*||
                                                                                  * nextLine.OperatorType == EOperatorType.FINALLY*/))
                                {
                                    nextLine = lines.ExitParentIf(nextLine);

                                    if (nextLine == null)
                                    {
                                        break;
                                    }
                                }

                                if (nextLine == null)
                                {
                                    return(ExitCurrentContext(
                                               PainContext));
                                }

                                if (nextLine.Depth < currentLine.Depth)
                                {
                                    //PainCodeLine prevIf = lines.
                                    //    PrevLineWithLessDepth(currentLine, l => l.OperatorType == EOperatorType.IF || l.OperatorType == EOperatorType.ELIF);

                                    while (true)
                                    {
                                        PainCodeLine prevConditionLine = lines.
                                                                         PrevLineWithLessDepth(
                                            currentLine,
                                            l => l.OperatorType == EOperatorType.IF || l.OperatorType == EOperatorType.ELIF || l.OperatorType == EOperatorType.ELSE || l.OperatorType == EOperatorType.WHILE);

                                        if (prevConditionLine != null &&
                                            prevConditionLine.Depth >= nextLine.Depth &&
                                            prevConditionLine.OperatorType == EOperatorType.WHILE)
                                        {
                                            currentState.CurrentLineID = prevConditionLine.ID;
                                            break;
                                        }
                                        else if (prevConditionLine != null)
                                        {
                                            currentLine = prevConditionLine;
                                        }
                                        else
                                        {
                                            currentState.CurrentLineID = nextLine.ID;
                                            break;
                                        }
                                    }
                                }
                                else
                                {
                                    currentState.CurrentLineID = nextLine.ID;
                                }
                            }
                            else
                            {
                                currentState.CurrentLineID = nextLine.ID;
                            }
                        }
                    }
                }
                else if (
                    currentLine.OperatorType == EOperatorType.TRY ||
                    currentLine.OperatorType == EOperatorType.ELSE)
                {
                    PainCodeLine nextLine = lines.NextOnSameOrHigher(currentLine);
                    if (nextLine != null)
                    {
                        currentState.CurrentLineID = nextLine.ID;
                    }
                    else
                    {
                        throw new NotImplementedException();
                    }
                }
                else if (
                    (currentLine.OperatorType == EOperatorType.FINALLY))
                {
                    throw new NotImplementedException("FINALLY");
                }
                else if (
                    (currentLine.OperatorType == EOperatorType.CATCH))
                {
                    if (PainContext.Error != null)
                    {
                        PainContext.Error = null;
                        PainCodeLine nextLine = lines.NextOnSameOrHigher(currentLine);
                        if (nextLine != null)
                        {
                            currentState.CurrentLineID = nextLine.ID;
                        }
                        else
                        {
                            throw new NotImplementedException();
                        }
                    }
                    else
                    {
                        PainCodeLine nextLine = lines.NextOnSameOrLower(currentLine);
                        if (nextLine != null)
                        {
                            currentState.CurrentLineID = nextLine.ID;
                        }
                        else
                        {
                            return(ExitCurrentContext(
                                       PainContext));
                        }
                    }
                }
                else if (currentLine.OperatorType == EOperatorType.NONE)
                {
                    PainCodeLine nextLine = lines.NextLine(currentLine);
                    if (nextLine != null)
                    {
                        while (
                            nextLine != null &
                            (nextLine.OperatorType == EOperatorType.ELSE ||
                             nextLine.OperatorType == EOperatorType.ELIF /*||
                                                                          * nextLine.OperatorType == EOperatorType.FINALLY*/))
                        {
                            nextLine = lines.ExitParentIf(nextLine);

                            if (nextLine == null)
                            {
                                return(ExitCurrentContext(
                                           PainContext));
                            }
                        }

                        if (nextLine == null)
                        {
                            return(ExitCurrentContext(
                                       PainContext));
                        }

                        if (nextLine.Depth < currentLine.Depth)
                        {
                            //PainCodeLine prevIf = lines.
                            //    PrevLineWithLessDepth(currentLine, l => l.OperatorType == EOperatorType.IF || l.OperatorType == EOperatorType.ELIF);

                            while (true)
                            {
                                PainCodeLine prevConditionLine = lines.
                                                                 PrevLineWithLessDepth(
                                    currentLine,
                                    l => l.OperatorType == EOperatorType.IF || l.OperatorType == EOperatorType.ELIF || l.OperatorType == EOperatorType.ELSE || l.OperatorType == EOperatorType.WHILE);

                                if (prevConditionLine != null &&
                                    prevConditionLine.Depth >= nextLine.Depth &&
                                    prevConditionLine.OperatorType == EOperatorType.WHILE)
                                {
                                    currentState.CurrentLineID = prevConditionLine.ID;
                                    break;
                                }
                                else if (prevConditionLine != null)
                                {
                                    currentLine = prevConditionLine;
                                }
                                else
                                {
                                    currentState.CurrentLineID = nextLine.ID;
                                    break;
                                }
                            }
                        }
                        else
                        {
                            currentState.CurrentLineID = nextLine.ID;
                        }
                    }
                    // jeśli ostatnia linia i jesteśmy w while'u
                    else
                    {
                        //PainCodeLine prevIf = lines.
                        //    PrevLineWithLessDepth(currentLine, l => l.OperatorType == EOperatorType.IF || l.OperatorType == EOperatorType.ELIF);

                        while (true)
                        {
                            PainCodeLine prevConditionLine = lines.
                                                             PrevLineWithLessDepth(
                                currentLine,
                                l => l.OperatorType == EOperatorType.IF || l.OperatorType == EOperatorType.ELIF || l.OperatorType == EOperatorType.ELSE || l.OperatorType == EOperatorType.WHILE);

                            if (prevConditionLine != null &&
                                prevConditionLine.OperatorType == EOperatorType.WHILE)
                            {
                                currentState.CurrentLineID = prevConditionLine.ID;
                                break;
                            }
                            else if (prevConditionLine != null)
                            {
                                currentLine = prevConditionLine;
                            }
                            else
                            {
                                return(ExitCurrentContext(
                                           PainContext));
                            }
                        }
                    }
                }
                return(false);
            }
            catch
            {
                throw;
            }
        }
コード例 #23
0
        public static Boolean ExecuteNext(
            PainContext PainContext)
        {
            try
            {
                Object    currentValue = null;
                PainState currentState = PainContext.
                                         CurrentState;

                Boolean?checkResult = CheckIfFinishedOrEmptyLine(
                    PainContext,
                    currentState);

                if (checkResult != null)
                {
                    return(checkResult.Value);
                }

                Boolean?executeResult = ExecuteCalculations(
                    PainContext,
                    currentState,
                    out currentValue);

                if (executeResult != null)
                {
                    return(executeResult.Value);
                }

                Boolean gotoResult = GotoNextLine(
                    PainContext,
                    currentState,
                    currentValue);

                return(gotoResult);
            }
            catch (Exception ex)
            {
                Exception error = (ex is TargetInvocationException ? ex.InnerException : ex);

                Boolean result = false;

                PainContext.Error = error;

                PainState currentState = PainContext.
                                         CurrentState;

                // próba obsługi błędu
                Boolean handled = PainContext.RaiseError(
                    currentState,
                    error);

                if (!handled)
                {
                    result = GotoCatch(
                        PainContext,
                        error);
                }
                else
                {
                    PainContext.Error = null;
                    result            = true;
                }

                if (PainContext.IsFinished && PainContext.Error != null)
                {
                    throw PainContext.Error;
                }

                return(result);
            }
        }
コード例 #24
0
        public static Boolean EvaluateMethod(
            Object Object,
            Object MethodObject,
            IList <Object> Parameters,
            PainContext PainContext)
        {
            if (MethodObject is PainMethod)
            {
                if (Parameters == null)
                {
                    Parameters = new Object[0];
                }

                PainMethod      method      = (PainMethod)MethodObject;
                PainContextType contextType = PainContextType.METHOD;

                // jesli tworzenie klasy (wolanie konstruktora)
                if (MethodObject is PainClass)
                {
                    contextType = PainContextType.CLASS;
                }

                PainState newContext = PainContext.
                                       PushContext(method, contextType, Parameters);

                newContext.Object.ParentObject = method.ParentObject;

                return(true);
            }
            else if (MethodObject is PainProgram)
            {
                PainProgram program = (PainProgram)MethodObject;

                IDictionary <String, Object> currentValues = (PainContext == null || PainContext.CurrentState == null || PainContext.CurrentState.Object == null ?
                                                              null :
                                                              PainContext.
                                                              CurrentState.
                                                              Object.
                                                              DynamicValues);

                IDictionary <String, Object> currentStaticValues = (PainContext == null || PainContext.CurrentState == null || PainContext.CurrentState.Object == null ?
                                                                    null :
                                                                    PainContext.
                                                                    CurrentState.
                                                                    Object.
                                                                    StaticValues);

                PainState newState = PainContext.PushContext(
                    program,
                    PainContextType.METHOD,
                    null);

                if (currentValues != null)
                {
                    foreach (String key in currentValues.Keys)
                    {
                        newState.Object.DynamicValues[key] = currentValues[key];
                    }
                }
                newState.Object.StaticValues = currentStaticValues;

                return(true);
            }
            else
            {
                ExpressionMethodResult methodResult = EvaluateInlineMethod(
                    Object,
                    MethodObject,
                    Parameters,
                    PainContext);

                if (methodResult != null &&
                    methodResult.NewContextCreated)
                {
                    return(true);
                }
                else
                {
                    var v = methodResult == null ? null : methodResult.Value;
                    PainContext.CurrentExpressionState.PushValue(v);
                    return(false);
                }
            }
        }
コード例 #25
0
ファイル: PainRunner.cs プロジェクト: JackWangCUMT/PainLang
        private static PainContext InvokeMethodGetContext(
            String Method,
            IList <Object> MethodParameters,
            IDictionary <String, Object> Values,
            IDictionary <String, Object> StaticValues)
        {
            PainContext newContext = CreateContext(
                new PainCodeLines(),
                Values,
                StaticValues,
                false, true);
            PainObject globalObject = newContext.GlobalObject;

            ExpressionGroup expressionGroup = new ExpressionGroup(false);

            expressionGroup.MainExpression = new Expression();
            expressionGroup.MainExpression.IsOnpExecution = false;
            expressionGroup.MainExpression.Tokens         = new ExpressionTokens();

            expressionGroup.MainExpression.Tokens.Add(
                new ExpressionToken(Method, TokenType.VARIABLE));

            expressionGroup.MainExpression.Tokens.Add(
                new ExpressionToken('@', TokenType.OPERATOR));

            expressionGroup.MainExpression.Tokens.Add(
                new ExpressionToken('(', TokenType.BRACKET_BEGIN));

            if (MethodParameters != null)
            {
                Int32 i = -1;
                foreach (Object parameter in MethodParameters)
                {
                    i++;
                    if (i > 0)
                    {
                        expressionGroup.MainExpression.Tokens.Add(
                            new ExpressionToken(',', TokenType.SEPARATOR));
                    }

                    String parameterName = IdGenerator.Generate();
                    globalObject.DynamicValues[parameterName] = parameter; // much faster
                    //newContext[parameterName] = parameter;

                    expressionGroup.MainExpression.Tokens.Add(
                        new ExpressionToken(parameterName, TokenType.VARIABLE));
                }
            }

            expressionGroup.MainExpression.Tokens.Add(
                new ExpressionToken(')', TokenType.BRACKET_END));

            PainCodeLine lineOfCode = new PainCodeLine()
            {
                ExpressionGroup = expressionGroup,
                Depth           = 0,
                IsLineEmpty     = false,
                OperatorType    = EOperatorType.RETURN
            };

            newContext.GlobalState.Program.Lines.Add(lineOfCode);

            return(newContext);
        }
コード例 #26
0
        ////////////////////////////////////////////////////////////////////////

        public static Object Execute(PainContext EvaluateContext, Object obj, IList <Object> Parameters)
        {
            Object Collection = obj;
            Object value      = Parameters != null && Parameters.Count > 0 ? Parameters[0] : null;
            Object Key        = Parameters != null && Parameters.Count > 1 ? Parameters[1] : null;

            if (Collection == null)
            {
                return(null);
            }

            if (Collection is PainObject)
            {
                PainObject painObj = Collection as PainObject;

                String finalKey = (String)(Key.GetType() == typeof(String) ? Key :
                                           Convert.ChangeType(Key, typeof(String), System.Globalization.CultureInfo.InvariantCulture));

                Object finValue = value == null ? null : (value.GetType() == typeof(Object) ? value :
                                                          Convert.ChangeType(value, typeof(Object), System.Globalization.CultureInfo.InvariantCulture));

                painObj[finalKey] = finValue;

                return(value);
            }

            if (Collection is IDictionary)
            {
                IDictionary dict = (IDictionary)Collection;

                Type[] arguments = dict.GetType().GetGenericArguments();
                Type   keyType   = arguments[0];
                Type   valueType = arguments[1];

                Object finalKey = Key.GetType() == keyType ? Key :
                                  Convert.ChangeType(Key, keyType, System.Globalization.CultureInfo.InvariantCulture);

                Object finValue = value == null ? null : (value.GetType() == valueType ? value :
                                                          Convert.ChangeType(value, valueType, System.Globalization.CultureInfo.InvariantCulture));

                lock (dict)
                {
                    dict.Remove(finalKey);
                    dict.Add(finalKey, finValue);
                }

                return(value);
            }

            if (Collection is IList)
            {
                Int32?index = UniConvert.ToInt32N(Key);
                if (index == null || index < 0)
                {
                    return(null);
                }

                IList list = (IList)Collection;
                if (index >= list.Count)
                {
                    return(null);
                }

                Type listType = MyTypeHelper.GetListType(list);

                Object finValue = value == null ? null : (value.GetType() == listType ? value :
                                                          Convert.ChangeType(value, listType, System.Globalization.CultureInfo.InvariantCulture));

                list[index.Value] = finValue;

                return(value);
            }

            return(null);
        }
コード例 #27
0
        private static ExpressionMethodResult EvaluateInlineMethod(
            Object Object,
            Object Method,
            IList <Object> MethodParameters,
            PainContext PainContext)
        {
            if (Method is OnpMethodInfo)
            {
                OnpMethodInfo methodInfo = Method as OnpMethodInfo;

                DynamicCallResult callResult = MyReflectionHelper.CallMethod(
                    methodInfo.Obj,
                    methodInfo.Name,
                    MethodParameters);

                if (callResult != null)
                {
                    return(new ExpressionMethodResult(callResult.Value));
                }
            }
            else if (Method is ExpressionMethod)
            {
                ExpressionMethod       onpMethod = Method as ExpressionMethod;
                ExpressionMethodResult result    = null;

                if (Object is EmptyObject)
                {
                    result = onpMethod.
                             CalculateValueDelegate(
                        PainContext,
                        MethodParameters);
                }
                else
                {
                    result = onpMethod.
                             CalculateValueDelegate(
                        PainContext,
                        new[] { Object }.Union(MethodParameters).ToArray());
                }

                return(result == null ?
                       new ExpressionMethodResult(null) :
                       result);
            }
            else if (Method is ExpressionMethodInfo)
            {
                ExpressionMethodInfo   onpMethodInfo = Method as ExpressionMethodInfo;
                ExpressionMethod       onpMethod     = BuildinMethods.GetByID(onpMethodInfo.ID);
                ExpressionMethodResult result        = null;

                if (onpMethod == null)
                {
                    return(new ExpressionMethodResult(result));
                }

                if (Object is EmptyObject)
                {
                    result = onpMethod.
                             CalculateValueDelegate(
                        PainContext,
                        MethodParameters);
                }
                else
                {
                    result = onpMethod.
                             CalculateValueDelegate(
                        PainContext,
                        new[] { Object }.Union(MethodParameters).ToArray());
                }

                return(result == null ?
                       new ExpressionMethodResult(null) :
                       result);
            }
            else if (Method is ExpressionExtender)
            {
                ExpressionExtender onpExtender = Method as ExpressionExtender;

                return(new ExpressionMethodResult(
                           onpExtender.
                           CalculateValueDelegate(
                               PainContext,
                               Object,
                               MethodParameters)));
            }
            else if (Method is ExpressionExtenderInfo)
            {
                ExpressionExtenderInfo onpExtenderInfo = Method as ExpressionExtenderInfo;
                ExpressionExtender     onpExtender     = BuildinExtenders.GetByID(onpExtenderInfo.ID);

                if (onpExtender == null)
                {
                    return(new ExpressionMethodResult(null));
                }

                return(new ExpressionMethodResult(
                           onpExtender.
                           CalculateValueDelegate(
                               PainContext,
                               Object,
                               MethodParameters)));
            }

            if (Method == null)
            {
                if (Object == null)
                {
                    throw new PainMethodNotFoundException("Cannot find a method to call");
                }
                else
                {
                    throw new PainMethodNotFoundException("Cannot find a method to call in object " + Object.GetType().Name + "");
                }
            }
            throw new PainUnsupportedMethodTypeException("Unsupported method type " + Method.GetType() + "!");
        }
コード例 #28
0
        public static Boolean EvaluateOnp(
            PainContext PainContext)
        {
            Boolean           result     = false;
            ExpressionState   expState   = PainContext.CurrentExpressionState;
            ExpressionContext expContext = PainContext.CurrentExpressionContext;

            // czy zakończyć i zapisać wynik
            if (expState.TokenIndex >= expState.Expression.OnpTokens.Count)
            {
                Object finResult = null;
                if (expState.ValueStack.Count > 0)
                {
                    finResult = expState.ValueStack.Pop();
                }

                expState.ValueStack.Clear();
                expState.Finished = true;
                expState.Result   = InternalTypeConverter.ToOuter(finResult);

                expContext.Stack.Pop();

                if (expContext.Current != null)
                {
                    expContext.Current.PushValue(InternalTypeConverter.ToOuter(finResult));
                    return(false);
                }
                else
                {
                    expContext.Result     = InternalTypeConverter.ToOuter(finResult);
                    expContext.IsFinished = true;
                    return(true);
                }
            }

            ExpressionToken token = expState.Expression.OnpTokens[expState.TokenIndex];

            // wykonanie następnej operacji
            if (token.TokenType == TokenType.VALUE)
            {
                ExpressionValue operationValue = StringHelper.
                                                 GetValueFromText(token.TokenChars);

                Object value = operationValue == null ? null :
                               InternalTypeConverter.ToInner(operationValue.Value);

                expState.PushValue(value);
            }
            else if (token.TokenType == TokenType.PROPERTY_NAME)
            {
                expState.PushValue(token.TokenName);
            }
            if (token.TokenType == TokenType.VARIABLE)
            {
                result = ObjectValueGetter.EvaluateValue(
                    token.TokenName,
                    PainContext);
            }
            else if (token.TokenType == TokenType.OPERATOR)
            {
                Object valueA = InternalTypeConverter.ToInner(
                    expState.ValueStack.Pop());

                Object valueB = InternalTypeConverter.ToInner(
                    expState.ValueStack.Pop());

                Object       value        = null;
                OperatorType operatorType = OperatorTypeHelper.
                                            GetOperationType(token.TokenChars);

                try
                {
                    value = OperationHelper.Do(
                        operatorType,
                        valueB,
                        valueA);

                    expState.PushValue(value);
                }
                catch
                {
                    throw;
                }
            }

            expState.TokenIndex++;
            return(result);
        }