【问题标题】:Reflection.Emit unsafe codeReflection.Emit 不安全代码
【发布时间】:2014-12-10 19:58:17
【问题描述】:

我正在用 F# 中的反射发射做一些黑客行为。我正在尝试执行与此 C# 代码等效的操作:

var ass = AppDomain.CurrentDomain.DefineDynamicAssembly(new AssemblyName("Test"), AssemblyBuilderAccess.RunAndSave);
var mb = ass.DefineDynamicModule("Test", "Test.dll", false);
var t = mb.DefineType("Foo", TypeAttributes.Public, typeof(ValueType));
t.DefineField("foo", typeof(int*), FieldAttributes.Public);
t.CreateType();
ass.Save("Test.dll");

该行尤其是定义字段行。在 F# 中,我能得到的最接近的是

let f = t.DefineField("foo", (typeof<nativeptr<int>>), FieldAttributes.Public)

但是,编译后的字段最终编译为 IntPtr 类型而不是 int*。(注意它也是用于 nativeint 或任何其他类型的 IntPtr)

此外,我希望能够使用我以编程方式定义的结构,并在另一个结构中有一个 Foo*,但显然在这种情况下我无法使用 typeof(在 C# 或 F# 中)。有没有办法从 Type/TypeBuilder 中将字段定义为 Foo*?

在任何人指出这一切都可能是疯狂的(我同意)之前,这是一个有趣的项目,让我自己弄清楚我可以多么疯狂地生成 C# 不允许我的代码:)

【问题讨论】:

    标签: c# .net f# reflection.emit


    【解决方案1】:

    我相信ilsigptr&lt;int&gt; 是 C# 的 int* 的 F# 对应物。

    另见:

    【讨论】:

    • 这适用于第一种情况:let f = t.DefineField("foo", (typeof>), FieldAttributes.Public) 谢谢!
    • 对于第二种情况 let p = typedefof>.MakeGenericType([|t :> Type|]) let f = t.DefineField("rec", p, FieldAttributes.Public ) 它在 MakeGenericType 上引发 InvalidOperation 异常,因为它推断 ilsigptr 的泛型类型,而对于 let p = typedefof>.MakeGenericType([|t :> Type|]) let f = t.DefineField(" rec", p, FieldAttributes.Public) 效果很好。我猜想 ilsigptr 有一些特别之处,但如果能访问指向生成的结构的指针会很棒。有什么想法吗?
    • 实际上,事实证明你可以这样做,它适用于所有情况 let p = t.MakePointerType() let f = t.DefineField("rec", p, FieldAttributes.Public) 呼。感谢丹尼尔的帮助。标记为答案,因为它是正确方向的一个大“指针”。
    • 啊,太容易了。很高兴你明白了。
    猜你喜欢
    • 2011-08-06
    • 2016-11-07
    • 1970-01-01
    • 1970-01-01
    • 2010-09-10
    • 2011-03-11
    • 1970-01-01
    • 1970-01-01
    • 2014-09-27
    相关资源
    最近更新 更多