3

Consider the code:

int main(void)
{
    int a;
}

As far as I know, int a; is a definition, as it causes storage to be reserved. Citing the C standard (N1570 Committee Draft — April 12, 2011):

6.7/5 Semantics A declaration specifies the interpretation and attributes of a set of identifiers. A definition of an identifier is a declaration for that identifier that:

— for an object, causes storage to be reserved for that object;

...

Here comes the question: the compiler may optimize away the storage, since we are not using the variable. Is then int a; a declaration then? And what if we do a printf("%p", &a) in main(void) - certainly now the compiler has to allocate storage, so is the concept of declaration/definition dependent on whether you later use the identifier or not?

vsoftco
  • 55,410
  • 12
  • 139
  • 252
  • A definition is always a definition, even if not used (and even when the compilers doesn't actually emit code or reserves space for it). – Some programmer dude Oct 16 '15 at 05:17
  • @JoachimPileborg Well the standard is a bit ambiguous, it certainly says: *causes storage to be reserved...*. And then throughout the standard the term is used interchangeably, e.g. they call `int* p;` a *declaration*. The whole discussion started [here](http://stackoverflow.com/a/33159989/3093378) – vsoftco Oct 16 '15 at 05:19
  • Possible duplicate of [What is the difference between a definition and a declaration?](http://stackoverflow.com/questions/1410563/what-is-the-difference-between-a-definition-and-a-declaration) – Rahul Tripathi Oct 16 '15 at 05:21
  • @RahulTripathi No it's not a dupe, I would like an answer according to the standard, that's why the language-lawyer tag also. – vsoftco Oct 16 '15 at 05:21

4 Answers4

5

The text you quoted from 6.7/5 is actually meant to be interpreted the other way around than what you have done: the text is saying that definitions cause storage to be allocated.

The text which specifies that int a; is a definition is elsewhere.

C is defined in terms of an abstract machine. There is storage allocated in the abstract machine. Whether or not any memory is allocated on your PC is unrelated.

M.M
  • 138,810
  • 21
  • 208
  • 365
  • The thing that confused me is the fact that they refer to e.g. `const int *ptr_to_constant;` as a *declaration*, see 6.7.6.1/3 (page 130 of the document I linked). And technically it's correct, since a definition can also be a declaration... – vsoftco Oct 16 '15 at 05:32
  • @vsoftco All definitions are declarations so that terminology is correct (although perhaps misleading) – M.M Oct 16 '15 at 05:33
  • Yeah that's what's going on probably. But the abstract machine is certainly the right way of thinking about it. But what about `int f(); main(){} int f(){return 0;}` Isn't the `int f(){return 0;}` only a definition? Or you are talking about variables? – vsoftco Oct 16 '15 at 05:33
  • @vsoftco, no this are also a declaration of the functions `main` and `f`, but declarations without "prototype". – Jens Gustedt Oct 16 '15 at 09:46
2

Is then int a; a declaration then?

Yes.

In fact, every definition is also a declaration. A variable can have only one definition, but could have multiple declarations.

Yu Hao
  • 119,891
  • 44
  • 235
  • 294
2
int a;

This is a definition There is a memory allocated for variable a

extern int a;

This is a declaration. Memory is not allocated because it is not defined.

Once a variable is defined you can use the address of it which is totally legal.

Gopi
  • 19,784
  • 4
  • 24
  • 36
0

A declaration introduces an identifier and describes its type, be it a type, object, or function. A declaration is what the compiler needs to accept references to that identifier. These are declarations:

extern int bar;
extern int g(int, int);

A definition actually instantiates/implements this identifier. It's what the linker needs in order to link references to those entities. These are definitions corresponding to the above declarations:

int bar;
int g(int lhs, int rhs) {return lhs*rhs;}