[cfe-dev] [PATCH]: Parsing for C++ classes
Argiris Kirtzidis
akyrtzi at gmail.com
Sat Jun 21 08:23:00 PDT 2008
Eli Friedman wrote:
> A couple more potential issues that I found while re-reading the patch:
> + bool isInstField = (DS.getStorageClassSpec() ==
> DeclSpec::SCS_unspecified &&
> + !DeclaratorInfo.isFunctionDeclarator());
>
> This check isn't reliable. Simple example: "typedef int func(); class
> C {func a,b;};".
>
Ah, good find!
How about adding a Action::isFunctionTypeDeclarator for the parser to
get this kind of information:
> // typedef int func();
> // class C {func a,b;};
> bool isTypedefFunc = (!DeclaratorInfo.isFunctionDeclarator() &&
>
> Actions.isFunctionTypeDeclarator(DeclaratorInfo, CurScope));
> bool isInstField = (DS.getStorageClassSpec() ==
> DeclSpec::SCS_unspecified &&
> !DeclaratorInfo.isFunctionDeclarator() &&
> !isTypedefFunc);
Do you have some other suggestion ?
> + typedef std::list<LexedInlineMethod> LexedInlineMethodsTy;
> + /// LexedInlineMethods - During parsing of a C++ class, its inline method
> + /// definitions and the inline method definitions of its nested classes are
> + /// lexed and stored here.
> + LexedInlineMethodsTy LexedInlineMethods;
> [...]
> + if (!(CurScope->getFlags() & Scope::CXXClassScope)) {
> + // We are no longer inside a C++ class. This class and its nested classes
> + // are complete and we can parse the lexed inline method definitions.
> + for (LexedInlineMethodsTy::iterator I = LexedInlineMethods.begin();
> + I != LexedInlineMethods.end(); ++I) {
>
> This isn't quite right; consider the following:
> class X {
>
> int outer() {
> static int b;
> class C {
> public:
> int inner() {
> return b;
> }
> } r;
> return r.inner();
> };
>
> int other() {return b;}
>
> int x;
> };
>
> With the current code, at least according to my reading, first X gets
> parsed, then we start parsing outer, then we finish parsing class C,
> then we attempt to start parsing outer again, then bad things happen.
>
> I'd suggest allocating LexedInlineMethods in
> ParseCXXMemberSpecification, rather than making it a member of Parser.
>
Ok, I now use a "stack<LexedInlineMethodsTy>" as member of Parser and
ParseCXXMemberSpecification pushes a new LexedInlineMethodsTy container
for each non-nested class.
ParseInlineMethodDef pushes the new method to the top container.
Thanks for the catch!
-Argiris
More information about the cfe-dev
mailing list