LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Passing cluster with strings to C DLL.

Solved!
Go to solution

Hi there.
First I want to tell about my projetc:
The project is to record frames of data inside MySQL DB, the data contains basicaly doubles, but to keep the things organized I need to work with some tables that use a lot of string filds.
The main goal of this projetc is make the things simple. So, for testing, I developing 1 function for recording, that will open a connection record the data inside the table and close the connection, everything without the need to manipulate handles in labview, all the stuff will be done inside the dll (like call MySQL-lib etc).

THE PROBLEM: because I have to pass a lot of info to connect to MySQL (like host, user, et...) I choused to pass this variables inside a cluster. Everything goes OK when the cluster have only numbers, but with mixed variables it does't work.

Here a example of typedef.

typedef struct {
char *host;
char *user;
char *pwd;
int port;
}  *pconn;

DLL CALL PROTOTYPE
int Record(pconn cluster){
//code here//
}

I can access the port value, but no succes with host, user and pwd. Processing any char inside cluster breakes the labview. Passing strings directely to a dll functions works fine (but isn't the way that I want :p)

PS. I spended 3 days reading the labview forum's posts about this subject, but withwout conclusive soluticon, the solutions it's appears to change with the labview versions!

0 Kudos
Message 1 of 7
(2,996 Views)

@D.Prodocimo wrote:


I can access the port value, but no succes with host, user and pwd. Processing any char inside cluster breakes the labview. Passing strings directely to a dll functions works fine (but isn't the way that I want :p)


Well you can pass the strings as individual parameters to the DLL or start doing a complicated project of your own to do what you want. What do you think is more efficient?

 

LabVIEW has no way to do that directly as the memory management paradigma is very different between LabVIEW and C (with C having no memory management standard at all, it's all up to the individual developer).

Rolf Kalbermatter
My Blog
0 Kudos
Message 2 of 7
(2,969 Views)

Its the way by now.
But....
I tried a solution, now I can access and modify the first array.
typedef struct {

   char *host[128];

   char *user[128];

} *pconn;

My function  (just fot testing)

int NewRecod(pconn connect) {
    errno_t ret;

    ofstream output_file("R:\\struct.dmp", ios::binary);
    output_file.write((char*)connect, sizeof(connect));
    output_file.close();

    //Tryed to use strcpy_s() but don't work
    ret = memcpy_s(connect->host, 128, "Host_cp", 8);  // WORK
    ret = memcpy_s(connect->user, 128, "User_cp", 8); // DON'T WORK
    return 0;
}
In the dll function I've putted a sub function to dump the struct pointer content to a file.
in the dumped file I found the content of the fist char variable only.

My VI is
Captura de Tela (24).png
I've done this to study about labview memory system, but like you sayed I'm thinking to pass the main param as a filepatch to the file with the "static" MySQL config. Or pass a string with "\n" between the parameters to be interpreted this on dll.

I'll be trying ultill the success.

0 Kudos
Message 3 of 7
(2,823 Views)
Solution
Accepted by topic author D.Prodocimo

What do you think is this declaration doing?

typedef struct {
   char *host[128];
   char *user[128];
} *pconn;

Maybe, just maybe, it would start to behave a little more like what you expect when you change it to:

typedef struct {
   char host[128];
   char user[128];
} *pconn;

Take a minute and think good and then tell me why it didn't work the way you wanted.

 

But look at your resulting diagram. Is this really worth all the hassle? This code is much less runtime performant than if you pass the strings as individual parameters to the function. In addition it is a dragon of code to maintain later. Most beginners in software always forget that code they write now is not going to be ever finished. Somewhere in the future, someone will be required to make modification to that software, and if it is you, you will wonder how you ever could write such code, and if it is someone else he or she is going to curse you for this. Smiley Very Happy

 

If you control both sides of the interface, make it easy on yourself as much as possible and don't try to implement something based on some strange requirements like not wanting to have a function with more than two or three parameters! Putting parameters into a cluster (or struct) just because, is a bad habit in programming that should be punishable by law. Smiley Wink

Rolf Kalbermatter
My Blog
Message 4 of 7
(2,807 Views)

You are right! I’ll pass string by string and make a subVI to hold all the wires. I’m spending to much time trying to figure out something that is not the project’s goal!

Thanks for you opinion, some times the solution aren’t just coding but a more effective approach!!

0 Kudos
Message 5 of 7
(2,796 Views)

Just to put the solution here to collaborate with future users.
So, here the solution..
As @rolfk sayed, the best solution is forget to pass the struct stuff to DLL.
I passed string by string, and created a internal functions to convert it to c_string (just add the null char at end of each string).
How we can see, was necessary to pass a big string to labview to pre-alocate the memory (using malloc crashs everything, using a shorter string than returned string,  works but crashes the labview when I tryed to save the VI).

VI GUI.jpgVI G.jpg

0 Kudos
Message 6 of 7
(2,781 Views)

You can't malloc a string and hope to return it to LabVIEW. Instead you need to preallocated it in LabVIEW and the easiest way is to simply configure the Maximum Size in the Call Library Node configuration for the relevant parameter.

 

That is not even LabVIEW specific, it's standard C procedure that the caller allocates any buffers that the function may want to fill in. Anything else is always meaning trouble if the programmer doesn't know exactly how it needs to be done.

Rolf Kalbermatter
My Blog
Message 7 of 7
(2,775 Views)