w32: Change an npth_eselect arg to unsigned.
[npth.git] / w32 / npth.h
1 /* npth.h - a lightweight implementation of pth over pthread.
2    Copyright (C) 2011 g10 Code GmbH
3
4    This file is part of NPTH.
5
6    NPTH is free software; you can redistribute it and/or modify it
7    under the terms of either
8
9    - the GNU Lesser General Public License as published by the Free
10    Software Foundation; either version 3 of the License, or (at
11    your option) any later version.
12
13    or
14
15    - the GNU General Public License as published by the Free
16    Software Foundation; either version 2 of the License, or (at
17    your option) any later version.
18
19    or both in parallel, as here.
20
21    NPTH is distributed in the hope that it will be useful, but WITHOUT
22    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
23    or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
24    License for more details.
25
26    You should have received a copies of the GNU General Public License
27    and the GNU Lesser General Public License along with this program;
28    if not, see <http://www.gnu.org/licenses/>.  */
29
30 #ifndef _NPTH_H
31 #define _NPTH_H
32
33 #include <sys/types.h>
34 #include <time.h>
35 #include <errno.h>
36
37 #include <winsock2.h>
38 #include <ws2tcpip.h>
39 #include <windows.h>
40
41 #ifdef __cplusplus
42 extern "C" {
43 #if 0 /* (Keep Emacsens' auto-indent happy.) */
44 }
45 #endif
46 #endif
47
48 struct msghdr;
49
50 /* At least with version 2 the mingw-w64 headers define timespec.  For
51    older compilers we keep our replacement.  */
52 #if __MINGW64_VERSION_MAJOR < 2
53 struct timespec {
54   long tv_sec;                 /* seconds */
55   long tv_nsec;                /* nanoseconds */
56 };
57 #endif /*__MINGW64_VERSION_MAJOR < 2*/
58
59
60 #ifndef ETIMEDOUT
61 #define ETIMEDOUT 10060  /* This is WSAETIMEDOUT.  */
62 #endif
63 #ifndef EOPNOTSUPP
64 #define EOPNOTSUPP 10045 /* This is WSAEOPNOTSUPP.  */
65 #endif
66
67
68 int npth_init (void);
69
70 typedef struct npth_attr_s *npth_attr_t;
71 typedef unsigned long int npth_t;
72 typedef struct npth_mutexattr_s *npth_mutexattr_t;
73 typedef struct npth_mutex_s *npth_mutex_t;
74 typedef struct npth_rwlockattr_s *npth_rwlockattr_t;
75 typedef struct npth_rwlock_s *npth_rwlock_t;
76 typedef struct npth_condattr_s *npth_condattr_t;
77 typedef struct npth_cond_s *npth_cond_t;
78
79 int npth_attr_init (npth_attr_t *attr);
80 int npth_attr_destroy (npth_attr_t *attr);
81 #define NPTH_CREATE_JOINABLE 0
82 #define NPTH_CREATE_DETACHED 1
83 int npth_attr_getdetachstate(npth_attr_t *attr, int *detachstate);
84 int npth_attr_setdetachstate(npth_attr_t *attr, int detachstate);
85 int npth_getname_np (npth_t target_thread, char *buf, size_t buflen);
86 int npth_setname_np (npth_t target_thread, const char *name);
87
88 int npth_create (npth_t *newthread, const npth_attr_t *attr,
89                  void *(*start_routine) (void *), void *arg);
90
91 npth_t npth_self (void);
92
93 int npth_join (npth_t th, void **thread_return);
94 int npth_detach (npth_t th);
95 void npth_exit (void *retval);
96
97 typedef DWORD npth_key_t;
98 int npth_key_create (npth_key_t *key,
99                      void (*destr_function) (void *));
100 int npth_key_delete (npth_key_t key);
101 void *npth_getspecific (npth_key_t key);
102 int npth_setspecific (npth_key_t key, const void *pointer);
103
104 int npth_mutexattr_init (npth_mutexattr_t *attr);
105 int npth_mutexattr_destroy (npth_mutexattr_t *attr);
106 int npth_mutexattr_gettype (const npth_mutexattr_t *attr,
107                             int *kind);
108 int npth_mutexattr_settype (npth_mutexattr_t *attr, int kind);
109 #define NPTH_MUTEX_NORMAL 0
110 #define NPTH_MUTEX_RECURSIVE 1
111 #define NPTH_MUTEX_ERRORCHECK 2
112 #define NPTH_MUTEX_DEFAULT NPTH_MUTEX_NORMAL
113
114 #define NPTH_MUTEX_INITIALIZER ((npth_mutex_t) -1)
115 #define NPTH_RECURSIVE_MUTEX_INITIALIZER_NP ((npth_mutex_t) -2)
116 #define NPTH_ERRORCHECK_MUTEX_INITIALIZER_NP ((npth_mutex_t) -3)
117 int npth_mutex_init (npth_mutex_t *mutex, const npth_mutexattr_t *mutexattr);
118 int npth_mutex_destroy (npth_mutex_t *mutex);
119 int npth_mutex_trylock(npth_mutex_t *mutex);
120 int npth_mutex_lock(npth_mutex_t *mutex);
121 int npth_mutex_timedlock(npth_mutex_t *mutex, const struct timespec *abstime);
122 int npth_mutex_unlock(npth_mutex_t *mutex);
123
124 int npth_rwlockattr_init (npth_rwlockattr_t *attr);
125 int npth_rwlockattr_destroy (npth_rwlockattr_t *attr);
126 int npth_rwlockattr_gettype_np (const npth_rwlockattr_t *attr,
127                                 int *kind);
128 int npth_rwlockattr_settype_np (npth_rwlockattr_t *attr, int kind);
129 #define NPTH_RWLOCK_PREFER_READER_NP 0
130 #define NPTH_RWLOCK_PREFER_WRITER_NP 1
131 #define NPTH_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP 2
132 #define NPTH_RWLOCK_DEFAULT_NP NPTH_RWLOCK_PREFER_READER_NP
133 #define NPTH_RWLOCK_INITIALIZER ((npth_rwlock_t) -1)
134 #define NPTH_RWLOCK_WRITER_NONRECURSIVE_INITIALIZER_NP ((npth_rwlock_t) -2)
135
136 /* For now, we don't support any rwlock attributes.  */
137 int npth_rwlock_init (npth_rwlock_t *rwlock,
138                       const npth_rwlockattr_t *attr);
139 int npth_rwlock_destroy (npth_rwlock_t *rwlock);
140 int npth_rwlock_tryrdlock (npth_rwlock_t *rwlock);
141 int npth_rwlock_rdlock (npth_rwlock_t *rwlock);
142 int npth_rwlock_timedrdlock (npth_rwlock_t *rwlock,
143                              const struct timespec *abstime);
144 int npth_rwlock_trywrlock (npth_rwlock_t *rwlock);
145
146 int npth_rwlock_wrlock (npth_rwlock_t *rwlock);
147 int npth_rwlock_timedwrlock (npth_rwlock_t *rwlock,
148                              const struct timespec *abstime);
149 int npth_rwlock_unlock (npth_rwlock_t *rwlock);
150
151 #define NPTH_COND_INITIALIZER ((npth_cond_t) -1)
152 /* For now, we don't support any cond attributes.  */
153 int npth_cond_init (npth_cond_t *cond,
154                     const npth_condattr_t *cond_attr);
155 int npth_cond_broadcast (npth_cond_t *cond);
156 int npth_cond_signal (npth_cond_t *cond);
157 int npth_cond_destroy (npth_cond_t *cond);
158 int npth_cond_wait (npth_cond_t *cond, npth_mutex_t *mutex);
159 int npth_cond_timedwait (npth_cond_t *cond, npth_mutex_t *mutex,
160                          const struct timespec *abstime);
161
162 int npth_usleep(unsigned int usec);
163 unsigned int npth_sleep(unsigned int sec);
164
165 pid_t npth_waitpid(pid_t pid, int *status, int options);
166 int npth_system(const char *cmd);
167
168 #if 0
169 /* We do not support this on windows.  */
170 int npth_sigmask(int how, const sigset_t *set, sigset_t *oldset);
171 int npth_sigwait(const sigset_t *set, int *sig);
172 #endif
173
174 int npth_connect(int s, const struct sockaddr *addr, socklen_t addrlen);
175 int npth_accept(int s, struct sockaddr *addr, socklen_t *addrlen);
176 /* Only good for sockets!  */
177 int npth_select(int nfd, fd_set *rfds, fd_set *wfds, fd_set *efds,
178                 struct timeval *timeout);
179 #if 0
180 /* We do not support this on windows.  */
181 int npth_pselect(int nfd, fd_set *rfds, fd_set *wfds, fd_set *efds,
182                  const struct timespec *timeout, const sigset_t *sigmask);
183 #endif
184 /* Wait on the FDs (only good for sockets!) and the
185    INVALID_HANDLE_VALUE terminated list of extra events.  On return
186    (even on error), the bits in EVENTS_SET will contain the extra
187    events that occured (which means that there can only be up to 31
188    extra events).  */
189 int npth_eselect(int nfd, fd_set *rfds, fd_set *wfds, fd_set *efds,
190                  const struct timespec *timeout,
191                  HANDLE *events, unsigned int *events_set);
192
193 ssize_t npth_read(int fd, void *buf, size_t nbytes);
194 ssize_t npth_write(int fd, const void *buf, size_t nbytes);
195 int npth_recvmsg (int fd, struct msghdr *msg, int flags);
196 int npth_sendmsg (int fd, const struct msghdr *msg, int flags);
197
198 void npth_unprotect (void);
199 void npth_protect (void);
200
201
202 int npth_clock_gettime(struct timespec *tp);
203
204 /* CMP may be ==, < or >.  Do not use <= or >=.  */
205 #define npth_timercmp(t1, t2, cmp)                                      \
206   (((t1)->tv_sec == (t2)->tv_sec) ?                                     \
207    ((t1)->tv_nsec cmp (t2)->tv_nsec) :                                  \
208    ((t1)->tv_sec cmp (t2)->tv_sec))
209 #define npth_timeradd(t1, t2, result)                                   \
210   do {                                                                  \
211     (result)->tv_sec = (t1)->tv_sec + (t2)->tv_sec;                     \
212     (result)->tv_nsec = (t1)->tv_nsec + (t2)->tv_nsec;                  \
213     if ((result)->tv_nsec >= 1000000000)                                \
214       {                                                                 \
215         ++(result)->tv_sec;                                             \
216         (result)->tv_nsec -= 1000000000;                                \
217       }                                                                 \
218   } while (0)
219 #define npth_timersub(t1, t2, result)                                   \
220   do {                                                                  \
221     (result)->tv_sec = (t1)->tv_sec - (t2)->tv_sec;                     \
222     (result)->tv_nsec = (t1)->tv_nsec - (t2)->tv_nsec;                  \
223     if ((result)->tv_nsec < 0) {                                        \
224       --(result)->tv_sec;                                               \
225       (result)->tv_nsec += 1000000000;                                  \
226     }                                                                   \
227   } while (0)
228
229 \f
230 #if 0
231 /* We do not support this on windows.  */
232 void npth_sigev_init (void);
233 void npth_sigev_add (int signum);
234 void npth_sigev_fini (void);
235 sigset_t *npth_sigev_sigmask (void);
236 int npth_sigev_get_pending (int *r_signum);
237 #endif
238
239 #if 0 /* (Keep Emacsens' auto-indent happy.) */
240 {
241 #endif
242 #ifdef __cplusplus
243 }
244 #endif
245 #endif /*_NPTH_H*/