1

I have a project which uses a library which was mostly build on and around C++. The delivered DLL with this library, i have imported into my C# project. After importing the following method in Unity:

    [DllImport("pst")]
private static extern int pst_get_sensor(PSTSensor sensor);

I require this PSTSensor struct, so actually use the method. In the C++ .h file, the struct is defines as :

struct PSTSensor
{
        char    name[80];       /**< Device name */
        int     id;             /**< Device identifier (for other tracking interfaces */
        float   pose[16];       /**< Device pose estimate as row-major matrix */
        double  timestamp;      /**< Time the data was recorded */
};

I have tried to replicate it in C#, and i ended up with this following:

    struct PSTSensor{
    PSTSensor(char[] name, int id, float[] pose, double timestamp){
        this.name = name;
        this.id = id;
        this.pose = pose;
        this.timestamp = timestamp;
    }
    public char[] name;
    public int id;
    public float[] pose;
    public double timestamp;
}

In the example C++ code that came with this project was stated to call pst_get_sensor(&sensor) this '&' sign, i do not recognize? How would i call this method in C#, and make it work?

I think i ruined the struct, seeing how i never worked with them before. At least it doesn't throw errors on compilation anymore, but i think it is still wrong. Any ideas on that?

Many thanks in advance, Smiley

0

3 Answers 3

2

I'm not sure if I'm answering your question entirely, but in c++ the & is used to pass an argument by reference which means that the argument you're passing in can be manipulated inside the function. To me it looks like the original function is used to fill out a sensor struct.

int C# you can pass by reference with the ref or out keyword:

private static extern int pst_get_sensor(PSTSensor ref sensor);

Why did you add a constructor in your C# implementation?

Sign up to request clarification or add additional context in comments.

15 Comments

This is a great help already, i added a constructor because i was not sure how to define the arrays in a fixed size without it. I tried different ways which mostly just threw errors at me.
'private static extern int pst_get_sensor(PSTSensor ref sensor);' This gives the error: Identifier expected, 'ref' is a keyword.
I'm sorry, I think the ref keyword is actually supposed to come first: (ref PSTSensor sensor). Check out the C# reference, maybe it will help you to gain more understanding of passing by reference in C#: msdn.microsoft.com/en-us/library/vstudio/0f66670z.aspx
Yep, that seems to fix it just right! Do you have any idea on the proper use of the structs? I can't find a lot of good examples on it yet.
what do you mean by "the proper use of structs?"
|
1

It seams that all you need to do is declare the parameter as ref

private static extern int pst_get_sensor(ref PSTSensor sensor);

If you want to have a look at an example, there is one here

Comments

1

You did not show the C++ declaration of your function, but give that you call it like this:

pst_get_sensor(&sensor);

it is presumably declared like so:

int pst_get_sensor(PSTSensor *sensor);

The function receives a pointer to the struct. That is clear since the call uses the & operator which takes the address of an object.

On the C# side you translate this parameter as a ref parameter. Like this:

[DllImport(...)]
static extern int pst_get_sensor(ref PSTSensor sensor);

Now, your other problem is that your struct is declared incorrectly. It contains inline arrays and you must communicate the lengths of those arrays to the marshaller. Like this:

[StructLayout(LayoutKind.Sequential, CharSet=CharSet.Ansi)]
struct PSTSensor
{
    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 80)]
    public string name;
    public int id;
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
    public float[] pose;
    public double timestamp;
}

Comments

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.