I suspect this is treated as a "\n" actually (which may be irrelevant at least for your example).Baker wrote:We think of comments as being ignored. This isn't actually true.
They are interpreted as whitespace.
int x/*hello*/y = 5; // Error. If the comments were ignored, this line would be int xy=5;
Funny C Rules (And Low-Level Languages in general)
-
- Posts: 2126
- Joined: Sat Nov 25, 2006 1:49 pm
Re: Funny C Rules (And Low-Level Languages in general)
I know FrikaC made a cgi-bin version of the quakec interpreter once and wrote part of his website in QuakeC (LordHavoc)
Re: Funny C Rules (And Low-Level Languages in general)
It can't be because this works and preprocessor directives are terminated by a newline, so this inline comment is bridging the newline.frag.machine wrote:I suspect this is treated as a "\n" actually (which may be irrelevant at least for your example).
This fails ...#define name "dick" /* this works
hello world */ "jones"
And this obviously fails too#define name "dick" // Hello
"jones"
However, just to see what is really going on I did a compile using /i in Visual Studio, which generates preprocessed output and to my surprise the preprocessed file generates this.#define name "dick"
"jones"
becomes ...int x/*hello*/y=5;
However, it does not compile and generates error "syntax error : missing ';' before identifier y".int xy=5;
Which caused me to check CodeBlocks/mingw and it gets same error message when compiling.
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..
Re: Funny C Rules (And Low-Level Languages in general)
Baker wrote:strcmp and memcmp's -1, 0, 1 return values are great for sorting.mankrip wrote:When using strcmp, the coder is essentially asking "does those strings match?", and a no is a valid answer for such a question, so in cases like this it makes no sense to assign the return values as if they were error codes.
I feel dumb. I can't remember if I ever knew about strcmp's return values behaving like that.Baker wrote:An example is FitzQuake's cvar list. Your own engine feeds (sorting by distance) qsort --- which requires a comparison function be supplied, what is essentially memcmp (although I think you slightly wrap it).
And from what I've read now, they're not limited to 1 and -1. strcmp("example asset", "example data") should return -3, because 'a' - 'd' == -3.
Now I know why the "old man" fired him.Baker wrote:This fails ...And this obviously fails too#define name "dick" // Hello
"jones"#define name "dick"
"jones"
Maybe there's a null character between x and y. Or the error checking is done before the preprocessing.Baker wrote:However, just to see what is really going on I did a compile using /i in Visual Studio, which generates preprocessed output and to my surprise the preprocessed file generates this.becomes ...int x/*hello*/y=5;However, it does not compile and generates error "syntax error : missing ';' before identifier y".int xy=5;
Which caused me to check CodeBlocks/mingw and it gets same error message when compiling.
Re: Funny C Rules (And Low-Level Languages in general)
Hehe. Yeah, Robocop referencemankrip wrote:Now I know why the "old man" fired him.
Just checked with hex editor ---- nothing between x and y, not even null character.Baker wrote:Maybe there's a null character between x and y.
Yes, this discrepancy does seem odd, but then again I've been coming up with absurd scenarios to see how the compiler reacts to them.
In part because I'm trying to pull the functions out of C source files to create the headers automatically. And also have a index of functions. CTags does this, but I don't like the source code nor the output format.
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..
Re: Funny C Rules (And Low-Level Languages in general)
I wonder if it's a rule that /* */ comments are treated as whitespace, or if that behavior could vary from compiler to compiler. Obvious approach is, "Don't do that!"
Re: Funny C Rules (And Low-Level Languages in general)
Found an answer. https://msdn.microsoft.com/en-us/library/wfwda74e.aspxjitspoe wrote:I wonder if it's a rule that /* */ comments are treated as whitespace, or if that behavior could vary from compiler to compiler. Obvious approach is, "Don't do that!"
Probably does not vary from compiler to compiler and most likely ANSI C behavior. On the MSDN page, it does not say "Microsoft specific" for that section.
MSDN wrote:A "comment" is a sequence of characters beginning with a forward slash/asterisk combination (/*) that is treated as a single white-space character by the compiler and is otherwise ignored.
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..
Re: Funny C Rules (And Low-Level Languages in general)
Shortcircuit operators don't yield the same result as non-shortcircuit operators.
if (2 & 1) // Non-shortcircuiting. Will evaluate to false because 2 AND 1 = 0 (bit operation)
if (2 && 1) // Shortcircuiting. 2 will pass. Then 1 will pass. Will evaluate to true.
if (2 & 1) // Non-shortcircuiting. Will evaluate to false because 2 AND 1 = 0 (bit operation)
if (2 && 1) // Shortcircuiting. 2 will pass. Then 1 will pass. Will evaluate to true.
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..
Re: Funny C Rules (And Low-Level Languages in general)
Code: Select all
do
{
stuff (); // this works
} while (true);
Code: Select all
do
{
stuff (); // this doesn't, even though it comes before the conditional check
} while (false);
i = sizeof(cvar_t *) - 1;
instead of
i = sizeof cvar_t * - 1;
Re: Funny C Rules (And Low-Level Languages in general)
I'm don't think that is true. ... I just tried this.
> HelloCode: Select all
do { printf ("Hello\n"); } while (0);
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..
Re: Funny C Rules (And Low-Level Languages in general)
everything is false until it's true.
Re: Funny C Rules (And Low-Level Languages in general)
Still, it happened in my code. My guess is that some compiler (MSVC ToolKit 2003) optimization may be the cause.Baker wrote:I'm don't think that is true. ... I just tried this.> HelloCode: Select all
do { printf ("Hello\n"); } while (0);
Re: Funny C Rules (And Low-Level Languages in general)
Probably not recommended way of naming variables.>My value is 5Code: Select all
int ____ = 5; printf ("My value %i \n", ____ );
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..
Re: Funny C Rules (And Low-Level Languages in general)
one leading underscore is reserved for the libc.
two leading underscores are reserved for the compiler.
I have no idea who four leading underscores is reserved for...
two leading underscores are reserved for the compiler.
I have no idea who four leading underscores is reserved for...
Re: Funny C Rules (And Low-Level Languages in general)
One particularly funny one i seen in C is tag names
#define thistag L# or LL# for 64 bit long long names.
Took me a while to figure out that one and some compilers dont like tags.
#define thistag L# or LL# for 64 bit long long names.
Took me a while to figure out that one and some compilers dont like tags.
Productivity is a state of mind.
Re: Funny C Rules (And Low-Level Languages in general)
I've been thinking of calling conventions lately.
Then I realized something.
WinMain and the message handling function (tends to be named something like MainWndProc or such in Quake) are both WINAPI which is stdcall, not cdecl.
I've never really paid too much attention to how those 2 specific functions must use a different calling convention than the rest of the code.
No doubt because it is "interfacing" with the operating system, just like how Windows API calls are WINAPI calling convention.
Then I realized something.
WinMain and the message handling function (tends to be named something like MainWndProc or such in Quake) are both WINAPI which is stdcall, not cdecl.
I've never really paid too much attention to how those 2 specific functions must use a different calling convention than the rest of the code.
No doubt because it is "interfacing" with the operating system, just like how Windows API calls are WINAPI calling convention.
The night is young. How else can I annoy the world before sunsrise? Inquisitive minds want to know ! And if they don't -- well like that ever has stopped me before ..