tutil.c - vaccinewars - be a doctor and try to vaccinate the world
HTML git clone git://src.adamsgaard.dk/vaccinewars
DIR Log
DIR Files
DIR Refs
DIR README
DIR LICENSE
---
tutil.c (5511B)
---
1 /************************************************************************
2 * util.c Miscellaneous utility and portability functions *
3 * Copyright (C) 1998-2021 Ben Webb *
4 * Email: benwebb@users.sf.net *
5 * WWW: https://dopewars.sourceforge.io/ *
6 * *
7 * This program is free software; you can redistribute it and/or *
8 * modify it under the terms of the GNU General Public License *
9 * as published by the Free Software Foundation; either version 2 *
10 * of the License, or (at your option) any later version. *
11 * *
12 * This program is distributed in the hope that it will be useful, *
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
15 * GNU General Public License for more details. *
16 * *
17 * You should have received a copy of the GNU General Public License *
18 * along with this program; if not, write to the Free Software *
19 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, *
20 * MA 02111-1307, USA. *
21 ************************************************************************/
22
23 #ifdef HAVE_CONFIG_H
24 #include <config.h>
25 #endif
26
27 #ifdef HAVE_UNISTD_H
28 #include <unistd.h>
29 #endif
30
31 #ifdef HAVE_STDLIB_H
32 #include <stdlib.h>
33 #endif
34
35 #ifdef HAVE_FCNTL_H
36 #include <fcntl.h>
37 #endif
38
39 #ifdef CYGWIN
40 #include <conio.h>
41 #endif
42
43 #include <string.h>
44 #include "util.h"
45 #include "dopewars.h"
46
47 #ifndef HAVE_GETOPT
48 char *optarg;
49
50 static int apos = 1; /* Skip argv[0], the executable name */
51
52 int getopt(int argc, char *const argv[], const char *str)
53 {
54 int i, c;
55 char *pt;
56
57 while (apos < argc && argv[apos]) {
58 if (argv[apos][0] != '-') {
59 apos++;
60 return 0;
61 }
62 for (i = 1; i < strlen(argv[apos]); i++) {
63 c = argv[apos][i];
64 pt = strchr(str, c);
65 if (pt) {
66 argv[apos][i] = '-';
67 if (*(pt + 1) == ':') {
68 if (apos + 1 < argc && i == strlen(argv[apos]) - 1) {
69 apos++;
70 optarg = argv[apos];
71 apos++;
72 } else
73 return 0;
74 }
75 return c;
76 }
77 }
78 apos++;
79 }
80 return EOF;
81 }
82 #endif /* HAVE_GETOPT */
83
84
85 #ifdef CYGWIN /* Code for native Win32 build under Cygwin */
86
87 void sigemptyset(int *mask)
88 {
89 }
90
91 void sigaddset(int *mask, int sig)
92 {
93 }
94
95 int sigaction(int sig, struct sigaction *sact, char *pt)
96 {
97 return 0;
98 }
99
100 void sigprocmask(int flag, int *mask, char *pt)
101 {
102 }
103
104 /*static gboolean IsKeyPressed()
105 {
106 INPUT_RECORD ConsoleIn;
107 DWORD NumConsoleIn;
108
109 while (PeekConsoleInput(hIn, &ConsoleIn, 1, &NumConsoleIn)
110 && NumConsoleIn == 1) {
111 if (ConsoleIn.EventType == KEY_EVENT
112 && ConsoleIn.Event.KeyEvent.bKeyDown) {
113 return TRUE;
114 } else {
115 ReadConsoleInput(hIn, &ConsoleIn, 1, &NumConsoleIn);
116 }
117 }
118 return FALSE;
119 }*/
120
121 int bselect(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds,
122 struct timeval *tm)
123 {
124 int retval;
125 struct timeval tv, *tp;
126 fd_set localread, localexcept;
127 char CheckKbHit = 0;
128
129 if (nfds == 0 && tm) {
130 Sleep(tm->tv_sec * 1000 + tm->tv_usec / 1000);
131 return 0;
132 }
133 if (FD_ISSET(0, readfds)) {
134 if (nfds == 1)
135 return 1;
136 tp = &tv;
137 CheckKbHit = 1;
138 FD_CLR(0, readfds);
139 } else
140 tp = tm;
141 while (1) {
142 tv.tv_sec = 0;
143 tv.tv_usec = 250000;
144
145 if (readfds)
146 memcpy(&localread, readfds, sizeof(fd_set));
147 if (exceptfds)
148 memcpy(&localexcept, exceptfds, sizeof(fd_set));
149 if (CheckKbHit && kbhit())
150 tv.tv_usec = 0;
151 retval = select(nfds, readfds, writefds, exceptfds, tp);
152 if (retval == SOCKET_ERROR)
153 return retval;
154 if (CheckKbHit && kbhit()) {
155 retval++;
156 FD_SET(0, readfds);
157 }
158 if (retval > 0 || !CheckKbHit)
159 break;
160 if (CheckKbHit && tm) {
161 if (tm->tv_usec >= 250000)
162 tm->tv_usec -= 250000;
163 else if (tm->tv_sec) {
164 tm->tv_usec += 750000;
165 tm->tv_sec--;
166 } else
167 break;
168 }
169 if (readfds)
170 memcpy(readfds, &localread, sizeof(fd_set));
171 if (exceptfds)
172 memcpy(exceptfds, &localexcept, sizeof(fd_set));
173 }
174 return retval;
175 }
176
177 /* We don't do locking under Win32 right now */
178 int ReadLock(FILE * fp)
179 {
180 return 0;
181 }
182
183 int WriteLock(FILE * fp)
184 {
185 return 0;
186 }
187
188 void ReleaseLock(FILE * fp)
189 {
190 }
191
192 #else /* Code for Unix build */
193
194 #include <errno.h>
195
196 static int DoLock(FILE * fp, int l_type)
197 {
198 struct flock lk;
199
200 lk.l_type = l_type;
201 lk.l_whence = lk.l_start = lk.l_len = 0;
202 lk.l_pid = 0;
203
204 do {
205 if (fcntl(fileno(fp), F_SETLKW, &lk) == 0) {
206 return 0;
207 }
208 } while (errno == EINTR);
209 return 1;
210 }
211
212 int ReadLock(FILE * fp)
213 {
214 return DoLock(fp, F_RDLCK);
215 }
216
217 int WriteLock(FILE * fp)
218 {
219 return DoLock(fp, F_WRLCK);
220 }
221
222 void ReleaseLock(FILE * fp)
223 {
224 (void)DoLock(fp, F_UNLCK);
225 }
226
227 #endif /* CYGWIN */
228
229 /*
230 * On systems with select, sleep for "microsec" microseconds.
231 */
232 void MicroSleep(int microsec)
233 {
234 #if defined(HAVE_SELECT) || CYGWIN
235 struct timeval tv;
236
237 tv.tv_sec = 0;
238 tv.tv_usec = microsec;
239 bselect(0, NULL, NULL, NULL, &tv);
240 #endif
241 }