06-01-2010 04:27 AM
Hi,
Given below is the code written in LabWindows in which accessing a Dll dynamically is done using Windows API's LoadLibrary(), GetProcAddress() and FreeLibrary().
I could successfully Load the library and get the procedure address using Call Library node in LabVIEW. But.......got stuck after that.
As I am not good in C/C++ coding, Request someone to really help me write the same in LabVIEW.
Kindly do the needful.
#include <z_CviFastIF.h> // Function prototypes. #include <cviauto.h> // CVI Active X definitions. #include <formatio.h> #include <cvirte.h> /* Needed if linking in external compiler; harmless otherwise */ #include <ansi_c.h> #include <windows.h> typedef long __stdcall( *OLECREATEOBJECT)(char*); static HINSTANCE Hinstlib; static long gvntISystem; long CviCreateFastObjects (void) { OLECREATEOBJECT procAdd; pStrTempmem = (char*)CA_AllocMemory(1); Hinstlib = LoadLibrary("FastTrio"); if( Hinstlib != NULL) { procAdd = (OLECREATEOBJECT) GetProcAddress(Hinstlib, "OLECreateObject"); if(fRunTimeLinkSucess = (procAdd != NULL)) { gvntISystem = (procAdd)("FAST.IMFASTSystemInterface"); return 0; } else return 1; } else { return 1; } }
Solved! Go to Solution.
06-01-2010 04:56 AM
Hey,
"Call library function" is having both calling convention as WINAPI and C .. u can see them in function tab of "call library function"
i will just give u few primary steps to configure the "call library function"
1) press function tab --> select the library path and below that select the function name in drop down box.. select Run in UI thread and C as calling convention...
2) press Parameters tab --> specify the return type and press add a parameter in order to specify each of your input parameters.
this is few primary step to call library function then just finish and work in usual way of labview..
Hope it helps
HS
06-02-2010 07:14 AM
Hi HS,
I would like to thank you for the reply.
But can you pls explain me what is done in the LabWindow code by calling the LoadLibrary() and GetProcAddress() functions?
And as to what is done after getting the procedure address (GetProcAddress) of the function exported in the Dll.
Thank you,
Regards,
S.P.Vani
06-02-2010 07:45 AM
Hey S.P Vani,
First of all you can get better response if you post it in LabWindows forum but still i can give quick help on that ...
-> Any executable or DLL can link to a DLL only through an import library. and it is done dynamically by calling the Windows SDK LoadLibrary function..
-> GetProcAddress() gets the address of function and variable in DLL
It will be great if you have look on MSDN website about DLL functions ..
Hope it helps
HS
06-02-2010 07:55 AM
All the information you need is in the C code.
06-02-2010 11:23 PM
Hello,
Thanks a lot.
Pls find the attachment of the code and Kindly let me know whether it is correct or not..
Thanking you,
Regards,
Vani
06-02-2010 11:26 PM
Hi,
It is written in LabVIEW 8.0.
Also find the attachment of the Dll too.
Regards,
Vani
06-03-2010 01:55 AM
Hi,
Pls ignore the Fastdll.vi, I sent.
CviGetFASTVersionNumber() calls the OLEGetFASTVersionNumber() by passing the parameters gvntISystem (obtained from CviCreateFastObjects()) and CStrBuffer as its input.
I have implemented the same for calling OLECREATEOBJECT and OLEGETFASTVERSIONNUMBER too in LabVIEW (which I have attached with this message). I have also attached the Dll file in previous messages.
Kindly have a look at it and let me know if it is correct or not.
Waiting for your reply.
void CviGetFASTVersionNumber (char *cString){ long status = -99; FASTVERNUM procAdd; char *cStrBuffer; cStrBuffer = (char*)CA_AllocMemory(300); if( Hinstlib != NULL){ //get the procedure address procAdd = (FASTVERNUM) GetProcAddress(Hinstlib, "OLEGetFASTVersionNumber"); if(fRunTimeLinkSucess = (procAdd != NULL)){ // if address success status = (procAdd)(gvntISystem,cStrBuffer);//call the function strcpy (cString, cStrBuffer); } } //Free memory CA_FreeMemory (cStrBuffer); }
Regards,
Vani
06-03-2010 02:19 PM - edited 06-03-2010 02:22 PM
One recommendation (if you would use LabVIEW 8.5 or better):
Make the return value of the CreateObject function to be a pointer sized integer. As it is now you do assume 32 Bit Windows and DLL and that might bite you later on when you upgrade to a 64 Bit Windows, LabVIEw and DLL.
As to the implementation itself you make the typical LabVIEW Call Library Node starter error. The string to the second function is an output buffer. From LabVIEW you are used that it will take care to resize any string or array automatically to whatever size is needed. That does not work for DLL calls.
Did you notice the CA_AllocMemory(300) call in the CVI source code? For what might this be necessary??
Indeed it allocates a memory buffer for the function to write in the version string. LabVIEW has no way to know that this function wants a buffer to write in this information so you have to explicitedly tell LabVIEW that.
You do this with Initialize Array by creating a byte array large enough for the function parameter and then using the Byte Array To String function to turn it into the string. If you had LabVIEW 8.5 or better you could also simply configure this parameter in the Call Library Node configuration dialog to be of the desired minimum size and LabVIEW will take care about allocating that buffer automatically.
Ohh and by the way you should put a Delay function in the False case. Otherwise the loop does try to do very hard nothing and that has a rather nasty effect under LabVIEW for Windows of monopolizing the CPU almost completely.
06-03-2010 05:09 PM
Vanisp,
Have you tried the "Import Shared Library Wizard". Try it out it works good.
Tools menu >> Import >> Shared Library (.dll)...
Steve