cpp: Use #pragma once instead of #ifndef guards
[ghc.git] / libraries / base / include / HsBase.h
1 /* -----------------------------------------------------------------------------
2 *
3 * (c) The University of Glasgow 2001-2004
4 *
5 * Definitions for package `base' which are visible in Haskell land.
6 *
7 * ---------------------------------------------------------------------------*/
8
9 #pragma once
10
11 #include "HsBaseConfig.h"
12
13 /* ultra-evil... */
14 #undef PACKAGE_BUGREPORT
15 #undef PACKAGE_NAME
16 #undef PACKAGE_STRING
17 #undef PACKAGE_TARNAME
18 #undef PACKAGE_VERSION
19
20 /* Needed to get the macro version of errno on some OSs (eg. Solaris).
21 We must do this, because these libs are only compiled once, but
22 must work in both single-threaded and multi-threaded programs. */
23 #define _REENTRANT 1
24
25 #include "HsFFI.h"
26
27 #include <stdio.h>
28 #include <stdlib.h>
29 #include <math.h>
30
31 #if HAVE_SYS_TYPES_H
32 #include <sys/types.h>
33 #endif
34 #if HAVE_UNISTD_H
35 #include <unistd.h>
36 #endif
37 #if HAVE_SYS_STAT_H
38 #include <sys/stat.h>
39 #endif
40 #if HAVE_FCNTL_H
41 # include <fcntl.h>
42 #endif
43 #if HAVE_TERMIOS_H
44 #include <termios.h>
45 #endif
46 #if HAVE_SIGNAL_H
47 #include <signal.h>
48 /* Ultra-ugly: OpenBSD uses broken macros for sigemptyset and sigfillset (missing casts) */
49 #if __OpenBSD__
50 #undef sigemptyset
51 #undef sigfillset
52 #endif
53 #endif
54 #if HAVE_ERRNO_H
55 #include <errno.h>
56 #endif
57 #if HAVE_STRING_H
58 #include <string.h>
59 #endif
60 #if HAVE_UTIME_H
61 #include <utime.h>
62 #endif
63 #if HAVE_SYS_UTSNAME_H
64 #include <sys/utsname.h>
65 #endif
66 #if HAVE_GETTIMEOFDAY
67 # if HAVE_SYS_TIME_H
68 # include <sys/time.h>
69 # endif
70 #elif HAVE_GETCLOCK
71 # if HAVE_SYS_TIMERS_H
72 # define POSIX_4D9 1
73 # include <sys/timers.h>
74 # endif
75 #endif
76 #if HAVE_TIME_H
77 #include <time.h>
78 #endif
79 #if HAVE_SYS_TIMEB_H && !defined(__FreeBSD__)
80 #include <sys/timeb.h>
81 #endif
82 #if HAVE_WINDOWS_H
83 #include <windows.h>
84 #endif
85 #if HAVE_SYS_TIMES_H
86 #include <sys/times.h>
87 #endif
88 #if HAVE_WINSOCK_H && defined(_WIN32)
89 #include <winsock.h>
90 #endif
91 #if HAVE_LIMITS_H
92 #include <limits.h>
93 #endif
94 #if HAVE_WCTYPE_H
95 #include <wctype.h>
96 #endif
97 #if HAVE_INTTYPES_H
98 # include <inttypes.h>
99 #elif HAVE_STDINT_H
100 # include <stdint.h>
101 #endif
102 #ifdef HAVE_CLOCK_GETTIME
103 # ifdef _POSIX_MONOTONIC_CLOCK
104 # define CLOCK_ID CLOCK_MONOTONIC
105 # else
106 # define CLOCK_ID CLOCK_REALTIME
107 # endif
108 #elif defined(darwin_HOST_OS)
109 # include <mach/mach.h>
110 # include <mach/mach_time.h>
111 #endif
112
113 #if !defined(_WIN32)
114 # if HAVE_SYS_RESOURCE_H
115 # include <sys/resource.h>
116 # endif
117 #endif
118
119 #if !HAVE_GETRUSAGE && HAVE_SYS_SYSCALL_H
120 # include <sys/syscall.h>
121 # if defined(SYS_GETRUSAGE) /* hpux_HOST_OS */
122 # define getrusage(a, b) syscall(SYS_GETRUSAGE, a, b)
123 # define HAVE_GETRUSAGE 1
124 # endif
125 #endif
126
127 /* For System */
128 #if HAVE_SYS_WAIT_H
129 #include <sys/wait.h>
130 #endif
131 #if HAVE_VFORK_H
132 #include <vfork.h>
133 #endif
134 #include "WCsubst.h"
135
136 #if defined(_WIN32)
137 /* in Win32Utils.c */
138 extern void maperrno (void);
139 extern int maperrno_func(DWORD dwErrorCode);
140 extern HsWord64 getMonotonicUSec(void);
141 #endif
142
143 #if defined(_WIN32)
144 #include <io.h>
145 #include <fcntl.h>
146 #include <shlobj.h>
147 #include <share.h>
148 #endif
149
150 #if HAVE_SYS_SELECT_H
151 #include <sys/select.h>
152 #endif
153
154 /* in inputReady.c */
155 extern int fdReady(int fd, int write, int msecs, int isSock);
156
157 /* -----------------------------------------------------------------------------
158 INLINE functions.
159
160 These functions are given as inlines here for when compiling via C,
161 but we also generate static versions into the cbits library for
162 when compiling to native code.
163 -------------------------------------------------------------------------- */
164
165 #ifndef INLINE
166 # if defined(_MSC_VER)
167 # define INLINE extern __inline
168 # else
169 # define INLINE static inline
170 # endif
171 #endif
172
173 INLINE int __hscore_get_errno(void) { return errno; }
174 INLINE void __hscore_set_errno(int e) { errno = e; }
175
176 INLINE HsInt
177 __hscore_bufsiz(void)
178 {
179 return BUFSIZ;
180 }
181
182 INLINE int
183 __hscore_o_binary(void)
184 {
185 #if defined(_MSC_VER)
186 return O_BINARY;
187 #else
188 return CONST_O_BINARY;
189 #endif
190 }
191
192 INLINE int
193 __hscore_o_rdonly(void)
194 {
195 #ifdef O_RDONLY
196 return O_RDONLY;
197 #else
198 return 0;
199 #endif
200 }
201
202 INLINE int
203 __hscore_o_wronly( void )
204 {
205 #ifdef O_WRONLY
206 return O_WRONLY;
207 #else
208 return 0;
209 #endif
210 }
211
212 INLINE int
213 __hscore_o_rdwr( void )
214 {
215 #ifdef O_RDWR
216 return O_RDWR;
217 #else
218 return 0;
219 #endif
220 }
221
222 INLINE int
223 __hscore_o_append( void )
224 {
225 #ifdef O_APPEND
226 return O_APPEND;
227 #else
228 return 0;
229 #endif
230 }
231
232 INLINE int
233 __hscore_o_creat( void )
234 {
235 #ifdef O_CREAT
236 return O_CREAT;
237 #else
238 return 0;
239 #endif
240 }
241
242 INLINE int
243 __hscore_o_excl( void )
244 {
245 #ifdef O_EXCL
246 return O_EXCL;
247 #else
248 return 0;
249 #endif
250 }
251
252 INLINE int
253 __hscore_o_trunc( void )
254 {
255 #ifdef O_TRUNC
256 return O_TRUNC;
257 #else
258 return 0;
259 #endif
260 }
261
262 INLINE int
263 __hscore_o_noctty( void )
264 {
265 #ifdef O_NOCTTY
266 return O_NOCTTY;
267 #else
268 return 0;
269 #endif
270 }
271
272 INLINE int
273 __hscore_o_nonblock( void )
274 {
275 #ifdef O_NONBLOCK
276 return O_NONBLOCK;
277 #else
278 return 0;
279 #endif
280 }
281
282 INLINE int
283 __hscore_ftruncate( int fd, off_t where )
284 {
285 #if defined(HAVE_FTRUNCATE)
286 return ftruncate(fd,where);
287 #elif defined(HAVE__CHSIZE)
288 return _chsize(fd,where);
289 #else
290 // ToDo: we should use _chsize_s() on Windows which allows a 64-bit
291 // offset, but it doesn't seem to be available from mingw at this time
292 // --SDM (01/2008)
293 #error at least ftruncate or _chsize functions are required to build
294 #endif
295 }
296
297 INLINE int
298 __hscore_setmode( int fd, HsBool toBin )
299 {
300 #if defined(_WIN32)
301 return _setmode(fd,(toBin == HS_BOOL_TRUE) ? _O_BINARY : _O_TEXT);
302 #else
303 return 0;
304 #endif
305 }
306
307 #if defined(_WIN32)
308 // We want the versions of stat/fstat/lseek that use 64-bit offsets,
309 // and you have to ask for those explicitly. Unfortunately there
310 // doesn't seem to be a 64-bit version of truncate/ftruncate, so while
311 // hFileSize and hSeek will work with large files, hSetFileSize will not.
312 typedef struct _stati64 struct_stat;
313 typedef off64_t stsize_t;
314 #else
315 typedef struct stat struct_stat;
316 typedef off_t stsize_t;
317 #endif
318
319 INLINE HsInt
320 __hscore_sizeof_stat( void )
321 {
322 return sizeof(struct_stat);
323 }
324
325 INLINE time_t __hscore_st_mtime ( struct_stat* st ) { return st->st_mtime; }
326 INLINE stsize_t __hscore_st_size ( struct_stat* st ) { return st->st_size; }
327 #if !defined(_MSC_VER)
328 INLINE mode_t __hscore_st_mode ( struct_stat* st ) { return st->st_mode; }
329 INLINE dev_t __hscore_st_dev ( struct_stat* st ) { return st->st_dev; }
330 INLINE ino_t __hscore_st_ino ( struct_stat* st ) { return st->st_ino; }
331 #endif
332
333 #if defined(_WIN32)
334 INLINE int __hscore_stat(wchar_t *file, struct_stat *buf) {
335 return _wstati64(file,buf);
336 }
337
338 INLINE int __hscore_fstat(int fd, struct_stat *buf) {
339 return _fstati64(fd,buf);
340 }
341 INLINE int __hscore_lstat(wchar_t *fname, struct_stat *buf )
342 {
343 return _wstati64(fname,buf);
344 }
345 #else
346 INLINE int __hscore_stat(char *file, struct_stat *buf) {
347 return stat(file,buf);
348 }
349
350 INLINE int __hscore_fstat(int fd, struct_stat *buf) {
351 return fstat(fd,buf);
352 }
353
354 INLINE int __hscore_lstat( const char *fname, struct stat *buf )
355 {
356 #if HAVE_LSTAT
357 return lstat(fname, buf);
358 #else
359 return stat(fname, buf);
360 #endif
361 }
362 #endif
363
364 #if HAVE_TERMIOS_H
365 INLINE tcflag_t __hscore_lflag( struct termios* ts ) { return ts->c_lflag; }
366
367 INLINE void
368 __hscore_poke_lflag( struct termios* ts, tcflag_t t ) { ts->c_lflag = t; }
369
370 INLINE unsigned char*
371 __hscore_ptr_c_cc( struct termios* ts )
372 { return (unsigned char*) &ts->c_cc; }
373
374 INLINE HsInt
375 __hscore_sizeof_termios( void )
376 {
377 #ifndef _WIN32
378 return sizeof(struct termios);
379 #else
380 return 0;
381 #endif
382 }
383 #endif
384
385 #if !defined(_WIN32)
386 INLINE HsInt
387 __hscore_sizeof_sigset_t( void )
388 {
389 return sizeof(sigset_t);
390 }
391 #endif
392
393 INLINE int
394 __hscore_echo( void )
395 {
396 #ifdef ECHO
397 return ECHO;
398 #else
399 return 0;
400 #endif
401
402 }
403
404 INLINE int
405 __hscore_tcsanow( void )
406 {
407 #ifdef TCSANOW
408 return TCSANOW;
409 #else
410 return 0;
411 #endif
412
413 }
414
415 INLINE int
416 __hscore_icanon( void )
417 {
418 #ifdef ICANON
419 return ICANON;
420 #else
421 return 0;
422 #endif
423 }
424
425 INLINE int __hscore_vmin( void )
426 {
427 #ifdef VMIN
428 return VMIN;
429 #else
430 return 0;
431 #endif
432 }
433
434 INLINE int __hscore_vtime( void )
435 {
436 #ifdef VTIME
437 return VTIME;
438 #else
439 return 0;
440 #endif
441 }
442
443 INLINE int __hscore_sigttou( void )
444 {
445 #ifdef SIGTTOU
446 return SIGTTOU;
447 #else
448 return 0;
449 #endif
450 }
451
452 INLINE int __hscore_sig_block( void )
453 {
454 #ifdef SIG_BLOCK
455 return SIG_BLOCK;
456 #else
457 return 0;
458 #endif
459 }
460
461 INLINE int __hscore_sig_setmask( void )
462 {
463 #ifdef SIG_SETMASK
464 return SIG_SETMASK;
465 #else
466 return 0;
467 #endif
468 }
469
470 #ifndef _WIN32
471 INLINE size_t __hscore_sizeof_siginfo_t (void)
472 {
473 return sizeof(siginfo_t);
474 }
475 #endif
476
477 INLINE int
478 __hscore_f_getfl( void )
479 {
480 #ifdef F_GETFL
481 return F_GETFL;
482 #else
483 return 0;
484 #endif
485 }
486
487 INLINE int
488 __hscore_f_setfl( void )
489 {
490 #ifdef F_SETFL
491 return F_SETFL;
492 #else
493 return 0;
494 #endif
495 }
496
497 INLINE int
498 __hscore_f_setfd( void )
499 {
500 #ifdef F_SETFD
501 return F_SETFD;
502 #else
503 return 0;
504 #endif
505 }
506
507 INLINE long
508 __hscore_fd_cloexec( void )
509 {
510 #ifdef FD_CLOEXEC
511 return FD_CLOEXEC;
512 #else
513 return 0;
514 #endif
515 }
516
517 // defined in rts/RtsStartup.c.
518 extern void* __hscore_get_saved_termios(int fd);
519 extern void __hscore_set_saved_termios(int fd, void* ts);
520
521 #ifdef _WIN32
522 INLINE int __hscore_open(wchar_t *file, int how, mode_t mode) {
523 if ((how & O_WRONLY) || (how & O_RDWR) || (how & O_APPEND))
524 return _wsopen(file,how | _O_NOINHERIT,_SH_DENYNO,mode);
525 // _O_NOINHERIT: see #2650
526 else
527 return _wsopen(file,how | _O_NOINHERIT,_SH_DENYNO,mode);
528 // _O_NOINHERIT: see #2650
529 }
530 #else
531 INLINE int __hscore_open(char *file, int how, mode_t mode) {
532 return open(file,how,mode);
533 }
534 #endif
535
536 #if darwin_HOST_OS
537 // You should not access _environ directly on Darwin in a bundle/shared library.
538 // See #2458 and http://developer.apple.com/library/mac/#documentation/Darwin/Reference/ManPages/man7/environ.7.html
539 #include <crt_externs.h>
540 INLINE char **__hscore_environ(void) { return *(_NSGetEnviron()); }
541 #else
542 /* ToDo: write a feature test that doesn't assume 'environ' to
543 * be in scope at link-time. */
544 extern char** environ;
545 INLINE char **__hscore_environ(void) { return environ; }
546 #endif
547
548 /* lossless conversions between pointers and integral types */
549 INLINE void * __hscore_from_uintptr(uintptr_t n) { return (void *)n; }
550 INLINE void * __hscore_from_intptr (intptr_t n) { return (void *)n; }
551 INLINE uintptr_t __hscore_to_uintptr (void *p) { return (uintptr_t)p; }
552 INLINE intptr_t __hscore_to_intptr (void *p) { return (intptr_t)p; }
553
554 void errorBelch2(const char*s, char *t);
555 void debugBelch2(const char*s, char *t);