Problem with COM-Interoperability

D

Daniel

Hello,

i have an assembly which is developped in C#.NET. The
assembly provides two classes, one class has a method
which accepts an instance of the other class as a
parameter, like this:

--- BOC ---
[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsOne
{
public clsOne() {}
}

[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsTwo
{
public clsTwo() {}

public void test(clsOne cOne)
{
}
}
--- EOC ---

Now i create and register an COM-Typelib with RegAsm.exe.
After this, i can create instances from both classes in
Visual Basic 6. But if i create an instance of clsOne and
clsTwo, and call the method "test" in clsTwo with the
instance from clsOne, this clsOne-instance is NULL, when
the assembly finally gets it.

--- BOC ---
private sub test()
Dim cOne as New clsOne
Dim cTwo as New clsTwo

Call cTwo(cOne)
end sub
--- EOC ---

cOne is NULL is this case when the assembly gets the
parameter. Why? Do i have to declare anything else?

Thanks in advance for help.

Regards,
Daniel
 
B

Bonj

Try modifying the VB6 code to be:
--- BOC ---
private sub test()
Dim cOne as clsOne
Dim cTwo as clsTwo
Set cOne = New clsOne
Set cTwo = New clsTwo
cTwo.test cOne
end sub
--- EOC ---

In VB6, unlike VB.NET and C#, writing "Dim x as New Class1" doesn't actually
create an instance of Class1 until you call a method on it. In your case, it
seems like you were trying to call a method on cTwo - I don't know whether
this worked or not but you seemed to have the wrong syntax - you don't want
to be calling its constructor, that is called when a new instance of it is
created (even if by VB6's auto-instantiation) - but you should be calling
the method "test" by using the dot syntax. But clsOne certainly hadn't had a
method called on it, so it was no surprise it was null (Nothing in VB6).
Writing "Dim x as New y" in VB.NET is fine as you know that it will be
constructed there and then, and there is no confusion about when it will be
instantiated, but if you read the vb6 newsgroup you will find that the
general opinion is that "Dim x as New y" is bad syntax for production code,
as it causes confusion as to when exactly the object will be instantiated -
because that will only be whenever a method on it is called. It's generally
included in VB6 for writing quick throwaway code to test the objects.
 
D

Daniel

Thanks for the answer, but my code was just an example. I
actually create the clsOne-instance as you suggested, and
i call a method on it, before i pass it to the
method "test" of clsTwo. I even call a property of the
clsOne-instance before i pass it, and it returns me the
correct value. In VB, the instance is definitely not NULL
or NOTHING, but when it gets in the assembly, it is NULL.
Quite confusing...

Any other ideas?

Thanks,
Daniel
-----Original Message-----
Try modifying the VB6 code to be:
--- BOC ---
private sub test()
Dim cOne as clsOne
Dim cTwo as clsTwo
Set cOne = New clsOne
Set cTwo = New clsTwo
cTwo.test cOne
end sub
--- EOC ---

In VB6, unlike VB.NET and C#, writing "Dim x as New Class1" doesn't actually
create an instance of Class1 until you call a method on it. In your case, it
seems like you were trying to call a method on cTwo - I don't know whether
this worked or not but you seemed to have the wrong syntax - you don't want
to be calling its constructor, that is called when a new instance of it is
created (even if by VB6's auto-instantiation) - but you should be calling
the method "test" by using the dot syntax. But clsOne certainly hadn't had a
method called on it, so it was no surprise it was null (Nothing in VB6).
Writing "Dim x as New y" in VB.NET is fine as you know that it will be
constructed there and then, and there is no confusion about when it will be
instantiated, but if you read the vb6 newsgroup you will find that the
general opinion is that "Dim x as New y" is bad syntax for production code,
as it causes confusion as to when exactly the object will be instantiated -
because that will only be whenever a method on it is called. It's generally
included in VB6 for writing quick throwaway code to test the objects.


Hello,

i have an assembly which is developped in C#.NET. The
assembly provides two classes, one class has a method
which accepts an instance of the other class as a
parameter, like this:

--- BOC ---
[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsOne
{
public clsOne() {}
}

[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsTwo
{
public clsTwo() {}

public void test(clsOne cOne)
{
}
}
--- EOC ---

Now i create and register an COM-Typelib with RegAsm.exe.
After this, i can create instances from both classes in
Visual Basic 6. But if i create an instance of clsOne and
clsTwo, and call the method "test" in clsTwo with the
instance from clsOne, this clsOne-instance is NULL, when
the assembly finally gets it.

--- BOC ---
private sub test()
Dim cOne as New clsOne
Dim cTwo as New clsTwo

Call cTwo(cOne)
end sub
--- EOC ---

cOne is NULL is this case when the assembly gets the
parameter. Why? Do i have to declare anything else?

Thanks in advance for help.

Regards,
Daniel


.
 
G

Guest

You'll have to post the *actual* code which isn't "just an example", that
fails to work. You posted code which didn't look good, and I've told you what
I reckoned was wrong with it. *That* code shouldn't work, but should have
been corrected with my suggestion. Does it? I can't diagnose your real code,
if you only post "example code". Try to chop it down to the smallest amount
of lines that enable it to still demonstrate the problem, and then post that
- with a description of exactly what point in the code you expect a value to
be non-null when it is null, and also how you know that it is null at that
point.

Although off the top of my head, one of the things you might want to try is
getting the "test" method to accept a parameter of type *object* rather than
of type clsOne, and then cast it to a clsOne when it's safely home and dry on
the C# side.

Also, how are you debugging this configuration, by the way?


Daniel said:
Thanks for the answer, but my code was just an example. I
actually create the clsOne-instance as you suggested, and
i call a method on it, before i pass it to the
method "test" of clsTwo. I even call a property of the
clsOne-instance before i pass it, and it returns me the
correct value. In VB, the instance is definitely not NULL
or NOTHING, but when it gets in the assembly, it is NULL.
Quite confusing...

Any other ideas?

Thanks,
Daniel
-----Original Message-----
Try modifying the VB6 code to be:
--- BOC ---
private sub test()
Dim cOne as clsOne
Dim cTwo as clsTwo
Set cOne = New clsOne
Set cTwo = New clsTwo
cTwo.test cOne
end sub
--- EOC ---

In VB6, unlike VB.NET and C#, writing "Dim x as New Class1" doesn't actually
create an instance of Class1 until you call a method on it. In your case, it
seems like you were trying to call a method on cTwo - I don't know whether
this worked or not but you seemed to have the wrong syntax - you don't want
to be calling its constructor, that is called when a new instance of it is
created (even if by VB6's auto-instantiation) - but you should be calling
the method "test" by using the dot syntax. But clsOne certainly hadn't had a
method called on it, so it was no surprise it was null (Nothing in VB6).
Writing "Dim x as New y" in VB.NET is fine as you know that it will be
constructed there and then, and there is no confusion about when it will be
instantiated, but if you read the vb6 newsgroup you will find that the
general opinion is that "Dim x as New y" is bad syntax for production code,
as it causes confusion as to when exactly the object will be instantiated -
because that will only be whenever a method on it is called. It's generally
included in VB6 for writing quick throwaway code to test the objects.


Hello,

i have an assembly which is developped in C#.NET. The
assembly provides two classes, one class has a method
which accepts an instance of the other class as a
parameter, like this:

--- BOC ---
[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsOne
{
public clsOne() {}
}

[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsTwo
{
public clsTwo() {}

public void test(clsOne cOne)
{
}
}
--- EOC ---

Now i create and register an COM-Typelib with RegAsm.exe.
After this, i can create instances from both classes in
Visual Basic 6. But if i create an instance of clsOne and
clsTwo, and call the method "test" in clsTwo with the
instance from clsOne, this clsOne-instance is NULL, when
the assembly finally gets it.

--- BOC ---
private sub test()
Dim cOne as New clsOne
Dim cTwo as New clsTwo

Call cTwo(cOne)
end sub
--- EOC ---

cOne is NULL is this case when the assembly gets the
parameter. Why? Do i have to declare anything else?

Thanks in advance for help.

Regards,
Daniel


.
 
D

Daniel

Ok, i will try to reproduce the problem with a postable samplecode.
Nevertheless i recognized, that the instance of the parameter is not NULL
when it reaches the assembly, it is no valid reference. I get a
NullReferenceException, Error -2147467261, "object referance is not linked
to an object instance" (i hope i've translated it correctly).

Regards,
Daniel

Bonj said:
You'll have to post the *actual* code which isn't "just an example", that
fails to work. You posted code which didn't look good, and I've told you what
I reckoned was wrong with it. *That* code shouldn't work, but should have
been corrected with my suggestion. Does it? I can't diagnose your real code,
if you only post "example code". Try to chop it down to the smallest amount
of lines that enable it to still demonstrate the problem, and then post that
- with a description of exactly what point in the code you expect a value to
be non-null when it is null, and also how you know that it is null at that
point.

Although off the top of my head, one of the things you might want to try is
getting the "test" method to accept a parameter of type *object* rather than
of type clsOne, and then cast it to a clsOne when it's safely home and dry on
the C# side.

Also, how are you debugging this configuration, by the way?


Daniel said:
Thanks for the answer, but my code was just an example. I
actually create the clsOne-instance as you suggested, and
i call a method on it, before i pass it to the
method "test" of clsTwo. I even call a property of the
clsOne-instance before i pass it, and it returns me the
correct value. In VB, the instance is definitely not NULL
or NOTHING, but when it gets in the assembly, it is NULL.
Quite confusing...

Any other ideas?

Thanks,
Daniel
-----Original Message-----
Try modifying the VB6 code to be:
--- BOC ---
private sub test()
Dim cOne as clsOne
Dim cTwo as clsTwo
Set cOne = New clsOne
Set cTwo = New clsTwo
cTwo.test cOne
end sub
--- EOC ---

In VB6, unlike VB.NET and C#, writing "Dim x as New Class1" doesn't actually
create an instance of Class1 until you call a method on it. In your case, it
seems like you were trying to call a method on cTwo - I don't know whether
this worked or not but you seemed to have the wrong syntax - you don't want
to be calling its constructor, that is called when a new instance of it is
created (even if by VB6's auto-instantiation) - but you should be calling
the method "test" by using the dot syntax. But clsOne certainly hadn't had a
method called on it, so it was no surprise it was null (Nothing in VB6).
Writing "Dim x as New y" in VB.NET is fine as you know that it will be
constructed there and then, and there is no confusion about when it will be
instantiated, but if you read the vb6 newsgroup you will find that the
general opinion is that "Dim x as New y" is bad syntax for production code,
as it causes confusion as to when exactly the object will be instantiated -
because that will only be whenever a method on it is called. It's generally
included in VB6 for writing quick throwaway code to test the objects.


Hello,

i have an assembly which is developped in C#.NET. The
assembly provides two classes, one class has a method
which accepts an instance of the other class as a
parameter, like this:

--- BOC ---
[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsOne
{
public clsOne() {}
}

[ClassInterface(ClassInterfaceType.AutoDispatch)]
public class clsTwo
{
public clsTwo() {}

public void test(clsOne cOne)
{
}
}
--- EOC ---

Now i create and register an COM-Typelib with RegAsm.exe.
After this, i can create instances from both classes in
Visual Basic 6. But if i create an instance of clsOne and
clsTwo, and call the method "test" in clsTwo with the
instance from clsOne, this clsOne-instance is NULL, when
the assembly finally gets it.

--- BOC ---
private sub test()
Dim cOne as New clsOne
Dim cTwo as New clsTwo

Call cTwo(cOne)
end sub
--- EOC ---

cOne is NULL is this case when the assembly gets the
parameter. Why? Do i have to declare anything else?

Thanks in advance for help.

Regards,
Daniel



.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top