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 

double destruction of ActiveForm....

 
Post new topic   Reply to topic    BorlandTalk.com Forum Index -> C++ Builder (ActiveX)
View previous topic :: View next topic  
Author Message
Marcelo R. Lopez, Jr.
Guest





PostPosted: Tue Jun 15, 2004 10:37 pm    Post subject: double destruction of ActiveForm.... Reply with quote



This has been working for almost two years, and suddenly it's not working
anymore....

I have a set of ActiveLibraries with ActiveForms inside them that I
instrument into my application by instantiating them via
CoClassFactory::CreateInstance()...and then inject inside of panels of the
main app ( encapsulating by a TOleContainer ).
Just before handling the exit of the application I perform an orderly
shutdown of each of these ActiveLibraries.

The problem is that now, after almost two years of working just fine. I will
get a circumstance, where ONE of these ActiveLibraries will get it's
ActiveForms destructor called more than once. It only happens to this one
ActiveForm within one of the ActiveLibraries.

I've tried Memproof, but that doesn't show me enough granularity. There used
to be SleuthQA, but they're gone now. I've tried the AutomatedQA, but the
Demo only does so much.

Has any one ever run across a situation where ATL has gotten it's reference
counts screwy, and tried to forceably destruct an ActiveForm needlessly (
Notice, it's not calling the release for the ActiveLibrary either ), it's
calling the ~TActiveForm base class for my form. What's oddest in all of
this...is that I NEVER get my "ActiveFormDestroy" event handler called, even
though I've got code in there to watchdog it and do some
"OutputDebugString()" calls.

Any ideas, no matter how hair-brained, will be greatly appreciated.

Marcelo R. Lopez, Jr.

Todays's quote of the day:
Don't EVER try to do COM by hand, it's like when your mother told you not to
touch a burner on a stovetop. But you touched it anyway.


Back to top
Marcelo R. Lopez, Jr.
Guest





PostPosted: Fri Jun 18, 2004 3:59 pm    Post subject: Re: double destruction of ActiveForm.... Reply with quote



No one has any ideas ??

"Marcelo R. Lopez, Jr." <mlopez (AT) voicerite (DOT) com> wrote

Quote:
This has been working for almost two years, and suddenly it's not working
anymore....

I have a set of ActiveLibraries with ActiveForms inside them that I
instrument into my application by instantiating them via
CoClassFactory::CreateInstance()...and then inject inside of panels of the
main app ( encapsulating by a TOleContainer ).
Just before handling the exit of the application I perform an orderly
shutdown of each of these ActiveLibraries.

The problem is that now, after almost two years of working just fine. I
will
get a circumstance, where ONE of these ActiveLibraries will get it's
ActiveForms destructor called more than once. It only happens to this one
ActiveForm within one of the ActiveLibraries.

I've tried Memproof, but that doesn't show me enough granularity. There
used
to be SleuthQA, but they're gone now. I've tried the AutomatedQA, but the
Demo only does so much.

Has any one ever run across a situation where ATL has gotten it's
reference
counts screwy, and tried to forceably destruct an ActiveForm needlessly (
Notice, it's not calling the release for the ActiveLibrary either ), it's
calling the ~TActiveForm base class for my form. What's oddest in all of
this...is that I NEVER get my "ActiveFormDestroy" event handler called,
even
though I've got code in there to watchdog it and do some
"OutputDebugString()" calls.

Any ideas, no matter how hair-brained, will be greatly appreciated.

Marcelo R. Lopez, Jr.

Todays's quote of the day:
Don't EVER try to do COM by hand, it's like when your mother told you not
to
touch a burner on a stovetop. But you touched it anyway.





Back to top
Jean-Marie Babet
Guest





PostPosted: Fri Jun 18, 2004 7:44 pm    Post subject: Re: double destruction of ActiveForm.... Reply with quote



Hello Marcelo,

If the destructor of a particular instance of an object is being invoked
more than once, specially an instance of ActiveForm, which is not something
that one typically creates many instances of, I would suspect two culprits:

1. Memory corruption
2. Bad codegen

The second item is easier to track down. Put plainly, the compiler messed up
and generated code that results in two calls to the destructor. To track
this down, I would try to find out who's calling the destructor. One
approach would be to hardcode a breakpoint in the destructor and use a
debugger. [You can do that by having call to 'DebugBreak' or, as in the old
days, hardcode the emission of the __emit__(0xcc) ]. The other approach
would be to generate assembly and find references to the destructor. Things
get a little complex with the latter because undoubtedly this destructor
will be virtual, which means the reference to it will probably be in a
vtable - so it won't be clear who's directly calling this method.

Have stack trace from the hardcoded breakpoint might prove useful, specially
if you end up with two different stack traces. If you need help looking at
these, I'll be more than happy to help out and have others here [who are
more CPU window savvy] take a peek also.

The first item is harder to track down. In the past I've used tools [some of
which you mentioned], I've reordered the order of object modules and
libraries - this does not fix the problem, but sometimes it moves the issue
to some other places that may be easier to spot. Or the very fact that the
issue moves somewhere else is often a good hint that we're after a memory
corruption.

On the issue of memory corruption, often switching from debug to non-debug
builds [or vice-versa] will change things also.

I apologize for not providing very concrete steps but this type of problem
is elusive and often requires broad trials before you can narrow down. I can
confirm that I have had plenty of double destructor calls and they often
take a long time to resolve.

Regards,


Bruneau.




"Marcelo R. Lopez, Jr." <mlopez (AT) voicerite (DOT) com> wrote

Quote:
No one has any ideas ??

"Marcelo R. Lopez, Jr." <mlopez (AT) voicerite (DOT) com> wrote in message
news:40cf7a13$1 (AT) newsgroups (DOT) borland.com...
This has been working for almost two years, and suddenly it's not
working
anymore....

I have a set of ActiveLibraries with ActiveForms inside them that I
instrument into my application by instantiating them via
CoClassFactory::CreateInstance()...and then inject inside of panels of
the
main app ( encapsulating by a TOleContainer ).
Just before handling the exit of the application I perform an orderly
shutdown of each of these ActiveLibraries.

The problem is that now, after almost two years of working just fine. I
will
get a circumstance, where ONE of these ActiveLibraries will get it's
ActiveForms destructor called more than once. It only happens to this
one
ActiveForm within one of the ActiveLibraries.

I've tried Memproof, but that doesn't show me enough granularity. There
used
to be SleuthQA, but they're gone now. I've tried the AutomatedQA, but
the
Demo only does so much.

Has any one ever run across a situation where ATL has gotten it's
reference
counts screwy, and tried to forceably destruct an ActiveForm needlessly
(
Notice, it's not calling the release for the ActiveLibrary either ),
it's
calling the ~TActiveForm base class for my form. What's oddest in all of
this...is that I NEVER get my "ActiveFormDestroy" event handler called,
even
though I've got code in there to watchdog it and do some
"OutputDebugString()" calls.

Any ideas, no matter how hair-brained, will be greatly appreciated.

Marcelo R. Lopez, Jr.

Todays's quote of the day:
Don't EVER try to do COM by hand, it's like when your mother told you
not
to
touch a burner on a stovetop. But you touched it anyway.







Back to top
Marcelo R. Lopez, Jr.
Guest





PostPosted: Tue Jun 22, 2004 4:08 pm    Post subject: Re: double destruction of ActiveForm.... Reply with quote

Jean-Marie,

My thoughts exactly...but here's what I discovered. Inside my active
form, I have a button ...a TButton, which I set up in the designer as
being "Enabled = False, Visible = False". If I start up my application,
and let it run, I receive certain notifications which I process, and add
to a TreeView, sounds simple so far, right ?

Well, while I'm processing these notifications, if I receive a
notification of a certain type, I would set the Visible and Enabled
properties of this particular TButton to "True". Well, not only does the
control NOT get displayed, but when I exit, that's when I get this
double-destructor call sequence. I discovered this by
good-old-fashioned, break and step. I kept putting breaks further and
further down the processing chain until I got to this piece of code that
handled "turning the button On or Off".

If I handled the notification in question, fully, with exception of
updating this Button's state, everything was fine. If I let it perform
the Enabled = true; Visible = true; then I would run into problems.

Deleting the button, and creating a different button, didn't make a
difference. I tried so many different combinations it wasn't even funny
! If the button is disabled and invisible to start with, it wouldn't
display, and it would generate this behavior. Another thing I noticed,
and it might be along the lines of your bad code-gen theory is that that
button is the ONLY button that has those two properties set that give me
the problem. I have other buttons that are conditionally shown/enabled
during similar circumstances, and none of those buttons ( or code
surrounding them ) have given me such problems. How can I tell what the
known issues with generating resources exist within BCB ? I looked in
Quality Central and didn't see anything that would remotely indicate a
problem with handling resource creation/destruction.

I continue my research.......

Marcelo


Jean-Marie Babet wrote:

Quote:
Hello Marcelo,

If the destructor of a particular instance of an object is being invoked
more than once, specially an instance of ActiveForm, which is not something
that one typically creates many instances of, I would suspect two culprits:

1. Memory corruption
2. Bad codegen

The second item is easier to track down. Put plainly, the compiler messed up
and generated code that results in two calls to the destructor. To track
this down, I would try to find out who's calling the destructor. One
approach would be to hardcode a breakpoint in the destructor and use a
debugger. [You can do that by having call to 'DebugBreak' or, as in the old
days, hardcode the emission of the __emit__(0xcc) ]. The other approach
would be to generate assembly and find references to the destructor. Things
get a little complex with the latter because undoubtedly this destructor
will be virtual, which means the reference to it will probably be in a
vtable - so it won't be clear who's directly calling this method.

Have stack trace from the hardcoded breakpoint might prove useful, specially
if you end up with two different stack traces. If you need help looking at
these, I'll be more than happy to help out and have others here [who are
more CPU window savvy] take a peek also.

The first item is harder to track down. In the past I've used tools [some of
which you mentioned], I've reordered the order of object modules and
libraries - this does not fix the problem, but sometimes it moves the issue
to some other places that may be easier to spot. Or the very fact that the
issue moves somewhere else is often a good hint that we're after a memory
corruption.

On the issue of memory corruption, often switching from debug to non-debug
builds [or vice-versa] will change things also.

I apologize for not providing very concrete steps but this type of problem
is elusive and often requires broad trials before you can narrow down. I can
confirm that I have had plenty of double destructor calls and they often
take a long time to resolve.

Regards,


Bruneau.




"Marcelo R. Lopez, Jr." <mlopez (AT) voicerite (DOT) com> wrote in message
news:40d31144$1 (AT) newsgroups (DOT) borland.com...


No one has any ideas ??

"Marcelo R. Lopez, Jr." <mlopez (AT) voicerite (DOT) com> wrote in message
news:40cf7a13$1 (AT) newsgroups (DOT) borland.com...


This has been working for almost two years, and suddenly it's not


working


anymore....

I have a set of ActiveLibraries with ActiveForms inside them that I
instrument into my application by instantiating them via
CoClassFactory::CreateInstance()...and then inject inside of panels of


the


main app ( encapsulating by a TOleContainer ).
Just before handling the exit of the application I perform an orderly
shutdown of each of these ActiveLibraries.

The problem is that now, after almost two years of working just fine. I


will


get a circumstance, where ONE of these ActiveLibraries will get it's
ActiveForms destructor called more than once. It only happens to this


one


ActiveForm within one of the ActiveLibraries.

I've tried Memproof, but that doesn't show me enough granularity. There


used


to be SleuthQA, but they're gone now. I've tried the AutomatedQA, but


the


Demo only does so much.

Has any one ever run across a situation where ATL has gotten it's


reference


counts screwy, and tried to forceably destruct an ActiveForm needlessly


(


Notice, it's not calling the release for the ActiveLibrary either ),


it's


calling the ~TActiveForm base class for my form. What's oddest in all of
this...is that I NEVER get my "ActiveFormDestroy" event handler called,


even


though I've got code in there to watchdog it and do some
"OutputDebugString()" calls.

Any ideas, no matter how hair-brained, will be greatly appreciated.

Marcelo R. Lopez, Jr.

Todays's quote of the day:
Don't EVER try to do COM by hand, it's like when your mother told you


not


to


touch a burner on a stovetop. But you touched it anyway.











Back to top
Marcelo R. Lopez, Jr.
Guest





PostPosted: Thu Jun 24, 2004 8:20 pm    Post subject: Re: double destruction of ActiveForm.... Reply with quote

Ok...so here's the scoop...and I think there's definitely some funky
code-gen going on .
The long and the short of it is as follows:

If I set the "Visible" flag of a particular TButton to False in the
designer, and later in my application
try to set it's Visible flag to True.....I get this crash on exit.

If I set it the Visible flag to True in the designer, and later set it's
Visible flag to False ( I was setting it to false in an initialization
interface defined in the Impl object that calls a public method in the
active form to set the property to false ), I get the crash on exit. I
know that the ActiveForm has already gone through it's creation at this
point, because I implemented ActiveFormCreate and stuck a
OutputDebugString(), just to see that it had already been passed through.

If I set the Visible flag to false, and then in the same initialization
interface in the Impl object do the following:

#define WM_MY_DISABLE_XXX WM_USER+1023
TGuiFormImpl::Intiailize(.....)
{
// Other initialization....
::PostMessage( form->Handle, WM_MY_DISABLE_XXX, 0,0 );
}

and implement WndProc for the Activeform:

void __fastcall TGUIForm::WndProc(Messages::TMessage &Message)
{
switch ( Message.Msg ){
case WM_MY_DISABLE_XXX:
{
ButtonCallBack->Enabled = false;
ButtonCallBack->Visible = false;
}
break;
default:
TActiveForm::WndProc(Message);
break;
}
}

THIS, actually works. I can then enable/disable, hide/show the button at
WILL.

Very strange.....as an FYI for anyone who ever runs into a weird
behavior like this. It was VERY tricky to track down. Thanks for your
help Jean-Marie. This is all on BCB6 + Update 4, in case
anyone's curious.

Marcelo
Back to top
Jean-Marie Babet
Guest





PostPosted: Thu Jun 24, 2004 10:32 pm    Post subject: Re: double destruction of ActiveForm.... Reply with quote

Marcelo,

Thanks for the follow-up post.


Quote:
( I was setting it to false in an initialization
interface defined in the Impl object that calls a public method in the
active form to set the property to false )

This is probably not related but due to the Delphi nature of the underlying
objects used by CBuilder sometimes there are timing issues at creation and
destruction time. As long as this initialization interface is not called too
early, I don't think this is the problem. Too early would be, for example,
if the initialization interface is called from a virtual method invoked by
the underlying VCL object. You've probably seen posts here also recommending
that the constructor be used instead of the Create-related events/virtuals
typically invoked by VCL.



Quote:
If I set the Visible flag to false, and then in the same initialization
interface in the Impl object do the following:

....

THIS, actually works. I can then enable/disable, hide/show the button at
WILL.


This definitely points to a timing issue. I'm curious what the stack trace
looked like in the previous setup.

But again, thanks for the post and happy to hear to have a resolution.

Regards,


Bruneau.



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.