pcg@cs.aber.ac.uk (Piercarlo Grandi) (06/29/90)
In article <31208@cup.portal.com> wmmiller@cup.portal.com (William Michael Miller) writes: If allowed, "static" in the definition would mean that the member had internal linkage, which contradicts the statement in the ARM, section 9.4, that "static members of a global class have external linkage." Ahh, but consts have internal linkage unless _explicitly_ specified extern. Which rule prevails? The correct rule for static members (data and functions) is to put the "static" modifier in the class declaration and omit it in the definition. This would be wonderful... But where is it said that a storage class specifier is illegal in the definition of a static class member? The following snippet of code compiles without errors whatsoever under g++ 1.36.x: struct s { static v; static const c; static f(); }; static s::v = 1; // external static const s::c = 2; // external static s::f() { return; } // internal struct b { static v; static const c; }; static b::v; // external static const b::c; // external BSS struct e { static v; static const c; static f(); }; extern e::v = 1; // external extern const e::c = 2; // external extern e::f() { return; } // external struct t { static v; static const c; static f(); }; typedef t::v; // external, typedef ignored typedef const t::c; // external BSS, typedef ignored typedef t::f(); // oh my... completely ignored And the generated code is (slightly compactified): #NO_APP gcc_compiled.: .globl _s$v; .data; .even;_s$v: .long 1 .text; .even; f__1s: link a6,#0; jra L1; L1: unlk a6; rts .globl _e$v; .data; .even;_e$v: .long 1 .text; .even; .globl _f__1e; f__1e: link a6,#0; jra L2; L2: unlk a6; rts .comm _t$c,4 .comm _t$v,4 .globl _e$c; .even;_e$c: .long 2 .comm _b$c,4 .comm _b$v,4 .globl _s$c; .even;_s$c: .long 2 There is clearly some problem here with G++ 1.36.x, but would anyone care to explain to Michael Tiemann what should be done here? Quoting chapter and verse of some reliable (time stamped, given the torrid pace of C++ evolution) source? Note that I have my own ideas about all this mess; just like all the confusion about member pointers is caused by the useless notion of member function, and that around MI is caused by the erroneous notion of prefixing, all the trouble here is caused by the lack of a notion of class objec, or the unresolved tension between class-as-module and class-as-object-template. In other words, to clarify C++ in a consistent way, you have to jettison or restructure some of its most critical areas... -- Piercarlo "Peter" Grandi | ARPA: pcg%cs.aber.ac.uk@nsfnet-relay.ac.uk Dept of CS, UCW Aberystwyth | UUCP: ...!mcsun!ukc!aber-cs!pcg Penglais, Aberystwyth SY23 3BZ, UK | INET: pcg@cs.aber.ac.uk
wmmiller@cup.portal.com (William Michael Miller) (07/01/90)
pcg@cs.aber.ac.uk (Piercarlo Grandi) writes: > Ahh, but consts have internal linkage unless _explicitly_ specified > extern. Which rule prevails? There's no conflict. The rule to which you refer states: "A name of file scope that is explicitly declared const and not explicitly declared extern is local to its file" (ARM 3.3). Const class members do not have file scope. > This would be wonderful... But where is it said that a storage class > specifier is illegal in the definition of a static class member? It's not as explicit as one might like, and I expect that X3J16 may want to add some wording to the description here. It is implicit, however, in a comparison of sections 3.3, 7.1.1, and 9.4 of the ARM. 3.3 and 9.4 say that a name declared in a class as static has external linkage. 3.3 and 7.1.1 say that a name at file scope specified static has internal linkage. 7.1.1 says that all linkage specifications for a name must agree and gives examples where it is illegal to specify a name as static once it has already received, even implicitly, external linkage. (Rereading these two comments back-to-back make it evident that the terminology in the ARM needs to be tightened up: const class members don't have file scope because they're declared inside a class; however, static class members *must* be defined at file scope. Perhaps concepts like "introducing declaration" and "defining declaration" should be used.) > Note that I have my own ideas about all this mess; just like all the > confusion about member pointers is caused by the useless notion of > member function, and that around MI is caused by the erroneous notion of > prefixing, all the trouble here is caused by the lack of a notion of > class objec, or the unresolved tension between class-as-module and > class-as-object-template. You seem to find a lot of problems that don't particularly seem like problems to me. C++ is clearly not the most elegant, concise, and formally pure language conceivable, but I don't think it's as fundamentally flawed as you do. ------------------------------------------------------------------------------ William M. Miller, Glockenspiel, Inc.; P. O. Box 366, Sudbury, MA 01776-0003 wmmiller@cup.portal.com BIX: wmiller CI$: 72105,1744