* macrotab.c -Werror
@ 2002-05-13 16:35 Andrew Cagney
2002-05-13 17:28 ` Daniel Berlin
0 siblings, 1 reply; 5+ messages in thread
From: Andrew Cagney @ 2002-05-13 16:35 UTC (permalink / raw)
To: Jim blandy, gdb-patches
[second attempt at posting]
Jim,
FYI, I'm seeing:
gdb/macrotab.c:504: warning: `best_depth' might be used uninitialized in
this function
gmake: *** [macrotab.o] Error 1
for the code:
/* It's not us. Try all our children, and return the lowest. */
{
struct macro_source_file *child;
struct macro_source_file *best = 0;
int best_depth;
for (child = source->includes; child; child = child->next_included)
{
struct macro_source_file *result
= macro_lookup_inclusion (child, name);
if (result)
{
int result_depth = inclusion_depth (result);
if (! best || result_depth < best_depth) <-- HERE
{
best = result;
best_depth = result_depth;
}
}
}
return best;
}
enjoy,
Andrew
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: macrotab.c -Werror
2002-05-13 16:35 macrotab.c -Werror Andrew Cagney
@ 2002-05-13 17:28 ` Daniel Berlin
2002-05-14 12:55 ` Jim Blandy
0 siblings, 1 reply; 5+ messages in thread
From: Daniel Berlin @ 2002-05-13 17:28 UTC (permalink / raw)
To: Andrew Cagney; +Cc: Jim blandy, gdb-patches
On Mon, 13 May 2002, Andrew Cagney wrote:
> [second attempt at posting]
>
> Jim,
>
> FYI, I'm seeing:
>
> gdb/macrotab.c:504: warning: `best_depth' might be used uninitialized in
> this function
> gmake: *** [macrotab.o] Error 1
>
> for the code:
>
> /* It's not us. Try all our children, and return the lowest. */
> {
> struct macro_source_file *child;
> struct macro_source_file *best = 0;
> int best_depth;
>
> for (child = source->includes; child; child = child->next_included)
> {
> struct macro_source_file *result
> = macro_lookup_inclusion (child, name);
>
> if (result)
> {
> int result_depth = inclusion_depth (result);
>
> if (! best || result_depth < best_depth) <-- HERE
It's an obvious false positive (!best will be true the first time through,
meaning the only time we check best_depth, it's already been set at
least once).
Here, you can't just initialize best_depth to 0, you have to initialize it
to either INT_MAX, or inclusion_depth (result).
Sucks.
--Dan
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: macrotab.c -Werror
2002-05-13 17:28 ` Daniel Berlin
@ 2002-05-14 12:55 ` Jim Blandy
2002-05-14 13:27 ` Andrew Cagney
2002-05-14 13:50 ` Daniel Berlin
0 siblings, 2 replies; 5+ messages in thread
From: Jim Blandy @ 2002-05-14 12:55 UTC (permalink / raw)
To: Daniel Berlin; +Cc: Andrew Cagney, gdb-patches
Daniel Berlin <dberlin@dberlin.org> writes:
> It's an obvious false positive (!best will be true the first time through,
> meaning the only time we check best_depth, it's already been set at
> least once).
>
> Here, you can't just initialize best_depth to 0, you have to initialize it
> to either INT_MAX, or inclusion_depth (result).
>
> Sucks.
You're going too fast. Here's the whole loop, for the sake of
discussion:
/* It's not us. Try all our children, and return the lowest. */
{
struct macro_source_file *child;
struct macro_source_file *best = 0;
int best_depth;
for (child = source->includes; child; child = child->next_included)
{
struct macro_source_file *result
= macro_lookup_inclusion (child, name);
if (result)
{
int result_depth = inclusion_depth (result);
if (! best || result_depth < best_depth)
{
best = result;
best_depth = result_depth;
}
}
}
The only reference to `best_depth''s value is in the right operand of
`||'. That operand will never be evaluated unless `best' is non-zero.
But `best' is initially zero, and is only assigned along with
`best_depth'. So `best_depth''s initial value is never used. This
means:
- the original code is correct (although the compiler doesn't figure
that out), and
- you can initialize it to anything you want, since its initial value
is never used.
I don't actually know how many unnecessary initializations there are
in GDB to silence the compiler, but it's my impression that the
compiler's false positive rate for `var might be used uninitialized'
warnings is low enough that it's still a useful sanity check. So I'm
happy to add a few unnecessary initializations.
What sucks (a bit) is that every one of those unnecessary
initializations does end up generating code --- if the compiler could
tell it was unnecessary, it wouldn't have printed the warning!
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: macrotab.c -Werror
2002-05-14 12:55 ` Jim Blandy
@ 2002-05-14 13:27 ` Andrew Cagney
2002-05-14 13:50 ` Daniel Berlin
1 sibling, 0 replies; 5+ messages in thread
From: Andrew Cagney @ 2002-05-14 13:27 UTC (permalink / raw)
To: Jim Blandy; +Cc: Daniel Berlin, gdb-patches
> I don't actually know how many unnecessary initializations there are
> in GDB to silence the compiler, but it's my impression that the
> compiler's false positive rate for `var might be used uninitialized'
> warnings is low enough that it's still a useful sanity check.
See http://sources.redhat.com/gdb/onlinedocs/gdbint_13.html#SEC104
When fixing the original warnings (few were present) a significant
number of those really were bugs. Look for Wuninitialized in the
ChangeLogs.
enjoy,
Andrew
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: macrotab.c -Werror
2002-05-14 12:55 ` Jim Blandy
2002-05-14 13:27 ` Andrew Cagney
@ 2002-05-14 13:50 ` Daniel Berlin
1 sibling, 0 replies; 5+ messages in thread
From: Daniel Berlin @ 2002-05-14 13:50 UTC (permalink / raw)
To: Jim Blandy; +Cc: Andrew Cagney, gdb-patches
On 14 May 2002, Jim Blandy wrote:
>
> Daniel Berlin <dberlin@dberlin.org> writes:
> > It's an obvious false positive (!best will be true the first time through,
> > meaning the only time we check best_depth, it's already been set at
> > least once).
> >
> > Here, you can't just initialize best_depth to 0, you have to initialize it
> > to either INT_MAX, or inclusion_depth (result).
> >
> > Sucks.
>
> You're going too fast. Here's the whole loop, for the sake of
> discussion:
>
> /* It's not us. Try all our children, and return the lowest. */
> {
> struct macro_source_file *child;
> struct macro_source_file *best = 0;
> int best_depth;
>
> for (child = source->includes; child; child = child->next_included)
> {
> struct macro_source_file *result
> = macro_lookup_inclusion (child, name);
>
> if (result)
> {
> int result_depth = inclusion_depth (result);
>
> if (! best || result_depth < best_depth)
> {
> best = result;
> best_depth = result_depth;
> }
> }
> }
>
As the third person to point this out, you can be sure i'm aware that the
!best short circuits it.
In fact, i realized it 5 seconds after the email.
> The only reference to `best_depth''s value is in the right operand of
> `||'. That operand will never be evaluated unless `best' is non-zero.
> But `best' is initially zero, and is only assigned along with
> `best_depth'. So `best_depth''s initial value is never used. This
> means:
> - the original code is correct (although the compiler doesn't figure
> that out), and
> - you can initialize it to anything you want, since its initial value
> is never used.
However, it's a bad idea, since with the current unnecessary
initialization, someone could think they could eliminate !best, since
doing so
A. won't cause a warning
B. probably wouldn't cause any very easily noticeable problems (unless we
have tests that fail if it picks the wrong macro depth).
You could also eliminate the !best altogether, by initializing best_depth
to INT_MAX.
>
> I don't actually know how many unnecessary initializations there are
> in GDB to silence the compiler, but it's my impression that the
> compiler's false positive rate for `var might be used uninitialized'
> warnings is low enough that it's still a useful sanity check. So I'm
> happy to add a few unnecessary initializations.
>
> What sucks (a bit) is that every one of those unnecessary
> initializations does end up generating code --- if the compiler could
> tell it was unnecessary, it wouldn't have printed the warning!
Actually, this isn't true necessarily for gcc, but it's offtopic.
Suffice to say:
/buildspace/cfg-branch/gcc/cc1 -O2 test.c -da -fverbose-asm -Wall -fnew-unroll-loops
test.c: In function `main':
test.c:16: warning: control reaches end of non-void function
[dberlin@dberlin gcc]$ /buildspace/cfg-branch/gcc/cc1 -O2 test.c -da -fverbose-asm -Wall
main
test.c: In function `main':
test.c:16: warning: control reaches end of non-void function
test.c:4: warning: `best_depth' might be used uninitialized in this
function
We don't actually eliminate it by unrolling the loop, but we won't get
the warning.
I can show cases that do the other case as well (we do eliminate it, but
get the warning).
But, the fact that we can't currently eliminate it on the mainline
is yet another reason to initialize best_depth to INT_MAX and remove the !best;
It removes a branch.
In fact, it generates code without *any* branches on a p2/p4
(-march/-mcpu=pentiumpro+).
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2002-05-14 20:50 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2002-05-13 16:35 macrotab.c -Werror Andrew Cagney
2002-05-13 17:28 ` Daniel Berlin
2002-05-14 12:55 ` Jim Blandy
2002-05-14 13:27 ` Andrew Cagney
2002-05-14 13:50 ` Daniel Berlin
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox