LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

IDispatch/IUnknown

A LabView user posted to this group yesterday about a problem with a component he is testing for my company. As the author of the component, I would like to repost with more details. This is a COM issue relating to IDispatch/IUnknown interfaces. LabView is acting as the COM client in this case. It is communicating with a COM server, which I’ll call the alg server, on an IDispatch interface. I understand that LabView can communicate only via IDispatch.

All goes well until an error is detected by the alg server, e.g., an illegal input value supplied by the user. The alg server then tries to communicate with another COM server, the language server, on an IUnknown interface to get localized error messages. Note that the LabView client never communicates directly with the language server. It talks only to the alg server.

The HRESULT return code from the failing QueryInterface call by the alg server decodes as "No such interface supported". I understand that this is the same error that occurs when an IDispatch client (like LabView) tries to get an interface and finds only an IUnknown version. But the alg server is acting like the client here and *it* is capable of communicating via IUnknown.

A main COM idea is hiding implementation details from the client. So a LabView client mandating IDispatch for all servers "down the line" from the one it talks to directly seems strange. I can write a VB dumb client that uses CreateObject to get the IDispatch interface on the alg server. This VB client does not get "No such interface supported" when an user error is detected; instead the correctly localized error message is returned.

It seem likely that adding an IDispatch interface to the language server might solve this problem. However, I would like to avoid this if possible….more work!

Can anyone comment and/or suggest an easier solution? For example, could a missing registry entry cause this problem? All components are registered properly as near as I can tell.

Thanks in advance,
Message 1 of 12
(4,960 Views)
I can't see any way that LabVIEW could force a COM/ActiveX component to do anything internally (regardless of the LV version). COM is a binary standard for APIs, not implementation. We have no way of knowing what you are doing inside your component.

First question - is the customer using LV 7.x or an earlier version?

The reason I ask is that before 7.x we did require an IDispatch interface. However, 7 added full v-table support so as long as the object is either a custom or dual interface, LabVIEW goes through the binary interface, not IDispatch.

Second question - Have you tried this same sequence from a C++ client? The reason I ask is that I have been working with another customer using an ActiveX interface that worked in VB but not in LabVIEW. Turns out that it didn't work in C++ either - it wasn't correctly supporting any early binding client.
Message 2 of 12
(4,952 Views)
Thanks for the quick response and good questions!

>We have no way of knowing what
>you are doing inside your component.

This is *exactly* what i was thinking...how can LabView know what the component is doing?

The LabView version is 6.1.

The code works with C++ clients, VB clients, even from Excel. The alg server's IUnknown interfaces came first; then later its IDispatch versions were added. Via ATL.

The language server is a MFC COM object. So getting it to support IDispatch means porting into ATL, which is what I'd like to avoid.

This is a real mystery to me.
0 Kudos
Message 3 of 12
(4,957 Views)
Yikes! Sticky stuff everywhere and every place you turn there is another mess.

You obviously do not want to re-invent the wheel here.

Two questions

1) You said it works with all MS products, any non-MS products?

I have seen stuff work in MS environments that were somehow shared internally within MS stuff but LV 6.1 could not get at it. (SlideShow End from PP event never fired. I think there was a law suit over this, not sure. I mention this because the other thread mentioned that re-installing MS stuff has fixed a similar issue.)

2) Have you concidered using a C dll in a LV wrapper just to make it work?

That is all I have to offer for now. I will watch.

Ben
Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
0 Kudos
Message 4 of 12
(4,949 Views)
mbb_WA,

Do you have LV 6.1 on your machine? I was just wondering if you could use a debug build of your component to see if any more information was forthcoming when trying this out.

I also agree with Ben in trying to add another layer between LV and the COM server to see what changes that brings.
Message 5 of 12
(4,935 Views)
thanks for the comments/questions...

>1) You said it works with all MS products, any non-MS products?

One of our C++ clients is built with a Borland compiler and *it* has no problem.

>2) Have you concidered using a C dll in a LV wrapper just to make it work?

Not sure what you mean. I'm at a bit of a disadvantage because I am not a LabView user so I am not cognizant of the various actions available there. Do you mean make a non-COM C style dll and then doing some magic in LabView to wrap it?

please elaborate if possible.
0 Kudos
Message 6 of 12
(4,922 Views)
LabVIEW has a simple integration option for C-style DLLs. If you could create a piece of C++ code that access the COM server and then exposes that functionality as extern "C" statements, we could try using that. That removes LV as a COM client in this case.
0 Kudos
Message 7 of 12
(4,762 Views)
LV can call dll's.

Create a dll in C and use that dll by calling a VI that invokes the dll. Once this VI is written it looks like a normal LV VI from the outside but has a dll call on the inside. It is commonly called a "wrapper".

Ben

Collision detected!

Ignore me, listen to Brian.

Message Edited by Ben on 05-06-2005 12:25 PM

Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
0 Kudos
Message 8 of 12
(4,758 Views)
> Do you have LV 6.1 on your machine?

no.

>I was just wondering if you could use a debug
>build of your component to see if any more
>information was forthcoming when trying this out.

yes, this is possible.

>I also agree with Ben in trying to add another
> layer between LV and the COM server.

but, but...there is *already* another layer. LabView has no problem talking to the alg server. i can't see much hope in wrapping it. Wrapping the language server (how?) might change things but then I may as well bite the bullet and re-do the dll with ATL.

>re-installing MS stuff
this was mentioned by Ben.
the language server has minimal dependencies on MS dlls. it needs MFC42.dll and MSVCRT.dll. and the fact that non-LabView clients work on this user's machine seems to indicate that these dlls are not corrupted.
0 Kudos
Message 9 of 12
(4,915 Views)
The only reason Ben and I suggested wrapping was to eliminate LV as a COM client. If the alg and language server work fine from a C++ client, then you could create a C++ client to the alg object as a DLL that exposes basic C calls for the test. Then LV calls those C methods. This should work if there is indeed something wrong with the LV COM client side.

If it doesn't work, then there might be something about LV being the host application.

BTW - What style of server are alg and the language server (inproc/oop)? I am just wondering if it is something about all of the code running inside the LV process space.

Do I have a thought? No. I can't think why this is failing, but I'm just trying ways of getting more info out of it (especially since it sounds like you need to use the customer's system to test it).

Does this make any sense?
Message 10 of 12
(4,907 Views)