C Program Not Recognizing Constant From Header File - c

I have the following really simple header file:
#ifndef __ZYNQ_CSORT_H__
#define __ZYNQ_CSORT_H__
#define CONSTANT 5
#endif
I am including this header file in another C file in the same folder. The preprocessor doesn't complain at all about the header file include, but when I try to print the value of the constant, it tells me that it is not defined. Anybody know what's up?

When I'm uncertain about what the preprocessor is up to, I find it is often revealing to run the C preprocessor by itself. For example, given test1.h:
#ifndef TEST1_H
#define TEST1_H
/* In TEST1_H */
#define CONSTANT 5
#endif
... and test1.c:
#include "test1.h"
#include "test1.h"
int main(int argc, char **argv) {
return CONSTANT;
}
... running cpp -C test1.c test1.c.out (the -C argument makes the preprocessor retain comments) gives test1.c.out as follows:
# 1 "test1.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "test1.c"
# 1 "test1.h" 1
/* In TEST1_H */
# 2 "test1.c" 2
int main(int argc, char **argv) {
return 5;
}
Thus, for my case I can be confident that the right header file is being included.

CONSTANT would be undefined if __ZYNC_CSORT_H were already defined when this file was parsed.

Related

C Preprocessor include directive

When I include another source(I.e stdio.h) the preprocessor is smart enough to include only the functions that I am using in my code?
Example: Assuming this small program, would be ease to include only what I am using, and what the printf functions uses, including them recursively, but what about bigger programs?
#include <stdio.h>
int main(void) {
printf("Hello World\n");
return 0;
}
No. On the contrary:
#include performs textual replacement: it opens the file and copies all1 of its contents into your main C file. In the process it executes all preprocessor instructions in the included file. Amongst other things, this means that it will recursively include all files that are #included in the header.
#include does not know and does not care which part of the included file you end up using.
1 As mentioned, preprocessor instructions are executed in the included file. This can modify what gets included. For example, assume the following header file header.h:
#ifndef HEADER_H
#define HEADER_H
#ifdef NDEBUG
# define LOG(...) ((void) 0)
#else
# define LOG(...) log_message(__FILE__, __LINE__, __VA_ARGS__)
inline void log_message(const char* filename, int line, ...) {
// Logging code omitted for brevity.
}
#endif
// other stuff
#endif
Now, if your main.c file looks as follows:
#define NDEBUG
#include "header.h"
int main(void) {
// …
LOG("hello");
}
… then, after preprocessing, your main.c file would looks something like this (I’m omitting some irrelevant stuff):
# 1 "main.c"
# 1 "./header.h" 1
# 13 "./header.h"
// other stuff
# 3 "main.c" 2
int main(void) {
// …
((void) 0);
}
… in other words, only the part of header.h that corresponds to #ifdef NDEBUG was included, not the part in the #else clause. If we had included header.h without defining NDEBUG, then the included header code would have contained the definition of log_message.
As others have said, #include will paste verbatim the entire file you are targeting. However you normally include headers, which tend to look like
extern int a (int b);
extern char * c (void);
static inline int d (int e, int f) {
...
}
extern void * g (void * h);
...
The code above occupies exactly zero memory (unless you start using one of the inline functions), since it is entirely composed of instructions for the compiler and nothing else.

C: Confused about preprocessor macros

I've added a bunch of "debug(x)" statements to my code using preprocessing macros in a header file. I've also implemented a toggle (via an #ifdef / #else structure in the header file) that lets me turn off the debug statements. I'm having trouble getting this toggle to work and am hoping someone can figure out the reason.
Rather than re-posting the actual code (which is lengthy), I'm including an illustrative example (which does compile).
Here's our .h file. It consists of a macro for a function named "superman". The statement should print if and only if KRYPTONITE is not defined in our .c file.
test.h:
#ifndef __test_h__
#define __test_h__
#ifdef KRYPTONITE
#define superman(...)
#else
#define superman(xs) printf("%s\n\n",xs)
#endif
#endif
As you can see in the cases below, adding a "#define KRYPTONITE 1" statement to the beginning of our .c file does not toggle off the "superman" function (Case 2 below). However, we do successfully toggle off if we define KRYPTONITE via a flag in our compile instruction (Case 3).
What else do I need to do in order to toggle off the "superman" function via a "#define" statement in the .c file?
Case 1: KRYPTONITE not defined in the .c file (it's commented out). As expected, the statement prints. (The .c file and output is below.)
test1.c:
#include <stdio.h>
#include "test.h"
//#define KRYPTONITE
int main (int argc, char *argv[])
{
printf("\nSuperman, are you here?\n\n");
superman("I'm here");
return 0;
}
Output:
dchaudh#dchaudhUbuntu:~/SO$ gcc test1.c -o test1
dchaudh#dchaudhUbuntu:~/SO$ ./test1
Superman, are you here?
I'm here
dchaudh#dchaudhUbuntu:~/SO$
Case 2: KRYPTONITE is defined in our .c file, yet the statement prints.
test2.c:
#include <stdio.h>
#include "test.h"
#define KRYPTONITE
int main (int argc, char *argv[])
{
printf("\nSuperman, are you here?\n\n");
superman("I'm here");
return 0;
}
Output:
dchaudh#dchaudhUbuntu:~/SO$ gcc test2.c -o test2
dchaudh#dchaudhUbuntu:~/SO$ ./test2
Superman, are you here?
I'm here
dchaudh#dchaudhUbuntu:~/SO$
Case 3: KRYPTONITE is not defined in our .c file but we define it via a flag when compiling. In this case, the superman function is successfully toggled off.
Output:
dchaudh#dchaudhUbuntu:~/SO$ gcc -DKRYPTONITE test1.c -o test3
dchaudh#dchaudhUbuntu:~/SO$ ./test3
Superman, are you here?
dchaudh#dchaudhUbuntu:~/SO$
The proeprocessor, just like the C compiler, scans files from top to bottom. That means macros must be defined before they are used.
So to solve your problem, put the #define before the #include.
#include <stdio.h>
#define KRYPTONITE
#include "test.h"
int main (int argc, char *argv[])
{
printf("\nSuperman, are you here?\n\n");
superman("I'm here"); // Doesn't print
return 0;
}

Any way to get the c preproccessor to ignore all #include's?

Using pycparser to parse a slew of .c source files, but the parser can't handle many things in the #included libraries, and I really don't need them for my purposes. I don't need to have it compile, just need to generate the AST from the specific .c I'm processing.
The cpp args i'm passing it right now are:
cpp_args=["-D__attribute__=","-D__extension__=","-D__builtin_va_list=void*"]
Any ideas?
Thanks!
Try specifying the -nostdinc option to the preprocessor (and make sure you're not passing any -I options). Given this input in foo.c:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
int main(int argc, char **argv) {
return 0;
}
Running:
cpp -nostdinc foo.c
Gives me:
# 1 "foo.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "foo.c"
int main(int argc, char **argv) {
return 0;
}
And the following errors:
foo.c:1:19: error: no include path in which to search for stdio.h
foo.c:2:20: error: no include path in which to search for stdlib.h
foo.c:3:20: error: no include path in which to search for unistd.h
One solution would be to use the #include guards
If you have the traditional wrapper in each header, eg.
#ifndef THIS_FILE_H
#define THIS_FILE_H
// stuff
#endif
Then you could simply #define all the header guard tags you want to ignore

I don't want to preprocess specific macros. It should not replace it with its value. Is it possible?

Example =
#define a 100
#define b 200
main()
{
int c=a+b;
}
After preprocessing
Output-
#define a 100
main()
{
int c=a+200;
}
You could try refactoring the macros to allow external configuration, i.e.
/* config.h */
/* set defaults for a and b */
#ifndef a
#define a 100
#endif
#ifndef b
#define b 200
#endif
and
/* main.c */
#include "config.h"
int main(void)
{
int c = a + b;
}
Then you can set the macros externally when building, for instance like this:
$ gcc -E -Da=a main.c
# 1 "main.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "main.c"
# 1 "config.h" 1
# 4 "main.c" 2
int main(void)
{
int c = a + 200;
}
$ gcc -E -Db=b main.c
# 1 "main.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "main.c"
# 1 "config.h" 1
# 4 "main.c" 2
int main(void)
{
int c = 100 + b;
}
Now, of course you don't have to use a separate configuration header, but I'd recommend it from a maintenance perspective, it will make it easier to keep track of available configuration settings and their defaults.
#define a 100
#define b 200
main()
{
#undef b
int c=a+b;
}
No. What's your real goal?
If you want to do, it's better to make some script to do that.
If you don't want to preprocess a macro, just don't use it:
#define a 100
//#define b 200
int main()
{
int c = a + 200;
return 0;
}
The purpose of preprocessing is to process the preprocessing directives. I don't know of any way to keep a specific preprocessing directive, especially because the next step, compilation, doesn't know anything about these.
This is another reason why you should be careful when using macros -- when the name is found in the source, then it is substituted, no matter what:
#define a 100
main()
{
int a; // Compilation error happens here
....
}
Regarding Peter Miehle's answer, unifdef can be used to partially process #if and #ifdef directives, but it cannot be used to selectively expand macros. See http://dotat.at/prog/unifdef

#define f(g,g2) g##g2

#define f(g,g2) g##g2
main()
{
int var12=100;
printf("%d",f(var,12));
}
The above program prints 100 in c by concatenating var and 12. How does g##g2 work??
## just pastes tokens together. It is a preprocessor directive.
E.g.
#define PASTE(a,b) a##b
int i=PASTE(1,2); /* int i=12; */
## is the preprocessor "command" for concatenating what comes before and after.
This is token pasting, described here for gcc. Token pasting is done by the preprocessor, not the compiler.
So after preprocess it will look like this:
main()
{
int var12=100;
printf("%d",var12);
}
Concatenation is being performed by the preprocessor because you used the ## command.
When you are unsure what the preprocessor is doing you can ask gcc to stop after it has run the preprocessor. Since this is before the compiler runs, the output is fairly easy to understand.
For example, assume you have a file pre.c
#define FOO 123
#define CONCAT(x,y) x##y
#define STRING(x) #x
void main()
{
int a = FOO;
int b = CONCAT(123,4567);
char* c = STRING(IGetQuoted);
}
You can produce the preprocessor output by passing the -E option to gcc.
$ gcc -E pre.c
# 1 "pre.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "pre.c"
void main()
{
int a = 123;
int b = 1234567;
char* c = "IGetQuoted";
}
Keep in mind that #include will pull in the contents of the file it specifies and can make the preprocessor output rather long.

Resources