本文整理汇总了C#中Mono.CSharp.Expression.Emit方法的典型用法代码示例。如果您正苦于以下问题:C# Expression.Emit方法的具体用法?C# Expression.Emit怎么用?C# Expression.Emit使用的例子?那么恭喜您, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类Mono.CSharp.Expression
的用法示例。
在下文中一共展示了Expression.Emit方法的14个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C#代码示例。
示例1: EmitAssign
public void EmitAssign(EmitContext ec, Expression source, bool leave_copy, bool prepare_for_load)
{
prepared = prepare_for_load;
EmitInstance (ec, prepared);
source.Emit (ec);
if (leave_copy) {
ec.Emit (OpCodes.Dup);
if (!IsStatic) {
temp = new LocalTemporary (this.Type);
temp.Store (ec);
}
}
if ((spec.Modifiers & Modifiers.VOLATILE) != 0)
ec.Emit (OpCodes.Volatile);
spec.MemberDefinition.SetIsAssigned ();
if (IsStatic)
ec.Emit (OpCodes.Stsfld, spec);
else
ec.Emit (OpCodes.Stfld, spec);
if (temp != null) {
temp.Emit (ec);
temp.Release (ec);
temp = null;
}
}
示例2: EmitAssign
//
// source is ignored, because we already have a copy of it from the
// LValue resolution and we have already constructed a pre-cached
// version of the arguments (ea.set_arguments);
//
public void EmitAssign (EmitContext ec, Expression source, bool leave_copy, bool prepare_for_load)
{
prepared = prepare_for_load;
Expression value = set_expr;
if (prepared) {
Invocation.EmitCall (ec, is_base_indexer, instance_expr, get,
arguments, loc, true, false);
prepared_value = new LocalTemporary (type);
prepared_value.Store (ec);
source.Emit (ec);
prepared_value.Release (ec);
if (leave_copy) {
ec.ig.Emit (OpCodes.Dup);
temp = new LocalTemporary (Type);
temp.Store (ec);
}
} else if (leave_copy) {
temp = new LocalTemporary (Type);
source.Emit (ec);
temp.Store (ec);
value = temp;
}
if (!prepared)
arguments.Add (new Argument (value));
Invocation.EmitCall (ec, is_base_indexer, instance_expr, set, arguments, loc, false, prepared);
if (temp != null) {
temp.Emit (ec);
temp.Release (ec);
}
}
示例3: EmitAssign
public void EmitAssign (EmitContext ec, Expression source, bool leave_copy, bool prepare_for_load)
{
FieldAttributes fa = FieldInfo.Attributes;
bool is_static = (fa & FieldAttributes.Static) != 0;
bool is_readonly = (fa & FieldAttributes.InitOnly) != 0;
ILGenerator ig = ec.ig;
if (is_readonly && !ec.IsConstructor){
Report_AssignToReadonly (source);
return;
}
prepared = prepare_for_load;
EmitInstance (ec, prepared);
source.Emit (ec);
if (leave_copy) {
ec.ig.Emit (OpCodes.Dup);
if (!FieldInfo.IsStatic) {
temp = new LocalTemporary (this.Type);
temp.Store (ec);
}
}
FieldBase f = TypeManager.GetField (FieldInfo);
if (f != null){
if ((f.ModFlags & Modifiers.VOLATILE) != 0)
ig.Emit (OpCodes.Volatile);
f.SetAssigned ();
}
if (is_static)
ig.Emit (OpCodes.Stsfld, GetConstructedFieldInfo ());
else
ig.Emit (OpCodes.Stfld, GetConstructedFieldInfo ());
if (temp != null) {
temp.Emit (ec);
temp.Release (ec);
temp = null;
}
}
示例4: EmitAssign
public void EmitAssign (EmitContext ec, Expression source)
{
ILGenerator ig = ec.ig;
int arg_idx = idx;
if (!ec.IsStatic)
arg_idx++;
if (is_ref)
EmitLdArg (ig, arg_idx);
source.Emit (ec);
if (is_ref)
StoreFromPtr (ig, type);
else {
if (arg_idx <= 255)
ig.Emit (OpCodes.Starg_S, (byte) arg_idx);
else
ig.Emit (OpCodes.Starg, arg_idx);
}
}
示例5: EmitCallInstance
static TypeSpec EmitCallInstance (EmitContext ec, Expression instance, TypeSpec declaringType, OpCode callOpcode)
{
var instance_type = instance.Type;
//
// Push the instance expression
//
if ((instance_type.IsStructOrEnum && (callOpcode == OpCodes.Callvirt || (callOpcode == OpCodes.Call && declaringType.IsStruct))) ||
instance_type.IsGenericParameter || declaringType.IsNullableType) {
//
// If the expression implements IMemoryLocation, then
// we can optimize and use AddressOf on the
// return.
//
// If not we have to use some temporary storage for
// it.
var iml = instance as IMemoryLocation;
if (iml != null) {
iml.AddressOf (ec, AddressOp.Load);
} else {
LocalTemporary temp = new LocalTemporary (instance_type);
instance.Emit (ec);
temp.Store (ec);
temp.AddressOf (ec, AddressOp.Load);
}
return ReferenceContainer.MakeType (ec.Module, instance_type);
}
if (instance_type.IsStructOrEnum) {
instance.Emit (ec);
ec.Emit (OpCodes.Box, instance_type);
return ec.BuiltinTypes.Object;
}
instance.Emit (ec);
return instance_type;
}
示例6: MarkYield
//
// Called back from Yield
//
public void MarkYield(EmitContext ec, Expression expr, int resume_pc, bool unwind_protect, Label resume_point)
{
// Store the new current
ec.Emit (OpCodes.Ldarg_0);
expr.Emit (ec);
ec.Emit (OpCodes.Stfld, IteratorHost.CurrentField.Spec);
// store resume program-counter
ec.Emit (OpCodes.Ldarg_0);
ec.EmitInt (resume_pc);
ec.Emit (OpCodes.Stfld, IteratorHost.PC.Spec);
// mark finally blocks as disabled
if (unwind_protect && skip_finally != null) {
ec.EmitInt (1);
ec.Emit (OpCodes.Stloc, skip_finally);
}
// Return ok
ec.Emit (unwind_protect ? OpCodes.Leave : OpCodes.Br, move_next_ok);
ec.MarkLabel (resume_point);
}
示例7: MarkYield
//
// Called back from Yield
//
public void MarkYield (EmitContext ec, Expression expr, int resume_pc, bool unwind_protect, Label resume_point)
{
// Store the new current
ec.Emit (OpCodes.Ldarg_0);
expr.Emit (ec);
ec.Emit (OpCodes.Stfld, IteratorHost.CurrentField.Spec);
//
// Guard against being disposed meantime
//
Label disposed = ec.DefineLabel ();
ec.Emit (OpCodes.Ldarg_0);
ec.Emit (OpCodes.Ldfld, IteratorHost.DisposingField.Spec);
ec.Emit (OpCodes.Brtrue_S, disposed);
//
// store resume program-counter
//
ec.Emit (OpCodes.Ldarg_0);
ec.EmitInt (resume_pc);
ec.Emit (OpCodes.Stfld, IteratorHost.PC.Spec);
ec.MarkLabel (disposed);
// mark finally blocks as disabled
if (unwind_protect && skip_finally != null) {
ec.EmitInt (1);
ec.Emit (OpCodes.Stloc, skip_finally);
}
// Return ok
ec.Emit (unwind_protect ? OpCodes.Leave : OpCodes.Br, move_next_ok);
ec.MarkLabel (resume_point);
}
示例8: MarkYield
//
// Called back from Yield
//
public void MarkYield (EmitContext ec, Expression expr, int resume_pc, bool unwind_protect, Label resume_point)
{
ILGenerator ig = ec.ig;
// Store the new current
ig.Emit (OpCodes.Ldarg_0);
expr.Emit (ec);
ig.Emit (OpCodes.Stfld, IteratorHost.CurrentField.FieldBuilder);
// store resume program-counter
ig.Emit (OpCodes.Ldarg_0);
IntConstant.EmitInt (ig, resume_pc);
ig.Emit (OpCodes.Stfld, IteratorHost.PC.FieldBuilder);
// mark finally blocks as disabled
if (unwind_protect && skip_finally != null) {
ig.Emit (OpCodes.Ldc_I4_1);
ig.Emit (OpCodes.Stloc, skip_finally);
}
// Return ok
ig.Emit (unwind_protect ? OpCodes.Leave : OpCodes.Br, move_next_ok);
ig.MarkLabel (resume_point);
}
示例9: ImplicitReferenceConversion
static Expression ImplicitReferenceConversion (Expression expr, Type target_type, bool explicit_cast)
{
Type expr_type = expr.Type;
if (expr_type == null && expr.eclass == ExprClass.MethodGroup){
// if we are a method group, emit a warning
expr.Emit (null);
}
if (expr_type == TypeManager.void_type)
return null;
if (TypeManager.IsGenericParameter (expr_type))
return ImplicitTypeParameterConversion (expr, target_type);
//
// from the null type to any reference-type.
//
NullLiteral nl = expr as NullLiteral;
if (nl != null) {
return nl.ConvertImplicitly(target_type);
}
if (ImplicitReferenceConversionExists (expr, target_type)) {
//
// Avoid wrapping implicitly convertible reference type
//
if (!explicit_cast)
return expr;
return EmptyCast.Create (expr, target_type);
}
bool use_class_cast;
if (ImplicitBoxingConversionExists (expr, target_type, out use_class_cast)) {
if (use_class_cast)
return new ClassCast (expr, target_type);
else
return new BoxedCast (expr, target_type);
}
return null;
}
示例10: EmitCall
/// <remarks>
/// is_base tells whether we want to force the use of the `call'
/// opcode instead of using callvirt. Call is required to call
/// a specific method, while callvirt will always use the most
/// recent method in the vtable.
///
/// is_static tells whether this is an invocation on a static method
///
/// instance_expr is an expression that represents the instance
/// it must be non-null if is_static is false.
///
/// method is the method to invoke.
///
/// Arguments is the list of arguments to pass to the method or constructor.
/// </remarks>
public static void EmitCall (EmitContext ec, bool is_base,
bool is_static, Expression instance_expr,
MethodBase method, ArrayList Arguments, Location loc)
{
ILGenerator ig = ec.ig;
bool struct_call = false;
Type decl_type = method.DeclaringType;
if (!RootContext.StdLib) {
// Replace any calls to the system's System.Array type with calls to
// the newly created one.
if (method == TypeManager.system_int_array_get_length)
method = TypeManager.int_array_get_length;
else if (method == TypeManager.system_int_array_get_rank)
method = TypeManager.int_array_get_rank;
else if (method == TypeManager.system_object_array_clone)
method = TypeManager.object_array_clone;
else if (method == TypeManager.system_int_array_get_length_int)
method = TypeManager.int_array_get_length_int;
else if (method == TypeManager.system_int_array_get_lower_bound_int)
method = TypeManager.int_array_get_lower_bound_int;
else if (method == TypeManager.system_int_array_get_upper_bound_int)
method = TypeManager.int_array_get_upper_bound_int;
else if (method == TypeManager.system_void_array_copyto_array_int)
method = TypeManager.void_array_copyto_array_int;
}
//
// This checks the `ConditionalAttribute' on the method, and the
// ObsoleteAttribute
//
TypeManager.MethodFlags flags = TypeManager.GetMethodFlags (method, loc);
if ((flags & TypeManager.MethodFlags.IsObsoleteError) != 0)
return;
if ((flags & TypeManager.MethodFlags.ShouldIgnore) != 0)
return;
if (!is_static){
if (decl_type.IsValueType)
struct_call = true;
//
// If this is ourselves, push "this"
//
if (instance_expr == null){
ig.Emit (OpCodes.Ldarg_0);
} else {
//
// Push the instance expression
//
if (instance_expr.Type.IsValueType){
//
// Special case: calls to a function declared in a
// reference-type with a value-type argument need
// to have their value boxed.
struct_call = true;
if (decl_type.IsValueType){
//
// If the expression implements IMemoryLocation, then
// we can optimize and use AddressOf on the
// return.
//
// If not we have to use some temporary storage for
// it.
if (instance_expr is IMemoryLocation){
((IMemoryLocation)instance_expr).
AddressOf (ec, AddressOp.LoadStore);
}
else {
Type t = instance_expr.Type;
instance_expr.Emit (ec);
LocalBuilder temp = ig.DeclareLocal (t);
ig.Emit (OpCodes.Stloc, temp);
ig.Emit (OpCodes.Ldloca, temp);
}
} else {
instance_expr.Emit (ec);
ig.Emit (OpCodes.Box, instance_expr.Type);
}
} else
instance_expr.Emit (ec);
}
}
//.........这里部分代码省略.........
示例11: TableSwitchEmit
/// <summary>
/// This method emits code for a lookup-based switch statement (non-string)
/// Basically it groups the cases into blocks that are at least half full,
/// and then spits out individual lookup opcodes for each block.
/// It emits the longest blocks first, and short blocks are just
/// handled with direct compares.
/// </summary>
/// <param name="ec"></param>
/// <param name="val"></param>
/// <returns></returns>
void TableSwitchEmit (EmitContext ec, Expression val)
{
int element_count = Elements.Count;
object [] element_keys = new object [element_count];
Elements.Keys.CopyTo (element_keys, 0);
Array.Sort (element_keys);
// initialize the block list with one element per key
var key_blocks = new List<KeyBlock> (element_count);
foreach (object key in element_keys)
key_blocks.Add (new KeyBlock (System.Convert.ToInt64 (key)));
KeyBlock current_kb;
// iteratively merge the blocks while they are at least half full
// there's probably a really cool way to do this with a tree...
while (key_blocks.Count > 1)
{
var key_blocks_new = new List<KeyBlock> ();
current_kb = (KeyBlock) key_blocks [0];
for (int ikb = 1; ikb < key_blocks.Count; ikb++)
{
KeyBlock kb = (KeyBlock) key_blocks [ikb];
if ((current_kb.Size + kb.Size) * 2 >= KeyBlock.TotalLength (current_kb, kb))
{
// merge blocks
current_kb.last = kb.last;
current_kb.Size += kb.Size;
}
else
{
// start a new block
key_blocks_new.Add (current_kb);
current_kb = kb;
}
}
key_blocks_new.Add (current_kb);
if (key_blocks.Count == key_blocks_new.Count)
break;
key_blocks = key_blocks_new;
}
// initialize the key lists
foreach (KeyBlock kb in key_blocks)
kb.element_keys = new List<object> ();
// fill the key lists
int iBlockCurr = 0;
if (key_blocks.Count > 0) {
current_kb = (KeyBlock) key_blocks [0];
foreach (object key in element_keys)
{
bool next_block = (key is UInt64) ? (ulong) key > (ulong) current_kb.last :
System.Convert.ToInt64 (key) > current_kb.last;
if (next_block)
current_kb = (KeyBlock) key_blocks [++iBlockCurr];
current_kb.element_keys.Add (key);
}
}
// sort the blocks so we can tackle the largest ones first
key_blocks.Sort ();
// okay now we can start...
Label lbl_end = ec.DefineLabel (); // at the end ;-)
Label lbl_default = default_target;
Type type_keys = null;
if (element_keys.Length > 0)
type_keys = element_keys [0].GetType (); // used for conversions
TypeSpec compare_type;
if (TypeManager.IsEnumType (SwitchType))
compare_type = EnumSpec.GetUnderlyingType (SwitchType);
else
compare_type = SwitchType;
for (int iBlock = key_blocks.Count - 1; iBlock >= 0; --iBlock)
{
KeyBlock kb = ((KeyBlock) key_blocks [iBlock]);
lbl_default = (iBlock == 0) ? default_target : ec.DefineLabel ();
if (kb.Length <= 2)
{
foreach (object key in kb.element_keys) {
SwitchLabel sl = (SwitchLabel) Elements [key];
if (key is int && (int) key == 0) {
val.EmitBranchable (ec, sl.GetILLabel (ec), false);
} else {
val.Emit (ec);
EmitObjectInteger (ec, key);
//.........这里部分代码省略.........
示例12: EmitCall
// `dup_args' leaves an extra copy of the arguments on the stack
// `omit_args' does not leave any arguments at all.
// So, basically, you could make one call with `dup_args' set to true,
// and then another with `omit_args' set to true, and the two calls
// would have the same set of arguments. However, each argument would
// only have been evaluated once.
public static void EmitCall (EmitContext ec, bool is_base,
Expression instance_expr,
MethodBase method, Arguments Arguments, Location loc,
bool dup_args, bool omit_args)
{
ILGenerator ig = ec.ig;
bool struct_call = false;
bool this_call = false;
LocalTemporary this_arg = null;
Type decl_type = method.DeclaringType;
if (IsMethodExcluded (method, loc))
return;
bool is_static = method.IsStatic;
if (!is_static){
this_call = instance_expr is This;
if (TypeManager.IsStruct (decl_type) || TypeManager.IsEnumType (decl_type))
struct_call = true;
//
// If this is ourselves, push "this"
//
if (!omit_args) {
Type t = null;
Type iexpr_type = instance_expr.Type;
//
// Push the instance expression
//
if (TypeManager.IsValueType (iexpr_type) || TypeManager.IsGenericParameter (iexpr_type)) {
//
// Special case: calls to a function declared in a
// reference-type with a value-type argument need
// to have their value boxed.
if (TypeManager.IsStruct (decl_type) ||
TypeManager.IsGenericParameter (iexpr_type)) {
//
// If the expression implements IMemoryLocation, then
// we can optimize and use AddressOf on the
// return.
//
// If not we have to use some temporary storage for
// it.
if (instance_expr is IMemoryLocation) {
((IMemoryLocation)instance_expr).
AddressOf (ec, AddressOp.LoadStore);
} else {
LocalTemporary temp = new LocalTemporary (iexpr_type);
instance_expr.Emit (ec);
temp.Store (ec);
temp.AddressOf (ec, AddressOp.Load);
}
// avoid the overhead of doing this all the time.
if (dup_args)
t = TypeManager.GetReferenceType (iexpr_type);
} else {
instance_expr.Emit (ec);
// FIXME: should use instance_expr is IMemoryLocation + constraint.
// to help JIT to produce better code
ig.Emit (OpCodes.Box, instance_expr.Type);
t = TypeManager.object_type;
}
} else {
instance_expr.Emit (ec);
t = instance_expr.Type;
}
if (dup_args) {
ig.Emit (OpCodes.Dup);
if (Arguments != null && Arguments.Count != 0) {
this_arg = new LocalTemporary (t);
this_arg.Store (ec);
}
}
}
}
if (!omit_args && Arguments != null)
Arguments.Emit (ec, dup_args, this_arg);
OpCode call_op;
if (is_static || struct_call || is_base || (this_call && !method.IsVirtual)) {
call_op = OpCodes.Call;
} else {
call_op = OpCodes.Callvirt;
#if GMCS_SOURCE
if ((instance_expr != null) && (instance_expr.Type.IsGenericParameter))
ig.Emit (OpCodes.Constrained, instance_expr.Type);
#endif
//.........这里部分代码省略.........
示例13: ImplicitReferenceConversion
public static Expression ImplicitReferenceConversion (Expression expr, TypeSpec target_type, bool explicit_cast)
{
TypeSpec expr_type = expr.Type;
if (expr_type == null && expr.eclass == ExprClass.MethodGroup){
// if we are a method group, emit a warning
expr.Emit (null);
}
if (expr_type == TypeManager.void_type)
return null;
if (expr_type.Kind == MemberKind.TypeParameter)
return ImplicitTypeParameterConversion (expr, target_type);
//
// from the null type to any reference-type.
//
NullLiteral nl = expr as NullLiteral;
if (nl != null) {
return nl.ConvertImplicitly (null, target_type);
}
if (ImplicitReferenceConversionExists (expr, target_type)) {
//
// Avoid wrapping implicitly convertible reference type
//
if (!explicit_cast)
return expr;
return EmptyCast.Create (expr, target_type);
}
return ImplicitBoxingConversion (expr, expr_type, target_type);
}
示例14: EmitAssign
public void EmitAssign (EmitContext ec, Expression source, bool leave_copy, bool isCompound)
{
if (isCompound)
throw new NotImplementedException ();
source.Emit (ec);
Store (ec);
if (leave_copy)
Emit (ec);
}