Rizin
unix-like reverse engineering framework and cli tools
pipe.c File Reference
#include "uv.h"
#include "internal.h"
#include <assert.h>
#include <errno.h>
#include <string.h>
#include <sys/un.h>
#include <unistd.h>
#include <stdlib.h>

Go to the source code of this file.

Functions

int uv_pipe_init (uv_loop_t *loop, uv_pipe_t *handle, int ipc)
 
int uv_pipe_bind (uv_pipe_t *handle, const char *name)
 
int uv_pipe_listen (uv_pipe_t *handle, int backlog, uv_connection_cb cb)
 
void uv__pipe_close (uv_pipe_t *handle)
 
int uv_pipe_open (uv_pipe_t *handle, uv_file fd)
 
void uv_pipe_connect (uv_connect_t *req, uv_pipe_t *handle, const char *name, uv_connect_cb cb)
 
static int uv__pipe_getsockpeername (const uv_pipe_t *handle, uv__peersockfunc func, char *buffer, size_t *size)
 
int uv_pipe_getsockname (const uv_pipe_t *handle, char *buffer, size_t *size)
 
int uv_pipe_getpeername (const uv_pipe_t *handle, char *buffer, size_t *size)
 
void uv_pipe_pending_instances (uv_pipe_t *handle, int count)
 
int uv_pipe_pending_count (uv_pipe_t *handle)
 
uv_handle_type uv_pipe_pending_type (uv_pipe_t *handle)
 
int uv_pipe_chmod (uv_pipe_t *handle, int mode)
 

Function Documentation

◆ uv__pipe_close()

void uv__pipe_close ( uv_pipe_t handle)

Definition at line 120 of file pipe.c.

120  {
121  if (handle->pipe_fname) {
122  /*
123  * Unlink the file system entity before closing the file descriptor.
124  * Doing it the other way around introduces a race where our process
125  * unlinks a socket with the same name that's just been created by
126  * another thread or process.
127  */
128  unlink(handle->pipe_fname);
129  uv__free((void*)handle->pipe_fname);
130  handle->pipe_fname = NULL;
131  }
132 
134 }
static mcore_handle handle
Definition: asm_mcore.c:8
#define NULL
Definition: cris-opc.c:27
static static fork const void static count static fd const char static mode unlink
Definition: sflib.h:41
void uv__stream_close(uv_stream_t *handle)
Definition: stream.c:1633
void uv__free(void *ptr)
Definition: uv-common.c:81

References handle, NULL, unlink, uv__free(), and uv__stream_close().

Referenced by uv_close().

◆ uv__pipe_getsockpeername()

static int uv__pipe_getsockpeername ( const uv_pipe_t handle,
uv__peersockfunc  func,
char *  buffer,
size_t size 
)
static

Definition at line 240 of file pipe.c.

243  {
244  struct sockaddr_un sa;
246  int err;
247 
248  addrlen = sizeof(sa);
249  memset(&sa, 0, addrlen);
251  func,
252  (struct sockaddr*) &sa,
253  (int*) &addrlen);
254  if (err < 0) {
255  *size = 0;
256  return err;
257  }
258 
259 #if defined(__linux__)
260  if (sa.sun_path[0] == 0)
261  /* Linux abstract namespace */
262  addrlen -= offsetof(struct sockaddr_un, sun_path);
263  else
264 #endif
265  addrlen = strlen(sa.sun_path);
266 
267 
268  if ((size_t)addrlen >= *size) {
269  *size = addrlen + 1;
270  return UV_ENOBUFS;
271  }
272 
273  memcpy(buffer, sa.sun_path, addrlen);
274  *size = addrlen;
275 
276  /* only null-terminate if it's not an abstract socket */
277  if (buffer[0] != '\0')
278  buffer[addrlen] = '\0';
279 
280  return 0;
281 }
static bool err
Definition: armass.c:435
voidpf void uLong size
Definition: ioapi.h:138
#define offsetof(type, member)
return memset(p, 0, total)
memcpy(mem, inblock.get(), min(CONTAINING_RECORD(inblock.get(), MEMBLOCK, data) ->size, size))
static const void static count static fd struct stat static buf struct pollfd unsigned static timeout void static offset void static length char static len const struct iovec static count unsigned long static filedes static sched_yield static flags static oldfd static pause unsigned static seconds static protocol struct sockaddr addrlen
Definition: sflib.h:75
unsigned int socklen_t
Definition: sftypes.h:219
Definition: buffer.h:15
char sun_path[108]
Definition: sftypes.h:356
int uv__getsockpeername(const uv_handle_t *handle, uv__peersockfunc func, struct sockaddr *name, int *namelen)
Definition: core.c:1490

References addrlen, err, handle, memcpy(), memset(), offsetof, sockaddr_un::sun_path, and uv__getsockpeername().

Referenced by uv_pipe_getpeername(), and uv_pipe_getsockname().

◆ uv_pipe_bind()

int uv_pipe_bind ( uv_pipe_t handle,
const char *  name 
)

Definition at line 43 of file pipe.c.

43  {
44  struct sockaddr_un saddr;
45  const char* pipe_fname;
46  int sockfd;
47  int err;
48 
49  pipe_fname = NULL;
50 
51  /* Already bound? */
52  if (uv__stream_fd(handle) >= 0)
53  return UV_EINVAL;
54 
55  /* Make a copy of the file name, it outlives this function's scope. */
56  pipe_fname = uv__strdup(name);
57  if (pipe_fname == NULL)
58  return UV_ENOMEM;
59 
60  /* We've got a copy, don't touch the original any more. */
61  name = NULL;
62 
64  if (err < 0)
65  goto err_socket;
66  sockfd = err;
67 
68  memset(&saddr, 0, sizeof saddr);
69  uv__strscpy(saddr.sun_path, pipe_fname, sizeof(saddr.sun_path));
70  saddr.sun_family = AF_UNIX;
71 
72  if (bind(sockfd, (struct sockaddr*)&saddr, sizeof saddr)) {
73  err = UV__ERR(errno);
74  /* Convert ENOENT to EACCES for compatibility with Windows. */
75  if (err == UV_ENOENT)
76  err = UV_EACCES;
77 
79  goto err_socket;
80  }
81 
82  /* Success. */
83  handle->flags |= UV_HANDLE_BOUND;
84  handle->pipe_fname = pipe_fname; /* Is a strdup'ed copy. */
85  handle->io_watcher.fd = sockfd;
86  return 0;
87 
88 err_socket:
89  uv__free((void*)pipe_fname);
90  return err;
91 }
#define UV__ERR(x)
Definition: errno.h:29
static sockfd
Definition: sfsocketcall.h:114
static bind
Definition: sfsocketcall.h:114
#define AF_UNIX
Definition: sftypes.h:285
@ SOCK_STREAM
Definition: sftypes.h:224
ssize_t uv__strscpy(char *d, const char *s, size_t n)
Definition: strscpy.c:25
Definition: z80asm.h:102
int uv__socket(int domain, int type, int protocol)
Definition: core.c:436
int uv__close(int fd)
Definition: core.c:569
#define uv__stream_fd(handle)
Definition: internal.h:282
char * uv__strdup(const char *s)
Definition: uv-common.c:55
@ UV_HANDLE_BOUND
Definition: uv-common.h:91

◆ uv_pipe_chmod()

int uv_pipe_chmod ( uv_pipe_t handle,
int  mode 
)

Definition at line 326 of file pipe.c.

326  {
327  unsigned desired_mode;
328  struct stat pipe_stat;
329  char* name_buffer;
330  size_t name_len;
331  int r;
332 
333  if (handle == NULL || uv__stream_fd(handle) == -1)
334  return UV_EBADF;
335 
336  if (mode != UV_READABLE &&
337  mode != UV_WRITABLE &&
339  return UV_EINVAL;
340 
341  /* Unfortunately fchmod does not work on all platforms, we will use chmod. */
342  name_len = 0;
343  r = uv_pipe_getsockname(handle, NULL, &name_len);
344  if (r != UV_ENOBUFS)
345  return r;
346 
347  name_buffer = uv__malloc(name_len);
348  if (name_buffer == NULL)
349  return UV_ENOMEM;
350 
351  r = uv_pipe_getsockname(handle, name_buffer, &name_len);
352  if (r != 0) {
353  uv__free(name_buffer);
354  return r;
355  }
356 
357  /* stat must be used as fstat has a bug on Darwin */
358  if (stat(name_buffer, &pipe_stat) == -1) {
359  uv__free(name_buffer);
360  return -errno;
361  }
362 
363  desired_mode = 0;
364  if (mode & UV_READABLE)
365  desired_mode |= S_IRUSR | S_IRGRP | S_IROTH;
366  if (mode & UV_WRITABLE)
367  desired_mode |= S_IWUSR | S_IWGRP | S_IWOTH;
368 
369  /* Exit early if pipe already has desired mode. */
370  if ((pipe_stat.st_mode & desired_mode) == desired_mode) {
371  uv__free(name_buffer);
372  return 0;
373  }
374 
375  pipe_stat.st_mode |= desired_mode;
376 
377  r = chmod(name_buffer, pipe_stat.st_mode);
378  uv__free(name_buffer);
379 
380  return r != -1 ? 0 : UV__ERR(errno);
381 }
#define r
Definition: crypto_rc6.c:12
static static fork const void static count static fd const char const char static newpath const char static path chmod
Definition: sflib.h:35
const char int mode
Definition: ioapi.h:137
static stat
Definition: sflib.h:131
Definition: sftypes.h:80
int uv_pipe_getsockname(const uv_pipe_t *handle, char *buffer, size_t *size)
Definition: pipe.c:284
void * uv__malloc(size_t size)
Definition: uv-common.c:75
@ UV_WRITABLE
Definition: uv.h:801
@ UV_READABLE
Definition: uv.h:800

◆ uv_pipe_connect()

void uv_pipe_connect ( uv_connect_t req,
uv_pipe_t handle,
const char *  name,
uv_connect_cb  cb 
)

Definition at line 173 of file pipe.c.

176  {
177  struct sockaddr_un saddr;
178  int new_sock;
179  int err;
180  int r;
181 
182  new_sock = (uv__stream_fd(handle) == -1);
183 
184  if (new_sock) {
186  if (err < 0)
187  goto out;
188  handle->io_watcher.fd = err;
189  }
190 
191  memset(&saddr, 0, sizeof saddr);
192  uv__strscpy(saddr.sun_path, name, sizeof(saddr.sun_path));
193  saddr.sun_family = AF_UNIX;
194 
195  do {
196  r = connect(uv__stream_fd(handle),
197  (struct sockaddr*)&saddr, sizeof saddr);
198  }
199  while (r == -1 && errno == EINTR);
200 
201  if (r == -1 && errno != EINPROGRESS) {
202  err = UV__ERR(errno);
203 #if defined(__CYGWIN__) || defined(__MSYS__)
204  /* EBADF is supposed to mean that the socket fd is bad, but
205  Cygwin reports EBADF instead of ENOTSOCK when the file is
206  not a socket. We do not expect to see a bad fd here
207  (e.g. due to new_sock), so translate the error. */
208  if (err == UV_EBADF)
209  err = UV_ENOTSOCK;
210 #endif
211  goto out;
212  }
213 
214  err = 0;
215  if (new_sock) {
219  }
220 
221  if (err == 0)
222  uv__io_start(handle->loop, &handle->io_watcher, POLLOUT);
223 
224 out:
225  handle->delayed_error = err;
226  handle->connect_req = req;
227 
228  uv__req_init(handle->loop, req, UV_CONNECT);
229  req->handle = (uv_stream_t*)handle;
230  req->cb = cb;
231  QUEUE_INIT(&req->queue);
232 
233  /* Force callback to run on next tick in case of error. */
234  if (err)
235  uv__io_feed(handle->loop, &handle->io_watcher);
236 
237 }
const lzma_allocator const uint8_t size_t uint8_t * out
Definition: block.h:528
static static sync static getppid static getegid const char static filename char static len const char char static bufsiz static mask static vfork const void static prot static getpgrp const char static swapflags static arg static fd static protocol static who struct sockaddr static addrlen static backlog struct timeval struct timezone static tz const struct iovec static count static mode const void const struct sockaddr static tolen const char static pathname void static offset struct stat static buf void long static basep static whence static length const void static len static semflg const void static shmflg const struct timespec req
Definition: sflib.h:128
#define QUEUE_INIT(q)
Definition: queue.h:45
#define EINTR
Definition: sftypes.h:114
#define EINPROGRESS
Definition: sftypes.h:175
void uv__io_start(uv_loop_t *loop, uv__io_t *w, unsigned int events)
Definition: core.c:882
void uv__io_feed(uv_loop_t *loop, uv__io_t *w)
Definition: core.c:952
int uv__stream_open(uv_stream_t *, int fd, int flags)
Definition: stream.c:406
@ UV_HANDLE_WRITABLE
Definition: uv-common.h:93
@ UV_HANDLE_READABLE
Definition: uv-common.h:92
#define uv__req_init(loop, req, typ)
Definition: uv-common.h:329
static const char * cb[]
Definition: z80_tab.h:176

◆ uv_pipe_getpeername()

int uv_pipe_getpeername ( const uv_pipe_t handle,
char *  buffer,
size_t size 
)

Definition at line 289 of file pipe.c.

289  {
290  return uv__pipe_getsockpeername(handle, getpeername, buffer, size);
291 }
static int uv__pipe_getsockpeername(const uv_pipe_t *handle, uv__peersockfunc func, char *buffer, size_t *size)
Definition: pipe.c:240

◆ uv_pipe_getsockname()

int uv_pipe_getsockname ( const uv_pipe_t handle,
char *  buffer,
size_t size 
)

Definition at line 284 of file pipe.c.

284  {
285  return uv__pipe_getsockpeername(handle, getsockname, buffer, size);
286 }

Referenced by uv_pipe_chmod().

◆ uv_pipe_init()

int uv_pipe_init ( uv_loop_t loop,
uv_pipe_t handle,
int  ipc 
)

Definition at line 33 of file pipe.c.

33  {
34  uv__stream_init(loop, (uv_stream_t*)handle, UV_NAMED_PIPE);
35  handle->shutdown_req = NULL;
36  handle->connect_req = NULL;
37  handle->pipe_fname = NULL;
38  handle->ipc = ipc;
39  return 0;
40 }
uv_loop_t * loop
Definition: main.c:7
void uv__stream_init(uv_loop_t *loop, uv_stream_t *stream, uv_handle_type type)
Definition: stream.c:85

◆ uv_pipe_listen()

int uv_pipe_listen ( uv_pipe_t handle,
int  backlog,
uv_connection_cb  cb 
)

Definition at line 94 of file pipe.c.

94  {
95  if (uv__stream_fd(handle) == -1)
96  return UV_EINVAL;
97 
98  if (handle->ipc)
99  return UV_EINVAL;
100 
101 #if defined(__MVS__) || defined(__PASE__)
102  /* On zOS, backlog=0 has undefined behaviour */
103  /* On IBMi PASE, backlog=0 leads to "Connection refused" error */
104  if (backlog == 0)
105  backlog = 1;
106  else if (backlog < 0)
107  backlog = SOMAXCONN;
108 #endif
109 
110  if (listen(uv__stream_fd(handle), backlog))
111  return UV__ERR(errno);
112 
113  handle->connection_cb = cb;
114  handle->io_watcher.cb = uv__server_io;
115  uv__io_start(handle->loop, &handle->io_watcher, POLLIN);
116  return 0;
117 }
static struct sockaddr static addrlen listen
Definition: sfsocketcall.h:116
void uv__server_io(uv_loop_t *loop, uv__io_t *w, unsigned int events)
Definition: stream.c:528

◆ uv_pipe_open()

int uv_pipe_open ( uv_pipe_t handle,
uv_file  fd 
)

Definition at line 137 of file pipe.c.

137  {
138  int flags;
139  int mode;
140  int err;
141  flags = 0;
142 
143  if (uv__fd_exists(handle->loop, fd))
144  return UV_EEXIST;
145 
146  do
147  mode = fcntl(fd, F_GETFL);
148  while (mode == -1 && errno == EINTR);
149 
150  if (mode == -1)
151  return UV__ERR(errno); /* according to docs, must be EBADF */
152 
153  err = uv__nonblock(fd, 1);
154  if (err)
155  return err;
156 
157 #if defined(__APPLE__)
158  err = uv__stream_try_select((uv_stream_t*) handle, &fd);
159  if (err)
160  return err;
161 #endif /* defined(__APPLE__) */
162 
163  mode &= O_ACCMODE;
164  if (mode != O_WRONLY)
166  if (mode != O_RDONLY)
168 
170 }
static static sync static getppid static getegid const char static filename char static len const char char static bufsiz static mask static vfork const void static prot static getpgrp const char static swapflags fcntl
Definition: sflib.h:79
static struct sockaddr static addrlen static backlog const void static flags void flags
Definition: sfsocketcall.h:123
#define F_GETFL
Definition: sftypes.h:506
#define O_WRONLY
Definition: sftypes.h:487
#define O_ACCMODE
Definition: sftypes.h:485
#define O_RDONLY
Definition: sftypes.h:486
int uv__fd_exists(uv_loop_t *loop, int fd)
Definition: core.c:965
#define uv__nonblock
Definition: internal.h:170
static const z80_opcode fd[]
Definition: z80_tab.h:997

◆ uv_pipe_pending_count()

int uv_pipe_pending_count ( uv_pipe_t handle)

Definition at line 298 of file pipe.c.

298  {
299  uv__stream_queued_fds_t* queued_fds;
300 
301  if (!handle->ipc)
302  return 0;
303 
304  if (handle->accepted_fd == -1)
305  return 0;
306 
307  if (handle->queued_fds == NULL)
308  return 1;
309 
310  queued_fds = handle->queued_fds;
311  return queued_fds->offset + 1;
312 }
unsigned int offset
Definition: internal.h:153

◆ uv_pipe_pending_instances()

void uv_pipe_pending_instances ( uv_pipe_t handle,
int  count 
)

Definition at line 294 of file pipe.c.

294  {
295 }

◆ uv_pipe_pending_type()

uv_handle_type uv_pipe_pending_type ( uv_pipe_t handle)

Definition at line 315 of file pipe.c.

315  {
316  if (!handle->ipc)
317  return UV_UNKNOWN_HANDLE;
318 
319  if (handle->accepted_fd == -1)
320  return UV_UNKNOWN_HANDLE;
321  else
322  return uv__handle_type(handle->accepted_fd);
323 }
uv_handle_type uv__handle_type(int fd)
Definition: stream.c:958
@ UV_UNKNOWN_HANDLE
Definition: uv.h:190