Parse-declaration-specifiers
Parse a list of one or more declaration specifiers.
- Signature
(parse-declaration-specifiers tyspec-seenp parstate)
→
(mv erp declspecs span new-parstate)
- Arguments
- tyspec-seenp — Guard (booleanp tyspec-seenp).
- parstate — Guard (parstatep parstate).
- Returns
- declspecs — Type (declspec-listp declspecs).
- span — Type (spanp span).
- new-parstate — Type (parstatep new-parstate), given (parstatep parstate).
We parse a declaration specifier,
which must exist because the list must not be empty.
Then we need to decide whether we have reached the end of the list
or there may be another declaration specifier.
If the next token is an identifier,
it could be a typedef name
or (the start of) a declarator.
To resolve this ambiguity,
we exploit the fact that
a list of declaration specifiers must contain
at least one type specifier [C:6.7.2/2]
and only the multisets listed in [C:6.7.2/2].
One of those multisets is a single identifier (a typedef name).
So we carry around a flag saying whether
we have encountered at least one type specifier in the list or not.
Initially the flag is nil,
and it gets set when parse-declaration-specifier
returns amy type specifier.
This flag participates in the decision of whether an identifier
must be another declaration specifier (a type specifier)
or (the start of) a declarator:
if the flag is t,
it means that we have already encountered
at least one type specifier,
and therefore the identifier cannot be another one,
and it must be (the start of) a declarator;
if the flag is nil,
the identifier cannot be (the start of) a declarator,
because we have not found a type specifier yet,
and thus the identifier must be the missing type specifier.