-
Notifications
You must be signed in to change notification settings - Fork 635
Expand file tree
/
Copy pathtradstdc.h
More file actions
583 lines (542 loc) · 18.1 KB
/
Copy pathtradstdc.h
File metadata and controls
583 lines (542 loc) · 18.1 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
/* NetHack 5.0 tradstdc.h $NHDT-Date: 1781973090 2026/06/20 16:31:30 $ $NHDT-Branch: NetHack-5.0 $:$NHDT-Revision: 1.71 $ */
/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
/*-Copyright (c) Robert Patrick Rankin, 2006. */
/* NetHack may be freely redistributed. See license for details. */
#ifndef TRADSTDC_H
#define TRADSTDC_H
#if defined(DUMB) && !defined(NOVOID)
#define NOVOID
#endif
#ifdef NOVOID
#define void int
#endif
/*
* Borland C provides enough ANSI C compatibility in its Borland C++
* mode to warrant this. But it does not set __STDC__ unless it compiles
* in its ANSI keywords only mode, which prevents use of <dos.h> and
* far pointer use.
*/
#if (defined(__STDC__) || defined(__TURBOC__)) && !defined(NOTSTDC)
#define NHSTDC
#endif
#if defined(ultrix) && defined(__STDC__) && !defined(__LANGUAGE_C)
/* Ultrix seems to be in a constant state of flux. This check attempts to
* set up ansi compatibility if it wasn't set up correctly by the compiler.
*/
#ifdef mips
#define __mips mips
#endif
#ifdef LANGUAGE_C
#define __LANGUAGE_C LANGUAGE_C
#endif
#endif
/*
* ANSI X3J11 detection.
* Makes substitutes for compatibility with the old C standard.
*/
/* Decide how to handle variable parameter lists:
* USE_STDARG means use the ANSI <stdarg.h> facilities (only ANSI compilers
* should do this, and only if the library supports it).
* USE_VARARGS means use the <varargs.h> facilities. Again, this should only
* be done if the library supports it. ANSI is *not* required for this.
* Otherwise, the kludgy old methods are used.
*/
/* #define USE_VARARGS */ /* use <varargs.h> instead of <stdarg.h> */
/* #define USE_OLDARGS */ /* don't use any variable argument facilities */
#if defined(apollo) /* Apollos have stdarg(3) but not stdarg.h */
#define USE_VARARGS
#endif
#if !defined(USE_STDARG) && !defined(USE_VARARGS) && !defined(USE_OLDARGS)
/* the old VARARGS and OLDARGS stuff is still here, but since we're
requiring C99 these days it's unlikely to be useful */
#define USE_STDARG
#endif
#ifdef NEED_VARARGS /* only define these if necessary */
/*
* These changed in 3.6.0. VA_END() provides a hidden
* closing brace to complement VA_DECL()'s hidden opening brace, so code
* started with VA_DECL() needs an extra opening brace to complement
* the explicit final closing brace. This was done so that the source
* would look less strange, where VA_DECL() appeared to introduce a
* function whose opening brace was missing; there are now visible and
* invisible braces at beginning and end. Sample usage:
void foo VA_DECL(int, arg) --macro expansion has a hidden opening brace
{ --explicit opening brace (actually introduces a nested block)
VA_START(bar);
...code for foo...
VA_END(); --expansion provides a closing brace for the nested block
} --closing brace, pairs with the hidden one in VA_DECL()
* Reading the code--or using source browsing tools which match braces--
* results in seeing a matched set of braces. Usage of VA_END() is
* potentially trickier, but nethack uses it in a straightforward manner.
*/
#ifdef USE_STDARG
#include <stdarg.h>
#define VA_DECL(typ1, var1) \
(typ1 var1, ...) \
{ \
va_list the_args;
#define VA_DECL2(typ1, var1, typ2, var2) \
(typ1 var1, typ2 var2, ...) \
{ \
va_list the_args;
#define VA_INIT(var1, typ1)
#define VA_NEXT(var1, typ1) (var1 = va_arg(the_args, typ1))
#define VA_ARGS the_args
#define VA_START(x) va_start(the_args, x)
#define VA_END() \
va_end(the_args); \
}
#define VA_PASS1(a1) a1
#if defined(ULTRIX_PROTO) && !defined(_VA_LIST_)
#define _VA_LIST_ /* prevents multiple def in stdio.h */
#endif
#else
#ifdef USE_VARARGS
#include <varargs.h>
#define VA_DECL(typ1, var1) \
(va_alist) va_dcl \
{ \
va_list the_args; \
typ1 var1;
#define VA_DECL2(typ1, var1, typ2, var2) \
(va_alist) va_dcl \
{ \
va_list the_args; \
typ1 var1; \
typ2 var2;
#define VA_ARGS the_args
#define VA_START(x) va_start(the_args)
#define VA_INIT(var1, typ1) var1 = va_arg(the_args, typ1)
#define VA_NEXT(var1, typ1) (var1 = va_arg(the_args, typ1))
#define VA_END() \
va_end(the_args); \
}
#define VA_PASS1(a1) a1
#else
/*USE_OLDARGS*/
/*
* CAVEAT: passing double (including float promoted to double) will
* almost certainly break this, as would any integer type bigger than
* sizeof (char *).
* NetHack avoids floating point, and any configuration able to use
* 'long long int' or I64P32 or the like should be using USE_STDARG.
*/
#ifndef VA_TYPE
typedef const char *vA;
#define VA_TYPE
#endif
#define VA_ARGS arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9
#define VA_DECL(typ1, var1) \
(var1, VA_ARGS) typ1 var1; vA VA_ARGS; \
{
#define VA_DECL2(typ1, var1, typ2, var2) \
(var1, var2, VA_ARGS) typ1 var1; typ2 var2; vA VA_ARGS; \
{
#define VA_START(x)
#define VA_INIT(var1, typ1)
/* This is inherently risky, and should only be attempted as a
very last resort; manipulating arguments which haven't actually
been passed may or may not cause severe trouble depending on
the function-calling/argument-passing mechanism being used.
[nethack's core doesn't use VA_NEXT() so doesn't use VA_SHIFT()
either, and this definition is just retained for completeness.
lev_comp does use VA_NEXT(), but it passes all 'argX' arguments.
Note: as of 5.0.0, lev_comp doesn't exist anymore.]
*/
#define VA_SHIFT() \
(arg1 = arg2, arg2 = arg3, arg3 = arg4, arg4 = arg5, arg5 = arg6, \
arg6 = arg7, arg7 = arg8, arg8 = arg9, arg9 = 0)
#define VA_NEXT(var1, typ1) ((var1 = (typ1) arg1), VA_SHIFT(), var1)
#define VA_END() }
/* needed in pline.c, where full number of arguments is known and expected */
#define VA_PASS1(a1) \
(vA) a1, (vA) 0, (vA) 0, (vA) 0, (vA) 0, (vA) 0, (vA) 0, (vA) 0, (vA) 0
#endif
#endif
#endif /* NEED_VARARGS */
/* generic pointer, always a macro; genericptr_t is usually a typedef */
#define genericptr void *
#ifndef genericptr_t
typedef genericptr genericptr_t; /* (void *) or (char *) */
#endif
#ifndef NO_PTR_FMT
/* We actually want to know which systems have an ANSI run-time library
* to know which support the %p format for printing pointers.
* Since we require C99 or later, assume the library supports it. */
#define HAS_PTR_FMT
#endif
/*
* According to ANSI C, prototypes for old-style function definitions like
* int func(arg) short arg; { ... }
* must specify widened arguments (char and short to int, float to double),
* int func(int);
* same as how narrow arguments get passed when there is no prototype info.
* However, various compilers accept shorter arguments (char, short, etc.)
* in prototypes and do typechecking with them. Therefore this mess to
* allow the better typechecking while also allowing some prototypes for
* the ANSI compilers so people quit trying to fix the prototypes to match
* the standard and thus lose the typechecking.
*/
#if defined(MSDOS) && !defined(__GO32__)
#define UNWIDENED_PROTOTYPES
#endif
#if defined(AMIGA) && !defined(AZTEC_50)
#define UNWIDENED_PROTOTYPES
#endif
#if defined(macintosh) && (defined(__SC__) || defined(__MRC__))
#define WIDENED_PROTOTYPES
#endif
#if defined(__MWERKS__) && defined(__BEOS__)
#define UNWIDENED_PROTOTYPES
#endif
#if defined(WIN32)
#define UNWIDENED_PROTOTYPES
#endif
#if defined(ULTRIX_PROTO) && defined(ULTRIX_CC20)
#define UNWIDENED_PROTOTYPES
#endif
#if defined(apollo)
#define UNWIDENED_PROTOTYPES
#endif
#ifndef UNWIDENED_PROTOTYPES
#if defined(NHSTDC) || defined(ULTRIX_PROTO) || defined(THINK_C)
#ifndef WIDENED_PROTOTYPES
#define WIDENED_PROTOTYPES
#endif
#endif
#endif
/* this applies to both VMS and Digital Unix/HP Tru64 */
#ifdef WIDENED_PROTOTYPES
/* ANSI C uses "value preserving rules", where 'unsigned char' and
'unsigned short' promote to 'int' if signed int is big enough to hold
all possible values, rather than traditional "sign preserving rules"
where 'unsigned char' and 'unsigned short' promote to 'unsigned int'.
However, the ANSI C rules aren't binding on non-ANSI compilers.
When DEC C (aka Compaq C, then HP C) is in non-standard 'common' mode
it supports prototypes that expect widened types, but it uses the old
sign preserving rules for how to widen narrow unsigned types. (In its
default 'relaxed' mode, __STDC__ is 1 and uchar widens to 'int'.) */
#if defined(__DECC) && (!defined(__STDC__) || !__STDC__)
#define UCHAR_P unsigned int
#endif
#endif
/* These are used for arguments within VDECL prototype declarations.
*/
#ifdef UNWIDENED_PROTOTYPES
#define CHAR_P char
#define SCHAR_P schar
#define UCHAR_P uchar
#define XCHAR_P coordxy
#define SHORT_P short
#ifndef SKIP_BOOLEAN
#define BOOLEAN_P boolean
#endif
#define ALIGNTYP_P aligntyp
#else
#ifdef WIDENED_PROTOTYPES
#define CHAR_P int
#define SCHAR_P int
#ifndef UCHAR_P
#define UCHAR_P int
#endif
#define XCHAR_P int
#define SHORT_P int
#define BOOLEAN_P int
#define ALIGNTYP_P int
#else
/* Neither widened nor unwidened prototypes. Argument list expansion
* by VDECL always empty; all xxx_P vanish so defs aren't needed. */
#endif
#endif
/* OBJ_P and MONST_P should _only_ be used for declaring function pointers.
*/
#if defined(ULTRIX_PROTO) && !defined(__STDC__)
/* The ultrix 2.0 and 2.1 compilers (on Ultrix 4.0 and 4.2 respectively) can't
* handle "struct obj *" constructs in prototypes. Their bugs are different,
* but both seem to work if we put "void*" in the prototype instead. This
* gives us minimal prototype checking but avoids the compiler bugs.
*/
#define OBJ_P void *
#define MONST_P void *
#else
#define OBJ_P struct obj *
#define MONST_P struct monst *
#endif
#if 0
/* The problem below is still the case through 4.0.5F, but the suggested
* compiler flags in the Makefiles suppress the nasty messages, so we don't
* need to be quite so drastic.
*/
#if defined(__sgi) && !defined(__GNUC__)
/*
* As of IRIX 4.0.1, /bin/cc claims to be an ANSI compiler, but it thinks
* it's impossible for a prototype to match an old-style definition with
* unwidened argument types. Thus, we have to turn off all NetHack
* prototypes, and avoid declaring several system functions, since the system
* include files have prototypes and the compiler also complains that
* prototyped and unprototyped declarations don't match.
*/
#undef VDECL
#define VDECL(f, p) f()
#endif
#endif
/* MetaWare High-C defaults to unsigned chars */
/* AIX 3.2 needs this also */
#if defined(__HC__) || defined(_AIX32)
#undef signed
#endif
/*
* Language
* Standard
*
* NetHack 5.0 range
* /
* /
* C2y X NetHack 3.6 and earlier range
* C23 X /
* C17 X X
* C11 X X
* C99 X X
* C89 X
*
*
* The NetHack 5.0 source code currently makes use of the following
* C99 (and above) language features:
*
* commas at the end of enumerator lists
* variable declarations in for loop initializers
* mixing declarations and code
* variadic macros
* 'long long'
*
* The NetHack 5.0 source code adheres to the following greater-than C99
* language restrictions:
*
* Removal of K&R function definitions
* Removal of implicit int
*/
/*
* Provide a shorthand way of checking for a certain C standard
* in the NetHack header files by always setting NH_C to one
* of three possible values (as of January 2025):
*
* NH_C >= 202300L Being compiled under C23 or greater
* NH_C >= 199900L Being compiled under C99 or greater
* NH_C >= 198900L Being compiled under C89 or greater,
* or C std could not be determined.
*/
#if defined(__STDC_VERSION__)
#if (__STDC_VERSION__ >= 202000L)
#define NH_C 202300L
#else
#define NH_C 199900L
#endif /* C23 or C99 */
#else /* __STDC_VERSION not defined */
#define NH_C 198900L
#endif /* __STDC_VERSION not defined */
#ifndef NH_C
#define NH_C 198900L
#endif
/* NH_C is now defined to 198900L or 199900L or 202300L */
#if NH_C >= 202300L
/* Give first priority to standard */
#ifndef __has_c_attribute
#define __has_c_attribute(x) 0
#endif
/*
* noreturn
*/
#ifndef ATTRNORETURN
#define ATTRNORETURN [[noreturn]]
/* #warning [[noreturn]] from C23 */
#endif /* ATTRNORETURN not defined */
/*
* fallthrough
*/
#if __has_c_attribute(fallthrough)
/* Standard attribute is available, use it. */
#define FALLTHROUGH [[fallthrough]]
/* #warning [[fallthrough]] from C23 */
#endif /* __has_c_attribute(fallthrough) */
/*
* maybe_unused
*/
#if __has_c_attribute(maybe_unused)
#ifndef ATTRUNUSED
#define ATTRUNUSED [[maybe_unused]]
#endif
#endif /* __has_c_attribute(maybe_unused) */
#endif /* NH_C >= 202300L */
/*
* Compiler-specific
*/
#ifdef __clang__
/* clang's gcc emulation is sufficient for nethack's usage */
#ifndef __GNUC__
#define __GNUC__ 5 /* high enough for returns_nonnull */
#endif
#endif
/*
* gcc (and also clang which masquerades as__GNUC__==5 due to #define above)
*
* Allow gcc2 and above to check parameters of printf-like calls with
* -Wformat; append this to a prototype declaration (see pline() in extern.h).
*/
#ifdef __GNUC__
#if (__GNUC__ >= 2) && !defined(USE_OLDARGS)
#define PRINTF_F(f, v) __attribute__((format(printf, f, v)))
#endif
#if (__GNUC__ > 3) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1)
#define PRINTF_F_PTR(f, v) PRINTF_F(f, v)
#endif
#if __GNUC__ >= 3
#ifndef ATTRUNUSED
#define UNUSED __attribute__((unused))
#endif
#ifndef ATTRNORETURN
#ifndef NORETURN
#define NORETURN __attribute__((noreturn))
/* #warning NORETURN __attribute__((noreturn)) from __GNUC__ >= 3 */
#endif /* NORETURN */
#endif /* ATTRNORETURN */
#endif /* __GNUC__ >= 3 */
#if __GNUC__ >= 5
#ifndef NONNULLS_DEFINED
#define DO_DEFINE_NONNULLS
#endif /* !NONNULLS_DEFINED */
/* #pragma message is available */
#define NH_PRAGMA_MESSAGE 1
#endif /* __GNUC__ greater than or equal to 5 */
#if (!defined(__linux__) && !defined(MACOS)) || defined(GCC_URWARN)
/* disable gcc's __attribute__((__warn_unused_result__)) since explicitly
discarding the result by casting to (void) is not accepted as a 'use' */
#define __warn_unused_result__ /*empty*/
#define warn_unused_result /*empty*/
#endif /* GCC_URWARN || !__linux || !MACOS */
#endif /* __GNUC__ || clang masquerading as __GNUC__==5 */
/*
* clang-specific
*
*/
#if defined(__clang__)
#ifndef FALLTHROUGH
#if defined(__clang_major__)
#if __clang_major__ >= 9
#define FALLTHROUGH __attribute__((fallthrough))
/* #warning FALLTHROUGH __attribute__((fallthrough)) from clang */
#endif /* __clang_major__ greater than or equal to 9 */
#endif /* __clang_major__ is defined */
#endif /* FALLTHROUGH */
#if !defined(DO_DEFINE_NONNULLS)
#define DO_DEFINE_NONNULLS
#endif
#endif /* __clang__ */
/*
* NONNULL args
*/
#if defined(DO_DEFINE_NONNULLS) && !defined(NONNULLS_DEFINED)
#define NONNULL __attribute__((returns_nonnull))
#define NONNULLPTRS __attribute__((nonnull))
#define NONNULLARG1 __attribute__((nonnull (1)))
#define NONNULLARG2 __attribute__((nonnull (2)))
#define NONNULLARG3 __attribute__((nonnull (3)))
#define NONNULLARG4 __attribute__((nonnull (4)))
#define NONNULLARG5 __attribute__((nonnull (5)))
#define NONNULLARG6 __attribute__((nonnull (6)))
#define NONNULLARG7 __attribute__((nonnull (7))) /* for bhit() */
#define NONNULLARG12 __attribute__((nonnull (1, 2)))
#define NONNULLARG23 __attribute__((nonnull (2, 3)))
#define NONNULLARG123 __attribute__((nonnull (1, 2, 3)))
#define NONNULLARG13 __attribute__((nonnull (1, 3)))
#define NONNULLARG14 __attribute__((nonnull (1, 4))) /* for query_category */
#define NONNULLARG134 __attribute__((nonnull (1, 3, 4))) /* for do_stone_mon */
#define NONNULLARG145 __attribute__((nonnull (1, 4, 5))) /* find_roll_to_hit */
#define NONNULLARG17 __attribute__((nonnull (1, 7))) /* for askchain() */
#define NONNULLARG24 __attribute__((nonnull (2, 4))) /* query_objlist() */
#define NONNULLARG45 __attribute__((nonnull (4, 5))) /* do_screen_descri... */
#define NONNULLS_DEFINED
#undef DO_DEFINE_NONNULLS
#endif /* DO_DEFINE_NONNULLS && !NONNULLS_DEFINED */
/*
* Microsoft compiler
*/
#ifdef _MSC_VER
#ifndef ATTRNORETURN
#define ATTRNORETURN __declspec(noreturn)
/* #warning ATTRNORETURN __declspec(noreturn) from _MSC_VER */
#endif
/* #pragma message is available */
#define NH_PRAGMA_MESSAGE 1
#endif /* _MSC_VER */
#if !defined(UNUSED) && defined(ATTRUNUSED)
#define UNUSED ATTRUNUSED
#endif
/* Fallback implementations */
#ifndef PRINTF_F
#define PRINTF_F(f, v)
#endif
#ifndef PRINTF_F_PTR
#define PRINTF_F_PTR(f, v)
#endif
#ifndef UNUSED
#define UNUSED
#endif
#ifndef ATTRUNUSED
#define ATTRUNUSED
#endif
#ifndef FALLTHROUGH
#define FALLTHROUGH
#endif
#ifndef ATTRNORETURN
#define ATTRNORETURN
#endif
#ifndef NORETURN
#define NORETURN
#endif
#ifndef NONNULLS_DEFINED
#define NONNULL
#define NONNULLPTRS
#define NONNULLARG1
#define NONNULLARG2
#define NONNULLARG3
#define NONNULLARG4
#define NONNULLARG5
#define NONNULLARG6
#define NONNULLARG7
#define NONNULLARG12
#define NONNULLARG23
#define NONNULLARG123
#define NONNULLARG13
#define NONNULLARG14
#define NONNULLARG134
#define NONNULLARG145
#define NONNULLARG17
#define NONNULLARG24
#define NONNULLARG45
#define NONNULLS_DEFINED
#endif /* NONNULLS_DEFINED */
#ifndef NO_NNARGS
#define NO_NNARGS /*empty*/
#endif /* NO_NNARGS */
/*
* Allow gcc and clang to catch the use of non-C99 functions that
* NetHack has replaced with a C99 standard function. The old non-C99
* function will cause a link failure on non-Unix platforms,
* so it is preferrable to catch it early, during compile.
*/
#if !defined(X11_BUILD) && !defined(__cplusplus)
#if defined(__GNUC__) && !defined(__clang__)
#if __GNUC__ >= 12
extern char *index(const char *s, int c) __attribute__ ((unavailable));
extern char *rindex(const char *s, int c) __attribute__ ((unavailable));
#endif
#endif
#if defined(__clang__)
#if __clang_major__ >= 7
extern char *index(const char *s, int c) __attribute__ ((unavailable));
extern char *rindex(const char *s, int c) __attribute__ ((unavailable));
#endif
#endif
#endif
#endif /* TRADSTDC_H */