示例#1
0
文件: Duplicator.cs 项目: xornand/cci
 public override void RewriteChildren(TargetExpression targetExpression) {
   BoundField/*?*/ boundField;
   if (this.fieldForCapturedLocalOrParameter.TryGetValue(targetExpression.Definition, out boundField)) {
     targetExpression.Instance = new ThisReference();
     targetExpression.Definition = iteratorClosure.GetReferenceOfFieldUsedByPeers(boundField.Field);
     targetExpression.Type = boundField.Type;
     return;
   }
   base.RewriteChildren(targetExpression);
 }
示例#2
0
 private Statement ParseAssignment(IOperation currentOperation)
 {
     TargetExpression target = new TargetExpression();
       ITypeReference/*?*/ elementType = null;
       target.Alignment = this.alignment;
       target.Definition = currentOperation.Value;
       target.IsVolatile = this.sawVolatile;
       Assignment assignment = new Assignment();
       assignment.Target = target;
       assignment.Source = this.PopOperandStack();
       ExpressionStatement result = new ExpressionStatement();
       result.Expression = assignment;
       switch (currentOperation.OperationCode) {
     case OperationCode.Stfld:
       target.Instance = this.PopOperandStack();
       break;
     case OperationCode.Stelem:
     case OperationCode.Stelem_I:
     case OperationCode.Stelem_I1:
     case OperationCode.Stelem_I2:
     case OperationCode.Stelem_I4:
     case OperationCode.Stelem_I8:
     case OperationCode.Stelem_R4:
     case OperationCode.Stelem_R8:
     case OperationCode.Stelem_Ref:
       ArrayIndexer indexer = this.ParseArrayIndexer(currentOperation);
       target.Definition = indexer;
       target.Instance = indexer.IndexedObject;
       break;
     case OperationCode.Stind_I:
       elementType = this.platformType.SystemIntPtr;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I1:
       elementType = this.platformType.SystemInt8;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I2:
       elementType = this.platformType.SystemInt16;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I4:
       elementType = this.platformType.SystemInt32;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I8:
       elementType = this.platformType.SystemInt64;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_R4:
       elementType = this.platformType.SystemFloat32;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_R8:
       elementType = this.platformType.SystemFloat64;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_Ref:
     case OperationCode.Stobj:
       AddressDereference addressDereference = new AddressDereference();
       addressDereference.Address = this.PopOperandStack();
       addressDereference.Alignment = this.alignment;
       addressDereference.IsVolatile = this.sawVolatile;
       //capture the element type. The pointer might be untyped, in which case the instruction is the only point where the element type is known.
       if (elementType != null) addressDereference.Type = elementType; //else: The type inferencer will fill in the type once the pointer type is known.
       target.Definition = addressDereference;
       break;
     case OperationCode.Stloc:
     case OperationCode.Stloc_0:
     case OperationCode.Stloc_1:
     case OperationCode.Stloc_2:
     case OperationCode.Stloc_3:
     case OperationCode.Stloc_S:
       var local = this.GetLocalWithSourceName((ILocalDefinition)target.Definition);
       target.Definition = local;
       this.numberOfAssignments[local] =
     this.numberOfAssignments.ContainsKey(local) ?
     this.numberOfAssignments[local] + 1 :
     1;
       break;
       }
       this.alignment = 0;
       this.sawVolatile = false;
       return result;
 }
示例#3
0
 private Statement ParseArraySet(IOperation currentOperation)
 {
     ExpressionStatement result = new ExpressionStatement();
       Assignment assignment = new Assignment();
       result.Expression = assignment;
       assignment.Source = this.PopOperandStack();
       TargetExpression targetExpression = new TargetExpression();
       assignment.Target = targetExpression;
       ArrayIndexer indexer = this.ParseArrayIndexer(currentOperation);
       targetExpression.Definition = indexer;
       targetExpression.Instance = indexer.IndexedObject;
       return result;
 }
示例#4
0
 private Expression ParseCopyObject()
 {
     AddressDereference source = new AddressDereference();
       source.Address = this.PopOperandStack();
       AddressDereference addressDeref = new AddressDereference();
       addressDeref.Address = this.PopOperandStack();
       TargetExpression target = new TargetExpression();
       target.Definition = addressDeref;
       Assignment result = new Assignment();
       result.Source = source;
       result.Target = target;
       return result;
 }
 /// <summary>
 /// Rewrites the children of the given target expression.
 /// </summary>
 public override void RewriteChildren(TargetExpression targetExpression) {
   IFieldReference closureField;
   var map = this.isInsideAnonymousMethod ? this.fieldReferencesForUseInsideAnonymousMethods : this.fieldReferencesForUseInsideThisMethod;
   if (map.TryGetValue(targetExpression.Definition, out closureField)) {
     targetExpression.Instance = this.GetClosureObjectInstanceContaining(closureField);
     targetExpression.Definition = closureField;
     targetExpression.Type = closureField.Type;
     return;
   }
   base.RewriteChildren(targetExpression);
 }
 private Statement ParseAssignment(IOperation currentOperation) {
   Contract.Requires(currentOperation != null);
   TargetExpression target = new TargetExpression();
   ITypeReference/*?*/ elementType = null;
   if (this.alignment > 0) {
     Contract.Assume(this.alignment == 1 || this.alignment == 2 || this.alignment == 4);
     target.Alignment = this.alignment;
   }
   target.IsVolatile = this.sawVolatile;
   Assignment assignment = new Assignment();
   assignment.Target = target;
   assignment.Source = this.PopOperandStack();
   ExpressionStatement result = new ExpressionStatement();
   result.Expression = assignment;
   switch (currentOperation.OperationCode) {
     case OperationCode.Starg:
     case OperationCode.Starg_S: {
         var definition = currentOperation.Value;
         if (definition == null) {
           target.Definition = new ThisReference();
           var typeForThis = (INamedTypeDefinition)this.MethodDefinition.ContainingTypeDefinition;
           if (typeForThis.IsValueType)
             target.Type = Immutable.ManagedPointerType.GetManagedPointerType(Microsoft.Cci.MutableCodeModel.NamedTypeDefinition.SelfInstance(typeForThis, this.host.InternFactory), this.host.InternFactory);
           else
             target.Type = NamedTypeDefinition.SelfInstance(typeForThis, this.host.InternFactory);
         } else {
           var par = definition as IParameterDefinition;
           Contract.Assume(par != null);
           target.Definition = definition;
           target.Type = par.Type;
         }
         break;
       }
     case OperationCode.Stfld:
       target.Instance = this.PopOperandStack();
       goto case OperationCode.Stsfld;
     case OperationCode.Stsfld:
       Contract.Assume(currentOperation.Value is IFieldReference);
       var field = (IFieldReference)currentOperation.Value;
       target.Definition = field;
       target.Type = field.Type;
       break;
     case OperationCode.Stelem:
       elementType = (ITypeReference)currentOperation.Value;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_I:
       elementType = this.platformType.SystemIntPtr;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_I1:
       elementType = this.platformType.SystemInt8;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_I2:
       elementType = this.platformType.SystemInt16;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_I4:
       elementType = this.platformType.SystemInt32;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_I8:
       elementType = this.platformType.SystemInt64;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_R4:
       elementType = this.platformType.SystemFloat32;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_R8:
       elementType = this.platformType.SystemFloat64;
       goto case OperationCode.Stelem_Ref;
     case OperationCode.Stelem_Ref:
       ArrayIndexer indexer = this.ParseArrayIndexer(currentOperation, elementType??this.platformType.SystemObject, treatArrayAsSingleDimensioned: true);
       target.Definition = indexer;
       target.Instance = indexer.IndexedObject;
       target.Type = indexer.Type;
       break;
     case OperationCode.Stind_I:
       elementType = this.platformType.SystemIntPtr;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I1:
       elementType = this.platformType.SystemInt8;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I2:
       elementType = this.platformType.SystemInt16;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I4:
       elementType = this.platformType.SystemInt32;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_I8:
       elementType = this.platformType.SystemInt64;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_R4:
       elementType = this.platformType.SystemFloat32;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_R8:
       elementType = this.platformType.SystemFloat64;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stobj:
       elementType = (ITypeReference)currentOperation.Value;
       goto case OperationCode.Stind_Ref;
     case OperationCode.Stind_Ref:
       AddressDereference addressDereference = new AddressDereference();
       addressDereference.Address = this.PopOperandStack();
       addressDereference.Alignment = this.alignment;
       addressDereference.IsVolatile = this.sawVolatile;
       target.Definition = addressDereference;
       var pointerType = addressDereference.Address.Type as IPointerTypeReference;
       if (pointerType != null)
         addressDereference.Type = pointerType.TargetType;
       else {
         var managedPointerType = addressDereference.Address.Type as IManagedPointerTypeReference;
         if (managedPointerType != null)
           addressDereference.Type = managedPointerType.TargetType;
         else {
           //The pointer itself is untyped, so the instruction must have specified the element type
           addressDereference.Type = elementType??this.platformType.SystemObject;
         }
       }
       target.Type = addressDereference.Type;
       break;
     case OperationCode.Stloc:
     case OperationCode.Stloc_0:
     case OperationCode.Stloc_1:
     case OperationCode.Stloc_2:
     case OperationCode.Stloc_3:
     case OperationCode.Stloc_S:
       Contract.Assume(currentOperation.Value is ILocalDefinition);
       var local = this.GetLocalWithSourceName((ILocalDefinition)currentOperation.Value);
       target.Definition = local;
       this.numberOfAssignmentsToLocal[local] =
         this.numberOfAssignmentsToLocal.ContainsKey(local) ?
         this.numberOfAssignmentsToLocal[local] + 1 :
         1;
       target.Type = local.Type;
       break;
     default: {
         var definition = currentOperation.Value;
         Contract.Assume(definition is ILocalDefinition || definition is IParameterDefinition || 
         definition is IFieldReference || definition is IArrayIndexer || 
         definition is IAddressDereference || definition is IPropertyDefinition);
         target.Definition = definition;
         break;
       }
   }
   assignment.Source = TypeInferencer.Convert(assignment.Source, target.Type); //mainly to convert (u)ints to bools, chars and pointers.
   assignment.Type = target.Type;
   Contract.Assume(assignment.Target.Type.TypeCode != PrimitiveTypeCode.Boolean || assignment.Source.Type.TypeCode == PrimitiveTypeCode.Boolean || IsByRef(assignment.Target.Definition));
   this.alignment = 0;
   this.sawVolatile = false;
   return result;
 }
 private Statement ParseArraySet(IOperation currentOperation) {
   Contract.Requires(currentOperation != null);
   ExpressionStatement result = new ExpressionStatement();
   Assignment assignment = new Assignment();
   result.Expression = assignment;
   assignment.Source = this.PopOperandStack();
   TargetExpression targetExpression = new TargetExpression();
   assignment.Target = targetExpression;
   Contract.Assume(currentOperation.Value is IArrayTypeReference);
   ArrayIndexer indexer = this.ParseArrayIndexer(currentOperation, ((IArrayTypeReference)currentOperation.Value).ElementType);
   targetExpression.Definition = indexer;
   targetExpression.Instance = indexer.IndexedObject;
   targetExpression.Type = indexer.Type;
   assignment.Source = TypeInferencer.Convert(assignment.Source, indexer.Type);
   assignment.Type = indexer.Type;
   return result;
 }
        public override void BuildMethod()
        {
            AddStatement.DeclareInterceptedType(field.ContainingType.ResolvedType);

            Context.Log.WriteTrace("  Adding: var interceptedField = interceptedType.GetField('{0}');", field.Name.Value);
            Context.Block.Statements.Add(
                Declare.Variable<FieldInfo>("interceptedField").As(
                    Call.VirtualMethod("GetField", typeof (string)).ThatReturns<FieldInfo>().WithArguments(
                        Constant.Of(field.Name.Value)).On("interceptedType"))
            );

            AddStatement.DeclareArgumentsList();
            AddStatement.AddArgumentToList(Params["assignedValue"]);

            var actionT = SharpMockTypes.Actions[1];
            var actionActualT = new GenericTypeInstanceReference();
            actionActualT.GenericType = actionT;
            actionActualT.GenericArguments.Add(field.Type);

            var assignment = new AnonymousDelegate();
            assignment.Type = actionActualT;
            assignment.ReturnType = Context.Host.PlatformType.SystemVoid;
            assignment.CallingConvention = CallingConvention.HasThis;

            var parameterDefinition = new ParameterDefinition();
            parameterDefinition.Index = 0;
            parameterDefinition.Type = field.Type;
            parameterDefinition.Name = Context.Host.NameTable.GetNameFor("alteredValue");
            parameterDefinition.ContainingSignature = assignment;

            assignment.Parameters.Add(parameterDefinition);

            var assignmentBody = new BlockStatement();
            var assignActualField = new ExpressionStatement();
            var actualField = new TargetExpression();
            actualField.Type = field.Type;
            actualField.Definition = field;
            var value = new BoundExpression();
            value.Type = field.Type;
            value.Definition = parameterDefinition;
            var assignValueToField = new Assignment();
            assignValueToField.Source = value;
            assignValueToField.Target = actualField;
            assignValueToField.Type = field.Type;
            assignActualField.Expression = assignValueToField;

            actualField.Type = field.Type;
            actualField.Definition = field;

            assignmentBody.Statements.Add(assignActualField);
            assignmentBody.Statements.Add(new ReturnStatement());
            assignment.Body = assignmentBody;

            Context.Block.Statements.Add(
                Declare.Variable("local_0", actionActualT).As(assignment)
            );

            AddStatement.DeclareRegistryInterceptor();
            AddStatement.DeclareInvocation();
            AddStatement.SetArgumentsOnInvocation();
            AddStatement.SetOriginalCallOnInvocation();
            AddStatement.SetTargetOnInvocationToNull();

            Context.Block.Statements.Add(
                Do(Call.PropertySetter<MemberInfo>("OriginalCallInfo").WithArguments("interceptedField").On("invocation"))
            );

            AddStatement.CallShouldInterceptOnInterceptor();
            AddStatement.CallInterceptOnInterceptor();

            Context.Block.Statements.Add(Return.Void());
        }
示例#9
0
 /// <summary>
 /// Visits the specified target expression.
 /// </summary>
 /// <param name="targetExpression">The target expression.</param>
 /// <returns></returns>
 protected virtual ITargetExpression DeepCopy(TargetExpression targetExpression)
 {
     object def = targetExpression.Definition;
       ILocalDefinition/*?*/ loc = def as ILocalDefinition;
       if (loc != null)
     targetExpression.Definition = this.GetMutableCopyIfItExists(loc);
       else {
     IParameterDefinition/*?*/ par = targetExpression.Definition as IParameterDefinition;
     if (par != null)
       targetExpression.Definition = this.GetMutableCopyIfItExists(par);
     else {
       IFieldReference/*?*/ field = targetExpression.Definition as IFieldReference;
       if (field != null) {
     if (targetExpression.Instance != null)
       targetExpression.Instance = this.Substitute(targetExpression.Instance);
     targetExpression.Definition = this.Substitute(field);
       } else {
     IArrayIndexer/*?*/ indexer = def as IArrayIndexer;
     if (indexer != null) {
       targetExpression.Definition = this.Substitute(indexer);
       indexer = targetExpression.Definition as IArrayIndexer;
       if (indexer != null) {
         targetExpression.Instance = indexer.IndexedObject;
         targetExpression.Type = indexer.Type;
         return targetExpression;
       }
     } else {
       IAddressDereference/*?*/ adr = def as IAddressDereference;
       if (adr != null)
         targetExpression.Definition = this.Substitute(adr);
       else {
         IPropertyDefinition/*?*/ prop = def as IPropertyDefinition;
         if (prop != null) {
           if (targetExpression.Instance != null)
             targetExpression.Instance = this.Substitute(targetExpression.Instance);
           targetExpression.Definition = this.GetMutableCopyIfExists(prop);
         }
       }
     }
       }
     }
       }
       targetExpression.Type = this.Substitute(targetExpression.Type);
       return targetExpression;
 }
示例#10
0
 /// <summary>
 /// Visits the specified target expression.
 /// </summary>
 /// <param name="targetExpression">The target expression.</param>
 public override void Visit(ITargetExpression targetExpression)
 {
     TargetExpression mutableTargetExpression = new TargetExpression(targetExpression);
     this.resultExpression = this.myCodeCopier.DeepCopy(mutableTargetExpression);
 }
 public override ITargetExpression Visit(TargetExpression targetExpression)
 {
     var closureField = targetExpression.Definition as IFieldReference;
       if (closureField != null) {
     var unspecializedClosureField = UnspecializedMethods.UnspecializedFieldReference(closureField);
     IBoundExpression binding = null;
     if (this.capturedBinding.TryGetValue(unspecializedClosureField.InternedKey, out binding)) {
       targetExpression.Definition = binding.Definition;
       targetExpression.Instance = binding.Instance;
       return targetExpression;
     }
       }
       var parameter = targetExpression.Definition as IParameterDefinition;
       if (parameter != null) {
     IParameterDefinition parToSubstitute;
     if (this.parameterMap.TryGetValue(parameter, out parToSubstitute)) {
       targetExpression.Definition = parToSubstitute;
       return targetExpression;
     }
       }
       return base.Visit(targetExpression);
 }
示例#12
0
 /// <summary>
 /// Rewrites the children of the given target expression.
 /// </summary>
 public virtual void RewriteChildren(TargetExpression targetExpression)
 {
     this.RewriteChildren((Expression)targetExpression);
       var local = targetExpression.Definition as ILocalDefinition;
       if (local != null)
     targetExpression.Definition = this.RewriteReference(local);
       else {
     var parameter = targetExpression.Definition as IParameterDefinition;
     if (parameter != null)
       targetExpression.Definition = this.RewriteReference(parameter);
     else {
       var fieldReference = targetExpression.Definition as IFieldReference;
       if (fieldReference != null)
     targetExpression.Definition = this.Rewrite(fieldReference);
       else {
     var arrayIndexer = targetExpression.Definition as IArrayIndexer;
     if (arrayIndexer != null) {
       targetExpression.Definition = this.Rewrite(arrayIndexer);
       arrayIndexer = targetExpression.Definition as IArrayIndexer;
       if (arrayIndexer != null) {
         targetExpression.Instance = arrayIndexer.IndexedObject;
         return;
       }
     } else {
       var addressDereference = targetExpression.Definition as IAddressDereference;
       if (addressDereference != null)
         targetExpression.Definition = this.Rewrite(addressDereference);
       else {
         var propertyDefinition = (IPropertyDefinition)targetExpression.Definition;
         targetExpression.Definition = this.Rewrite(propertyDefinition);
       }
     }
       }
     }
       }
       if (targetExpression.Instance != null) {
     targetExpression.Instance = this.Rewrite(targetExpression.Instance);
       }
 }
示例#13
0
 /// <summary>
 /// Visits the specified target expression.
 /// </summary>
 /// <param name="targetExpression">The target expression.</param>
 public override void Visit(ITargetExpression targetExpression)
 {
     TargetExpression mutableTargetExpression = targetExpression as TargetExpression;
     if (alwaysMakeACopy || mutableTargetExpression == null) mutableTargetExpression = new TargetExpression(targetExpression);
     this.resultExpression = this.myCodeMutator.Visit(mutableTargetExpression);
 }
示例#14
0
 /// <summary>
 /// Visits the specified target expression.
 /// </summary>
 /// <param name="targetExpression">The target expression.</param>
 /// <returns></returns>
 public virtual ITargetExpression Visit(ITargetExpression targetExpression)
 {
     TargetExpression mutableTargetExpression = targetExpression as TargetExpression;
       if (!this.copyOnlyIfNotAlreadyMutable || mutableTargetExpression == null)
     mutableTargetExpression = new TargetExpression(targetExpression);
       return Visit(mutableTargetExpression);
 }
示例#15
0
 /// <summary>
 /// Visits the specified target expression.
 /// </summary>
 /// <param name="targetExpression">The target expression.</param>
 /// <returns></returns>
 public virtual ITargetExpression Visit(TargetExpression targetExpression)
 {
     object def = targetExpression.Definition;
       ILocalDefinition/*?*/ loc = def as ILocalDefinition;
       if (loc != null)
     targetExpression.Definition = this.VisitReferenceTo(loc);
       else {
     IParameterDefinition/*?*/ par = targetExpression.Definition as IParameterDefinition;
     if (par != null)
       targetExpression.Definition = this.VisitReferenceTo(par);
     else {
       IFieldReference/*?*/ field = targetExpression.Definition as IFieldReference;
       if (field != null) {
     if (targetExpression.Instance != null)
       targetExpression.Instance = this.Visit(targetExpression.Instance);
     targetExpression.Definition = this.Visit(field);
       } else {
     IArrayIndexer/*?*/ indexer = def as IArrayIndexer;
     if (indexer != null) {
       targetExpression.Definition = this.Visit(indexer);
       indexer = targetExpression.Definition as IArrayIndexer;
       if (indexer != null) {
         targetExpression.Instance = indexer.IndexedObject;
         targetExpression.Type = indexer.Type;
         return targetExpression;
       }
     } else {
       IAddressDereference/*?*/ adr = def as IAddressDereference;
       if (adr != null)
         targetExpression.Definition = this.Visit(adr);
       else {
         IPropertyDefinition/*?*/ prop = def as IPropertyDefinition;
         if (prop != null) {
           if (targetExpression.Instance != null)
             targetExpression.Instance = this.Visit(targetExpression.Instance);
           targetExpression.Definition = this.Visit(this.GetMutableCopy(prop));
         }
       }
     }
       }
     }
       }
       targetExpression.Type = this.Visit(targetExpression.Type);
       return targetExpression;
 }