I have a unit which has a variable of TComponent, I create this component on Initialization of the unit like following :
var
XComp: TComponent;
.
.
.
.
initialization
begin
XCom := TComponent.Create(Application);
end;
after installing the unit when I close Delphi it gives me an Access Violation error message (EAccessViolation)
but when I changed my creator to be as following
initialization
begin
XCom := TComponent.Create(nil);
end;
everything went fine...I would like to know the difference? and what is the better?
note : the error only appears when closing the delphi (means at design time).
Thanks.
When you use
XCom := TComponent.Create(Application);
you make Application the owner of XCom. When the application is terminating it will take care of destroying XCom, since it is the owner.
When you do
XCom := TComponent.Create(nil);
nobody is owner of XCom and you have to free it yourself when the application terminates.
You probably got the exception because you manually freed XCom and then Application tried to free XCom as well.
Basically both are allowed and it should not result in an AV even if you have code like this:
MyComp := TMyComp.Create(Application);
try
{...}
finally
MyComp.Free;
end;
This is because a properly coded component will remove itself from its owner's components list when it is being destroyed.
I think the problem here might be that the component was already freed by the application object and later on some code tries to access it. Maybe there is a finalize section in your code, that does it? Or you might have mixed objects and interfaces and reference counting got you.
To debug your problem, you could run the IDE in the debugger by setting your package's "host application" to Delphi (C:\Program Files\\BDS\\Bin\bds.exe). and set a breakpoint in your component's destructor. That way you will find out where it is being freed and also where the AV occurs.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With