Strange COM behavior called from .net

I am working on an application that calls the COM component of an affiliate application. Our .Net, they are not. I know little about COM; I know that the component we are calling is associated with a late delay.

obj As Object = CreateObject("THIRDPARTY.ThirdPartyObject")

Then we call the method on this COM object (Option Strict Off in the head of the VB file):

obj.AMethod(ByVal Arg1 As Integer, ByVal Arg2 As Integer, ByVal Arg3 as Boolean)

I am a little surprised that although this call works, this overload does not exist in the .dll COM interaction, which is created if I instead add a link to the COM server using the Add Reference. Accessible access to this method is available only to AMethod() .

However, this in itself is not what bothers me. I am worried that this call has been working for a while , THEN throws a TargetParameterCountException after successfully completing dozens of calls.

I ask you StackOverflow:

What .. Hell.

The only thing I can guess is that the documentation for the COM component states that this method runs synchronously - so maybe everything that is responsible for throwing this exception is blocked until some indefinite point in time? In addition, I am completely obsessed with this bizarre and, more importantly, inconsistent behavior.

edit # 1:

The more meaningful information that I just recalled is that from time to time a call raises instead of an ExecutionEngineException . He only glanced at the documentation to understand that it was VERY BAD. Doing a little digging tells me that a late call causes a stack corruption, a failure of the entire CLR. Presumably this means that runtime drops bad calls (with TargetParameterCountException ) for a while and misses them ( ExecutionEngineException ) of others.

edit # 2:

Answering David Lively's questions :

  • A call with null arguments that are currently contained in the code exists for a long time. I have not been able to get guidance for a third-party implementation of COM in the last two major revisions, so it is possible that they withdrew this signature from the service
  • There is only one location from which this method is called from
  • This is one desktop application that calls another on the same computer. Nothing unusual
  • The object is saved in the entire area of ​​user interaction with the application, so a new one is never created.

Unfortunately, it seems that there really is a mistake in the implementation, in your opinion. The problem with this seller is that when we report an error, their answer tends to follow a general form: i) deny the existence of a problem; ii) deny his problem; iii) refuse to correct it. These three steps typically cover a fairly long period of time.

+4
source share
3 answers

OK, basically a false signal. I did it wrong - I copied some kind of code due to something inappropriately, and what I called was never supposed to support this overload. Interestingly, the component did not reject this late call out of control, but did everything it had to do, at least initially.

0
source

No, this cannot damage the stack. IDispatch :: Invoke () is used to call the method, the arguments are packed into an array. Implementing the IDispatch stock will certainly detect an argument mismatch; it uses the type library information for validation. But it is entirely possible that the author of the COM server implemented it himself. Imperfect. This is what a C ++ hacker can do, inventory implementation is terribly slow. A corrupted GC heap is what happens when imperfect code is executed.

+3
source

I have not played with calling COM objects from VB for quite some time, but I will make a wild assumption:

I would expect an exception to be thrown if you call an object with too few or too many arguments, but it doesn't seem to be that way. What is the real signature of the method you are calling?

In some languages ​​and in some situations when you call a method, arguments are pushed onto the stack. If you put too many arguments, it is possible that outsiders remain on the stack after the method completes. This should cause many other problems.

Some features / considerations:

  • The object throws this exception from the inside. This should be reviewed by the author.

  • You call too many parameters. If, as you said, the overload you are trying to call is not published to the object type library, you can call another published method with a different signature. I would REALLY expect a compiler error if that is the case.

  • Are your later calls in the same part of your code or is there another thread of execution that might do something different and cause an error?

  • Are you running this from a desktop application / script or website? If you receive a valid expected response on a website or a request is executed, as if the internal lengthy process has not completed?

  • An object may or may not allocate resources, which may lead to undefined behavior when these resources are exhausted.

  • Do you free an object between calls or recreate it every time?

Also, re: your comments on late binding: the .CreateObject() method of instantiating a COM object is a normal, acceptable way to do this. This should have nothing to do with this problem. Based on the exceptions you listed, I am very inclined to believe that there is an internal problem with the object.

Good luck.

+1
source

All Articles