This is the mail archive of the
ecos-discuss@sourceware.org
mailing list for the eCos project.
Re: Re: Usefulness of CYGFUN_INFRA_EMPTY_DELETE_FUNCTIONS
"Christopher Cordahi" <christopher.cordahi@gmail.com> writes:
> On 07/02/07, Sergei Organov <osv@javad.com> wrote:
>> "Christopher Cordahi" <christopher.cordahi@gmail.com> writes:
>> > On 06/02/07, Andrew Lunn <andrew@lunn.ch> wrote:
>>
>> [...]
>>
>> > I created and destroyed a C++ object with a virtual destructor that
>> > was on the stack and the the free function wasn't included in the
>> > object code since there wasn't any dynamic memory.
>>
>> Depending on GCC version, it could be not enough to just have one virtual
>> destructor, -- you may need to have inheritance to see the problem, e.g.:
>>
>> struct A {
>> virtual ~A();
>> };
>>
>> struct B: public A {
>> virtual ~B();
>> };
>>
>> A::~A() {}
>> B::~B() {}
>
> That's basically what I had, I included printfs in the constructor and
> destructor to watch what was being constructed and destructed in
> my tests.
>
>> When I compile this file to assembly, I see a call to __builtin_delete
>> using old versions of GCC (2.95.x), and calls to an external symbol
>> _ZdlPv using newer version of GCC :(
>
> I don't understand your use of :(.
> Are you confirming that the option doesn't work as expected?
It meant "unfortunately", as I thought that existence of those calls
actually results in fetching unnecessary routines from libraries, thus
justifying the existence of the eCos option.
>>From what I see there are 3 destructors for the same object,
> and different ones are called for different situations and if the
> destructor is never called via the delete operator, the one with a
> call to delete is not linked in.
Well, with the 2.95 GCC for ARM, when I compile the code:
class A
{
public:
virtual ~A();
int a;
};
class B: public A
{
public:
virtual ~B();
int b;
};
A::~A() {}
B::~B() {}
int foo()
{
B b;
return b.b;
}
I get the assembly where foo() calls _._1B that in turn calls _._1A that
in turn calls __builtin_delete.
With newer GCC it seems that the generated code indeed doesn't call the
destructor that contains reference to external _ZdlPv, and then your
observations are right.
I have no idea when exactly GCC changed its behavior in this field, but
it seems that those eCos option is only required for older GCC.
For reference, here is the assembly got with GCC 2.95.2 that does
reference __builtin_delete:
.gcc2_compiled.:
.text
.align 2
.global _._1A
.type _._1A,function
_._1A:
@ args = 0, pretend = 0, frame = 0
@ frame_needed = 1, current_function_anonymous_args = 0
mov ip, sp
stmfd sp!, {fp, ip, lr, pc}
sub fp, ip, #4
ldr r3, .L6
tst r1, #1
str r3, [r0, #4]
ldmeqea fp, {fp, sp, pc}
bl __builtin_delete
ldmea fp, {fp, sp, pc}
.L7:
.align 2
.L6:
.word _vt.1A
.Lfe1:
.size _._1A,.Lfe1-_._1A
.align 2
.global _._1B
.type _._1B,function
_._1B:
@ args = 0, pretend = 0, frame = 0
@ frame_needed = 1, current_function_anonymous_args = 0
mov ip, sp
stmfd sp!, {fp, ip, lr, pc}
ldr r3, .L10
sub fp, ip, #4
str r3, [r0, #4]
bl _._1A
ldmea fp, {fp, sp, pc}
.L11:
.align 2
.L10:
.word _vt.1B
.Lfe2:
.size _._1B,.Lfe2-_._1B
.align 2
.global foo__Fv
.type foo__Fv,function
foo__Fv:
@ args = 0, pretend = 0, frame = 12
@ frame_needed = 1, current_function_anonymous_args = 0
mov ip, sp
stmfd sp!, {r4, fp, ip, lr, pc}
sub fp, ip, #4
sub r3, fp, #28
mov r0, r3
ldr r2, .L24
sub sp, sp, #12
str r2, [r3, #4]
mov r1, #2
ldr r4, [fp, #-20]
bl _._1B
mov r0, r4
b .L23
.L25:
.align 2
.L24:
.word _vt.1B
.L23:
ldmea fp, {r4, fp, sp, pc}
.Lfe3:
.size foo__Fv,.Lfe3-foo__Fv
.weak _vt.1B
.section .gnu.linkonce.d._vt.1B,"aw"
.align 2
.type _vt.1B,object
.size _vt.1B,24
_vt.1B:
.short 0
.short 0
.word 0
.short 0
.short 0
.word _._1B
.space 8
.weak _vt.1A
.section .gnu.linkonce.d._vt.1A,"aw"
.align 2
.type _vt.1A,object
.size _vt.1A,24
_vt.1A:
.short 0
.short 0
.word 0
.short 0
.short 0
.word _._1A
.space 8
-- Sergei.
--
Before posting, please read the FAQ: http://ecos.sourceware.org/fom/ecos
and search the list archive: http://ecos.sourceware.org/ml/ecos-discuss