Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Add event handling for Windows
Only handles sockets for now, which *can* be done through select(). But
now we can add the tun device handling into the loop...

Signed-off-by: David Woodhouse <David.Woodhouse@intel.com>
  • Loading branch information
David Woodhouse authored and David Woodhouse committed Feb 11, 2014
1 parent 67c6cf5 commit 1edb49e
Show file tree
Hide file tree
Showing 3 changed files with 52 additions and 0 deletions.
8 changes: 8 additions & 0 deletions library.c
Expand Up @@ -134,6 +134,14 @@ void openconnect_vpninfo_free(struct openconnect_info *vpninfo)
close(vpninfo->cmd_fd);
close(vpninfo->cmd_fd_write);
}
#ifdef _WIN32
if (vpninfo->cmd_event)
CloseHandle(vpninfo->cmd_event);
if (vpninfo->ssl_event)
CloseHandle(vpninfo->ssl_event);
if (vpninfo->dtls_event)
CloseHandle(vpninfo->dtls_event);
#endif
free(vpninfo->peer_addr);
free_optlist(vpninfo->cookies);
free_optlist(vpninfo->cstp_options);
Expand Down
26 changes: 26 additions & 0 deletions mainloop.c
Expand Up @@ -69,8 +69,13 @@ int openconnect_mainloop(struct openconnect_info *vpninfo,
while (!vpninfo->quit_reason) {
int did_work = 0;
int timeout = INT_MAX;
#ifdef _WIN32
HANDLE events[4];
int nr_events = 0;
#else
struct timeval tv;
fd_set rfds, wfds, efds;
#endif

#ifdef HAVE_DTLS
if (vpninfo->dtls_state != DTLS_DISABLED) {
Expand Down Expand Up @@ -118,6 +123,26 @@ int openconnect_mainloop(struct openconnect_info *vpninfo,

vpn_progress(vpninfo, PRG_TRACE,
_("No work to do; sleeping for %d ms...\n"), timeout);

#ifdef _WIN32
if (vpninfo->dtls_monitored) {
WSAEventSelect(vpninfo->dtls_fd, vpninfo->dtls_event, vpninfo->dtls_monitored);
events[nr_events++] = vpninfo->dtls_event;
}
if (vpninfo->ssl_monitored) {
WSAEventSelect(vpninfo->ssl_fd, vpninfo->ssl_event, vpninfo->ssl_monitored);
events[nr_events++] = vpninfo->ssl_event;
}
if (vpninfo->cmd_monitored) {
WSAEventSelect(vpninfo->cmd_fd, vpninfo->cmd_event, vpninfo->cmd_monitored);
events[nr_events++] = vpninfo->cmd_event;
}
if (WaitForMultipleObjects(nr_events, events, FALSE, timeout) == WAIT_FAILED) {
vpn_progress(vpninfo, PRG_ERR,
_("WaitForMultipleObjects failed: %lx\n"),
GetLastError());
}
#else
memcpy(&rfds, &vpninfo->_select_rfds, sizeof(rfds));
memcpy(&wfds, &vpninfo->_select_wfds, sizeof(wfds));
memcpy(&efds, &vpninfo->_select_efds, sizeof(efds));
Expand All @@ -126,6 +151,7 @@ int openconnect_mainloop(struct openconnect_info *vpninfo,
tv.tv_usec = (timeout % 1000) * 1000;

select(vpninfo->_select_nfds, &rfds, &wfds, &efds, &tv);
#endif
}

cstp_bye(vpninfo, vpninfo->quit_reason);
Expand Down
18 changes: 18 additions & 0 deletions openconnect-internal.h
Expand Up @@ -272,10 +272,15 @@ struct openconnect_info {

struct oc_ip_info ip_info;

#ifdef _WIN32
long dtls_monitored, ssl_monitored, cmd_monitored, tun_monitored;
HANDLE dtls_event, ssl_event, cmd_event, tun_event;
#else
int _select_nfds;
fd_set _select_rfds;
fd_set _select_wfds;
fd_set _select_efds;
#endif

#ifdef __sun__
int ip_fd;
Expand Down Expand Up @@ -319,6 +324,18 @@ struct openconnect_info {
openconnect_protect_socket_vfn protect_socket;
};

#ifdef _WIN32
#define monitor_read_fd(_v, _n) _v->_n##_monitored |= FD_READ
#define monitor_write_fd(_v, _n) _v->_n##_monitored |= FD_WRITE
#define monitor_except_fd(_v, _n) _v->_n##_monitored |= FD_CLOSE
#define unmonitor_read_fd(_v, _n) _v->_n##_monitored &= ~FD_READ
#define unmonitor_write_fd(_v, _n) _v->_n##_monitored &= ~FD_WRITE
#define unmonitor_except_fd(_v, _n) _v->_n##_monitored &= ~FD_CLOSE

#define monitor_fd_new(_v, _n) do { if (!_v->_n##_event) _v->_n##_event = CreateEvent(NULL, FALSE, FALSE, NULL); } while (0)
#define read_fd_monitored(_v, _n) (_v->_n##_monitored & FD_READ)

#else
#define monitor_read_fd(_v, _n) FD_SET(_v-> _n##_fd, &vpninfo->_select_rfds)
#define unmonitor_read_fd(_v, _n) FD_CLR(_v-> _n##_fd, &vpninfo->_select_rfds)
#define monitor_write_fd(_v, _n) FD_SET(_v-> _n##_fd, &vpninfo->_select_wfds)
Expand All @@ -332,6 +349,7 @@ struct openconnect_info {
} while (0)

#define read_fd_monitored(_v, _n) FD_ISSET(_v->_n##_fd, &_v->_select_rfds)
#endif

#if (defined(DTLS_OPENSSL) && defined(SSL_OP_CISCO_ANYCONNECT)) || \
(defined(DTLS_GNUTLS) && defined(HAVE_GNUTLS_SESSION_SET_PREMASTER))
Expand Down

0 comments on commit 1edb49e

Please sign in to comment.