예제 #1
0
            public override Evaluation Analyze(UnaryEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                Evaluation result;

                switch (node.Operation)
                {
                case Operations.Print:
                case Operations.Clone:
                case Operations.ObjectCast:
                case Operations.ArrayCast:
                    node.Expr = node.Expr.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                    result    = new Evaluation(node);
                    break;

                default:
                    Expression tmp;
                    result    = node.Expr.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Evaluate(node, out tmp);
                    node.Expr = tmp;
                    break;
                }

                return(result);
            }
예제 #2
0
            public override Evaluation Analyze(AssertEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                // assertion:
                if (analyzer.Context.Config.Compiler.Debug)
                {
                    Evaluation code_evaluation = node.CodeEx.Analyze(analyzer, ExInfoFromParent.DefaultExInfo);
                    //Evaluation desc_evaluation = node.DescriptionEx.Analyze(analyzer, ExInfoFromParent.DefaultExInfo);

                    // string parameter is parsed and converted to an expression:
                    if (code_evaluation.HasValue)
                    {
                        _inlinedCode = Convert.ObjectToString(code_evaluation.Value);
                        if (!string.IsNullOrEmpty(_inlinedCode))
                        {
                            const string prefix = "return ";

                            // the position of the last character before the parsed string:
                            var statements = analyzer.BuildAst(node.CodeEx.Span.Start - prefix.Length + 1, String.Concat(prefix, _inlinedCode, ";"));

                            // code is unevaluable:
                            if (statements == null)
                            {
                                return(new Evaluation(node, true));
                            }

                            if (statements.Length > 1)
                            {
                                analyzer.ErrorSink.Add(Warnings.MultipleStatementsInAssertion, analyzer.SourceUnit, node.Span);
                            }

                            Debug.Assert(statements.Length > 0 && statements[0] is JumpStmt);

                            node.CodeEx = ((JumpStmt)statements[0]).Expression;
                        }
                        else
                        {
                            // empty assertion:
                            return(new Evaluation(node, true));
                        }
                    }
                    else
                    {
                        node.CodeEx = code_evaluation.Expression;
                        analyzer.AddCurrentRoutineProperty(RoutineProperties.ContainsEval);
                    }

                    //
                    node.CodeEx = node.CodeEx.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();

                    return(new Evaluation(node));
                }
                else
                {
                    // replace with "true" value in release mode:
                    return(new Evaluation(node, true));
                }
            }
예제 #3
0
            public override Evaluation Analyze(NewEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                Debug.Assert(node.IsMemberOf == null);

                access = info.Access;

                this.typeArgsResolved = TypeRefHelper.Analyze(node.ClassNameRef, analyzer);

                DType            type = TypeRefHelper.ResolvedType(node.ClassNameRef);
                RoutineSignature signature;

                if (typeArgsResolved)
                {
                    analyzer.AnalyzeConstructedType(type);
                }

                if (type != null)
                {
                    bool error_reported = false;

                    // make checks if we are sure about character of the type:
                    if (type.IsIdentityDefinite)
                    {
                        if (type.IsAbstract || type.IsInterface)
                        {
                            analyzer.ErrorSink.Add(Errors.AbstractClassOrInterfaceInstantiated, analyzer.SourceUnit,
                                                   node.Span, type.FullName);
                            error_reported = true;
                        }
                    }

                    // disallow instantiation of Closure
                    if (type.RealType == typeof(PHP.Library.SPL.Closure))
                    {
                        analyzer.ErrorSink.Add(Errors.ClosureInstantiated, analyzer.SourceUnit, node.Span, type.FullName);
                        error_reported = true;
                    }

                    // type name resolved, look the constructor up:
                    constructor = analyzer.ResolveConstructor(type, node.Span, analyzer.CurrentType, analyzer.CurrentRoutine,
                                                              out runtimeVisibilityCheck);

                    if (constructor.ResolveOverload(analyzer, node.CallSignature, node.Span, out signature) == DRoutine.InvalidOverloadIndex)
                    {
                        if (!error_reported)
                        {
                            analyzer.ErrorSink.Add(Errors.ClassHasNoVisibleCtor, analyzer.SourceUnit, node.Span, type.FullName);
                        }
                    }
                }
                else
                {
                    signature = UnknownSignature.Default;
                }

                CallSignatureHelpers.Analyze(node.CallSignature, analyzer, signature, info, false);

                return(new Evaluation(node));
            }
예제 #4
0
            internal override void Analyze(Item node, Analyzer analyzer)
            {
                ExInfoFromParent info = new ExInfoFromParent(node);

                info.Access = AccessType.ReadRef;
                ((RefItem)node).RefToGet.Analyze(analyzer, info);
                base.Analyze(node, analyzer);
            }
예제 #5
0
            public override Evaluation Analyze(EvalEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                node.Code = node.Code.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                analyzer.AddCurrentRoutineProperty(RoutineProperties.ContainsEval);

                return(new Evaluation(node));
            }
예제 #6
0
            public override Evaluation Analyze(T node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                TypeRefHelper.Analyze(node.TypeRef, analyzer);
                this.type = TypeRefHelper.ResolvedTypeOrUnknown(node.TypeRef);

                analyzer.AnalyzeConstructedType(type);

                return(new Evaluation(node));
            }
예제 #7
0
            public override Evaluation Analyze(IncDecEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;
                ExInfoFromParent var_info = new ExInfoFromParent(node);

                var_info.Access = AccessType.ReadAndWrite;

                node.Variable.Analyze(analyzer, var_info);

                return(new Evaluation(node));
            }
예제 #8
0
            public override Evaluation Analyze(ExitEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                if (node.ResulExpr != null)
                {
                    node.ResulExpr = node.ResulExpr.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                }

                analyzer.EnterUnreachableCode();
                return(new Evaluation(node));
            }
예제 #9
0
            public override Evaluation Analyze(IssetEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                var vars = node.VarList;

                for (int i = 0; i < vars.Count; i++)
                {
                    vars[i].Analyze(analyzer, ExInfoFromParent.DefaultExInfo);
                }

                return(new Evaluation(node));
            }
예제 #10
0
            public void Analyze(StaticVarDecl /*!*/ node, Analyzer analyzer)
            {
                ExInfoFromParent sinfo = new ExInfoFromParent(node);

                sinfo.Access = AccessType.WriteRef;

                node.Variable.Analyze(analyzer, sinfo);

                if (node.Initializer != null)
                {
                    node.Initializer = node.Initializer.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                }
            }
예제 #11
0
            public override Evaluation Analyze(EmptyEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                var expression = node.Expression;
                var evaluation = expression
                                 .Analyze(analyzer, ExInfoFromParent.DefaultExInfo)
                                 .Evaluate(node, out expression);

                node.Expression = expression;

                return(evaluation);
            }
예제 #12
0
            public override Evaluation Analyze(TypeOfEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                typeArgsResolved = TypeRefHelper.Analyze(node.ClassNameRef, analyzer);

                if (typeArgsResolved)
                {
                    analyzer.AnalyzeConstructedType(TypeRefHelper.ResolvedType(node.ClassNameRef));
                }

                return(new Evaluation(node));
            }
예제 #13
0
            public override Evaluation Analyze(ArrayEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                foreach (var i in node.Items)
                {
                    if (i != null)
                    {
                        i.NodeCompiler <ItemCompiler>().Analyze(i, analyzer);
                    }
                }

                return(new Evaluation(node));
            }
예제 #14
0
            public void Analyze(CatchItem /*!*/ node, Analyzer /*!*/ analyzer)
            {
                ExInfoFromParent info = new ExInfoFromParent(node);

                info.Access = AccessType.Write;

                resolvedType = analyzer.ResolveTypeName(node.ClassName, analyzer.CurrentType, analyzer.CurrentRoutine, node.Span, false);

                node.Variable.Analyze(analyzer, info);

                analyzer.EnterConditionalCode();
                node.Statements.Analyze(analyzer);
                analyzer.LeaveConditionalCode();
            }
예제 #15
0
            public override Evaluation Analyze(InstanceOfEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                node.Expression = node.Expression.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();

                typeArgsResolved = TypeRefHelper.Analyze(node.ClassNameRef, analyzer);

                if (typeArgsResolved)
                {
                    analyzer.AnalyzeConstructedType(TypeRefHelper.ResolvedType(node.ClassNameRef));
                }

                return(new Evaluation(node));
            }
예제 #16
0
            public override Evaluation Analyze(IncludingEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                // if the expression should be emitted:
                if (characteristic == Characteristic.Dynamic || characteristic == Characteristic.StaticArgEvaluated)
                {
                    node.Target = node.Target.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                }

                analyzer.AddCurrentRoutineProperty(RoutineProperties.ContainsInclude);

                analyzer.CurrentScope = node.Scope;

                return(new Evaluation(node));
            }
예제 #17
0
            public void Analyze(ForeachVar /*!*/ node, Analyzer analyzer)
            {
                ExInfoFromParent info = new ExInfoFromParent(node);

                if (node.Alias)
                {
                    info.Access = AccessType.WriteRef;
                }
                else
                {
                    info.Access = AccessType.Write;
                }

                // retval not needed
                node.Expression.Analyze(analyzer, info);
            }
예제 #18
0
            internal override Statement Analyze(ForStmt node, Analyzer analyzer)
            {
                if (analyzer.IsThisCodeUnreachable())
                {
                    analyzer.ReportUnreachableCode(node.Span);
                    return(EmptyStmt.Unreachable);
                }

                ExInfoFromParent info = new ExInfoFromParent(node);

                info.Access = AccessType.None;

                var initExList = node.InitExList;

                for (int i = 0; i < initExList.Count; i++)
                {
                    initExList[i] = initExList[i].Analyze(analyzer, info).Literalize();
                }

                var condExList = node.CondExList;

                if (condExList.Count > 0)
                {
                    // all but the last expression is evaluated and the result is ignored (AccessType.None),
                    // the last is read:

                    for (int i = 0; i < condExList.Count - 1; i++)
                    {
                        condExList[i] = condExList[i].Analyze(analyzer, info).Literalize();
                    }

                    condExList[condExList.Count - 1] = condExList[condExList.Count - 1].Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                }

                var actionExList = node.ActionExList;

                for (int i = 0; i < actionExList.Count; i++)
                {
                    actionExList[i] = actionExList[i].Analyze(analyzer, info).Literalize();
                }

                analyzer.EnterLoopBody();
                node.Body = node.Body.Analyze(analyzer);
                analyzer.LeaveLoopBody();

                return(node);
            }
예제 #19
0
            public override Evaluation Analyze(ItemUse node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;

                // checks for write context of key-less array operator ($a =& $x[] is ok):
                if (node.Index == null &&
                    (access == AccessType.Read ||
                     access == AccessType.ReadAndWrite ||
                     access == AccessType.ReadAndWriteAndReadRef ||
                     access == AccessType.ReadAndWriteAndReadUnknown))
                {
                    analyzer.ErrorSink.Add(Errors.EmptyIndexInReadContext, analyzer.SourceUnit, node.Span);
                    return(new Evaluation(node));
                }

                base.Analyze(node, analyzer, info);

                ExInfoFromParent sinfo = new ExInfoFromParent(node);

                switch (info.Access)
                {
                case AccessType.Write:
                case AccessType.WriteRef:
                case AccessType.ReadRef: sinfo.Access = AccessType.Write; break;

                case AccessType.ReadAndWriteAndReadRef:
                case AccessType.WriteAndReadRef:
                case AccessType.ReadAndWrite: sinfo.Access = AccessType.ReadAndWrite; break;

                case AccessType.WriteAndReadUnknown:
                case AccessType.ReadAndWriteAndReadUnknown: sinfo.Access = info.Access; break;

                case AccessType.ReadUnknown: sinfo.Access = AccessType.ReadUnknown; break;

                default: sinfo.Access = AccessType.Read; break;
                }

                ((ItemUse)node).Array.Analyze(analyzer, sinfo);

                if (node.Index != null)
                {
                    node.Index = node.Index.Analyze(analyzer, ExInfoFromParent.DefaultExInfo).Literalize();
                }

                return(new Evaluation(node));
            }
예제 #20
0
            public override Evaluation Analyze(ConcatEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                Debug.Assert(node.Expressions.Length > 0);
                access = info.Access;

                var concatChunks = AnalyzeChunks(analyzer, node.Expressions);

                node.Expressions = ChunkExpressions(concatChunks).ToArray();   // replace expressions with optimized one

                if (concatChunks.Count == 1 && concatChunks[0].HasValue)
                {
                    return(new Evaluation(node, concatChunks[0].Value)); // can be resolved during compilation time
                }
                else
                {
                    return(new Evaluation(node));
                }
            }
예제 #21
0
            internal override Statement Analyze(GlobalStmt node, Analyzer analyzer)
            {
                if (analyzer.IsThisCodeUnreachable())
                {
                    analyzer.ReportUnreachableCode(node.Span);
                    return(EmptyStmt.Unreachable);
                }

                ExInfoFromParent info = new ExInfoFromParent(node);

                info.Access = AccessType.WriteRef;
                foreach (SimpleVarUse svu in node.VarList)
                {
                    svu.Analyze(analyzer, info);
                }

                return(node);
            }
예제 #22
0
            internal override Core.AST.Statement Analyze(EchoStmt node, Analyzer analyzer)
            {
                if (analyzer.IsThisCodeUnreachable())
                {
                    analyzer.ReportUnreachableCode(node.Span);
                    return(EmptyStmt.Unreachable);
                }

                ExInfoFromParent info = ExInfoFromParent.DefaultExInfo;

                var parameters = node.Parameters;

                for (int i = 0; i < parameters.Length; i++)
                {
                    parameters[i] = parameters[i].Analyze(analyzer, info).Literalize();
                }

                return(node);
            }
예제 #23
0
            public void Analyze(GlobalCode /*!*/ ast, Analyzer /*!*/ analyzer)
            {
                analyzer.LeaveUnreachableCode();

                ExInfoFromParent info = new ExInfoFromParent(ast);

                // analyze auto-prepended inclusion (no code reachability checks):
                if (PrependedInclusion != null)
                {
                    info.Access = AccessType.None;
                    PrependedInclusion.Analyze(analyzer, info);
                }

                for (int i = 0; i < ast.Statements.Length; i++) // NOTE: ast.Statements may change during analysis, iterate in this way!
                {
                    if (analyzer.IsThisCodeUnreachable() && ast.Statements[i].IsDeclaration)
                    {
                        //unreachable declarations in global code are valid
                        analyzer.LeaveUnreachableCode();
                        ast.Statements[i] = ast.Statements[i].Analyze(analyzer);
                        analyzer.EnterUnreachableCode();
                    }
                    else
                    {
                        ast.Statements[i] = ast.Statements[i].Analyze(analyzer);
                    }
                }

                if (!ast.SourceUnit.IsPure)
                {
                    Analyzer.ValidateLabels(analyzer.ErrorSink, ast.SourceUnit, labels);
                }

                // analyze auto-prepended inclusion (no code reachability checks):
                if (AppendedInclusion != null)
                {
                    info.Access = AccessType.Read;
                    AppendedInclusion.Analyze(analyzer, info);
                }

                analyzer.LeaveUnreachableCode();
            }
예제 #24
0
            internal override Statement Analyze(JumpStmt node, Analyzer analyzer)
            {
                if (analyzer.IsThisCodeUnreachable())
                {
                    analyzer.ReportUnreachableCode(node.Span);
                    return(EmptyStmt.Unreachable);
                }

                if (node.Expression != null)
                {
                    ExInfoFromParent sinfo = ExInfoFromParent.DefaultExInfo;

                    if (node.Type == JumpStmt.Types.Return &&
                        analyzer.CurrentRoutine != null && analyzer.CurrentRoutine.Signature.AliasReturn &&
                        node.Expression is VarLikeConstructUse)
                    {
                        sinfo.Access = AccessType.ReadRef;
                    }

                    node.Expression = node.Expression.Analyze(analyzer, sinfo).Literalize();

                    if (node.Type != JumpStmt.Types.Return && node.Expression.HasValue())
                    {
                        int level = Convert.ObjectToInteger(node.Expression.GetValue());
                        if (level > analyzer.LoopNestingLevel || level < 0)
                        {
                            analyzer.ErrorSink.Add(Errors.InvalidBreakLevelCount, analyzer.SourceUnit, node.Span, level);
                        }
                    }
                }
                else if (node.Type != JumpStmt.Types.Return && analyzer.LoopNestingLevel == 0)
                {
                    analyzer.ErrorSink.Add(Errors.InvalidBreakLevelCount, analyzer.SourceUnit, node.Span, 1);
                }

                // code in the same block after return, break, continue is unreachable
                analyzer.EnterUnreachableCode();
                return(node);
            }
예제 #25
0
            public override Evaluation Analyze(BinaryEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;
                ExInfoFromParent operand_info = ExInfoFromParent.DefaultExInfo;

                Evaluation left_eval = node.LeftExpr.Analyze(analyzer, operand_info);
                Evaluation right_eval;

                // Boolean expression evaluation semantics:
                if (node.Operation == Operations.Or)
                {
                    analyzer.EnterConditionalCode();
                    right_eval = node.RightExpr.Analyze(analyzer, operand_info);
                    analyzer.LeaveConditionalCode();
                }
                else
                {
                    right_eval = node.RightExpr.Analyze(analyzer, operand_info);
                }

                Expression rightTmp, leftTmp;
                Evaluation result = Evaluation.Evaluate(node, left_eval, out leftTmp, right_eval, out rightTmp);

                node.LeftExpr  = leftTmp;
                node.RightExpr = rightTmp;

                // division by zero check:
                if ((node.Operation == Operations.Div || node.Operation == Operations.Mod) && result.HasValue && result.Value is bool && (bool)result.Value == false)
                {
                    analyzer.ErrorSink.Add(Warnings.DivisionByZero, analyzer.SourceUnit, node.RightExpr.Span);
                }
                else if ((node.Operation == Operations.Div || node.Operation == Operations.Mod) && right_eval.HasValue && right_eval.Value is int && (int)right_eval.Value == 0)
                {
                    result = new Evaluation(node, false);
                    analyzer.ErrorSink.Add(Warnings.DivisionByZero, analyzer.SourceUnit, node.RightExpr.Span);
                }

                return(result);
            }
예제 #26
0
            public override Evaluation Analyze(T node, Analyzer analyzer, ExInfoFromParent info)
            {
                bool already_resolved = constant != null;

                if (!already_resolved)
                {
                    access = info.Access;
                    ResolveName(node, analyzer);
                }

                if (constant.IsUnknown)
                {
                    return(new Evaluation(node));
                }

                KnownConstant known_const = (KnownConstant)constant;

                if (known_const.HasValue)
                {
                    // constant value is known:
                    return(new Evaluation(node, known_const.Value));
                }
                else if (already_resolved)
                {
                    // circular definition:
                    constant.ReportCircularDefinition(analyzer.ErrorSink);
                    return(new Evaluation(node));
                }
                else
                {
                    // value is not known yet, try to resolve it:
                    if (known_const.Node != null)
                    {
                        known_const.Node.Analyze(analyzer);
                    }

                    return((known_const.HasValue) ? new Evaluation(node, known_const.Value) : new Evaluation(node));
                }
            }
예제 #27
0
            public override Evaluation Analyze(AssignEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;
                ExInfoFromParent lvalue_info = new ExInfoFromParent(node);
                ExInfoFromParent rvalue_info = new ExInfoFromParent(node);

                lvalue_info.Access = AccessType.WriteRef;
                rvalue_info.Access = AccessType.ReadRef;

                var refassignex = (RefAssignEx)node;

                node.lvalue        = (VariableUse)node.LValue.Analyze(analyzer, lvalue_info).Expression;
                refassignex.rvalue = refassignex.RValue.Analyze(analyzer, rvalue_info).Literalize();

                if (refassignex.RValue is NewEx)
                {
                    //PhpException.Throw(PhpError.Deprecated, CoreResources.GetString("assign_new_as_ref_is_deprecated"));
                    analyzer.ErrorSink.Add(Warnings.AssignNewByRefDeprecated, analyzer.SourceUnit, node.Span);
                }

                return(new Evaluation(node));
            }
예제 #28
0
            internal override Statement Analyze(ExpressionStmt node, Analyzer analyzer)
            {
                if (analyzer.IsThisCodeUnreachable())
                {
                    analyzer.ReportUnreachableCode(node.Span);
                    return(EmptyStmt.Unreachable);
                }

                ExInfoFromParent info = new ExInfoFromParent(node);

                info.Access = AccessType.None;

                Evaluation expr_eval = node.Expression.Analyze(analyzer, info);

                // skip statement if it is evaluable (has no side-effects):
                if (expr_eval.HasValue)
                {
                    return(EmptyStmt.Skipped);
                }

                node.Expression = expr_eval.Expression;
                return(node);
            }
예제 #29
0
파일: ListEx.cs 프로젝트: xmaxmex/Phalanger
            public override Evaluation Analyze(ListEx node, Analyzer analyzer, ExInfoFromParent info)
            {
                access = info.Access;
                ExInfoFromParent sinfo = new ExInfoFromParent(node);

                // r-value
                if (node.RValue != null)
                {
                    node.RValue = node.RValue.Analyze(analyzer, sinfo).Literalize();
                }

                // l-values
                sinfo.Access = AccessType.Write;

                for (int i = 0; i < node.LValues.Count; i++)
                {
                    if (node.LValues[i] != null)
                    {
                        node.LValues[i] = node.LValues[i].Analyze(analyzer, sinfo).Expression;
                    }
                }

                return(new Evaluation(node));
            }
예제 #30
0
 public static void Analyze(this CallSignature /*!*/ node, Analyzer /*!*/ analyzer, RoutineSignature /*!*/ signature, ExInfoFromParent info, bool isBaseCtorCallConstrained)
 {
     node.NodeCompiler <ICallSignatureCompiler>().Analyze(node, analyzer, signature, info, isBaseCtorCallConstrained);
 }