diff --git a/clang/lib/Headers/stddef.h b/clang/lib/Headers/stddef.h --- a/clang/lib/Headers/stddef.h +++ b/clang/lib/Headers/stddef.h @@ -8,22 +8,46 @@ */ #if !defined(__STDDEF_H) || defined(__need_ptrdiff_t) || \ - defined(__need_size_t) || defined(__need_wchar_t) || \ - defined(__need_NULL) || defined(__need_wint_t) + defined(__need_size_t) || defined(__need_rsize_t) || \ + defined(__need_wchar_t) || defined(__need_NULL) || \ + defined(__need_nullptr_t) || defined(__need_unreachable) || \ + defined(__need_max_align_t) || defined(__need_offsetof) || \ + defined(__need_wint_t) || \ + (defined(__STDC_WANT_LIB_EXT1__) && __STDC_WANT_LIB_EXT1__ >= 1) #if !defined(__need_ptrdiff_t) && !defined(__need_size_t) && \ - !defined(__need_wchar_t) && !defined(__need_NULL) && \ - !defined(__need_wint_t) + !defined(__need_rsize_t) && !defined(__need_wchar_t) && \ + !defined(__need_NULL) && !defined(__need_nullptr_t) && \ + !defined(__need_unreachable) && !defined(__need_max_align_t) && \ + !defined(__need_offsetof) && !defined(__need_wint_t) /* Always define miscellaneous pieces when modules are available. */ #if !__has_feature(modules) #define __STDDEF_H #endif #define __need_ptrdiff_t #define __need_size_t +/* ISO9899:2011 7.20 (C11 Annex K): Define rsize_t if __STDC_WANT_LIB_EXT1__ is + * enabled. */ +#if defined(__STDC_WANT_LIB_EXT1__) && __STDC_WANT_LIB_EXT1__ >= 1 +#define __need_rsize_t +#endif #define __need_wchar_t #define __need_NULL -#define __need_STDDEF_H_misc -/* __need_wint_t is intentionally not defined here. */ +#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 202311L) || \ + defined(__cplusplus) +#define __need_nullptr_t +#endif +#if defined(__STDC_VERSION__) && __STDC_VERSION__ >= 202311L +#define __need_unreachable +#endif +#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 201112L) || \ + (defined(__cplusplus) && __cplusplus >= 201103L) +#define __need_max_align_t +#endif +#define __need_offsetof +/* wint_t is provided by and not . It's here + * for compatibility, but must be explicitly requested. Therefore + * __need_wint_t is intentionally not defined here. */ #endif #if defined(__need_ptrdiff_t) @@ -48,18 +72,16 @@ #undef __need_size_t #endif /*defined(__need_size_t) */ -#if defined(__need_STDDEF_H_misc) -/* ISO9899:2011 7.20 (C11 Annex K): Define rsize_t if __STDC_WANT_LIB_EXT1__ is - * enabled. */ -#if (defined(__STDC_WANT_LIB_EXT1__) && __STDC_WANT_LIB_EXT1__ >= 1 && \ - !defined(_RSIZE_T)) || __has_feature(modules) +#if defined(__need_rsize_t) +#if !defined(_RSIZE_T) || __has_feature(modules) /* Always define rsize_t when modules are available. */ #if !__has_feature(modules) #define _RSIZE_T #endif typedef __SIZE_TYPE__ rsize_t; #endif -#endif /* defined(__need_STDDEF_H_misc) */ +#undef __need_rsize_t +#endif /* defined(__need_rsize_t) */ #if defined(__need_wchar_t) #if !defined(__cplusplus) || (defined(_MSC_VER) && !_NATIVE_WCHAR_T_DEFINED) @@ -88,32 +110,37 @@ #else # define NULL ((void*)0) #endif +#undef __need_NULL +#endif /* defined(__need_NULL) */ + +#if defined(__need_nullptr_t) #ifdef __cplusplus #if defined(_MSC_EXTENSIONS) && defined(_NATIVE_NULLPTR_SUPPORTED) -namespace std { typedef decltype(nullptr) nullptr_t; } +namespace std { +typedef decltype(nullptr) nullptr_t; +} using ::std::nullptr_t; #endif -#endif -#undef __need_NULL -#endif /* defined(__need_NULL) */ - -#if defined(__STDC_VERSION__) && __STDC_VERSION__ >= 202311L +#else typedef typeof(nullptr) nullptr_t; -#endif /* defined(__STDC_VERSION__) && __STDC_VERSION__ >= 202311L */ +#endif +#undef __need_nullptr_t +#endif /* defined(__need_nullptr_t) */ -#if defined(__need_STDDEF_H_misc) && defined(__STDC_VERSION__) && \ - __STDC_VERSION__ >= 202311L +#if defined(__need_unreachable) #define unreachable() __builtin_unreachable() -#endif /* defined(__need_STDDEF_H_misc) && >= C23 */ +#undef __need_unreachable +#endif /* defined(__need_unreachable) */ -#if defined(__need_STDDEF_H_misc) -#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 201112L) || \ - (defined(__cplusplus) && __cplusplus >= 201103L) +#if defined(__need_max_align_t) #include "__stddef_max_align_t.h" -#endif +#undef __need_max_align_t +#endif /* defined(__need_max_align_t) */ + +#if defined(__need_offsetof) #define offsetof(t, d) __builtin_offsetof(t, d) -#undef __need_STDDEF_H_misc -#endif /* defined(__need_STDDEF_H_misc) */ +#undef __need_offsetof +#endif /* defined(__need_offsetof) */ /* Some C libraries expect to see a wint_t here. Others (notably MinGW) will use __WINT_TYPE__ directly; accommodate both by requiring __need_wint_t */ diff --git a/clang/test/Headers/stddef.c b/clang/test/Headers/stddef.c new file mode 100644 --- /dev/null +++ b/clang/test/Headers/stddef.c @@ -0,0 +1,46 @@ +// RUN: %clang_cc1 -fsyntax-only -verify=c99 -std=c99 %s +// RUN: %clang_cc1 -fsyntax-only -verify=c11 -std=c11 %s +// RUN: %clang_cc1 -fsyntax-only -verify=c23 -std=c23 %s + +struct astruct { char member; }; + +ptrdiff_t p0; // c99-error{{unknown type name 'ptrdiff_t'}} c11-error{{unknown type}} c23-error{{unknown type}} +size_t s0; // c99-error{{unknown type name 'size_t'}} c11-error{{unknown type}} c23-error{{unknown type}} +rsize_t r0; // c99-error{{unknown type name 'rsize_t'}} c11-error{{unknown type}} c23-error{{unknown type}} +wchar_t wc0; // c99-error{{unknown type name 'wchar_t'}} c11-error{{unknown type}} c23-error{{unknown type}} +void *v0 = NULL; // c99-error{{use of undeclared identifier 'NULL'}} c11-error{{undeclared identifier}} c23-error{{undeclared identifier}} +nullptr_t n0; // c99-error{{unknown type name 'nullptr_t'}} c11-error{{unknown type}} c23-error{{unknown type}} +static void f0(void) { unreachable(); } // c99-error{{call to undeclared function 'unreachable'}} c11-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m0; // c99-error{{unknown type name 'max_align_t'}} c11-error{{unknown type}} c23-error{{unknown type}} +size_t o0 = offsetof(struct astruct, member); // c99-error{{unknown type name 'size_t'}} c99-error{{call to undeclared function 'offsetof'}} c99-error{{expected expression}} c99-error{{use of undeclared identifier 'member'}} \ + c11-error{{unknown type}} c11-error{{undeclared function}} c11-error{{expected expression}} c11-error{{undeclared identifier}} \ + c23-error{{unknown type}} c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi0; // c99-error{{unknown type name 'wint_t'}} c11-error{{unknown type}} c23-error{{unknown type}} + +#include + +ptrdiff_t p1; +size_t s1; +rsize_t r1; // c99-error{{unknown type}} c11-error{{unknown type}} c23-error{{unknown type}} + // c99-note@stddef.h:*{{'size_t' declared here}} c11-note@stddef.h:*{{'size_t' declared here}} c23-note@stddef.h:*{{'size_t' declared here}} +wchar_t wc1; +void *v1 = NULL; +nullptr_t n1; // c99-error{{unknown type}} c11-error{{unknown type}} +static void f1(void) { unreachable(); } // c99-error{{undeclared function}} c11-error{{undeclared function}} +max_align_t m1; // c99-error{{unknown type}} +size_t o1 = offsetof(struct astruct, member); +wint_t wi1; // c99-error{{unknown type}} c11-error{{unknown type}} c23-error{{unknown type}} + +// rsize_t needs to be opted into via __STDC_WANT_LIB_EXT1__ >= 1. +#define __STDC_WANT_LIB_EXT1__ 1 +#include +ptrdiff_t p2; +size_t s2; +rsize_t r2; +wchar_t wc2; +void *v2 = NULL; +nullptr_t n2; // c99-error{{unknown type}} c11-error{{unknown type}} +static void f2(void) { unreachable(); } // c99-error{{undeclared function}} c11-error{{undeclared function}} +max_align_t m2; // c99-error{{unknown type}} +size_t o2 = offsetof(struct astruct, member); +wint_t wi2; // c99-error{{unknown type}} c11-error{{unknown type}} c23-error{{unknown type}} diff --git a/clang/test/Headers/stddefneeds.c b/clang/test/Headers/stddefneeds.c new file mode 100644 --- /dev/null +++ b/clang/test/Headers/stddefneeds.c @@ -0,0 +1,169 @@ +// RUN: %clang_cc1 -fsyntax-only -verify=c99 -std=c99 %s +// RUN: %clang_cc1 -fsyntax-only -verify=c23 -std=c23 %s + +// Use C99 to verify that __need_ can be used to get types that wouldn't normally be available. + +struct astruct { char member; }; + +ptrdiff_t p0; // c99-error{{unknown type name 'ptrdiff_t'}} c23-error{{unknown type}} +size_t s0; // c99-error{{unknown type name 'size_t'}} c23-error{{unknown type}} +rsize_t r0; // c99-error{{unknown type name 'rsize_t'}} c23-error{{unknown type}} +wchar_t wc0; // c99-error{{unknown type name 'wchar_t'}} c23-error{{unknown type}} +void *v0 = NULL; // c99-error{{use of undeclared identifier 'NULL'}} c23-error{{undeclared identifier}} +nullptr_t n0; // c99-error{{unknown type name 'nullptr_t'}} c23-error{{unknown type}} +static void f0(void) { unreachable(); } // c99-error{{call to undeclared function 'unreachable'}} c23-error{{undeclared identifier 'unreachable'}} +max_align_t m0; // c99-error{{unknown type name 'max_align_t'}} c23-error{{unknown type}} +size_t o0 = offsetof(struct astruct, member); // c99-error{{unknown type name 'size_t'}} c99-error{{call to undeclared function 'offsetof'}} c99-error{{expected expression}} c99-error{{use of undeclared identifier 'member'}} \ + c23-error{{unknown type name 'size_t'}} c23-error{{undeclared identifier 'offsetof'}} c23-error{{expected expression}} c23-error{{use of undeclared identifier 'member'}} +wint_t wi0; // c99-error{{unknown type name 'wint_t'}} c23-error{{unknown type}} + +#define __need_ptrdiff_t +#include + +ptrdiff_t p1; +size_t s1; // c99-error{{unknown type}} c23-error{{unknown type}} +rsize_t r1; // c99-error{{unknown type}} c23-error{{unknown type}} +wchar_t wc1; // c99-error{{unknown type}} c23-error{{unknown type}} +void *v1 = NULL; // c99-error{{undeclared identifier}} c23-error{{undeclared identifier}} +nullptr_t n1; // c99-error{{unknown type}} c23-error{{unknown type}} +static void f1(void) { unreachable(); } // c99-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m1; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o1 = offsetof(struct astruct, member); // c99-error{{unknown type}} c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{unknown type}} c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi1; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_size_t +#include + +ptrdiff_t p2; +size_t s2; +rsize_t r2; // c99-error{{unknown type}} c23-error{{unknown type}} + // c99-note@stddef.h:*{{'size_t' declared here}} c23-note@stddef.h:*{{'size_t' declared here}} +wchar_t wc2; // c99-error{{unknown type}} c23-error{{unknown type}} +void *v2 = NULL; // c99-error{{undeclared identifier}} c23-error{{undeclared identifier}} +nullptr_t n2; // c99-error{{unknown type}} c23-error{{unknown type}} +static void f2(void) { unreachable(); } // c99-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m2; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o2 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi2; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_rsize_t +#include + +ptrdiff_t p3; +size_t s3; +rsize_t r3; +wchar_t wc3; // c99-error{{unknown type}} c23-error{{unknown type}} +void *v3 = NULL; // c99-error{{undeclared identifier}} c23-error{{undeclared identifier}} +nullptr_t n3; // c99-error{{unknown type}} c23-error{{unknown type}} +static void f3(void) { unreachable(); } // c99-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m3; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o3 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi3; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_wchar_t +#include + +ptrdiff_t p4; +size_t s4; +rsize_t r4; +wchar_t wc4; +void *v4 = NULL; // c99-error{{undeclared identifier}} c23-error{{undeclared identifier}} +nullptr_t n4; // c99-error{{unknown type}} c23-error{{unknown type}} +static void f4(void) { unreachable(); } // c99-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m4; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o4 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi4; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_NULL +#include + +ptrdiff_t p5; +size_t s5; +rsize_t r5; +wchar_t wc5; +void *v5 = NULL; +nullptr_t n5; // c99-error{{unknown type}} c23-error{{unknown type}} +static void f5(void) { unreachable(); } // c99-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m5; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o5 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi5; // c99-error{{unknown type}} c23-error{{unknown type}} + +// __need_nullptr_t generates an error in // c99-error@stddef.h:*{{expected function body}} + +ptrdiff_t p6; +size_t s6; +rsize_t r6; +wchar_t wc6; +void *v6 = NULL; +nullptr_t n6; // c99-error{{unknown type}} +static void f6(void) { unreachable(); } // c99-error{{undeclared function}} c23-error{{undeclared identifier}} +max_align_t m6; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o6 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi6; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_unreachable +#include + +ptrdiff_t p7; +size_t s7; +rsize_t r7; +wchar_t wc7; +void *v7 = NULL; +nullptr_t n7 ; // c99-error{{unknown type}} +static void f7(void) { unreachable(); } +max_align_t m7; // c99-error{{unknown type}} c23-error{{unknown type}} +size_t o7 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi7; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_max_align_t +#include + +ptrdiff_t p8; +size_t s8; +rsize_t r8; +wchar_t wc8; +void *v8 = NULL; +nullptr_t n8; // c99-error{{unknown type}} +static void f8(void) { unreachable(); } +max_align_t m8; +size_t o8 = offsetof(struct astruct, member); // c99-error{{expected expression}} c99-error{{undeclared identifier}} \ + c23-error{{undeclared identifier}} c23-error{{expected expression}} c23-error{{undeclared identifier}} +wint_t wi8; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_offsetof +#include + +ptrdiff_t p9; +size_t s9; +rsize_t r9; +nullptr_t n9; // c99-error{{unknown type}} +static void f9(void) { unreachable(); } +wchar_t wc9; +void *v9 = NULL; +max_align_t m9; +size_t o9 = offsetof(struct astruct, member); +wint_t wi9; // c99-error{{unknown type}} c23-error{{unknown type}} + +#define __need_wint_t +#include + +ptrdiff_t p10; +size_t s10; +rsize_t r10; +wchar_t wc10; +void *v10 = NULL; +nullptr_t n10; // c99-error{{unknown type}} +static void f10(void) { unreachable(); } +max_align_t m10; +size_t o10 = offsetof(struct astruct, member); +wint_t wi10;