Exemple #1
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            OpType xType = ( OpType )aOpCode;
            string xTypeID = GetTypeIDLabel(xType.Value);
            string mReturnNullLabel = GetLabel( aMethod, aOpCode ) + "_ReturnNull";

            new CPUx86.Mov { DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.ESP, SourceIsIndirect = true };

            new CPUx86.Compare { DestinationReg = CPUx86.Registers.EAX, SourceValue = 0 };
            new CPUx86.ConditionalJump { Condition = CPUx86.ConditionalTestEnum.Zero, DestinationLabel = mReturnNullLabel };

            // EAX contains a memory handle now. Lets convert it to a pointer
            new CPUx86.Mov { DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EAX, SourceIsIndirect = true };

            //new CPUx86.Mov {DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EAX, SourceIsIndirect = true};
            new CPUx86.Push { DestinationReg = CPUx86.Registers.EAX, DestinationIsIndirect = true };
            new CPUx86.Push { DestinationRef = Cosmos.Assembler.ElementReference.New( xTypeID ), DestinationIsIndirect = true };

            SysReflection.MethodBase xMethodIsInstance = ReflectionUtilities.GetMethodBase( typeof( VTablesImpl ), "IsInstance", "System.UInt32", "System.UInt32" );
//, new OpMethod( ILOpCode.Code.Call, aOpCode.Position, aOpCode.NextPosition, xMethodIsInstance, aOpCode.CurrentExceptionHandler));
            Call.DoExecute(Assembler, aMethod, xMethodIsInstance, aOpCode, GetLabel(aMethod, aOpCode), GetLabel(aMethod, aOpCode) + "_After_IsInstance_Call", DebugEnabled);

            new Label( GetLabel( aMethod, aOpCode ) + "_After_IsInstance_Call" );
            new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
            new CPUx86.Compare { DestinationReg = CPUx86.Registers.EAX, SourceValue = 0 };
            new CPUx86.ConditionalJump { Condition = CPUx86.ConditionalTestEnum.Equal, DestinationLabel = mReturnNullLabel };
            // push nothing now, as we should return the object instance pointer.
            new CPUx86.Jump { DestinationLabel = GetLabel(aMethod, aOpCode.NextPosition) };
            new Label( mReturnNullLabel );
            new CPUx86.Add { DestinationReg = CPUx86.Registers.ESP, SourceValue = 4 };
            new CPUx86.Push { DestinationValue = 0 };
        }
Exemple #2
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            var xStackContent = aOpCode.StackPopTypes[0];
            var xStackContentSecond = aOpCode.StackPopTypes[1];
            var xStackContentSize = SizeOfType(xStackContent);
            var xStackContentSecondSize = SizeOfType(xStackContentSecond);
			var xSize = Math.Max(xStackContentSize, xStackContentSecondSize);
            if (ILOp.Align(xStackContentSize, 4u) != ILOp.Align(xStackContentSecondSize, 4u))
            {
                throw new NotSupportedException("Operands have different size!");
            }
            if (xSize > 8)
            {
                throw new NotImplementedException("StackSize>8 not supported");
            }

            if (xSize > 4)
			{
				// [ESP] is low part
				// [ESP + 4] is high part
				// [ESP + 8] is low part
				// [ESP + 12] is high part
				XS.Pop(XSRegisters.EAX);
				XS.Pop(XSRegisters.EDX);
				// [ESP] is low part
				// [ESP + 4] is high part
				XS.Or(XSRegisters.ESP, XSRegisters.EAX, destinationIsIndirect: true);
				XS.Or(XSRegisters.ESP, XSRegisters.EDX, destinationDisplacement: 4);
			}
			else
			{
				XS.Pop(XSRegisters.EAX);
				XS.Or(XSRegisters.ESP, XSRegisters.EAX, destinationIsIndirect: true);
			}
        }
Exemple #3
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     DoNullReferenceCheck(Assembler, DebugEnabled, 0);
     new CPUx86.Pop { DestinationReg = CPUx86.Registers.ECX };
     new CPUx86.MoveZeroExtend { DestinationReg = CPUx86.Registers.EAX, Size = 16, SourceReg = CPUx86.Registers.ECX, SourceIsIndirect = true };
     new CPUx86.Push { DestinationReg = CPUx86.Registers.EAX };
 }
Exemple #4
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            OpToken xToken = ( OpToken )aOpCode;
            string xTokenAddress = null;

            if (xToken.ValueIsType)
            {
                xTokenAddress = ILOp.GetTypeIDLabel(xToken.ValueType);
            }
            if (xToken.ValueIsField)
            {
                xTokenAddress= DataMember.GetStaticFieldName(xToken.ValueField);
            }

            if (String.IsNullOrEmpty(xTokenAddress))
            {
                throw new Exception("Ldtoken not implemented!");
            }

            //if( mType != null )
            //{
            //    mTokenAddress = GetService<IMetaDataInfoService>().GetTypeIdLabel( mType );
            //}
            //XS.Push(xToken.Value);
            XS.Push(xTokenAddress);
            XS.Push(0);
        }
Exemple #5
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     DoNullReferenceCheck(Assembler, DebugEnabled, 0);
     XS.Pop(XSRegisters.ECX);
     new CPUx86.MoveSignExtend { DestinationReg = CPUx86.RegistersEnum.EAX, Size = 8, SourceReg = CPUx86.RegistersEnum.ECX, SourceIsIndirect = true };
     XS.Push(XSRegisters.EAX);
 }
Exemple #6
0
		public override void Execute(MethodInfo aMethod, ILOpCode aOpCode) {
			//TODO: What if the last ILOp in a method was Conv_Ovf_I_Un or an other?
            var xSource = aOpCode.StackPopTypes[0];
            var xSourceSize = SizeOfType(xSource);
            var xSourceIsFloat = TypeIsFloat(xSource);
			if(xSourceIsFloat)
				ThrowNotImplementedException("Conv_Ovf_I_Un throws an ArgumentException, because float is not implemented!");

			switch (xSourceSize)
			{
				case 1:
				case 2:
				case 4:
					break;
				case 8:
					{
						string NoOverflowLabel = GetLabel(aMethod, aOpCode) + "__NoOverflow";
						new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
						// EBX is high part and should be zero for unsigned, so we test it on zero
						{
							new CPUx86.Pop { DestinationReg = CPUx86.Registers.EBX };
							new CPUx86.Compare { DestinationReg = CPUx86.Registers.EBX, SourceValue = 0 };
							new CPUx86.ConditionalJump { Condition = CPUx86.ConditionalTestEnum.Equal, DestinationLabel = NoOverflowLabel };
							ThrowNotImplementedException("Conv_Ovf_I_Un throws an overflow exception, which is not implemented!");
						}
						new Label(NoOverflowLabel);
						new CPUx86.Push { DestinationReg = CPUx86.Registers.EAX };
						break;
					}
				default:
					ThrowNotImplementedException("Conv_Ovf_I_Un not implemented for this size!");
					break;
			}
		}
Exemple #7
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            var xValue = aOpCode.StackPopTypes[0];
            var xValueIsFloat = TypeIsFloat(xValue);
            var xValueSize = SizeOfType(xValue);
            if (xValueSize > 8)
            {
                //EmitNotImplementedException( Assembler, aServiceProvider, "Size '" + xSize.Size + "' not supported (add)", aCurrentLabel, aCurrentMethodInfo, aCurrentOffset, aNextLabel );
                throw new NotImplementedException();
            }
			//TODO if on stack a float it is first truncated, http://msdn.microsoft.com/en-us/library/system.reflection.emit.opcodes.conv_r_un.aspx
            if (!xValueIsFloat)
            {
                switch (xValueSize)
                {
                    case 1:
                    case 2:
                    case 4:
                        new CPUx86.Mov { SourceReg = CPUx86.RegistersEnum.ESP, DestinationReg = CPUx86.RegistersEnum.EAX, SourceIsIndirect = true };
                        XS.SSE.ConvertSI2SS(XSRegisters.XMM0, XSRegisters.EAX);
                        XS.SSE.MoveSS(XSRegisters.ESP, XSRegisters.XMM0, destinationIsIndirect: true);
                        break;
                    case 8:
                    //XS.Add(XSRegisters.ESP, 4);
                    //break;
                    default:
                        //EmitNotImplementedException( Assembler, GetServiceProvider(), "Conv_I: SourceSize " + xSource + " not supported!", mCurLabel, mMethodInformation, mCurOffset, mNextLabel );
                        throw new NotImplementedException();
                }
            }
            else
            {
                throw new NotImplementedException();
            }
        }
Exemple #8
0
 public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
 {
   var xStackContent = aOpCode.StackPopTypes[0];
   var xStackContentSize = SizeOfType(xStackContent);
   string BaseLabel = GetLabel(aMethod, aOpCode) + ".";
   DoExecute(xStackContentSize, BaseLabel);
 }
Exemple #9
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            OpType xType = ( OpType )aOpCode;
            string xTypeID = GetTypeIDLabel(xType.Value);
            string mReturnNullLabel = GetLabel( aMethod, aOpCode ) + "_ReturnNull";

            XS.Set(XSRegisters.EAX, XSRegisters.ESP, sourceIsIndirect: true);

            XS.Compare(XSRegisters.EAX, 0);
            XS.Jump(CPUx86.ConditionalTestEnum.Zero, mReturnNullLabel);

            // EAX contains a memory handle now. Lets convert it to a pointer
            XS.Set(XSRegisters.EAX, XSRegisters.EAX, sourceIsIndirect: true);

            //XS.Mov(XSRegisters.EAX, XSRegisters.EAX, sourceIsIndirect: true);
            XS.Push(XSRegisters.EAX, isIndirect: true);
            XS.Push(xTypeID, isIndirect: true);

            SysReflection.MethodBase xMethodIsInstance = ReflectionUtilities.GetMethodBase( typeof( VTablesImpl ), "IsInstance", "System.UInt32", "System.UInt32" );
            //, new OpMethod( ILOpCode.Code.Call, aOpCode.Position, aOpCode.NextPosition, xMethodIsInstance, aOpCode.CurrentExceptionHandler));
            Call.DoExecute(Assembler, aMethod, xMethodIsInstance, aOpCode, GetLabel(aMethod, aOpCode), GetLabel(aMethod, aOpCode) + "_After_IsInstance_Call", DebugEnabled);

            new Label( GetLabel( aMethod, aOpCode ) + "_After_IsInstance_Call" );
            XS.Pop(XSRegisters.EAX);
            XS.Compare(XSRegisters.EAX, 0);
            XS.Jump(CPUx86.ConditionalTestEnum.Equal, mReturnNullLabel);
            // push nothing now, as we should return the object instance pointer.
            new CPUx86.Jump { DestinationLabel = GetLabel(aMethod, aOpCode.NextPosition) };
            XS.Label(mReturnNullLabel );
            XS.Add(XSRegisters.ESP, 4);
            XS.Push(0);
        }
Exemple #10
0
    public override void Execute(MethodInfo aMethod, ILOpCode aOpCode) {
        var xSource = aOpCode.StackPopTypes[0];
        var xSourceSize = SizeOfType(xSource);
        switch (xSourceSize)
        {
            case 1:
            case 2:
            case 4:
				if (TypeIsFloat(xSource))
				{
					new CPUx86.SSE.ConvertSS2SD { DestinationReg = CPUx86.Registers.XMM0, SourceReg = CPUx86.Registers.ESP, SourceIsIndirect = true };
				}
				else
				{
					new CPUx86.SSE.ConvertSI2SD { DestinationReg = CPUx86.Registers.XMM0, SourceReg = CPUx86.Registers.ESP, SourceIsIndirect = true };
				}
				// expand stack, that moved data is valid stack
				new CPUx86.Sub { DestinationReg = CPUx86.Registers.ESP, SourceValue = 4 };
				new CPUx86.SSE.MoveSD { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.XMM0 };
				break;
            case 8:
                {
					if (!TypeIsFloat(xSource))
					{
						new CPUx86.x87.IntLoad { DestinationReg = CPUx86.Registers.ESP, Size = 64, DestinationIsIndirect = true };
						new CPUx86.x87.FloatStoreAndPop { DestinationReg = CPUx86.Registers.ESP, Size = 64, DestinationIsIndirect = true};
					}
                    break;
                }
            default:
                //EmitNotImplementedException( Assembler, GetServiceProvider(), "Conv_U8: SourceSize " + xSource + " not supported!", mCurLabel, mMethodInformation, mCurOffset, mNextLabel );
                throw new NotImplementedException();
		}
    }
Exemple #11
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     var xFieldSize = SizeOfType(aOpCode.StackPopTypes[0]);
     var xRoundedSize = Align(xFieldSize, 4);
     DoNullReferenceCheck(Assembler, DebugEnabled, xRoundedSize);
     
     new CPUx86.Mov { DestinationReg = CPUx86.Registers.ECX, SourceReg = CPUx86.Registers.ESP, SourceIsIndirect = true, SourceDisplacement = checked((int)xRoundedSize) };
     for( int i = 0; i < ( xFieldSize / 4 ); i++ )
     {
         new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
         new CPUx86.Mov { DestinationReg = CPUx86.Registers.ECX, DestinationIsIndirect = true, DestinationDisplacement = i * 4, SourceReg = CPUx86.Registers.EAX };
     }
     switch( xFieldSize % 4 )
     {
         case 1:
             {
                 new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
                 new CPUx86.Mov { DestinationReg = CPUx86.Registers.ECX, DestinationIsIndirect = true, DestinationDisplacement = checked((int)( xFieldSize / 4 ) * 4 ), SourceReg = CPUx86.Registers.AL };
                 break;
             }
         case 2:
             {
                 new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
                 new CPUx86.Mov { DestinationReg = CPUx86.Registers.ECX, DestinationIsIndirect = true, DestinationDisplacement = checked((int)( xFieldSize / 4 ) * 4 ), SourceReg = CPUx86.Registers.AX };
                 break;
             }
         case 0:
             {
                 break;
             }
         default:
             throw new Exception( "Remainder size " + ( xFieldSize % 4 ) + " not supported!" );
     }
     new CPUx86.Add { DestinationReg = CPUx86.Registers.ESP, SourceValue = 4 };
 }
Exemple #12
0
 public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
 {
   OpDouble xOp = (OpDouble)aOpCode;
   byte[] xBytes = BitConverter.GetBytes(xOp.Value);
   new CPU.Push { DestinationValue = BitConverter.ToUInt32(xBytes, 4) };
   new CPU.Push { DestinationValue = BitConverter.ToUInt32(xBytes, 0) };
 }
Exemple #13
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     DoNullReferenceCheck(Assembler, DebugEnabled, 0);
     new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
     new CPUx86.Add { DestinationReg = CPUx86.Registers.EAX, SourceValue = 8 };
     new CPUx86.Push { DestinationReg = CPUx86.Registers.EAX, DestinationIsIndirect = true };
 }
Exemple #14
0
 public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
 {
     //TODO: Return
     Jump_End(aMethod);
     // Need to jump to end of method. Assembler can emit this label for now
     //XS.Jump(MethodFooterOp.EndOfMethodLabelNameNormal);
 }
Exemple #15
0
    public override void Execute(MethodInfo aMethod, ILOpCode aOpCode) {
        var xSource = aOpCode.StackPopTypes[0];
        var xSourceSize = SizeOfType(xSource);
        switch (xSourceSize)
        {
            case 1:
            case 2:
            case 4:
				if (TypeIsFloat(xSource))
				{
					XS.SSE.ConvertSS2SD(XMM0, ESP, sourceIsIndirect: true);
				}
				else
				{
					XS.SSE2.ConvertSI2SD(XMM0, ESP, sourceIsIndirect: true);
				}
				// expand stack, that moved data is valid stack
				XS.Sub(XSRegisters.ESP, 4);
				XS.SSE2.MoveSD(ESP, XMM0, destinationIsIndirect: true);
				break;
            case 8:
                {
					if (!TypeIsFloat(xSource))
					{
						XS.FPU.IntLoad(ESP, isIndirect: true, size: RegisterSize.Long64);
						XS.FPU.FloatStoreAndPop(ESP, isIndirect: true, size: RegisterSize.Long64);
					}
                    break;
                }
            default:
                //EmitNotImplementedException( Assembler, GetServiceProvider(), "Conv_U8: SourceSize " + xSource + " not supported!", mCurLabel, mMethodInformation, mCurOffset, mNextLabel );
                throw new NotImplementedException();
		}
    }
Exemple #16
0
    public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
    {
      var xOpString = aOpCode as OpString;
      string xDataName = GetContentsArrayName(xOpString.Value);
      new Comment(Assembler, "String Value: " + xOpString.Value.Replace("\r", "\\r").Replace("\n", "\\n"));
      var xRefName = GetFakeHandleForLiteralArray(xDataName);
      new Mov { DestinationReg = RegistersEnum.EAX, SourceRef = Cosmos.Assembler.ElementReference.New(xRefName) };
      new Push { DestinationReg = RegistersEnum.EAX };
      // DEBUG VERIFICATION: leave it here for now. we have issues with fields ordering.
      // if that changes, we need to change the code below!
      // We also need to change the debugstub to fix this then.
      #region Debug verification

      var xFields = GetFieldsInfo(typeof(string), false).Where(i => !i.IsStatic).ToArray();
      if (xFields[0].Id != "System.Int32 System.String.m_stringLength"
        || xFields[0].Offset != 0)
      {
        throw new Exception("Fields changed!");
      }
      if (xFields[1].Id != "System.Char System.String.m_firstChar"
        || xFields[1].Offset != 4)
      {
        throw new Exception("Fields changed!");
      }
      #endregion
    }
Exemple #17
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     DoNullReferenceCheck(Assembler, DebugEnabled, 0);
     XS.Pop(XSRegisters.EAX);
     new CPUx86.Push { DestinationReg = CPUx86.RegistersEnum.EAX, DestinationIsIndirect = true, DestinationDisplacement = 4 };
     XS.Push(XSRegisters.EAX, isIndirect: true);
 }
Exemple #18
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode ) {
            var xOp = (OpInt64)aOpCode;
			// push high part
            new CPUx86.Push { DestinationValue = BitConverter.ToUInt32(BitConverter.GetBytes(xOp.Value), 4) };
			// push low part
			new CPUx86.Push { DestinationValue = BitConverter.ToUInt32(BitConverter.GetBytes(xOp.Value), 0) };
        }
Exemple #19
0
 public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
 {
   DoNullReferenceCheck(Assembler, DebugEnabled, 0);
   XS.Pop(XSRegisters.EAX);
   XS.Push(XSRegisters.EAX, isIndirect: true, displacement: 4);
   XS.Push(XSRegisters.EAX, isIndirect: true);
 }
Exemple #20
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     var xType = aOpCode.StackPopTypes[0];
     var xSize = SizeOfType(xType);
     var xIsFloat = TypeIsFloat(xType);
     DoExecute(xSize, xIsFloat);
 }
Exemple #21
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
          var xOpType = (OpType)aOpCode;
          var xSize = SizeOfType(xOpType.Value);

          Stelem_Ref.Assemble(Assembler, (uint)xSize, aMethod, aOpCode, DebugEnabled);
        }
Exemple #22
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            var xStackContent = aOpCode.StackPopTypes[0];
            var xStackContentSecond = aOpCode.StackPopTypes[1];
            var xStackContentSize = SizeOfType(xStackContent);
            var xStackContentSecondSize = SizeOfType(xStackContentSecond);
			var xSize = Math.Max(xStackContentSize, xStackContentSecondSize);
            if (ILOp.Align(xStackContentSize, 4u) != ILOp.Align(xStackContentSecondSize, 4u))
            {
                throw new NotSupportedException("Operands have different size!");
            }
            if (xSize > 8)
            {
                throw new NotImplementedException("StackSize>8 not supported");
            }

            if (xSize > 4)
			{
				// [ESP] is low part
				// [ESP + 4] is high part
				// [ESP + 8] is low part
				// [ESP + 12] is high part
				new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
				new CPUx86.Pop { DestinationReg = CPUx86.Registers.EDX };
				// [ESP] is low part
				// [ESP + 4] is high part
				new CPUx86.Or { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.EAX };
				new CPUx86.Or { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, DestinationDisplacement = 4, SourceReg = CPUx86.Registers.EDX };
			}
			else
			{
				new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
				new CPUx86.Or { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.EAX };
			}
        }
Exemple #23
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            OpToken xToken = ( OpToken )aOpCode;
            string xTokenAddress = null;
            
            if (xToken.ValueIsType)
            {
                xTokenAddress = ILOp.GetTypeIDLabel(xToken.ValueType);
            }
            if (xToken.ValueIsField)
            {
                xTokenAddress= DataMember.GetStaticFieldName(xToken.ValueField);
            }

            if (String.IsNullOrEmpty(xTokenAddress))
            {
                throw new Exception("Ldtoken not implemented!");
            }

            //if( mType != null )
            //{
            //    mTokenAddress = GetService<IMetaDataInfoService>().GetTypeIdLabel( mType );
            //}
            //new CPUx86.Push { DestinationValue = xToken.Value };
            new CPU.Push { DestinationRef = Cosmos.Assembler.ElementReference.New( xTokenAddress ) };
        }
Exemple #24
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     var xSize = Math.Max(SizeOfType(aOpCode.StackPopTypes[0]), SizeOfType(aOpCode.StackPopTypes[1]));
     XS.Pop(XSRegisters.EAX);
     XS.Pop(XSRegisters.EDX);
     XS.Xor(XSRegisters.EAX, XSRegisters.EDX);
     XS.Push(XSRegisters.EAX);
 }
Exemple #25
0
 public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
 {
     var xSize = Math.Max(SizeOfType(aOpCode.StackPopTypes[0]), SizeOfType(aOpCode.StackPopTypes[1]));
     new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
     new CPUx86.Pop { DestinationReg = CPUx86.Registers.EDX };
     new CPUx86.Xor { DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EDX };
     new CPUx86.Push { DestinationReg = CPUx86.Registers.EAX };
 }
Exemple #26
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
            DoNullReferenceCheck(Assembler, DebugEnabled, 4);
            XS.Add(XSRegisters.ESP, 4);
            XS.Pop(XSRegisters.EAX);

            XS.Push(XSRegisters.EAX, displacement: 8);
        }
Exemple #27
0
        public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
        {
            OpMethod xMethod = (OpMethod)aOpCode;
            string xCurrentLabel = GetLabel(aMethod, aOpCode);
            var xType = xMethod.Value.DeclaringType;

            Assemble(Assembler, aMethod, xMethod, xCurrentLabel, xType, xMethod.Value);
        }
Exemple #28
0
        public override void Execute( MethodInfo aMethod, ILOpCode aOpCode )
        {
			// TODO overflow check for float
            var xType = aOpCode.StackPopTypes[0];
            var xSize = SizeOfType(xType);
            var xIsFloat = TypeIsFloat(xType);
            if (xSize > 8)
            {
                //EmitNotImplementedException( Assembler, aServiceProvider, "Size '" + xSize.Size + "' not supported (add)", aCurrentLabel, aCurrentMethodInfo, aCurrentOffset, aNextLabel );
                throw new NotImplementedException("Cosmos.IL2CPU.x86->IL->Add_Ovf.cs->Error: StackSize > 8 not supported");
            }
            else
            {
				var xBaseLabel = GetLabel(aMethod, aOpCode) + ".";
				var xSuccessLabel = xBaseLabel + "Success";
                if (xSize > 4)
                {
                    if (xIsFloat)
                    {
						//TODO overflow check
                        new CPUx86.x87.FloatLoad { DestinationReg=Registers.ESP,Size=64, DestinationIsIndirect=true };
                        new CPUx86.Add { SourceValue = 8, DestinationReg = Registers.ESP };
                        new CPUx86.x87.FloatAdd { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect=true, Size=64 };
                        new CPUx86.x87.FloatStoreAndPop { DestinationReg = Registers.ESP, Size = 64, DestinationIsIndirect = true };
                    }
                    else
                    {
                        new CPUx86.Pop { DestinationReg = CPUx86.Registers.EDX }; // low part
                        new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX }; // high part
                        new CPUx86.Add { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.EDX };
						new CPUx86.AddWithCarry { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, DestinationDisplacement = 4, SourceReg = CPUx86.Registers.EAX };
                    }
                }
                else
                {
                    if (xIsFloat) //float
                    {
						//TODO overflow check
                        new CPUx86.SSE.MoveSS { DestinationReg = CPUx86.Registers.XMM0, SourceReg = CPUx86.Registers.ESP, SourceIsIndirect = true };
                        new CPUx86.Add { DestinationReg = CPUx86.Registers.ESP, SourceValue = 4 };
                        new CPUx86.SSE.MoveSS { DestinationReg = CPUx86.Registers.XMM1, SourceReg = CPUx86.Registers.ESP, SourceIsIndirect = true };
                        new CPUx86.SSE.AddSS { DestinationReg = CPUx86.Registers.XMM1, SourceReg = CPUx86.Registers.XMM0 };
                        new CPUx86.SSE.MoveSS { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.XMM1 };
                    }
                    else //integer
                    {
                        new CPUx86.Pop { DestinationReg = CPUx86.Registers.EAX };
                        new CPUx86.Add { DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.EAX };
                    }
                }
				if (false == xIsFloat)
				{
					new CPUx86.ConditionalJump { Condition = ConditionalTestEnum.NoOverflow, DestinationLabel = xSuccessLabel };
					ThrowOverflowException();
				}
				new Label(xSuccessLabel);
            }
        }
Exemple #29
0
    public static void Assemble(Assembler.Assembler aAssembler, uint aElementSize, MethodInfo aMethod, ILOpCode aOpCode, bool debugEnabled)
    {
      // stack     == the new value
      // stack + 1 == the index
      // stack + 2 == the array
      DoNullReferenceCheck(aAssembler, debugEnabled, (int)(8 + Align(aElementSize, 4)));

      uint xStackSize = aElementSize;
      if (xStackSize % 4 != 0)
      {
        xStackSize += 4 - xStackSize % 4;
      }

      // calculate element offset into array memory (including header)
      XS.Set(XSRegisters.EAX, XSRegisters.ESP, sourceDisplacement: (int)xStackSize); // the index
      XS.Set(XSRegisters.EDX, aElementSize);
      XS.Multiply(XSRegisters.EDX);
      XS.Add(XSRegisters.EAX, ObjectImpl.FieldDataOffset + 4);

      XS.Set(XSRegisters.EDX, XSRegisters.ESP, sourceDisplacement: (int)xStackSize + 8); // the array
      XS.Add(XSRegisters.EDX, XSRegisters.EAX);
      XS.Push(XSRegisters.EDX);

      XS.Pop(XSRegisters.ECX);
      for (int i = (int)(aElementSize / 4) - 1; i >= 0; i -= 1)
      {
        new Comment(aAssembler, "Start 1 dword");
        XS.Pop(XSRegisters.EBX);
        XS.Set(XSRegisters.ECX, XSRegisters.EBX, destinationIsIndirect: true);
        XS.Add(XSRegisters.ECX, 4);
      }
      switch (aElementSize % 4)
      {
        case 1:
          {
            new Comment(aAssembler, "Start 1 byte");
            XS.Pop(XSRegisters.EBX);
            XS.Set(XSRegisters.ECX, XSRegisters.BL, destinationIsIndirect: true);
            break;
          }
        case 2:
          {
            new Comment(aAssembler, "Start 1 word");
            XS.Pop(XSRegisters.EBX);
            XS.Set(XSRegisters.ECX, XSRegisters.BX, destinationIsIndirect: true);
            break;
          }
        case 0:
          {
            break;
          }
        default:
          throw new Exception("Remainder size " + (aElementSize % 4) + " not supported!");

      }
      XS.Add(XSRegisters.ESP, 12);
    }
        public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
        {
#warning TODO: This needs to either be implemented, or needs to throw a NotImplementedException!
            // todo: Implement correct Constrained support
            //throw new NotImplementedException("Constrained used in '" + aMethod.MethodBase.GetFullName() + "'");

            var xOpType = aOpCode as OpType;
            DoExecute(Assembler, aMethod, aOpCode, xOpType, DebugEnabled);
        }
Exemple #31
0
        public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
        {
            var xValue        = aOpCode.StackPopTypes[0];
            var xValueIsFloat = TypeIsFloat(xValue);
            var xValueSize    = SizeOfType(xValue);

            if (!xValueIsFloat)
            {
                switch (xValueSize)
                {
                case 1:
                case 2:
                case 4:
                    /*
                     * Code generated by C# / Visual Studio 2015
                     * mov         eax,dword ptr [anInt]
                     * mov         dword ptr [ebp-0E0h],eax
                     * cvtsi2sd    xmm0,dword ptr [ebp-0E0h]
                     * mov         ecx,dword ptr [ebp-0E0h]
                     * shr         ecx,1Fh
                     * addsd       xmm0,mmword ptr __xmm@41f00000000000000000000000000000 (01176B40h)[ecx*8]
                     * movsd       mmword ptr [aDouble],xmm0 # This for now means to copy our converted double to ESP
                     */
                    string BaseLabel           = GetLabel(aMethod, aOpCode) + ".";
                    string LabelSign_Bit_Unset = BaseLabel + "LabelSign_Bit_Unset";

                    XS.Set(EAX, ESP, sourceIsIndirect: true);
                    XS.Set(EBP, EAX, destinationDisplacement: -0xE0, destinationIsIndirect: true);
                    XS.SSE2.ConvertSI2SD(XMM0, EBP, sourceDisplacement: -0xE0, sourceIsIndirect: true);
                    XS.Set(ECX, EBP, sourceDisplacement: -0xE0, sourceIsIndirect: true);
                    // OK now we put in ECX the last bit of our unsigned value,  we call it "SIGN_BIT" but is a little improper...
                    XS.ShiftRight(ECX, 31);

                    /*
                     * if the 'SIGN_BIT' is 0 it means that our uint could have been placed in a normal int so ConvertSI2SD did already
                     * the right thing: we have finished
                     * if the value is 1 we need to do that addition with that weird constant to obtain the real value as double
                     */
                    XS.Compare(ECX, 0x00);
                    XS.Jump(ConditionalTestEnum.Equal, LabelSign_Bit_Unset);
                    XS.LiteralCode(@"addsd xmm0, [__uint2double_const]");
                    XS.Label(LabelSign_Bit_Unset);
                    // We have converted our value to double put it on ESP
                    // expand stack, that moved data is valid stack
                    XS.Sub(ESP, 4);
                    XS.SSE2.MoveSD(ESP, XMM0, destinationIsIndirect: true);
                    break;

                case 8:
                    BaseLabel           = GetLabel(aMethod, aOpCode) + ".";
                    LabelSign_Bit_Unset = BaseLabel + "LabelSign_Bit_Unset";

                    /*
                     * mov EAX, ESP + 4
                     * fild  qword ptr [esp]
                     * shr EAX, 31
                     * cmp ESP, 0
                     * jpe LabelSign_Bit_Unset
                     * LabelSign_Bit_Unset:
                     * fadd  dword ptr __ulong2double_const2
                     * fstp ESP
                     */
                    // Save the high part of the ulong in EAX (we cannot move all of ESP as it has 64 bit size)
                    XS.Set(EAX, ESP, sourceIsIndirect: true, sourceDisplacement: 4);
                    XS.FPU.IntLoad(ESP, isIndirect: true, size: RegisterSize.Long64);
                    XS.Test(EAX, EAX);
                    XS.Jump(ConditionalTestEnum.NotSign, LabelSign_Bit_Unset);
                    // If the sign is set we remove it using the constant __ulong2double_const4
                    XS.LiteralCode(@"fadd dword [__ulong2double_const]");
                    XS.Label(LabelSign_Bit_Unset);
                    // Convert the value to double and move it into the stack
                    XS.FPU.FloatStoreAndPop(ESP, isIndirect: true, size: RegisterSize.Long64);
                    break;

                default:
                    //EmitNotImplementedException( Assembler, GetServiceProvider(), "Conv_I: SourceSize " + xSource + " not supported!", mCurLabel, mMethodInformation, mCurOffset, mNextLabel );
                    throw new NotImplementedException("Conv_R_Un with type " + xValue + " not supported!");
                }
            }
            else
            {
                throw new NotImplementedException("Conv_R_Un with type " + xValue + " not supported!");
            }
        }
Exemple #32
0
 internal BranchInfo(int ilOffset, LabelHandle label, ILOpCode opCode)
 {
     ILOffset = ilOffset;
     Label    = label;
     _opCode  = (byte)opCode;
 }
Exemple #33
0
 public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
 {
     Assemble(Assembler, 8, aMethod, aOpCode, DebugEnabled);
 }
Exemple #34
0
        public static void Assemble(Assembler aAssembler, uint aElementSize, _MethodInfo aMethod, ILOpCode aOpCode, bool debugEnabled)
        {
            // stack     == the new value
            // stack + 1 == the index
            // stack + 2 == the array
            DoNullReferenceCheck(aAssembler, debugEnabled, (int)(8 + Align(aElementSize, 4)));

            uint xStackSize = aElementSize;

            if (xStackSize % 4 != 0)
            {
                xStackSize += 4 - xStackSize % 4;
            }
            // Do index out of range check
            var xBaseLabel = GetLabel(aMethod, aOpCode);
            var xNoIndexOutOfRangeExeptionLabel = xBaseLabel + "_NoIndexOutOfRangeException";
            var xIndexOutOfRangeExeptionLabel   = xBaseLabel + "_IndexOutOfRangeException";

            if (xStackSize == 4)
            {
                XS.Pop(ECX); //get value _, array, 0, index, value -> _, array, 0, index
            }
            else if (xStackSize == 8)
            {
                XS.Pop(ECX); //get value _, array, 0, index, value0, value1 -> _, array, 0, index, value0
                XS.Pop(EDX); //get value _, array, 0, index, value0 -> _, array, 0, index
            }
            else
            {
                throw new NotImplementedException();
            }
            XS.Pop(EBX);                                     //get Position _, array, 0, index -> _, array, 0
            XS.Push(ESP, true, 4);                           // _, array, 0 => _, array, 0, array
            XS.Push(ESP, true, 12);                          // _, array, 0, array => _, array, 0, array, 0
            Ldlen.Assemble(aAssembler, debugEnabled, false); // _, array, 0, array, 0 -> _, array, 0, length
            XS.Pop(EAX);                                     //Length of array _, array, 0, length -> _, array, 0
            XS.Compare(EAX, EBX);
            XS.Jump(CPUx86.ConditionalTestEnum.LessThanOrEqualTo, xIndexOutOfRangeExeptionLabel);

            XS.Compare(EBX, 0);
            XS.Jump(CPUx86.ConditionalTestEnum.GreaterThanOrEqualTo, xNoIndexOutOfRangeExeptionLabel);

            XS.Label(xIndexOutOfRangeExeptionLabel);
            XS.Pop(EAX);
            XS.Pop(EAX);
            Call.DoExecute(aAssembler, aMethod, ExceptionHelperRefs.ThrowIndexOutOfRangeException, aOpCode, xNoIndexOutOfRangeExeptionLabel, debugEnabled);

            XS.Label(xNoIndexOutOfRangeExeptionLabel);
            XS.Push(EBX); //_, array, 0 -> _, array, 0, index
            if (xStackSize == 4)
            {
                XS.Push(ECX); //_, array, 0 -> _, array, 0, index, value
            }
            else if (xStackSize == 8)
            {
                XS.Push(EDX); //_, array, 0, index -> _, array, 0, index, value0
                XS.Push(ECX); //_, array, 0, index, value0 -> _, array, 0, index, value0, value1
            }

            // calculate element offset into array memory (including header)
            XS.Set(EAX, ESP, sourceDisplacement: (int)xStackSize); // the index
            XS.Set(EDX, aElementSize);
            XS.Multiply(EDX);
            XS.Add(EAX, ObjectUtils.FieldDataOffset + 4);

            XS.Set(EDX, ESP, sourceDisplacement: (int)xStackSize + 8); // the array
            XS.Add(EDX, EAX);
            XS.Push(EDX);

            XS.Pop(ECX);
            for (int i = (int)(aElementSize / 4) - 1; i >= 0; i -= 1)
            {
                new Comment(aAssembler, "Start 1 dword");
                XS.Pop(EBX);
                XS.Set(ECX, EBX, destinationIsIndirect: true);
                XS.Add(ECX, 4);
            }
            switch (aElementSize % 4)
            {
            case 1:
            {
                new Comment(aAssembler, "Start 1 byte");
                XS.Pop(EBX);
                XS.Set(ECX, BL, destinationIsIndirect: true);
                break;
            }

            case 2:
            {
                new Comment(aAssembler, "Start 1 word");
                XS.Pop(EBX);
                XS.Set(ECX, BX, destinationIsIndirect: true);
                break;
            }

            case 0:
            {
                break;
            }

            default:
                throw new Exception("Remainder size " + (aElementSize % 4) + " not supported!");
            }
            XS.Add(ESP, 12);
        }
Exemple #35
0
        public override void Execute(MethodInfo aMethod, ILOpCode aOpCode)
        {
            var xOpCode = (ILOpCodes.OpField)aOpCode;

            DoExecute(Assembler, xOpCode.Value.DeclaringType, xOpCode.Value.GetFullName(), true, DebugEnabled, aOpCode.StackPopTypes[0]);
        }
Exemple #36
0
        public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
        {
            var xOpMethod = aOpCode as OpMethod;

            DoExecute(Assembler, aMethod, xOpMethod.Value, xOpMethod.ValueUID, aOpCode, DebugEnabled);
        }
Exemple #37
0
 public void SetBranch(object newLabel, ILOpCode branchCode, ILOpCode revBranchCode)
 {
     this.SetBranch(newLabel, branchCode);
     this.RevBranchCode = revBranchCode;
 }
Exemple #38
0
        public override void Execute(ILOpCode instr, MethodBase aMethod)
        {
            //This is branch type IL
            var xOffset     = ((OpBranch)instr).Value;
            var xSize       = Core.vStack.Pop().Size;
            var xTrueLabel  = ILHelper.GetLabel(aMethod, xOffset);
            var xFalseLabel = ILHelper.GetLabel(aMethod, instr.Position) + "._bne_un_false";

            //Make a pop because exactly we are popping up two items
            Core.vStack.Pop();

            /*
             *  value1 is pushed onto the stack.
             *  value2 is pushed onto the stack.
             *  value2 and value1 are popped from the stack;
             *  if value1 is not equal to value2, the branch operation is performed. --> value1 ≠ value2
             */

            switch (ILCompiler.CPUArchitecture)
            {
                #region _x86_
            case CPUArch.x86:
            {
                if (xSize <= 4)
                {
                    //***What we are going to do is***
                    //1) Pop Value 2 into EAX
                    //2) Pop Value 1 into EBX
                    //3) Compare EAX and EBX, Jump to Branch when the result is not zero
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EAX
                        });                                                                    //Value 2
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EBX
                        });                                                                    //Value 1
                    Core.AssemblerCode.Add(new Cmp {
                            DestinationReg = Registers.EAX, SourceReg = Registers.EBX
                        });
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JNE, DestinationRef = xTrueLabel
                        });
                }
                else if (xSize <= 8)
                {
                    //***What we are going to do is***
                    //1) Pop Value 2 low into EAX and high into EBX
                    //2) Pop Value 1 low into ECX and high into EDX
                    //3) Compare low values and check if zero than continue else if not than jump to Not Equal
                    //4) Compare high values and check if zero than jump to Branch else continue

                    //Value 2 EBX:EAX
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EAX
                        });                                                                    //low
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EBX
                        });                                                                    //high

                    //Value 1 EDX:ECX
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.ECX
                        });                                                                    //low
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EDX
                        });                                                                    //high

                    Core.AssemblerCode.Add(new Cmp {
                            DestinationReg = Registers.EAX, SourceReg = Registers.ECX
                        });
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JNE, DestinationRef = xTrueLabel
                        });
                    Core.AssemblerCode.Add(new Cmp {
                            DestinationReg = Registers.EBX, SourceReg = Registers.EDX
                        });
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JNE, DestinationRef = xTrueLabel
                        });

                    Core.AssemblerCode.Add(new Label(xFalseLabel));
                }
                else
                {
                    //Not called usually
                    throw new Exception("@Bne_Un: Branch operation bne_un for size > 8 is not yet implemented");
                }
            }
            break;

                #endregion
                #region _x64_
            case CPUArch.x64:
            {
            }
            break;

                #endregion
                #region _ARM_
            case CPUArch.ARM:
            {
            }
            break;
                #endregion
            }
        }
Exemple #39
0
 public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
 {
     throw new NotImplementedException();
 }
Exemple #40
0
        public static void DoExecute(Assembler Assembler, _MethodInfo aMethod, MethodBase aTargetMethod, uint aTargetMethodUID, ILOpCode aOp, bool debugEnabled)
        {
            string xCurrentMethodLabel = GetLabel(aMethod, aOp.Position);
            Type   xPopType            = aOp.StackPopTypes.Last();

            string xNormalAddress = "";

            if (aTargetMethod.IsStatic || !aTargetMethod.IsVirtual || aTargetMethod.IsFinal)
            {
                xNormalAddress = LabelName.Get(aTargetMethod);
            }

            uint xReturnSize = 0;
            var  xMethodInfo = aTargetMethod as MethodInfo;

            if (xMethodInfo != null)
            {
                xReturnSize = Align(SizeOfType(xMethodInfo.ReturnType), 4);
            }

            var  xExtraStackSize = Call.GetStackSizeToReservate(aTargetMethod, xPopType);
            uint xThisOffset     = 0;
            var  xParameters     = aTargetMethod.GetParameters();

            foreach (var xItem in xParameters)
            {
                xThisOffset += Align(SizeOfType(xItem.ParameterType), 4);
            }

            // This is finding offset to self? It looks like we dont need offsets of other
            // arguments, but only self. If so can calculate without calculating all fields
            // Might have to go to old data structure for the offset...
            // Can we add this method info somehow to the data passed in?
            // mThisOffset = mTargetMethodInfo.Arguments[0].Offset;

            XS.Comment("ThisOffset = " + xThisOffset);

            if (IsReferenceType(xPopType))
            {
                DoNullReferenceCheck(Assembler, debugEnabled, (int)xThisOffset + 4);
            }
            else
            {
                DoNullReferenceCheck(Assembler, debugEnabled, (int)xThisOffset);
            }

            if (!String.IsNullOrEmpty(xNormalAddress))
            {
                if (xExtraStackSize > 0)
                {
                    XS.Sub(ESP, xExtraStackSize);
                }

                XS.Call(xNormalAddress);
            }
            else
            {
                /*
                 * On the stack now:
                 * $esp                 Params
                 * $esp + mThisOffset   This
                 */
                if ((xPopType.IsPointer) || (xPopType.IsByRef))
                {
                    xPopType = xPopType.GetElementType();
                    string xTypeId = GetTypeIDLabel(xPopType);
                    XS.Push(xTypeId, isIndirect: true);
                }
                else
                {
                    XS.Set(EAX, ESP, sourceDisplacement: (int)xThisOffset + 4);
                    XS.Push(EAX, isIndirect: true);
                }
                XS.Push(aTargetMethodUID);
                XS.Call(LabelName.Get(VTablesImplRefs.GetMethodAddressForTypeRef));

                if (xExtraStackSize > 0)
                {
                    xThisOffset -= xExtraStackSize;
                }

                /*
                 * On the stack now:
                 * $esp                 Params
                 * $esp + mThisOffset   This
                 */
                XS.Pop(ECX);

                XS.Label(xCurrentMethodLabel + ".AfterAddressCheck");

                if (IsReferenceType(xPopType))
                {
                    /*
                     * On the stack now:
                     * $esp + 0              Params
                     * $esp + mThisOffset    This
                     */
                    // we need to see if $this is a boxed object, and if so, we need to unbox it
                    XS.Set(EAX, ESP, sourceDisplacement: (int)xThisOffset + 4);
                    XS.Compare(EAX, (int)ObjectUtils.InstanceTypeEnum.BoxedValueType, destinationIsIndirect: true, destinationDisplacement: 4, size: RegisterSize.Int32);

                    /*
                     * On the stack now:
                     * $esp                 Params
                     * $esp + mThisOffset   This
                     *
                     * ECX contains the method to call
                     * EAX contains the type pointer (not the handle!!)
                     */
                    XS.Jump(CPU.ConditionalTestEnum.NotEqual, xCurrentMethodLabel + ".NotBoxedThis");

                    /*
                     * On the stack now:
                     * $esp                 Params
                     * $esp + mThisOffset   This
                     *
                     * ECX contains the method to call
                     * EAX contains the type pointer (not the handle!!)
                     */
                    XS.Add(EAX, ObjectUtils.FieldDataOffset);
                    XS.Set(ESP, EAX, destinationDisplacement: (int)xThisOffset + 4);

                    var xHasParams           = xThisOffset != 0;
                    var xNeedsExtraStackSize = xReturnSize >= xThisOffset + 8;

                    if (xHasParams ||
                        !xNeedsExtraStackSize)
                    {
                        XS.Add(ESP, xThisOffset + 4);
                    }

                    for (int i = 0; i < xThisOffset / 4; i++)
                    {
                        XS.Push(ESP, displacement: -4);
                    }

                    if (xHasParams &&
                        xNeedsExtraStackSize)
                    {
                        XS.Sub(ESP, 4);
                    }

                    /*
                     * On the stack now:
                     * $esp                 Params
                     * $esp + mThisOffset   Pointer to address inside box
                     *
                     * ECX contains the method to call
                     */
                }

                XS.Label(xCurrentMethodLabel + ".NotBoxedThis");

                if (xExtraStackSize > 0)
                {
                    XS.Sub(ESP, xExtraStackSize);
                }

                XS.Call(ECX);
                XS.Label(xCurrentMethodLabel + ".AfterNotBoxedThis");
            }
            EmitExceptionLogic(Assembler, aMethod, aOp, true,
                               delegate
            {
                var xStackOffsetBefore = aOp.StackOffsetBeforeExecution.Value;

                uint xPopSize = 0;
                foreach (var type in aOp.StackPopTypes)
                {
                    xPopSize += Align(SizeOfType(type), 4);
                }

                var xResultSize = xReturnSize;
                if (xResultSize % 4 != 0)
                {
                    xResultSize += 4 - (xResultSize % 4);
                }

                EmitExceptionCleanupAfterCall(Assembler, xResultSize, xStackOffsetBefore, xPopSize);
            });
            XS.Label(xCurrentMethodLabel + ".NoExceptionAfterCall");
            XS.Comment("Argument Count = " + xParameters.Length);
        }
Exemple #41
0
        public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
        {
            var       xType            = aMethod.MethodBase.DeclaringType;
            var       xOpCode          = (ILOpCodes.OpField)aOpCode;
            FieldInfo xField           = xOpCode.Value;
            var       xIsReferenceType = TypeIsReferenceType(xField.FieldType);

            // call cctor:
            var xCctor = (xField.DeclaringType.GetConstructors(BindingFlags.Static | BindingFlags.NonPublic)).SingleOrDefault();

            if (xCctor != null)
            {
                XS.Call(LabelName.Get(xCctor));
                ILOp.EmitExceptionLogic(Assembler, aMethod, aOpCode, true, null, ".AfterCCTorExceptionCheck");
                XS.Label(".AfterCCTorExceptionCheck");
            }

            //int aExtraOffset;// = 0;
            //bool xNeedsGC = xField.FieldType.IsClass && !xField.FieldType.IsValueType;
            uint xSize = SizeOfType(xField.FieldType);

            //if( xNeedsGC )
            //{
            //    aExtraOffset = 12;
            //}
            new Comment(Assembler, "Type = '" + xField.FieldType.FullName /*+ "', NeedsGC = " + xNeedsGC*/);

            uint xOffset = 0;

            var xFields = xField.DeclaringType.GetFields();

            foreach (FieldInfo xInfo in xFields)
            {
                if (xInfo == xField)
                {
                    break;
                }

                xOffset += SizeOfType(xInfo.FieldType);
            }
            string xDataName = DataMember.GetStaticFieldName(xField);

            if (xIsReferenceType)
            {
                XS.Add(XSRegisters.ESP, 4);
                XS.Pop(XSRegisters.EAX);
                XS.Set(ElementReference.New(xDataName).Name, XSRegisters.EAX, destinationIsIndirect: true, destinationDisplacement: 4);
                return;
            }
            for (int i = 0; i < (xSize / 4); i++)
            {
                XS.Pop(XSRegisters.EAX);
                new CPUx86.Mov {
                    DestinationRef = ElementReference.New(xDataName, i * 4), DestinationIsIndirect = true, SourceReg = CPUx86.RegistersEnum.EAX
                };
            }
            switch (xSize % 4)
            {
            case 1:
            {
                XS.Pop(XSRegisters.EAX);
                new CPUx86.Mov {
                    DestinationRef = ElementReference.New(xDataName, (int)((xSize / 4) * 4)), DestinationIsIndirect = true, SourceReg = CPUx86.RegistersEnum.AL
                };
                break;
            }

            case 2:
            {
                XS.Pop(XSRegisters.EAX);
                new CPUx86.Mov {
                    DestinationRef = Cosmos.Assembler.ElementReference.New(xDataName, (int)((xSize / 4) * 4)), DestinationIsIndirect = true, SourceReg = CPUx86.RegistersEnum.AX
                };
                break;
            }

            case 0:
            {
                break;
            }

            default:
                //EmitNotImplementedException(Assembler, GetServiceProvider(), "Ldsfld: Remainder size " + (xSize % 4) + " not supported!", mCurLabel, mMethodInformation, mCurOffset, mNextLabel);
                throw new NotImplementedException();
                //break;
            }
        }
Exemple #42
0
 public override void Execute(ILOpCode instr, MethodBase aMethod)
 {
     //Do Nothing
     //COMPILER HACK ^^
 }
Exemple #43
0
        public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
        {
            var xIsSingleCompare = true;

            switch (aOpCode.OpCode)
            {
            case ILOpCode.Code.Beq:
            case ILOpCode.Code.Bge:
            case ILOpCode.Code.Bgt:
            case ILOpCode.Code.Bge_Un:
            case ILOpCode.Code.Bgt_Un:
            case ILOpCode.Code.Ble:
            case ILOpCode.Code.Ble_Un:
            case ILOpCode.Code.Bne_Un:
            case ILOpCode.Code.Blt:
            case ILOpCode.Code.Blt_Un:
                xIsSingleCompare = false;
                break;
            }

            var xStackContent     = aOpCode.StackPopTypes[0];
            var xStackContentSize = SizeOfType(xStackContent);

            if (xStackContentSize > 8)
            {
                throw new Exception("Cosmos.IL2CPU.x86->IL->Branch.cs->Error: StackSize > 8 not supported");
            }

            CPU.ConditionalTestEnum xTestOp;
            // all conditions are inverted here?
            switch (aOpCode.OpCode)
            {
            case ILOpCode.Code.Beq:
                xTestOp = CPU.ConditionalTestEnum.Zero;
                break;

            case ILOpCode.Code.Bge:
                xTestOp = CPU.ConditionalTestEnum.GreaterThanOrEqualTo;
                break;

            case ILOpCode.Code.Bgt:
                xTestOp = CPU.ConditionalTestEnum.GreaterThan;
                break;

            case ILOpCode.Code.Ble:
                xTestOp = CPU.ConditionalTestEnum.LessThanOrEqualTo;
                break;

            case ILOpCode.Code.Blt:
                xTestOp = CPU.ConditionalTestEnum.LessThan;
                break;

            case ILOpCode.Code.Bne_Un:
                xTestOp = CPU.ConditionalTestEnum.NotEqual;
                break;

            case ILOpCode.Code.Bge_Un:
                xTestOp = CPU.ConditionalTestEnum.AboveOrEqual;
                break;

            case ILOpCode.Code.Bgt_Un:
                xTestOp = CPU.ConditionalTestEnum.Above;
                break;

            case ILOpCode.Code.Ble_Un:
                xTestOp = CPU.ConditionalTestEnum.BelowOrEqual;
                break;

            case ILOpCode.Code.Blt_Un:
                xTestOp = CPU.ConditionalTestEnum.Below;
                break;

            case ILOpCode.Code.Brfalse:
                xTestOp = CPU.ConditionalTestEnum.Zero;
                break;

            case ILOpCode.Code.Brtrue:
                xTestOp = CPU.ConditionalTestEnum.NotZero;
                break;

            default:
                throw new Exception("Cosmos.IL2CPU.x86->IL->Branch.cs->Error: Unknown OpCode for conditional branch.");
            }
            if (!xIsSingleCompare)
            {
                if (xStackContentSize <= 4)
                {
                    //if (xStackContent.IsFloat)
                    //{
                    //    throw new Exception("Cosmos.IL2CPU.x86->IL->Branch.cs->Error: Comparison of floats (System.Single) is not yet supported!");
                    //}
                    //else
                    //{
                    XS.Pop(XSRegisters.EAX);
                    XS.Pop(XSRegisters.EBX);
                    XS.Compare(XSRegisters.EBX, XSRegisters.EAX);
                    new ConditionalJump {
                        Condition = xTestOp, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                    };
                    //}
                }
                else
                {
                    //if (xStackContent.IsFloat)
                    //{
                    //    throw new Exception("Cosmos.IL2CPU.x86->IL->Branch.cs->Error: Comparison of doubles (System.Double) is not yet supported!");
                    //}
                    //else
                    //{
                    var xNoJump = GetLabel(aMethod, aOpCode) + "__NoBranch";

                    // value 2  EBX:EAX
                    XS.Pop(XSRegisters.EAX);
                    XS.Pop(XSRegisters.EBX);
                    // value 1  EDX:ECX
                    XS.Pop(XSRegisters.ECX);
                    XS.Pop(XSRegisters.EDX);
                    switch (xTestOp)
                    {
                    case ConditionalTestEnum.Zero:     // Equal
                    case ConditionalTestEnum.NotEqual: // NotZero
                        XS.Xor(XSRegisters.EAX, XSRegisters.ECX);
                        new ConditionalJump {
                            Condition = xTestOp, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Xor(XSRegisters.EBX, XSRegisters.EDX);
                        new ConditionalJump {
                            Condition = xTestOp, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        break;

                    case ConditionalTestEnum.GreaterThanOrEqualTo:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        XS.Jump(ConditionalTestEnum.LessThan, xNoJump);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.GreaterThan, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        XS.Jump(ConditionalTestEnum.Below, xNoJump);
                        break;

                    case ConditionalTestEnum.GreaterThan:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        XS.Jump(ConditionalTestEnum.LessThan, xNoJump);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.GreaterThan, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        XS.Jump(ConditionalTestEnum.BelowOrEqual, xNoJump);
                        break;

                    case ConditionalTestEnum.LessThanOrEqualTo:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.LessThan, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Jump(ConditionalTestEnum.GreaterThan, xNoJump);
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.BelowOrEqual, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        break;

                    case ConditionalTestEnum.LessThan:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.LessThan, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Jump(ConditionalTestEnum.GreaterThan, xNoJump);
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Below, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        break;

                    // from here all unsigned
                    case ConditionalTestEnum.AboveOrEqual:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Above, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        XS.Jump(ConditionalTestEnum.Below, xNoJump);
                        break;

                    case ConditionalTestEnum.Above:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Above, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        XS.Jump(ConditionalTestEnum.BelowOrEqual, xNoJump);
                        break;

                    case ConditionalTestEnum.BelowOrEqual:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Above, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Jump(ConditionalTestEnum.Below, xNoJump);
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Above, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        break;

                    case ConditionalTestEnum.Below:
                        XS.Compare(XSRegisters.EDX, XSRegisters.EBX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Above, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        XS.Jump(ConditionalTestEnum.Below, xNoJump);
                        XS.Compare(XSRegisters.ECX, XSRegisters.EAX);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.AboveOrEqual, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                        break;

                    default:
                        throw new Exception("Unknown OpCode for conditional branch in 64-bit.");
                    }
                    XS.Label(xNoJump);
                    //}
                }
            }
            else
            {
                //if (xStackContent.IsFloat)
                //{
                //    throw new Exception("Cosmos.IL2CPU.x86->IL->Branch.cs->Error: Simple comparison of floating point numbers is not yet supported!");
                //}
                //else
                //{
                // todo: improve code clarity
                if (xStackContentSize <= 4)
                {
                    XS.Pop(XSRegisters.EAX);
                    if (xTestOp == ConditionalTestEnum.Zero)
                    {
                        XS.Compare(XSRegisters.EAX, 0);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.Equal, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                    }
                    else if (xTestOp == ConditionalTestEnum.NotZero)
                    {
                        XS.Compare(XSRegisters.EAX, 0);
                        new ConditionalJump {
                            Condition = ConditionalTestEnum.NotEqual, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                        };
                    }
                    else
                    {
                        throw new NotSupportedException("Cosmos.IL2CPU.x86->IL->Branch.cs->Error: Situation not supported yet! (In the Simple Comparison)");
                    }
                }
                else
                {
                    if (IsReferenceType(xStackContent))
                    {
                        XS.Add(XSRegisters.ESP, 4);
                        XS.Pop(XSRegisters.EAX);
                    }
                    else
                    {
                        XS.Pop(XSRegisters.EAX);
                        XS.Pop(XSRegisters.EBX);
                    }

                    switch (xTestOp)
                    {
                    case ConditionalTestEnum.Zero:    // Equal
                    case ConditionalTestEnum.NotZero: // NotEqual
                        if (IsReferenceType(xStackContent))
                        {
                            XS.Xor(XSRegisters.EAX, 0);
                            new ConditionalJump {
                                Condition = xTestOp, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                            };
                        }
                        else
                        {
                            XS.Xor(XSRegisters.EAX, 0);
                            new ConditionalJump {
                                Condition = xTestOp, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                            };
                            XS.Xor(XSRegisters.EBX, 0);
                            new ConditionalJump {
                                Condition = xTestOp, DestinationLabel = AppAssembler.TmpBranchLabel(aMethod, aOpCode)
                            };
                        }
                        break;

                    default:
                        throw new NotImplementedException("Cosmos.IL2CPU.X86.IL.Branch: Simple branch " + aOpCode.OpCode + " not implemented for operand ");
                    }
                }
            }
            //}
        }
Exemple #44
0
 public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
 {
     Ldelem_Ref.Assemble(Assembler, 1, true, aMethod, aOpCode, DebugEnabled);
 }
Exemple #45
0
        public override void Execute(ILOpCode instr, MethodBase aMethod)
        {
            //This is branch type IL
            var xOffset     = ((OpBranch)instr).Value;
            var xSize       = Core.vStack.Pop().Size;
            var xTrueLabel  = ILHelper.GetLabel(aMethod, xOffset);
            var xFalseLabel = ILHelper.GetLabel(aMethod, instr.Position) + "._bge_false";

            //Make a pop because exactly we are popping up two items
            Core.vStack.Pop();

            /*
             *  value1 is pushed onto the stack.
             *  value2 is pushed onto the stack.
             *  value2 and value1 are popped from the stack;
             *  if value1 is greater than or equal to value2, the branch operation is performed. --> value1 ≥ value2
             */

            switch (ILCompiler.CPUArchitecture)
            {
                #region _x86_
            case CPUArch.x86:
            {
                if (xSize <= 4)
                {
                    //***What we are going to do is***
                    //1) Pop Value 2 into EAX
                    //2) Pop Value 1 into EBX
                    //3) Compare EBX and EAX and jump if greator than equals to
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EAX
                        });                                                                    //value 2
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EBX
                        });                                                                    //value 1
                    Core.AssemblerCode.Add(new Cmp {
                            DestinationReg = Registers.EBX, SourceReg = Registers.EAX
                        });                                                                                               //value1 - value2
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JGE, DestinationRef = xTrueLabel
                        });
                }
                else if (xSize <= 8)
                {
                    //***What we are going to do is***
                    //1) Pop value 2 low into EAX and high into EBX
                    //2) Pop value 1 low into ECX and high into EDX
                    //3) Compare High parts of value 1 and value 2, if less than false  else if greator than jump true
                    //4) Compare Low parts of value 1 and value 2, if greator than jump true else continue

                    //Value 2 EBX:EAX
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EAX
                        });                                                                    //low
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EBX
                        });                                                                    //high

                    //Value 1 EDX:ECX
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.ECX
                        });                                                                    //low
                    Core.AssemblerCode.Add(new Pop {
                            DestinationReg = Registers.EDX
                        });                                                                    //high

                    Core.AssemblerCode.Add(new Cmp {
                            DestinationReg = Registers.EDX, SourceReg = Registers.EBX
                        });                                                                                               //value1_HI - value2_HI
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JL, DestinationRef = xFalseLabel
                        });
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JG, DestinationRef = xTrueLabel
                        });
                    Core.AssemblerCode.Add(new Xor {
                            DestinationReg = Registers.ECX, SourceReg = Registers.EAX
                        });                                                                                               //value1_LO - value2_LO
                    Core.AssemblerCode.Add(new Jmp {
                            Condition = ConditionalJumpEnum.JGE, DestinationRef = xTrueLabel
                        });

                    Core.AssemblerCode.Add(new Label(xFalseLabel));
                }
                else
                {
                    //Not called usually
                    throw new Exception("@Bge: Branch operation bge for size > 8 is not yet implemented");
                }
            }
            break;

                #endregion
                #region _x64_
            case CPUArch.x64:
            {
            }
            break;

                #endregion
                #region _ARM_
            case CPUArch.ARM:
            {
            }
            break;
                #endregion
            }
        }
Exemple #46
0
        public override void Execute(_MethodInfo aMethod, ILOpCode aOpCode)
        {
            var xOpVar = (OpVar)aOpCode;

            DoExecute(Assembler, aMethod, xOpVar.Value);
        }
Exemple #47
0
        public override void Execute(ILOpCode instr, MethodBase aMethod)
        {
            var xSource = Core.vStack.Pop();

            //Convert to int8, pushing int32 on stack.
            //Mean Just Convert Last 1 byte to Int32
            switch (ILCompiler.CPUArchitecture)
            {
                #region _x86_
            case CPUArch.x86:
            {
                switch (xSource.Size)
                {
                case 1:
                case 2:
                case 4:
                {
                    if (xSource.IsFloat)
                    {
                        throw new Exception("Conv_I2 -> Size 4 : Float");
                    }
                    else
                    {
                        //Just Pop into EAX, zero extend and push it.
                        Core.AssemblerCode.Add(new Pop {
                                    DestinationReg = Registers.EAX
                                });
                        Core.AssemblerCode.Add(new Movzx {
                                    DestinationReg = Registers.EAX, SourceReg = Registers.AX, Size = 16
                                });
                        Core.AssemblerCode.Add(new Push {
                                    DestinationReg = Registers.EAX
                                });
                    }
                }
                break;

                case 8:
                {
                    if (xSource.IsFloat)
                    {
                        throw new Exception("Conv_I2 -> Size 8 : Float");
                    }
                    else
                    {
                        //Just Erase The 8 byte as we want only first 4 byte manily 2 byte of it.
                        Core.AssemblerCode.Add(new Pop {
                                    DestinationReg = Registers.EAX
                                });
                        Core.AssemblerCode.Add(new Add {
                                    DestinationReg = Registers.ESP, SourceRef = "0x4"
                                });
                        Core.AssemblerCode.Add(new Movzx {
                                    DestinationReg = Registers.EAX, SourceReg = Registers.AX, Size = 16
                                });
                        Core.AssemblerCode.Add(new Push {
                                    DestinationReg = Registers.EAX
                                });
                    }
                }
                break;

                default:
                    throw new Exception("Not Yet Implemented Conv_I2 : Size" + xSource.Size);
                }
            }
            break;

                #endregion
                #region _x64_
            case CPUArch.x64:
            {
            }
            break;

                #endregion
                #region _ARM_
            case CPUArch.ARM:
            {
            }
            break;
                #endregion
            }

            Core.vStack.Push(4, typeof(short));
        }
Exemple #48
0
        public override void Execute(ILOpCode instr, MethodBase aMethod)
        {
            var xSource = Core.vStack.Pop();

            //Convert to int8, pushing int32 on stack.
            //Mean Just Convert Last 1 byte to Int32
            switch (ILCompiler.CPUArchitecture)
            {
                #region _x86_
            case CPUArch.x86:
            {
                switch (xSource.Size)
                {
                case 1:
                case 2:
                case 4:
                {
                    if (xSource.IsFloat)
                    {
                        throw new Exception("Conv_I4 -> Size 4 : Float");
                    }
                    else
                    {
                        //Not Required because it is already what we want, So Never called
                    }
                }
                break;

                case 8:
                {
                    if (xSource.IsFloat)
                    {
                        throw new Exception("Conv_I4 -> Size 8 : Float");
                    }
                    else
                    {
                        //Just Erase The 8 byte as we want only first 4 byte.
                        Core.AssemblerCode.Add(new Pop {
                                    DestinationReg = Registers.EAX
                                });
                        Core.AssemblerCode.Add(new Add {
                                    DestinationReg = Registers.ESP, SourceRef = "0x4"
                                });
                        Core.AssemblerCode.Add(new Push {
                                    DestinationReg = Registers.EAX
                                });
                    }
                }
                break;

                default:
                    throw new Exception("Not Yet Implemented Conv_I4 : Size" + xSource.Size);
                }
            }
            break;

                #endregion
                #region _x64_
            case CPUArch.x64:
            {
            }
            break;

                #endregion
                #region _ARM_
            case CPUArch.ARM:
            {
            }
            break;
                #endregion
            }

            Core.vStack.Push(4, typeof(Int32));
        }