Ejemplo n.º 1
0
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      // CCCC(indexA)SSSSSS(indexB)EEEEEE(indexC)
      
      var ifStatement = (CodeIfStatement)code;

      CodeDomCompiler.Compile(ifStatement.Condition, machine);
      //Put AX (result of condition evaluation) to BBX
      var exch = machine.CreateOperation<RegisterOperation>();
      exch.Source = MachineRegisters.AX;
      exch.Destination = MachineRegisters.BBX;
      //Jmp To Else
      var jmpToElse = machine.CreateOperation<JmpIfOperation>();
      int eCount = machine.CommandCount;    
      
      //Compile Statement
      CodeDomCompiler.Compile(ifStatement.Statement, machine);
      jmpToElse.Offset = machine.CommandCount - eCount + 1;     
      
      //Compile Else if Any
      if (ifStatement.ElseStatement != null)
      {
        //Jmp To Next
        var jmpToNext = machine.CreateOperation<JmpOperation>();
        //Modify jmpToElse
        jmpToElse.Offset++;

        int sCount = machine.CommandCount;
        CodeDomCompiler.Compile(ifStatement.ElseStatement, machine);
        jmpToNext.Offset = machine.CommandCount - sCount + 1;
      }

      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var codeExpression = (CodeObjectReference)code;

      if (codeExpression.Modifiers.Count == 0)
      {
        var op = machine.CreateOperation<GetValueOperation>();
        op.Id = codeExpression.Id;        
      }
      else
      {
        foreach (var modifier in codeExpression.Modifiers)
        {
          var functionCall = modifier as CodeObjectFunctionCall;
          if (functionCall == null) continue;

          CodeDomCompiler.Compile(modifier, machine);

          var callOp = machine.CreateOperation<ObjectMemberOperation>();
          callOp.MemberName = codeExpression.Id;
        }
      }

      if (codeExpression.Next != null)
      {
        machine.CreateOperation<PushOperation>();
        CodeDomCompiler.Compile(codeExpression.Next, machine);
      }

      return machine;
   }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      // CCCC(indexA)SSSSSS(indexC)
      var whileStatement = (CodeWhileStatement)code;

      int cCount = machine.CommandCount;

      CodeDomCompiler.Compile(whileStatement.Condition, machine);
      //Put AX (result of condition evaluation) to BBX
      var exch = machine.CreateOperation<RegisterOperation>();
      exch.Source = MachineRegisters.AX;
      exch.Destination = MachineRegisters.BBX;
      //Jmp To Else
      var jmpToNext = machine.CreateOperation<JmpIfOperation>();
      int eCount = machine.CommandCount;    
      
      //Compile Statement
      CodeDomCompiler.Compile(whileStatement.Statement, machine);

      var jmpToCondition = machine.CreateOperation<JmpIfOperation>();
      jmpToCondition.Offset = cCount - machine.CommandCount + 1;

      jmpToNext.Offset = machine.CommandCount - eCount + 1;
      
      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var codeSwitch = (CodeSwitchStatement)code;

      //switch(a) { case c1 : s1; case c2 : s2; default : s3 }
      //~
      //switch_expr = a;
      //if (a == c1) s1
      //else if (a == c2) s2
      //else s3

      _sid++;

      var block = new CodeBlockStatement { SourceSpan = codeSwitch.SourceSpan };

      var switchExpr = new CodeAssignExpression(
        "#switch_"+_sid, codeSwitch.Expression);
         
      var ifStatement = BuildNextIf(codeSwitch.Cases, 0);

      block.Statements.Add(new CodeExpressionStatement(switchExpr));
      block.Statements.Add(ifStatement);

      CodeDomCompiler.Compile(block, machine);

      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var op = machine.CreateOperation<ValueOperation>();
      op.Value = ((CodeValueReference)code).Value;
      op.SourceObject = code;

      return machine;
   }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var ret = (CodeReturnStatement)code;

      CodeDomCompiler.Compile(ret.Expression, machine);
      machine.CreateOperation<RetOperation>();

      return machine;
    }
Ejemplo n.º 7
0
        private void SetEndPragma(CodeObject co)
        {
            if (co == null)
                //We encountered an error - we can ignore this, since it will result in a compiler error
                return;

            co.location.endLine = t.line;
            co.location.endColumn = t.col + t.val.Length;
        }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var codeExpression = (CodeVariableReference)code;

      var op = machine.CreateOperation<GetValueOperation>();
      op.Id = codeExpression.Id;
      op.SourceObject = codeExpression;

      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var blockStatement = (CodeBlockStatement)code;

      foreach (var statement in blockStatement.Statements)
      {
        CodeDomCompiler.Compile(statement, machine);
      }

      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var codeExpression = (CodeAssignExpression)code;
      
      CodeDomCompiler.Compile(codeExpression.RightExpression, machine);

      var op = machine.CreateOperation<SetValueOperation>();
      op.Id = codeExpression.Id;
      op.SourceObject = code;

      return machine;
    }
Ejemplo n.º 11
0
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var program = (CodeProgram)code;

      foreach (var statement in program.Statements)
        CodeDomCompiler.Compile(statement, machine);
      
      machine.CreateOperation<RetOperation>();

      //TODO: Functions
      //foreach (CodeObject function in program.Functions)
      //  Compile(function, machine);

      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var forStatement = (CodeForEachStatement)code;

      //foreach (i in c) statement ~
      //
      //f_ = c.GetEnumerator();
      //while(f_.Next()) {i = f_.Current; statement; }

      _sid++;
      string fName = "#ForEach_" + _sid;

      var fblock = new CodeBlockStatement();

      var f = new CodeAssignExpression(fName, forStatement.Container);
      var f1 = new CodeAssignExpression(fName, 
        new CodeObjectReference(fName, 
           new CodeObjectReference("GetEnumerator", null,
            new CodeObject[] { new CodeObjectFunctionCall(new CodeExpression[0]) }), new CodeObject[0]));

      var fwhileBlock = new CodeBlockStatement();

      var i = new CodeAssignExpression(forStatement.Id.Id,
        new CodeObjectReference(fName,
           new CodeObjectReference("get_Current", null,
            new CodeObject[] { new CodeObjectFunctionCall(new CodeExpression[0]) }), new CodeObject[0]));

      fwhileBlock.Statements.Add(new CodeExpressionStatement(i));
      fwhileBlock.Statements.Add(forStatement.Statement);

      var fwhile = new CodeWhileStatement(
        new CodeObjectReference(fName,
           new CodeObjectReference("MoveNext", null,
            new CodeObject[] { new CodeObjectFunctionCall(new CodeExpression[0]) }), new CodeObject[0]),
        fwhileBlock);

      fblock.Statements.Add(new CodeExpressionStatement(f));
      fblock.Statements.Add(new CodeExpressionStatement(f1));
      fblock.Statements.Add(fwhile);

      CodeDomCompiler.Compile(fblock, machine);

      return machine;
    }
Ejemplo n.º 13
0
 internal void ValidateIdentifiers(CodeObject e)
 {
     if (e is CodeCompileUnit)
     {
         ValidateCodeCompileUnit((CodeCompileUnit)e);
     }
     else if (e is CodeComment)
     {
         ValidateComment((CodeComment)e);
     }
     else if (e is CodeExpression)
     {
         ValidateExpression((CodeExpression)e);
     }
     else if (e is CodeNamespace)
     {
         ValidateNamespace((CodeNamespace)e);
     }
     else if (e is CodeNamespaceImport)
     {
         ValidateNamespaceImport((CodeNamespaceImport)e);
     }
     else if (e is CodeStatement)
     {
         ValidateStatement((CodeStatement)e);
     }
     else if (e is CodeTypeMember)
     {
         ValidateTypeMember((CodeTypeMember)e);
     }
     else if (e is CodeTypeReference)
     {
         ValidateTypeReference((CodeTypeReference)e);
     }
     else if (e is CodeDirective)
     {
         ValidateCodeDirective((CodeDirective)e);
     }
     else
     {
         throw new ArgumentException(SR.Format(SR.InvalidElementType, e.GetType().FullName), nameof(e));
     }
 }
Ejemplo n.º 14
0
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var forStatement = (CodeForStatement)code;

      //for (init; cond; next) statement ~
      //
      //init;
      //while(cond) { statement; next;}

      CodeDomCompiler.Compile(forStatement.Init, machine);

      var body = new CodeBlockStatement();
      body.Statements.Add(forStatement.Statement);
      body.Statements.Add(new CodeExpressionStatement(forStatement.Next));
      var newWhile = new CodeWhileStatement(forStatement.Condition, body);

      CodeDomCompiler.Compile(newWhile, machine);
      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var codeExpression = (CodeBinaryOperator)code;

      CodeDomCompiler.Compile(codeExpression.Right, machine);
      var op = machine.CreateOperation<PushOperation>();
      op.SourceObject = codeExpression.Right;

      CodeDomCompiler.Compile(codeExpression.Left, machine);
      op = machine.CreateOperation<PushOperation>();
      op.SourceObject = codeExpression.Left;

      Operation sop;
      switch (codeExpression.Type)
      {
        case OperatorType.Plus:
          sop = machine.CreateOperation<AddOperation>();
          break;
        case OperatorType.Minus:
          sop = machine.CreateOperation<SubOperation>();
          break;
        case OperatorType.Mul:
          sop = machine.CreateOperation<MulOperation>();
          break;
        case OperatorType.Mod:
          sop = machine.CreateOperation<ModOperation>();
          break;
        case OperatorType.Div:
          sop = machine.CreateOperation<DivOperation>();
          break;
        default:
          var gop = machine.CreateOperation<GenericOperation>();
          gop.Symbol = Mapping[codeExpression.Type];
          sop = gop;
          break;
      }
      sop.SourceObject = codeExpression;

      var pop = machine.CreateOperation<PopOperation>();
      pop.SourceObject = codeExpression;

      return machine;
    }
    public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
    {
      var call = (CodeObjectFunctionCall)code;

      // AX = function name
      // BX = parameter count

      // stack is full of parameters

      foreach (var codeParameter in call.Parameters)
      {
        CodeDomCompiler.Compile(codeParameter, machine);
        var op = machine.CreateOperation<PushOperation>();
      }
      
      var countOp = machine.CreateOperation<RegisterOperation>();
      countOp.Destination = MachineRegisters.BX;
      countOp.Value = call.Parameters.Count;

      return machine;
   }
Ejemplo n.º 17
0
 /// <summary>
 /// This method returns a ScriptSource object from a System.CodeDom.CodeObject.
 /// This is a factory method for creating a ScriptSources with this language binding.
 ///
 /// The expected CodeDom support is extremely minimal for syntax-independent expression of semantics.
 ///
 /// Languages may do more, but hosts should only expect CodeMemberMethod support,
 /// and only sub nodes consisting of the following:
 ///     CodeSnippetStatement
 ///     CodeSnippetExpression
 ///     CodePrimitiveExpression
 ///     CodeMethodInvokeExpression
 ///     CodeExpressionStatement (for holding MethodInvoke)
 /// </summary>
 public ScriptSource CreateScriptSource(CodeObject content, string path)
 {
     return(CreateScriptSource(content, path, SourceCodeKind.File));
 }
Ejemplo n.º 18
0
 protected Default(Parser parser, CodeObject parent)
     : base(parser, parent)
 {
     parser.NextToken();              // Move past 'default'
     ParseTerminatorAndBody(parser);  // Parse ':' and body (if any)
 }
Ejemplo n.º 19
0
        private CodeObject GetVariable(CodeObject parent)
        {
            CodeObject function = parent;

            while (true)
            {
                Token token = this.ReadToken();
                if (token.Type == Scorpio.Compiler.TokenType.Period)
                {
                    function = new CodeMember(this.ReadIdentifier(), function);
                }
                else if (token.Type == Scorpio.Compiler.TokenType.LeftBracket)
                {
                    CodeObject member = this.GetObject();
                    this.ReadRightBracket();
                    if (member is CodeScriptObject)
                    {
                        ScriptObject obj4 = ((CodeScriptObject)member).Object;
                        if (member.Not)
                        {
                            function = new CodeMember(!obj4.LogicOperation(), function);
                        }
                        else if (member.Minus)
                        {
                            ScriptNumber number = obj4 as ScriptNumber;
                            if (number == null)
                            {
                                throw new ParserException("Script Object Type [" + obj4.Type + "] is cannot use [-] sign", token);
                            }
                            function = new CodeMember(number.Minus().KeyValue, function);
                        }
                        else if (member.Negative)
                        {
                            ScriptNumber number2 = obj4 as ScriptNumber;
                            if (number2 == null)
                            {
                                throw new ParserException("Script Object Type [" + obj4.Type + "] is cannot use [~] sign", token);
                            }
                            function = new CodeMember(number2.Negative().KeyValue, function);
                        }
                        else
                        {
                            function = new CodeMember(obj4.KeyValue, function);
                        }
                    }
                    else
                    {
                        function = new CodeMember(member, function);
                    }
                }
                else if (token.Type == Scorpio.Compiler.TokenType.LeftPar)
                {
                    this.UndoToken();
                    function = this.GetFunction(function);
                }
                else
                {
                    this.UndoToken();
                    return(function);
                }
                function.StackInfo = new StackInfo(this.m_strBreviary, token.SourceLine);
            }
        }
Ejemplo n.º 20
0
        private static string GenerateCode(CodeObject c, CodeDomProvider provider)
        {
            var sb = new StringBuilder();
            var writer = new StringWriter(sb);
            var options = new CodeGeneratorOptions();

            if (c is CodeStatement)
            {
                provider.GenerateCodeFromStatement((CodeStatement)c, writer, options);
            }
            else if (c is CodeCompileUnit)
            {
                provider.GenerateCodeFromCompileUnit((CodeCompileUnit)c, writer, options);
            }
            else if (c is CodeExpression)
            {
                provider.GenerateCodeFromExpression((CodeExpression)c, writer, options);
            }
            else if (c is CodeTypeMember)
            {
                provider.GenerateCodeFromMember((CodeTypeMember)c, writer, options);
            }
            else if (c is CodeTypeDeclaration)
            {
                provider.GenerateCodeFromType((CodeTypeDeclaration)c, writer, options);
            }
            else if (c is CodeNamespace)
            {
                provider.GenerateCodeFromNamespace((CodeNamespace)c, writer, options);
            }
            else
            {
                Assert.False(true, $"Unknown type: {c.GetType()}");
            }

            return sb.ToString();
        }
Ejemplo n.º 21
0
 /// <summary>
 /// Parse a <see cref="Lock"/>.
 /// </summary>
 public static Lock Parse(Parser parser, CodeObject parent, ParseFlags flags)
 {
     return(new Lock(parser, parent));
 }
Ejemplo n.º 22
0
        //internal Dictionary<Block, List<Expression>> BlockExpressions { get; set; } =
        //    new Dictionary<Block, List<Expression>>();

        public DecompileContext(CodeObject obj)
        {
            Object = obj;
        }
Ejemplo n.º 23
0
        protected void AssertEqual(CodeObject c, string expected)
        {
            // Validate all identifiers are valid
            CodeGenerator.ValidateIdentifiers(c);

            // Generate code
            CodeDomProvider provider = GetProvider();
            string code = GenerateCode(c, provider);

            // Make sure the code matches what we expected
            try
            {
                Assert.Equal(CoalesceWhitespace(expected), CoalesceWhitespace(code));
            }
            catch
            {
                Console.WriteLine(code);
                throw;
            }

            // Serialize and deserialize the CodeObject, and make sure code generated for it
            // is the same as the original.
            CodeObject clone = BinaryFormatterHelpers.Clone(c);
            string cloneCode = GenerateCode(clone, provider);
            Assert.Equal(code, cloneCode);
        }
Ejemplo n.º 24
0
        private static string GenerateCode(CodeObject c, CodeDomProvider provider)
        {
            var sb = new StringBuilder();
            var writer = new StringWriter(sb);
            var options = new CodeGeneratorOptions();

            if (c is CodeStatement)
            {
                provider.GenerateCodeFromStatement((CodeStatement)c, writer, options);
            }
            else if (c is CodeCompileUnit)
            {
                provider.GenerateCodeFromCompileUnit((CodeCompileUnit)c, writer, options);
            }
            else if (c is CodeExpression)
            {
                provider.GenerateCodeFromExpression((CodeExpression)c, writer, options);
            }
            else if (c is CodeTypeMember)
            {
                provider.GenerateCodeFromMember((CodeTypeMember)c, writer, options);
            }
            else if (c is CodeTypeDeclaration)
            {
                provider.GenerateCodeFromType((CodeTypeDeclaration)c, writer, options);
            }
            else if (c is CodeNamespace)
            {
                provider.GenerateCodeFromNamespace((CodeNamespace)c, writer, options);
            }
            else
            {
                throw new ArgumentException($"Tests not set up for unexpected type: {c.GetType()}");
            }

            return sb.ToString();
        }
Ejemplo n.º 25
0
 public CodeObject Context;            //变量
 public CodeRegion(CodeObject Context) { this.Context = Context; }
Ejemplo n.º 26
0
	// Validate all identifiers in a CodeDom tree.
	public static void ValidateIdentifiers(CodeObject e)
			{
				Validator.Validate(e);
			}
Ejemplo n.º 27
0
        public void Constructor0_Deny_Unrestricted()
        {
            CodeObject co = new CodeObject();

            Assert.IsNotNull(co.UserData, "UserData");
        }
Ejemplo n.º 28
0
 protected BitwiseXorAssign(Parser parser, CodeObject parent)
     : base(parser, parent)
 {
 }
Ejemplo n.º 29
0
 /// <summary>
 /// Create a <see cref="Finally"/>.
 /// </summary>
 public Finally(CodeObject body)
     : base(body, false)
 {
 }
Ejemplo n.º 30
0
 public CodeMember(object value, CodeObject parent)
 {
     this.Parent = parent;
     this.MemberValue = value;
     this.Type = MEMBER_TYPE.VALUE;
 }
Ejemplo n.º 31
0
 /// <summary>
 /// Parse a <see cref="Finally"/>.
 /// </summary>
 public static Finally Parse(Parser parser, CodeObject parent)
 {
     return(new Finally(parser, parent));
 }
Ejemplo n.º 32
0
 protected Multiply(Parser parser, CodeObject parent)
     : base(parser, parent)
 {
 }
Ejemplo n.º 33
0
 /// <summary>
 /// Parse an <see cref="ElIfDirective"/>.
 /// </summary>
 public static ElIfDirective Parse(Parser parser, CodeObject parent, ParseFlags flags)
 {
     return(new ElIfDirective(parser, parent));
 }
Ejemplo n.º 34
0
 /// <summary>
 /// Parse an <see cref="ElIfDirective"/>.
 /// </summary>
 public ElIfDirective(Parser parser, CodeObject parent)
     : base(parser, parent)
 {
 }
Ejemplo n.º 35
0
 /// <summary>
 /// Parse a <see cref="DocC"/>.
 /// </summary>
 public DocC(Parser parser, CodeObject parent)
 {
     ParseTag(parser, parent);  // Ignore any attributes
 }
Ejemplo n.º 36
0
 /// <summary>
 /// Create a <see cref="Default"/>.
 /// </summary>
 public Default(CodeObject body)
     : base(body)
 {
 }
Ejemplo n.º 37
0
 /// <devdoc>
 ///    <para>
 ///       Validates a tree to check if all the types and idenfier names follow the rules of an identifier
 ///       in a langauge independent manner.
 ///    </para>
 /// </devdoc>
 public static void ValidateIdentifiers(CodeObject e)
 {
     throw new NotImplementedException();
 }
Ejemplo n.º 38
0
 /// <summary>
 /// Prepare a fresh frame context and continuation for the code object. This will set it up to be run from
 /// scratch.
 /// </summary>
 /// <param name="newProgram">The code to prepare to run.</param>
 /// <returns>Scheduling state containing the the context that the interpreter can use to run the program as
 /// well as the continuation to kick it off (and resume it later).</returns>
 private ScheduledTaskRecord PrepareFrameContext(CodeObject newProgram)
 {
     return(PrepareFrameContext(newProgram, null));
 }
Ejemplo n.º 39
0
        /// <summary>
        /// Parse an expression, stopping when default terminators, or the specified terminators, or a higher-precedence
        /// operator is encountered.
        /// </summary>
        /// <param name="parser">The parser object.</param>
        /// <param name="parent">The parent object.</param>
        /// <param name="isTopLevel">True if EOL comments can be associated with the expression during parsing - generally
        /// true if the parent is a statement or expression list, but with some exceptions.</param>
        /// <param name="terminator">Optional terminating characters (null if none).</param>
        /// <param name="flags">Parsing flags.</param>
        /// <returns>The parsed <see cref="Expression"/>.</returns>
        public static Expression Parse(Parser parser, CodeObject parent, bool isTopLevel, string terminator, ParseFlags flags)
        {
            // Save the starting token of the expression for later
            Token startingToken = parser.Token;

            // Start a new Unused list in the parser
            parser.PushUnusedList();

            // Parse an expression, which can be in one of the following formats:
            //   - An identifier token, optionally followed by an operator (which is parsed only if precedence rules determine it should be)
            //   - An operator (which will itself look for previous and/or following expressions when parsed)
            //   - An open paren, expression, close paren sequence (handled by the installed parse-point above), optionally followed by an operator
            // Any other sequence will cause parsing of the expression to cease.
            // The expression will be terminated by any of ';,}]', or other specified terminator.

            // Create a string of possible terminators (assuming 1 char terminators for now)
            string terminators = Statement.ParseTokenTerminator + ParseTokenSeparator + Block.ParseTokenEnd + Index.ParseTokenEnd + terminator;

            // Keep a reference to the last token so we can move any skipped non-EOL comments to the expression later
            Token lastToken = parser.LastToken;

            // Loop until EOF or we find a terminator, or for directive expressions stop if we find a comment or a token on a new line.
            // NOTE: Keep this logic in sync with the 'if' statement further down in the loop that checks for termination.
            while (parser.TokenText != null &&
                   (parser.TokenText.Length != 1 || terminators.IndexOf(parser.TokenText[0]) < 0) &&
                   (!parser.InDirectiveExpression || ((parser.LastToken.TrailingComments == null || parser.LastToken.TrailingComments.Count == 0) && !parser.Token.IsFirstOnLine)))
            {
process_next:
                bool skipTerminationCheck = false;

                // Process the current token (will process operators)
                CodeObject obj = parser.ProcessToken(parent, flags | ParseFlags.Expression);
                if (obj != null)
                {
                    // If we got something, save it for later.
                    // Don't move any EOL comments here - they should have already been processed.

                    if (obj is CompilerDirective)
                    {
                        // If we have a compiler directive, and there's a preceeding unused object, add it there
                        CodeObject lastUnusedCodeObject = parser.LastUnusedCodeObject;
                        if (lastUnusedCodeObject != null && !(lastUnusedCodeObject is CompilerDirective))
                        {
                            lastUnusedCodeObject.AttachAnnotation((CompilerDirective)obj, AnnotationFlags.IsPostfix);
                        }
                        else
                        {
                            parser.AddUnused(obj);  // Add the object to the unused list
                            skipTerminationCheck = true;
                        }
                    }
                    else
                    {
                        obj.ParseUnusedAnnotations(parser, parent, true);  // Parse any annotations from the Unused list
                        parser.AddUnused(obj);                             // Add the object to the unused list
                    }
                }

                // Stop if EOF or we find a terminator, or for directive expressions stop if we find a comment or a token on a new line.
                // NOTE: Keep this logic in sync with that in the condition of the parent 'while' loop.
                if (parser.TokenText == null ||
                    (parser.TokenText.Length == 1 && terminators.IndexOf(parser.TokenText[0]) >= 0) ||
                    (parser.InDirectiveExpression && ((parser.LastToken.TrailingComments != null && parser.LastToken.TrailingComments.Count != 0) || parser.Token.IsFirstOnLine)))
                {
                    // Don't abort here on a '{' terminator if we're in a doc comment and we appear to have type arguments using
                    // braces (as opposed to an Initializer after a NewObject).  Go process the next object immediately instead.
                    if (parser.InDocComment && parser.TokenText == TypeRefBase.ParseTokenAltArgumentStart && parser.HasUnusedIdentifier &&
                        TypeRefBase.PeekTypeArguments(parser, TypeRefBase.ParseTokenAltArgumentEnd, flags))
                    {
                        goto process_next;
                    }
                    break;
                }

                // If the current token is the start of a compiler directive, check for special situations in which we want to skip
                // the termination check below.  This allows the directive to be attached to preceeding code objects such as literals
                // or operators, while not attaching to simple name or type expressions which might be part of a namespace or type header.
                if (parser.TokenText == CompilerDirective.ParseToken)
                {
                    CodeObject lastUnusedCodeObject = parser.LastUnusedCodeObject;
                    if (lastUnusedCodeObject is Literal || lastUnusedCodeObject is Operator)
                    {
                        skipTerminationCheck = true;
                        // Also, capture any pending trailing comments
                        if (obj != null)
                        {
                            obj.MoveCommentsAsPost(parser.LastToken);
                        }
                    }
                }

                // If we don't have a specific terminating character, then we're parsing a sub-expression and we should stop when we
                // get to an invalid operator, or an operator of greater precedence.  Skip this check if we just parsed a compiler
                // directive and didn't have a preceeding code object to attach it to, or if we're about to parse a compiler directive
                // and we have an unused code object that we'd like to attach it to.
                if (terminator == null && !skipTerminationCheck)
                {
                    // Check for '{' when used inside a doc comment in a generic type constructor or generic method instance
                    if (parser.InDocComment && parser.TokenText == TypeRefBase.ParseTokenAltArgumentStart &&
                        TypeRefBase.PeekTypeArguments(parser, TypeRefBase.ParseTokenAltArgumentEnd, flags))
                    {
                        continue;
                    }

                    // Check if the current token represents a valid operator
                    Parser.OperatorInfo operatorInfo = parser.GetOperatorInfoForToken();

                    // If the current token doesn't look like a valid operator, we're done with the expression
                    if (operatorInfo == null)
                    {
                        break;
                    }

                    // We have an operator - check if our parent is also an operator
                    if (parent is Operator)
                    {
                        // Special cases for Types:  Some operator symbols are overloaded and can also be part
                        // of a type name.  We must detect these here, and continue processing in these cases,
                        // skipping the operator precedence checks below that terminate the current expression.

                        // Check for '[' when used in an array type name
                        if (parser.TokenText == TypeRefBase.ParseTokenArrayStart && TypeRefBase.PeekArrayRanks(parser))
                        {
                            continue;
                        }

                        // Check for '<' when used in a generic type constructor or generic method instance
                        if (parser.TokenText == TypeRefBase.ParseTokenArgumentStart && TypeRefBase.PeekTypeArguments(parser, TypeRefBase.ParseTokenArgumentEnd, flags))
                        {
                            continue;
                        }

                        // Do NOT check for '?' used for nullable types, because it applies to the entire
                        // expression on the left, so we DO want to terminate processing.

                        // Determine the precedence of the parent operator
                        // NOTE: See the bottom of Operator.cs for a quick-reference of operator precedence.
                        int parentPrecedence = ((Operator)parent).GetPrecedence();

                        // Stop parsing if the parent operator has higher precedence
                        if (parentPrecedence < operatorInfo.Precedence)
                        {
                            break;
                        }

                        // If the parent has the same precedence, stop parsing if the operator is left-associative
                        if (parentPrecedence == operatorInfo.Precedence && operatorInfo.LeftAssociative)
                        {
                            break;
                        }
                    }
                }
            }

            // Get the expression
            Expression expression = parser.RemoveLastUnusedExpression();

            if (expression != null)
            {
                // Attach any skipped non-EOL comments from the front of the expression, but only if we're a top-level expression
                // (otherwise, comments that preceed a sub-expression will get attached to an outer expression instead).  This
                // prevents lost comments in places such as between a 'return' and the expression that follows.
                if (isTopLevel)
                {
                    expression.MoveAllComments(lastToken);
                }

                // If this is a top-level expression or if the next token is a close paren, move any trailing comments on the last
                // token of the expression as post comments. This prevents lost comments in places such as when some trailing parts of
                // an 'if' conditional expression are commented-out, or the trailing parts of any sub-expression before a close paren.
                if ((isTopLevel || parser.TokenText == ParseTokenEndGroup) && parser.LastToken.HasTrailingComments && !parser.InDirectiveExpression)
                {
                    expression.MoveCommentsAsPost(parser.LastToken);
                }
            }

            // Flush remaining unused objects as Unrecognized objects
            while (parser.HasUnused)
            {
                Expression preceedingUnused = parser.RemoveLastUnusedExpression(true);
                if (preceedingUnused != null)
                {
                    if (expression == null)
                    {
                        expression = new Unrecognized(false, parser.InDocComment, preceedingUnused);
                    }
                    else if (expression is Unrecognized && !expression.HasParens)
                    {
                        ((Unrecognized)expression).AddLeft(preceedingUnused);
                    }
                    else
                    {
                        expression = new Unrecognized(false, parser.InDocComment, preceedingUnused, expression);
                    }
                }
                else
                {
                    // If we have no expression to put them on, then parse any preceeding compiler directives into a temp object for later retrieval
                    if (expression == null)
                    {
                        expression = new TempExpr();
                    }
                    expression.ParseUnusedAnnotations(parser, parent, true);
                    break;
                }
            }
            if (expression is Unrecognized)
            {
                ((Unrecognized)expression).UpdateMessage();
            }

            parser.Unused.Clear();

            // Restore the previous Unused list in the parser
            parser.PopUnusedList();

            if (expression != null)
            {
                // Get any EOL comments
                if (parser.LastToken.HasTrailingComments)
                {
                    expression.MoveEOLComment(parser.LastToken);
                }

                // Set the parent starting token to the beginning of the expression
                parser.ParentStartingToken = startingToken;
            }

            return(expression);
        }
Ejemplo n.º 40
0
 /// <summary>
 /// This method returns a ScriptSource object from a System.CodeDom.CodeObject.
 /// This is a factory method for creating a ScriptSources with this language binding.
 ///
 /// The expected CodeDom support is extremely minimal for syntax-independent expression of semantics.
 ///
 /// Languages may do more, but hosts should only expect CodeMemberMethod support,
 /// and only sub nodes consisting of the following:
 ///     CodeSnippetStatement
 ///     CodeSnippetExpression
 ///     CodePrimitiveExpression
 ///     CodeMethodInvokeExpression
 ///     CodeExpressionStatement (for holding MethodInvoke)
 /// </summary>
 public ScriptSource CreateScriptSource(CodeObject content)
 {
     return(CreateScriptSource(content, null, SourceCodeKind.File));
 }
Ejemplo n.º 41
0
 /// <summary>
 /// Parse an expression, stopping when default terminators, or the specified terminators, or a higher-precedence
 /// operator is encountered.
 /// </summary>
 /// <param name="parser">The parser object.</param>
 /// <param name="parent">The parent object.</param>
 /// <param name="isTopLevel">True if EOL comments can be associated with the expression during parsing - generally
 /// true if the parent is a statement or expression list, but with some exceptions.</param>
 /// <param name="terminator">Optional terminating characters (null if none).</param>
 /// <returns>The parsed <see cref="Expression"/>.</returns>
 public static Expression Parse(Parser parser, CodeObject parent, bool isTopLevel, string terminator)
 {
     return(Parse(parser, parent, isTopLevel, terminator, ParseFlags.None));
 }
Ejemplo n.º 42
0
 /// <summary>
 /// This method returns a ScriptSource object from a System.CodeDom.CodeObject.
 /// This is a factory method for creating a ScriptSources with this language binding.
 ///
 /// The expected CodeDom support is extremely minimal for syntax-independent expression of semantics.
 ///
 /// Languages may do more, but hosts should only expect CodeMemberMethod support,
 /// and only sub nodes consisting of the following:
 ///     CodeSnippetStatement
 ///     CodeSnippetExpression
 ///     CodePrimitiveExpression
 ///     CodeMethodInvokeExpression
 ///     CodeExpressionStatement (for holding MethodInvoke)
 /// </summary>
 public ScriptSource CreateScriptSource(CodeObject content, SourceCodeKind kind)
 {
     return(CreateScriptSource(content, null, kind));
 }
Ejemplo n.º 43
0
 public CodeMember(CodeObject member, CodeObject parent)
 {
     this.MemberObject = member;
     this.Parent = parent;
     this.Type = MEMBER_TYPE.OBJECT;
 }
Ejemplo n.º 44
0
 /// <summary>
 /// Parse a <see cref="BitwiseXorAssign"/> operator.
 /// </summary>
 public static new BitwiseXorAssign Parse(Parser parser, CodeObject parent, ParseFlags flags)
 {
     return(new BitwiseXorAssign(parser, parent));
 }
Ejemplo n.º 45
0
 /// <summary>
 /// Parse an <see cref="Expression"/>.
 /// </summary>
 public static Expression Parse(Parser parser, CodeObject parent, bool isTopLevel, ParseFlags flags)
 {
     return(Parse(parser, parent, isTopLevel, null, flags));
 }
Ejemplo n.º 46
0
 /// <summary>
 /// Parse a <see cref="DocCDATA"/>.
 /// </summary>
 public static new DocCDATA Parse(Parser parser, CodeObject parent, ParseFlags flags)
 {
     return(new DocCDATA(parser, parent));
 }
Ejemplo n.º 47
0
        /// <summary>
        /// Parse a list of <see cref="Expression"/>s.
        /// </summary>
        public static ChildList <Expression> ParseList(Parser parser, CodeObject parent, string terminator, ParseFlags flags, bool allowSingleNullList)
        {
            ChildList <Expression> list   = null;
            bool skipStatementTerminators = (terminator == Initializer.ParseTokenEnd);
            bool lastCommaFirstOnLine     = false;

            while (true)
            {
                Expression expression = Parse(parser, parent, true, terminator, flags);
                bool       hasComma   = (parser.TokenText == ParseTokenSeparator);
                if (expression != null)
                {
                    // Force the expression to first-on-line if the last comma was (handles special-case
                    // formatting where the commas preceed the list items instead of following them).
                    if (lastCommaFirstOnLine)
                    {
                        expression.IsFirstOnLine = true;
                    }

                    // Get rid of any parens around the expression if they're not used on the code object by default
                    if (AutomaticFormattingCleanup && !parser.IsGenerated && expression.HasParens && !expression.HasParensDefault)
                    {
                        expression.HasParens = false;
                    }
                }

                if (expression is TempExpr)
                {
                    // If we got a TempExpr, move any directives as postfix on the previous expression
                    if (list != null && list.Count > 0)
                    {
                        Expression previous = list.Last;
                        foreach (Annotation annotation in expression.Annotations)
                        {
                            if (annotation is CompilerDirective)
                            {
                                previous.AttachAnnotation(annotation, AnnotationFlags.IsPostfix);
                            }
                        }
                    }
                }
                else if (expression != null || allowSingleNullList || hasComma)
                {
                    if (list == null)
                    {
                        list = new ChildList <Expression>(parent);
                    }
                    list.Add(expression);
                }

                // Continue processing if we have a ','.  Also treat ';' like a comma if we're parsing an Initializer
                // for better parsing of bad code (such as statements where an expression is expected).
                if (hasComma || (skipStatementTerminators && parser.TokenText == Statement.ParseTokenTerminator))
                {
                    lastCommaFirstOnLine = parser.Token.IsFirstOnLine;
                    parser.NextToken();  // Move past ',' (or ';')
                    if (expression != null)
                    {
                        // Move any EOL comment, and any regular comments as Post comments
                        expression.MoveEOLComment(parser.LastToken, false, false);

                        // Move any following regular comments as Post comments if on a line by themselves
                        if (parser.Token.IsFirstOnLine)
                        {
                            expression.MoveCommentsAsPost(parser.LastToken);
                        }
                    }
                }
                else
                {
                    break;
                }
            }
            return(list);
        }
 public ExecutableMachine Compile(CodeObject code, ExecutableMachine machine)
 {
   return CodeDomCompiler.Compile(((CodeExpressionStatement)code).Expression, machine);
 }
Ejemplo n.º 49
0
 /// <summary>
 /// Parse a list of <see cref="Expression"/>s.
 /// </summary>
 public static ChildList <Expression> ParseList(Parser parser, CodeObject parent, string terminator)
 {
     return(ParseList(parser, parent, terminator, ParseFlags.None, false));
 }
Ejemplo n.º 50
0
 /// <summary>
 /// Create a <see cref="Lock"/>.
 /// </summary>
 public Lock(Expression target, CodeObject body)
     : base(body, false)
 {
     Target = target;
 }
Ejemplo n.º 51
0
 /// <summary>
 /// Parse an <see cref="Expression"/>.
 /// </summary>
 protected Expression(Parser parser, CodeObject parent)
     : base(parser, parent)
 {
 }
Ejemplo n.º 52
0
 protected Lock(Parser parser, CodeObject parent)
     : base(parser, parent)
 {
     ParseKeywordArgumentBody(parser, ref _target, false, false);
 }
 /// <summary>
 /// Parse a <see cref="DocInclude"/>.
 /// </summary>
 public static new DocInclude Parse(Parser parser, CodeObject parent, ParseFlags flags)
 {
     return(new DocInclude(parser, parent));
 }
Ejemplo n.º 54
0
 public static void ValidateIdentifiers(CodeObject e)
 {
     CodeValidator codeValidator = new CodeValidator(); // This has internal state and hence is not static
     codeValidator.ValidateIdentifiers(e);
 }
Ejemplo n.º 55
0
        private CodeObject GetOneObject()
        {
            CodeObject parent = null;
            Token      token  = this.ReadToken();
            bool       flag   = false;
            bool       flag2  = false;
            bool       flag3  = false;
            CALC       nONE   = CALC.NONE;

            while (true)
            {
                if (token.Type == Scorpio.Compiler.TokenType.Not)
                {
                    flag = true;
                }
                else if (token.Type == Scorpio.Compiler.TokenType.Minus)
                {
                    flag2 = true;
                }
                else
                {
                    if (token.Type != Scorpio.Compiler.TokenType.Negative)
                    {
                        break;
                    }
                    flag3 = true;
                }
                token = this.ReadToken();
            }
            if (token.Type == Scorpio.Compiler.TokenType.Increment)
            {
                nONE  = CALC.PRE_INCREMENT;
                token = this.ReadToken();
            }
            else if (token.Type == Scorpio.Compiler.TokenType.Decrement)
            {
                nONE  = CALC.PRE_DECREMENT;
                token = this.ReadToken();
            }
            switch (token.Type)
            {
            case Scorpio.Compiler.TokenType.LeftBrace:
                this.UndoToken();
                parent = this.GetTable();
                break;

            case Scorpio.Compiler.TokenType.LeftPar:
                parent = new CodeRegion(this.GetObject());
                this.ReadRightParenthesis();
                break;

            case Scorpio.Compiler.TokenType.LeftBracket:
                this.UndoToken();
                parent = this.GetArray();
                break;

            case Scorpio.Compiler.TokenType.Function:
                this.UndoToken();
                parent = new CodeFunction(this.ParseFunctionDeclaration(false));
                break;

            case Scorpio.Compiler.TokenType.Boolean:
            case Scorpio.Compiler.TokenType.Number:
            case Scorpio.Compiler.TokenType.String:
            case Scorpio.Compiler.TokenType.SimpleString:
                parent = new CodeScriptObject(this.m_script, token.Lexeme);
                break;

            case Scorpio.Compiler.TokenType.Null:
                parent = new CodeScriptObject(this.m_script, null);
                break;

            case Scorpio.Compiler.TokenType.Eval:
                parent = this.GetEval();
                break;

            case Scorpio.Compiler.TokenType.Identifier:
                parent = new CodeMember((string)token.Lexeme);
                break;

            default:
                throw new ParserException("Object起始关键字错误 ", token);
            }
            parent.StackInfo = new StackInfo(this.m_strBreviary, token.SourceLine);
            parent           = this.GetVariable(parent);
            parent.Not       = flag;
            parent.Minus     = flag2;
            parent.Negative  = flag3;
            if (parent is CodeMember)
            {
                if (nONE != CALC.NONE)
                {
                    ((CodeMember)parent).Calc = nONE;
                    return(parent);
                }
                Token token2 = this.ReadToken();
                if (token2.Type == Scorpio.Compiler.TokenType.Increment)
                {
                    nONE = CALC.POST_INCREMENT;
                }
                else if (token2.Type == Scorpio.Compiler.TokenType.Decrement)
                {
                    nONE = CALC.POST_DECREMENT;
                }
                else
                {
                    this.UndoToken();
                }
                if (nONE != CALC.NONE)
                {
                    ((CodeMember)parent).Calc = nONE;
                }
                return(parent);
            }
            if (nONE != CALC.NONE)
            {
                throw new ParserException("++ 或者 -- 只支持变量的操作", token);
            }
            return(parent);
        }
Ejemplo n.º 56
0
 /// <summary>
 /// Parse an expression, stopping when default terminators, or the specified terminators, or a higher-precedence
 /// operator is encountered.
 /// </summary>
 /// <param name="parser">The parser object.</param>
 /// <param name="parent">The parent object.</param>
 /// <returns>The parsed <see cref="Expression"/>.</returns>
 public static Expression Parse(Parser parser, CodeObject parent)
 {
     return(Parse(parser, parent, false, null, ParseFlags.None));
 }
Ejemplo n.º 57
0
 private bool GetUserData(CodeObject e, string property, bool defaultValue)
 {
     object o = e.UserData[property];
     if (o != null && o is bool)
     {
         return (bool)o;
     }
     return defaultValue;
 }