blob: c26c460bec803fcff270fb26c806dcd64541cd03 [file] [log] [blame]
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001/*
2 * Copyright (c) 2016 Cisco and/or its affiliates.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at:
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15#include <unistd.h>
16#include <stdio.h>
17#include <signal.h>
18#include <dlfcn.h>
19#include <pthread.h>
20#include <time.h>
21#include <stdarg.h>
shrinivasan ganapathy1d359632017-10-15 15:46:09 -070022#include <sys/resource.h>
Dave Wallace048b1d62018-01-03 22:24:41 -050023#include <netinet/tcp.h>
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070024
Dave Wallace2a865272018-02-07 21:00:42 -050025#include <vcl/ldp_socket_wrapper.h>
26#include <vcl/ldp.h>
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070027#include <sys/time.h>
28
Dave Wallace5c7cf1c2017-10-24 04:12:18 -040029#include <vcl/vppcom.h>
Dave Wallace048b1d62018-01-03 22:24:41 -050030#include <vppinfra/time.h>
31#include <vppinfra/bitmap.h>
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070032
33#define HAVE_CONSTRUCTOR_ATTRIBUTE
34#ifdef HAVE_CONSTRUCTOR_ATTRIBUTE
35#define CONSTRUCTOR_ATTRIBUTE \
36 __attribute__ ((constructor))
37#else
38#define CONSTRUCTOR_ATTRIBUTE
39#endif /* HAVE_CONSTRUCTOR_ATTRIBUTE */
40
41#define HAVE_DESTRUCTOR_ATTRIBUTE
42#ifdef HAVE_DESTRUCTOR_ATTRIBUTE
43#define DESTRUCTOR_ATTRIBUTE \
44 __attribute__ ((destructor))
45#else
46#define DESTRUCTOR_ATTRIBUTE
47#endif
48
Dave Wallace048b1d62018-01-03 22:24:41 -050049typedef struct
50{
51 int init;
Dave Wallace2a865272018-02-07 21:00:42 -050052 char app_name[LDP_APP_NAME_MAX];
Dave Wallace048b1d62018-01-03 22:24:41 -050053 u32 sid_bit_val;
54 u32 sid_bit_mask;
55 u32 debug;
56 u8 *io_buffer;
57 clib_time_t clib_time;
58 clib_bitmap_t *rd_bitmap;
59 clib_bitmap_t *wr_bitmap;
60 clib_bitmap_t *ex_bitmap;
61 clib_bitmap_t *sid_rd_bitmap;
62 clib_bitmap_t *sid_wr_bitmap;
63 clib_bitmap_t *sid_ex_bitmap;
64 clib_bitmap_t *libc_rd_bitmap;
65 clib_bitmap_t *libc_wr_bitmap;
66 clib_bitmap_t *libc_ex_bitmap;
67 vcl_poll_t *vcl_poll;
68 u8 select_vcl;
69 u8 epoll_wait_vcl;
Dave Wallace2a865272018-02-07 21:00:42 -050070} ldp_main_t;
71#define LDP_DEBUG ldp->debug
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070072
Dave Wallace2a865272018-02-07 21:00:42 -050073static ldp_main_t ldp_main = {
74 .sid_bit_val = (1 << LDP_SID_BIT_MIN),
75 .sid_bit_mask = (1 << LDP_SID_BIT_MIN) - 1,
76 .debug = LDP_DEBUG_INIT,
Dave Wallace048b1d62018-01-03 22:24:41 -050077};
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070078
Dave Wallace2a865272018-02-07 21:00:42 -050079static ldp_main_t *ldp = &ldp_main;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070080
81/*
82 * RETURN: 0 on success or -1 on error.
83 * */
Dave Wallace048b1d62018-01-03 22:24:41 -050084static inline void
Dave Wallace2a865272018-02-07 21:00:42 -050085ldp_set_app_name (char *app_name)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070086{
Dave Wallace2a865272018-02-07 21:00:42 -050087 int rv = snprintf (ldp->app_name, LDP_APP_NAME_MAX,
88 "ldp-%d-%s", getpid (), app_name);
Dave Wallace048b1d62018-01-03 22:24:41 -050089
Dave Wallace2a865272018-02-07 21:00:42 -050090 if (rv >= LDP_APP_NAME_MAX)
91 app_name[LDP_APP_NAME_MAX - 1] = 0;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070092}
93
Dave Wallace048b1d62018-01-03 22:24:41 -050094static inline char *
Dave Wallace2a865272018-02-07 21:00:42 -050095ldp_get_app_name ()
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -070096{
Dave Wallace2a865272018-02-07 21:00:42 -050097 if (ldp->app_name[0] == '\0')
98 ldp_set_app_name ("app");
Dave Wallace048b1d62018-01-03 22:24:41 -050099
Dave Wallace2a865272018-02-07 21:00:42 -0500100 return ldp->app_name;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700101}
102
Dave Wallace048b1d62018-01-03 22:24:41 -0500103static inline int
Dave Wallace2a865272018-02-07 21:00:42 -0500104ldp_fd_from_sid (u32 sid)
Dave Wallace048b1d62018-01-03 22:24:41 -0500105{
Dave Wallace2a865272018-02-07 21:00:42 -0500106 if (PREDICT_FALSE (sid >= ldp->sid_bit_val))
Dave Wallace048b1d62018-01-03 22:24:41 -0500107 return -EMFILE;
108 else
Dave Wallace2a865272018-02-07 21:00:42 -0500109 return (sid | ldp->sid_bit_val);
Dave Wallace048b1d62018-01-03 22:24:41 -0500110}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700111
Dave Wallace048b1d62018-01-03 22:24:41 -0500112static inline int
Dave Wallace2a865272018-02-07 21:00:42 -0500113ldp_fd_is_sid (int fd)
Dave Wallace048b1d62018-01-03 22:24:41 -0500114{
Dave Wallace2a865272018-02-07 21:00:42 -0500115 return ((u32) fd & ldp->sid_bit_val) ? 1 : 0;
Dave Wallace048b1d62018-01-03 22:24:41 -0500116}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700117
Dave Wallace048b1d62018-01-03 22:24:41 -0500118static inline u32
Dave Wallace2a865272018-02-07 21:00:42 -0500119ldp_sid_from_fd (int fd)
Dave Wallace048b1d62018-01-03 22:24:41 -0500120{
Dave Wallace2a865272018-02-07 21:00:42 -0500121 return (ldp_fd_is_sid (fd) ? ((u32) fd & ldp->sid_bit_mask) :
Dave Wallace048b1d62018-01-03 22:24:41 -0500122 INVALID_SESSION_ID);
123}
124
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700125static inline int
Dave Wallace2a865272018-02-07 21:00:42 -0500126ldp_init (void)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700127{
Dave Wallace048b1d62018-01-03 22:24:41 -0500128 int rv = 0;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700129
Dave Wallace2a865272018-02-07 21:00:42 -0500130 if (PREDICT_FALSE (!ldp->init))
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700131 {
Dave Wallace2a865272018-02-07 21:00:42 -0500132 ldp->init = 1;
133 rv = vppcom_app_create (ldp_get_app_name ());
Dave Wallace048b1d62018-01-03 22:24:41 -0500134 if (rv == VPPCOM_OK)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700135 {
Dave Wallace2a865272018-02-07 21:00:42 -0500136 char *env_var_str = getenv (LDP_ENV_DEBUG);
Dave Wallace048b1d62018-01-03 22:24:41 -0500137 if (env_var_str)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700138 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500139 u32 tmp;
140 if (sscanf (env_var_str, "%u", &tmp) != 1)
Dave Wallace2a865272018-02-07 21:00:42 -0500141 clib_warning ("LDP<%d>: WARNING: Invalid LDP debug level "
142 "specified in the env var " LDP_ENV_DEBUG
Dave Wallace048b1d62018-01-03 22:24:41 -0500143 " (%s)!", getpid (), env_var_str);
144 else
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700145 {
Dave Wallace2a865272018-02-07 21:00:42 -0500146 ldp->debug = tmp;
Dave Wallace69d01192018-02-22 16:22:09 -0500147 if (LDP_DEBUG > 0)
148 clib_warning ("LDP<%d>: configured LDP debug level (%u) "
149 "from the env var " LDP_ENV_DEBUG "!",
150 getpid (), ldp->debug);
Dave Wallace048b1d62018-01-03 22:24:41 -0500151 }
152 }
153
Dave Wallace2a865272018-02-07 21:00:42 -0500154 env_var_str = getenv (LDP_ENV_APP_NAME);
Dave Wallace048b1d62018-01-03 22:24:41 -0500155 if (env_var_str)
156 {
Dave Wallace2a865272018-02-07 21:00:42 -0500157 ldp_set_app_name (env_var_str);
Dave Wallace69d01192018-02-22 16:22:09 -0500158 if (LDP_DEBUG > 0)
159 clib_warning ("LDP<%d>: configured LDP app name (%s) "
160 "from the env var " LDP_ENV_APP_NAME "!",
161 getpid (), ldp->app_name);
Dave Wallace048b1d62018-01-03 22:24:41 -0500162 }
163
Dave Wallace2a865272018-02-07 21:00:42 -0500164 env_var_str = getenv (LDP_ENV_SID_BIT);
Dave Wallace048b1d62018-01-03 22:24:41 -0500165 if (env_var_str)
166 {
167 u32 sb;
168 if (sscanf (env_var_str, "%u", &sb) != 1)
169 {
Dave Wallace2a865272018-02-07 21:00:42 -0500170 clib_warning ("LDP<%d>: WARNING: Invalid LDP sid bit "
Dave Wallace048b1d62018-01-03 22:24:41 -0500171 "specified in the env var "
Dave Wallace2a865272018-02-07 21:00:42 -0500172 LDP_ENV_SID_BIT " (%s)!"
Dave Wallace048b1d62018-01-03 22:24:41 -0500173 "sid bit value %d (0x%x)",
174 getpid (), env_var_str,
Dave Wallace2a865272018-02-07 21:00:42 -0500175 ldp->sid_bit_val, ldp->sid_bit_val);
Dave Wallace048b1d62018-01-03 22:24:41 -0500176 }
Dave Wallace2a865272018-02-07 21:00:42 -0500177 else if (sb < LDP_SID_BIT_MIN)
Dave Wallace048b1d62018-01-03 22:24:41 -0500178 {
Dave Wallace2a865272018-02-07 21:00:42 -0500179 ldp->sid_bit_val = (1 << LDP_SID_BIT_MIN);
180 ldp->sid_bit_mask = ldp->sid_bit_val - 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500181
Dave Wallace2a865272018-02-07 21:00:42 -0500182 clib_warning ("LDP<%d>: WARNING: LDP sid bit (%u) "
Dave Wallace048b1d62018-01-03 22:24:41 -0500183 "specified in the env var "
Dave Wallace2a865272018-02-07 21:00:42 -0500184 LDP_ENV_SID_BIT " (%s) is too small. "
185 "Using LDP_SID_BIT_MIN (%d)! "
Dave Wallace048b1d62018-01-03 22:24:41 -0500186 "sid bit value %d (0x%x)",
Dave Wallace2a865272018-02-07 21:00:42 -0500187 getpid (), sb, env_var_str, LDP_SID_BIT_MIN,
188 ldp->sid_bit_val, ldp->sid_bit_val);
Dave Wallace048b1d62018-01-03 22:24:41 -0500189 }
Dave Wallace2a865272018-02-07 21:00:42 -0500190 else if (sb > LDP_SID_BIT_MAX)
Dave Wallace048b1d62018-01-03 22:24:41 -0500191 {
Dave Wallace2a865272018-02-07 21:00:42 -0500192 ldp->sid_bit_val = (1 << LDP_SID_BIT_MAX);
193 ldp->sid_bit_mask = ldp->sid_bit_val - 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500194
Dave Wallace2a865272018-02-07 21:00:42 -0500195 clib_warning ("LDP<%d>: WARNING: LDP sid bit (%u) "
Dave Wallace048b1d62018-01-03 22:24:41 -0500196 "specified in the env var "
Dave Wallace2a865272018-02-07 21:00:42 -0500197 LDP_ENV_SID_BIT " (%s) is too big. "
198 "Using LDP_SID_BIT_MAX (%d)! "
Dave Wallace048b1d62018-01-03 22:24:41 -0500199 "sid bit value %d (0x%x)",
Dave Wallace2a865272018-02-07 21:00:42 -0500200 getpid (), sb, env_var_str, LDP_SID_BIT_MAX,
201 ldp->sid_bit_val, ldp->sid_bit_val);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700202 }
203 else
204 {
Dave Wallace2a865272018-02-07 21:00:42 -0500205 ldp->sid_bit_val = (1 << sb);
206 ldp->sid_bit_mask = ldp->sid_bit_val - 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500207
Dave Wallace69d01192018-02-22 16:22:09 -0500208 if (LDP_DEBUG > 0)
209 clib_warning ("LDP<%d>: configured LDP sid bit (%u) "
210 "from " LDP_ENV_SID_BIT
211 "! sid bit value %d (0x%x)", getpid (),
212 sb, ldp->sid_bit_val, ldp->sid_bit_val);
Dave Wallace048b1d62018-01-03 22:24:41 -0500213 }
214 }
215
Dave Wallace2a865272018-02-07 21:00:42 -0500216 clib_time_init (&ldp->clib_time);
Dave Wallace69d01192018-02-22 16:22:09 -0500217 if (LDP_DEBUG > 0)
218 clib_warning ("LDP<%d>: LDP initialization: done!", getpid ());
Dave Wallace048b1d62018-01-03 22:24:41 -0500219 }
220 else
221 {
Dave Wallace2a865272018-02-07 21:00:42 -0500222 fprintf (stderr, "\nLDP<%d>: ERROR: ldp_init: vppcom_app_create()"
Dave Wallace048b1d62018-01-03 22:24:41 -0500223 " failed! rv = %d (%s)\n",
224 getpid (), rv, vppcom_retval_str (rv));
Dave Wallace2a865272018-02-07 21:00:42 -0500225 ldp->init = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -0500226 }
227 }
228 return rv;
229}
230
231int
232close (int fd)
233{
234 int rv;
235 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -0500236 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -0500237
Dave Wallace2a865272018-02-07 21:00:42 -0500238 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500239 return -1;
240
241 if (sid != INVALID_SESSION_ID)
242 {
243 int epfd;
244
245 func_str = "vppcom_session_attr[GET_LIBC_EPFD]";
246 epfd = vppcom_session_attr (sid, VPPCOM_ATTR_GET_LIBC_EPFD, 0, 0);
247 if (epfd > 0)
248 {
249 func_str = "libc_close";
250
Dave Wallace2a865272018-02-07 21:00:42 -0500251 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -0500252 clib_warning
253 ("LDP<%d>: fd %d (0x%x): calling %s(): epfd %u (0x%x)",
254 getpid (), fd, fd, func_str, epfd, epfd);
255
256 rv = libc_close (epfd);
257 if (rv < 0)
258 {
259 u32 size = sizeof (epfd);
260 epfd = 0;
261
262 (void) vppcom_session_attr (sid, VPPCOM_ATTR_SET_LIBC_EPFD,
263 &epfd, &size);
264 }
265 }
266 else if (PREDICT_FALSE (epfd < 0))
267 {
268 errno = -epfd;
269 rv = -1;
270 goto done;
271 }
272
273 func_str = "vppcom_session_close";
274
Dave Wallace2a865272018-02-07 21:00:42 -0500275 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -0500276 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x)",
277 getpid (), fd, fd, func_str, sid, sid);
278
279 rv = vppcom_session_close (sid);
280 if (rv != VPPCOM_OK)
281 {
282 errno = -rv;
283 rv = -1;
284 }
285 }
286 else
287 {
288 func_str = "libc_close";
289
Dave Wallace2a865272018-02-07 21:00:42 -0500290 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -0500291 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s()",
292 getpid (), fd, fd, func_str);
293
294 rv = libc_close (fd);
295 }
296
297done:
Dave Wallace2a865272018-02-07 21:00:42 -0500298 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -0500299 {
300 if (rv < 0)
301 {
302 int errno_val = errno;
303 perror (func_str);
304 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
305 "rv %d, errno = %d", getpid (), fd, fd,
306 func_str, rv, errno_val);
307 errno = errno_val;
308 }
309 else
310 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
311 getpid (), fd, fd, rv, rv);
312 }
313 return rv;
314}
315
316ssize_t
317read (int fd, void *buf, size_t nbytes)
318{
319 ssize_t size;
320 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -0500321 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -0500322
Dave Wallace2a865272018-02-07 21:00:42 -0500323 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500324 return -1;
325
326 if (sid != INVALID_SESSION_ID)
327 {
328 func_str = "vppcom_session_read";
329
Dave Wallace2a865272018-02-07 21:00:42 -0500330 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500331 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
332 "sid %u (0x%x), buf %p, nbytes %u", getpid (),
333 fd, fd, func_str, sid, sid, buf, nbytes);
334
335 size = vppcom_session_read (sid, buf, nbytes);
336 if (size < 0)
337 {
338 errno = -size;
339 size = -1;
340 }
341 }
342 else
343 {
344 func_str = "libc_read";
345
Dave Wallace2a865272018-02-07 21:00:42 -0500346 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500347 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
348 "buf %p, nbytes %u", getpid (),
349 fd, fd, func_str, buf, nbytes);
350
351 size = libc_read (fd, buf, nbytes);
352 }
353
Dave Wallace2a865272018-02-07 21:00:42 -0500354 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500355 {
356 if (size < 0)
357 {
358 int errno_val = errno;
359 perror (func_str);
360 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
361 "rv %d, errno = %d", getpid (), fd, fd,
362 func_str, size, errno_val);
363 errno = errno_val;
364 }
365 else
366 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
367 getpid (), fd, fd, size, size);
368 }
369 return size;
370}
371
372ssize_t
373readv (int fd, const struct iovec * iov, int iovcnt)
374{
375 const char *func_str;
376 ssize_t size = 0;
Dave Wallace2a865272018-02-07 21:00:42 -0500377 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace8aaba562018-01-18 17:21:19 -0500378 int rv = 0, i, total = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -0500379
Dave Wallace2a865272018-02-07 21:00:42 -0500380 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500381 return -1;
382
383 if (sid != INVALID_SESSION_ID)
384 {
385 func_str = "vppcom_session_read";
386 do
387 {
388 for (i = 0; i < iovcnt; ++i)
389 {
Dave Wallace2a865272018-02-07 21:00:42 -0500390 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500391 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s() [%d]: "
392 "sid %u (0x%x), iov %p, iovcnt %d, total %d",
393 getpid (), fd, fd, func_str, i, sid, sid,
394 iov, iovcnt, total);
395
396 rv = vppcom_session_read (sid, iov[i].iov_base, iov[i].iov_len);
397 if (rv < 0)
398 break;
399 else
400 {
401 total += rv;
402 if (rv < iov[i].iov_len)
403 {
Dave Wallace2a865272018-02-07 21:00:42 -0500404 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500405 clib_warning ("LDP<%d>: fd %d (0x%x): "
406 "rv (%d) < iov[%d].iov_len (%d)",
407 getpid (), fd, fd, rv, i,
408 iov[i].iov_len);
409 break;
410 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700411 }
412 }
413 }
Dave Wallace048b1d62018-01-03 22:24:41 -0500414 while ((rv >= 0) && (total == 0));
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700415
Dave Wallace048b1d62018-01-03 22:24:41 -0500416 if (rv < 0)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700417 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500418 errno = -rv;
419 size = -1;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700420 }
Dave Wallace048b1d62018-01-03 22:24:41 -0500421 else
422 size = total;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700423 }
424 else
425 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500426 func_str = "libc_readv";
427
Dave Wallace2a865272018-02-07 21:00:42 -0500428 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500429 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
430 "iov %p, iovcnt %d", getpid (), fd, fd, iov, iovcnt);
431
432 size = libc_readv (fd, iov, iovcnt);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700433 }
434
Dave Wallace2a865272018-02-07 21:00:42 -0500435 if (LDP_DEBUG > 2)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700436 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500437 if (size < 0)
438 {
439 int errno_val = errno;
440 perror (func_str);
441 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
442 "rv %d, errno = %d", getpid (), fd, fd,
443 func_str, size, errno_val);
444 errno = errno_val;
445 }
446 else
447 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
448 getpid (), fd, fd, size, size);
449 }
450 return size;
451}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700452
Dave Wallace048b1d62018-01-03 22:24:41 -0500453ssize_t
454write (int fd, const void *buf, size_t nbytes)
455{
456 const char *func_str;
457 ssize_t size = 0;
Dave Wallace2a865272018-02-07 21:00:42 -0500458 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -0500459
Dave Wallace2a865272018-02-07 21:00:42 -0500460 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500461 return -1;
462
463 if (sid != INVALID_SESSION_ID)
464 {
465 func_str = "vppcom_session_write";
466
Dave Wallace2a865272018-02-07 21:00:42 -0500467 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500468 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
469 "sid %u (0x%x), buf %p, nbytes %u", getpid (),
470 fd, fd, func_str, sid, sid, buf, nbytes);
471
472 size = vppcom_session_write (sid, (void *) buf, nbytes);
473 if (size < 0)
474 {
475 errno = -size;
476 size = -1;
477 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700478 }
479 else
480 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500481 func_str = "libc_write";
482
Dave Wallace2a865272018-02-07 21:00:42 -0500483 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500484 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
485 "buf %p, nbytes %u", getpid (),
486 fd, fd, func_str, buf, nbytes);
487
488 size = libc_write (fd, buf, nbytes);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700489 }
490
Dave Wallace2a865272018-02-07 21:00:42 -0500491 if (LDP_DEBUG > 2)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700492 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500493 if (size < 0)
494 {
495 int errno_val = errno;
496 perror (func_str);
497 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
498 "rv %d, errno = %d", getpid (), fd, fd,
499 func_str, size, errno_val);
500 errno = errno_val;
501 }
502 else
503 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
504 getpid (), fd, fd, size, size);
505 }
506 return size;
507}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700508
Dave Wallace048b1d62018-01-03 22:24:41 -0500509ssize_t
510writev (int fd, const struct iovec * iov, int iovcnt)
511{
512 const char *func_str;
513 ssize_t size = 0, total = 0;
Dave Wallace2a865272018-02-07 21:00:42 -0500514 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace8aaba562018-01-18 17:21:19 -0500515 int i, rv = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -0500516
517 /*
518 * Use [f]printf() instead of clib_warning() to prevent recursion SIGSEGV.
519 */
520
Dave Wallace2a865272018-02-07 21:00:42 -0500521 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500522 return -1;
523
524 if (sid != INVALID_SESSION_ID)
525 {
526 func_str = "vppcom_session_write";
527 do
528 {
529 for (i = 0; i < iovcnt; ++i)
530 {
Dave Wallace2a865272018-02-07 21:00:42 -0500531 if (LDP_DEBUG > 4)
Dave Wallace048b1d62018-01-03 22:24:41 -0500532 printf ("%s:%d: LDP<%d>: fd %d (0x%x): calling %s() [%d]: "
533 "sid %u (0x%x), buf %p, nbytes %ld, total %ld",
534 __func__, __LINE__, getpid (), fd, fd, func_str,
535 i, sid, sid, iov[i].iov_base, iov[i].iov_len, total);
536
537 rv = vppcom_session_write (sid, iov[i].iov_base,
538 iov[i].iov_len);
539 if (rv < 0)
540 break;
541 else
542 {
543 total += rv;
544 if (rv < iov[i].iov_len)
545 {
Dave Wallace2a865272018-02-07 21:00:42 -0500546 if (LDP_DEBUG > 4)
Dave Wallace048b1d62018-01-03 22:24:41 -0500547 printf ("%s:%d: LDP<%d>: fd %d (0x%x): "
548 "rv (%d) < iov[%d].iov_len (%ld)",
549 __func__, __LINE__, getpid (), fd, fd,
550 rv, i, iov[i].iov_len);
551 break;
552 }
553 }
554 }
555 }
556 while ((rv >= 0) && (total == 0));
557
558 if (rv < 0)
559 {
560 errno = -rv;
561 size = -1;
562 }
563 else
564 size = total;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700565 }
566 else
567 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500568 func_str = "libc_writev";
569
Dave Wallace2a865272018-02-07 21:00:42 -0500570 if (LDP_DEBUG > 4)
Dave Wallace048b1d62018-01-03 22:24:41 -0500571 printf ("%s:%d: LDP<%d>: fd %d (0x%x): calling %s(): "
572 "iov %p, iovcnt %d\n", __func__, __LINE__, getpid (),
573 fd, fd, func_str, iov, iovcnt);
574
575 size = libc_writev (fd, iov, iovcnt);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700576 }
577
Dave Wallace2a865272018-02-07 21:00:42 -0500578 if (LDP_DEBUG > 4)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700579 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500580 if (size < 0)
581 {
582 int errno_val = errno;
583 perror (func_str);
584 fprintf (stderr,
585 "%s:%d: LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
586 "rv %ld, errno = %d\n", __func__, __LINE__, getpid (), fd,
587 fd, func_str, size, errno_val);
588 errno = errno_val;
589 }
590 else
591 printf ("%s:%d: LDP<%d>: fd %d (0x%x): returning %ld\n",
592 __func__, __LINE__, getpid (), fd, fd, size);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700593 }
Dave Wallace048b1d62018-01-03 22:24:41 -0500594 return size;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700595}
596
597int
Dave Wallace048b1d62018-01-03 22:24:41 -0500598fcntl (int fd, int cmd, ...)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700599{
Dave Wallace048b1d62018-01-03 22:24:41 -0500600 const char *func_str = __func__;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700601 int rv = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -0500602 va_list ap;
Dave Wallace2a865272018-02-07 21:00:42 -0500603 u32 sid = ldp_sid_from_fd (fd);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700604
Dave Wallace2a865272018-02-07 21:00:42 -0500605 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500606 return -1;
607
608 va_start (ap, cmd);
609 if (sid != INVALID_SESSION_ID)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700610 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500611 int flags = va_arg (ap, int);
612 u32 size;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700613
Dave Wallace048b1d62018-01-03 22:24:41 -0500614 size = sizeof (flags);
615 rv = -EOPNOTSUPP;
616 switch (cmd)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700617 {
Dave Wallace048b1d62018-01-03 22:24:41 -0500618 case F_SETFL:
619 func_str = "vppcom_session_attr[SET_FLAGS]";
Dave Wallace2a865272018-02-07 21:00:42 -0500620 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500621 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
622 "sid %u (0x%x) flags %d (0x%x), size %d",
623 getpid (), fd, fd, func_str, sid, sid,
624 flags, flags, size);
625
626 rv =
627 vppcom_session_attr (sid, VPPCOM_ATTR_SET_FLAGS, &flags, &size);
628 break;
629
630 case F_GETFL:
631 func_str = "vppcom_session_attr[GET_FLAGS]";
Dave Wallace2a865272018-02-07 21:00:42 -0500632 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500633 clib_warning
634 ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), "
635 "flags %d (0x%x), size %d", getpid (), fd, fd, func_str, sid,
636 sid, flags, flags, size);
637
638 rv =
639 vppcom_session_attr (sid, VPPCOM_ATTR_GET_FLAGS, &flags, &size);
640 if (rv == VPPCOM_OK)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700641 {
Dave Wallace2a865272018-02-07 21:00:42 -0500642 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500643 clib_warning ("LDP<%d>: fd %d (0x%x), cmd %d (F_GETFL): "
644 "%s() returned flags %d (0x%x)",
645 getpid (), fd, fd, cmd, func_str, flags, flags);
646 rv = flags;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700647 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700648 break;
649
650 default:
Dave Wallace048b1d62018-01-03 22:24:41 -0500651 rv = -EOPNOTSUPP;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700652 break;
653 }
Dave Wallace048b1d62018-01-03 22:24:41 -0500654 if (rv < 0)
655 {
656 errno = -rv;
657 rv = -1;
658 }
659 }
660 else
661 {
662 func_str = "libc_vfcntl";
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700663
Dave Wallace2a865272018-02-07 21:00:42 -0500664 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500665 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): cmd %d",
666 getpid (), fd, fd, func_str, cmd);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700667
Dave Wallace048b1d62018-01-03 22:24:41 -0500668 rv = libc_vfcntl (fd, cmd, ap);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -0700669 }
670
Dave Wallace048b1d62018-01-03 22:24:41 -0500671 va_end (ap);
672
Dave Wallace2a865272018-02-07 21:00:42 -0500673 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500674 {
675 if (rv < 0)
676 {
677 int errno_val = errno;
678 perror (func_str);
679 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
680 "rv %d, errno = %d", getpid (), fd, fd,
681 func_str, rv, errno_val);
682 errno = errno_val;
683 }
684 else
685 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
686 getpid (), fd, fd, rv, rv);
687 }
688 return rv;
689}
690
691int
692ioctl (int fd, unsigned long int cmd, ...)
693{
694 const char *func_str;
695 int rv;
696 va_list ap;
Dave Wallace2a865272018-02-07 21:00:42 -0500697 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -0500698
Dave Wallace2a865272018-02-07 21:00:42 -0500699 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -0500700 return -1;
701
702 va_start (ap, cmd);
703 if (sid != INVALID_SESSION_ID)
704 {
705 func_str = "vppcom_session_attr[GET_NREAD]";
706
707 switch (cmd)
708 {
709 case FIONREAD:
Dave Wallace2a865272018-02-07 21:00:42 -0500710 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500711 clib_warning
712 ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x)",
713 getpid (), fd, fd, func_str, sid, sid);
714
715 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_NREAD, 0, 0);
716 break;
717
718 case FIONBIO:
719 {
720 u32 flags = va_arg (ap, int) ? O_NONBLOCK : 0;
721 u32 size = sizeof (flags);
722
723 /* TBD: When VPPCOM_ATTR_[GS]ET_FLAGS supports flags other than
724 * non-blocking, the flags should be read here and merged
725 * with O_NONBLOCK.
726 */
Dave Wallace2a865272018-02-07 21:00:42 -0500727 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500728 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
729 "sid %u (0x%x), flags %d (0x%x), size %d",
730 getpid (), fd, fd, func_str, sid, sid,
731 flags, flags, size);
732
733 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_FLAGS, &flags,
734 &size);
735 }
736 break;
737
738 default:
739 rv = -EOPNOTSUPP;
740 break;
741 }
742 if (rv < 0)
743 {
744 errno = -rv;
745 rv = -1;
746 }
747 }
748 else
749 {
750 func_str = "libc_vioctl";
751
Dave Wallace2a865272018-02-07 21:00:42 -0500752 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500753 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): cmd %d",
754 getpid (), fd, fd, func_str, cmd);
755
756 rv = libc_vioctl (fd, cmd, ap);
757 }
758
Dave Wallace2a865272018-02-07 21:00:42 -0500759 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -0500760 {
761 if (rv < 0)
762 {
763 int errno_val = errno;
764 perror (func_str);
765 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
766 "rv %d, errno = %d", getpid (), fd, fd,
767 func_str, rv, errno_val);
768 errno = errno_val;
769 }
770 else
771 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
772 getpid (), fd, fd, rv, rv);
773 }
774 va_end (ap);
775 return rv;
776}
777
778int
Dave Wallace2a865272018-02-07 21:00:42 -0500779ldp_pselect (int nfds, fd_set * __restrict readfds,
780 fd_set * __restrict writefds,
781 fd_set * __restrict exceptfds,
782 const struct timespec *__restrict timeout,
783 const __sigset_t * __restrict sigmask)
Dave Wallace048b1d62018-01-03 22:24:41 -0500784{
785 int rv;
786 char *func_str = "##";
787 f64 time_out;
788 int fd;
789 uword sid_bits, sid_bits_set, libc_bits, libc_bits_set;
790 u32 minbits = clib_max (nfds, BITS (uword));
791 u32 sid;
792
793 if (nfds < 0)
794 {
795 errno = EINVAL;
796 return -1;
797 }
798
Dave Wallace3ee1fe12018-02-23 01:09:11 -0500799 if (timeout)
800 {
801 time_out = (timeout->tv_sec == 0 && timeout->tv_nsec == 0) ?
802 (f64) 0 : (f64) timeout->tv_sec +
803 (f64) timeout->tv_nsec / (f64) 1000000000;
804
805 /* select as fine grained sleep */
806 if (!nfds)
807 {
808 if (LDP_DEBUG > 3)
809 clib_warning ("LDP<%d>: sleeping for %.02f seconds",
810 getpid (), time_out);
811
812 time_out += clib_time_now (&ldp->clib_time);
813 while (clib_time_now (&ldp->clib_time) < time_out)
814 ;
815 return 0;
816 }
817 }
818 else if (!nfds)
819 {
820 errno = EINVAL;
821 return -1;
822 }
823 else
824 time_out = -1;
825
826
Dave Wallace2a865272018-02-07 21:00:42 -0500827 if (nfds <= ldp->sid_bit_val)
Dave Wallace048b1d62018-01-03 22:24:41 -0500828 {
829 func_str = "libc_pselect";
830
Dave Wallace2a865272018-02-07 21:00:42 -0500831 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500832 clib_warning
833 ("LDP<%d>: calling %s(): nfds %d, readfds %p, writefds %p, "
834 "exceptfds %p, timeout %p, sigmask %p", getpid (), func_str, nfds,
835 readfds, writefds, exceptfds, timeout, sigmask);
836
837 rv = libc_pselect (nfds, readfds, writefds, exceptfds,
838 timeout, sigmask);
839 goto done;
840 }
841
Dave Wallace2a865272018-02-07 21:00:42 -0500842 if (PREDICT_FALSE (ldp->sid_bit_val > FD_SETSIZE / 2))
Dave Wallace048b1d62018-01-03 22:24:41 -0500843 {
Dave Wallace2a865272018-02-07 21:00:42 -0500844 clib_warning ("LDP<%d>: ERROR: LDP sid bit value %d (0x%x) > "
Dave Wallace048b1d62018-01-03 22:24:41 -0500845 "FD_SETSIZE/2 %d (0x%x)!", getpid (),
Dave Wallace2a865272018-02-07 21:00:42 -0500846 ldp->sid_bit_val, ldp->sid_bit_val,
Dave Wallace048b1d62018-01-03 22:24:41 -0500847 FD_SETSIZE / 2, FD_SETSIZE / 2);
848 errno = EOVERFLOW;
849 return -1;
850 }
851
Dave Wallace048b1d62018-01-03 22:24:41 -0500852 sid_bits = libc_bits = 0;
853 if (readfds)
854 {
Dave Wallace2a865272018-02-07 21:00:42 -0500855 clib_bitmap_validate (ldp->sid_rd_bitmap, minbits);
856 clib_bitmap_validate (ldp->libc_rd_bitmap, minbits);
857 clib_bitmap_validate (ldp->rd_bitmap, minbits);
858 clib_memcpy (ldp->rd_bitmap, readfds,
859 vec_len (ldp->rd_bitmap) * sizeof (clib_bitmap_t));
Dave Wallace048b1d62018-01-03 22:24:41 -0500860 FD_ZERO (readfds);
861
862 /* *INDENT-OFF* */
Dave Wallace2a865272018-02-07 21:00:42 -0500863 clib_bitmap_foreach (fd, ldp->rd_bitmap,
Dave Wallace048b1d62018-01-03 22:24:41 -0500864 ({
Dave Wallace2a865272018-02-07 21:00:42 -0500865 sid = ldp_sid_from_fd (fd);
866 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500867 clib_warning ("LDP<%d>: readfds: fd %d (0x%x), sid %u (0x%x)",
868 getpid (), fd, fd, sid, sid);
869 if (sid == INVALID_SESSION_ID)
Dave Wallace2a865272018-02-07 21:00:42 -0500870 clib_bitmap_set_no_check (ldp->libc_rd_bitmap, fd, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -0500871 else
Dave Wallace2a865272018-02-07 21:00:42 -0500872 clib_bitmap_set_no_check (ldp->sid_rd_bitmap, sid, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -0500873 }));
874 /* *INDENT-ON* */
875
Dave Wallace2a865272018-02-07 21:00:42 -0500876 sid_bits_set = clib_bitmap_last_set (ldp->sid_rd_bitmap) + 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500877 sid_bits = (sid_bits_set > sid_bits) ? sid_bits_set : sid_bits;
878
Dave Wallace2a865272018-02-07 21:00:42 -0500879 libc_bits_set = clib_bitmap_last_set (ldp->libc_rd_bitmap) + 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500880 libc_bits = (libc_bits_set > libc_bits) ? libc_bits_set : libc_bits;
881
Dave Wallace2a865272018-02-07 21:00:42 -0500882 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500883 clib_warning ("LDP<%d>: readfds: sid_bits_set %d, sid_bits %d, "
884 "libc_bits_set %d, libc_bits %d", getpid (),
885 sid_bits_set, sid_bits, libc_bits_set, libc_bits);
886 }
887 if (writefds)
888 {
Dave Wallace2a865272018-02-07 21:00:42 -0500889 clib_bitmap_validate (ldp->sid_wr_bitmap, minbits);
890 clib_bitmap_validate (ldp->libc_wr_bitmap, minbits);
891 clib_bitmap_validate (ldp->wr_bitmap, minbits);
892 clib_memcpy (ldp->wr_bitmap, writefds,
893 vec_len (ldp->wr_bitmap) * sizeof (clib_bitmap_t));
Dave Wallace048b1d62018-01-03 22:24:41 -0500894 FD_ZERO (writefds);
895
896 /* *INDENT-OFF* */
Dave Wallace2a865272018-02-07 21:00:42 -0500897 clib_bitmap_foreach (fd, ldp->wr_bitmap,
Dave Wallace048b1d62018-01-03 22:24:41 -0500898 ({
Dave Wallace2a865272018-02-07 21:00:42 -0500899 sid = ldp_sid_from_fd (fd);
900 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500901 clib_warning ("LDP<%d>: writefds: fd %d (0x%x), sid %u (0x%x)",
902 getpid (), fd, fd, sid, sid);
903 if (sid == INVALID_SESSION_ID)
Dave Wallace2a865272018-02-07 21:00:42 -0500904 clib_bitmap_set_no_check (ldp->libc_wr_bitmap, fd, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -0500905 else
Dave Wallace2a865272018-02-07 21:00:42 -0500906 clib_bitmap_set_no_check (ldp->sid_wr_bitmap, sid, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -0500907 }));
908 /* *INDENT-ON* */
909
Dave Wallace2a865272018-02-07 21:00:42 -0500910 sid_bits_set = clib_bitmap_last_set (ldp->sid_wr_bitmap) + 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500911 sid_bits = (sid_bits_set > sid_bits) ? sid_bits_set : sid_bits;
912
Dave Wallace2a865272018-02-07 21:00:42 -0500913 libc_bits_set = clib_bitmap_last_set (ldp->libc_wr_bitmap) + 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500914 libc_bits = (libc_bits_set > libc_bits) ? libc_bits_set : libc_bits;
915
Dave Wallace2a865272018-02-07 21:00:42 -0500916 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500917 clib_warning ("LDP<%d>: writefds: sid_bits_set %d, sid_bits %d, "
918 "libc_bits_set %d, libc_bits %d", getpid (),
919 sid_bits_set, sid_bits, libc_bits_set, libc_bits);
920 }
921 if (exceptfds)
922 {
Dave Wallace2a865272018-02-07 21:00:42 -0500923 clib_bitmap_validate (ldp->sid_ex_bitmap, minbits);
924 clib_bitmap_validate (ldp->libc_ex_bitmap, minbits);
925 clib_bitmap_validate (ldp->ex_bitmap, minbits);
926 clib_memcpy (ldp->ex_bitmap, exceptfds,
927 vec_len (ldp->ex_bitmap) * sizeof (clib_bitmap_t));
Dave Wallace048b1d62018-01-03 22:24:41 -0500928 FD_ZERO (exceptfds);
929
930 /* *INDENT-OFF* */
Dave Wallace2a865272018-02-07 21:00:42 -0500931 clib_bitmap_foreach (fd, ldp->ex_bitmap,
Dave Wallace048b1d62018-01-03 22:24:41 -0500932 ({
Dave Wallace2a865272018-02-07 21:00:42 -0500933 sid = ldp_sid_from_fd (fd);
934 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500935 clib_warning ("LDP<%d>: exceptfds: fd %d (0x%x), sid %u (0x%x)",
936 getpid (), fd, fd, sid, sid);
937 if (sid == INVALID_SESSION_ID)
Dave Wallace2a865272018-02-07 21:00:42 -0500938 clib_bitmap_set_no_check (ldp->libc_ex_bitmap, fd, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -0500939 else
Dave Wallace2a865272018-02-07 21:00:42 -0500940 clib_bitmap_set_no_check (ldp->sid_ex_bitmap, sid, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -0500941 }));
942 /* *INDENT-ON* */
943
Dave Wallace2a865272018-02-07 21:00:42 -0500944 sid_bits_set = clib_bitmap_last_set (ldp->sid_ex_bitmap) + 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500945 sid_bits = (sid_bits_set > sid_bits) ? sid_bits_set : sid_bits;
946
Dave Wallace2a865272018-02-07 21:00:42 -0500947 libc_bits_set = clib_bitmap_last_set (ldp->libc_ex_bitmap) + 1;
Dave Wallace048b1d62018-01-03 22:24:41 -0500948 libc_bits = (libc_bits_set > libc_bits) ? libc_bits_set : libc_bits;
949
Dave Wallace2a865272018-02-07 21:00:42 -0500950 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -0500951 clib_warning ("LDP<%d>: exceptfds: sid_bits_set %d, sid_bits %d, "
952 "libc_bits_set %d, libc_bits %d", getpid (),
953 sid_bits_set, sid_bits, libc_bits_set, libc_bits);
954 }
955
956 if (PREDICT_FALSE (!sid_bits && !libc_bits))
957 {
958 errno = EINVAL;
959 rv = -1;
960 goto done;
961 }
962
963 do
964 {
965 if (sid_bits)
966 {
Dave Wallace2a865272018-02-07 21:00:42 -0500967 if (!ldp->select_vcl)
Dave Wallace048b1d62018-01-03 22:24:41 -0500968 {
969 func_str = "vppcom_select";
970
971 if (readfds)
Dave Wallace2a865272018-02-07 21:00:42 -0500972 clib_memcpy (ldp->rd_bitmap, ldp->sid_rd_bitmap,
973 vec_len (ldp->rd_bitmap) *
Dave Wallace048b1d62018-01-03 22:24:41 -0500974 sizeof (clib_bitmap_t));
975 if (writefds)
Dave Wallace2a865272018-02-07 21:00:42 -0500976 clib_memcpy (ldp->wr_bitmap, ldp->sid_wr_bitmap,
977 vec_len (ldp->wr_bitmap) *
Dave Wallace048b1d62018-01-03 22:24:41 -0500978 sizeof (clib_bitmap_t));
979 if (exceptfds)
Dave Wallace2a865272018-02-07 21:00:42 -0500980 clib_memcpy (ldp->ex_bitmap, ldp->sid_ex_bitmap,
981 vec_len (ldp->ex_bitmap) *
Dave Wallace048b1d62018-01-03 22:24:41 -0500982 sizeof (clib_bitmap_t));
983
984 rv = vppcom_select (sid_bits,
Dave Wallace2a865272018-02-07 21:00:42 -0500985 readfds ? ldp->rd_bitmap : NULL,
986 writefds ? ldp->wr_bitmap : NULL,
987 exceptfds ? ldp->ex_bitmap : NULL, 0);
Dave Wallace048b1d62018-01-03 22:24:41 -0500988 if (rv < 0)
989 {
990 errno = -rv;
991 rv = -1;
992 }
993 else if (rv > 0)
994 {
995 if (readfds)
996 {
997 /* *INDENT-OFF* */
Dave Wallace2a865272018-02-07 21:00:42 -0500998 clib_bitmap_foreach (sid, ldp->rd_bitmap,
Dave Wallace048b1d62018-01-03 22:24:41 -0500999 ({
Dave Wallace2a865272018-02-07 21:00:42 -05001000 fd = ldp_fd_from_sid (sid);
Dave Wallace048b1d62018-01-03 22:24:41 -05001001 if (PREDICT_FALSE (fd < 0))
1002 {
1003 errno = EBADFD;
1004 rv = -1;
1005 goto done;
1006 }
1007 FD_SET (fd, readfds);
1008 }));
1009 /* *INDENT-ON* */
1010 }
1011 if (writefds)
1012 {
1013 /* *INDENT-OFF* */
Dave Wallace2a865272018-02-07 21:00:42 -05001014 clib_bitmap_foreach (sid, ldp->wr_bitmap,
Dave Wallace048b1d62018-01-03 22:24:41 -05001015 ({
Dave Wallace2a865272018-02-07 21:00:42 -05001016 fd = ldp_fd_from_sid (sid);
Dave Wallace048b1d62018-01-03 22:24:41 -05001017 if (PREDICT_FALSE (fd < 0))
1018 {
1019 errno = EBADFD;
1020 rv = -1;
1021 goto done;
1022 }
1023 FD_SET (fd, writefds);
1024 }));
1025 /* *INDENT-ON* */
1026 }
1027 if (exceptfds)
1028 {
1029 /* *INDENT-OFF* */
Dave Wallace2a865272018-02-07 21:00:42 -05001030 clib_bitmap_foreach (sid, ldp->ex_bitmap,
Dave Wallace048b1d62018-01-03 22:24:41 -05001031 ({
Dave Wallace2a865272018-02-07 21:00:42 -05001032 fd = ldp_fd_from_sid (sid);
Dave Wallace048b1d62018-01-03 22:24:41 -05001033 if (PREDICT_FALSE (fd < 0))
1034 {
1035 errno = EBADFD;
1036 rv = -1;
1037 goto done;
1038 }
1039 FD_SET (fd, exceptfds);
1040 }));
1041 /* *INDENT-ON* */
1042 }
Dave Wallace2a865272018-02-07 21:00:42 -05001043 ldp->select_vcl = 1;
Dave Wallace048b1d62018-01-03 22:24:41 -05001044 goto done;
1045 }
1046 }
1047 else
Dave Wallace2a865272018-02-07 21:00:42 -05001048 ldp->select_vcl = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -05001049 }
1050 if (libc_bits)
1051 {
1052 struct timespec tspec;
1053
1054 func_str = "libc_pselect";
1055
1056 if (readfds)
Dave Wallace2a865272018-02-07 21:00:42 -05001057 clib_memcpy (readfds, ldp->libc_rd_bitmap,
1058 vec_len (ldp->rd_bitmap) * sizeof (clib_bitmap_t));
Dave Wallace048b1d62018-01-03 22:24:41 -05001059 if (writefds)
Dave Wallace2a865272018-02-07 21:00:42 -05001060 clib_memcpy (writefds, ldp->libc_wr_bitmap,
1061 vec_len (ldp->wr_bitmap) * sizeof (clib_bitmap_t));
Dave Wallace048b1d62018-01-03 22:24:41 -05001062 if (exceptfds)
Dave Wallace2a865272018-02-07 21:00:42 -05001063 clib_memcpy (exceptfds, ldp->libc_ex_bitmap,
1064 vec_len (ldp->ex_bitmap) * sizeof (clib_bitmap_t));
Dave Wallace048b1d62018-01-03 22:24:41 -05001065 tspec.tv_sec = tspec.tv_nsec = 0;
1066 rv = libc_pselect (libc_bits,
1067 readfds ? readfds : NULL,
1068 writefds ? writefds : NULL,
1069 exceptfds ? exceptfds : NULL, &tspec, sigmask);
1070 if (rv != 0)
1071 goto done;
1072 }
1073 }
Dave Wallace2a865272018-02-07 21:00:42 -05001074 while ((time_out == -1) || (clib_time_now (&ldp->clib_time) < time_out));
Dave Wallace048b1d62018-01-03 22:24:41 -05001075 rv = 0;
1076
1077done:
1078 /* TBD: set timeout to amount of time left */
Dave Wallace2a865272018-02-07 21:00:42 -05001079 vec_reset_length (ldp->rd_bitmap);
1080 vec_reset_length (ldp->sid_rd_bitmap);
1081 vec_reset_length (ldp->libc_rd_bitmap);
1082 vec_reset_length (ldp->wr_bitmap);
1083 vec_reset_length (ldp->sid_wr_bitmap);
1084 vec_reset_length (ldp->libc_wr_bitmap);
1085 vec_reset_length (ldp->ex_bitmap);
1086 vec_reset_length (ldp->sid_ex_bitmap);
1087 vec_reset_length (ldp->libc_ex_bitmap);
Dave Wallace048b1d62018-01-03 22:24:41 -05001088
Dave Wallace2a865272018-02-07 21:00:42 -05001089 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05001090 {
1091 if (rv < 0)
1092 {
1093 int errno_val = errno;
1094 perror (func_str);
1095 clib_warning ("LDP<%d>: ERROR: %s() failed! "
1096 "rv %d, errno = %d", getpid (),
1097 func_str, rv, errno_val);
1098 errno = errno_val;
1099 }
1100 else
1101 clib_warning ("LDP<%d>: returning %d (0x%x)", getpid (), rv, rv);
1102 }
1103 return rv;
1104}
1105
1106int
1107select (int nfds, fd_set * __restrict readfds,
1108 fd_set * __restrict writefds,
1109 fd_set * __restrict exceptfds, struct timeval *__restrict timeout)
1110{
1111 struct timespec tspec;
1112
1113 if (timeout)
1114 {
1115 tspec.tv_sec = timeout->tv_sec;
1116 tspec.tv_nsec = timeout->tv_usec * 1000;
1117 }
Dave Wallace2a865272018-02-07 21:00:42 -05001118 return ldp_pselect (nfds, readfds, writefds, exceptfds,
1119 timeout ? &tspec : NULL, NULL);
Dave Wallace048b1d62018-01-03 22:24:41 -05001120}
1121
1122#ifdef __USE_XOPEN2K
1123int
1124pselect (int nfds, fd_set * __restrict readfds,
1125 fd_set * __restrict writefds,
1126 fd_set * __restrict exceptfds,
1127 const struct timespec *__restrict timeout,
1128 const __sigset_t * __restrict sigmask)
1129{
Dave Wallace2a865272018-02-07 21:00:42 -05001130 return ldp_pselect (nfds, readfds, writefds, exceptfds, timeout, 0);
Dave Wallace048b1d62018-01-03 22:24:41 -05001131}
1132#endif
1133
1134int
1135socket (int domain, int type, int protocol)
1136{
1137 const char *func_str;
1138 int rv;
1139 u8 is_nonblocking = type & SOCK_NONBLOCK ? 1 : 0;
1140 int sock_type = type & ~(SOCK_CLOEXEC | SOCK_NONBLOCK);
1141
Dave Wallace2a865272018-02-07 21:00:42 -05001142 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001143 return -1;
1144
1145 if (((domain == AF_INET) || (domain == AF_INET6)) &&
1146 ((sock_type == SOCK_STREAM) || (sock_type == SOCK_DGRAM)))
1147 {
1148 int sid;
Dave Wallace048b1d62018-01-03 22:24:41 -05001149 u8 proto = ((sock_type == SOCK_DGRAM) ?
1150 VPPCOM_PROTO_UDP : VPPCOM_PROTO_TCP);
1151
1152 func_str = "vppcom_session_create";
1153
Dave Wallace2a865272018-02-07 21:00:42 -05001154 if (LDP_DEBUG > 0)
Dave Wallacec04cbf12018-02-07 18:14:02 -05001155 clib_warning ("LDP<%d>: : calling %s(): "
Dave Wallace048b1d62018-01-03 22:24:41 -05001156 "proto %u (%s), is_nonblocking %u",
Dave Wallacec04cbf12018-02-07 18:14:02 -05001157 getpid (), func_str, proto,
Dave Wallace048b1d62018-01-03 22:24:41 -05001158 vppcom_proto_str (proto), is_nonblocking);
1159
Dave Wallacec04cbf12018-02-07 18:14:02 -05001160 sid = vppcom_session_create (proto, is_nonblocking);
Dave Wallace048b1d62018-01-03 22:24:41 -05001161 if (sid < 0)
1162 {
1163 errno = -sid;
1164 rv = -1;
1165 }
1166 else
1167 {
Dave Wallace2a865272018-02-07 21:00:42 -05001168 func_str = "ldp_fd_from_sid";
1169 rv = ldp_fd_from_sid (sid);
Dave Wallace048b1d62018-01-03 22:24:41 -05001170 if (rv < 0)
1171 {
1172 (void) vppcom_session_close (sid);
1173 errno = -rv;
1174 rv = -1;
1175 }
1176 }
1177 }
1178 else
1179 {
1180 func_str = "libc_socket";
1181
Dave Wallace2a865272018-02-07 21:00:42 -05001182 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001183 clib_warning ("LDP<%d>: : calling %s()", getpid (), func_str);
1184
1185 rv = libc_socket (domain, type, protocol);
1186 }
1187
Dave Wallace2a865272018-02-07 21:00:42 -05001188 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001189 {
1190 if (rv < 0)
1191 {
1192 int errno_val = errno;
1193 perror (func_str);
1194 clib_warning ("LDP<%d>: ERROR: %s() failed! "
1195 "rv %d, errno = %d",
1196 getpid (), func_str, rv, errno_val);
1197 errno = errno_val;
1198 }
1199 else
1200 clib_warning ("LDP<%d>: : returning fd %d (0x%x)", getpid (), rv, rv);
1201 }
1202 return rv;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001203}
1204
1205/*
1206 * Create two new sockets, of type TYPE in domain DOMAIN and using
1207 * protocol PROTOCOL, which are connected to each other, and put file
1208 * descriptors for them in FDS[0] and FDS[1]. If PROTOCOL is zero,
1209 * one will be chosen automatically.
1210 * Returns 0 on success, -1 for errors.
1211 * */
1212int
Dave Wallace048b1d62018-01-03 22:24:41 -05001213socketpair (int domain, int type, int protocol, int fds[2])
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001214{
Dave Wallace048b1d62018-01-03 22:24:41 -05001215 const char *func_str;
1216 int rv;
1217 int sock_type = type & ~(SOCK_CLOEXEC | SOCK_NONBLOCK);
1218
Dave Wallace2a865272018-02-07 21:00:42 -05001219 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001220 return -1;
1221
1222 if (((domain == AF_INET) || (domain == AF_INET6)) &&
1223 ((sock_type == SOCK_STREAM) || (sock_type == SOCK_DGRAM)))
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001224 {
Dave Wallace8aaba562018-01-18 17:21:19 -05001225 func_str = __func__;
1226
Dave Wallace048b1d62018-01-03 22:24:41 -05001227 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
1228 errno = ENOSYS;
1229 rv = -1;
1230 }
1231 else
1232 {
1233 func_str = "libc_socket";
1234
Dave Wallace2a865272018-02-07 21:00:42 -05001235 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05001236 clib_warning ("LDP<%d>: : calling %s()", getpid (), func_str);
1237
1238 rv = libc_socket (domain, type, protocol);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001239 }
1240
Dave Wallace2a865272018-02-07 21:00:42 -05001241 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05001242 {
1243 if (rv < 0)
1244 {
1245 int errno_val = errno;
1246 perror (func_str);
1247 clib_warning ("LDP<%d>: ERROR: %s() failed! "
1248 "rv %d, errno = %d",
1249 getpid (), func_str, rv, errno_val);
1250 errno = errno_val;
1251 }
1252 else
1253 clib_warning ("LDP<%d>: : returning fd %d (0x%x)", getpid (), rv, rv);
1254 }
1255 return rv;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001256}
1257
1258int
Dave Wallace048b1d62018-01-03 22:24:41 -05001259bind (int fd, __CONST_SOCKADDR_ARG addr, socklen_t len)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001260{
1261 int rv;
Dave Wallace048b1d62018-01-03 22:24:41 -05001262 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05001263 u32 sid = ldp_sid_from_fd (fd);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001264
Dave Wallace2a865272018-02-07 21:00:42 -05001265 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001266 return -1;
1267
1268 if (sid != INVALID_SESSION_ID)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001269 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001270 vppcom_endpt_t ep;
1271
1272 func_str = "vppcom_session_bind";
1273
Dave Wallace048b1d62018-01-03 22:24:41 -05001274 switch (addr->sa_family)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001275 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001276 case AF_INET:
1277 if (len != sizeof (struct sockaddr_in))
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001278 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001279 clib_warning
1280 ("LDP<%d>: ERROR: fd %d (0x%x): sid %u (0x%x): Invalid "
1281 "AF_INET addr len %u!", getpid (), fd, fd, sid, sid, len);
1282 errno = EINVAL;
1283 rv = -1;
1284 goto done;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001285 }
Dave Wallace048b1d62018-01-03 22:24:41 -05001286 ep.is_ip4 = VPPCOM_IS_IP4;
1287 ep.ip = (u8 *) & ((const struct sockaddr_in *) addr)->sin_addr;
1288 ep.port = (u16) ((const struct sockaddr_in *) addr)->sin_port;
1289 break;
1290
1291 case AF_INET6:
1292 if (len != sizeof (struct sockaddr_in6))
1293 {
1294 clib_warning
1295 ("LDP<%d>: ERROR: fd %d (0x%x): sid %u (0x%x): Invalid "
1296 "AF_INET6 addr len %u!", getpid (), fd, fd, sid, sid, len);
1297 errno = EINVAL;
1298 rv = -1;
1299 goto done;
1300 }
1301 ep.is_ip4 = VPPCOM_IS_IP6;
1302 ep.ip = (u8 *) & ((const struct sockaddr_in6 *) addr)->sin6_addr;
1303 ep.port = (u16) ((const struct sockaddr_in6 *) addr)->sin6_port;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001304 break;
1305
1306 default:
Dave Wallace048b1d62018-01-03 22:24:41 -05001307 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): sid %u (0x%x): "
1308 "Unsupported address family %u!",
1309 getpid (), fd, fd, sid, sid, addr->sa_family);
1310 errno = EAFNOSUPPORT;
1311 rv = -1;
1312 goto done;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001313 }
Dave Wallace2a865272018-02-07 21:00:42 -05001314 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001315 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), "
1316 "addr %p, len %u",
1317 getpid (), fd, fd, func_str, sid, sid, addr, len);
1318
1319 rv = vppcom_session_bind (sid, &ep);
1320 if (rv != VPPCOM_OK)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001321 {
1322 errno = -rv;
Dave Wallace048b1d62018-01-03 22:24:41 -05001323 rv = -1;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001324 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001325 }
Dave Wallace048b1d62018-01-03 22:24:41 -05001326 else
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001327 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001328 func_str = "libc_bind";
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001329
Dave Wallace2a865272018-02-07 21:00:42 -05001330 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001331 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1332 "addr %p, len %u",
1333 getpid (), fd, fd, func_str, addr, len);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001334
Dave Wallace048b1d62018-01-03 22:24:41 -05001335 rv = libc_bind (fd, addr, len);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001336 }
1337
Dave Wallace048b1d62018-01-03 22:24:41 -05001338done:
Dave Wallace2a865272018-02-07 21:00:42 -05001339 if (LDP_DEBUG > 0)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001340 {
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001341 if (rv < 0)
1342 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001343 int errno_val = errno;
1344 perror (func_str);
1345 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1346 "rv %d, errno = %d", getpid (), fd, fd,
1347 func_str, rv, errno_val);
1348 errno = errno_val;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001349 }
Dave Wallace048b1d62018-01-03 22:24:41 -05001350 else
1351 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1352 getpid (), fd, fd, rv, rv);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001353 }
1354 return rv;
1355}
1356
1357static inline int
Dave Wallace2a865272018-02-07 21:00:42 -05001358ldp_copy_ep_to_sockaddr (__SOCKADDR_ARG addr, socklen_t * __restrict len,
1359 vppcom_endpt_t * ep)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001360{
Dave Wallace048b1d62018-01-03 22:24:41 -05001361 int rv = 0;
1362 int sa_len, copy_len;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001363
Dave Wallace2a865272018-02-07 21:00:42 -05001364 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001365 return -1;
1366
1367 if (addr && len && ep)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001368 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001369 addr->sa_family = (ep->is_ip4 == VPPCOM_IS_IP4) ? AF_INET : AF_INET6;
1370 switch (addr->sa_family)
1371 {
1372 case AF_INET:
1373 ((struct sockaddr_in *) addr)->sin_port = ep->port;
1374 if (*len > sizeof (struct sockaddr_in))
1375 *len = sizeof (struct sockaddr_in);
1376 sa_len = sizeof (struct sockaddr_in) - sizeof (struct in_addr);
1377 copy_len = *len - sa_len;
1378 if (copy_len > 0)
1379 memcpy (&((struct sockaddr_in *) addr)->sin_addr, ep->ip,
1380 copy_len);
1381 break;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001382
Dave Wallace048b1d62018-01-03 22:24:41 -05001383 case AF_INET6:
1384 ((struct sockaddr_in6 *) addr)->sin6_port = ep->port;
1385 if (*len > sizeof (struct sockaddr_in6))
1386 *len = sizeof (struct sockaddr_in6);
1387 sa_len = sizeof (struct sockaddr_in6) - sizeof (struct in6_addr);
1388 copy_len = *len - sa_len;
1389 if (copy_len > 0)
1390 memcpy (((struct sockaddr_in6 *) addr)->sin6_addr.
1391 __in6_u.__u6_addr8, ep->ip, copy_len);
1392 break;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001393
Dave Wallace048b1d62018-01-03 22:24:41 -05001394 default:
1395 /* Not possible */
1396 rv = -EAFNOSUPPORT;
1397 break;
1398 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001399 }
Dave Wallacee695cb42017-11-02 22:04:42 -04001400 return rv;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001401}
1402
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001403int
Dave Wallace048b1d62018-01-03 22:24:41 -05001404getsockname (int fd, __SOCKADDR_ARG addr, socklen_t * __restrict len)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001405{
1406 int rv;
Dave Wallace048b1d62018-01-03 22:24:41 -05001407 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05001408 u32 sid = ldp_sid_from_fd (fd);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001409
Dave Wallace2a865272018-02-07 21:00:42 -05001410 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001411 return -1;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001412
Dave Wallace048b1d62018-01-03 22:24:41 -05001413 if (sid != INVALID_SESSION_ID)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001414 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001415 vppcom_endpt_t ep;
1416 u8 addr_buf[sizeof (struct in6_addr)];
1417 u32 size = sizeof (ep);
1418
1419 ep.ip = addr_buf;
1420 func_str = "vppcom_session_attr[GET_LCL_ADDR]";
1421
Dave Wallace2a865272018-02-07 21:00:42 -05001422 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001423 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), "
1424 "addr %p, len %u",
1425 getpid (), fd, fd, func_str, sid, sid, addr, len);
1426
1427 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_LCL_ADDR, &ep, &size);
1428 if (rv != VPPCOM_OK)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001429 {
1430 errno = -rv;
Dave Wallace048b1d62018-01-03 22:24:41 -05001431 rv = -1;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001432 }
Dave Wallace048b1d62018-01-03 22:24:41 -05001433 else
1434 {
Dave Wallace2a865272018-02-07 21:00:42 -05001435 rv = ldp_copy_ep_to_sockaddr (addr, len, &ep);
Dave Wallace048b1d62018-01-03 22:24:41 -05001436 if (rv != VPPCOM_OK)
1437 {
1438 errno = -rv;
1439 rv = -1;
1440 }
1441 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001442 }
1443 else
1444 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001445 func_str = "libc_getsockname";
1446
Dave Wallace2a865272018-02-07 21:00:42 -05001447 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001448 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1449 "addr %p, len %u",
1450 getpid (), fd, fd, func_str, addr, len);
1451
1452 rv = libc_getsockname (fd, addr, len);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001453 }
1454
Dave Wallace2a865272018-02-07 21:00:42 -05001455 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001456 {
1457 if (rv < 0)
1458 {
1459 int errno_val = errno;
1460 perror (func_str);
1461 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1462 "rv %d, errno = %d", getpid (), fd, fd,
1463 func_str, rv, errno_val);
1464 errno = errno_val;
1465 }
1466 else
1467 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1468 getpid (), fd, fd, rv, rv);
1469 }
1470 return rv;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001471}
1472
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001473int
Dave Wallace048b1d62018-01-03 22:24:41 -05001474connect (int fd, __CONST_SOCKADDR_ARG addr, socklen_t len)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001475{
Dave Wallace048b1d62018-01-03 22:24:41 -05001476 int rv;
1477 const char *func_str = __func__;
Dave Wallace2a865272018-02-07 21:00:42 -05001478 u32 sid = ldp_sid_from_fd (fd);
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001479
Dave Wallace2a865272018-02-07 21:00:42 -05001480 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001481 return -1;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001482
Dave Wallace048b1d62018-01-03 22:24:41 -05001483 if (!addr)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001484 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001485 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): NULL addr, len %u",
1486 getpid (), fd, fd, len);
1487 errno = EINVAL;
1488 rv = -1;
1489 goto done;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07001490 }
1491
Dave Wallace048b1d62018-01-03 22:24:41 -05001492 if (sid != INVALID_SESSION_ID)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001493 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001494 vppcom_endpt_t ep;
1495
1496 func_str = "vppcom_session_connect";
1497
Dave Wallace048b1d62018-01-03 22:24:41 -05001498 switch (addr->sa_family)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001499 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001500 case AF_INET:
1501 if (len != sizeof (struct sockaddr_in))
1502 {
1503 clib_warning
1504 ("LDP<%d>: fd %d (0x%x): ERROR sid %u (0x%x): Invalid "
1505 "AF_INET addr len %u!", getpid (), fd, fd, sid, sid, len);
1506 errno = EINVAL;
1507 rv = -1;
1508 goto done;
1509 }
1510 ep.is_ip4 = VPPCOM_IS_IP4;
1511 ep.ip = (u8 *) & ((const struct sockaddr_in *) addr)->sin_addr;
1512 ep.port = (u16) ((const struct sockaddr_in *) addr)->sin_port;
1513 break;
1514
1515 case AF_INET6:
1516 if (len != sizeof (struct sockaddr_in6))
1517 {
1518 clib_warning
1519 ("LDP<%d>: fd %d (0x%x): ERROR sid %u (0x%x): Invalid "
1520 "AF_INET6 addr len %u!", getpid (), fd, fd, sid, sid, len);
1521 errno = EINVAL;
1522 rv = -1;
1523 goto done;
1524 }
1525 ep.is_ip4 = VPPCOM_IS_IP6;
1526 ep.ip = (u8 *) & ((const struct sockaddr_in6 *) addr)->sin6_addr;
1527 ep.port = (u16) ((const struct sockaddr_in6 *) addr)->sin6_port;
1528 break;
1529
1530 default:
1531 clib_warning ("LDP<%d>: fd %d (0x%x): ERROR sid %u (0x%x): "
1532 "Unsupported address family %u!",
1533 getpid (), fd, fd, sid, sid, addr->sa_family);
1534 errno = EAFNOSUPPORT;
1535 rv = -1;
1536 goto done;
1537 }
Dave Wallace2a865272018-02-07 21:00:42 -05001538 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001539 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x) "
1540 "addr %p len %u",
1541 getpid (), fd, fd, func_str, sid, sid, addr, len);
1542
1543 rv = vppcom_session_connect (sid, &ep);
1544 if (rv != VPPCOM_OK)
1545 {
1546 errno = -rv;
1547 rv = -1;
1548 }
1549 }
1550 else
1551 {
1552 func_str = "libc_connect";
1553
Dave Wallace2a865272018-02-07 21:00:42 -05001554 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001555 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1556 "addr %p, len %u",
1557 getpid (), fd, fd, func_str, addr, len);
1558
1559 rv = libc_connect (fd, addr, len);
1560 }
1561
1562done:
Dave Wallace2a865272018-02-07 21:00:42 -05001563 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05001564 {
1565 if (rv < 0)
1566 {
1567 int errno_val = errno;
1568 perror (func_str);
1569 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1570 "rv %d, errno = %d", getpid (), fd, fd,
1571 func_str, rv, errno_val);
1572 errno = errno_val;
1573 }
1574 else
1575 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1576 getpid (), fd, fd, rv, rv);
1577 }
1578 return rv;
1579}
1580
1581int
1582getpeername (int fd, __SOCKADDR_ARG addr, socklen_t * __restrict len)
1583{
1584 int rv;
1585 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05001586 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05001587
Dave Wallace2a865272018-02-07 21:00:42 -05001588 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001589 return -1;
1590
Dave Wallace048b1d62018-01-03 22:24:41 -05001591 if (sid != INVALID_SESSION_ID)
1592 {
1593 vppcom_endpt_t ep;
1594 u8 addr_buf[sizeof (struct in6_addr)];
1595 u32 size = sizeof (ep);
1596
1597 ep.ip = addr_buf;
1598 func_str = "vppcom_session_attr[GET_PEER_ADDR]";
1599
Dave Wallace2a865272018-02-07 21:00:42 -05001600 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001601 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), "
1602 "addr %p, len %u",
1603 getpid (), fd, fd, func_str, sid, sid, addr, len);
1604
1605 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_PEER_ADDR, &ep, &size);
1606 if (rv != VPPCOM_OK)
1607 {
1608 errno = -rv;
1609 rv = -1;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001610 }
1611 else
1612 {
Dave Wallace2a865272018-02-07 21:00:42 -05001613 rv = ldp_copy_ep_to_sockaddr (addr, len, &ep);
Dave Wallace048b1d62018-01-03 22:24:41 -05001614 if (rv != VPPCOM_OK)
1615 {
1616 errno = -rv;
1617 rv = -1;
1618 }
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001619 }
1620 }
Dave Wallace048b1d62018-01-03 22:24:41 -05001621 else
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001622 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001623 func_str = "libc_getpeername";
1624
Dave Wallace2a865272018-02-07 21:00:42 -05001625 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001626 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1627 "addr %p, len %u",
1628 getpid (), fd, fd, func_str, addr, len);
1629
1630 rv = libc_getpeername (fd, addr, len);
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001631 }
1632
Dave Wallace2a865272018-02-07 21:00:42 -05001633 if (LDP_DEBUG > 2)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001634 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001635 if (rv < 0)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001636 {
Dave Wallace048b1d62018-01-03 22:24:41 -05001637 int errno_val = errno;
1638 perror (func_str);
1639 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1640 "rv %d, errno = %d", getpid (), fd, fd,
1641 func_str, rv, errno_val);
1642 errno = errno_val;
1643 }
1644 else
1645 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1646 getpid (), fd, fd, rv, rv);
1647 }
1648 return rv;
1649}
1650
1651ssize_t
1652send (int fd, const void *buf, size_t n, int flags)
1653{
1654 ssize_t size;
1655 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05001656 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05001657
Dave Wallace2a865272018-02-07 21:00:42 -05001658 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001659 return -1;
1660
1661 if (sid != INVALID_SESSION_ID)
1662 {
1663
1664 func_str = "vppcom_session_sendto";
1665
Dave Wallace2a865272018-02-07 21:00:42 -05001666 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001667 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), "
1668 "buf %p, n %u, flags 0x%x",
1669 getpid (), fd, fd, func_str, sid, sid, buf, n, flags);
1670
1671 size = vppcom_session_sendto (sid, (void *) buf, n, flags, NULL);
qchangaa8f63c2018-05-30 11:44:18 -07001672 if (size < VPPCOM_OK)
Dave Wallace048b1d62018-01-03 22:24:41 -05001673 {
1674 errno = -size;
1675 size = -1;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07001676 }
1677 }
Dave Wallace048b1d62018-01-03 22:24:41 -05001678 else
1679 {
1680 func_str = "libc_send";
1681
Dave Wallace2a865272018-02-07 21:00:42 -05001682 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001683 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1684 "buf %p, n %u, flags 0x%x",
1685 getpid (), fd, fd, func_str, buf, n, flags);
1686
1687 size = libc_send (fd, buf, n, flags);
1688 }
1689
Dave Wallace2a865272018-02-07 21:00:42 -05001690 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001691 {
1692 if (size < 0)
1693 {
1694 int errno_val = errno;
1695 perror (func_str);
1696 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1697 "rv %d, errno = %d", getpid (), fd, fd,
1698 func_str, size, errno_val);
1699 errno = errno_val;
1700 }
1701 else
1702 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1703 getpid (), fd, fd, size, size);
1704 }
1705 return size;
1706}
1707
1708ssize_t
1709sendfile (int out_fd, int in_fd, off_t * offset, size_t len)
1710{
1711 ssize_t size = 0;
1712 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05001713 u32 sid = ldp_sid_from_fd (out_fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05001714
Dave Wallace2a865272018-02-07 21:00:42 -05001715 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001716 return -1;
1717
1718 if (sid != INVALID_SESSION_ID)
1719 {
1720 int rv;
1721 ssize_t results = 0;
1722 size_t n_bytes_left = len;
1723 size_t bytes_to_read;
1724 int nbytes;
1725 int errno_val;
1726 u8 eagain = 0;
1727 u32 flags, flags_len = sizeof (flags);
1728
1729 func_str = "vppcom_session_attr[GET_FLAGS]";
1730 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_FLAGS, &flags,
1731 &flags_len);
1732 if (PREDICT_FALSE (rv != VPPCOM_OK))
1733 {
1734 clib_warning ("LDP<%d>: ERROR: out fd %d (0x%x): %s(): "
1735 "sid %u (0x%x), returned %d (%s)!", getpid (),
1736 out_fd, out_fd, func_str, sid, sid, rv,
1737 vppcom_retval_str (rv));
1738
Dave Wallace2a865272018-02-07 21:00:42 -05001739 vec_reset_length (ldp->io_buffer);
Dave Wallace048b1d62018-01-03 22:24:41 -05001740 errno = -rv;
1741 size = -1;
1742 goto done;
1743 }
1744
1745 if (offset)
1746 {
1747 off_t off = lseek (in_fd, *offset, SEEK_SET);
1748 if (PREDICT_FALSE (off == -1))
1749 {
1750 func_str = "lseek";
1751 errno_val = errno;
1752 clib_warning ("LDP<%d>: ERROR: out fd %d (0x%x): %s(): "
1753 "SEEK_SET failed: in_fd %d, offset %p, "
1754 "*offset %ld, rv %ld, errno %d", getpid (),
1755 out_fd, out_fd, in_fd, offset, *offset, off,
1756 errno_val);
1757 errno = errno_val;
1758 size = -1;
1759 goto done;
1760 }
1761
1762 ASSERT (off == *offset);
1763 }
1764
1765 do
1766 {
1767 func_str = "vppcom_session_attr[GET_NWRITE]";
1768 size = vppcom_session_attr (sid, VPPCOM_ATTR_GET_NWRITE, 0, 0);
1769 if (size < 0)
1770 {
1771 clib_warning
1772 ("LDP<%d>: ERROR: fd %d (0x%x): %s(): sid %u (0x%x), "
1773 "returned %d (%s)!", getpid (), out_fd, out_fd, func_str,
1774 sid, sid, size, vppcom_retval_str (size));
Dave Wallace2a865272018-02-07 21:00:42 -05001775 vec_reset_length (ldp->io_buffer);
Dave Wallace048b1d62018-01-03 22:24:41 -05001776 errno = -size;
1777 size = -1;
1778 goto done;
1779 }
1780
1781 bytes_to_read = size;
Dave Wallace2a865272018-02-07 21:00:42 -05001782 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001783 clib_warning
1784 ("LDP<%d>: fd %d (0x%x): called %s(): sid %u (0x%x), "
1785 "results %ld, n_bytes_left %lu, bytes_to_read %lu", getpid (),
1786 out_fd, out_fd, func_str, sid, sid, results, n_bytes_left,
1787 bytes_to_read);
1788
1789 if (bytes_to_read == 0)
1790 {
1791 if (flags & O_NONBLOCK)
1792 {
1793 if (!results)
1794 {
Dave Wallace2a865272018-02-07 21:00:42 -05001795 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001796 clib_warning ("LDP<%d>: fd %d (0x%x): sid %u (0x%x): "
1797 "EAGAIN",
1798 getpid (), out_fd, out_fd, sid, sid);
1799 eagain = 1;
1800 }
1801 goto update_offset;
1802 }
1803 else
1804 continue;
1805 }
1806 bytes_to_read = clib_min (n_bytes_left, bytes_to_read);
Dave Wallace2a865272018-02-07 21:00:42 -05001807 vec_validate (ldp->io_buffer, bytes_to_read);
1808 nbytes = libc_read (in_fd, ldp->io_buffer, bytes_to_read);
Dave Wallace048b1d62018-01-03 22:24:41 -05001809 if (nbytes < 0)
1810 {
1811 func_str = "libc_read";
1812 errno_val = errno;
1813 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): in_fd (%d), "
1814 "io_buffer %p, bytes_to_read %lu, rv %d, "
1815 "errno %d", getpid (), out_fd, out_fd, func_str,
Dave Wallace2a865272018-02-07 21:00:42 -05001816 in_fd, ldp->io_buffer, bytes_to_read, nbytes,
Dave Wallace048b1d62018-01-03 22:24:41 -05001817 errno_val);
1818 errno = errno_val;
1819
1820 if (results == 0)
1821 {
Dave Wallace2a865272018-02-07 21:00:42 -05001822 vec_reset_length (ldp->io_buffer);
Dave Wallace048b1d62018-01-03 22:24:41 -05001823 size = -1;
1824 goto done;
1825 }
1826 goto update_offset;
1827 }
1828 func_str = "vppcom_session_write";
Dave Wallace2a865272018-02-07 21:00:42 -05001829 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001830 clib_warning
1831 ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), "
1832 "buf %p, nbytes %u: results %d, n_bytes_left %d", getpid (),
Dave Wallace2a865272018-02-07 21:00:42 -05001833 out_fd, out_fd, func_str, sid, sid, ldp->io_buffer, nbytes,
Dave Wallace048b1d62018-01-03 22:24:41 -05001834 results, n_bytes_left);
1835
Dave Wallace2a865272018-02-07 21:00:42 -05001836 size = vppcom_session_write (sid, ldp->io_buffer, nbytes);
Dave Wallace048b1d62018-01-03 22:24:41 -05001837 if (size < 0)
1838 {
1839 if (size == VPPCOM_EAGAIN)
1840 {
1841 if (flags & O_NONBLOCK)
1842 {
1843 if (!results)
1844 {
Dave Wallace2a865272018-02-07 21:00:42 -05001845 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001846 clib_warning
1847 ("LDP<%d>: fd %d (0x%x): sid %u (0x%x): "
1848 "EAGAIN", getpid (), out_fd, out_fd, sid, sid);
1849 eagain = 1;
1850 }
1851 goto update_offset;
1852 }
1853 else
1854 continue;
1855 }
1856 else
1857 {
1858 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s():"
1859 "sid %u, io_buffer %p, nbytes %u "
1860 "returned %d (%s)",
1861 getpid (), out_fd, out_fd, func_str,
Dave Wallace2a865272018-02-07 21:00:42 -05001862 sid, ldp->io_buffer, nbytes,
Dave Wallace048b1d62018-01-03 22:24:41 -05001863 size, vppcom_retval_str (size));
1864 }
1865 if (results == 0)
1866 {
Dave Wallace2a865272018-02-07 21:00:42 -05001867 vec_reset_length (ldp->io_buffer);
Dave Wallace048b1d62018-01-03 22:24:41 -05001868 errno = -size;
1869 size = -1;
1870 goto done;
1871 }
1872 goto update_offset;
1873 }
1874
1875 results += nbytes;
1876 ASSERT (n_bytes_left >= nbytes);
1877 n_bytes_left = n_bytes_left - nbytes;
1878 }
1879 while (n_bytes_left > 0);
1880
1881 update_offset:
Dave Wallace2a865272018-02-07 21:00:42 -05001882 vec_reset_length (ldp->io_buffer);
Dave Wallace048b1d62018-01-03 22:24:41 -05001883 if (offset)
1884 {
1885 off_t off = lseek (in_fd, *offset, SEEK_SET);
1886 if (PREDICT_FALSE (off == -1))
1887 {
1888 func_str = "lseek";
1889 errno_val = errno;
1890 clib_warning ("LDP<%d>: ERROR: %s(): SEEK_SET failed: "
1891 "in_fd %d, offset %p, *offset %ld, "
1892 "rv %ld, errno %d", getpid (), in_fd,
1893 offset, *offset, off, errno_val);
1894 errno = errno_val;
1895 size = -1;
1896 goto done;
1897 }
1898
1899 ASSERT (off == *offset);
1900 *offset += results + 1;
1901 }
1902 if (eagain)
1903 {
1904 errno = EAGAIN;
1905 size = -1;
1906 }
1907 else
1908 size = results;
1909 }
1910 else
1911 {
1912 func_str = "libc_send";
1913
Dave Wallace2a865272018-02-07 21:00:42 -05001914 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001915 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1916 "in_fd %d, offset %p, len %u",
1917 getpid (), out_fd, out_fd, func_str,
1918 in_fd, offset, len);
1919
1920 size = libc_sendfile (out_fd, in_fd, offset, len);
1921 }
1922
1923done:
Dave Wallace2a865272018-02-07 21:00:42 -05001924 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001925 {
1926 if (size < 0)
1927 {
1928 int errno_val = errno;
1929 perror (func_str);
1930 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1931 "rv %d, errno = %d", getpid (), out_fd, out_fd,
1932 func_str, size, errno_val);
1933 errno = errno_val;
1934 }
1935 else
1936 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1937 getpid (), out_fd, out_fd, size, size);
1938 }
1939 return size;
1940}
1941
1942ssize_t
1943sendfile64 (int out_fd, int in_fd, off_t * offset, size_t len)
1944{
1945 return sendfile (out_fd, in_fd, offset, len);
1946}
1947
1948ssize_t
1949recv (int fd, void *buf, size_t n, int flags)
1950{
1951 ssize_t size;
1952 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05001953 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05001954
Dave Wallace2a865272018-02-07 21:00:42 -05001955 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05001956 return -1;
1957
1958 if (sid != INVALID_SESSION_ID)
1959 {
1960 func_str = "vppcom_session_recvfrom";
1961
Dave Wallace2a865272018-02-07 21:00:42 -05001962 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001963 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1964 "sid %u (0x%x), buf %p, n %u, flags 0x%x", getpid (),
1965 fd, fd, func_str, sid, sid, buf, n, flags);
1966
1967 size = vppcom_session_recvfrom (sid, buf, n, flags, NULL);
1968 if (size < 0)
1969 {
1970 errno = -size;
1971 size = -1;
1972 }
1973 }
1974 else
1975 {
1976 func_str = "libc_recv";
1977
Dave Wallace2a865272018-02-07 21:00:42 -05001978 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001979 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
1980 "buf %p, n %u, flags 0x%x", getpid (),
1981 fd, fd, func_str, buf, n, flags);
1982
1983 size = libc_recv (fd, buf, n, flags);
1984 }
1985
Dave Wallace2a865272018-02-07 21:00:42 -05001986 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05001987 {
1988 if (size < 0)
1989 {
1990 int errno_val = errno;
1991 perror (func_str);
1992 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
1993 "rv %d, errno = %d", getpid (), fd, fd,
1994 func_str, size, errno_val);
1995 errno = errno_val;
1996 }
1997 else
1998 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
1999 getpid (), fd, fd, size, size);
2000 }
2001 return size;
2002}
2003
2004ssize_t
2005sendto (int fd, const void *buf, size_t n, int flags,
2006 __CONST_SOCKADDR_ARG addr, socklen_t addr_len)
2007{
2008 ssize_t size;
2009 const char *func_str = __func__;
Dave Wallace2a865272018-02-07 21:00:42 -05002010 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002011
Dave Wallace2a865272018-02-07 21:00:42 -05002012 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002013 return -1;
2014
2015 if (sid != INVALID_SESSION_ID)
2016 {
2017 vppcom_endpt_t *ep = 0;
2018 vppcom_endpt_t _ep;
2019
2020 if (addr)
2021 {
2022 ep = &_ep;
Dave Wallace048b1d62018-01-03 22:24:41 -05002023 switch (addr->sa_family)
2024 {
2025 case AF_INET:
2026 ep->is_ip4 = VPPCOM_IS_IP4;
2027 ep->ip =
2028 (uint8_t *) & ((const struct sockaddr_in *) addr)->sin_addr;
2029 ep->port =
2030 (uint16_t) ((const struct sockaddr_in *) addr)->sin_port;
2031 break;
2032
2033 case AF_INET6:
2034 ep->is_ip4 = VPPCOM_IS_IP6;
2035 ep->ip =
2036 (uint8_t *) & ((const struct sockaddr_in6 *) addr)->sin6_addr;
2037 ep->port =
2038 (uint16_t) ((const struct sockaddr_in6 *) addr)->sin6_port;
2039 break;
2040
2041 default:
2042 errno = EAFNOSUPPORT;
2043 size = -1;
2044 goto done;
2045 }
2046 }
2047
2048 func_str = "vppcom_session_sendto";
2049
Dave Wallace2a865272018-02-07 21:00:42 -05002050 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002051 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2052 "sid %u (0x%x), buf %p, n %u, flags 0x%x, ep %p",
2053 getpid (), fd, fd, func_str, sid, sid, buf, n,
2054 flags, ep);
2055
2056 size = vppcom_session_sendto (sid, (void *) buf, n, flags, ep);
2057 if (size < 0)
2058 {
2059 errno = -size;
2060 size = -1;
2061 }
2062 }
2063 else
2064 {
2065 func_str = "libc_sendto";
2066
Dave Wallace2a865272018-02-07 21:00:42 -05002067 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002068 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2069 "buf %p, n %u, flags 0x%x, addr %p, addr_len %d",
2070 getpid (), fd, fd, func_str, buf, n, flags,
2071 addr, addr_len);
2072
2073 size = libc_sendto (fd, buf, n, flags, addr, addr_len);
2074 }
2075
2076done:
Dave Wallace2a865272018-02-07 21:00:42 -05002077 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002078 {
2079 if (size < 0)
2080 {
2081 int errno_val = errno;
2082 perror (func_str);
2083 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2084 "rv %d, errno = %d", getpid (), fd, fd,
2085 func_str, size, errno_val);
2086 errno = errno_val;
2087 }
2088 else
2089 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2090 getpid (), fd, fd, size, size);
2091 }
2092 return size;
2093}
2094
2095ssize_t
2096recvfrom (int fd, void *__restrict buf, size_t n, int flags,
2097 __SOCKADDR_ARG addr, socklen_t * __restrict addr_len)
2098{
2099 ssize_t size;
2100 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002101 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002102
Dave Wallace2a865272018-02-07 21:00:42 -05002103 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002104 return -1;
2105
2106 if (sid != INVALID_SESSION_ID)
2107 {
2108 vppcom_endpt_t ep;
2109 u8 src_addr[sizeof (struct sockaddr_in6)];
2110
2111 func_str = "vppcom_session_recvfrom";
2112
Dave Wallace2a865272018-02-07 21:00:42 -05002113 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002114 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2115 "sid %u (0x%x), buf %p, n %u, flags 0x%x, ep %p",
2116 getpid (), fd, fd, func_str, sid, sid, buf, n,
2117 flags, &ep);
2118 if (addr)
2119 {
2120 ep.ip = src_addr;
2121 size = vppcom_session_recvfrom (sid, buf, n, flags, &ep);
2122
2123 if (size > 0)
Dave Wallace2a865272018-02-07 21:00:42 -05002124 size = ldp_copy_ep_to_sockaddr (addr, addr_len, &ep);
Dave Wallace048b1d62018-01-03 22:24:41 -05002125 }
2126 else
2127 size = vppcom_session_recvfrom (sid, buf, n, flags, NULL);
2128
2129 if (size < 0)
2130 {
2131 errno = -size;
2132 size = -1;
2133 }
2134 }
2135 else
2136 {
2137 func_str = "libc_recvfrom";
2138
Dave Wallace2a865272018-02-07 21:00:42 -05002139 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002140 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2141 "buf %p, n %u, flags 0x%x, addr %p, addr_len %d",
2142 getpid (), fd, fd, func_str, buf, n, flags,
2143 addr, addr_len);
2144
2145 size = libc_recvfrom (fd, buf, n, flags, addr, addr_len);
2146 }
2147
Dave Wallace2a865272018-02-07 21:00:42 -05002148 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002149 {
2150 if (size < 0)
2151 {
2152 int errno_val = errno;
2153 perror (func_str);
2154 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2155 "rv %d, errno = %d", getpid (), fd, fd,
2156 func_str, size, errno_val);
2157 errno = errno_val;
2158 }
2159 else
2160 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2161 getpid (), fd, fd, size, size);
2162 }
2163 return size;
2164}
2165
2166ssize_t
2167sendmsg (int fd, const struct msghdr * message, int flags)
2168{
2169 ssize_t size;
2170 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002171 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002172
Dave Wallace2a865272018-02-07 21:00:42 -05002173 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002174 return -1;
2175
2176 if (sid != INVALID_SESSION_ID)
2177 {
Dave Wallace8aaba562018-01-18 17:21:19 -05002178 func_str = __func__;
2179
Dave Wallace048b1d62018-01-03 22:24:41 -05002180 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
2181 errno = ENOSYS;
2182 size = -1;
2183 }
2184 else
2185 {
2186 func_str = "libc_sendmsg";
2187
Dave Wallace2a865272018-02-07 21:00:42 -05002188 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002189 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2190 "message %p, flags 0x%x",
2191 getpid (), fd, fd, func_str, message, flags);
2192
2193 size = libc_sendmsg (fd, message, flags);
2194 }
2195
Dave Wallace2a865272018-02-07 21:00:42 -05002196 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002197 {
2198 if (size < 0)
2199 {
2200 int errno_val = errno;
2201 perror (func_str);
2202 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2203 "rv %d, errno = %d", getpid (), fd, fd,
2204 func_str, size, errno_val);
2205 errno = errno_val;
2206 }
2207 else
2208 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2209 getpid (), fd, fd, size, size);
2210 }
2211 return size;
2212}
2213
2214#ifdef USE_GNU
2215int
2216sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
2217{
2218 ssize_t size;
2219 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002220 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002221
Dave Wallace2a865272018-02-07 21:00:42 -05002222 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002223 return -1;
2224
2225 if (sid != INVALID_SESSION_ID)
2226 {
2227 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
2228 errno = ENOSYS;
2229 size = -1;
2230 }
2231 else
2232 {
2233 func_str = "libc_sendmmsg";
2234
Dave Wallace2a865272018-02-07 21:00:42 -05002235 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002236 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2237 "vmessages %p, vlen %u, flags 0x%x",
2238 getpid (), fd, fd, func_str, vmessages, vlen, flags);
2239
2240 size = libc_sendmmsg (fd, vmessages, vlen, flags);
2241 }
2242
Dave Wallace2a865272018-02-07 21:00:42 -05002243 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002244 {
2245 if (size < 0)
2246 {
2247 int errno_val = errno;
2248 perror (func_str);
2249 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2250 "rv %d, errno = %d", getpid (), fd, fd,
2251 func_str, size, errno_val);
2252 errno = errno_val;
2253 }
2254 else
2255 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2256 getpid (), fd, fd, size, size);
2257 }
2258 return size;
2259}
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002260#endif
2261
Dave Wallace048b1d62018-01-03 22:24:41 -05002262ssize_t
2263recvmsg (int fd, struct msghdr * message, int flags)
2264{
2265 ssize_t size;
2266 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002267 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002268
Dave Wallace2a865272018-02-07 21:00:42 -05002269 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002270 return -1;
2271
2272 if (sid != INVALID_SESSION_ID)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002273 {
Dave Wallace8aaba562018-01-18 17:21:19 -05002274 func_str = __func__;
2275
Dave Wallace048b1d62018-01-03 22:24:41 -05002276 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
2277 errno = ENOSYS;
2278 size = -1;
2279 }
2280 else
2281 {
2282 func_str = "libc_recvmsg";
2283
Dave Wallace2a865272018-02-07 21:00:42 -05002284 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002285 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2286 "message %p, flags 0x%x",
2287 getpid (), fd, fd, func_str, message, flags);
2288
2289 size = libc_recvmsg (fd, message, flags);
2290 }
2291
Dave Wallace2a865272018-02-07 21:00:42 -05002292 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002293 {
2294 if (size < 0)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002295 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002296 int errno_val = errno;
2297 perror (func_str);
2298 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2299 "rv %d, errno = %d", getpid (), fd, fd,
2300 func_str, size, errno_val);
2301 errno = errno_val;
2302 }
2303 else
2304 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2305 getpid (), fd, fd, size, size);
2306 }
2307 return size;
2308}
2309
2310#ifdef USE_GNU
2311int
2312recvmmsg (int fd, struct mmsghdr *vmessages,
2313 unsigned int vlen, int flags, struct timespec *tmo)
2314{
2315 ssize_t size;
2316 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002317 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002318
Dave Wallace2a865272018-02-07 21:00:42 -05002319 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002320 return -1;
2321
2322 if (sid != INVALID_SESSION_ID)
2323 {
2324 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
2325 errno = ENOSYS;
2326 size = -1;
2327 }
2328 else
2329 {
2330 func_str = "libc_recvmmsg";
2331
Dave Wallace2a865272018-02-07 21:00:42 -05002332 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002333 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2334 "vmessages %p, vlen %u, flags 0x%x, tmo %p",
2335 getpid (), fd, fd, func_str, vmessages, vlen,
2336 flags, tmo);
2337
2338 size = libc_recvmmsg (fd, vmessages, vlen, flags, tmo);
2339 }
2340
Dave Wallace2a865272018-02-07 21:00:42 -05002341 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05002342 {
2343 if (size < 0)
2344 {
2345 int errno_val = errno;
2346 perror (func_str);
2347 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2348 "rv %d, errno = %d", getpid (), fd, fd,
2349 func_str, size, errno_val);
2350 errno = errno_val;
2351 }
2352 else
2353 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2354 getpid (), fd, fd, size, size);
2355 }
2356 return size;
2357}
2358#endif
2359
2360int
2361getsockopt (int fd, int level, int optname,
2362 void *__restrict optval, socklen_t * __restrict optlen)
2363{
2364 int rv;
2365 const char *func_str = __func__;
Dave Wallace2a865272018-02-07 21:00:42 -05002366 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace8aaba562018-01-18 17:21:19 -05002367 u32 buflen = optlen ? (u32) * optlen : 0;
Dave Wallace048b1d62018-01-03 22:24:41 -05002368
Dave Wallace2a865272018-02-07 21:00:42 -05002369 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002370 return -1;
2371
2372 if (sid != INVALID_SESSION_ID)
2373 {
2374 rv = -EOPNOTSUPP;
2375
2376 switch (level)
2377 {
2378 case SOL_TCP:
2379 switch (optname)
2380 {
2381 case TCP_NODELAY:
2382 func_str = "vppcom_session_attr[SOL_TCP,GET_TCP_NODELAY]";
Dave Wallace2a865272018-02-07 21:00:42 -05002383 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002384 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2385 "sid %u (0x%x)",
2386 getpid (), fd, fd, func_str, sid, sid);
2387 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_TCP_NODELAY,
2388 optval, optlen);
2389 break;
2390 case TCP_MAXSEG:
2391 func_str = "vppcom_session_attr[SOL_TCP,GET_TCP_USER_MSS]";
Dave Wallace2a865272018-02-07 21:00:42 -05002392 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002393 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2394 "sid %u (0x%x)",
2395 getpid (), fd, fd, func_str, sid, sid);
2396 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_TCP_USER_MSS,
2397 optval, optlen);
2398 break;
2399 case TCP_KEEPIDLE:
2400 func_str = "vppcom_session_attr[SOL_TCP,GET_TCP_KEEPIDLE]";
Dave Wallace2a865272018-02-07 21:00:42 -05002401 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002402 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2403 "sid %u (0x%x)",
2404 getpid (), fd, fd, func_str, sid, sid);
2405 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_TCP_KEEPIDLE,
2406 optval, optlen);
2407 break;
2408 case TCP_KEEPINTVL:
2409 func_str = "vppcom_session_attr[SOL_TCP,GET_TCP_KEEPINTVL]";
Dave Wallace2a865272018-02-07 21:00:42 -05002410 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002411 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2412 "sid %u (0x%x), SOL_TCP",
2413 getpid (), fd, fd, func_str, sid, sid);
2414 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_TCP_KEEPINTVL,
2415 optval, optlen);
2416 break;
2417 case TCP_INFO:
2418 if (optval && optlen && (*optlen == sizeof (struct tcp_info)))
2419 {
Dave Wallace2a865272018-02-07 21:00:42 -05002420 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002421 clib_warning ("LDP<%d>: fd %d (0x%x): sid %u (0x%x), "
2422 "SOL_TCP, TCP_INFO, optval %p, "
2423 "optlen %d: #LDP-NOP#",
2424 getpid (), fd, fd, sid, sid,
2425 optval, *optlen);
2426 memset (optval, 0, *optlen);
2427 rv = VPPCOM_OK;
2428 }
2429 else
2430 rv = -EFAULT;
2431 break;
2432 default:
Dave Wallace2a865272018-02-07 21:00:42 -05002433 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002434 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): "
2435 "sid %u (0x%x), SOL_TCP, "
2436 "optname %d unsupported!",
2437 getpid (), fd, fd, func_str, sid, sid, optname);
2438 break;
2439 }
2440 break;
2441 case SOL_IPV6:
2442 switch (optname)
2443 {
2444 case IPV6_V6ONLY:
2445 func_str = "vppcom_session_attr[SOL_IPV6,GET_V6ONLY]";
Dave Wallace2a865272018-02-07 21:00:42 -05002446 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002447 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2448 "sid %u (0x%x)",
2449 getpid (), fd, fd, func_str, sid, sid);
2450 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_V6ONLY,
2451 optval, optlen);
2452 break;
2453 default:
Dave Wallace2a865272018-02-07 21:00:42 -05002454 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002455 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): "
2456 "sid %u (0x%x), SOL_IPV6, "
2457 "optname %d unsupported!",
2458 getpid (), fd, fd, func_str, sid, sid, optname);
2459 break;
2460 }
2461 break;
2462 case SOL_SOCKET:
2463 switch (optname)
2464 {
2465 case SO_ACCEPTCONN:
2466 func_str = "vppcom_session_attr[SOL_SOCKET,GET_ACCEPTCONN]";
Dave Wallace2a865272018-02-07 21:00:42 -05002467 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002468 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2469 "sid %u (0x%x)",
2470 getpid (), fd, fd, func_str, sid, sid);
2471 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_LISTEN,
2472 optval, optlen);
2473 break;
2474 case SO_KEEPALIVE:
2475 func_str = "vppcom_session_attr[SOL_SOCKET,GET_KEEPALIVE]";
Dave Wallace2a865272018-02-07 21:00:42 -05002476 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002477 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2478 "sid %u (0x%x)",
2479 getpid (), fd, fd, func_str, sid, sid);
2480 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_KEEPALIVE,
2481 optval, optlen);
2482 break;
2483 case SO_PROTOCOL:
2484 func_str = "vppcom_session_attr[SOL_SOCKET,GET_PROTOCOL]";
Dave Wallace2a865272018-02-07 21:00:42 -05002485 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002486 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2487 "sid %u (0x%x)",
2488 getpid (), fd, fd, func_str, sid, sid);
2489 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_PROTOCOL,
2490 optval, optlen);
2491 *(int *) optval = *(int *) optval ? SOCK_DGRAM : SOCK_STREAM;
2492 break;
2493 case SO_SNDBUF:
2494 func_str = "vppcom_session_attr[SOL_SOCKET,GET_TX_FIFO_LEN]";
Dave Wallace2a865272018-02-07 21:00:42 -05002495 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002496 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2497 "sid %u (0x%x), optlen %d",
2498 getpid (), fd, fd, func_str, sid, sid, buflen);
2499 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_TX_FIFO_LEN,
2500 optval, optlen);
2501 break;
2502 case SO_RCVBUF:
2503 func_str = "vppcom_session_attr[SOL_SOCKET,GET_RX_FIFO_LEN]";
Dave Wallace2a865272018-02-07 21:00:42 -05002504 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002505 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2506 "sid %u (0x%x), optlen %d",
Dave Wallaceb4cd4ff2018-01-19 12:17:08 -05002507 getpid (), fd, fd, func_str, sid, sid, buflen);
Dave Wallace048b1d62018-01-03 22:24:41 -05002508 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_RX_FIFO_LEN,
2509 optval, optlen);
2510 break;
2511 case SO_REUSEADDR:
2512 func_str = "vppcom_session_attr[SOL_SOCKET,GET_REUSEADDR]";
Dave Wallace2a865272018-02-07 21:00:42 -05002513 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002514 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2515 "sid %u (0x%x)",
2516 getpid (), fd, fd, func_str, sid, sid);
2517 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_REUSEADDR,
2518 optval, optlen);
2519 break;
2520 case SO_BROADCAST:
2521 func_str = "vppcom_session_attr[SOL_SOCKET,GET_BROADCAST]";
Dave Wallace2a865272018-02-07 21:00:42 -05002522 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002523 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2524 "sid %u (0x%x)",
2525 getpid (), fd, fd, func_str, sid, sid);
2526 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_BROADCAST,
2527 optval, optlen);
2528 break;
2529 case SO_ERROR:
2530 func_str = "vppcom_session_attr[SOL_SOCKET,GET_ERROR]";
Dave Wallace2a865272018-02-07 21:00:42 -05002531 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002532 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2533 "sid %u (0x%x)",
2534 getpid (), fd, fd, func_str, sid, sid);
2535 rv = vppcom_session_attr (sid, VPPCOM_ATTR_GET_ERROR,
2536 optval, optlen);
2537 break;
2538 default:
Dave Wallace2a865272018-02-07 21:00:42 -05002539 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002540 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): "
2541 "sid %u (0x%x), SOL_SOCKET, "
2542 "optname %d unsupported!",
2543 getpid (), fd, fd, func_str, sid, sid, optname);
2544 break;
2545 }
2546 break;
2547 default:
2548 break;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002549 }
2550
Dave Wallace048b1d62018-01-03 22:24:41 -05002551 if (rv != VPPCOM_OK)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002552 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002553 errno = -rv;
2554 rv = -1;
2555 }
2556 }
2557 else
2558 {
2559 func_str = "libc_getsockopt";
2560
Dave Wallace2a865272018-02-07 21:00:42 -05002561 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002562 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): level %d, "
2563 "optname %d, optval %p, optlen %d",
2564 getpid (), fd, fd, func_str, level, optname,
2565 optval, optlen);
2566
2567 rv = libc_getsockopt (fd, level, optname, optval, optlen);
2568 }
2569
Dave Wallace2a865272018-02-07 21:00:42 -05002570 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002571 {
2572 if (rv < 0)
2573 {
2574 int errno_val = errno;
2575 perror (func_str);
2576 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2577 "rv %d, errno = %d", getpid (), fd, fd,
2578 func_str, rv, errno_val);
2579 errno = errno_val;
2580 }
2581 else
2582 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2583 getpid (), fd, fd, rv, rv);
2584 }
2585 return rv;
2586}
2587
2588int
2589setsockopt (int fd, int level, int optname,
2590 const void *optval, socklen_t optlen)
2591{
2592 int rv;
2593 const char *func_str = __func__;
Dave Wallace2a865272018-02-07 21:00:42 -05002594 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002595
Dave Wallace2a865272018-02-07 21:00:42 -05002596 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002597 return -1;
2598
2599 if (sid != INVALID_SESSION_ID)
2600 {
2601 rv = -EOPNOTSUPP;
2602
2603 switch (level)
2604 {
2605 case SOL_TCP:
2606 switch (optname)
2607 {
2608 case TCP_NODELAY:
2609 func_str = "vppcom_session_attr[SOL_TCP,SET_TCP_NODELAY]";
Dave Wallace2a865272018-02-07 21:00:42 -05002610 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002611 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2612 "sid %u (0x%x)",
2613 getpid (), fd, fd, func_str, sid, sid);
2614 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_TCP_NODELAY,
2615 (void *) optval, &optlen);
2616 break;
2617 case TCP_MAXSEG:
2618 func_str = "vppcom_session_attr[SOL_TCP,SET_TCP_USER_MSS]";
Dave Wallace2a865272018-02-07 21:00:42 -05002619 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002620 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2621 "sid %u (0x%x)",
2622 getpid (), fd, fd, func_str, sid, sid);
2623 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_TCP_USER_MSS,
2624 (void *) optval, &optlen);
2625 break;
2626 case TCP_KEEPIDLE:
2627 func_str = "vppcom_session_attr[SOL_TCP,SET_TCP_KEEPIDLE]";
Dave Wallace2a865272018-02-07 21:00:42 -05002628 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002629 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2630 "sid %u (0x%x)",
2631 getpid (), fd, fd, func_str, sid, sid);
2632 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_TCP_KEEPIDLE,
2633 (void *) optval, &optlen);
2634 break;
2635 case TCP_KEEPINTVL:
2636 func_str = "vppcom_session_attr[SOL_TCP,SET_TCP_KEEPINTVL]";
Dave Wallace2a865272018-02-07 21:00:42 -05002637 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002638 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2639 "sid %u (0x%x), SOL_TCP",
2640 getpid (), fd, fd, func_str, sid, sid);
2641 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_TCP_KEEPINTVL,
2642 (void *) optval, &optlen);
2643 break;
2644 default:
Dave Wallace2a865272018-02-07 21:00:42 -05002645 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002646 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): "
2647 "sid %u (0x%x), SOL_TCP, "
2648 "optname %d unsupported!",
2649 getpid (), fd, fd, func_str, sid, sid, optname);
2650 break;
2651 }
2652 break;
2653 case SOL_IPV6:
2654 switch (optname)
2655 {
2656 case IPV6_V6ONLY:
2657 func_str = "vppcom_session_attr[SOL_IPV6,SET_V6ONLY]";
Dave Wallace2a865272018-02-07 21:00:42 -05002658 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002659 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2660 "sid %u (0x%x)",
2661 getpid (), fd, fd, func_str, sid, sid);
2662 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_V6ONLY,
2663 (void *) optval, &optlen);
2664 break;
2665 default:
Dave Wallace2a865272018-02-07 21:00:42 -05002666 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002667 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): "
2668 "sid %u (0x%x), SOL_IPV6, "
2669 "optname %d unsupported!",
2670 getpid (), fd, fd, func_str, sid, sid, optname);
2671 break;
2672 }
2673 break;
2674 case SOL_SOCKET:
2675 switch (optname)
2676 {
2677 case SO_KEEPALIVE:
2678 func_str = "vppcom_session_attr[SOL_SOCKET,SET_KEEPALIVE]";
Dave Wallace2a865272018-02-07 21:00:42 -05002679 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002680 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2681 "sid %u (0x%x)",
2682 getpid (), fd, fd, func_str, sid, sid);
2683 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_KEEPALIVE,
2684 (void *) optval, &optlen);
2685 break;
2686 case SO_REUSEADDR:
2687 func_str = "vppcom_session_attr[SOL_SOCKET,SET_REUSEADDR]";
Dave Wallace2a865272018-02-07 21:00:42 -05002688 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002689 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2690 "sid %u (0x%x)",
2691 getpid (), fd, fd, func_str, sid, sid);
2692 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_REUSEADDR,
2693 (void *) optval, &optlen);
2694 break;
2695 case SO_BROADCAST:
2696 func_str = "vppcom_session_attr[SOL_SOCKET,SET_BROADCAST]";
Dave Wallace2a865272018-02-07 21:00:42 -05002697 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002698 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): "
2699 "sid %u (0x%x)",
2700 getpid (), fd, fd, func_str, sid, sid);
2701 rv = vppcom_session_attr (sid, VPPCOM_ATTR_SET_BROADCAST,
2702 (void *) optval, &optlen);
2703 break;
2704 default:
Dave Wallace2a865272018-02-07 21:00:42 -05002705 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002706 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s(): "
2707 "sid %u (0x%x), SOL_SOCKET, "
2708 "optname %d unsupported!",
2709 getpid (), fd, fd, func_str, sid, sid, optname);
2710 break;
2711 }
2712 break;
2713 default:
2714 break;
2715 }
2716
2717 if (rv != VPPCOM_OK)
2718 {
2719 errno = -rv;
2720 rv = -1;
2721 }
2722 }
2723 else
2724 {
2725 func_str = "libc_setsockopt";
2726
Dave Wallace2a865272018-02-07 21:00:42 -05002727 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002728 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): level %d, "
2729 "optname %d, optval %p, optlen %d",
2730 getpid (), fd, fd, func_str, level, optname,
2731 optval, optlen);
2732
2733 rv = libc_setsockopt (fd, level, optname, optval, optlen);
2734 }
2735
Dave Wallace2a865272018-02-07 21:00:42 -05002736 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002737 {
2738 if (rv < 0)
2739 {
2740 int errno_val = errno;
2741 perror (func_str);
2742 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2743 "rv %d, errno = %d", getpid (), fd, fd,
2744 func_str, rv, errno_val);
2745 errno = errno_val;
2746 }
2747 else
2748 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2749 getpid (), fd, fd, rv, rv);
2750 }
2751 return rv;
2752}
2753
2754int
2755listen (int fd, int n)
2756{
2757 int rv;
2758 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002759 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002760
Dave Wallace2a865272018-02-07 21:00:42 -05002761 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002762 return -1;
2763
2764 if (sid != INVALID_SESSION_ID)
2765 {
2766 func_str = "vppcom_session_listen";
2767
Dave Wallace2a865272018-02-07 21:00:42 -05002768 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05002769 clib_warning
2770 ("LDP<%d>: fd %d (0x%x): calling %s(): sid %u (0x%x), n %d",
2771 getpid (), fd, fd, func_str, sid, sid, n);
2772
2773 rv = vppcom_session_listen (sid, n);
2774 if (rv != VPPCOM_OK)
2775 {
2776 errno = -rv;
2777 rv = -1;
2778 }
2779 }
2780 else
2781 {
2782 func_str = "libc_listen";
2783
Dave Wallace2a865272018-02-07 21:00:42 -05002784 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05002785 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): n %d",
2786 getpid (), fd, fd, func_str, n);
2787
2788 rv = libc_listen (fd, n);
2789 }
2790
Dave Wallace2a865272018-02-07 21:00:42 -05002791 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05002792 {
2793 if (rv < 0)
2794 {
2795 int errno_val = errno;
2796 perror (func_str);
2797 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2798 "rv %d, errno = %d", getpid (), fd, fd,
2799 func_str, rv, errno_val);
2800 errno = errno_val;
2801 }
2802 else
2803 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2804 getpid (), fd, fd, rv, rv);
2805 }
2806 return rv;
2807}
2808
2809static inline int
Dave Wallace2a865272018-02-07 21:00:42 -05002810ldp_accept4 (int listen_fd, __SOCKADDR_ARG addr,
2811 socklen_t * __restrict addr_len, int flags)
Dave Wallace048b1d62018-01-03 22:24:41 -05002812{
2813 int rv;
2814 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002815 u32 listen_sid = ldp_sid_from_fd (listen_fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05002816 int accept_sid;
2817
Dave Wallace2a865272018-02-07 21:00:42 -05002818 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002819 return -1;
2820
2821 if (listen_sid != INVALID_SESSION_ID)
2822 {
2823 vppcom_endpt_t ep;
2824 u8 src_addr[sizeof (struct sockaddr_in6)];
Dave Wallace8aaba562018-01-18 17:21:19 -05002825 memset (&ep, 0, sizeof (ep));
Dave Wallace048b1d62018-01-03 22:24:41 -05002826 ep.ip = src_addr;
2827
2828 func_str = "vppcom_session_accept";
2829
Dave Wallace2a865272018-02-07 21:00:42 -05002830 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05002831 clib_warning ("LDP<%d>: listen fd %d (0x%x): calling %s(): "
2832 "listen sid %u (0x%x), ep %p, flags 0x%x",
2833 getpid (), listen_fd, listen_fd, func_str,
2834 listen_sid, listen_sid, ep, flags);
2835
2836 accept_sid = vppcom_session_accept (listen_sid, &ep, flags);
2837 if (accept_sid < 0)
2838 {
2839 errno = -accept_sid;
2840 rv = -1;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002841 }
2842 else
2843 {
Dave Wallace2a865272018-02-07 21:00:42 -05002844 rv = ldp_copy_ep_to_sockaddr (addr, addr_len, &ep);
Dave Wallace048b1d62018-01-03 22:24:41 -05002845 if (rv != VPPCOM_OK)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002846 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002847 (void) vppcom_session_close ((u32) accept_sid);
2848 errno = -rv;
2849 rv = -1;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002850 }
Dave Wallace048b1d62018-01-03 22:24:41 -05002851 else
2852 {
Dave Wallace2a865272018-02-07 21:00:42 -05002853 func_str = "ldp_fd_from_sid";
2854 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05002855 clib_warning ("LDP<%d>: listen fd %d (0x%x): calling %s(): "
2856 "accept sid %u (0x%x), ep %p, flags 0x%x",
2857 getpid (), listen_fd, listen_fd,
2858 func_str, accept_sid, accept_sid, ep, flags);
Dave Wallace2a865272018-02-07 21:00:42 -05002859 rv = ldp_fd_from_sid ((u32) accept_sid);
Dave Wallace048b1d62018-01-03 22:24:41 -05002860 if (rv < 0)
2861 {
2862 (void) vppcom_session_close ((u32) accept_sid);
2863 errno = -rv;
2864 rv = -1;
2865 }
2866 }
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002867 }
2868 }
Dave Wallace048b1d62018-01-03 22:24:41 -05002869 else
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002870 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002871 func_str = "libc_accept4";
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002872
Dave Wallace2a865272018-02-07 21:00:42 -05002873 if (LDP_DEBUG > 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05002874 clib_warning ("LDP<%d>: listen fd %d (0x%x): calling %s(): "
2875 "addr %p, addr_len %p, flags 0x%x",
2876 getpid (), listen_fd, listen_fd, func_str,
2877 addr, addr_len, flags);
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002878
Dave Wallace048b1d62018-01-03 22:24:41 -05002879 rv = libc_accept4 (listen_fd, addr, addr_len, flags);
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002880 }
2881
Dave Wallace2a865272018-02-07 21:00:42 -05002882 if (LDP_DEBUG > 0)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002883 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002884 if (rv < 0)
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002885 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002886 int errno_val = errno;
2887 perror (func_str);
2888 clib_warning ("LDP<%d>: ERROR: listen fd %d (0x%x): %s() failed! "
2889 "rv %d, errno = %d", getpid (), listen_fd,
2890 listen_fd, func_str, rv, errno_val);
2891 errno = errno_val;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002892 }
Dave Wallace048b1d62018-01-03 22:24:41 -05002893 else
2894 clib_warning ("LDP<%d>: listen fd %d (0x%x): returning %d (0x%x)",
2895 getpid (), listen_fd, listen_fd, rv, rv);
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002896 }
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002897 return rv;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002898}
2899
Dave Wallace048b1d62018-01-03 22:24:41 -05002900int
2901accept4 (int fd, __SOCKADDR_ARG addr, socklen_t * __restrict addr_len,
2902 int flags)
2903{
Dave Wallace2a865272018-02-07 21:00:42 -05002904 return ldp_accept4 (fd, addr, addr_len, flags);
Dave Wallace048b1d62018-01-03 22:24:41 -05002905}
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002906
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002907int
Dave Wallace048b1d62018-01-03 22:24:41 -05002908accept (int fd, __SOCKADDR_ARG addr, socklen_t * __restrict addr_len)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002909{
Dave Wallace2a865272018-02-07 21:00:42 -05002910 return ldp_accept4 (fd, addr, addr_len, 0);
Dave Wallace048b1d62018-01-03 22:24:41 -05002911}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002912
Dave Wallace048b1d62018-01-03 22:24:41 -05002913int
2914shutdown (int fd, int how)
2915{
2916 int rv;
2917 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05002918 u32 sid = ldp_sid_from_fd (fd);
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002919
Dave Wallace2a865272018-02-07 21:00:42 -05002920 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002921 return -1;
2922
2923 if (sid != INVALID_SESSION_ID)
2924 {
Dave Wallace8aaba562018-01-18 17:21:19 -05002925 func_str = __func__;
2926
Dave Wallace048b1d62018-01-03 22:24:41 -05002927 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
2928 errno = ENOSYS;
2929 rv = -1;
2930 }
2931 else
2932 {
2933 func_str = "libc_shutdown";
2934
Dave Wallace2a865272018-02-07 21:00:42 -05002935 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002936 clib_warning ("LDP<%d>: fd %d (0x%x): calling %s(): how %d",
2937 getpid (), fd, fd, func_str, how);
2938
2939 rv = libc_shutdown (fd, how);
2940 }
2941
Dave Wallace2a865272018-02-07 21:00:42 -05002942 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002943 {
2944 if (rv < 0)
2945 {
2946 int errno_val = errno;
2947 perror (func_str);
2948 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
2949 "rv %d, errno = %d", getpid (), fd, fd,
2950 func_str, rv, errno_val);
2951 errno = errno_val;
2952 }
2953 else
2954 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
2955 getpid (), fd, fd, rv, rv);
2956 }
2957 return rv;
2958}
2959
2960int
2961epoll_create1 (int flags)
2962{
2963 const char *func_str;
2964 int rv;
2965
Dave Wallace2a865272018-02-07 21:00:42 -05002966 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05002967 return -1;
2968
2969 func_str = "vppcom_epoll_create";
2970
Dave Wallace2a865272018-02-07 21:00:42 -05002971 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05002972 clib_warning ("LDP<%d>: calling %s()", getpid (), func_str);
2973
2974 rv = vppcom_epoll_create ();
2975
2976 if (PREDICT_FALSE (rv < 0))
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002977 {
2978 errno = -rv;
Dave Wallace048b1d62018-01-03 22:24:41 -05002979 rv = -1;
shrinivasan ganapathy1d359632017-10-15 15:46:09 -07002980 }
Dave Wallace048b1d62018-01-03 22:24:41 -05002981 else
Dave Wallace2a865272018-02-07 21:00:42 -05002982 rv = ldp_fd_from_sid ((u32) rv);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002983
Dave Wallace2a865272018-02-07 21:00:42 -05002984 if (LDP_DEBUG > 1)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002985 {
Dave Wallace048b1d62018-01-03 22:24:41 -05002986 if (rv < 0)
2987 {
2988 int errno_val = errno;
2989 perror (func_str);
2990 clib_warning ("LDP<%d>: ERROR: %s() failed! "
2991 "rv %d, errno = %d",
2992 getpid (), func_str, rv, errno_val);
2993 errno = errno_val;
2994 }
2995 else
2996 clib_warning ("LDP<%d>: returning epfd %d (0x%x)", getpid (), rv, rv);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002997 }
Dave Wallace048b1d62018-01-03 22:24:41 -05002998 return rv;
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07002999}
3000
3001int
Dave Wallace048b1d62018-01-03 22:24:41 -05003002epoll_create (int size)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003003{
Dave Wallace048b1d62018-01-03 22:24:41 -05003004 return epoll_create1 (0);
3005}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003006
Dave Wallace048b1d62018-01-03 22:24:41 -05003007int
3008epoll_ctl (int epfd, int op, int fd, struct epoll_event *event)
3009{
3010 int rv;
3011 const char *func_str;
Dave Wallace2a865272018-02-07 21:00:42 -05003012 u32 vep_idx = ldp_sid_from_fd (epfd);
Dave Wallace048b1d62018-01-03 22:24:41 -05003013
Dave Wallace2a865272018-02-07 21:00:42 -05003014 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05003015 return -1;
3016
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003017 if (PREDICT_TRUE (vep_idx != INVALID_SESSION_ID))
Dave Wallace048b1d62018-01-03 22:24:41 -05003018 {
Dave Wallace2a865272018-02-07 21:00:42 -05003019 u32 sid = ldp_sid_from_fd (fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05003020
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003021 if (LDP_DEBUG > 1)
3022 clib_warning ("LDP<%d>: epfd %d (0x%x), vep_idx %d (0x%x), "
3023 "sid %d (0x%x)", getpid (), epfd, epfd,
3024 vep_idx, vep_idx, sid, sid);
3025
Dave Wallace048b1d62018-01-03 22:24:41 -05003026 if (sid != INVALID_SESSION_ID)
3027 {
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003028 func_str = "vppcom_epoll_ctl";
Dave Wallace048b1d62018-01-03 22:24:41 -05003029
Dave Wallace2a865272018-02-07 21:00:42 -05003030 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05003031 clib_warning ("LDP<%d>: epfd %d (0x%x): calling %s(): "
3032 "vep_idx %d (0x%x), op %d, sid %u (0x%x), event %p",
3033 getpid (), epfd, epfd, func_str, vep_idx, vep_idx,
3034 sid, sid, event);
3035
3036 rv = vppcom_epoll_ctl (vep_idx, op, sid, event);
3037 if (rv != VPPCOM_OK)
3038 {
3039 errno = -rv;
3040 rv = -1;
3041 }
3042 }
3043 else
3044 {
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003045 int libc_epfd;
Dave Wallace048b1d62018-01-03 22:24:41 -05003046 u32 size = sizeof (epfd);
3047
3048 func_str = "vppcom_session_attr[GET_LIBC_EPFD]";
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003049 libc_epfd = vppcom_session_attr (vep_idx,
3050 VPPCOM_ATTR_GET_LIBC_EPFD, 0, 0);
3051 if (LDP_DEBUG > 1)
3052 clib_warning ("LDP<%d>: epfd %d (0x%x), vep_idx %d (0x%x): "
3053 "%s() returned libc_epfd %d (0x%x)",
3054 getpid (), epfd, epfd, vep_idx, vep_idx,
3055 func_str, libc_epfd, libc_epfd);
3056
3057 if (!libc_epfd)
Dave Wallace048b1d62018-01-03 22:24:41 -05003058 {
3059 func_str = "libc_epoll_create1";
3060
Dave Wallace2a865272018-02-07 21:00:42 -05003061 if (LDP_DEBUG > 1)
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003062 clib_warning ("LDP<%d>: epfd %d (0x%x), vep_idx %d (0x%x): "
3063 "calling %s(): EPOLL_CLOEXEC",
3064 getpid (), epfd, epfd, vep_idx, vep_idx,
3065 func_str);
Dave Wallace048b1d62018-01-03 22:24:41 -05003066
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003067 libc_epfd = libc_epoll_create1 (EPOLL_CLOEXEC);
3068 if (libc_epfd < 0)
Dave Wallace048b1d62018-01-03 22:24:41 -05003069 {
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003070 rv = libc_epfd;
Dave Wallace048b1d62018-01-03 22:24:41 -05003071 goto done;
3072 }
3073
3074 func_str = "vppcom_session_attr[SET_LIBC_EPFD]";
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003075 if (LDP_DEBUG > 1)
3076 clib_warning ("LDP<%d>: epfd %d (0x%x): calling %s(): "
3077 "vep_idx %d (0x%x), VPPCOM_ATTR_SET_LIBC_EPFD, "
3078 "libc_epfd %d (0x%x), size %d",
3079 getpid (), epfd, epfd, func_str,
3080 vep_idx, vep_idx, libc_epfd, libc_epfd, size);
3081
Dave Wallace048b1d62018-01-03 22:24:41 -05003082 rv = vppcom_session_attr (vep_idx, VPPCOM_ATTR_SET_LIBC_EPFD,
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003083 &libc_epfd, &size);
Dave Wallace048b1d62018-01-03 22:24:41 -05003084 if (rv < 0)
3085 {
3086 errno = -rv;
3087 rv = -1;
3088 goto done;
3089 }
3090 }
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003091 else if (PREDICT_FALSE (libc_epfd < 0))
Dave Wallace048b1d62018-01-03 22:24:41 -05003092 {
3093 errno = -epfd;
3094 rv = -1;
3095 goto done;
3096 }
3097
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003098 func_str = "libc_epoll_ctl";
3099
3100 if (LDP_DEBUG > 1)
3101 clib_warning ("LDP<%d>: epfd %d (0x%x): calling %s(): "
3102 "libc_epfd %d (0x%x), op %d, "
3103 "fd %d (0x%x), event %p",
3104 getpid (), epfd, epfd, func_str,
3105 libc_epfd, libc_epfd, op, fd, fd, event);
3106
3107 rv = libc_epoll_ctl (libc_epfd, op, fd, event);
Dave Wallace048b1d62018-01-03 22:24:41 -05003108 }
3109 }
3110 else
3111 {
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003112 /* The LDP epoll_create1 always creates VCL epfd's.
3113 * The app should never have a kernel base epoll fd unless it
3114 * was acquired outside of the LD_PRELOAD process context.
3115 * In any case, if we get one, punt it to libc_epoll_ctl.
3116 */
Dave Wallace048b1d62018-01-03 22:24:41 -05003117 func_str = "libc_epoll_ctl";
3118
Dave Wallace2a865272018-02-07 21:00:42 -05003119 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05003120 clib_warning ("LDP<%d>: epfd %d (0x%x): calling %s(): "
3121 "op %d, fd %d (0x%x), event %p",
3122 getpid (), epfd, epfd, func_str, op, fd, fd, event);
3123
3124 rv = libc_epoll_ctl (epfd, op, fd, event);
3125 }
3126
3127done:
Dave Wallace2a865272018-02-07 21:00:42 -05003128 if (LDP_DEBUG > 1)
Dave Wallace048b1d62018-01-03 22:24:41 -05003129 {
3130 if (rv < 0)
3131 {
3132 int errno_val = errno;
3133 perror (func_str);
3134 clib_warning ("LDP<%d>: ERROR: fd %d (0x%x): %s() failed! "
3135 "rv %d, errno = %d", getpid (), fd, fd,
3136 func_str, rv, errno_val);
3137 errno = errno_val;
3138 }
3139 else
3140 clib_warning ("LDP<%d>: fd %d (0x%x): returning %d (0x%x)",
3141 getpid (), fd, fd, rv, rv);
3142 }
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003143 return rv;
3144}
Dave Wallace048b1d62018-01-03 22:24:41 -05003145
3146static inline int
Dave Wallace2a865272018-02-07 21:00:42 -05003147ldp_epoll_pwait (int epfd, struct epoll_event *events,
3148 int maxevents, int timeout, const sigset_t * sigmask)
Dave Wallace048b1d62018-01-03 22:24:41 -05003149{
3150 const char *func_str;
Dave Wallace8aaba562018-01-18 17:21:19 -05003151 int rv = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -05003152 double time_to_wait = (double) 0;
3153 double time_out, now = 0;
Dave Wallace2a865272018-02-07 21:00:42 -05003154 u32 vep_idx = ldp_sid_from_fd (epfd);
Dave Wallace048b1d62018-01-03 22:24:41 -05003155 int libc_epfd;
3156
Dave Wallace2a865272018-02-07 21:00:42 -05003157 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05003158 return -1;
3159
3160 if (PREDICT_FALSE (!events || (timeout < -1)))
3161 {
3162 errno = EFAULT;
3163 return -1;
3164 }
3165
3166 if (PREDICT_FALSE (vep_idx == INVALID_SESSION_ID))
3167 {
3168 clib_warning ("LDP<%d>: ERROR: epfd %d (0x%x): bad vep_idx %d (0x%x)!",
3169 getpid (), epfd, epfd, vep_idx, vep_idx);
3170 errno = EBADFD;
3171 return -1;
3172 }
3173
Florin Coras54693d22018-07-17 10:46:29 -07003174 time_to_wait = ((timeout >= 0) ? (double) timeout : 0);
Dave Wallace2a865272018-02-07 21:00:42 -05003175 time_out = clib_time_now (&ldp->clib_time) + time_to_wait;
Dave Wallace048b1d62018-01-03 22:24:41 -05003176
3177 func_str = "vppcom_session_attr[GET_LIBC_EPFD]";
3178 libc_epfd = vppcom_session_attr (vep_idx, VPPCOM_ATTR_GET_LIBC_EPFD, 0, 0);
3179 if (PREDICT_FALSE (libc_epfd < 0))
3180 {
3181 errno = -libc_epfd;
3182 rv = -1;
3183 goto done;
3184 }
3185
Dave Wallace2a865272018-02-07 21:00:42 -05003186 if (LDP_DEBUG > 2)
Dave Wallace048b1d62018-01-03 22:24:41 -05003187 clib_warning ("LDP<%d>: epfd %d (0x%x): vep_idx %d (0x%x), "
3188 "libc_epfd %d (0x%x), events %p, maxevents %d, "
Dave Wallace3ee1fe12018-02-23 01:09:11 -05003189 "timeout %d, sigmask %p: time_to_wait %.02f",
3190 getpid (), epfd, epfd, vep_idx, vep_idx,
3191 libc_epfd, libc_epfd, events, maxevents, timeout,
3192 sigmask, time_to_wait, time_out);
Dave Wallace048b1d62018-01-03 22:24:41 -05003193 do
3194 {
Dave Wallace2a865272018-02-07 21:00:42 -05003195 if (!ldp->epoll_wait_vcl)
Dave Wallace048b1d62018-01-03 22:24:41 -05003196 {
3197 func_str = "vppcom_epoll_wait";
3198
Dave Wallace2a865272018-02-07 21:00:42 -05003199 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003200 clib_warning ("LDP<%d>: epfd %d (0x%x): calling %s(): "
3201 "vep_idx %d (0x%x), events %p, maxevents %d",
3202 getpid (), epfd, epfd, func_str,
3203 vep_idx, vep_idx, events, maxevents);
3204
3205 rv = vppcom_epoll_wait (vep_idx, events, maxevents, 0);
3206 if (rv > 0)
3207 {
Dave Wallace2a865272018-02-07 21:00:42 -05003208 ldp->epoll_wait_vcl = 1;
Dave Wallace048b1d62018-01-03 22:24:41 -05003209 goto done;
3210 }
3211 else if (rv < 0)
3212 {
3213 errno = -rv;
3214 rv = -1;
3215 goto done;
3216 }
3217 }
3218 else
Dave Wallace2a865272018-02-07 21:00:42 -05003219 ldp->epoll_wait_vcl = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -05003220
3221 if (libc_epfd > 0)
3222 {
3223 func_str = "libc_epoll_pwait";
3224
Dave Wallace2a865272018-02-07 21:00:42 -05003225 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003226 clib_warning ("LDP<%d>: epfd %d (0x%x): calling %s(): "
3227 "libc_epfd %d (0x%x), events %p, "
3228 "maxevents %d, sigmask %p",
3229 getpid (), epfd, epfd, func_str,
3230 libc_epfd, libc_epfd, events, maxevents, sigmask);
3231
Keith Burns (alagalah)5368efa2018-02-07 13:20:28 -08003232 rv = libc_epoll_pwait (libc_epfd, events, maxevents, 1, sigmask);
Dave Wallace048b1d62018-01-03 22:24:41 -05003233 if (rv != 0)
3234 goto done;
3235 }
3236
3237 if (timeout != -1)
Dave Wallace2a865272018-02-07 21:00:42 -05003238 now = clib_time_now (&ldp->clib_time);
Dave Wallace048b1d62018-01-03 22:24:41 -05003239 }
3240 while (now < time_out);
3241
3242done:
Dave Wallace2a865272018-02-07 21:00:42 -05003243 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003244 {
Keith Burns (alagalah)5368efa2018-02-07 13:20:28 -08003245 if (libc_epfd > 0)
3246 epfd = libc_epfd;
Dave Wallace048b1d62018-01-03 22:24:41 -05003247 if (rv < 0)
3248 {
3249 int errno_val = errno;
3250 perror (func_str);
3251 clib_warning ("LDP<%d>: ERROR: epfd %d (0x%x): %s() failed! "
3252 "rv %d, errno = %d", getpid (), epfd, epfd,
3253 func_str, rv, errno_val);
3254 errno = errno_val;
3255 }
3256 else
3257 clib_warning ("LDP<%d>: epfd %d (0x%x): returning %d (0x%x)",
3258 getpid (), epfd, epfd, rv, rv);
3259 }
3260 return rv;
3261}
3262
3263int
3264epoll_pwait (int epfd, struct epoll_event *events,
3265 int maxevents, int timeout, const sigset_t * sigmask)
3266{
Dave Wallace2a865272018-02-07 21:00:42 -05003267 return ldp_epoll_pwait (epfd, events, maxevents, timeout, sigmask);
Dave Wallace048b1d62018-01-03 22:24:41 -05003268}
3269
3270int
3271epoll_wait (int epfd, struct epoll_event *events, int maxevents, int timeout)
3272{
Dave Wallace2a865272018-02-07 21:00:42 -05003273 return ldp_epoll_pwait (epfd, events, maxevents, timeout, NULL);
Dave Wallace048b1d62018-01-03 22:24:41 -05003274}
3275
3276int
3277poll (struct pollfd *fds, nfds_t nfds, int timeout)
3278{
3279 const char *func_str = __func__;
3280 int rv, i, n_libc_fds, n_revents;
3281 u32 sid;
3282 vcl_poll_t *vp;
3283 double wait_for_time;
3284
Dave Wallace2a865272018-02-07 21:00:42 -05003285 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003286 clib_warning ("LDP<%d>: fds %p, nfds %d, timeout %d",
3287 getpid (), fds, nfds, timeout);
3288
3289 if (timeout >= 0)
3290 wait_for_time = (f64) timeout / 1000;
3291 else
3292 wait_for_time = -1;
3293
3294 n_libc_fds = 0;
3295 for (i = 0; i < nfds; i++)
3296 {
3297 if (fds[i].fd >= 0)
3298 {
Dave Wallace2a865272018-02-07 21:00:42 -05003299 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003300 clib_warning ("LDP<%d>: fds[%d].fd %d (0x%0x), .events = 0x%x, "
3301 ".revents = 0x%x", getpid (), i, fds[i].fd,
3302 fds[i].fd, fds[i].events, fds[i].revents);
3303
Dave Wallace2a865272018-02-07 21:00:42 -05003304 sid = ldp_sid_from_fd (fds[i].fd);
Dave Wallace048b1d62018-01-03 22:24:41 -05003305 if (sid != INVALID_SESSION_ID)
3306 {
3307 fds[i].fd = -fds[i].fd;
Dave Wallace2a865272018-02-07 21:00:42 -05003308 vec_add2 (ldp->vcl_poll, vp, 1);
Dave Wallace048b1d62018-01-03 22:24:41 -05003309 vp->fds_ndx = i;
3310 vp->sid = sid;
3311 vp->events = fds[i].events;
3312#ifdef __USE_XOPEN2K
3313 if (fds[i].events & POLLRDNORM)
3314 vp->events |= POLLIN;
3315 if (fds[i].events & POLLWRNORM)
3316 vp->events |= POLLOUT;
3317#endif
3318 vp->revents = &fds[i].revents;
3319 }
3320 else
3321 n_libc_fds++;
3322 }
3323 }
3324
3325 n_revents = 0;
3326 do
3327 {
Dave Wallace2a865272018-02-07 21:00:42 -05003328 if (vec_len (ldp->vcl_poll))
Dave Wallace048b1d62018-01-03 22:24:41 -05003329 {
3330 func_str = "vppcom_poll";
3331
Dave Wallace2a865272018-02-07 21:00:42 -05003332 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003333 clib_warning ("LDP<%d>: calling %s(): "
3334 "vcl_poll %p, n_sids %u (0x%x): "
3335 "n_libc_fds %u",
Dave Wallace2a865272018-02-07 21:00:42 -05003336 getpid (), func_str, ldp->vcl_poll,
3337 vec_len (ldp->vcl_poll), vec_len (ldp->vcl_poll),
Dave Wallace048b1d62018-01-03 22:24:41 -05003338 n_libc_fds);
3339
Dave Wallace2a865272018-02-07 21:00:42 -05003340 rv = vppcom_poll (ldp->vcl_poll, vec_len (ldp->vcl_poll), 0);
Dave Wallace048b1d62018-01-03 22:24:41 -05003341 if (rv < 0)
3342 {
3343 errno = -rv;
3344 rv = -1;
3345 goto done;
3346 }
3347 else
3348 n_revents += rv;
3349 }
3350
3351 if (n_libc_fds)
3352 {
3353 func_str = "libc_poll";
3354
Dave Wallace2a865272018-02-07 21:00:42 -05003355 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003356 clib_warning ("LDP<%d>: calling %s(): fds %p, nfds %u: n_sids %u",
Dave Wallace2a865272018-02-07 21:00:42 -05003357 getpid (), fds, nfds, vec_len (ldp->vcl_poll));
Dave Wallace048b1d62018-01-03 22:24:41 -05003358
3359 rv = libc_poll (fds, nfds, 0);
3360 if (rv < 0)
3361 goto done;
3362 else
3363 n_revents += rv;
3364 }
3365
3366 if (n_revents)
3367 {
3368 rv = n_revents;
3369 goto done;
3370 }
3371 }
3372 while ((wait_for_time == -1) ||
Dave Wallace2a865272018-02-07 21:00:42 -05003373 (clib_time_now (&ldp->clib_time) < wait_for_time));
Dave Wallace048b1d62018-01-03 22:24:41 -05003374 rv = 0;
3375
3376done:
Dave Wallace2a865272018-02-07 21:00:42 -05003377 vec_foreach (vp, ldp->vcl_poll)
Dave Wallace048b1d62018-01-03 22:24:41 -05003378 {
3379 fds[vp->fds_ndx].fd = -fds[vp->fds_ndx].fd;
3380#ifdef __USE_XOPEN2K
3381 if ((fds[vp->fds_ndx].revents & POLLIN) &&
3382 (fds[vp->fds_ndx].events & POLLRDNORM))
3383 fds[vp->fds_ndx].revents |= POLLRDNORM;
3384 if ((fds[vp->fds_ndx].revents & POLLOUT) &&
3385 (fds[vp->fds_ndx].events & POLLWRNORM))
3386 fds[vp->fds_ndx].revents |= POLLWRNORM;
3387#endif
3388 }
Dave Wallace2a865272018-02-07 21:00:42 -05003389 vec_reset_length (ldp->vcl_poll);
Dave Wallace048b1d62018-01-03 22:24:41 -05003390
Dave Wallace2a865272018-02-07 21:00:42 -05003391 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003392 {
3393 if (rv < 0)
3394 {
3395 int errno_val = errno;
3396 perror (func_str);
3397 clib_warning ("LDP<%d>: ERROR: %s() failed! "
3398 "rv %d, errno = %d", getpid (),
3399 func_str, rv, errno_val);
3400 errno = errno_val;
3401 }
3402 else
3403 {
3404 clib_warning ("LDP<%d>: returning %d (0x%x): n_sids %u, "
3405 "n_libc_fds %d", getpid (), rv, rv,
Dave Wallace2a865272018-02-07 21:00:42 -05003406 vec_len (ldp->vcl_poll), n_libc_fds);
Dave Wallace048b1d62018-01-03 22:24:41 -05003407
3408 for (i = 0; i < nfds; i++)
3409 {
3410 if (fds[i].fd >= 0)
3411 {
Dave Wallace2a865272018-02-07 21:00:42 -05003412 if (LDP_DEBUG > 3)
Dave Wallace048b1d62018-01-03 22:24:41 -05003413 clib_warning ("LDP<%d>: fds[%d].fd %d (0x%0x), "
3414 ".events = 0x%x, .revents = 0x%x",
3415 getpid (), i, fds[i].fd, fds[i].fd,
3416 fds[i].events, fds[i].revents);
3417 }
3418 }
3419 }
3420 }
3421
3422 return rv;
3423}
3424
3425#ifdef USE_GNU
3426int
3427ppoll (struct pollfd *fds, nfds_t nfds,
3428 const struct timespec *timeout, const sigset_t * sigmask)
3429{
Dave Wallace2a865272018-02-07 21:00:42 -05003430 if ((errno = -ldp_init ()))
Dave Wallace048b1d62018-01-03 22:24:41 -05003431 return -1;
3432
3433 clib_warning ("LDP<%d>: LDP-TBD", getpid ());
3434 errno = ENOSYS;
3435
3436
3437 return -1;
3438}
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003439#endif
3440
Dave Wallace2a865272018-02-07 21:00:42 -05003441void CONSTRUCTOR_ATTRIBUTE ldp_constructor (void);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003442
Dave Wallace2a865272018-02-07 21:00:42 -05003443void DESTRUCTOR_ATTRIBUTE ldp_destructor (void);
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003444
Dave Wallace048b1d62018-01-03 22:24:41 -05003445/*
3446 * This function is called when the library is loaded
3447 */
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003448void
Dave Wallace2a865272018-02-07 21:00:42 -05003449ldp_constructor (void)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003450{
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003451 swrap_constructor ();
Dave Wallace2a865272018-02-07 21:00:42 -05003452 if (ldp_init () != 0)
3453 fprintf (stderr, "\nLDP<%d>: ERROR: ldp_constructor: failed!\n",
Dave Wallace048b1d62018-01-03 22:24:41 -05003454 getpid ());
Dave Wallace69d01192018-02-22 16:22:09 -05003455 else if (LDP_DEBUG > 0)
Dave Wallace2a865272018-02-07 21:00:42 -05003456 clib_warning ("LDP<%d>: LDP constructor: done!\n", getpid ());
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003457}
3458
3459/*
3460 * This function is called when the library is unloaded
3461 */
3462void
Dave Wallace2a865272018-02-07 21:00:42 -05003463ldp_destructor (void)
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003464{
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003465 swrap_destructor ();
Dave Wallace2a865272018-02-07 21:00:42 -05003466 if (ldp->init)
Dave Wallace048b1d62018-01-03 22:24:41 -05003467 {
3468 vppcom_app_destroy ();
Dave Wallace2a865272018-02-07 21:00:42 -05003469 ldp->init = 0;
Dave Wallace048b1d62018-01-03 22:24:41 -05003470 }
3471
3472 /* Don't use clib_warning() here because that calls writev()
Dave Wallace2a865272018-02-07 21:00:42 -05003473 * which will call ldp_init().
Dave Wallace048b1d62018-01-03 22:24:41 -05003474 */
Dave Wallace69d01192018-02-22 16:22:09 -05003475 if (LDP_DEBUG > 0)
3476 printf ("%s:%d: LDP<%d>: LDP destructor: done!\n",
3477 __func__, __LINE__, getpid ());
Keith Burns (alagalah)b327c2b2017-10-09 08:52:59 -07003478}
3479
3480
3481/*
3482 * fd.io coding-style-patch-verification: ON
3483 *
3484 * Local Variables:
3485 * eval: (c-set-style "gnu")
3486 * End:
3487 */