Re: More proof of errors going uncorrected among the "regs"

Discussion in 'C Programming' started by Eric Sosman, Feb 20, 2009.

  1. Eric Sosman

    Eric Sosman Guest

    pete wrote:
    > Han from China wrote:
    >>
    >> Defect Report #016
    >> Submission Date: 10 Dec 92 Submittor: WG14 Source: X3J11/90-052 (Sam
    >> Kendall) Question 1 I can find no prohibition of the following
    >> translation unit: struct foo x;
    >> struct foo { int i; }; What I was looking for, but didn't find,
    >> was a statement that an implicitly initialized declaration of an object
    >> with static storage duration must have object type. Is this
    >> translation unit legal? Response The translation unit cited is valid.
    >> It falls into the same category of construct as int array[];

    >
    > I would have recognized that as a valid example
    > of a declaration of an object with incomplete type.


    No. The first mention is a tentative definition, and the
    second mention combines with it to complete the type. 6.9.2p2:

    A declaration of an identifier for an object that has
    file scope without an initializer, and without a
    storage-class specifier or with the storage-class
    specifier static, constitutes a /tentative definition/.
    If a translation unit contains one or more tentative
    definitions for an identifier, and the translation unit
    contains no external definition for that identifier,
    then the behavior is exactly as if the translation unit
    contains a file scope declaration of that identifier,
    *with the composite type* [emphasis mine] as of the end
    of the translation unit, with an initializer equal to 0.

    So in the DR's fragment, `x' identifies a defined object
    of the complete type `struct foo'.

    --
    Eric Sosman
    lid
    Eric Sosman, Feb 20, 2009
    #1
    1. Advertising

  2. Eric Sosman

    Eric Sosman Guest

    pete wrote:
    >
    > I meant that I would have recognized
    > int array[];
    > as a valid example
    > of a declaration of an object with incomplete type.
    >
    > I've worked with code that had an array declared like that.
    > The object was defined in another translation unit.


    This is one of those areas of the language where my
    footing is a little uncertain, but I think that a translation
    unit containing `int array[];' at file scope and with no
    further declaration of `array' is in error, and a diagnostic
    is required.

    `extern int array[];' is a different matter, and perfectly
    legal.

    --
    Eric Sosman
    lid
    Eric Sosman, Feb 21, 2009
    #2
    1. Advertising

  3. Eric Sosman

    Tim Rentsch Guest

    Eric Sosman <> writes:

    > pete wrote:
    > >
    > > I meant that I would have recognized
    > > int array[];
    > > as a valid example
    > > of a declaration of an object with incomplete type.
    > >
    > > I've worked with code that had an array declared like that.
    > > The object was defined in another translation unit.

    >
    > This is one of those areas of the language where my
    > footing is a little uncertain, but I think that a translation
    > unit containing `int array[];' at file scope and with no
    > further declaration of `array' is in error, and a diagnostic
    > is required.


    I think not. For 'static int array[];', yes. Without the
    static, there is the example in 6.9.2 p 5:

    EXAMPLE 2 If at the end of the translation unit containing

    int i[];

    the array i still has incomplete type, the implicit initializer causes
    it to have one element, which is set to zero on program startup.
    Tim Rentsch, Feb 21, 2009
    #3
  4. Eric Sosman

    Eric Sosman Guest

    Tim Rentsch wrote:
    > Eric Sosman <> writes:
    >
    >> pete wrote:
    >>> I meant that I would have recognized
    >>> int array[];
    >>> as a valid example
    >>> of a declaration of an object with incomplete type.
    >>>
    >>> I've worked with code that had an array declared like that.
    >>> The object was defined in another translation unit.

    >> This is one of those areas of the language where my
    >> footing is a little uncertain, but I think that a translation
    >> unit containing `int array[];' at file scope and with no
    >> further declaration of `array' is in error, and a diagnostic
    >> is required.

    >
    > I think not. For 'static int array[];', yes. Without the
    > static, there is the example in 6.9.2 p 5:
    >
    > EXAMPLE 2 If at the end of the translation unit containing
    >
    > int i[];
    >
    > the array i still has incomplete type, the implicit initializer causes
    > it to have one element, which is set to zero on program startup.


    Hmm. Well, as I said, "This is one of those areas of the
    language where my footing is a little uncertain." Looks like
    it was a good thing I said so ...

    --



    --
    Eric Sosman
    lid
    Eric Sosman, Feb 21, 2009
    #4
  5. Eric Sosman

    Tim Rentsch Guest

    Eric Sosman <> writes:

    > Tim Rentsch wrote:
    > > Eric Sosman <> writes:
    > >
    > >> pete wrote:
    > >>> I meant that I would have recognized
    > >>> int array[];
    > >>> as a valid example
    > >>> of a declaration of an object with incomplete type.
    > >>>
    > >>> I've worked with code that had an array declared like that.
    > >>> The object was defined in another translation unit.
    > >> This is one of those areas of the language where my
    > >> footing is a little uncertain, but I think that a translation
    > >> unit containing `int array[];' at file scope and with no
    > >> further declaration of `array' is in error, and a diagnostic
    > >> is required.

    > >
    > > I think not. For 'static int array[];', yes. Without the
    > > static, there is the example in 6.9.2 p 5:
    > >
    > > EXAMPLE 2 If at the end of the translation unit containing
    > >
    > > int i[];
    > >
    > > the array i still has incomplete type, the implicit initializer causes
    > > it to have one element, which is set to zero on program startup.

    >
    > Hmm. Well, as I said, "This is one of those areas of the
    > language where my footing is a little uncertain." Looks like
    > it was a good thing I said so ...


    To my way of thinking, this rule fits with tentative
    definitions in general -- declare the variable early, then
    define it late, and the definition can take advantage of
    other variables declared/defined in the meantime. The thing
    with the implicit initializer causing the number of elements
    to be one is a little funny, but other than that it all
    makes sense.

    What I find odd, or sometimes irritating, is that the rule
    for static variables (ie, variables with internal linkage)
    is different. This discrepancy is one of those edge cases
    that C would benefit from having cleared up, IMOBIHOO.*


    [*] In my opinion, be it humble or otherwise
    Tim Rentsch, Feb 21, 2009
    #5
  6. Eric Sosman

    Tim Rentsch Guest

    Han from China <> writes:

    > Tim Rentsch wrote:
    > > The thing with the implicit initializer causing the number of elements
    > > to be one is a little funny, but other than that it all makes sense.

    >
    > It's odd at first but follows naturally from a few facts:
    >
    > 1. int array[] is the composite type as of the end of the translation
    > unit.
    > 2. Therefore, the behavior is as if int array[] had been declared
    > "with an initializer equal to 0." (6.9.2{2})
    > 3. The initializer for such an array is a "brace-enclosed list of
    > initializers." (6.7.8{16})
    > 4. But the grammar itself (6.7.8{1}) reveals that
    >
    > initializer: { initializer-list }
    > \
    > |
    > v
    > initializer: assignment-expression
    >
    > In other words, what's *between* the braces is the initializer
    > proper. It's assignment-expression that should be equal to 0 for
    > the default initializer.
    > 5. Therefore, an initializer equal to 0, for this array, means
    > {0}, though the reasoning is kind of backward -- you have your
    > assignment-expression initializer equal to 0, but 6.7.8{16}
    > means you have to slap on some braces to yield the full
    > initializer.
    > 6. Therefore, the tentative definition is resolved as if it had
    > been int array[] = {0};


    Oh, I understand why it happens. It's just one of those weird
    results that C has, like a == i[a], that -- even though they
    make sense after they're explained -- are at first not immediately
    apparent, and so come as something of a surprise.

    By contrast, 'int a[];' being legal follows pretty naturally once
    one has seen the pattern of 'int x; ... int x = 4;', just like
    function prototypes precede function defintions; 'int a[];' can
    be seen as a "variable prototype", and in fact I first heard that
    term used by other developers. The point of my earlier comment is
    only that allowing the partial declaration isn't that surprising,
    whereas what happens if there is no subsequent definition is more
    of an odd consequence than an expectable (or useful) result.
    Tim Rentsch, Feb 24, 2009
    #6
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Karl Core

    Any regs up for a CSS challenge

    Karl Core, Feb 20, 2005, in forum: HTML
    Replies:
    2
    Views:
    408
    Augustus
    Feb 21, 2005
  2. what are REGS,SREGS ?

    , Oct 5, 2005, in forum: C Programming
    Replies:
    5
    Views:
    686
    Alexei A. Frounze
    Oct 6, 2005
  3. Rod Pemberton

    RE: union REGS don't get DOS Version

    Rod Pemberton, Feb 8, 2006, in forum: C Programming
    Replies:
    1
    Views:
    496
    Bruno Barros
    Feb 9, 2006
  4. Marcpp
    Replies:
    1
    Views:
    269
    Jorgen Bodde
    Jun 12, 2007
  5. Ben Bacarisse
    Replies:
    5
    Views:
    333
Loading...

Share This Page