BorlandTalk.com Forum Index BorlandTalk.com
Borland discussion newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Upgrading COM projects from BCB5 to BDS2006

 
Post new topic   Reply to topic    BorlandTalk.com Forum Index -> C++ Builder (ActiveX)
View previous topic :: View next topic  
Author Message
Old Wolf
Guest





PostPosted: Thu Apr 26, 2007 2:53 am    Post subject: Upgrading COM projects from BCB5 to BDS2006 Reply with quote



Is there a guide or a list of gotchas anywhere for this upgrade process?

So far I have spent a lot of time and not got very far, and it would be good if I did not have to rediscover the wheel every step of the way! Opening the project in BDS2006 did not work well; the type library does not appear in the editor. I can open it with File->Open but then any changes do not propagate to the xxxxImpl.cpp file.

I would like to avoid creating an entirely new project and trying to set up the interface to be the same as the old one, if possible, as that means the new version of the DLL would not be a drop-in replacement for the old one.

Also, what syntax should I use for TLIBIMP to generate the same _TLB and _ATL files that the IDE generates?
Back to top
Old Wolf
Guest





PostPosted: Thu Apr 26, 2007 7:29 am    Post subject: Re: Upgrading COM projects from BCB5 to BDS2006 Reply with quote



A follow-up question here.

In my interface I have functions that accept and return
SAFEARRAYs, via a VARIANT. (The parameter type in the type
library is a Variant). In BCB5 the FooImpl.h file came out as:

STDMETHOD(send(TVariantInParam data));
STDMETHOD(recv(TVariant *data));

But in BDS2006 the Foo_TLB.h file declared these differently and
did not update FooImpl, so to get it to compile I have had to
manually change the above to:

STDMETHOD(send(VARIANT data));
STDMETHOD(recv(VARIANT *data));

(which does seem the better solution). But now I am not sure if
my code leaks memory or not. The previous code, which did not
leak (as far as I know!) was essentially:

STDMETHODIMP TFooImpl::send(TVariantInParam data)
{
LPSAFEARRAY psa = data;
/* ... */
SafeArrayDestroy(psa);
}
STDMETHODIMP TFooImpl::recv(TVariant *data)
{
LPSAFEARRAY *psa = SafeArrayCreate(........);
*data = psa;
}

To get it to compile in BDS2006 I have changed it to this, but
not sure if this is leaky or not:

STDMETHODIMP TFooImpl::send(VARIANT data)
{
LPSAFEARRAY psa = TVariant( data );
/* ... */
SafeArrayDestroy(psa);
}
STDMETHODIMP TFooImpl::recv(VARIANT *data)
{
LPSAFEARRAY *psa = SafeArrayCreate(........);
*data = TVariant( psa );
}
Back to top
Remy Lebeau (TeamB)
Guest





PostPosted: Thu Apr 26, 2007 8:10 am    Post subject: Re: Upgrading COM projects from BCB5 to BDS2006 Reply with quote



"Old Wolf" <oldwolf (AT) inspire (DOT) net.nz> wrote in message
news:46300ea2$1 (AT) newsgroups (DOT) borland.com...

Quote:
In BCB5 the FooImpl.h file came out as:

STDMETHOD(send(TVariantInParam data));
STDMETHOD(recv(TVariant *data));

Borland stopped using smart wrapper classes for COM function
parameters in BCB 6.

Quote:
STDMETHODIMP TFooImpl::send(VARIANT data)
{
LPSAFEARRAY psa = TVariant( data );

Passing a VARIANT to TVariant's constructor makes a copy of the
VARIANT data. Then invoking the SAFEARRAY conversion operator creates
another copy of the array. You should just extract the SAFEARRAY from
the original VARIANT directly instead and avoid all the copies, ie:

STDMETHODIMP TFooImpl::send(VARIANT data)
{
LPSAFEARRAY psa = NULL;
if( V_VT(&data) & VT_ARRAY )
{
if( V_VT(&data) & VT_BYREF )
psa = V_ARRAYREF(&data);
else
psa = V_ARRAY(&data);
}

if( psa )
// use psa as needed ...

//...
}

This applies to BCB 5 as well.

Quote:
STDMETHODIMP TFooImpl::recv(VARIANT *data)
{
LPSAFEARRAY *psa = SafeArrayCreate(........);
*data = TVariant( psa );

TVariant does not have a conversion operator for VARIANT. You should
just fill in the VARIANT directly:

STDMETHODIMP TFooImpl::recv(VARIANT *data)
{
VariantInit(data);

V_ARRAY(data) = SafeArrayCreate(........);
if( V_ARRAY(data) != NULL )
V_VT(data) = VT_ARRAY | VT_WhateverYourArrayTypeIs;

//...
}

Gambit
Back to top
Old Wolf
Guest





PostPosted: Mon Apr 30, 2007 5:39 am    Post subject: Re: Upgrading COM projects from BCB5 to BDS2006 Reply with quote

"Remy Lebeau \(TeamB\)" <no.spam (AT) no (DOT) spam.com> wrote:
Quote:
STDMETHODIMP TFooImpl::send(VARIANT data)
{
LPSAFEARRAY psa = NULL;
if( V_VT(&data) & VT_ARRAY )
{
if( V_VT(&data) & VT_BYREF )
psa = V_ARRAYREF(&data);
else
psa = V_ARRAY(&data);
}

if( psa )
// use psa as needed ...

//...
}

Thanks for the sample code. To clarify, I should NOT be calling
SafeArrayDestroy once I'm done, and I should NOT call
VariantClear(&data) either ? In fact the latter would have no
effect on the caller, who would then try to deallocate the
SafeArray anyway ?
Back to top
Remy Lebeau (TeamB)
Guest





PostPosted: Mon Apr 30, 2007 11:54 pm    Post subject: Re: Upgrading COM projects from BCB5 to BDS2006 Reply with quote

"Old Wolf" <oldwolf (AT) inspire (DOT) net.nz> wrote in message
news:46353ab4$1 (AT) newsgroups (DOT) borland.com...

Quote:
To clarify, I should NOT be calling SafeArrayDestroy once
I'm done, and I should NOT call VariantClear(&data) either ?

Correct on both. The only reason you needed to call
SafeArrayDestroy() in your TVariant code is because TVariant's
SAFEARRAY conversion operator returns a copy of the array. In the
snippet I gave you, the code is now accessing the original array
directly, not a copy. The caller owns the original array, and is
responsible for freeing it after send() exits.


Gambit
Back to top
Old Wolf
Guest





PostPosted: Tue May 01, 2007 5:44 am    Post subject: Re: Upgrading COM projects from BCB5 to BDS2006 Reply with quote

Final question, I hope: for functions that accepted VARIANT_BOOL, in BCB5 it came out as:

STDMETHODIMP TFooImpl::bar(TOLEBOOL* Value)
{
// ...
*Value = true;
// ...
}

But now the function has to be declared as:

STDMETHODIMP TFooImpl::bar(VARIANT_BOOL* Value)

I see that VARIANT_TRUE is defined as (-1). Do I have to be careful to set *Value = VARIANT_TRUE, or will it work if I just set *Value = true ?
Back to top
Remy Lebeau (TeamB)
Guest





PostPosted: Tue May 01, 2007 6:24 am    Post subject: Re: Upgrading COM projects from BCB5 to BDS2006 Reply with quote

"Old Wolf" <oldwolf (AT) inspire (DOT) net.nz> wrote in message
news:46368d80$1 (AT) newsgroups (DOT) borland.com...

Quote:
Final question, I hope: for functions that accepted VARIANT_BOOL, in
BCB5 it came out as:

STDMETHODIMP TFooImpl::bar(TOLEBOOL* Value)

TOLEBOOL is another Borland wrapper class. It wraps a VARIANT_BOOL.

Quote:
I see that VARIANT_TRUE is defined as (-1).

Correct. Well, more accurately, VARIANT_TRUE is actually 0xFFFF, but
VARIANT_BOOL is treated as a signed short, so 0xFFFF is the same as -1
in a signed numeric type.

Quote:
Do I have to be careful to set *Value = VARIANT_TRUE, or
will it work if I just set *Value = true ?

Passing 'true' to a numeric type converts it to a value of 1. 1 is
not a valid value for VARIANT_BOOL. TOLEBOOL handled that conversion
for you. If you want to continue using TOLEBOOL, then you can use it
like this:

STDMETHODIMP TFooImpl::bar(VARIANT_BOOL * Value)
{
// ...
*Value = TOLEBOOL(true);
// ...
}


Gambit
Back to top
Display posts from previous:   
Post new topic   Reply to topic    BorlandTalk.com Forum Index -> C++ Builder (ActiveX) All times are GMT
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.