Coverage Report

Created: 2025-07-18 07:06

/src/libvncserver/src/common/sockets.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * common/sockets.c - Common internal socket functions used by both
3
 * libvncclient and libvncserver.
4
 */
5
6
/*
7
 *  Copyright (C) 2022 Christian Beier
8
 *
9
 *  This is free software; you can redistribute it and/or modify
10
 *  it under the terms of the GNU General Public License as published by
11
 *  the Free Software Foundation; either version 2 of the License, or
12
 *  (at your option) any later version.
13
 *
14
 *  This software is distributed in the hope that it will be useful,
15
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
 *  GNU General Public License for more details.
18
 *
19
 *  You should have received a copy of the GNU General Public License
20
 *  along with this software; if not, write to the Free Software
21
 *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307,
22
 *  USA.
23
 */
24
25
#include <errno.h>
26
#include <fcntl.h>
27
#include <string.h>
28
29
#include "sockets.h"
30
31
32
rfbBool sock_set_nonblocking(rfbSocket sock, rfbBool non_blocking, void (*log)(const char *format, ...))
33
0
{
34
#ifdef WIN32
35
  unsigned long non_blocking_ulong = non_blocking;
36
  if(ioctlsocket(sock, FIONBIO, &non_blocking_ulong) == SOCKET_ERROR) {
37
    errno=WSAGetLastError();
38
#else
39
0
  int flags = fcntl(sock, F_GETFL);
40
0
  int new_flags;
41
0
  if(non_blocking)
42
0
      new_flags = flags | O_NONBLOCK;
43
0
  else
44
0
      new_flags = flags & ~O_NONBLOCK;
45
0
  if(flags < 0 || fcntl(sock, F_SETFL, new_flags) < 0) {
46
0
#endif
47
0
    log("Setting socket to %sblocking mode failed: %s\n", non_blocking ? "non-" : "", strerror(errno));
48
0
    return FALSE;
49
0
  }
50
0
  return TRUE;
51
0
}
52
53
54
rfbBool sock_wait_for_connected(int socket, unsigned int timeout_seconds)
55
0
{
56
0
  fd_set writefds;
57
0
  fd_set exceptfds;
58
0
  struct timeval timeout;
59
60
0
  timeout.tv_sec=timeout_seconds;
61
0
  timeout.tv_usec=0;
62
63
0
  if(socket == RFB_INVALID_SOCKET) {
64
0
      errno = EBADF;
65
0
      return FALSE;
66
0
  }
67
68
0
  FD_ZERO(&writefds);
69
0
  FD_SET(socket, &writefds);
70
0
  FD_ZERO(&exceptfds);
71
0
  FD_SET(socket, &exceptfds);
72
0
  if (select(socket+1, NULL, &writefds, &exceptfds, &timeout)==1) {
73
#ifdef WIN32
74
    if (FD_ISSET(socket, &exceptfds))
75
      return FALSE;
76
#else
77
0
    int so_error;
78
0
    socklen_t len = sizeof so_error;
79
0
    getsockopt(socket, SOL_SOCKET, SO_ERROR, &so_error, &len);
80
0
    if (so_error!=0)
81
0
      return FALSE;
82
0
#endif
83
0
    return TRUE;
84
0
  }
85
86
0
  return FALSE;
87
0
}
88
89
90