CRTSCTS are not determined at compilation as C99

I write serial code on raspberry pi and switched to C99. When I did this, I started getting the error "error:" CRTSCTS uneclared (use in this function first) "

$ c99 -M serial01.c | grep termios.h /usr/include/termios.h /usr/include/arm-linux-gnueabihf/bits/termios.h \ $ gcc -M serial01.c | grep termios.h /usr/include/termios.h /usr/include/arm-linux-gnueabihf/bits/termios.h \ 

using -M opens 2 termios.h headers. the former does not contain a definition for CRTSCTS, and the latter does.

I assume that the c89 standard uses good and c99, but I'm not sure, since the result of calling -M is identical. Can someone explain to me why this happens when I switch to C99 and how to fix it?

+5
source share
2 answers

-std=gnu99 is a solution. More details below.

The result of calling gcc / c99 -M is identical, but that doesn't mean anything! The explanation for this behavior is preprocessor macros (in particular, GNU extensions such as Mat).

More details:

 cat -n main.c 1 #include <termios.h> 2 3 int printf(const char *, ...); 4 5 int main(void) 6 { 7 printf("%d\n", CRTSCTS); 8 return 0; 9 } gcc main.c -o main --std=c89 -> 'CRTSCTS' undeclared compilation error gcc main.c -o main --std=cgnu89 -> successfully compiled 

This behavior is for c99 and gnu99!

As Cameron said, -M output is identical:

 gcc -M --std=c89 main.c | grep termios.h | nl 1 main.o: main.c /usr/include/termios.h /usr/include/features.h \ 2 /usr/include/arm-linux-gnueabihf/bits/termios.h gcc -M --std=gnu89 main.c | grep termios.h | nl 1 main.o: main.c /usr/include/termios.h /usr/include/features.h \ 2 /usr/include/arm-linux-gnueabihf/bits/termios.h \ 

CRTSCTS is defined in the /termios.h bits when __USE_MISC is defined

  1 #ifdef __USE_MISC 2 # define CIBAUD 002003600000 /* input baud rate (not used) */ 3 # define CMSPAR 010000000000 /* mark or space (stick) parity */ 4 # define CRTSCTS 020000000000 /* flow control */ 

Take a look at __USE_MISC.

 gcc -M /usr/include/termios.h | nl 1 termios.o: /usr/include/termios.h /usr/include/features.h \ 2 /usr/include/arm-linux-gnueabihf/bits/predefs.h \ 3 /usr/include/arm-linux-gnueabihf/sys/cdefs.h \ 4 /usr/include/arm-linux-gnueabihf/bits/wordsize.h \ 5 /usr/include/arm-linux-gnueabihf/gnu/stubs.h \ 6 /usr/include/arm-linux-gnueabihf/bits/types.h \ 7 /usr/include/arm-linux-gnueabihf/bits/typesizes.h \ 8 /usr/include/arm-linux-gnueabihf/bits/termios.h \ 9 /usr/include/arm-linux-gnueabihf/sys/ttydefaults.h 

First, features.h, contains the definition of __USE_MISC, but only when defining _BSD_SOURCE or _SVID_SOURCE

 grep 'define __USE_MISC' /usr/include/features.h -B 1 | nl 1 #if defined _BSD_SOURCE || defined _SVID_SOURCE 2 # define __USE_MISC 1 

and _BSD_SOURCE and _SVID_SOURCE are defined when _GNU_SOURCE or "nothing" is defined

  1 #ifdef _GNU_SOURCE 2 # undef _ISOC95_SOURCE 3 # define _ISOC95_SOURCE 1 4 # undef _ISOC99_SOURCE 5 # define _ISOC99_SOURCE 1 6 # undef _POSIX_SOURCE 7 # define _POSIX_SOURCE 1 8 # undef _POSIX_C_SOURCE 9 # define _POSIX_C_SOURCE 200809L 10 # undef _XOPEN_SOURCE 11 # define _XOPEN_SOURCE 700 12 # undef _XOPEN_SOURCE_EXTENDED 13 # define _XOPEN_SOURCE_EXTENDED 1 14 # undef _LARGEFILE64_SOURCE 15 # define _LARGEFILE64_SOURCE 1 16 # undef _BSD_SOURCE 17 # define _BSD_SOURCE 1 18 # undef _SVID_SOURCE 19 # define _SVID_SOURCE 1 20 # undef _ATFILE_SOURCE 21 # define _ATFILE_SOURCE 1 22 #endif 23 /* If nothing (other than _GNU_SOURCE) is defined, 24 define _BSD_SOURCE and _SVID_SOURCE. */ 25 #if (!defined __STRICT_ANSI__ && !defined _ISOC99_SOURCE && \ 26 !defined _POSIX_SOURCE && !defined _POSIX_C_SOURCE && \ 27 !defined _XOPEN_SOURCE && !defined _BSD_SOURCE && !defined _SVID_SOURCE) 28 # define _BSD_SOURCE 1 29 # define _SVID_SOURCE 1 30 #endif 
+4
source

As requested by xtreye, and since the official answer explains, but doesn’t explicitly list the solution, we both fixed it using the -std=gnu99 compiler.

Hope this helps.

+2
source

Source: https://habr.com/ru/post/1206935/


All Articles