FS-9934: [mod_redis] fix segfault on windows on close or connect failure

This commit is contained in:
Mike Jerris 2017-01-10 18:17:09 -06:00
parent 9b9408bc9e
commit 1ec5e87468
1 changed files with 13 additions and 6 deletions

View File

@ -38,6 +38,8 @@
#if _MSC_VER < 1900 #if _MSC_VER < 1900
#define snprintf _snprintf #define snprintf _snprintf
#endif #endif
typedef SOCKET credis_socket_t;
#define CREDIS_SOCK_INVALID INVALID_SOCKET
#else #else
#include <unistd.h> #include <unistd.h>
#include <sys/select.h> #include <sys/select.h>
@ -49,6 +51,8 @@
#include <netinet/in.h> #include <netinet/in.h>
#endif #endif
#include <arpa/inet.h> #include <arpa/inet.h>
typedef int credis_socket_t;
#define CREDIS_SOCK_INVALID -1
#endif #endif
#include <fcntl.h> #include <fcntl.h>
#include <errno.h> #include <errno.h>
@ -558,14 +562,19 @@ static int cr_sendfandreceive(REDIS rhnd, char recvtype, const char *format, ...
void credis_close(REDIS rhnd) void credis_close(REDIS rhnd)
{ {
if (rhnd->fd > 0) if (rhnd->fd != CREDIS_SOCK_INVALID)
#ifdef _MSC_VER
closesocket(rhnd->fd);
#else
close(rhnd->fd); close(rhnd->fd);
#endif
cr_delete(rhnd); cr_delete(rhnd);
} }
REDIS credis_connect(const char *host, int port, int timeout) REDIS credis_connect(const char *host, int port, int timeout)
{ {
int fd, yes = 1; credis_socket_t fd = CREDIS_SOCK_INVALID;
int yes = 1;
struct sockaddr_in sa; struct sockaddr_in sa;
REDIS rhnd; REDIS rhnd;
int valid = 0; int valid = 0;
@ -578,7 +587,7 @@ REDIS credis_connect(const char *host, int port, int timeout)
if (port == 0) if (port == 0)
port = 6379; port = 6379;
if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == -1 || if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == CREDIS_SOCK_INVALID ||
setsockopt(fd, SOL_SOCKET, SO_KEEPALIVE, &yes, sizeof(yes)) == -1 || setsockopt(fd, SOL_SOCKET, SO_KEEPALIVE, &yes, sizeof(yes)) == -1 ||
setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &yes, sizeof(yes)) == -1) setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &yes, sizeof(yes)) == -1)
goto error; goto error;
@ -612,9 +621,7 @@ REDIS credis_connect(const char *host, int port, int timeout)
return rhnd; return rhnd;
error: error:
if (fd >= 0) credis_close(rhnd);
close(fd);
cr_delete(rhnd);
return NULL; return NULL;
} }