2

Let's say I have a struct that's not one of the C# primitives.

I'd like to know if there's a way (including unsafe code) to get a pointer from an instance of the struct type (the pointer doesn't have to be type-safe, it could be void*) and get an instance of the struct type from a pointer, but without boxing involved.

(I know that the System.Runtime.InteropServices.Marshal class offers almost what I'm describing, but it involves passing and getting structs as object, which means that boxing is involved.)

2 Answers 2

4

You can use an unsafe region to get the pointer using the & operator and convert back to the type using the * operator.

public struct Foo
{
    public int bar;
};

void Main()
{
    var foo = new Foo();
    foo.bar = 5;

    unsafe
    {
        Foo * fooPtr = &foo;
        Console.WriteLine("Foo address {0:X}", *fooPtr);

        Foo anotherFoo = *fooPtr;
        Console.WriteLine("Bar= {0}", anotherFoo.bar);
    }
}
Sign up to request clarification or add additional context in comments.

3 Comments

I guess 5 is the lucky number. We both use the same :p
I was just thinking that :)
@SriramSakthivel, why 5? Everyone knows that the answer is 42 ;)
3

I don't quite understand what is the problem with taking the address of the struct with & operator. If you're not aware of that, there exist address of operator.

For example:

struct Demo
{
    public int SomeField;
}

internal static class Program
{
    static Demo demo = new Demo { SomeField = 5 };

    private static void Main()
    {
        Print();
    }

    public static unsafe void Print()
    {
        fixed (Demo* demop = &demo)
        {
            Console.WriteLine(demop->SomeField);
        }
    }
}

This code doesn't boxes the struct, though it needs unsafe context to compile.

1 Comment

Oh, this is very embarassing - I had tried doing this in a generic method using a T : struct and it failed with a "cannot take address of a managed type" error (while it worked on int, etc). So I (quite wrongly) assumed the problem was the type, not the fact that I was using generics. Considering this, my actual question should have been different, but since it is what it is, you are both correct of course.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.