Sun Nov 8 19:30:53 2015 UTC ()
Add debugging for pollfd


(christos)
diff -r1.11 -r1.12 src/lib/libc/rpc/svc_fdset.c

cvs diff -r1.11 -r1.12 src/lib/libc/rpc/svc_fdset.c (switch to unified diff)

--- src/lib/libc/rpc/svc_fdset.c 2015/11/08 02:46:53 1.11
+++ src/lib/libc/rpc/svc_fdset.c 2015/11/08 19:30:53 1.12
@@ -1,455 +1,477 @@ @@ -1,455 +1,477 @@
1/* $NetBSD: svc_fdset.c,v 1.11 2015/11/08 02:46:53 christos Exp $ */ 1/* $NetBSD: svc_fdset.c,v 1.12 2015/11/08 19:30:53 christos Exp $ */
2 2
3/*- 3/*-
4 * Copyright (c) 2015 The NetBSD Foundation, Inc. 4 * Copyright (c) 2015 The NetBSD Foundation, Inc.
5 * All rights reserved. 5 * All rights reserved.
6 * 6 *
7 * This code is derived from software contributed to The NetBSD Foundation 7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Christos Zoulas. 8 * by Christos Zoulas.
9 * 9 *
10 * Redistribution and use in source and binary forms, with or without 10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions 11 * modification, are permitted provided that the following conditions
12 * are met: 12 * are met:
13 * 1. Redistributions of source code must retain the above copyright 13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer. 14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright 15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the 16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution. 17 * documentation and/or other materials provided with the distribution.
18 * 18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE. 29 * POSSIBILITY OF SUCH DAMAGE.
30 */ 30 */
31 31
32#include <sys/cdefs.h> 32#include <sys/cdefs.h>
33__RCSID("$NetBSD: svc_fdset.c,v 1.11 2015/11/08 02:46:53 christos Exp $"); 33__RCSID("$NetBSD: svc_fdset.c,v 1.12 2015/11/08 19:30:53 christos Exp $");
34 34
35 35
36#include "reentrant.h" 36#include "reentrant.h"
37 37
38#include <sys/fd_set.h> 38#include <sys/fd_set.h>
39 39
40#include <rpc/rpc.h> 40#include <rpc/rpc.h>
41 41
42#ifdef FDSET_DEBUG 42#ifdef FDSET_DEBUG
43#include <stdio.h> 43#include <stdio.h>
44#include <stdarg.h> 44#include <stdarg.h>
45#include <unistd.h> 45#include <unistd.h>
46#include <lwp.h> 46#include <lwp.h>
47#endif 47#endif
48#include <stdlib.h> 48#include <stdlib.h>
49#include <string.h> 49#include <string.h>
50#include <poll.h> 50#include <poll.h>
51 51
52#include "svc_fdset.h" 52#include "svc_fdset.h"
53 53
54#undef svc_fdset 54#undef svc_fdset
55#undef svc_maxfd 55#undef svc_maxfd
56#ifdef _LIBC 56#ifdef _LIBC
57extern __fd_set_256 svc_fdset; 57extern __fd_set_256 svc_fdset;
58#endif 58#endif
59extern int svc_maxfd; 59extern int svc_maxfd;
60int __svc_flags; 60int __svc_flags;
61 61
62struct svc_fdset { 62struct svc_fdset {
63 /* select */ 63 /* select */
64 fd_set *fdset; 64 fd_set *fdset;
65 int fdmax; 65 int fdmax;
66 int fdsize; 66 int fdsize;
67 /* poll */ 67 /* poll */
68 struct pollfd *fdp; 68 struct pollfd *fdp;
69 int fdnum; 69 int fdnum;
70 int fdused; 70 int fdused;
71}; 71};
72 72
73/* The single threaded, one global fd_set version */ 73/* The single threaded, one global fd_set version */
74static struct svc_fdset __svc_fdset; 74static struct svc_fdset __svc_fdset;
75 75
76static thread_key_t fdsetkey = -2; 76static thread_key_t fdsetkey = -2;
77 77
78#ifdef FDSET_DEBUG 78#ifdef FDSET_DEBUG
79 79
80static void __printflike(3, 0) 80static void __printflike(3, 0)
81svc_header(const char *func, size_t line, const char *fmt, va_list ap) 81svc_header(const char *func, size_t line, const char *fmt, va_list ap)
82{ 82{
83 fprintf(stderr, "%s[%d.%d]: %s, %zu: ", getprogname(), (int)getpid(), 83 fprintf(stderr, "%s[%d.%d]: %s, %zu: ", getprogname(), (int)getpid(),
84 (int)_lwp_self(), func, line); 84 (int)_lwp_self(), func, line);
85 vfprintf(stderr, fmt, ap); 85 vfprintf(stderr, fmt, ap);
86 va_end(ap); 86 va_end(ap);
87} 87}
88 88
89static void __printflike(4, 5) 89static void __printflike(4, 5)
90svc_fdset_print(const char *func, size_t line, struct svc_fdset *fds,  90svc_fdset_print(const char *func, size_t line, struct svc_fdset *fds,
91 const char *fmt, ...) 91 const char *fmt, ...)
92{ 92{
93 va_list ap; 93 va_list ap;
94 const char *did = ""; 94 const char *did = "";
95 95
96 va_start(ap, fmt); 96 va_start(ap, fmt);
97 svc_header(func, line, fmt, ap); 97 svc_header(func, line, fmt, ap);
98 va_end(ap); 98 va_end(ap);
99 99
100 fprintf(stderr, "%p[%d] <", fds->fdset, fds->fdmax); 100 fprintf(stderr, "%p[%d] fd_set<", fds->fdset, fds->fdmax);
101 for (int i = 0; i <= fds->fdmax; i++) { 101 for (int i = 0; i <= fds->fdmax; i++) {
102 if (!FD_ISSET(i, fds->fdset)) 102 if (!FD_ISSET(i, fds->fdset))
103 continue; 103 continue;
104 fprintf(stderr, "%s%d", did, i); 104 fprintf(stderr, "%s%d", did, i);
105 did = ", "; 105 did = ", ";
106 } 106 }
 107 did = "";
 108 fprintf(stderr, "> poll<");
 109 for (int i = 0; i < fds->fdused; i++) {
 110 int fd = fds->fdp[i].fd;
 111 if (fd == -1)
 112 continue;
 113 fprintf(stderr, "%s%d", did, fd);
 114 did = ", ";
 115 }
107 fprintf(stderr, ">\n"); 116 fprintf(stderr, ">\n");
108} 117}
109 118
110static void __printflike(3, 4) 119static void __printflike(3, 4)
111svc_print(const char *func, size_t line, const char *fmt, ...) 120svc_print(const char *func, size_t line, const char *fmt, ...)
112{ 121{
113 va_list ap; 122 va_list ap;
114 123
115 va_start(ap, fmt); 124 va_start(ap, fmt);
116 svc_header(func, line, fmt, ap); 125 svc_header(func, line, fmt, ap);
117 va_end(ap); 126 va_end(ap);
118 fprintf(stderr, "\n"); 127 fprintf(stderr, "\n");
119} 128}
120 129
121#define DPRINTF(...) svc_print(__func__, __LINE__, __VA_ARGS__) 130#define DPRINTF(...) svc_print(__func__, __LINE__, __VA_ARGS__)
122#define DPRINTF_FDSET(...) svc_fdset_print(__func__, __LINE__, __VA_ARGS__) 131#define DPRINTF_FDSET(...) svc_fdset_print(__func__, __LINE__, __VA_ARGS__)
123 132
124#else 133#else
125 134
126#define DPRINTF(...) 135#define DPRINTF(...)
127#define DPRINTF_FDSET(...) 136#define DPRINTF_FDSET(...)
128 137
129#endif 138#endif
130 139
131 140
132static inline void 141static inline void
133svc_fdset_sanitize(struct svc_fdset *fds) 142svc_fdset_sanitize(struct svc_fdset *fds)
134{ 143{
135 while (fds->fdmax >= 0 && !FD_ISSET(fds->fdmax, fds->fdset)) 144 while (fds->fdmax >= 0 && !FD_ISSET(fds->fdmax, fds->fdset))
136 fds->fdmax--; 145 fds->fdmax--;
137#ifdef _LIBC 146#ifdef _LIBC
138 /* Compat update */ 147 /* Compat update */
139 if (fds == &__svc_fdset) { 148 if (fds == &__svc_fdset) {
140 svc_fdset = *(__fd_set_256 *)__svc_fdset.fdset; 149 svc_fdset = *(__fd_set_256 *)__svc_fdset.fdset;
141 svc_maxfd = __svc_fdset.fdmax; 150 svc_maxfd = __svc_fdset.fdmax;
142 } 151 }
143#endif 152#endif
144} 153}
145 154
146static void 155static void
147svc_fdset_free(void *v) 156svc_fdset_free(void *v)
148{ 157{
149 struct svc_fdset *fds = v; 158 struct svc_fdset *fds = v;
150 DPRINTF_FDSET(fds, "free"); 159 DPRINTF_FDSET(fds, "free");
151 160
152 free(fds->fdp); 161 free(fds->fdp);
153 free(fds->fdset); 162 free(fds->fdset);
154 free(fds); 163 free(fds);
155} 164}
156 165
157static void 166static void
158svc_pollfd_init(struct pollfd *pfd, int nfd) 167svc_pollfd_init(struct pollfd *pfd, int nfd)
159{ 168{
160 for (int i = 0; i < nfd; i++) { 169 for (int i = 0; i < nfd; i++) {
161 pfd[i].fd = -1; 170 pfd[i].fd = -1;
162 pfd[i].events = POLLIN | POLLPRI | POLLRDNORM | POLLRDBAND; 171 pfd[i].events = POLLIN | POLLPRI | POLLRDNORM | POLLRDBAND;
163 pfd[i].revents = 0; 172 pfd[i].revents = 0;
164 } 173 }
165} 174}
166 175
167static struct pollfd * 176static struct pollfd *
168svc_pollfd_alloc(struct svc_fdset *fds) 177svc_pollfd_alloc(struct svc_fdset *fds)
169{ 178{
 179 if (fds->fdp != NULL)
 180 return fds->fdp;
 181
170 fds->fdnum = FD_SETSIZE; 182 fds->fdnum = FD_SETSIZE;
171 fds->fdp = calloc(fds->fdnum, sizeof(*fds->fdp)); 183 fds->fdp = calloc(fds->fdnum, sizeof(*fds->fdp));
172 if (fds->fdp == NULL) 184 if (fds->fdp == NULL)
173 return NULL; 185 return NULL;
174 svc_pollfd_init(fds->fdp, fds->fdnum); 186 svc_pollfd_init(fds->fdp, fds->fdnum);
175 return fds->fdp; 187 return fds->fdp;
176} 188}
177 189
178 190
179static struct svc_fdset * 191static struct svc_fdset *
180svc_pollfd_add(int fd, struct svc_fdset *fds) 192svc_pollfd_add(int fd, struct svc_fdset *fds)
181{ 193{
182 struct pollfd *pfd; 194 struct pollfd *pfd;
183 195
184 if ((pfd = svc_pollfd_alloc(fds)) == NULL) 196 if ((pfd = svc_pollfd_alloc(fds)) == NULL)
185 return NULL; 197 return NULL;
186 198
187 for (int i = 0; i < fds->fdnum; i++) 199 for (int i = 0; i < fds->fdnum; i++)
188 if (pfd[i].fd == -1) { 200 if (pfd[i].fd == -1) {
189 if (i > fds->fdused) 201 if (i >= fds->fdused)
190 fds->fdused = i + 1; 202 fds->fdused = i + 1;
 203 DPRINTF("add fd=%d slot=%d fdused=%d",
 204 fd, i, fds->fdused);
191 pfd[i].fd = fd; 205 pfd[i].fd = fd;
192 return fds; 206 return fds;
193 } 207 }
194 208
195 pfd = realloc(fds->fdp, (fds->fdnum + FD_SETSIZE) * sizeof(*fds->fdp)); 209 pfd = realloc(fds->fdp, (fds->fdnum + FD_SETSIZE) * sizeof(*fds->fdp));
196 if (pfd == NULL) 210 if (pfd == NULL)
197 return NULL; 211 return NULL;
198 212
199 svc_pollfd_init(pfd + fds->fdnum, FD_SETSIZE); 213 svc_pollfd_init(pfd + fds->fdnum, FD_SETSIZE);
200 pfd[fds->fdnum].fd = fd; 214 pfd[fds->fdnum].fd = fd;
201 fds->fdused = fds->fdnum + 1; 215 fds->fdused = fds->fdnum + 1;
 216 DPRINTF("add fd=%d slot=%d fdused=%d", fd, fds->fdnum, fds->fdused);
202 fds->fdnum += FD_SETSIZE; 217 fds->fdnum += FD_SETSIZE;
203 return fds; 218 return fds;
204} 219}
205 220
206static struct svc_fdset * 221static struct svc_fdset *
207svc_pollfd_del(int fd, struct svc_fdset *fds) 222svc_pollfd_del(int fd, struct svc_fdset *fds)
208{ 223{
209 struct pollfd *pfd; 224 struct pollfd *pfd;
210 225
211 if ((pfd = svc_pollfd_alloc(fds)) == NULL) 226 if ((pfd = svc_pollfd_alloc(fds)) == NULL)
212 return NULL; 227 return NULL;
213 228
214 for (int i = 0; i < fds->fdnum; i++) { 229 for (int i = 0; i < fds->fdnum; i++) {
215 if (pfd[i].fd != fd) 230 if (pfd[i].fd != fd)
216 continue; 231 continue;
217 232
218 pfd[i].fd = -1; 233 pfd[i].fd = -1;
 234 DPRINTF("del fd=%d slot=%d", fd, fds->fdused);
219 if (i != fds->fdused - 1) 235 if (i != fds->fdused - 1)
220 return fds; 236 return fds;
221 237
222 do 238 do
223 if (pfd[i].fd != -1)  239 if (pfd[i].fd != -1)
224 break; 240 break;
225 while (--i >= 0); 241 while (--i >= 0);
 242
226 fds->fdused = i + 1; 243 fds->fdused = i + 1;
 244 DPRINTF("del fd=%d fdused=%d", fd, fds->fdused);
227 return fds; 245 return fds;
228 } 246 }
 247 DPRINTF("del fd=%d not found", fd);
229 return NULL; 248 return NULL;
230} 249}
231 250
232static struct svc_fdset * 251static struct svc_fdset *
233svc_fdset_resize(int fd, struct svc_fdset *fds) 252svc_fdset_resize(int fd, struct svc_fdset *fds)
234{ 253{
235 if (fds->fdset && fd < fds->fdsize) { 254 if (fds->fdset && fd < fds->fdsize) {
236 DPRINTF_FDSET(fds, "keeping %d < %d", fd, fds->fdsize); 255 DPRINTF_FDSET(fds, "keeping %d < %d", fd, fds->fdsize);
237 return fds; 256 return fds;
238 } 257 }
239 258
240 fd += FD_SETSIZE;  259 fd += FD_SETSIZE;
241 260
242 char *newfdset = realloc(fds->fdset, __NFD_BYTES(fd)); 261 char *newfdset = realloc(fds->fdset, __NFD_BYTES(fd));
243 if (newfdset == NULL) 262 if (newfdset == NULL)
244 return NULL; 263 return NULL;
245 264
246 memset(newfdset + __NFD_BYTES(fds->fdsize), 0, 265 memset(newfdset + __NFD_BYTES(fds->fdsize), 0,
247 __NFD_BYTES(fd) - __NFD_BYTES(fds->fdsize)); 266 __NFD_BYTES(fd) - __NFD_BYTES(fds->fdsize));
248 267
249 268
250 fds->fdset = (void *)newfdset; 269 fds->fdset = (void *)newfdset;
251 DPRINTF_FDSET(fds, "resize %d > %d", fd, fds->fdsize); 270 DPRINTF_FDSET(fds, "resize %d > %d", fd, fds->fdsize);
252 fds->fdsize = fd; 271 fds->fdsize = fd;
253 272
254 return fds; 273 return fds;
255} 274}
256 275
257static struct svc_fdset * 276static struct svc_fdset *
258svc_fdset_alloc(int fd) 277svc_fdset_alloc(int fd)
259{ 278{
260 struct svc_fdset *fds; 279 struct svc_fdset *fds;
261 280
262 if (!__isthreaded || fdsetkey == -2) 281 if (!__isthreaded || fdsetkey == -2)
263 return svc_fdset_resize(fd, &__svc_fdset); 282 return svc_fdset_resize(fd, &__svc_fdset);
264 283
265 if (fdsetkey == -1) 284 if (fdsetkey == -1)
266 thr_keycreate(&fdsetkey, svc_fdset_free); 285 thr_keycreate(&fdsetkey, svc_fdset_free);
267 286
268 if ((fds = thr_getspecific(fdsetkey)) == NULL) { 287 if ((fds = thr_getspecific(fdsetkey)) == NULL) {
269 288
270 fds = calloc(1, sizeof(*fds)); 289 fds = calloc(1, sizeof(*fds));
271 if (fds == NULL) 290 if (fds == NULL)
272 return NULL; 291 return NULL;
273 292
274 (void)thr_setspecific(fdsetkey, fds); 293 (void)thr_setspecific(fdsetkey, fds);
275 294
276 if (__svc_fdset.fdsize != 0) { 295 if (__svc_fdset.fdsize != 0) {
277 *fds = __svc_fdset; 296 *fds = __svc_fdset;
278 DPRINTF("switching to %p", fds->fdset); 297 DPRINTF("switching to %p", fds->fdset);
279 } else { 298 } else {
280 DPRINTF("first thread time %p", fds->fdset); 299 DPRINTF("first thread time %p", fds->fdset);
281 } 300 }
282 } else { 301 } else {
283 DPRINTF("again for %p", fds->fdset); 302 DPRINTF("again for %p", fds->fdset);
284 if (fd < fds->fdsize) 303 if (fd < fds->fdsize)
285 return fds; 304 return fds;
286 } 305 }
287 306
288 return svc_fdset_resize(fd, fds); 307 return svc_fdset_resize(fd, fds);
289} 308}
290 309
291/* allow each thread to have their own copy */ 310/* allow each thread to have their own copy */
292void 311void
293svc_fdset_init(int flags) 312svc_fdset_init(int flags)
294{ 313{
295 DPRINTF("%x", flags); 314 DPRINTF("%x", flags);
296 __svc_flags = flags; 315 __svc_flags = flags;
297 if ((flags & SVC_FDSET_MT) && fdsetkey == -2) 316 if ((flags & SVC_FDSET_MT) && fdsetkey == -2)
298 fdsetkey = -1; 317 fdsetkey = -1;
299} 318}
300 319
301void 320void
302svc_fdset_zero(void) 321svc_fdset_zero(void)
303{ 322{
304 DPRINTF("zero"); 323 DPRINTF("zero");
305 324
306 struct svc_fdset *fds = svc_fdset_alloc(0); 325 struct svc_fdset *fds = svc_fdset_alloc(0);
307 memset(fds->fdset, 0, fds->fdsize); 326 memset(fds->fdset, 0, fds->fdsize);
308 fds->fdmax = -1; 327 fds->fdmax = -1;
309 328
310 free(fds->fdp); 329 free(fds->fdp);
311 fds->fdp = NULL; 330 fds->fdp = NULL;
312 fds->fdnum = fds->fdused = 0; 331 fds->fdnum = fds->fdused = 0;
313} 332}
314 333
315int 334int
316svc_fdset_set(int fd) 335svc_fdset_set(int fd)
317{ 336{
318 struct svc_fdset *fds = svc_fdset_alloc(fd); 337 struct svc_fdset *fds = svc_fdset_alloc(fd);
319 338
320 if (fds == NULL) 339 if (fds == NULL)
321 return -1; 340 return -1;
322 341
323 FD_SET(fd, fds->fdset); 342 FD_SET(fd, fds->fdset);
324 if (fd > fds->fdmax) 343 if (fd > fds->fdmax)
325 fds->fdmax = fd; 344 fds->fdmax = fd;
326 345
 346 int rv = svc_pollfd_add(fd, fds) ? 0 : -1;
327 DPRINTF_FDSET(fds, "%d", fd); 347 DPRINTF_FDSET(fds, "%d", fd);
328 348
329 svc_fdset_sanitize(fds); 349 svc_fdset_sanitize(fds);
330 return svc_pollfd_add(fd, fds) ? 0 : -1; 350 return rv;
331} 351}
332 352
333int 353int
334svc_fdset_isset(int fd) 354svc_fdset_isset(int fd)
335{ 355{
336 struct svc_fdset *fds = svc_fdset_alloc(fd); 356 struct svc_fdset *fds = svc_fdset_alloc(fd);
337 357
338 if (fds == NULL) 358 if (fds == NULL)
339 return -1; 359 return -1;
340 360
341 DPRINTF_FDSET(fds, "%d", fd); 361 DPRINTF_FDSET(fds, "%d", fd);
342 362
343 return FD_ISSET(fd, fds->fdset) != 0; 363 return FD_ISSET(fd, fds->fdset) != 0;
344} 364}
345 365
346int 366int
347svc_fdset_clr(int fd) 367svc_fdset_clr(int fd)
348{ 368{
349 struct svc_fdset *fds = svc_fdset_alloc(fd); 369 struct svc_fdset *fds = svc_fdset_alloc(fd);
350 370
351 if (fds == NULL) 371 if (fds == NULL)
352 return -1; 372 return -1;
353 373
354 FD_CLR(fd, fds->fdset); 374 FD_CLR(fd, fds->fdset);
 375
 376 int rv = svc_pollfd_del(fd, fds) ? 0 : -1;
355 DPRINTF_FDSET(fds, "%d", fd); 377 DPRINTF_FDSET(fds, "%d", fd);
356 378
357 svc_fdset_sanitize(fds); 379 svc_fdset_sanitize(fds);
358 return svc_pollfd_del(fd, fds) ? 0 : -1; 380 return rv;
359} 381}
360 382
361fd_set * 383fd_set *
362svc_fdset_copy(const fd_set *orig) 384svc_fdset_copy(const fd_set *orig)
363{ 385{
364 int size = svc_fdset_getsize(0); 386 int size = svc_fdset_getsize(0);
365 fd_set *copy = calloc(1, __NFD_BYTES(size)); 387 fd_set *copy = calloc(1, __NFD_BYTES(size));
366 if (copy == NULL) 388 if (copy == NULL)
367 return NULL; 389 return NULL;
368 if (orig) 390 if (orig)
369 memcpy(copy, orig, __NFD_BYTES(size)); 391 memcpy(copy, orig, __NFD_BYTES(size));
370 return copy; 392 return copy;
371} 393}
372 394
373fd_set * 395fd_set *
374svc_fdset_get(void) 396svc_fdset_get(void)
375{ 397{
376 struct svc_fdset *fds = svc_fdset_alloc(0); 398 struct svc_fdset *fds = svc_fdset_alloc(0);
377 399
378 if (fds == NULL) 400 if (fds == NULL)
379 return NULL; 401 return NULL;
380 402
381 DPRINTF_FDSET(fds, "get"); 403 DPRINTF_FDSET(fds, "get");
382 svc_fdset_sanitize(fds); 404 svc_fdset_sanitize(fds);
383 return fds->fdset; 405 return fds->fdset;
384} 406}
385 407
386int * 408int *
387svc_fdset_getmax(void) 409svc_fdset_getmax(void)
388{ 410{
389 struct svc_fdset *fds = svc_fdset_alloc(0); 411 struct svc_fdset *fds = svc_fdset_alloc(0);
390 412
391 if (fds == NULL) 413 if (fds == NULL)
392 return NULL; 414 return NULL;
393 415
394 DPRINTF_FDSET(fds, "getmax"); 416 DPRINTF_FDSET(fds, "getmax");
395 svc_fdset_sanitize(fds); 417 svc_fdset_sanitize(fds);
396 return &fds->fdmax; 418 return &fds->fdmax;
397} 419}
398 420
399int 421int
400svc_fdset_getsize(int fd) 422svc_fdset_getsize(int fd)
401{ 423{
402 struct svc_fdset *fds = svc_fdset_alloc(fd); 424 struct svc_fdset *fds = svc_fdset_alloc(fd);
403 425
404 if (fds == NULL) 426 if (fds == NULL)
405 return -1; 427 return -1;
406 428
407 DPRINTF_FDSET(fds, "getsize"); 429 DPRINTF_FDSET(fds, "getsize");
408 return fds->fdsize; 430 return fds->fdsize;
409} 431}
410 432
411struct pollfd * 433struct pollfd *
412svc_pollfd_copy(const struct pollfd *orig) 434svc_pollfd_copy(const struct pollfd *orig)
413{ 435{
414 int size = svc_fdset_getsize(0); 436 int size = svc_fdset_getsize(0);
415 struct pollfd *copy = calloc(size, sizeof(*orig)); 437 struct pollfd *copy = calloc(size, sizeof(*orig));
416 if (copy == NULL) 438 if (copy == NULL)
417 return NULL; 439 return NULL;
418 if (orig) 440 if (orig)
419 memcpy(copy, orig, size * sizeof(*orig)); 441 memcpy(copy, orig, size * sizeof(*orig));
420 return copy; 442 return copy;
421} 443}
422 444
423struct pollfd * 445struct pollfd *
424svc_pollfd_get(void) 446svc_pollfd_get(void)
425{ 447{
426 struct svc_fdset *fds = svc_fdset_alloc(0); 448 struct svc_fdset *fds = svc_fdset_alloc(0);
427 449
428 if (fds == NULL) 450 if (fds == NULL)
429 return NULL; 451 return NULL;
430 452
431 DPRINTF_FDSET(fds, "getpoll"); 453 DPRINTF_FDSET(fds, "getpoll");
432 return fds->fdp; 454 return fds->fdp;
433} 455}
434 456
435int * 457int *
436svc_pollfd_getmax(void) 458svc_pollfd_getmax(void)
437{ 459{
438 struct svc_fdset *fds = svc_fdset_alloc(0); 460 struct svc_fdset *fds = svc_fdset_alloc(0);
439 461
440 if (fds == NULL) 462 if (fds == NULL)
441 return NULL; 463 return NULL;
442 return &fds->fdused; 464 return &fds->fdused;
443} 465}
444 466
445int 467int
446svc_pollfd_getsize(int fd) 468svc_pollfd_getsize(int fd)
447{ 469{
448 struct svc_fdset *fds = svc_fdset_alloc(fd); 470 struct svc_fdset *fds = svc_fdset_alloc(fd);
449 471
450 if (fds == NULL) 472 if (fds == NULL)
451 return -1; 473 return -1;
452 474
453 DPRINTF_FDSET(fds, "getsize"); 475 DPRINTF_FDSET(fds, "getsize");
454 return fds->fdnum; 476 return fds->fdnum;
455} 477}