views:

205

answers:

3

Hello,

I have a question regarding marshalling of C++ arrays to C#. Does the double* automatically convert to double[]?

I know double is a blittable type, so double from C++ is the same as double from C#. And what about double**, does it convert to double[,] ?

I have the following unmanaged function: int get_values(double** param,int sz)

where param is a pointer to array of doubles and sz it's size.

How can I DLLImport this function to C#?

Thanks in advance

A: 

This article says the following:

The following complex types are also blittable types:

One-dimensional arrays of blittable types, such as an array of integers. However, a type that contains a variable array of blittable types is not itself blittable.

Robert Harvey
A: 

In the context of a function's parameter type, double* and double[] are identical:

void f(double* p);
void g(double p[]);
void h(double p[10]); // even if you supply a size! (it's ignored)

void i(double (&a)[10]); // now this is different

In other contexts they aren't:

void j() {
  double a[10]; // sizeof a == sizeof(double) * 10
  double* p; // sizeof p == sizeof(void*)
}

This holds similarly for double** vs double*[], but note double[][] (without sizes) is different, and with sizes means a pointer-to-array (you have to specify all but one dimension).

It does sound like you're using a double** when it's not needed. Does just passing the array as a double* work for you?

int get_values(double* array, int size);

void func() {
  double a[10];
  get_values(a, 10);
}

(I know I didn't answer your DLLImport question, I don't know the answer.)

Roger Pate
I think the technical requirement is `sizeof(double*) <= sizeof(void*)` (because you're allowed to put any pointer-to-object into a `void*` and get it back out), but they are usually the same size. It may even be more peculiar.
Roger Pate
+1  A: 

The declaration makes no sense. It would make sense if the function takes a pointer to an array of doubles, but then the declaration would be

int get_values(double* array, int size);

Where size would give the size of the array allocated by the client and the function's return value indicates how many doubles were actually copied into the array. The equivalent P/Invoke declaration would be:

[DllImport("blah.dll")]
private static extern int get_values(double[] array, int size);

You have to allocate the array with new to the size you promised before calling the function.

But the double** argument is a hangup. It could mean that the function returns a pointer to an array of doubles but then the size argument makes little sense. Since it is the function that owns the array and controls its size. Or it could mean that the client passes a two-dimensional array, but then having only one size argument makes no sense.

Please update your question with the correct interpretation of what the function does.

Hans Passant