A pointer type static field's value is displayed as zero 0x0 by the debugger while it actually has a valid value

99封情书 提交于 2019-12-10 18:12:49

问题


I came across this behaviour while trying to access the value of a struct's static field with type uint*

While debugging, watch window shows the static field StaticBitMask's value as zero, but actually (and as expected) it is a valid pointer, and Console.WriteLine() prints it, as can be seen in the console output below:

Pointers:
-----------------
Static bitmask pointer: 0x706790
Instance bitmask pointer: 0x708A20

Values:
-----------------
Static bitmask pointer val: 0xFFFFFFFF
Instance bitmask pointer val: 0xFFFFFFFF

This inconsistent behaviour is not observed with the fixed instance fields. For those, the actual value can be seen in the watch window and is printed out.

Why is this happening? I know that it is not a showstopper by the way, but why, one wonder.

Also, what will the consequences of having a static field with a pointer type in a struct? Since it cannot be marked as fixed, is it possible that it may be moved around buy GC anytime?

Here is the source code which you can directly run as a console application to reproduce the problem.

Thanks.

using System;
using System.Runtime.InteropServices;

public unsafe struct UIntBitMask
{
    private static int uintNumberOfBits = sizeof(uint) * 0x8;

    public static uint* StaticBitMask;

    public fixed uint InstanceBitMask[1024]; // uintNumberOfBits * uintNumberOfBits = 32 * 32 = 1024

    public UIntBitMask(bool fillBitMask)
    {
        GetUnmanagedBitMask();
    }

    static UIntBitMask()
    {
        IntPtr pointer = Marshal.AllocHGlobal(uintNumberOfBits * uintNumberOfBits * sizeof(uint));
        StaticBitMask = (uint*)pointer.ToPointer();
        for (int i = 0; i < uintNumberOfBits; i++)
            for (int j = 0; j < uintNumberOfBits; j++)
                ((uint*)&StaticBitMask[i])[j] = ((uint.MaxValue >> (uintNumberOfBits - j)) << i);
    }

    private void GetUnmanagedBitMask()
    {
        fixed (uint* structPointer = InstanceBitMask)
        {
            for (int i = 0; i < uintNumberOfBits; i++)
                for (int j = 0; j < uintNumberOfBits; j++)
                    ((uint*)&structPointer[i])[j] = ((uint.MaxValue >> (uintNumberOfBits - j)) << i);
        }
    }
}

public class PointerTypeStaticFieldLab
{
    static unsafe void Main()
    {
        UIntBitMask instance = new UIntBitMask(true);
        Console.WriteLine("Pointers:");
        Console.WriteLine("-----------------");
        Console.WriteLine("Static bitmask pointer: 0x{0:X}", new IntPtr(UIntBitMask.StaticBitMask).ToInt64());
        Console.WriteLine("Instance bitmask pointer: 0x{0:X}", new IntPtr(instance.InstanceBitMask).ToInt64());
        Console.WriteLine();
        Console.WriteLine("Values:");
        Console.WriteLine("-----------------");
        Console.WriteLine("Static bitmask pointer val: 0x{0:X}", UIntBitMask.StaticBitMask[0]);
        Console.WriteLine("Instance bitmask pointer val: 0x{0:X}", instance.InstanceBitMask[0]);
    }
}

来源:https://stackoverflow.com/questions/34138112/a-pointer-type-static-fields-value-is-displayed-as-zero-0x0-by-the-debugger-whi

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!