02-21-2017 08:32 AM
Hi,
I am trying to call a dll which uses nested structs and the structs contain arrays. I may have to use DSNewPtr and MoveBlock I think. However, I have created a very simple example to test these functions and while the VI will run and return the correct data, LabVIEW crashes when I close the VI. I guess a size or type is configured incorrectly but I cannot spot where. I have tried Signed and Unsigned Pointer Integers. Please take a look, thank you,
Michael.
Solved! Go to Solution.
02-21-2017 09:53 AM
My guess is the second MoveBlock needs a fixed size array constant wiring in to set the size of the destination array. I'm out so I will try when I get back.
02-21-2017 11:16 AM
Setting the datatype to Array instead of Adapt to Type works for this example.
02-22-2017 08:54 AM - edited 02-22-2017 09:04 AM
@Michael_78 wrote:
Setting the datatype to Array instead of Adapt to Type works for this example.
That may seem to work but is only a partial fix! It corrects the datatype so that the MoveBlock function can actually see the pointer in the actual LabVIEW array instad of the handle, which the MoveBlock function knows absolutely nothing about!
But!!!!
The pointer that the second MoveBlock sees is a pointer to an array that only can hold 0 bytes of data (because you didn't pre-initialize the array to a specific size).
You need to make sure that LabVIEW preallocates the array to the necessary number of elements by either explicitedly adding an Initialize Array function to create an array of the neccessary number of U8 elements, or configure the Call Library Node for that parameter to use the size input as "Minimum size".
Also to be safe you should make sure that the array that is wired to the first MoveBlock function actually does contain at least the number of elements that you tell the MoveBlock functìon to copy, as there is a chance that the memory beyond the end of the array is not mapped into the current process and even just reading it might generate a general protection fault anyhow.
05-28-2018 01:28 AM - edited 05-28-2018 01:29 AM
Hi,
DLL returns a Pointer to the array (4 byte) in my project. Can I use similar move Block example to read data located at memory address mentioned in 'pointer to array'?
05-28-2018 06:40 AM
Yes you can, but you may not have to! Show us what your DLL does and we can very likely show you how to configure your Call Library Node in a way that does not require this kind of magic.
08-01-2018 04:39 AM
Hello, I have to do the same thing but in the ways : get memory address from a 2D array to send it to the DLL and recreate a 2D array from a pointer received from the DLL. Is there a simple way to do that ?
08-01-2018 04:42 AM
My previous answer applies here too. Show us what you need to do. There are about 500 different things that might be done about this depending on your specific use case and I'm not going to explain them all here.
08-01-2018 04:44 AM - edited 08-01-2018 04:47 AM
I will try to be clear in my explanations.
I wrote a C++ DLL with Visual Studio and add a C wrapper to use it on several langages (C++, Python, LabVIEW, ...). In this one, I am dealing with images, so 2D array. I created a labview library using LabVIEW tools so I attached this library to my project.
First, the function to allocate and free the handle for the DLL is working correctly so the communication seems okay. Moreover, my DLL function take as parameter a pointer on the first pixel of the image, so on the first value of the tab, in order to recreate a matrix (library OpenCV) to perform some operations.
Here is the C function:
__declspec(dllimport) unsigned short* __stdcall imAdjustBrightness(void* handle, void * ptrImg, int width, int height, int inputType, int brightnessValue) { if (handle) { EpsImageProcessing* data = (EpsImageProcessing*)handle; return data->imAdjustBrightness(ptrImg, width, height, inputType, brightnessValue); } return NULL; }
And some images to illustrate :
08-01-2018 04:56 AM - edited 08-01-2018 04:59 AM
Just configure the second parameter of the Call Library Node to be of type Array, 2 dimensions, integer type of your 2D image array, and passed as C array pointer and you are done.
Obviously you will also need to make sure that the inputType really matches the image data that you load and pass in, or your EpsImageProcessing function might screw up when trying to reference the array pointer as something else than it is.