Go forward to Copying Objects.
Go backward to Error Reporting.
Go up to Top.
Parser
======
Some comments on the parser:
The `after_type_declarator' / `notype_declarator' hack is necessary
in order to allow redeclarations of `TYPENAME's, for instance
typedef int foo;
class A {
char *foo;
};
In the above, the first `foo' is parsed as a `notype_declarator',
and the second as a `after_type_declarator'.
Ambiguities:
There are currently four reduce/reduce ambiguities in the parser.
They are:
1) Between `template_parm' and `named_class_head_sans_basetype', for
the tokens `aggr identifier'. This situation occurs in code looking
like
template <class T> class A { };
It is ambiguous whether `class T' should be parsed as the
declaration of a template type parameter named `T' or an unnamed
constant parameter of type `class T'. Section 14.6, paragraph 3 of the
January '94 working paper states that the first interpretation is the
correct one. This ambiguity results in two reduce/reduce conflicts.
2) Between `primary' and `type_id' for code like `int()' in places
where both can be accepted, such as the argument to `sizeof'. Section
8.1 of the pre-San Diego working paper specifies that these ambiguous
constructs will be interpreted as `typename's. This ambiguity results
in six reduce/reduce conflicts between `absdcl' and `functional_cast'.
3) Between `functional_cast' and `complex_direct_notype_declarator',
for various token strings. This situation occurs in code looking like
int (*a);
This code is ambiguous; it could be a declaration of the variable
`a' as a pointer to `int', or it could be a functional cast of `*a' to
`int'. Section 6.8 specifies that the former interpretation is
correct. This ambiguity results in 7 reduce/reduce conflicts. Another
aspect of this ambiguity is code like 'int (x[2]);', which is resolved
at the '[' and accounts for 6 reduce/reduce conflicts between
`direct_notype_declarator' and `primary'/`overqualified_id'. Finally,
there are 4 r/r conflicts between `expr_or_declarator' and `primary'
over code like 'int (a);', which could probably be resolved but would
also probably be more trouble than it's worth. In all, this situation
accounts for 17 conflicts. Ack!
The second case above is responsible for the failure to parse
'LinppFile ppfile (String (argv[1]), &outs, argc, argv);' (from Rogue
Wave Math.h++) as an object declaration, and must be fixed so that it
does not resolve until later.
4) Indirectly between `after_type_declarator' and `parm', for type
names. This occurs in (as one example) code like
typedef int foo, bar;
class A {
foo (bar);
};
What is `bar' inside the class definition? We currently interpret
it as a `parm', as does Cfront, but IBM xlC interprets it as an
`after_type_declarator'. I believe that xlC is correct, in light of
7.1p2, which says "The longest sequence of decl-specifiers that could
possibly be a type name is taken as the decl-specifier-seq of a
declaration." However, it seems clear that this rule must be violated
in the case of constructors. This ambiguity accounts for 8 conflicts.
Unlike the others, this ambiguity is not recognized by the Working
Paper.