"error: invalid preprocessing directive #DEFINE"

A

alien

When i'm trying to compile a program with #DEFINE it says:
2:2: error: invalid preprocessing directive #DEFINE

Why, and how do i fix it?
 
E

Eric Sosman

alien said:
When i'm trying to compile a program with #DEFINE it says:
2:2: error: invalid preprocessing directive #DEFINE

Why, and how do i fix it?

Try #define.

(Language lawyers: Was his compiler justified in
rejecting his code, assuming that it did? See 6.10,
fourth production of group-part; the Standard says very
little about this topic.)
 
K

kr0wie

#define

Somehow you must have got a c source file from an oddball system that
doesn't have lower case.

Okay. It works with #define, thanks for the quick answer.
 
S

Seebs

When i'm trying to compile a program with #DEFINE it says:
2:2: error: invalid preprocessing directive #DEFINE

Why, and how do i fix it?

STOP SHOUTING AT YOUR COMPILER.

-s
p.s.: No, really. This is the correct answer to your question.
 
T

Tim Rentsch

Eric Sosman said:
Try #define.

(Language lawyers: Was his compiler justified in
rejecting his code, assuming that it did? See 6.10,
fourth production of group-part; the Standard says very
little about this topic.)

My reading is that

#DEFINE <pp-tokens> <new-line>

(which presumably is what was there) is legal, and should not
have been rejected.
 
J

jameskuyper

Kenneth said:
Based on what? Section 6.10 clearly shows several varations on "#define",
but all are listed with lowercase "define", and I see nothing which states
or implies case insignificance.

Based upon 6.10p1, the production covering "# non-directive". Since
DEFINE satisfies the requirements for a pp-token, "DEFINE pp-tokens
new-line" matches the requirements for a "non-directive". The only
requirement imposed upon a non-directive is that it "shall not begin
with any of the directive names appearing in the syntax." (6.10p3).
DEFINE is definitely not one of those directive names.

It might seem that the standard defines no behaviour for non-
directives; if that were the case, then the behaviour would be
undefined by reason of the absence of a definition.

However, there's a tricky argument that can be made that the behavior
IS defined, though in a very minimalist way. The only other thing the
standard says about non-directives is to point out, in footnote 150,
that "Despite the name, a non-directive is a preprocessing
directive.". While non-normative, that note merely confirms what can
already be inferred from the normative grammar productions in 6.10p1.
Because a non-directive is a preprocessing directive, 5.1.1.2p4
applies, which says that at the end of translation phase 4 "All
preprocessing directives are then deleted." Arguably, this defines the
behaviour of non-directives: they exist, like comments, solely for the
purpose of being removed without having any actual effect on the
translation of the program.

I'm not happy with this argument; I'd prefer a direct statement that
non-directives are simply to be ignored.
 
T

Tim Rentsch

Kenneth Brody said:
Based on what? Section 6.10 clearly shows several varations on
"#define", but all are listed with lowercase "define", and I see
nothing which states or implies case insignificance.

6.4.2.1p2, "Lowercase and uppercase letters are distinct."
 
T

Tim Rentsch

Kenneth Brody said:
Based on what? Section 6.10 clearly shows several varations on
"#define", but all are listed with lowercase "define", and I see
nothing which states or implies case insignificance.

Sorry, I answered the wrong sense of your question earlier.

Given that case is significant, my statement was based on (a) syntax
rules in 6.10p1, specifically for 'group-part:' and 'non-directive:',
(b) the second sentence in 6.10p3 ('DEFINE' is different from
'define'), and (c) the reassurance given in the footnote in 6.10.3p11.

The counter-argument is that, since there is no explicit definition
of behavior for a 'non-directive', the behavior is undefined. I don't
have any substantial defense to offer in response to this argument
(my previous checking wasn't thorough enough). Given that, I withdraw
my previous statement, and now venture to say that, since there is
no explicit definition of behavior, the compiler is within its
rights to do whatever it chooses, including rejecting the program.
 
K

Keith Thompson

jameskuyper said:
Kenneth said:
Tim Rentsch wrote: [...]
My reading is that

#DEFINE <pp-tokens> <new-line>

(which presumably is what was there) is legal, and should not
have been rejected.

Based on what? Section 6.10 clearly shows several varations on "#define",
but all are listed with lowercase "define", and I see nothing which states
or implies case insignificance.

Based upon 6.10p1, the production covering "# non-directive". Since
DEFINE satisfies the requirements for a pp-token, "DEFINE pp-tokens
new-line" matches the requirements for a "non-directive". The only
requirement imposed upon a non-directive is that it "shall not begin
with any of the directive names appearing in the syntax." (6.10p3).
DEFINE is definitely not one of those directive names.

It might seem that the standard defines no behaviour for non-
directives; if that were the case, then the behaviour would be
undefined by reason of the absence of a definition.

However, there's a tricky argument that can be made that the behavior
IS defined, though in a very minimalist way. The only other thing the
standard says about non-directives is to point out, in footnote 150,
that "Despite the name, a non-directive is a preprocessing
directive.". While non-normative, that note merely confirms what can
already be inferred from the normative grammar productions in 6.10p1.
Because a non-directive is a preprocessing directive, 5.1.1.2p4
applies, which says that at the end of translation phase 4 "All
preprocessing directives are then deleted." Arguably, this defines the
behaviour of non-directives: they exist, like comments, solely for the
purpose of being removed without having any actual effect on the
translation of the program.

I'm not happy with this argument; I'd prefer a direct statement that
non-directives are simply to be ignored.

I'd be even happier with a direct statement that non-directives
require a diagnostic, like any syntax error.

If I can write

#defnie SOME_IMPORTANT_SYMBOL

or

and have the compiler silently ignore it, that's not a good thing.
Similarly, if I write:

#if SOME_CONDITION
this_code;
#elsif SOME_OTHER_CONDITION
that_code;
#endif

and both this_code and that_code are executed (because I typed
"#elsif" rather than "#elif"), that could lead to some bugs that
are very difficult to track down.

There's very little discussion of them in the Standard. The Rationale
has this to say (6.10):

Neither text-line nor non-directive is implementation
defined. They are strictly defined as sequences of pp-tokens
followed by new-line. Each of these rules represents a placeholder
for an intermediate state in the phases of translation, and is
expressed as a non-terminal since it has no associated semantics
at this phase.

which is less than illuminating. If it were the intent that
non-directives are ignored, I presume the standard would say so,
as it does for the null directive.

I'll post to comp.std.c in the vague hope of catching the attention
of someone who can explain the actual intent.
 
W

Willem

Keith Thompson wrote:
) I'd be even happier with a direct statement that non-directives
) require a diagnostic, like any syntax error.

How about making it implementation-defined behaviour ?
Then you can read the docs of the compiler and be sure that it doesn't
silently ignore those typoes.


SaSW, Willem
--
Disclaimer: I am in no way responsible for any of the statements
made in the above text. For all I know I might be
drugged or something..
No I'm not paranoid. You all think I'm paranoid, don't you !
#EOT
 
K

Keith Thompson

Willem said:
Keith Thompson wrote:
) I'd be even happier with a direct statement that non-directives
) require a diagnostic, like any syntax error.

How about making it implementation-defined behaviour ?
Then you can read the docs of the compiler and be sure that it doesn't
silently ignore those typoes.

Just from a usability point of view, how would making it
implementation-defined be better than a mandatory diagnostic?

If I misspell a keyword, I get a diagnostic. If I misspell a
preprocessor directive name, I want the same thing. (And that's
what I get on the two compilers I tried.)
 
J

jameskuyper

Kenneth said:
jameskuyper said:
Kenneth said:
Tim Rentsch wrote: [...]
My reading is that

#DEFINE <pp-tokens> <new-line>

(which presumably is what was there) is legal, and should not
have been rejected.
Based on what? Section 6.10 clearly shows several varations on "#define",
but all are listed with lowercase "define", and I see nothing which states
or implies case insignificance.

Based upon 6.10p1, the production covering "# non-directive". Since
DEFINE satisfies the requirements for a pp-token, "DEFINE pp-tokens
new-line" matches the requirements for a "non-directive". The only
requirement imposed upon a non-directive is that it "shall not begin
with any of the directive names appearing in the syntax." (6.10p3).
DEFINE is definitely not one of those directive names.
[... snip detailed analysis ...]
I'm not happy with this argument; I'd prefer a direct statement that
non-directives are simply to be ignored.

While I agree with what you said for the most part, I would have to say that
allowing "anything" as a "non-directive" (which I agree the Standard says is
the case) to "simply be ignored" would be "A Bad Thing[tm]". Consider what
happens with a simple typo:

#defien SOME_CONFIG_FLAG 1

or

#if USE_VERSION == 1
... first version of the code ...
#elseif USE_VERSION == 2
... second version ...
#else
... default version ...
#endif

or

#IfDef CONFIG_FLAG
... code ...
#Endif

Try debugging that, and trying to figure out why the wrong conditional code
is being used.

While useful as a way of adding implementation-specific features, a
catch-all "comment" doesn't sound good to me.

I agree; I was trying to figure out what the standard actually says,
and to suggest alternative wording that would make it clearer.
However, all the committee had to do to make a diagnostic mandatory
would have been to leave out non-directives entirely; they would then
have constituted syntax errors. In defining a "non-directive", the
committee went out of their way to make it not be a syntax error; I
presume they had a reason - I'm curious what it was. Until I know that
reason, and can judge it's validity, I didn't want to suggest changing
it to a syntax error.
 
W

Willem

Keith Thompson wrote:
) Just from a usability point of view, how would making it
) implementation-defined be better than a mandatory diagnostic?

Extensibility, basically. Otherwise any compiler that recognizes
directives that are not defined in the standard would be required to emit a
diagnostic even though to them it's something they're perfectly happy with.


SaSW, Willem
--
Disclaimer: I am in no way responsible for any of the statements
made in the above text. For all I know I might be
drugged or something..
No I'm not paranoid. You all think I'm paranoid, don't you !
#EOT
 
K

Keith Thompson

Willem said:
Keith Thompson wrote:
) Just from a usability point of view, how would making it
) implementation-defined be better than a mandatory diagnostic?

Extensibility, basically. Otherwise any compiler that recognizes
directives that are not defined in the standard would be required to emit a
diagnostic even though to them it's something they're perfectly happy with.

We have exactly the same situation with extensions.

If a compiler defines an extension, say, a "long long long" type, it's
still required to issue a diagnostic for any occurrence of "long long
long"; it's then free to continue compilation and implement whatever
behavior it likes. If you want to use "long long long" without being
bothered by diagnostics, just invoke the compiler in a non-conforming
mode. You can use the extension, and I can still get a diagnostic if
I type "long" more times than I intended to.

In any case, I don't think that was the intent. As the Rationale says:

Neither text-line nor non-directive is implementation
defined. They are strictly defined as sequences of pp-tokens
followed by new-line. Each of these rules represents a placeholder
for an intermediate state in the phases of translation, and is
expressed as a non-terminal since it has no associated semantics
at this phase.

However, these sequences of pp-tokens are still subject to normal
processing in the subsequent phases of translation.

My best guess is that the intent was that a non-directive would never
survive all the phases of translation. I just can't figure out how
that's supposed to happen. I'm hoping my query in comp.std.c will
produce either a definitive answer or an acknowledgement that the
standard's text doesn't properly describe the intent.
 
T

Tim Rentsch

jameskuyper said:
Based upon 6.10p1, the production covering "# non-directive". Since
DEFINE satisfies the requirements for a pp-token, "DEFINE pp-tokens
new-line" matches the requirements for a "non-directive". The only
requirement imposed upon a non-directive is that it "shall not begin
with any of the directive names appearing in the syntax." (6.10p3).
DEFINE is definitely not one of those directive names.

It might seem that the standard defines no behaviour for non-
directives; if that were the case, then the behaviour would be
undefined by reason of the absence of a definition.

However, there's a tricky argument that can be made that the behavior
IS defined, though in a very minimalist way. The only other thing the
standard says about non-directives is to point out, in footnote 150,
that "Despite the name, a non-directive is a preprocessing
directive.". While non-normative, that note merely confirms what can
already be inferred from the normative grammar productions in 6.10p1.
Because a non-directive is a preprocessing directive, 5.1.1.2p4
applies, which says that at the end of translation phase 4 "All
preprocessing directives are then deleted." Arguably, this defines the
behaviour of non-directives: they exist, like comments, solely for the
purpose of being removed without having any actual effect on the
translation of the program.

I'm not happy with this argument; I'd prefer a direct statement that
non-directives are simply to be ignored.

The problem is, 5.1.1.2p4 says "Preprocessing directives are
executed," but there is no statement of what behavior occurs
when a 'non-directive' is executed. There is for every other
preprocessing directive (including '# <new-line>'). It's
this absence that convinved me that an unskipped 'non-directive'
is undefined behavior.
 
T

Tim Rentsch

Keith Thompson said:
We have exactly the same situation with extensions.

If a compiler defines an extension, say, a "long long long" type, it's
still required to issue a diagnostic for any occurrence of "long long
long"; it's then free to continue compilation and implement whatever
behavior it likes. If you want to use "long long long" without being
bothered by diagnostics, just invoke the compiler in a non-conforming
mode. You can use the extension, and I can still get a diagnostic if
I type "long" more times than I intended to.

In any case, I don't think that was the intent. As the Rationale says:

Neither text-line nor non-directive is implementation
defined. They are strictly defined as sequences of pp-tokens
followed by new-line. Each of these rules represents a placeholder
for an intermediate state in the phases of translation, and is
expressed as a non-terminal since it has no associated semantics
at this phase.

However, these sequences of pp-tokens are still subject to normal
processing in the subsequent phases of translation.

My best guess is that the intent was that a non-directive would never
survive all the phases of translation.

Right. It's deleted at the end of phase 4 (assuming that the UB
that arises from "executing" it doesn't contradict that).
I just can't figure out how that's supposed to happen.

It gets deleted because of the last sentence of 5.1.1.2p1.4 says
it will be (oops, bad reference in a previous posting). The
question is what happens when it gets executed, and the Standard
doesn't say anything about that, which is what makes the behavior
undefined.

I'm hoping my query in comp.std.c will
produce either a definitive answer or an acknowledgement that the
standard's text doesn't properly describe the intent.

It's there to make sure that every line starting with '#' is
considered a preprocessing directive, and it's undefined to
give implementations a chance to define them. It just would be
nice if that had been handled a little better and been made
a little more clear in the Standard.
 
J

James Kuyper

Kenneth said:
jameskuyper said:
Kenneth Brody wrote: [...]
While useful as a way of adding implementation-specific features, a
catch-all "comment" doesn't sound good to me.

I agree; I was trying to figure out what the standard actually says,
and to suggest alternative wording that would make it clearer.
However, all the committee had to do to make a diagnostic mandatory
would have been to leave out non-directives entirely; they would then
have constituted syntax errors. In defining a "non-directive", the
committee went out of their way to make it not be a syntax error; I
presume they had a reason - I'm curious what it was. Until I know that
reason, and can judge it's validity, I didn't want to suggest changing
it to a syntax error.

It doesn't have to be a "syntax error" to be an "error". After all, the
following isn't a "syntax error", either:

I would want a diagnostic to be mandatory; the simplest way to make that
happen is to make it a syntax error, by removing 'non-directive' from
the grammar. Of course, a constraint violation or an explicit statement
that a diagnostic is required would do just as well.

This would not prevent the development of implementation-specific
preprocessing directives. In conforming mode, a compiler could issue a
diagnostic saying "warning: non-standard feature #explain used", and
that warning could be turned off by an option that would render the
compiler non-conforming.

My point is - the committee went out of their way to put "non-directive"
into the grammar. Why? Until I know why, I don't want to suggest
removing it. Keith's inquiry on comp.std.c has received no authoritative
response yet, which is a bit disappointing.
 
J

jacob navia

James Kuyper a écrit :
My point is - the committee went out of their way to put "non-directive"
into the grammar. Why? Until I know why, I don't want to suggest
removing it. Keith's inquiry on comp.std.c has received no authoritative
response yet, which is a bit disappointing.

Well, this is just a bug.

Nobody is perfect, and committee members aren't either.

The preprocessor of lcc-win uses is a version that was written by Dennis Ritchie.
I have maintained his code for many years, and he does complain at any
directive that is not a known directive. This bug in the specs was introduced
later, and I am glad his version doesn't have it.
 
K

Keith Thompson

jacob navia said:
James Kuyper a écrit :

Well, this is just a bug.

Nobody is perfect, and committee members aren't either.

The preprocessor of lcc-win uses is a version that was written by
Dennis Ritchie. I have maintained his code for many years, and he
does complain at any directive that is not a known directive. This
bug in the specs was introduced later, and I am glad his version
doesn't have it.

Assuming that the behavior of a "non-directive" is undefined,
Ritchie's preprocessor is consistent with the spec, at least with
respect to this feature.
 
K

Keith Thompson

Tim Rentsch said:
Right. It's deleted at the end of phase 4 (assuming that the UB
that arises from "executing" it doesn't contradict that).


It gets deleted because of the last sentence of 5.1.1.2p1.4 says
it will be (oops, bad reference in a previous posting). The
question is what happens when it gets executed, and the Standard
doesn't say anything about that, which is what makes the behavior
undefined.

Ok. The reference paragraph, which describes translation phase 4,
says

Preprocessing directives are executed, macro invocations are
expanded, and _Pragma unary operator expressions are executed.
[snip]
All preprocessing directives are then deleted.

And yes, the meaning of executing a non-directive (which is a
directive) is the sticking point. Since the standard doesn't define
the behavior, the behavior is undefined.
It's there to make sure that every line starting with '#' is
considered a preprocessing directive, and it's undefined to
give implementations a chance to define them. It just would be
nice if that had been handled a little better and been made
a little more clear in the Standard.

I have a much clearer understanding of what the standard *says*
about non-directives. But I'm still waiting for a definitive
statement about the intent. (Such a statement cannot be based
only on the wording of the standard; it's about the state of mind
of the authors.)

The standard would be substantially improved by an explicit
statement that the behavior of executing a non-directive is
undefined. It would be improved even more, IMHO, by a statement
that executing a non-directive is a constraint violation. If I
misspell a keyword, the compiler complains, and in most cases
it's required to complain. The (apparent) fact that this doesn't
apply to misspelled preprocessor directives is counterintuitive.
This would still leave room for implementation-defined extensions.

(I thought about using the common extension "#warning" as an example,
but since the whole purpose of "#warning" is to trigger a diagnostic,
it's probably the worst possible example.)
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,764
Messages
2,569,565
Members
45,041
Latest member
RomeoFarnh

Latest Threads

Top