I'm learning how GNU Make and makefile works.
I have a small project with 7 *.c and *.h files and a main.c file.
here's the makefile:
CC = "gcc"
CFLAGS = "-std=c11"
#PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/snap/bin
# the PATH variable is set after I got the error. But adding this didnt change the result
src := src/lib
bin := bin
project: $(bin)/aaa.o $(bin)/bbb.o $(bin)/ccc.o $(bin)/ddd.o $(bin)/eee.o $(bin)/fff.o $(bin)/main.o
$(CC) $(CFLAGS) $(bin)/aaa.o $(bin)/bbb.o $(bin)/ccc.o $(bin)/ddd.o $(bin)/eee.o $(bin)/fff.o $(bin)/main.o -o $(bin)/project
$(bin)/aaa.o: $(src)/aaa.c $(src)/ddd.h
$(CC) $(CFLAGS) -c $(src)/aaa.c
$(bin)/bbb.o: $(src)/bbb.c $(src)/aaa.h $(src)/bbb.h $(src)/ddd.h $(src)/fff.h
$(CC) $(CFLAGS) -c $(src)/bbb.c
$(bin)/ccc.o: $(src)/ccc.c $(src)/aaa.h $(src)/fff.h
$(CC) $(CFLAGS) -c $(src)/ccc.c
# ... (and so on for all other .o files
clean:
rm $(bin)/*
aaa.c
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <unistd.h>
#include "aaa.h"
#include "ddd.h"
bbb.c
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "aaa.h"
#include "bbb.h"
#include "ddd.h"
#include "fff.h"
ccc.c
#include <stdio.h>
#include <stdlib.h>
#include <termios.h>
#include "aaa.h"
#include "fff.h"
when ran, It gave me this error:
"gcc" "-std=c11" -c src/lib/aaa.c
src/lib/aaa.c: In function ‘init_fileSize’:
src/lib/aaa.c:103:14: warning: implicit declaration of function ‘fileno’ [-Wimplicit-function-declaration]
103 | if((fd = fileno(arg->srcstream)) == -1)
| ^~~~~~
"gcc" "-std=c11" -c src/lib/bbb.c
"gcc" "-std=c11" -c src/lib/ccc.c
src/lib/ccc.c: In function ‘closeProgram’:
src/lib/ccc.c:10:15: error: ‘STDIN_FILENO’ undeclared (first use in this function)
10 | tcsetattr(STDIN_FILENO, TCSANOW, &(trml->termios_default));
| ^~~~~~~~~~~~
src/lib/ccc.c:10:15: note: each undeclared identifier is reported only once for each function it appears in
make: *** [makefile:19: bin/ccc.o] Error 1
from the error message, I conclude that the gcc couldn't find the definitions for functions and other identities declared in standard headers like stdio.h.
These preprocessor symbols and functions are not a part of Standard C. They are defined in the POSIX standard.
On program startup, the integer file descriptors associated with the streams stdin, stdout, and stderr are 0, 1, and 2, respectively. The preprocessor symbols STDIN_FILENO, STDOUT_FILENO, and STDERR_FILENO are defined with these values in <unistd.h>.
So you're missing:
#include <unistd.h>
for the macros.
And fileno(3)
(declared in stdio.h
), requires a feature test macro to be defined:
/* Before including any headers, define this at the top. */
#define _POSIX_C_SOURCE 200819L
/* Now include the headers. */
Alternatively, you could replace -std=cXX
with -std=gnuXX
, and that will include all sorts of extensions to the language.