我在业余时间构建一个带有反射的编译器。

有点上下文,我有一个具有几种类型的运行时间,其中一种是float2,这是一个更简单的向量结构,具有两个float值(x和y)。我已经制作了几个属性,使我可以浏览值(la hlsl)。例如,如果我有一个新的float2(1.0f,2.0f),如果我做了类似的东西(new Float2(1.0f,2.0f))。yx我将获得float2(2.0f,1.0f)i '在我的语言中使用这种类型并目前测试这种情况(省略该语言的次要详细信息):

float2 a = float2(1.0, 2.0).yx;
return a;

我正在新调用中转换float2(1.0,2.0),并访问.yx中的float2类型的属性yx。

问题在于我得到了一个“系统。AccessviolationException:尝试读取或写下受保护的内存。这通常表明其他内存是损坏的。”。我不明白为什么,因为如果我做这样的事情:

float2 a = float2(1.0, 2.0);
return a;

一切顺利。

我要生成的IL代码如下(我认为问题发生在“ L_0014:STLOC.0”中,我不知道为什么会发生):

    .method public virtual final instance valuetype
[Bifrost.Psl]Bifrost.Psl.Compiler.Runtime.Float2 Main() cil managed
{
    .maxstack 3
    .locals init (
        [0] valuetype [Bifrost.Psl]Bifrost.Psl.Compiler.Runtime.Float2 num)
    L_0000: ldc.r4 1
    L_0005: ldc.r4 2
    L_000a: newobj instance void [Bifrost.Psl]Bifrost.Psl.Compiler.Runtime.Float2::.ctor(float32, float32)
    L_000f: call instance valuetype [Bifrost.Psl]Bifrost.Psl.Compiler.Runtime.Float2 [Bifrost.Psl]Bifrost.Psl.Compiler.Runtime.Float2::get_XY()
    L_0014: stloc.0 
    L_0015: ldloc.0 
    L_0016: ret 
}

Peverify的结果:

IL]:错误:[offset 0x0000000f] [找到值'bifrost.psl.compiler.runtime.float2'] [预期的bifrost.psl.psl.compiler.runtime.float2']堆栈上的意外类型。

有帮助吗?

解决方案

我看起来还不错,尽管我不知道你 Float2 好像。

我找到了调试的最佳方法是将汇编保存到磁盘,然后运行 同胞. 。生成一个的任何代码 AccessViolationException 会导致错误 同胞.

编辑:newobj MSDN上的文档 谈论将对象引用推到堆栈上,我认为这是一个指向值类型的指针。如果您从中遇到此错误 同胞 那我想你需要

  1. newobj
  2. stloc 到临时变量
  3. ldloca 获取存储在临时变量中的值类型的地址
  4. call

现在我考虑了一下,这就是C#编译器在直接调用值类型的情况 4.ToString();.

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top