This is the mail archive of the gcc@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Re: patch to supress trailing missing initializer warnings


| 	struct A { char const *name; ...; int v1;};
| In a static table of these things, I have to init v1 to zero, to remove
| the warning.
| 	static A thing = {"wibble", ..., 0};
| Now, I find I need to add v2, for the same kind of thing. With my patch,
| I don't have to change the definition of thing, it already has a
| trailing zero init. With Carlo's suggestion I must add another zero.
| 
| Now iterate this a few times and you've got v1 ... v6. Each time a new
| one was added, all the the inititializers needed amending under Carlo's
| scheme. But the final result could be ok as the original initializer
| which just did v1. Later reading of the code might confuse one as to why
| you've explicitly inited all the trailing values to zero.

Apart from it being a very rare case, I still think that would be the
desired behaviour: Everytime you add ONE variable, it would be a risk
to assume that this new value needs to be initialized by zero too (or
that it isn't inserted in the middle and you simply forgot to initialize
it).

| Carlo's example in another email about an array initializer is not
| addressed by this warning or patch, and hence not relevant to this
| discussion (the check is only for class member initialization).

Then I think the patch should be extended to also have effect on
array initializers; There is no difference, the same arguments hold
of course.

| I also believe your analysis of the problem to be incomplete. Let me try
| you with this one,
| 
| Case A - no detection at all (i.e. warning is disabled)
| Case B - the way egcs is now (i.e. warn about every uninited member)
| Case C - the patch behaviour when it's not in mode B (warn if last is
| not NULL)
| Case D - Carlo's proposal.
| 
| For any particular warning there can be false positives (spuirious
| warnings) and false negatives (missed warnings). Obviously we want to
| minimize these. However, it is my contention that we want to work really
| hard minimizing the false positives. Hence 1 false positive is
| equivalent to more than one false negative.

Absolutely not!  A missed warning in the discussed case is almost ALWAYS
an error.  While the "spuirious warnings" can easily be gotten rid of
by adding one or two zero's to the initializer list!  I am sure that
I much rather want to get those warnings!

| Here's a little figure to show what I think the relative behavious of
| the schemes are. Each column is a particular code case. The columns are
| not equally weighted
| 	         1234567
| 	ideal    nnnnppp
| 	Case A   nnnnNNN
| 	Case B   nPPPppp
| 	Case C   nnnPNNp
| 	Case D   nnPPNpp
| 
| N == false Negative, P = false positive, n = negative, p = positive
| 
| The figure shows that case B gives the most false positives, but catches
| all the true positive (I don't think it can give a false negative). Case
| C gives the least false positives, but does give more false negatives
| than case D. Now are enough cases in column 6 to outweigh the annoyance
| of cases in column 3? If so we should use method D, if not the method C.

The advantage of case D or case C sits in column 6: It catches errors
where the programmer forgot one initializer.  In the case he is too lazy
to add that extra single zero to the end of the initializer list, he
will get a warning that he can get ONLY rid of by either turning off
all warnings (case A) or by adding that zero.  I think that the advantage
of catching the missed warning in column 6 out weights the annoyance
of having to add that zero (not of getting that warning, warnings are
always very annoying).

| The only hard evidence I have is my particular circumstance, where it is
| very much the case that column 6 has negligible size and column 3 does
| not.

In the case that you keep adding variables, then you could at one moment
decide to *remove* initializers instead of adding a zero.  That would
be a clear and not to be misunderstood action.  Ie, going from:

struct A { int v1, v2, v3 } = { 0, 0, 0 };

to

struct A { int v1, v2, v3, v4 } = { 0 };

is not likely an error.

While going to 

struct A { int v1, v2, v3, v4 } =  { 0, 0, 0 };

*is* likely an error imho.

| probably a far too long an analysis of such a minor issue! Oh well, I've
| written it now.
| 
| nathan
| -- 
| Dr Nathan Sidwell :: Computer Science Department :: Bristol University
|       You can up the bandwidth, but you can't up the speed of light      
| nathan@acm.org  http://www.cs.bris.ac.uk/~nathan/  nathan@cs.bris.ac.uk

-- 
 Carlo Wood  <carlo@runaway.xs4all.nl>


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]