Merge pull request #1027 from dermojo/mingw
Support for Windows / MinGW
This commit is contained in:
commit
56ee3d4820
|
@ -27,7 +27,9 @@
|
|||
|
||||
#include "nghttp2_config.h"
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <sys/uio.h>
|
||||
#endif // !_WIN32
|
||||
|
||||
#include <cassert>
|
||||
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include "asio_common.h"
|
||||
|
||||
#include <memory>
|
||||
#include <fcntl.h>
|
||||
|
||||
#include "util.h"
|
||||
#include "template.h"
|
||||
|
|
|
@ -28,7 +28,15 @@
|
|||
#include "nghttp2_config.h"
|
||||
|
||||
#include <limits.h>
|
||||
#ifdef _WIN32
|
||||
/* Structure for scatter/gather I/O. */
|
||||
struct iovec {
|
||||
void *iov_base; /* Pointer to data. */
|
||||
size_t iov_len; /* Length of data. */
|
||||
};
|
||||
#else
|
||||
#include <sys/uio.h>
|
||||
#endif // _WIN32
|
||||
|
||||
#include <cassert>
|
||||
#include <cstring>
|
||||
|
|
|
@ -33,7 +33,11 @@
|
|||
#ifdef HAVE_SYS_SOCKET_H
|
||||
#include <sys/socket.h>
|
||||
#endif // HAVE_SYS_SOCKET_H
|
||||
#ifdef _WIN32
|
||||
#include <ws2tcpip.h>
|
||||
#else
|
||||
#include <sys/un.h>
|
||||
#endif // _WIN32
|
||||
#ifdef HAVE_NETINET_IN_H
|
||||
#include <netinet/in.h>
|
||||
#endif // HAVE_NETINET_IN_H
|
||||
|
@ -48,7 +52,9 @@ union sockaddr_union {
|
|||
sockaddr sa;
|
||||
sockaddr_in6 in6;
|
||||
sockaddr_in in;
|
||||
#ifndef _WIN32
|
||||
sockaddr_un un;
|
||||
#endif // !_WIN32
|
||||
};
|
||||
|
||||
struct Address {
|
||||
|
|
68
src/util.cc
68
src/util.cc
|
@ -41,7 +41,12 @@
|
|||
#ifdef HAVE_NETINET_IN_H
|
||||
#include <netinet/in.h>
|
||||
#endif // HAVE_NETINET_IN_H
|
||||
#ifdef _WIN32
|
||||
#include <ws2tcpip.h>
|
||||
#include <boost/date_time/posix_time/posix_time.hpp>
|
||||
#else
|
||||
#include <netinet/tcp.h>
|
||||
#endif // _WIN32
|
||||
#ifdef HAVE_ARPA_INET_H
|
||||
#include <arpa/inet.h>
|
||||
#endif // HAVE_ARPA_INET_H
|
||||
|
@ -65,6 +70,28 @@ namespace nghttp2 {
|
|||
|
||||
namespace util {
|
||||
|
||||
#ifdef _WIN32
|
||||
// inet_pton-wrapper for Windows
|
||||
static int inet_pton(int af, const char *src, void *dst)
|
||||
{
|
||||
#if _WIN32_WINNT >= 0x0600
|
||||
return InetPtonA(af, src, dst);
|
||||
#else
|
||||
// the function takes a 'char*', so we need to make a copy
|
||||
char addr[INET6_ADDRSTRLEN + 1];
|
||||
strncpy(addr, src, sizeof(addr));
|
||||
addr[sizeof(addr)-1] = 0;
|
||||
|
||||
int size = sizeof(struct in6_addr);
|
||||
|
||||
if (WSAStringToAddress(addr, af, NULL, (LPSOCKADDR)dst, &size) == 0)
|
||||
return 1;
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
#endif // _WIN32
|
||||
|
||||
|
||||
const char UPPER_XDIGITS[] = "0123456789ABCDEF";
|
||||
|
||||
bool in_rfc3986_unreserved_chars(const char c) {
|
||||
|
@ -352,13 +379,33 @@ char *iso8601_date(char *res, int64_t ms) {
|
|||
return p;
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
namespace bt = boost::posix_time;
|
||||
// one-time definition of the locale that is used to parse UTC strings
|
||||
// (note that the time_input_facet is ref-counted and deleted automatically)
|
||||
static const std::locale ptime_locale(std::locale::classic(),
|
||||
new bt::time_input_facet("%a, %d %b %Y %H:%M:%S GMT"));
|
||||
#endif //_WIN32
|
||||
|
||||
time_t parse_http_date(const StringRef &s) {
|
||||
#ifdef _WIN32
|
||||
// there is no strptime - use boost
|
||||
std::stringstream sstr(s.str());
|
||||
sstr.imbue(ptime_locale);
|
||||
bt::ptime ltime;
|
||||
sstr >> ltime;
|
||||
if (!sstr)
|
||||
return 0;
|
||||
|
||||
return boost::posix_time::to_time_t(ltime);
|
||||
#else
|
||||
tm tm{};
|
||||
char *r = strptime(s.c_str(), "%a, %d %b %Y %H:%M:%S GMT", &tm);
|
||||
if (r == 0) {
|
||||
return 0;
|
||||
}
|
||||
return nghttp2_timegm_without_yday(&tm);
|
||||
#endif // _WIN32
|
||||
}
|
||||
|
||||
char upcase(char c) {
|
||||
|
@ -628,9 +675,11 @@ std::string numeric_name(const struct sockaddr *sa, socklen_t salen) {
|
|||
|
||||
std::string to_numeric_addr(const Address *addr) {
|
||||
auto family = addr->su.storage.ss_family;
|
||||
#ifndef _WIN32
|
||||
if (family == AF_UNIX) {
|
||||
return addr->su.un.sun_path;
|
||||
}
|
||||
#endif // !_WIN32
|
||||
|
||||
std::array<char, NI_MAXHOST> host;
|
||||
std::array<char, NI_MAXSERV> serv;
|
||||
|
@ -818,6 +867,10 @@ std::vector<std::string> parse_config_str_list(const StringRef &s, char delim) {
|
|||
}
|
||||
|
||||
int make_socket_closeonexec(int fd) {
|
||||
#ifdef _WIN32
|
||||
(void)fd;
|
||||
return 0;
|
||||
#else
|
||||
int flags;
|
||||
int rv;
|
||||
while ((flags = fcntl(fd, F_GETFD)) == -1 && errno == EINTR)
|
||||
|
@ -825,15 +878,24 @@ int make_socket_closeonexec(int fd) {
|
|||
while ((rv = fcntl(fd, F_SETFD, flags | FD_CLOEXEC)) == -1 && errno == EINTR)
|
||||
;
|
||||
return rv;
|
||||
#endif // _WIN32
|
||||
}
|
||||
|
||||
int make_socket_nonblocking(int fd) {
|
||||
int flags;
|
||||
int rv;
|
||||
|
||||
#ifdef _WIN32
|
||||
u_long mode = 1;
|
||||
|
||||
rv = ioctlsocket(fd, FIONBIO, &mode);
|
||||
#else
|
||||
int flags;
|
||||
while ((flags = fcntl(fd, F_GETFL, 0)) == -1 && errno == EINTR)
|
||||
;
|
||||
while ((rv = fcntl(fd, F_SETFL, flags | O_NONBLOCK)) == -1 && errno == EINTR)
|
||||
;
|
||||
#endif // _WIN32
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
@ -874,7 +936,7 @@ int create_nonblock_socket(int family) {
|
|||
bool check_socket_connected(int fd) {
|
||||
int error;
|
||||
socklen_t len = sizeof(error);
|
||||
if (getsockopt(fd, SOL_SOCKET, SO_ERROR, &error, &len) != 0) {
|
||||
if (getsockopt(fd, SOL_SOCKET, SO_ERROR, (char*)&error, &len) != 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -884,7 +946,7 @@ bool check_socket_connected(int fd) {
|
|||
int get_socket_error(int fd) {
|
||||
int error;
|
||||
socklen_t len = sizeof(error);
|
||||
if (getsockopt(fd, SOL_SOCKET, SO_ERROR, &error, &len) != 0) {
|
||||
if (getsockopt(fd, SOL_SOCKET, SO_ERROR, (char*)&error, &len) != 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue