You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

189 lines
8.3KB

  1. /* This header file provides the reentrancy. */
  2. /* The reentrant system calls here serve two purposes:
  3. 1) Provide reentrant versions of the system calls the ANSI C library
  4. requires.
  5. 2) Provide these system calls in a namespace clean way.
  6. It is intended that *all* system calls that the ANSI C library needs
  7. be declared here. It documents them all in one place. All library access
  8. to the system is via some form of these functions.
  9. The target may provide the needed syscalls by any of the following:
  10. 1) Define the reentrant versions of the syscalls directly.
  11. (eg: _open_r, _close_r, etc.). Please keep the namespace clean.
  12. When you do this, set "syscall_dir" to "syscalls" and add
  13. -DREENTRANT_SYSCALLS_PROVIDED to newlib_cflags in configure.host.
  14. 2) Define namespace clean versions of the system calls by prefixing
  15. them with '_' (eg: _open, _close, etc.). Technically, there won't be
  16. true reentrancy at the syscall level, but the library will be namespace
  17. clean.
  18. When you do this, set "syscall_dir" to "syscalls" in configure.host.
  19. 3) Define or otherwise provide the regular versions of the syscalls
  20. (eg: open, close, etc.). The library won't be reentrant nor namespace
  21. clean, but at least it will work.
  22. When you do this, add -DMISSING_SYSCALL_NAMES to newlib_cflags in
  23. configure.host.
  24. 4) Define or otherwise provide the regular versions of the syscalls,
  25. and do not supply functional interfaces for any of the reentrant
  26. calls. With this method, the reentrant syscalls are redefined to
  27. directly call the regular system call without the reentrancy argument.
  28. When you do this, specify both -DREENTRANT_SYSCALLS_PROVIDED and
  29. -DMISSING_SYSCALL_NAMES via newlib_cflags in configure.host and do
  30. not specify "syscall_dir".
  31. Stubs of the reentrant versions of the syscalls exist in the libc/reent
  32. source directory and are provided if REENTRANT_SYSCALLS_PROVIDED isn't
  33. defined. These stubs call the native system calls: _open, _close, etc.
  34. if MISSING_SYSCALL_NAMES is *not* defined, otherwise they call the
  35. non-underscored versions: open, close, etc. when MISSING_SYSCALL_NAMES
  36. *is* defined.
  37. By default, newlib functions call the reentrant syscalls internally,
  38. passing a reentrancy structure as an argument. This reentrancy structure
  39. contains data that is thread-specific. For example, the errno value is
  40. kept in the reentrancy structure. If multiple threads exist, each will
  41. keep a separate errno value which is intuitive since the application flow
  42. cannot check for failure reliably otherwise.
  43. The reentrant syscalls are either provided by the platform, by the
  44. libc/reent stubs, or in the case of both MISSING_SYSCALL_NAMES and
  45. REENTRANT_SYSCALLS_PROVIDED being defined, the calls are redefined to
  46. simply call the regular syscalls with no reentrancy struct argument.
  47. A single-threaded application does not need to worry about the reentrancy
  48. structure. It is used internally.
  49. A multi-threaded application needs either to manually manage reentrancy
  50. structures or use dynamic reentrancy.
  51. Manually managing reentrancy structures entails calling special reentrant
  52. versions of newlib functions that have an additional reentrancy argument.
  53. For example, _printf_r. By convention, the first argument is the
  54. reentrancy structure. By default, the normal version of the function
  55. uses the default reentrancy structure: _REENT. The reentrancy structure
  56. is passed internally, eventually to the reentrant syscalls themselves.
  57. How the structures are stored and accessed in this model is up to the
  58. application.
  59. Dynamic reentrancy is specified by the __DYNAMIC_REENT__ flag. This
  60. flag denotes setting up a macro to replace _REENT with a function call
  61. to __getreent(). This function needs to be implemented by the platform
  62. and it is meant to return the reentrancy structure for the current
  63. thread. When the regular C functions (e.g. printf) go to call internal
  64. routines with the default _REENT structure, they end up calling with
  65. the reentrancy structure for the thread. Thus, application code does not
  66. need to call the _r routines nor worry about reentrancy structures. */
  67. /* WARNING: All identifiers here must begin with an underscore. This file is
  68. included by stdio.h and others and we therefore must only use identifiers
  69. in the namespace allotted to us. */
  70. #ifndef _REENT_H_
  71. #ifdef __cplusplus
  72. extern "C" {
  73. #endif
  74. #define _REENT_H_
  75. #include <sys/reent.h>
  76. #include <sys/_types.h>
  77. #define __need_size_t
  78. #define __need_ptrdiff_t
  79. #include <stddef.h>
  80. /* FIXME: not namespace clean */
  81. struct stat;
  82. struct tms;
  83. struct timeval;
  84. struct timezone;
  85. #if defined(REENTRANT_SYSCALLS_PROVIDED) && defined(MISSING_SYSCALL_NAMES)
  86. #define _close_r(__reent, __fd) close(__fd)
  87. #define _execve_r(__reent, __f, __arg, __env) execve(__f, __arg, __env)
  88. #define _fcntl_r(__reent, __fd, __cmd, __arg) fcntl(__fd, __cmd, __arg)
  89. #define _fork_r(__reent) fork()
  90. #define _fstat_r(__reent, __fdes, __stat) fstat(__fdes, __stat)
  91. #define _getpid_r(__reent) getpid()
  92. #define _isatty_r(__reent, __desc) isatty(__desc)
  93. #define _kill_r(__reent, __pid, __signal) kill(__pid, __signal)
  94. #define _link_r(__reent, __oldpath, __newpath) link(__oldpath, __newpath)
  95. #define _lseek_r(__reent, __fdes, __off, __w) lseek(__fdes, __off, __w)
  96. #define _mkdir_r(__reent, __path, __m) mkdir(__path, __m)
  97. #define _open_r(__reent, __path, __flag, __m) open(__path, __flag, __m)
  98. #define _read_r(__reent, __fd, __buff, __cnt) read(__fd, __buff, __cnt)
  99. #define _rename_r(__reent, __old, __new) rename(__old, __new)
  100. #define _sbrk_r(__reent, __incr) sbrk(__incr)
  101. #define _stat_r(__reent, __path, __buff) stat(__path, __buff)
  102. #define _times_r(__reent, __time) times(__time)
  103. #define _unlink_r(__reent, __path) unlink(__path)
  104. #define _wait_r(__reent, __status) wait(__status)
  105. #define _write_r(__reent, __fd, __buff, __cnt) write(__fd, __buff, __cnt)
  106. #define _gettimeofday_r(__reent, __tp, __tzp) gettimeofday(__tp, __tzp)
  107. #ifdef __LARGE64_FILES
  108. #define _lseek64_r(__reent, __fd, __off, __w) lseek64(__fd, __off, __w)
  109. #define _fstat64_r(__reent, __fd, __buff) fstat64(__fd, __buff)
  110. #define _open64_r(__reent, __path, __flag, __m) open64(__path, __flag, __m)
  111. #endif
  112. #else
  113. /* Reentrant versions of system calls. */
  114. extern int _close_r (struct _reent *, int);
  115. extern int _execve_r (struct _reent *, const char *, char *const *, char *const *);
  116. extern int _fcntl_r (struct _reent *, int, int, int);
  117. extern int _fork_r (struct _reent *);
  118. extern int _fstat_r (struct _reent *, int, struct stat *);
  119. extern int _getpid_r (struct _reent *);
  120. extern int _isatty_r (struct _reent *, int);
  121. extern int _kill_r (struct _reent *, int, int);
  122. extern int _link_r (struct _reent *, const char *, const char *);
  123. extern _off_t _lseek_r (struct _reent *, int, _off_t, int);
  124. extern int _mkdir_r (struct _reent *, const char *, int);
  125. extern int _open_r (struct _reent *, const char *, int, int);
  126. extern _ssize_t _read_r (struct _reent *, int, void *, size_t);
  127. extern int _rename_r (struct _reent *, const char *, const char *);
  128. extern void *_sbrk_r (struct _reent *, ptrdiff_t);
  129. extern int _stat_r (struct _reent *, const char *, struct stat *);
  130. extern _CLOCK_T_ _times_r (struct _reent *, struct tms *);
  131. extern int _unlink_r (struct _reent *, const char *);
  132. extern int _wait_r (struct _reent *, int *);
  133. extern _ssize_t _write_r (struct _reent *, int, const void *, size_t);
  134. /* This one is not guaranteed to be available on all targets. */
  135. extern int _gettimeofday_r (struct _reent *, struct timeval *__tp, void *__tzp);
  136. #ifdef __LARGE64_FILES
  137. #if defined(__CYGWIN__)
  138. #define stat64 stat
  139. #endif
  140. struct stat64;
  141. extern _off64_t _lseek64_r (struct _reent *, int, _off64_t, int);
  142. extern int _fstat64_r (struct _reent *, int, struct stat64 *);
  143. extern int _open64_r (struct _reent *, const char *, int, int);
  144. extern int _stat64_r (struct _reent *, const char *, struct stat64 *);
  145. /* Don't pollute namespace if not building newlib. */
  146. #if defined (__CYGWIN__) && !defined (_COMPILING_NEWLIB)
  147. #undef stat64
  148. #endif
  149. #endif
  150. #endif
  151. #ifdef __cplusplus
  152. }
  153. #endif
  154. #endif /* _REENT_H_ */