예제 #1
0
        internal static Block CreateTryFinallyBlock(Method method, Block tryBody, Block finallyBody)
        {
          Contract.Requires(method != null);
          Contract.Requires(tryBody != null);
          Contract.Requires(finallyBody != null);

            if (method.ExceptionHandlers == null) method.ExceptionHandlers = new ExceptionHandlerList();

            Block result = new Block(new StatementList());
            Block afterFinally = new Block(new StatementList());

            tryBody.Statements.Add(new Branch(null, afterFinally, false, true, true));
            finallyBody.Statements.Add(new EndFinally());

            result.Statements.Add(tryBody);
            result.Statements.Add(finallyBody);
            result.Statements.Add(afterFinally);

            ExceptionHandler fb = new ExceptionHandler();
            fb.TryStartBlock = tryBody;
            fb.BlockAfterTryEnd = finallyBody;
            fb.HandlerStartBlock = finallyBody;
            fb.BlockAfterHandlerEnd = afterFinally;
            fb.HandlerType = NodeType.Finally;
            method.ExceptionHandlers.Add(fb);

            return result;
        }
예제 #2
0
 public override Block VisitBlock(Block block)
 {
     if (block == null) return null;
     LocalsStack stackLocalsAtEntry = (LocalsStack)this.StackLocalsAtEntry[block.UniqueKey];
     if (stackLocalsAtEntry == null)
     {
         //Unreachable code, or the very first block
         stackLocalsAtEntry = new LocalsStack();
     }
     this.localsStack = stackLocalsAtEntry.Clone();
     base.VisitBlock(block);
     Block successor = (Block)this.SucessorBlock[block.UniqueKey];
     if (successor != null)
     {
         //Dropping off into successor.
         LocalsStack targetStack = (LocalsStack)this.StackLocalsAtEntry[successor.UniqueKey];
         if (targetStack != null && targetStack.top >= 0)
         {
             //Another predecessor block has already decided what the stack for the successor block is going to look like.
             //Reconcile the stack from this block with the stack expected by the successor block.
             this.localsStack.Transfer(targetStack, block.Statements);
         }
         else
         {
             this.StackLocalsAtEntry[successor.UniqueKey] = this.localsStack;
         }
     }
     return block;
 }
        public CollectOldExpressions(Module module, Method method, ContractNodes contractNodes, Dictionary<TypeNode, Local> closureLocals,
            int localCounterStart)
        {
            this.contractNodes = contractNodes;
            this.prestateValuesOfOldExpressions = new Block(new StatementList());
            this.closureLocals = closureLocals;

            this.stackOfMethods = new List<MethodCall>();
            this.stackOfBoundVariables = new List<Parameter>();

            this.module = module;
            this.currentMethod = method;
            this.counter = localCounterStart;
        }
예제 #4
0
파일: Parser.cs 프로젝트: hesam/SketchSharp
 public override Block VisitBlock(Block block){
   if (block == null) return null;
   StatementList savedStatementList = this.CurrentStatementList;
   try{
     StatementList oldStatements = block.Statements;
     int n = oldStatements == null ? 0 : oldStatements.Length;
     StatementList newStatements = this.CurrentStatementList = block.Statements = new StatementList(n);
     for (int i = 0; i < n; i++)
       newStatements.Add((Statement)this.Visit(oldStatements[i]));
     return block;
   }finally{
     this.CurrentStatementList = savedStatementList;
   }
 }
예제 #5
0
        internal static Statement GenerateForLoop(Variable loopVariable, Expression lowerBound, Expression upperBound, Statement body)
        {
            Block bodyAsBlock = body as Block ?? new Block(new StatementList(body));
            Block init = new Block(new StatementList(2));
            Block increment = new Block(new StatementList(1));
            Block test = new Block(new StatementList(new Branch(
              new BinaryExpression(loopVariable, upperBound, NodeType.Lt), bodyAsBlock))); //, false, true, false)));

            init.Statements.Add(new AssignmentStatement(loopVariable, lowerBound));
            init.Statements.Add(new Branch(null, test));

            increment.Statements.Add(new AssignmentStatement(loopVariable, new BinaryExpression(loopVariable, Literal.Int32One, NodeType.Add)));

            Block forLoop = new Block(new StatementList(4));
            forLoop.Statements.Add(init);
            forLoop.Statements.Add(bodyAsBlock);
            forLoop.Statements.Add(increment);
            forLoop.Statements.Add(test);
            return forLoop;
        }
예제 #6
0
    BinaryExpression IsStartOf(Block block, TypeNode type, StatementList statements, Expression nameLocal, Expression nsLocal, StringBuilder expecting) {
      BinaryExpression result = null;
      if (IsStructuralType(type)) {
        SchemaElementDecl sd = SchemaElementDecl.Compile(this.module, type, Checker.GetCollectionElementType(type), this.errorHandler, schemaElementDeclCache);
        SchemaValidator validator = validator = sd.CreateValidator(this.errorHandler);   
        ValidationState context = new ValidationState();
        context.ErrorHandler = this.errorHandler;
        validator.validator.InitValidation(context);
        ArrayList members = validator.validator.ExpectedElements(context, false, false);
      
        foreach (TerminalNode node in members) {
          if (node is NamedNode) {
            NamedNode n = node as NamedNode;
            Identifier name = n.Name;
            if (expecting.Length>0) expecting.Append(" | ");
            expecting.Append(name.Name);
            BinaryExpression isName = new BinaryExpression(nameLocal, new Literal(name.Name, SystemTypes.String), NodeType.Eq);
            if (name.Prefix != null) {
              isName = new BinaryExpression(isName,
                new BinaryExpression(nsLocal, new Literal(name.Prefix.Name, SystemTypes.String), NodeType.Eq), 
                NodeType.And);
            }

            if (result == null) result = isName;
            else result = new BinaryExpression(result, isName, NodeType.Or);
          } else if (node is WildcardNode) {
            // todo:???
          }
        }
      } else {
        Identifier name = Checker.GetDefaultElementName(type);
        if (expecting.Length>0) expecting.Append(" | ");
        expecting.Append(name.Name);
        result = new BinaryExpression(nameLocal, new Literal(name.Name, SystemTypes.String), NodeType.Eq);
        if (name.Prefix != null) {
          result = new BinaryExpression(result,
            new BinaryExpression(nsLocal, new Literal(name.Prefix.Name, SystemTypes.String), NodeType.Eq), 
            NodeType.And);
        }
      }
      return result;
    }
예제 #7
0
    void AddReadStream(Block block, TypeNode type, StatementList statements, Identifier reader, 
      Expression target, Expression result){
      // Read next element and figure out if it matches the stream element type, if so read it and add it to the list
      // If not, then return (throw an error if there are no items and the list is the non-empty type).

      // flexArray = new flexarray();
      // while (reader.Read() && read.NodeType != XmlNodeType.EndElement) {
      //    if (reader.NodeType == XmlNodeType.Element) {
      //      readchild(flexarray);
      //    }
      // }
      // target = flexArray; 

      Local nameLocal = new Local(Identifier.For("name"),SystemTypes.String, block);
      Local nsLocal = new Local(Identifier.For("ns"),SystemTypes.String, block);
      Local nodeType = new Local(Identifier.For("nodeType"),Runtime.XmlNodeType, block);
      Local optional = new Local(Identifier.Empty, SystemTypes.Boolean, block);
      Local foundChild = new Local(Identifier.Empty, SystemTypes.Boolean, block);
      statements.Add(new AssignmentStatement(optional, Literal.False));

      TypeNode eType = Checker.GetCollectionElementType(type);
      Local local = new Local(Identifier.Empty, eType, block);
      Method addMethod = null;
      Local localArray = null;

      if (type.Template == SystemTypes.GenericBoxed) {

        addMethod = null; // only needs one!

      } else if (Checker.IsGenericList(type)) {
        //TODO: this call is invalid if the eType is not public
        TypeNode flexArrayType = SystemTypes.GenericList.GetTemplateInstance(this.module, eType);
        localArray = new Local(Identifier.For("stream"+streamCount++), flexArrayType, block);

        statements.Add(new AssignmentStatement(localArray,
          new Construct(new MemberBinding(null, flexArrayType), new ExpressionList(), flexArrayType)));

        addMethod = flexArrayType.GetMethod(Identifier.For("Add"), eType);
      } else  {        
        TypeNode arrayType = SystemTypes.ArrayList;
        localArray = new Local(Identifier.Empty, arrayType, block);
        statements.Add(new AssignmentStatement(localArray,
          new Construct(new MemberBinding(null, arrayType), new ExpressionList(), arrayType)));

        addMethod = arrayType.GetMethod(Identifier.For("Add"), SystemTypes.Object);
      }

      Block whileBody = new Block(new StatementList());
      MethodCall moveToContent = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("MoveToContent")), new ExpressionList());
      BinaryExpression notAtEnd = new BinaryExpression(moveToContent, 
        new QualifiedIdentifier(Identifier.For("XmlNodeType"), Identifier.For("EndElement")), NodeType.Ne);
      BinaryExpression notEOF = new BinaryExpression(
        new QualifiedIdentifier(reader, Identifier.For("EOF")), Literal.True, NodeType.Ne);

      While w = new While(new BinaryExpression(notAtEnd, notEOF, NodeType.And), whileBody);
      statements.Add(w);

      whileBody.Statements.Add(new AssignmentStatement(nameLocal, new QualifiedIdentifier(reader, Identifier.For("LocalName"))));
      whileBody.Statements.Add(new AssignmentStatement(nsLocal, new QualifiedIdentifier(reader, Identifier.For("NamespaceURI"))));
      whileBody.Statements.Add(new AssignmentStatement(nodeType, new QualifiedIdentifier(reader, Identifier.For("NodeType"))));

      StatementList trueStatements = whileBody.Statements;
      if (type.Template == SystemTypes.GenericBoxed){
        type = Checker.GetCollectionElementType(type);
      }

      trueStatements.Add(new AssignmentStatement(foundChild, Literal.False));

      if (eType is TupleType || eType is TypeUnion || IsStream(eType)) {
        AddCallDeserializer(eType, trueStatements, reader, local, optional, foundChild);        
      } else  {
        AddReadChild(whileBody, trueStatements, Checker.GetDefaultElementName(eType), eType, local, reader, foundChild, true, false);
      }

      If ifFound = new If(new BinaryExpression(foundChild, Literal.True, NodeType.Eq),
        new Block(new StatementList()), new Block(new StatementList()));
      ifFound.TrueBlock.Statements.Add(new AssignmentStatement(result, Literal.True)); // set our result to true then.
      ifFound.FalseBlock.Statements.Add(new Exit()); // break out of loop then.

      trueStatements.Add(ifFound);

      if (addMethod == null) {        
        trueStatements.Add(new AssignmentStatement(target, 
          CastTo(local, type))); // box the result.
        trueStatements.Add(new Exit()); // break out of loop we have it!
      } else {
        MemberBinding addCall = new MemberBinding(localArray, addMethod);
        trueStatements.Add(new ExpressionStatement(new MethodCall(addCall, 
          new ExpressionList(new Expression[1] {local}))));
      }

      // clear out the local, it is a struct of some sort.
      if (local.Type.IsValueType && ! local.Type.IsPrimitive) {
        trueStatements.Add(new AssignmentStatement(local, 
          new Construct(new MemberBinding(null,local.Type), new ExpressionList(), local.Type)));
      }

      // end while
      // assign resulting array to the target object (if we have anything to assign).
      If ifResult = new If(new BinaryExpression(result, Literal.True, NodeType.Eq),
        new Block(new StatementList()), null);
      statements.Add(ifResult);
      statements = ifResult.TrueBlock.Statements;

      if (addMethod != null) {
        if (type is ArrayType) {
          // target = (type)localArray.ToArray(etype);
          Method toArray = SystemTypes.ArrayList.GetMethod(Identifier.For("ToArray"), SystemTypes.Type);
          ExpressionList args = new ExpressionList();
          args.Add(new UnaryExpression(new Literal(eType, SystemTypes.Type), NodeType.Typeof, SystemTypes.Type));
          statements.Add(new AssignmentStatement(target, 
            CastTo(new MethodCall(new MemberBinding(localArray, toArray), 
                     args, NodeType.Callvirt, SystemTypes.Array), type)));

        } else if (type.Template == SystemTypes.GenericNonEmptyIEnumerable) {
          // Explicit coercion of IEnumerable to NonEmptyIEnumerable requires constructing 
          // the NonEmptyIEnumerable object passing in the IEnumerable as an argument.
          TypeNode ienumtype = Checker.GetIEnumerableTypeFromNonEmptyIEnumerableStruct(this.module, type);
          Debug.Assert(ienumtype!=null);
          //TODO: this call is invalid if the eType is not public
          TypeNode nonEmptyIEnum = SystemTypes.GenericNonEmptyIEnumerable.GetTemplateInstance(this.module, eType);

          InstanceInitializer ii = nonEmptyIEnum.GetConstructor(ienumtype);
          Construct c = new Construct(new MemberBinding(null, ii), new ExpressionList(localArray), nonEmptyIEnum);
          statements.Add(new AssignmentStatement(target, c));
        } else {
          statements.Add(new AssignmentStatement(target, localArray));
        }
      }
    }
예제 #8
0
 void AddReadRequiredChild(Block scope, StatementList statements, Identifier name, TypeNode type, Expression target, Identifier reader, Expression result, Expression required, bool unwrapChild, bool ignoreNamespace) {
   Block elseBlock = AddReadChild(scope, statements, name, type, target, reader, result, unwrapChild, ignoreNamespace).FalseBlock;
   If notFoundButRequired = new If(new BinaryExpression(required,Literal.True,NodeType.Eq),
     new Block(new StatementList()), null);
   InvalidContent(notFoundButRequired.TrueBlock.Statements, reader, name.Name.ToString());
   elseBlock.Statements.Add(notFoundButRequired);
 }
예제 #9
0
    void AddReadChoice(Block block, TypeUnion tu, StatementList statements, Identifier reader, 
      Expression target, Expression required, Expression result){
      // Read next element and figure out which of the choices in the type union it is then read the matching Type.
      
      Local nameLocal = new Local(Identifier.For("name"),SystemTypes.String,block);
      Local nsLocal = new Local(Identifier.For("ns"),SystemTypes.String,block);
      Local nodeType = new Local(Identifier.For("nodeType"),Runtime.XmlNodeType,block);
      statements.Add(new AssignmentStatement(nameLocal, new QualifiedIdentifier(reader, Identifier.For("LocalName"))));
      statements.Add(new AssignmentStatement(nsLocal, new QualifiedIdentifier(reader, Identifier.For("NamespaceURI"))));
      statements.Add(new AssignmentStatement(nodeType, new QualifiedIdentifier(reader, Identifier.For("NodeType"))));

      Local localRequired = new Local(Identifier.Empty,SystemTypes.Boolean,block);
      statements.Add(new AssignmentStatement(localRequired, Literal.True));

      Expression readString = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("ReadString")), null, NodeType.Callvirt, SystemTypes.String);
      
      If ifIsElement = new If(new BinaryExpression(nodeType, 
                              new QualifiedIdentifier(Identifier.For("XmlNodeType"), Identifier.For("Element")), NodeType.Eq),
                              new Block(new StatementList()), new Block(new StatementList()));
      statements.Add(ifIsElement);
        
      StatementList elseList = ifIsElement.TrueBlock.Statements;
      StringBuilder expecting = new StringBuilder();
      Expression bestCoercion = null;
      TypeNode bestChoice = null;
      TypeNode bestUnwrappedChoice = null;
      bool stringCoercionAmbiguous = false;

      for (int i = 0, n = tu.Types.Length; i < n; i++) {
        TypeNode choice = tu.Types[i];
        if (choice == null) continue; // type resolution error.

        TypeNode unwrapped = UnwrapSingletonTuple(Unwrap(choice), false);
        if (unwrapped == null) unwrapped = choice;
        Expression coercion = GetConvertFromString(unwrapped, readString, false);
        if (coercion != null) {
          // Keep track of the best coercion to string and use this to handle text nodes below.
          if (bestChoice == null){
            bestChoice = choice;
            bestUnwrappedChoice = unwrapped;
            bestCoercion = coercion;
          } else if (tempTypeSystem.IsBetterMatch(unwrapped, bestUnwrappedChoice, SystemTypes.String)) {
            bestChoice = choice;
            bestUnwrappedChoice = unwrapped;
            bestCoercion = coercion;
          } else {
            stringCoercionAmbiguous = true;
          }
        }

        BinaryExpression be = IsStartOf(block, choice, statements, nameLocal, nsLocal, expecting);    
        StatementList trueStatements = new StatementList();
        If ifIsStartOf = new If(be, new Block(trueStatements), new Block(new StatementList()));
        elseList.Add(ifIsStartOf);
        Local choiceTarget = new Local(Identifier.Empty, choice, block);
        if (choice.Template == SystemTypes.GenericBoxed){
          choice = Checker.GetCollectionElementType(choice);
        }
        if (!AddReadSimpleType(choice, trueStatements, reader, choiceTarget, result, false)) {
          AddCallDeserializer(choice, trueStatements, reader, choiceTarget, localRequired, result);            
        } 
        trueStatements.Add(new AssignmentStatement(target, 
          CastTo(choiceTarget, target.Type)));

        elseList = ifIsStartOf.FalseBlock.Statements;
      }
      if (bestCoercion != null && !stringCoercionAmbiguous) {      
        // Then we can also accept text nodes
        StatementList ifTextStatements = new StatementList();
        If ifIsText = new If(IsTextNode(nodeType), new Block(ifTextStatements), null);            
        ifIsElement.FalseBlock.Statements.Add(ifIsText);
        // then we can also handle text nodes in this choice.
        ifTextStatements.Add(new AssignmentStatement(target, CastTo(CastTo(bestCoercion, bestChoice), tu)));
        ifTextStatements.Add(new AssignmentStatement(result, Literal.True));        
      }

      // If this was a required element, then throw an error.
      If isRequired = new If(new BinaryExpression(required, Literal.True, NodeType.Eq), 
        new Block(new StatementList()), new Block(new StatementList()));
      elseList.Add(isRequired);
      InvalidContent(isRequired.TrueBlock.Statements, reader, expecting.ToString());
      isRequired.FalseBlock.Statements.Add(new AssignmentStatement(result, Literal.False));

    }
예제 #10
0
    //================= reader methods ==========================================    
    void AddReadAttributes(TypeNode type, StatementList statements, Identifier reader, Expression target, SchemaValidator validator) {

      if (validator.Attributes != null) {
        Block whileBody = new Block(new StatementList());
        Literal trueLit = Literal.True;
        MethodCall movenext = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("MoveToNextAttribute")), new ExpressionList());
        BinaryExpression condition = new BinaryExpression(movenext, trueLit, NodeType.Eq);
        While w = new While(condition, whileBody);
        statements.Add(w);
        Block lastElseBlock = null;

        Local nameLocal = new Local(SystemTypes.String);
        whileBody.Statements.Add(new AssignmentStatement(nameLocal, new QualifiedIdentifier(reader, Identifier.For("LocalName"))));
        Local nsLocal = new Local(SystemTypes.String);
        whileBody.Statements.Add(new AssignmentStatement(nsLocal, new QualifiedIdentifier(reader, Identifier.For("NamespaceURI"))));

        foreach (SchemaAttDef ad in validator.Attributes) {
          // todo: any way to do tokenized compares?
          BinaryExpression nameEqual = new BinaryExpression(nameLocal,
            new Literal(ad.Name.Name, SystemTypes.String), NodeType.Eq);
          BinaryExpression nsEqual = new BinaryExpression(nsLocal,
            new Literal(ad.Name.Prefix != null ? ad.Name.Prefix.Name : "", SystemTypes.String), NodeType.Eq);
          Block elseBlock = new Block(new StatementList());
          If ifExpr = new If(new BinaryExpression(nameEqual, nsEqual, NodeType.And), new Block(new StatementList()), elseBlock);
          if (lastElseBlock != null) {
            lastElseBlock.Statements.Add(ifExpr);
          } else {
            whileBody.Statements.Add(ifExpr);
          }
          lastElseBlock = elseBlock;

          // body of if test, parse the attribute value as the specified type.
          Debug.Assert(ad.Member is Field || ad.Member is Property);
          AddReadSimpleType(Checker.GetMemberType(ad.Member), ifExpr.TrueBlock.Statements, reader, GetMemberBinding(target, ad.Member), null, true);
        }
        //todo: report unknown attributes?
      }
    }
예제 #11
0
        private void GenerateMethodReturn(Block block, AssignmentStatement assignmentStatement, MethodCall call)
        {
            ZMethod method = (ZMethod)((MemberBinding)call.Callee).BoundMember;

            // Eventually, this will be checked by an earlier phase.
            Debug.Assert(method.Parameters.Count == call.Operands.Count);

            // process output parameters and the return value;
            for (int i = 0, n = call.Operands.Count; i < n; i++)
            {
                Parameter param = method.Parameters[i];
                if ((param.Flags & ParameterFlags.Out) != 0 && call.Operands[i] != null && method.Parameters[i] != null)
                {
                    Statement assignOutParam = Templates.GetStatementTemplate("FetchOutputParameter");
                    Replacer.Replace(assignOutParam, "_dest",
                        this.VisitExpression(((UnaryExpression)call.Operands[i]).Operand));
                    Replacer.Replace(assignOutParam, "_paramName", new Identifier("_Lfc_" + method.Parameters[i].Name.Name));
                    Replacer.Replace(assignOutParam, "_Callee", method.Name);
                    Replacer.Replace(assignOutParam, "_CalleeClass", method.DeclaringType.Name);
                    block.Statements.Add(assignOutParam);
                }
            }

            if (assignmentStatement != null)
            {
                Statement assignReturnValue = Templates.GetStatementTemplate("FetchReturnValue");
                Replacer.Replace(assignReturnValue, "_dest", this.VisitExpression(assignmentStatement.Target));
                Replacer.Replace(assignReturnValue, "_CalleeClass", method.DeclaringType.Name);
                Replacer.Replace(assignReturnValue, "_Callee", method.Name);

                block.Statements.Add(assignReturnValue);
            }

            Statement stmt = Templates.GetStatementTemplate("InvalidateLastFunctionCompleted");
            block.Statements.Add(stmt);
        }
예제 #12
0
        public override Statement VisitExpressionStatement(ExpressionStatement statement)
        {
            // Check for statements that require special handling
            AssignmentExpression assignmentExpr = statement.Expression as AssignmentExpression;
            AssignmentStatement assignmentStatement = null;
            MethodCall methodCall = statement.Expression as MethodCall;
            UnaryExpression choose = null;

            if (assignmentExpr != null)
            {
                assignmentStatement = assignmentExpr.AssignmentStatement as AssignmentStatement;
                if (assignmentStatement != null && assignmentStatement.Source is MethodCall)
                    methodCall = (MethodCall)assignmentStatement.Source;

                if (assignmentStatement != null && assignmentStatement.Source is UnaryExpression &&
                    assignmentStatement.Source.NodeType == (NodeType)ZingNodeType.Choose)
                    choose = (UnaryExpression)assignmentStatement.Source;
            }

            if (methodCall != null)
            {
                Block stmtBlock = new Block();
                stmtBlock.Statements = new StatementList();

                // The following if statement (and the if-branch) added by Jiri Adamek
                // Reason: the NativeZOM method calls are generated differntly from
                //         common Zing method calls
                // The original code is in the else-branch
                if (((MemberBinding)methodCall.Callee).BoundMember.DeclaringType is NativeZOM)
                {
                    GenerateNativeZOMCall(stmtBlock, methodCall, statement is AsyncMethodCall, assignmentStatement);
                }
                else
                {
                    if (this.secondOfTwo)
                        GenerateMethodReturn(stmtBlock, assignmentStatement, methodCall);
                    else
                        GenerateMethodCall(stmtBlock, methodCall, statement is AsyncMethodCall);
                }

                return stmtBlock;
            }
            else if (choose != null)
            {
                Statement chooseStmt;

                if (this.secondOfTwo)
                {
                    // Finishing a "choose" is always the same...
                    chooseStmt = Templates.GetStatementTemplate("FinishChoose");
                    TypeNode tn = choose.Type;
                    if (tn is Set || tn is ZArray || tn is Class || tn is Chan)
                        Replacer.Replace(chooseStmt, "_targetType", new Identifier("Pointer"));
                    else
                        Replacer.Replace(chooseStmt, "_targetType", this.VisitExpression(choose.Type.Name));

                    Replacer.Replace(chooseStmt, "_target", this.VisitExpression(assignmentStatement.Target));
                }
                else
                {
                    // Starting a "choose" is different for the static and dynamic cases
                    if (choose.Operand.Type.FullName == "Boolean")
                    {
                        chooseStmt = Templates.GetStatementTemplate("StartChooseByBoolType");
                    }
                    else if (choose.Operand.Type == SystemTypes.Type)
                    {
                        // static
                        Literal lit = choose.Operand as Literal;
                        Debug.Assert(lit != null);
                        TypeNode tn = lit.Value as TypeNode;
                        Debug.Assert(tn != null);
                        chooseStmt = Templates.GetStatementTemplate("StartChooseByType");
                        Replacer.Replace(chooseStmt, "_typeExpr", new QualifiedIdentifier(new Identifier("Application"), tn.Name));
                    }
                    else
                    {
                        // dynamic
                        chooseStmt = Templates.GetStatementTemplate("StartChooseByValue");
                        Replacer.Replace(chooseStmt, "_ptrExpr", this.VisitExpression(choose.Operand));
                    }
                }

                return chooseStmt;
            }
            else if (assignmentStatement != null && assignmentStatement.Target.Type is Set &&
                assignmentStatement.Source is BinaryExpression)
            {
                BinaryExpression binaryExpression = (BinaryExpression)assignmentStatement.Source;
                Statement setOpStmt;

                if (binaryExpression.Operand1.Type == binaryExpression.Operand2.Type)
                {
                    if (binaryExpression.NodeType == NodeType.Add)
                        setOpStmt = Templates.GetStatementTemplate("SetAddSet");
                    else
                        setOpStmt = Templates.GetStatementTemplate("SetRemoveSet");
                }
                else
                {
                    if (binaryExpression.NodeType == NodeType.Add)
                        setOpStmt = Templates.GetStatementTemplate("SetAddItem");
                    else
                        setOpStmt = Templates.GetStatementTemplate("SetRemoveItem");
                }

                Replacer.Replace(setOpStmt, "_ptrExpr", this.VisitExpression(binaryExpression.Operand1));
                Replacer.Replace(setOpStmt, "_itemExpr", this.VisitExpression(binaryExpression.Operand2));

                return setOpStmt;
            }
            else
            {
                // The default scenario...

                inExpressionStatement = true;
                Expression newExpr = this.VisitExpression(statement.Expression);
                inExpressionStatement = false;

                //
                // In some scenarios, a simple assignment becomes something much more
                // complicated. We have to detect when such a case has occurred and
                // return the more complex statement directly rather than leaving it
                // embedded within an ExpressionStatement.
                //
                AssignmentExpression newAssignmentExpr = newExpr as AssignmentExpression;
                if (newAssignmentExpr != null && !(newAssignmentExpr.AssignmentStatement is AssignmentStatement))
                    return newAssignmentExpr.AssignmentStatement;

                Statement result = new ExpressionStatement(newExpr, statement.SourceContext);
                return result;
            }
        }
예제 #13
0
    void AddWriteChoice(TypeUnion tu, StatementList statements, TypeNode referringType, Expression src, Identifier writer) {
      // generate the following code:
      //    Type srcType = src.GetType();
      //    if (choiceType.IsAssignableFrom(srcType)){ 
      //      XxxxSerializer s = new XxxxSerializer();
      //      s.Serialize((runtimeType)src, writer);
      //    } else if (...) {
      //      // and so on.
      //    }
      // What we cannot do here is by creating nested XmlSerializers
      // based on runtime type because this could cause infinite recurrsion.
      // So we cannot serialize a type union where one of the choices is "object".

      TypeNodeList choices = tu.Types;

      MethodCall call = new MethodCall();
      call.Callee = new QualifiedIdentifier(src, Identifier.For("GetType"));
      call.Operands = new ExpressionList();

      Local local = new Local(SystemTypes.Type);
      statements.Add(new AssignmentStatement(local, call));

      for (int i = 0, n = choices.Length; i < n; i++) {
        TypeNode choiceType = choices[i];
        if (choiceType == null) continue; // type resolution error.

        // if (choiceType.IsAssignableFrom(srcType)){ 
        BinaryExpression condition = new BinaryExpression(
          new MethodCall(
            new QualifiedIdentifier(new UnaryExpression(new MemberBinding(null, choiceType), NodeType.Typeof), Identifier.For("IsAssignableFrom")),
            new ExpressionList(new Expression[] { local })),
          Literal.True,
          NodeType.Eq);

        Block block = new Block();
        block.Statements = new StatementList();
        BinaryExpression cast = CastTo(src, choiceType);

        Expression name = null, ns = null;
        GetNameAndNamespace(choiceType, out name, out ns);
        Expression simplename = name, simplens = ns;

        // Check for choice of type: [string] and match this with XmlTextNode.
        TypeNode unwrapped = UnwrapSingletonTuple(choiceType, true);
        if (unwrapped == null) unwrapped = choiceType;
        if (unwrapped != null && unwrapped.IsPrimitive) {
          simplename = simplens = null;
          choiceType = unwrapped;
        }

        if (!AddWriteSimpleType(choiceType, block.Statements, referringType, writer, cast, simplename, simplens)) {
          AddCallSerializer(choiceType, block.Statements, cast, writer, name, ns);
        }
        If ifStatement = new If(condition, block, null);
        statements.Add(ifStatement);
      } 
    }
예제 #14
0
파일: Looker.cs 프로젝트: hesam/SketchSharp
 public override void ConstructMethodForNestedFunction(Node func, Method method, TypeNode returnType, ParameterList parList, Block body){
   base.ConstructMethodForNestedFunction(func, method, returnType, parList, body);
   if (method != null && body != null)
     method.SourceContext.EndPos = body.SourceContext.EndPos+1;
 }
예제 #15
0
        /// <summary>
        /// Scans the entire block to find 0 or more closure initializations. For each, it adds an entry to the dictionary
        /// mapping the closure type to the closure local.
        /// </summary>
        internal static void RecordClosureInitialization(Method containing, Block b, Dictionary<TypeNode, Local> closureLocalMap)
        {
            Contract.Requires(closureLocalMap != null);

            Local closureLocal = null;
            if (b == null || b.Statements == null || !(b.Statements.Count > 0))
            {
                return;
            }
            for (int i = 0; i < b.Statements.Count; i++)
            {
                Statement s = b.Statements[i];
                if (s == null || s.NodeType == NodeType.Nop) continue;
                if (HelperMethods.IsClosureCreation(containing, s, out closureLocal))
                {
                  if (closureLocal != null)
                  {
                    closureLocalMap.Add(closureLocal.Type, closureLocal);
                  }
                }
            }
        }
예제 #16
0
파일: Looker.cs 프로젝트: hesam/SketchSharp
 public override Block VisitBlock(Block block){
   if (block == null) return null;
   Block savedCurrentBlock = this.currentBlock;
   this.currentBlock = block;
   block = base.VisitBlock(block);
   if (block != null && block.Scope != null){
     MemberList blockLocals = block.Scope.Members;      
     for (int i = 0, n = blockLocals == null ? 0 : blockLocals.Count; i < n; i++){
       Field f = blockLocals[i] as Field;
       if (f == null) continue;
     }
   }
   this.currentBlock = savedCurrentBlock;
   return block;
 }
예제 #17
0
        private Statement VisitJoinStatement(JoinStatement joinstmt)
        {
            //
            // The first block of a join statement pair only tests the condition.
            // It needs no executable statements.
            //
            if (!this.secondOfTwo)
                return null;

            bool anyEvents = false;

            Block stmtBlock = new Block();
            stmtBlock.Statements = new StatementList();

            for (int i = 0, n = joinstmt.joinPatternList.Length; i < n; i++)
            {
                JoinPattern jp = joinstmt.joinPatternList[i];
                ReceivePattern receivePattern = jp as ReceivePattern;
                WaitPattern waitPattern = jp as WaitPattern;
                EventPattern eventPattern = jp as EventPattern;

                if (receivePattern != null)
                {
                    // Construct a statement to actually perform the receive.
                    Statement receiveStmt = Templates.GetStatementTemplate("ReceivePattern");
                    Replacer.Replace(receiveStmt, "_chanExpr", this.VisitExpression(receivePattern.channel));
                    Replacer.Replace(receiveStmt, "_chanType", receivePattern.channel.Type.Name);
                    Replacer.Replace(receiveStmt, "_target", this.VisitExpression(receivePattern.data));
                    Replacer.Replace(receiveStmt, "_context", splicer.SourceContextConstructor(jp.SourceContext));
                    Replacer.Replace(receiveStmt, "_contextAttr", splicer.ContextAttributeConstructor(this.attributes));

                    //
                    // If the type is complex, we need to cast to Z.Pointer instead of the given type
                    //
                    TypeNode tn = receivePattern.data.Type;
                    if (tn is Set || tn is ZArray || tn is Class || tn is Chan)
                        Replacer.Replace(receiveStmt, "_targetType", new Identifier("Pointer"));
                    else
                        Replacer.Replace(receiveStmt, "_targetType", receivePattern.data.Type.Name);

                    stmtBlock.Statements.Add(receiveStmt); ;
                }
                else if (eventPattern != null)
                {
                    Statement eventStmt = Templates.GetStatementTemplate("Event");

                    Replacer.Replace(eventStmt, "_chanExpr", this.VisitExpression(eventPattern.channelNumber));
                    Replacer.Replace(eventStmt, "_msgExpr", this.VisitExpression(eventPattern.messageType));
                    Replacer.Replace(eventStmt, "_dirExpr", this.VisitExpression(eventPattern.direction));
                    Replacer.Replace(eventStmt, "_context", splicer.SourceContextConstructor(eventPattern.SourceContext));
                    Replacer.Replace(eventStmt, "_contextAttr", splicer.ContextAttributeConstructor(this.attributes));

                    stmtBlock.Statements.Add(eventStmt);

                    anyEvents = true;
                }
            }

            if (joinstmt.visible && !anyEvents)
            {
                Statement eventStmt = Templates.GetStatementTemplate("TauEvent");
                Replacer.Replace(eventStmt, "_context", splicer.SourceContextConstructor(joinstmt.SourceContext));
                Replacer.Replace(eventStmt, "_contextAttr", splicer.ContextAttributeConstructor(this.attributes));

                stmtBlock.Statements.Add(eventStmt);
            }

            return stmtBlock;
        }
예제 #18
0
        // The method added by Jiri Adamek
        // It generates NAtiveZOM calls
        private void GenerateNativeZOMCall(Block block, MethodCall call, bool callIsAsync, AssignmentStatement assignmentStatement)
        {
            ZMethod method = (ZMethod)((MemberBinding)call.Callee).BoundMember;

            // Eventually, this will be checked by an earlier phase.
            Debug.Assert(method.Parameters.Count == call.Operands.Count);

            // Asynchronous calls
            Debug.Assert(!callIsAsync, "async not supporrted for NativeZOM calls");

            // Debugging - parameters
            for (int i = 0, n = call.Operands.Count; i < n; i++)
            {
                Parameter param = method.Parameters[i];

                Debug.Assert(param != null);

                // In fact, call.operands[i] MAY BE null due to the error recovery (if the type of the
                // expression does not match the type in the method definition)
                //
                // Debug.Assert(call.Operands[i] != null);

                Debug.Assert((param.Flags & ParameterFlags.Out) == 0, "out parameters not supported for NativeZOM calls");
            }

            Expression typename = new QualifiedIdentifier(new Identifier("Microsoft.Zing"), method.DeclaringType.Name);
            Expression callee;

            if (!method.IsStatic)
            {
                callee = Templates.GetExpressionTemplate("NativeZOMCallee");
                Replacer.Replace(callee, "_TypeName", typename);
                Expression pointer = this.VisitExpression(((MemberBinding)call.Callee).TargetObject);
                Replacer.Replace(callee, "_Pointer", pointer);
                Replacer.Replace(callee, "_MethodName", method.Name);
            }
            else
            {
                callee = Templates.GetExpressionTemplate("NativeZOMStaticCall");
                Replacer.Replace(callee, "_ClassName", typename);
                Replacer.Replace(callee, "_MethodName", method.Name);
            }

            ExpressionList argumentList = new ExpressionList();
            argumentList.Add(Templates.GetExpressionTemplate("NativeZOMCallFirstArgument"));
            foreach (Expression operand in call.Operands) argumentList.Add(this.VisitExpression(operand));
            MethodCall nativeCall = new MethodCall(callee, argumentList);

            Statement newStatement;
            if (assignmentStatement != null)
            {
                newStatement = Templates.GetStatementTemplate("NativeZOMCallWithAssignment");
                Replacer.Replace(newStatement, "_Dest", this.VisitExpression(assignmentStatement.Target));
                Replacer.Replace(newStatement, "_Source", nativeCall);
            }
            else
            {
                newStatement = new ExpressionStatement(nativeCall);
            }

            block.Statements.Add(newStatement);
        }
예제 #19
0
    void AddReadAlias( Block block, TypeAlias alias, StatementList statements, Identifier reader, 
      Expression target, Expression required, Expression result) {

      Local local = new Local(Identifier.Empty, alias.AliasedType, block);
      AddReadRequiredChild(block, statements, alias.Name, alias.AliasedType, local, reader, result, required, true, true);
      statements.Add(new AssignmentStatement(target, this.tempChecker.typeSystem.ImplicitCoercion(local, target.Type)));

    }
예제 #20
0
    void AddReadContentNode(ContentNode n, Block block, StatementList statements, Identifier reader, 
      Expression target, Expression required, Expression result, SchemaValidator validator) {
      if (n.TypeNode == null) {
        Debug.Assert(n is SequenceNode);
        // In the class inheritance case we have two independent left and right children inside
        // a parent sequence that has no unified type or member.
        SequenceNode s = (SequenceNode)n;
        AddReadContentNode(s.LeftChild, block, statements, reader, target, required, result, validator);
        AddReadContentNode(s.RightChild, block, statements, reader, target, required, result, validator);
        return;
      }
      TypeNode ct = n.TypeNode;
      Debug.Assert(ct != null);
      if (n.Member != null && !(n.Member is Method))  {
        target = GetMemberBinding(target, n.Member);
        ct = target.Type;
      }

      // todo: might be content model AND mixed, in which case we have to pass the MixedMember
      // to AddReadTuple, AddReadChoice and AddReadStream.
      if (ct.Template == SystemTypes.GenericBoxed){
        ct = Checker.GetCollectionElementType(ct);
      }
      if (ct is TupleType) {
        AddReadTuple(block, ct as TupleType, statements, reader, target, required, result);
      } else if (ct is TypeUnion) {
        AddReadChoice(block, ct as TypeUnion, statements, reader, target, required, result);
      } else if (IsStream(ct)) {
        AddReadStream(block, ct, statements, reader, target, result);
      } else if (ct is TypeAlias) {
        AddReadAlias(block, ct as TypeAlias, statements, reader, target, required, result);
      } else {
        Identifier name = Checker.GetDefaultElementName(ct);
        AddReadRequiredChild(block, statements, name, ct, target, reader, result, required, true, false);
      }
    }
예제 #21
0
    If AddReadChild(Block scope, StatementList statements, Identifier name, TypeNode type, Expression target, Identifier reader, Expression result, bool unwrapChild, bool ignoreNamespace) {
      ExpressionList args = new ExpressionList();
      args.Add(new Literal(name.Name, SystemTypes.String));
      if (name.Prefix != null) args.Add(new Literal(name.Prefix.Name, SystemTypes.String));
      
      // see if we're on a text node...
      Local nodeType = new Local(Identifier.For("nodeType"), Runtime.XmlNodeType, scope);
      statements.Add(new AssignmentStatement(nodeType, new QualifiedIdentifier(reader, Identifier.For("NodeType"))));
      StatementList ifTextStatements = new StatementList();      
      If ifIsText = new If(
        new BinaryExpression(IsTextNode(nodeType),
          new BinaryExpression(nodeType,
            new QualifiedIdentifier(Identifier.For("XmlNodeType"), Identifier.For("EndElement")), NodeType.Eq),
        NodeType.Or), new Block(ifTextStatements), new Block(new StatementList()));            
      statements.Add(ifIsText);
      
      // then see if we can force the text into the desired type.
      TypeNode unwrapped = UnwrapSingletonTuple(Unwrap(type), false);
      if (unwrapped == null) unwrapped = type;
      Expression readString = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("ReadString")), null, NodeType.Callvirt, SystemTypes.String);
      Expression coercion = GetConvertFromString(unwrapped, readString, false);
      if (coercion != null) {
        ifTextStatements = ifIsText.TrueBlock.Statements;
        ifTextStatements.Add(new AssignmentStatement(target, CastTo(CastTo(coercion, unwrapped),type)));
        ifTextStatements.Add(new AssignmentStatement(result, Literal.True));        
      }
      statements = ifIsText.FalseBlock.Statements;

      If ifFound = null;
      string method = ignoreNamespace ? "IsStartElementIgnoreNamespace" : "IsStartElement";
      MethodCall isStartEle = new MethodCall(new QualifiedIdentifier(reader, Identifier.For(method)), args);
      ifFound = new If(isStartEle, new Block(new StatementList()), new Block(new StatementList()));
      statements.Add(ifFound);
      statements = ifFound.TrueBlock.Statements;       
      
      statements.Add(new AssignmentStatement(result, Literal.True));

      // body of if test, parse the child element as the specified type.
      MethodCall read = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("Read")), new ExpressionList());
      bool isStructuralType = this.IsStructuralType(type);
      if (isStructuralType && unwrapChild) {
        // consume member element wrapper.
        statements.Add(new ExpressionStatement(read));
      }
      if (type.Template == SystemTypes.GenericBoxed){
        type = Checker.GetCollectionElementType(type);
      }

      if (!AddReadSimpleType(type, statements, reader, target, result, false)) {
        AddCallDeserializer(type, statements, reader, target, result, result);
      }
      if (isStructuralType && unwrapChild) {
        // consume member element end tag wrapper.
        statements.Add(new ExpressionStatement(new MethodCall(new QualifiedIdentifier(reader, Identifier.For("ReadEndTag")), new ExpressionList(new Literal(name.Name, SystemTypes.String)))));
      }
      return ifFound;
    }
예제 #22
0
        public override Block VisitBlock(Block block)
        {
            // We special-case this because it's how a null statement is
            // represented.
            if (block.Statements == null)
            {
                WriteLine(";");
                return block;
            }

            if (this.braceOnNewLine)
            {
                WriteFinish(string.Empty);
                WriteLine("{");
            }
            else
                WriteFinish(" {");

            In();
            Block result = base.VisitBlock(block);
            Out();
            WriteLine("}");
            return result;
        }
예제 #23
0
    void AddWriteStream(TypeNode type, StatementList statements, TypeNode referringType, Expression src, Identifier writer) {
      // Generate the following code:
      // XxxxSerializer s = new XxxxSerializer();
      // foreach (Xxxx x in src) {
      //    s.Serialize(x,writer);
      // }
      // Where Xxxx is the element type for the given stream type.

      if (type.Template == SystemTypes.GenericNonEmptyIEnumerable) {
        type = Checker.GetIEnumerableTypeFromNonEmptyIEnumerableStruct(this.module, type);
      } else {
        statements = AddCheckForNull(statements, Duplicate(src, referringType), type);
      }
      TypeNode ceType = Checker.GetCollectionElementType(type);  
      //todo: should check that type has an IEnumerator.

      Identifier loopVariable = Identifier.For("e");
      loopVariable.Type = ceType;
      Block body = new Block();
      body.Statements = new StatementList();

      Expression name, ns;
      GetNameAndNamespace(ceType, out name, out ns);

      // call the Serialize method on it, passing the member we're serializing.  
      if (!AddWriteSimpleType(ceType, body.Statements, referringType, writer, loopVariable, name, ns)) {
        AddCallSerializer(ceType, body.Statements, loopVariable, writer, name, ns);
      }

      ForEach fe = new ForEach(ceType, loopVariable, src, body);      
      statements.Add(fe);
    }
예제 #24
0
        internal static bool IsNonTrivial(Block block)
        {
            if (block == null) return false;

            if (block.Statements == null) return false;
            
            foreach (var s in block.Statements)
            {
                if (IsNonTrivial(s)) return true;
            }
            
            return false;
        }
예제 #25
0
    void AddReadContent(Class serializer, Block block, TypeNode type, StatementList statements, Identifier reader, 
      Expression target, Expression required, Expression result, SchemaValidator validator) {
    
      // position us in the content.
      statements.Add(new ExpressionStatement(new MethodCall(new QualifiedIdentifier(reader, Identifier.For("MoveToContent")), new ExpressionList())));
      Local elementName = new Local(Identifier.Empty,SystemTypes.String);
      statements.Add(new AssignmentStatement(elementName, new QualifiedIdentifier(reader, Identifier.For("LocalName"))));
      
      // make sure the element is not empty.
      If isEmpty = AddEmptyElementCheck(statements, reader);

      // Read the contents.
      statements = isEmpty.FalseBlock.Statements;
      statements.Add(new ExpressionStatement(new MethodCall(new QualifiedIdentifier(reader, Identifier.For("Read")), new ExpressionList())));
      statements.Add(new ExpressionStatement(new MethodCall(new QualifiedIdentifier(reader, Identifier.For("MoveToContent")), new ExpressionList())));

      ValidationState context = new ValidationState();
      context.ErrorHandler = this.errorHandler;
      validator.validator.InitValidation(context);
      ArrayList members = null;
      if (validator.validator is AllElementsContentValidator) {
        members = validator.validator.ExpectedElements(context, false, false);
        AddReadAllGroup(serializer, block, type, statements, reader, target, required, result, members, validator.validator.MixedMember);
      } else {

        // There should be one root level anonymous Item0 member.
        SequenceNode seq = (SequenceNode)validator.RootNode; // this is a wrapper node.
        if (seq == null) {
          // perhaps it is ContentType.Empty or Mixed.
          if (validator.validator.ContentType == XmlSchemaContentType.Mixed ||
            validator.validator.ContentType == XmlSchemaContentType.TextOnly){
            Debug.Assert(validator.validator.MixedMember != null);
            statements.Add(new AssignmentStatement(GetMemberBinding(target, validator.validator.MixedMember), 
              new MethodCall(new QualifiedIdentifier(reader, Identifier.For("ReadStringElement")), new ExpressionList())));         
          }
          return;
        } else {
          ContentNode n = seq.LeftChild;
          AddReadContentNode(n, block, statements, reader, target, required, result, validator);
        }
      }    

      // consume final end tag
      statements.Add(new ExpressionStatement(new MethodCall(new QualifiedIdentifier(reader, Identifier.For("ReadEndTag")), new ExpressionList(elementName))));
    }
예제 #26
0
        private void GenerateMethodCall(Block block, MethodCall call, bool callIsAsync)
        {
            ZMethod method = (ZMethod)((MemberBinding)call.Callee).BoundMember;

            // Eventually, this will be checked by an earlier phase.
            Debug.Assert(method.Parameters.Count == call.Operands.Count);

            Statement createCallFrame;
            if (method.DeclaringType is Interface)
            {
                createCallFrame = Templates.GetStatementTemplate("CreateCallFrameForInterface");
                Replacer.Replace(createCallFrame, "_thisExpr", this.VisitExpression(((MemberBinding)call.Callee).TargetObject));
                Replacer.Replace(createCallFrame, "_CreateMethod", new Identifier("Create" + method.Name.Name));
            }
            else
            {
                createCallFrame = Templates.GetStatementTemplate("CreateCallFrame");
            }
            Replacer.Replace(createCallFrame, "_calleeClass", new Identifier(method.DeclaringType.FullName));
            Replacer.Replace(createCallFrame, "_Callee", method.Name);
            block.Statements.Add(createCallFrame);

            // process input parameters
            for (int i = 0, n = call.Operands.Count; i < n; i++)
            {
                Parameter param = method.Parameters[i];

                if ((param.Flags & ParameterFlags.Out) == 0 && call.Operands[i] != null && method.Parameters[i] != null)
                {
                    Statement assignInParam = Templates.GetStatementTemplate("SetInputParameter");
                    Replacer.Replace(assignInParam, "_src", this.VisitExpression(call.Operands[i]));
                    Replacer.Replace(assignInParam, "_paramName", new Identifier("priv_" + method.Parameters[i].Name.Name));
                    block.Statements.Add(assignInParam);
                }
            }

            if (!method.IsStatic)
            {
                Statement setThis = Templates.GetStatementTemplate("SetThis");
                Replacer.Replace(setThis, "_thisExpr", this.VisitExpression(((MemberBinding)call.Callee).TargetObject));
                block.Statements.Add(setThis);
            }

            if (callIsAsync)
            {
                ExpressionStatement asyncInvoke = (ExpressionStatement)Templates.GetStatementTemplate("InvokeAsyncMethod");

                Replacer.Replace(asyncInvoke, "_methodName",
                    new Literal(method.DeclaringType.Name.Name + "." + method.Name.Name, SystemTypes.String));
                Replacer.Replace(asyncInvoke, "_context", splicer.SourceContextConstructor(call.SourceContext));
                Replacer.Replace(asyncInvoke, "_contextAttr", splicer.ContextAttributeConstructor(attributes));

                block.Statements.Add(asyncInvoke);
            }
            else
            {
                block.Statements.Add(Templates.GetStatementTemplate("InvokeMethod"));
                block.Statements.Add(Templates.GetStatementTemplate("SetIsCall"));
            }
        }
예제 #27
0
    void AddReadAllGroup(Class serializer, Block block, TypeNode type, StatementList statements, Identifier reader, 
      Expression target, Expression required, Expression result, ArrayList members, Member mixedMember) {

      // todo: keep track of which members have been read and report error on duplicates
      MethodCall read = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("Read")), new ExpressionList());

      Local sb = new Local(SystemTypes.StringBuilder);
      bool isMixed = mixedMember != null;
      if (isMixed) {
        statements.Add(new AssignmentStatement(sb,
          new Construct(new MemberBinding(null, SystemTypes.StringBuilder), new ExpressionList(), SystemTypes.StringBuilder)));
      }

      Block whileBody = new Block(new StatementList());
      BinaryExpression notEndTag = new BinaryExpression(
        new QualifiedIdentifier(reader, Identifier.For("NodeType")) ,
        new QualifiedIdentifier(Identifier.For("XmlNodeType"), Identifier.For("EndElement")), NodeType.Ne);
      BinaryExpression notEOF = new BinaryExpression(
        new QualifiedIdentifier(reader, Identifier.For("EOF")), Literal.True, NodeType.Ne);
      While w = new While(new BinaryExpression(notEndTag, notEOF, NodeType.And), whileBody);
      statements.Add(w);

      Local nameLocal = new Local(Identifier.For("name"),SystemTypes.String,block);
      Local nsLocal = new Local(Identifier.For("ns"),SystemTypes.String,block);
      Local nodeType = new Local(Identifier.For("nodeType"),Runtime.XmlNodeType,block);

      whileBody.Statements.Add(new AssignmentStatement(nameLocal, new QualifiedIdentifier(reader, Identifier.For("LocalName"))));
      whileBody.Statements.Add(new AssignmentStatement(nsLocal, new QualifiedIdentifier(reader, Identifier.For("NamespaceURI"))));
      whileBody.Statements.Add(new AssignmentStatement(nodeType, new QualifiedIdentifier(reader, Identifier.For("NodeType"))));
      
      Block childBlock = whileBody;

      if (isMixed) {
        // Append the text node to the current StringBuilder contents.
        childBlock = new Block(new StatementList());
        If ifText = new If(IsTextNode(nodeType), new Block(new StatementList()), childBlock);

        whileBody.Statements.Add(ifText);
        ExpressionList args = new ExpressionList();
        args.Add(new QualifiedIdentifier(reader, Identifier.For("Value")));
        ifText.TrueBlock.Statements.Add(new ExpressionStatement(new MethodCall(
          new QualifiedIdentifier(sb, Identifier.For("Append")), args)));
        ifText.TrueBlock.Statements.Add(new ExpressionStatement(read)); // advance to next node
      }      

      If ifElement = new If(new BinaryExpression(nodeType,
        new QualifiedIdentifier(Identifier.For("XmlNodeType"), Identifier.For("Element")), NodeType.Eq),
        new Block(new StatementList()), new Block(new StatementList()));
      childBlock.Statements.Add(ifElement);
      childBlock = ifElement.TrueBlock;

      //AddConsoleWrite(statements, new Literal("name=",SystemTypes.String));
      //AddConsoleWriteLine(statements, nameLocal);
      //AddConsoleWrite(statements, new Literal("nodeType=",SystemTypes.String));
      //AddConsoleWriteLine(statements, nodeType);

      foreach (NamedNode childNode in members) {
        if (!(childNode.Member is Field || childNode.Member is Property)) {
          AddError(statements, reader, RuntimeError.SerializationOfTypeNotSupported, 
            new Literal(childNode.Member.GetType().FullName, SystemTypes.String));
        } else {
          Expression mb = GetMemberBinding(target, childNode.Member);
          childBlock = AddReadChild(block, childBlock.Statements, childNode.Name, childNode.TypeNode, mb, reader, result, true, false).FalseBlock;
          // todo: throw error if child is required. (e.g. NonEmptyIEnumerable...)
        }
      }
      // if it isn't any of the expected elements then throw an error.
      AddError(childBlock.Statements, reader, RuntimeError.NoSuchMember,
        new Expression[2]{new Literal(tempChecker.GetTypeName(type),SystemTypes.String), nameLocal});

      // If it's not an element then consume it anyway to keep the reader advancing.
      // Probably a comment or PI or something.
      ifElement.FalseBlock.Statements.Add(new ExpressionStatement(new MethodCall(
        new QualifiedIdentifier(reader, Identifier.For("Skip")), new ExpressionList())));

      if (isMixed) {
        statements.Add(new AssignmentStatement(GetMemberBinding(target, mixedMember), 
          new MethodCall(new QualifiedIdentifier(sb, Identifier.For("ToString")), new ExpressionList())));         
      }
      statements.Add(new AssignmentStatement(result, Literal.True));

    }
예제 #28
0
    void AddReadTuple(Block block, TupleType tuple, StatementList statements, Identifier reader, 
      Expression target, Expression required, Expression result){

      Local lt = new Local(Identifier.Empty, tuple, block);

      StatementList currentBlock = statements;

      for(int i = 0, n = tuple.Members.Length; i < n; i++) {
        Member mem = tuple.Members[i];
        if (mem is Field) {
          Field f = (Field)mem;
          TypeNode mt = f.Type;
          if (mt == null) continue; // type resolution error.
          Expression mb = GetMemberBinding(target, f, mt);
          if (mt.Template == SystemTypes.GenericBoxed){
            AddReadOptional(block, statements, f, mb, reader, result);
          }          
          else if (mem.IsAnonymous) {
            if (mt is TupleType || mt is TypeUnion || IsStream(mt)) {
              AddCallDeserializer(mt, statements, reader, mb, required, result);        
            } else  {
              Identifier name = Checker.GetDefaultElementName(mt);
              AddReadRequiredChild(block, statements, name, mt, mb, reader, result, Literal.True, true, true);
            }            
          } else {
            // could reduce a bit of code if we could assign currentName and pass the local to AddReadChild...
            AddReadRequiredChild(block, statements, mem.Name, mt, mb, reader, result, required, false, true);
          }
        }
      }
    }
예제 #29
0
        private static void AddInterfaceImplementationWrapper(Class Class, Method intfMethod, Method baseMethod)
        {
            var d = new Duplicator(Class.DeclaringModule, Class);
            
            d.SkipBodies = true;

            var copy = d.VisitMethod(baseMethod);
            
            copy.Flags = MethodFlags.Private | MethodFlags.HideBySig | MethodFlags.Virtual | MethodFlags.NewSlot |
                         MethodFlags.Final;
            
            copy.ImplementedInterfaceMethods = new MethodList(intfMethod);
            copy.Name = Identifier.For("InheritedInterfaceImplementationContractWrapper$" + intfMethod.Name.Name);
            copy.ClearBody();
            copy.ThisParameter.Type = Class;
            
            var bodyBlock = new Block(new StatementList());
            copy.Body = new Block(new StatementList(bodyBlock));

            // add call to baseMethod
            var calledMethod = (baseMethod.TemplateParameters != null && baseMethod.TemplateParameters.Count > 0)
                ? baseMethod.GetTemplateInstance(Class, copy.TemplateParameters)
                : baseMethod;

            var argList = new ExpressionList();
            for (int i = 0; i < copy.Parameters.Count; i++)
            {
                argList.Add(copy.Parameters[i]);
            }

            var callExpression = new MethodCall(new MemberBinding(copy.ThisParameter, calledMethod), argList);
            if (HelperMethods.IsVoidType(intfMethod.ReturnType))
            {
                bodyBlock.Statements.Add(new ExpressionStatement(callExpression));
            }
            else
            {
                bodyBlock.Statements.Add(new Return(callExpression));
            }
            
            Class.Members.Add(copy);
        }
예제 #30
0
 void AddReadOptional(Block block, StatementList statements, Member mem, Expression target, Identifier reader, Expression result) {
   TypeNode boxed = Checker.GetMemberType(mem);
   TypeNode type = Checker.GetCollectionElementType(boxed);
   statements.Add(new ExpressionStatement(new MethodCall(new QualifiedIdentifier(reader, Identifier.For("MoveToContent")), new ExpressionList())));
   Local nameLocal = new Local(Identifier.For("name"),SystemTypes.String, block);
   Local nsLocal = new Local(Identifier.For("ns"),SystemTypes.String, block);
   statements.Add(new AssignmentStatement(nameLocal, new QualifiedIdentifier(reader, Identifier.For("LocalName"))));
   statements.Add(new AssignmentStatement(nsLocal, new QualifiedIdentifier(reader, Identifier.For("NamespaceURI"))));
   StringBuilder expecting = new StringBuilder();
   Expression isFound = null;
   if (mem.IsAnonymous) {
     isFound = IsStartOf(block, type, statements, nameLocal, nsLocal, expecting);    
   } else {
     ExpressionList args = new ExpressionList();
     args.Add(new Literal(mem.Name.Name, SystemTypes.String));
     isFound = new MethodCall(new QualifiedIdentifier(reader, Identifier.For("IsStartElement")), args);
   }
   StatementList trueStatements = new StatementList();
   If ifIsFound = new If(isFound, new Block(trueStatements), null);
   statements.Add(ifIsFound);
   
   if (!AddReadSimpleType(type, trueStatements, reader, target, result, false)) {
     Local localRequired = new Local(Identifier.Empty,SystemTypes.Boolean,block);
     statements.Add(new AssignmentStatement(localRequired, Literal.True));
     AddCallDeserializer(type, trueStatements, reader, target, localRequired, result);            
   } 
 }