Create integer array to pass by interface

Dear all,

I have a host application written in Delphi (C++ Builder) XE2 and a plugin written in VS2012, C#, I want to pass an integer array by an interface, but I have a problem in creating the array. Here’s my Delphi code:

procedure TestProcedure();
var
  Bounds: TVarArrayBoundArray;
  ind: array [0..0] of Integer;
  TestArray: PVarArray;
  TestValue: Integer;
begin
  TestArray := nil;
  Bounds[0].LowBound := 0;
  Bounds[0].ElementCount := 3;
  TestArray := SafeArrayCreate(varInteger, 1, Bounds);
  ind[0] := 0;
  TestValue := 5;
  SafeArrayPutElement(TestArray, @ind, PInteger(TestValue));
  ind[0] := 1;     // HERE I GET A RUNTIME ERROR
  TestValue := 6;
  SafeArrayPutElement(TestArray, @ind, PInteger(TestValue));
  ind[0] := 2;
  TestValue := 7;
  SafeArrayPutElement(TestArray, @ind, PInteger(TestValue));
  TestProcedureFromInterface(TestArray);
end;

I can compile this code, but then I get a runtime error in line “ind[0] := 1;”. What am I doing wrong?

Best regards,

Matthias

Im not sure if Array [0…0] is a valid definition.

Just try changing to array[1…2]

And this:

ind[1] := 1;

Try following changes…

var
  ...
  ind: PVarArrayCoorArray;// array [0..0] of Integer;
  ...
begin
  GetMem(ind, SizeOf(Integer));
  ...
  FreeMem(ind);
end;

You can try to use approach described in this article

Thank you for answers, with “GetMem” and “FreeMem” it works. With my code I refered to the article http://wiki.remobjects.com/wiki/How_to_pass_arrays , but there “GetMem” and “FreeMem” is missing, perhaps you should add it.

I’m sorry, but I still have a problem with my integer array. The test array has two elements and the C# plugin receives two elements, no error and no exception, but both values are 0, so I think “SafeArrayPutElement” ist the problem. This is my current code:

var
  SafeArray: PVarArray;
  CoorArray: PVarArrayCoorArray;
  BoundArray: PVarArrayBoundArray;
  intValue: Integer;

begin

  GetMem(CoorArray, SizeOf(TVarArrayCoorArray));
  GetMem(BoundArray, SizeOf(TVarArrayBoundArray));

  BoundArray[0].LowBound := 0;
  BoundArray[0].ElementCount := 2;
  SafeArray := SafeArrayCreate(varInteger, 1, BoundArray);

  CoorArray[0] := 0;
  intValue := 70;
  SafeArrayPutElement(SafeArray, @CoorArray, PInteger(intValue));
  CoorArray[0] := 1;
  intValue := 123;
  SafeArrayPutElement(SafeArray, @CoorArray, PInteger(intValue));

FunctionForInterfaceCalling(..., SafeArray);

  SafeArrayDestroy(SafeArray);

  FreeMem(CoorArray);
  FreeMem(BoundArray);

end;

Please take a look at the small example, works fine for me.
IntegerArray.zip (9.6 KB)

Hello, I have the same problem. I tried all the solutions in this topic, but nothing works.
Is it possible to pass integer array to an hydra interface ?
Marie.

Hi,

What platform(s) are you using?

hello, i want to pass integer array delphi to .net hydra plugin.
I use this method :
function IntArrayAsSafeArray(Arr: ArrayOfInt): PVarArray;
var
pvData: PIntegerArray;
Bounds: TVarArrayBoundArray;
begin
Bounds[0].LowBound:=0;
Bounds[0].ElementCount:=Length(Arr);

Result := SafeArrayCreate(varInteger, 1, Bounds);
SafeArrayAccessData(Result, Pointer(pvData));
Move(Arr[0], pvData[0], Length(Arr));
// FreeMem(ind);
end;

But in .net the values of integer array are bad.

I also tried : to transform int to an object :
ArrayOfIntObject = array of IIntObjectDto;
IIntObjectDto = interface(IHYCrossPlatformInterface)
[‘{0A2B8CD8-E929-4B66-A455-E6FB11A8C9B7}’]
function get_Value: LongInt; safecall;
procedure set_Value(const value: LongInt); safecall;
property Value: LongInt read get_Value write set_Value;
end;

and i use the function:
function IntArrayAsSafeArray(Arr: ArrayOfInt): PVarArray;
var
Bounds: TVarArrayBoundArray;
i: Integer;
ind: array[0…0] of Integer;
//intObj: IIntObjectDto;
intObjsArray: ArrayOfIntObject;
begin
Result := nil;
if (Arr = nil) or (Length(Arr) = 0) then
Exit;

SetLength(intObjsArray, Length(Arr));
for i := 0 to Length(Arr) - 1 do
begin
intObjsArray[i] := IntObjectDto.Create(Arr[i]);
end;

Bounds[0].LowBound := 0;
Bounds[0].ElementCount := Length(Arr);

Result := SafeArrayCreate(varDispatch, 1, Bounds);
for i := 0 to Length(Arr) - 1 do
begin
ind[0] := i;
SafeArrayPutElement(Result, @ind, PDispatch(intObjsArray[i]));
end;
end;

But with this code i have a exception :SafeArrayRankMismatchException in .net plugin hydra.

I use : Delphi 7 with .net 4.8

Hi,

pls review testcase: testcase.zip (28.5 KB)

I have

Original array:
1951372325 589676224 606092741 1856441051 29140556 1691529598 530248571 2070835049 636146962 268940124
.NET side:
1951372325 589676224 606092741 1856441051 29140556 1691529598 530248571 2070835049 636146962 268940124
Received array:
1951372325 589676224 606092741 1856441051 29140556 1691529598 530248571 2070835049 636146962 268940124