ReactOS  0.4.15-dev-2979-gfd8baca
netconnection.c File Reference
#include "ws2tcpip.h"
#include <time.h>
#include <stdarg.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <assert.h>
#include "windef.h"
#include "winbase.h"
#include "wininet.h"
#include "winerror.h"
#include "wine/debug.h"
#include "internet.h"
Include dependency graph for netconnection.c:

Go to the source code of this file.

Macros

#define NONAMELESSUNION
 

Functions

 WINE_DEFAULT_DEBUG_CHANNEL (wininet)
 
static DWORD netconn_verify_cert (netconn_t *conn, PCCERT_CONTEXT cert, HCERTSTORE store)
 
static BOOL ensure_cred_handle (void)
 
static BOOL WINAPI winsock_startup (INIT_ONCE *once, void *param, void **context)
 
void init_winsock (void)
 
static void set_socket_blocking (netconn_t *conn, BOOL is_blocking)
 
static DWORD create_netconn_socket (server_t *server, netconn_t *netconn, DWORD timeout)
 
DWORD create_netconn (server_t *server, DWORD security_flags, BOOL mask_errors, DWORD timeout, netconn_t **ret)
 
BOOL is_valid_netconn (netconn_t *netconn)
 
void close_netconn (netconn_t *netconn)
 
void free_netconn (netconn_t *netconn)
 
void NETCON_unload (void)
 
int sock_send (int fd, const void *msg, size_t len, int flags)
 
int sock_recv (int fd, void *msg, size_t len, int flags)
 
static DWORD netcon_secure_connect_setup (netconn_t *connection, BOOL compat_mode)
 
DWORD NETCON_secure_connect (netconn_t *connection, server_t *server)
 
static BOOL send_ssl_chunk (netconn_t *conn, const void *msg, size_t size)
 
DWORD NETCON_send (netconn_t *connection, const void *msg, size_t len, int flags, int *sent)
 
static BOOL read_ssl_chunk (netconn_t *conn, void *buf, SIZE_T buf_size, BOOL blocking, SIZE_T *ret_size, BOOL *eof)
 
DWORD NETCON_recv (netconn_t *connection, void *buf, size_t len, BOOL blocking, int *recvd)
 
BOOL NETCON_is_alive (netconn_t *netconn)
 
LPCVOID NETCON_GetCert (netconn_t *connection)
 
int NETCON_GetCipherStrength (netconn_t *connection)
 
DWORD NETCON_set_timeout (netconn_t *connection, BOOL send, DWORD value)
 

Variables

static SecHandle cred_handle
 
static SecHandle compat_cred_handle
 
static BOOL cred_handle_initialized
 
static BOOL have_compat_cred_handle
 
static CRITICAL_SECTION init_sechandle_cs = { &init_sechandle_cs_debug, -1, 0, 0, 0, 0 }
 
static CRITICAL_SECTION_DEBUG init_sechandle_cs_debug
 
static BOOL winsock_loaded = FALSE
 

Macro Definition Documentation

◆ NONAMELESSUNION

#define NONAMELESSUNION

Definition at line 28 of file netconnection.c.

Function Documentation

◆ close_netconn()

void close_netconn ( netconn_t netconn)

Definition at line 379 of file netconnection.c.

380 {
382  netconn->socket = -1;
383 }
#define closesocket
Definition: ncftp.h:477

Referenced by free_netconn(), and http_release_netconn().

◆ create_netconn()

DWORD create_netconn ( server_t server,
DWORD  security_flags,
BOOL  mask_errors,
DWORD  timeout,
netconn_t **  ret 
)

Definition at line 347 of file netconnection.c.

348 {
350  int result;
351 
352  netconn = heap_alloc_zero(sizeof(*netconn));
353  if(!netconn)
354  return ERROR_OUTOFMEMORY;
355 
356  netconn->socket = -1;
357  netconn->security_flags = security_flags | server->security_flags;
358  netconn->mask_errors = mask_errors;
359  list_init(&netconn->pool_entry);
361 
363  if (result != ERROR_SUCCESS) {
365  return result;
366  }
367 
369  netconn->server = server;
370  *ret = netconn;
371  return result;
372 }
static rfbScreenInfoPtr server
Definition: vnc.c:74
#define ERROR_SUCCESS
Definition: deptool.c:10
GLuint64EXT * result
Definition: glext.h:11304
Definition: dhcpd.h:245
#define SecInvalidateHandle(x)
Definition: sspi.h:58
CtxtHandle ssl_ctx
int ret
void server_addref(server_t *server)
Definition: http.c:149
__WINE_SERVER_LIST_INLINE void list_init(struct list *list)
Definition: list.h:149
static DWORD create_netconn_socket(server_t *server, netconn_t *netconn, DWORD timeout)
#define ERROR_OUTOFMEMORY
Definition: deptool.c:13
static BOOL heap_free(void *mem)
Definition: appwiz.h:75

Referenced by open_http_connection().

◆ create_netconn_socket()

static DWORD create_netconn_socket ( server_t server,
netconn_t netconn,
DWORD  timeout 
)
static

Definition at line 296 of file netconnection.c.

297 {
298  int result;
299  ULONG flag;
300  DWORD res;
301 
302  init_winsock();
303 
304  assert(server->addr_len);
305  result = netconn->socket = socket(server->addr.ss_family, SOCK_STREAM, 0);
306  if(result != -1) {
308  result = connect(netconn->socket, (struct sockaddr*)&server->addr, server->addr_len);
309  if(result == -1)
310  {
311  res = WSAGetLastError();
312  if (res == WSAEINPROGRESS || res == WSAEWOULDBLOCK) {
313  FD_SET set;
314  int res;
315  socklen_t len = sizeof(res);
316  TIMEVAL timeout_timeval = {0, timeout*1000};
317 
318  FD_ZERO(&set);
319  FD_SET(netconn->socket, &set);
320  res = select(netconn->socket+1, NULL, &set, NULL, &timeout_timeval);
321  if(!res || res == SOCKET_ERROR) {
323  netconn->socket = -1;
325  }
326  if (!getsockopt(netconn->socket, SOL_SOCKET, SO_ERROR, (void *)&res, &len) && !res)
327  result = 0;
328  }
329  }
330  if(result == -1)
331  {
333  netconn->socket = -1;
334  }
335  }
336  if(result == -1)
338 
339  flag = 1;
341  if(result < 0)
342  WARN("setsockopt(TCP_NODELAY) failed\n");
343 
344  return ERROR_SUCCESS;
345 }
Definition: winsock.h:66
#define SOCKET_ERROR
Definition: winsock.h:333
static rfbScreenInfoPtr server
Definition: vnc.c:74
SOCKET WSAAPI socket(IN INT af, IN INT type, IN INT protocol)
Definition: socklife.c:143
#define ERROR_SUCCESS
Definition: deptool.c:10
GLuint64EXT * result
Definition: glext.h:11304
#define WARN(fmt,...)
Definition: debug.h:112
#define WSAEWOULDBLOCK
Definition: winerror.h:1948
#define assert(x)
Definition: debug.h:53
#define closesocket
Definition: ncftp.h:477
Definition: dhcpd.h:245
#define SOL_SOCKET
Definition: winsock.h:398
#define FD_ZERO(set)
Definition: winsock.h:96
#define FD_SET(fd, set)
Definition: winsock.h:89
INT WSAAPI connect(IN SOCKET s, IN CONST struct sockaddr *name, IN INT namelen)
Definition: sockctrl.c:23
#define WSAEINPROGRESS
Definition: winerror.h:1949
#define ERROR_INTERNET_CANNOT_CONNECT
Definition: wininet.h:2018
void init_winsock(void)
#define TCP_NODELAY
Definition: tcpdef.h:117
#define FALSE
Definition: types.h:117
INT WSAAPI select(IN INT s, IN OUT LPFD_SET readfds, IN OUT LPFD_SET writefds, IN OUT LPFD_SET exceptfds, IN CONST struct timeval *timeout)
Definition: select.c:41
INT WSAAPI setsockopt(IN SOCKET s, IN INT level, IN INT optname, IN CONST CHAR FAR *optval, IN INT optlen)
Definition: sockctrl.c:421
#define SO_ERROR
Definition: winsock.h:194
static UINT set(struct ID3DXConstantTableImpl *table, IDirect3DDevice9 *device, struct ctab_constant *constant, const void **indata, D3DXPARAMETER_TYPE intype, UINT *size, UINT incol, D3DXPARAMETER_CLASS inclass, UINT index, BOOL is_pointer)
Definition: shader.c:1102
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
unsigned long DWORD
Definition: ntddk_ex.h:95
int socklen_t
Definition: tcp.c:35
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean flag
Definition: glfuncs.h:52
GLenum GLsizei len
Definition: glext.h:6722
INT WSAAPI getsockopt(IN SOCKET s, IN INT level, IN INT optname, OUT CHAR FAR *optval, IN OUT INT FAR *optlen)
Definition: sockctrl.c:271
#define NULL
Definition: types.h:112
static void set_socket_blocking(netconn_t *conn, BOOL is_blocking)
GLuint res
Definition: glext.h:9613
unsigned int ULONG
Definition: retypes.h:1
#define SOCK_STREAM
Definition: tcpip.h:118
Definition: _set.h:46

Referenced by create_netconn(), and NETCON_secure_connect().

◆ ensure_cred_handle()

static BOOL ensure_cred_handle ( void  )
static

Definition at line 231 of file netconnection.c.

232 {
234 
236 
240 
242  NULL, NULL, &cred_handle, NULL);
243  if(res == SEC_E_OK) {
250  }
251  }
252 
254  }
255 
257 
258  if(res != SEC_E_OK) {
259  WARN("Failed: %08x\n", res);
260  return FALSE;
261  }
262 
263  return TRUE;
264 }
#define SECPKG_ATTR_SUPPORTED_PROTOCOLS
Definition: schannel.h:74
#define SECPKG_CRED_OUTBOUND
Definition: sspi.h:291
SECURITY_STATUS WINAPI AcquireCredentialsHandleW(SEC_WCHAR *pszPrincipal, SEC_WCHAR *pszPackage, ULONG fCredentialsUse, PLUID pvLogonID, PVOID pAuthData, SEC_GET_KEY_FN pGetKeyFn, PVOID pvGetKeyArgument, PCredHandle phCredential, PTimeStamp ptsExpiry)
Definition: wrapper.c:105
#define TRUE
Definition: types.h:120
#define WARN(fmt,...)
Definition: debug.h:112
static SecHandle cred_handle
void WINAPI EnterCriticalSection(LPCRITICAL_SECTION)
static BOOL cred_handle_initialized
SECURITY_STATUS WINAPI QueryCredentialsAttributesA(PCredHandle phCredential, ULONG ulAttribute, void *pBuffer)
Definition: wrapper.c:177
#define FALSE
Definition: types.h:117
#define SCHANNEL_CRED_VERSION
Definition: schannel.h:22
DWORD grbitEnabledProtocols
Definition: schannel.h:96
static CRITICAL_SECTION init_sechandle_cs
LONG SECURITY_STATUS
Definition: sspi.h:34
static SecHandle compat_cred_handle
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define SEC_E_OK
Definition: winerror.h:2356
#define SP_PROT_TLS1_1PLUS_CLIENT
Definition: schannel.h:52
#define NULL
Definition: types.h:112
#define UNISP_NAME_W
Definition: sspi.h:38
GLuint res
Definition: glext.h:9613
void WINAPI LeaveCriticalSection(LPCRITICAL_SECTION)
static BOOL have_compat_cred_handle

Referenced by netcon_secure_connect_setup().

◆ free_netconn()

void free_netconn ( netconn_t netconn)

Definition at line 385 of file netconnection.c.

386 {
387  server_release(netconn->server);
388 
389  if (netconn->secure) {
392  netconn->peek_msg = NULL;
393  netconn->peek_len = 0;
395  netconn->ssl_buf = NULL;
398  netconn->extra_len = 0;
399  }
402 
405 }
char * peek_msg_mem
size_t peek_len
void close_netconn(netconn_t *netconn)
char * extra_buf
size_t extra_len
char * peek_msg
#define SecIsValidHandle(x)
Definition: sspi.h:63
void server_release(server_t *server)
Definition: http.c:154
CtxtHandle ssl_ctx
#define NULL
Definition: types.h:112
char * ssl_buf
SECURITY_STATUS WINAPI DeleteSecurityContext(PCtxtHandle phContext)
Definition: wrapper.c:450
static BOOL heap_free(void *mem)
Definition: appwiz.h:75

Referenced by collect_connections(), and open_http_connection().

◆ init_winsock()

void init_winsock ( void  )

Definition at line 281 of file netconnection.c.

282 {
283  static INIT_ONCE init_once = INIT_ONCE_STATIC_INIT;
285 }
static BOOL WINAPI winsock_startup(INIT_ONCE *once, void *param, void **context)
#define INIT_ONCE_STATIC_INIT
Definition: winbase.h:609
BOOL NTAPI InitOnceExecuteOnce(INIT_ONCE *once, PINIT_ONCE_FN func, void *param, void **context)
#define NULL
Definition: types.h:112

Referenced by create_netconn_socket(), FTP_Connect(), FTP_InitListenSocket(), InternetCheckConnectionW(), and InternetOpenW().

◆ is_valid_netconn()

◆ NETCON_GetCert()

LPCVOID NETCON_GetCert ( netconn_t connection)

Definition at line 887 of file netconnection.c.

888 {
889  const CERT_CONTEXT *ret;
891 
893  return res == SEC_E_OK ? ret : NULL;
894 }
CtxtHandle ssl_ctx
Definition: internet.h:72
#define SECPKG_ATTR_REMOTE_CERT_CONTEXT
Definition: schannel.h:69
LONG SECURITY_STATUS
Definition: sspi.h:34
int ret
#define SEC_E_OK
Definition: winerror.h:2356
SECURITY_STATUS WINAPI QueryContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer)
Definition: wrapper.c:535
#define NULL
Definition: types.h:112
GLuint res
Definition: glext.h:9613

Referenced by get_security_cert_struct().

◆ NETCON_GetCipherStrength()

int NETCON_GetCipherStrength ( netconn_t connection)

Definition at line 896 of file netconnection.c.

897 {
900 
901  if (!connection->secure)
902  return 0;
903 
904  res = QueryContextAttributesW(&connection->ssl_ctx, SECPKG_ATTR_CONNECTION_INFO, (void*)&conn_info);
905  if(res != SEC_E_OK)
906  WARN("QueryContextAttributesW failed: %08x\n", res);
907  return res == SEC_E_OK ? conn_info.dwCipherStrength : 0;
908 }
CtxtHandle ssl_ctx
Definition: internet.h:72
#define WARN(fmt,...)
Definition: debug.h:112
LONG SECURITY_STATUS
Definition: sspi.h:34
BOOL secure
Definition: internet.h:70
#define SECPKG_ATTR_CONNECTION_INFO
Definition: schannel.h:76
#define SEC_E_OK
Definition: winerror.h:2356
SECURITY_STATUS WINAPI QueryContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer)
Definition: wrapper.c:535
GLuint res
Definition: glext.h:9613

Referenced by get_security_cert_struct(), and netcon_secure_connect_setup().

◆ NETCON_is_alive()

BOOL NETCON_is_alive ( netconn_t netconn)

Definition at line 876 of file netconnection.c.

877 {
878  int len;
879  char b;
880 
882  len = sock_recv(netconn->socket, &b, 1, MSG_PEEK);
883 
884  return len == 1 || (len == -1 && WSAGetLastError() == WSAEWOULDBLOCK);
885 }
int sock_recv(int fd, void *msg, size_t len, int flags)
#define WSAEWOULDBLOCK
Definition: winerror.h:1948
#define FALSE
Definition: types.h:117
#define b
Definition: ke_i.h:79
GLboolean GLboolean GLboolean b
Definition: glext.h:6204
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
GLenum GLsizei len
Definition: glext.h:6722
static void set_socket_blocking(netconn_t *conn, BOOL is_blocking)
#define MSG_PEEK
Definition: winsock.h:222

Referenced by open_http_connection().

◆ NETCON_recv()

DWORD NETCON_recv ( netconn_t connection,
void buf,
size_t  len,
BOOL  blocking,
int recvd 
)

Definition at line 824 of file netconnection.c.

825 {
826  *recvd = 0;
827  if (!len)
828  return ERROR_SUCCESS;
829 
830  if (!connection->secure)
831  {
832  set_socket_blocking(connection, blocking);
833  *recvd = sock_recv(connection->socket, buf, len, 0);
834  return *recvd == -1 ? WSAGetLastError() : ERROR_SUCCESS;
835  }
836  else
837  {
838  SIZE_T size = 0;
839  BOOL eof;
840  DWORD res;
841 
842  if(connection->peek_msg) {
843  size = min(len, connection->peek_len);
844  memcpy(buf, connection->peek_msg, size);
845  connection->peek_len -= size;
846  connection->peek_msg += size;
847 
848  if(!connection->peek_len) {
849  heap_free(connection->peek_msg_mem);
850  connection->peek_msg_mem = connection->peek_msg = NULL;
851  }
852 
853  *recvd = size;
854  return ERROR_SUCCESS;
855  }
856 
857  do {
858  res = read_ssl_chunk(connection, (BYTE*)buf, len, blocking, &size, &eof);
859  if(res != ERROR_SUCCESS) {
860  if(res == WSAEWOULDBLOCK) {
861  if(size)
862  res = ERROR_SUCCESS;
863  }else {
864  WARN("read_ssl_chunk failed\n");
865  }
866  break;
867  }
868  }while(!size && !eof);
869 
870  TRACE("received %ld bytes\n", size);
871  *recvd = size;
872  return res;
873  }
874 }
static BOOL read_ssl_chunk(netconn_t *conn, void *buf, SIZE_T buf_size, BOOL blocking, SIZE_T *ret_size, BOOL *eof)
#define ERROR_SUCCESS
Definition: deptool.c:10
#define WARN(fmt,...)
Definition: debug.h:112
int sock_recv(int fd, void *msg, size_t len, int flags)
#define WSAEWOULDBLOCK
Definition: winerror.h:1948
size_t peek_len
Definition: internet.h:80
int socket
Definition: internet.h:69
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
unsigned int BOOL
Definition: ntddk_ex.h:94
BOOL secure
Definition: internet.h:70
#define TRACE(s)
Definition: solgame.cpp:4
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
GLsizeiptr size
Definition: glext.h:5919
unsigned long DWORD
Definition: ntddk_ex.h:95
char * peek_msg_mem
Definition: internet.h:79
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
GLenum GLsizei len
Definition: glext.h:6722
unsigned char BYTE
Definition: xxhash.c:193
_Check_return_ _CRTIMP int __cdecl __cdecl eof(_In_ int _FileHandle)
ULONG_PTR SIZE_T
Definition: typedefs.h:80
#define min(a, b)
Definition: monoChain.cc:55
#define NULL
Definition: types.h:112
static void set_socket_blocking(netconn_t *conn, BOOL is_blocking)
char * peek_msg
Definition: internet.h:78
GLuint res
Definition: glext.h:9613
static BOOL heap_free(void *mem)
Definition: appwiz.h:75

Referenced by chunked_read(), netconn_drain_content(), netconn_read(), and read_more_data().

◆ NETCON_secure_connect()

DWORD NETCON_secure_connect ( netconn_t connection,
server_t server 
)

Definition at line 604 of file netconnection.c.

605 {
606  DWORD res;
607 
608  /* can't connect if we are already connected */
609  if(connection->secure) {
610  ERR("already connected\n");
612  }
613 
614  if(server != connection->server) {
615  server_release(connection->server);
617  connection->server = server;
618  }
619 
620  /* connect with given TLS options */
621  res = netcon_secure_connect_setup(connection, FALSE);
622  if (res == ERROR_SUCCESS)
623  return res;
624 
625  /* FIXME: when got version alert and FIN from server */
626  /* fallback to connect without TLSv1.1/TLSv1.2 */
628  {
629  closesocket(connection->socket);
630  res = create_netconn_socket(connection->server, connection, 500);
631  if (res != ERROR_SUCCESS)
632  return res;
633  res = netcon_secure_connect_setup(connection, TRUE);
634  }
635  return res;
636 }
static rfbScreenInfoPtr server
Definition: vnc.c:74
#define ERROR_SUCCESS
Definition: deptool.c:10
#define TRUE
Definition: types.h:120
#define closesocket
Definition: ncftp.h:477
void server_release(server_t *server)
Definition: http.c:154
int socket
Definition: internet.h:69
#define ERROR_INTERNET_CANNOT_CONNECT
Definition: wininet.h:2018
#define FALSE
Definition: types.h:117
BOOL secure
Definition: internet.h:70
static DWORD netcon_secure_connect_setup(netconn_t *connection, BOOL compat_mode)
unsigned long DWORD
Definition: ntddk_ex.h:95
void server_addref(server_t *server)
Definition: http.c:149
#define ERR(fmt,...)
Definition: debug.h:110
#define ERROR_INTERNET_SECURITY_CHANNEL_ERROR
Definition: wininet.h:2069
GLuint res
Definition: glext.h:9613
static DWORD create_netconn_socket(server_t *server, netconn_t *netconn, DWORD timeout)
server_t * server
Definition: internet.h:74
static BOOL have_compat_cred_handle

Referenced by HTTP_HttpSendRequestW().

◆ netcon_secure_connect_setup()

static DWORD netcon_secure_connect_setup ( netconn_t connection,
BOOL  compat_mode 
)
static

Definition at line 440 of file netconnection.c.

441 {
442  SecBuffer out_buf = {0, SECBUFFER_TOKEN, NULL}, in_bufs[2] = {{0, SECBUFFER_TOKEN}, {0, SECBUFFER_EMPTY}};
443  SecBufferDesc out_desc = {SECBUFFER_VERSION, 1, &out_buf}, in_desc = {SECBUFFER_VERSION, 2, in_bufs};
444  SecHandle *cred = &cred_handle;
445  BYTE *read_buf;
446  SIZE_T read_buf_size = 2048;
447  ULONG attrs = 0;
448  CtxtHandle ctx;
449  SSIZE_T size;
450  int bits;
451  const CERT_CONTEXT *cert;
454 
457 
458  if(!ensure_cred_handle())
460 
461  if(compat_mode) {
464  cred = &compat_cred_handle;
465  }
466 
467  read_buf = heap_alloc(read_buf_size);
468  if(!read_buf)
469  return ERROR_OUTOFMEMORY;
470 
471  status = InitializeSecurityContextW(cred, NULL, connection->server->name, isc_req_flags, 0, 0, NULL, 0,
472  &ctx, &out_desc, &attrs, NULL);
473 
474  assert(status != SEC_E_OK);
475 
476  set_socket_blocking(connection, TRUE);
477 
479  if(out_buf.cbBuffer) {
481 
482  TRACE("sending %u bytes\n", out_buf.cbBuffer);
483 
484  size = sock_send(connection->socket, out_buf.pvBuffer, out_buf.cbBuffer, 0);
485  if(size != out_buf.cbBuffer) {
486  ERR("send failed\n");
488  break;
489  }
490 
491  FreeContextBuffer(out_buf.pvBuffer);
492  out_buf.pvBuffer = NULL;
493  out_buf.cbBuffer = 0;
494  }
495 
497  assert(in_bufs[1].cbBuffer < read_buf_size);
498 
499  memmove(read_buf, (BYTE*)in_bufs[0].pvBuffer+in_bufs[0].cbBuffer-in_bufs[1].cbBuffer, in_bufs[1].cbBuffer);
500  in_bufs[0].cbBuffer = in_bufs[1].cbBuffer;
501 
502  in_bufs[1].BufferType = SECBUFFER_EMPTY;
503  in_bufs[1].cbBuffer = 0;
504  in_bufs[1].pvBuffer = NULL;
505  }
506 
507  assert(in_bufs[0].BufferType == SECBUFFER_TOKEN);
508  assert(in_bufs[1].BufferType == SECBUFFER_EMPTY);
509 
510  if(in_bufs[0].cbBuffer + 1024 > read_buf_size) {
511  BYTE *new_read_buf;
512 
513  new_read_buf = heap_realloc(read_buf, read_buf_size + 1024);
514  if(!new_read_buf) {
516  break;
517  }
518 
519  in_bufs[0].pvBuffer = read_buf = new_read_buf;
520  read_buf_size += 1024;
521  }
522 
523  size = sock_recv(connection->socket, read_buf+in_bufs[0].cbBuffer, read_buf_size-in_bufs[0].cbBuffer, 0);
524  if(size < 1) {
525  WARN("recv error\n");
527  break;
528  }
529 
530  TRACE("recv %lu bytes\n", size);
531 
532  in_bufs[0].cbBuffer += size;
533  in_bufs[0].pvBuffer = read_buf;
534  status = InitializeSecurityContextW(cred, &ctx, connection->server->name, isc_req_flags, 0, 0, &in_desc,
535  0, NULL, &out_desc, &attrs, NULL);
536  TRACE("InitializeSecurityContext ret %08x\n", status);
537 
538  if(status == SEC_E_OK) {
539  if(SecIsValidHandle(&connection->ssl_ctx))
540  DeleteSecurityContext(&connection->ssl_ctx);
541  connection->ssl_ctx = ctx;
542 
543  if(in_bufs[1].BufferType == SECBUFFER_EXTRA)
544  FIXME("SECBUFFER_EXTRA not supported\n");
545 
547  if(status != SEC_E_OK) {
548  WARN("Could not get sizes\n");
549  break;
550  }
551 
553  if(status == SEC_E_OK) {
554  res = netconn_verify_cert(connection, cert, cert->hCertStore);
556  if(res != ERROR_SUCCESS) {
557  WARN("cert verify failed: %u\n", res);
558  break;
559  }
560  }else {
561  WARN("Could not get cert\n");
562  break;
563  }
564 
565  connection->ssl_buf = heap_alloc(connection->ssl_sizes.cbHeader + connection->ssl_sizes.cbMaximumMessage
566  + connection->ssl_sizes.cbTrailer);
567  if(!connection->ssl_buf) {
568  res = GetLastError();
569  break;
570  }
571  }
572  }
573 
575 
576  if(status != SEC_E_OK || res != ERROR_SUCCESS) {
577  WARN("Failed to establish SSL connection: %08x (%u)\n", status, res);
578  heap_free(connection->ssl_buf);
579  connection->ssl_buf = NULL;
581  }
582 
583  TRACE("established SSL connection\n");
584  connection->secure = TRUE;
585  connection->security_flags |= SECURITY_FLAG_SECURE;
586 
587  bits = NETCON_GetCipherStrength(connection);
588  if (bits >= 128)
590  else if (bits >= 56)
592  else
594 
595  if(connection->mask_errors)
596  connection->server->security_flags = connection->security_flags;
597  return ERROR_SUCCESS;
598 }
#define ISC_REQ_SEQUENCE_DETECT
Definition: sspi.h:365
#define SECURITY_FLAG_STRENGTH_MEDIUM
Definition: winhttp.h:287
#define memmove(s1, s2, n)
Definition: mkisofs.h:881
CtxtHandle ssl_ctx
Definition: internet.h:72
static DWORD netconn_verify_cert(netconn_t *conn, PCCERT_CONTEXT cert, HCERTSTORE store)
Definition: netconnection.c:50
#define SECURITY_FLAG_STRENGTH_STRONG
Definition: winhttp.h:288
#define ERROR_SUCCESS
Definition: deptool.c:10
SECURITY_STATUS WINAPI FreeContextBuffer(PVOID pv)
Definition: sspi.c:699
#define TRUE
Definition: types.h:120
#define SecIsValidHandle(x)
Definition: sspi.h:63
BOOL WINAPI CertFreeCertificateContext(PCCERT_CONTEXT pCertContext)
Definition: cert.c:371
#define WARN(fmt,...)
Definition: debug.h:112
int sock_recv(int fd, void *msg, size_t len, int flags)
#define SECPKG_ATTR_REMOTE_CERT_CONTEXT
Definition: schannel.h:69
static SecHandle cred_handle
#define assert(x)
Definition: debug.h:53
DWORD WINAPI GetLastError(VOID)
Definition: except.c:1040
LONG_PTR SSIZE_T
Definition: basetsd.h:183
GLenum GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * bits
Definition: glext.h:10929
int socket
Definition: internet.h:69
static void * heap_realloc(void *mem, size_t len)
Definition: appwiz.h:70
static void * heap_alloc(size_t len)
Definition: appwiz.h:65
#define SECBUFFER_EXTRA
Definition: sspi.h:164
unsigned read_buf(z_streamp strm, Bytef *buf, unsigned size)
Definition: deflate.c:1167
#define ISC_REQ_MANUAL_CRED_VALIDATION
Definition: sspi.h:381
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define FIXME(fmt,...)
Definition: debug.h:111
#define SECBUFFER_EMPTY
Definition: sspi.h:159
int sock_send(int fd, const void *msg, size_t len, int flags)
#define SEC_I_CONTINUE_NEEDED
Definition: winerror.h:2927
static BYTE cert[]
Definition: msg.c:1437
DWORD security_flags
Definition: internet.h:81
LONG SECURITY_STATUS
Definition: sspi.h:34
BOOL secure
Definition: internet.h:70
static SecHandle compat_cred_handle
#define TRACE(s)
Definition: solgame.cpp:4
GLsizeiptr size
Definition: glext.h:5919
SECURITY_STATUS WINAPI InitializeSecurityContextW(PCredHandle phCredential, PCtxtHandle phContext, SEC_WCHAR *pszTargetName, ULONG fContextReq, ULONG Reserved1, ULONG TargetDataRep, PSecBufferDesc pInput, ULONG Reserved2, PCtxtHandle phNewContext, PSecBufferDesc pOutput, ULONG *pfContextAttr, PTimeStamp ptsExpiry)
Definition: wrapper.c:301
static BOOL ensure_cred_handle(void)
DWORD security_flags
Definition: internet.h:49
unsigned long DWORD
Definition: ntddk_ex.h:95
#define ISC_REQ_USE_SESSION_KEY
Definition: sspi.h:367
#define SECPKG_ATTR_STREAM_SIZES
Definition: sspi.h:525
#define ISC_REQ_ALLOCATE_MEMORY
Definition: sspi.h:370
#define SECBUFFER_TOKEN
Definition: sspi.h:161
WCHAR * name
Definition: internet.h:36
#define SEC_E_OK
Definition: winerror.h:2356
unsigned char BYTE
Definition: xxhash.c:193
SECURITY_STATUS WINAPI QueryContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer)
Definition: wrapper.c:535
#define ERR(fmt,...)
Definition: debug.h:110
BOOL mask_errors
Definition: internet.h:82
ULONG_PTR SIZE_T
Definition: typedefs.h:80
#define SECBUFFER_VERSION
Definition: sspi.h:187
ULONG cbBuffer
Definition: sspi.h:153
#define ERROR_INTERNET_SECURITY_CHANNEL_ERROR
Definition: wininet.h:2069
#define NULL
Definition: types.h:112
int NETCON_GetCipherStrength(netconn_t *connection)
static void set_socket_blocking(netconn_t *conn, BOOL is_blocking)
char * ssl_buf
Definition: internet.h:75
GLuint res
Definition: glext.h:9613
unsigned int ULONG
Definition: retypes.h:1
#define ISC_REQ_CONFIDENTIALITY
Definition: sspi.h:366
#define SECURITY_FLAG_SECURE
Definition: winhttp.h:285
#define ISC_REQ_REPLAY_DETECT
Definition: sspi.h:364
static SERVICE_STATUS status
Definition: service.c:31
server_t * server
Definition: internet.h:74
SecPkgContext_StreamSizes ssl_sizes
Definition: internet.h:73
#define SEC_E_INCOMPLETE_MESSAGE
Definition: winerror.h:2934
#define SECURITY_FLAG_STRENGTH_WEAK
Definition: winhttp.h:286
SECURITY_STATUS WINAPI DeleteSecurityContext(PCtxtHandle phContext)
Definition: wrapper.c:450
#define ERROR_OUTOFMEMORY
Definition: deptool.c:13
static BOOL have_compat_cred_handle
static BOOL heap_free(void *mem)
Definition: appwiz.h:75
Definition: ps.c:97

Referenced by NETCON_secure_connect().

◆ NETCON_send()

DWORD NETCON_send ( netconn_t connection,
const void msg,
size_t  len,
int  flags,
int sent 
)

Definition at line 669 of file netconnection.c.

671 {
672  /* send is always blocking. */
673  set_socket_blocking(connection, TRUE);
674 
675  if(!connection->secure)
676  {
677  *sent = sock_send(connection->socket, msg, len, flags);
678  return *sent == -1 ? WSAGetLastError() : ERROR_SUCCESS;
679  }
680  else
681  {
682  const BYTE *ptr = msg;
683  size_t chunk_size;
684 
685  *sent = 0;
686 
687  while(len) {
688  chunk_size = min(len, connection->ssl_sizes.cbMaximumMessage);
689  if(!send_ssl_chunk(connection, ptr, chunk_size))
691 
692  *sent += chunk_size;
693  ptr += chunk_size;
694  len -= chunk_size;
695  }
696 
697  return ERROR_SUCCESS;
698  }
699 }
#define ERROR_SUCCESS
Definition: deptool.c:10
#define TRUE
Definition: types.h:120
int socket
Definition: internet.h:69
static PVOID ptr
Definition: dispmode.c:27
int sock_send(int fd, const void *msg, size_t len, int flags)
BOOL secure
Definition: internet.h:70
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
GLbitfield flags
Definition: glext.h:7161
Definition: msg.h:34
GLenum GLsizei len
Definition: glext.h:6722
unsigned char BYTE
Definition: xxhash.c:193
static BOOL send_ssl_chunk(netconn_t *conn, const void *msg, size_t size)
#define ERROR_INTERNET_SECURITY_CHANNEL_ERROR
Definition: wininet.h:2069
#define min(a, b)
Definition: monoChain.cc:55
static void set_socket_blocking(netconn_t *conn, BOOL is_blocking)
#define msg(x)
Definition: auth_time.c:54
SecPkgContext_StreamSizes ssl_sizes
Definition: internet.h:73

Referenced by HTTP_HttpSendRequestW(), and HTTPREQ_WriteFile().

◆ NETCON_set_timeout()

DWORD NETCON_set_timeout ( netconn_t connection,
BOOL  send,
DWORD  value 
)

Definition at line 910 of file netconnection.c.

911 {
912  int result;
913 
914  result = setsockopt(connection->socket, SOL_SOCKET,
915  send ? SO_SNDTIMEO : SO_RCVTIMEO, (void*)&value,
916  sizeof(value));
917  if (result == -1)
918  {
919  WARN("setsockopt failed\n");
920  return WSAGetLastError();
921  }
922  return ERROR_SUCCESS;
923 }
Definition: pdh_main.c:93
#define ERROR_SUCCESS
Definition: deptool.c:10
GLuint64EXT * result
Definition: glext.h:11304
#define WARN(fmt,...)
Definition: debug.h:112
#define SOL_SOCKET
Definition: winsock.h:398
int socket
Definition: internet.h:69
INT WSAAPI setsockopt(IN SOCKET s, IN INT level, IN INT optname, IN CONST CHAR FAR *optval, IN INT optlen)
Definition: sockctrl.c:421
#define SO_RCVTIMEO
Definition: winsock.h:193
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
INT WSAAPI send(IN SOCKET s, IN CONST CHAR FAR *buf, IN INT len, IN INT flags)
Definition: send.c:23
#define SO_SNDTIMEO
Definition: winsock.h:192

Referenced by HTTP_GetResponseHeaders(), and HTTP_HttpSendRequestW().

◆ NETCON_unload()

void NETCON_unload ( void  )

Definition at line 407 of file netconnection.c.

408 {
414  if(winsock_loaded)
415  WSACleanup();
416 }
INT WSAAPI WSACleanup(VOID)
Definition: startup.c:60
static SecHandle cred_handle
SECURITY_STATUS WINAPI FreeCredentialsHandle(PCredHandle phCredential)
Definition: wrapper.c:151
static BOOL winsock_loaded
static BOOL cred_handle_initialized
static CRITICAL_SECTION init_sechandle_cs
static SecHandle compat_cred_handle
void WINAPI DeleteCriticalSection(PCRITICAL_SECTION)
static BOOL have_compat_cred_handle

Referenced by DllMain().

◆ netconn_verify_cert()

static DWORD netconn_verify_cert ( netconn_t conn,
PCCERT_CONTEXT  cert,
HCERTSTORE  store 
)
static

Definition at line 50 of file netconnection.c.

51 {
52  BOOL ret;
53  CERT_CHAIN_PARA chainPara = { sizeof(chainPara), { 0 } };
55  char oid_server_auth[] = szOID_PKIX_KP_SERVER_AUTH;
56  char *server_auth[] = { oid_server_auth };
57  DWORD err = ERROR_SUCCESS, errors;
58 
59  static const DWORD supportedErrors =
65 
66  TRACE("verifying %s\n", debugstr_w(conn->server->name));
67 
69  chainPara.RequestedUsage.Usage.rgpszUsageIdentifier = server_auth;
70  if (!(ret = CertGetCertificateChain(NULL, cert, NULL, store, &chainPara, 0, NULL, &chain))) {
71  TRACE("failed\n");
72  return GetLastError();
73  }
74 
75  errors = chain->TrustStatus.dwErrorStatus;
76 
77  do {
78  /* This seems strange, but that's what tests show */
79  if(errors & CERT_TRUST_IS_PARTIAL_CHAIN) {
80  WARN("ERROR_INTERNET_SEC_CERT_REV_FAILED\n");
82  if(conn->mask_errors)
85  break;
86  }
87 
88  if (chain->TrustStatus.dwErrorStatus & ~supportedErrors) {
89  WARN("error status %x\n", chain->TrustStatus.dwErrorStatus & ~supportedErrors);
91  errors &= supportedErrors;
92  if(!conn->mask_errors)
93  break;
94  WARN("unknown error flags\n");
95  }
96 
97  if(errors & CERT_TRUST_IS_NOT_TIME_VALID) {
98  WARN("CERT_TRUST_IS_NOT_TIME_VALID\n");
101  if(!conn->mask_errors)
102  break;
104  }
105  errors &= ~CERT_TRUST_IS_NOT_TIME_VALID;
106  }
107 
108  if(errors & CERT_TRUST_IS_UNTRUSTED_ROOT) {
109  WARN("CERT_TRUST_IS_UNTRUSTED_ROOT\n");
112  if(!conn->mask_errors)
113  break;
115  }
116  errors &= ~CERT_TRUST_IS_UNTRUSTED_ROOT;
117  }
118 
119  if(errors & CERT_TRUST_IS_PARTIAL_CHAIN) {
120  WARN("CERT_TRUST_IS_PARTIAL_CHAIN\n");
123  if(!conn->mask_errors)
124  break;
126  }
127  errors &= ~CERT_TRUST_IS_PARTIAL_CHAIN;
128  }
129 
130  if(errors & CERT_TRUST_IS_NOT_SIGNATURE_VALID) {
131  WARN("CERT_TRUST_IS_NOT_SIGNATURE_VALID\n");
134  if(!conn->mask_errors)
135  break;
137  }
139  }
140 
141  if(errors & CERT_TRUST_IS_NOT_VALID_FOR_USAGE) {
142  WARN("CERT_TRUST_IS_NOT_VALID_FOR_USAGE\n");
145  if(!conn->mask_errors)
146  break;
147  WARN("CERT_TRUST_IS_NOT_VALID_FOR_USAGE, unknown error flags\n");
148  }
150  }
151 
154  err = ERROR_SUCCESS;
155  }
156  }while(0);
157 
158  if(!err || conn->mask_errors) {
159  CERT_CHAIN_POLICY_PARA policyPara;
160  SSL_EXTRA_CERT_CHAIN_POLICY_PARA sslExtraPolicyPara;
161  CERT_CHAIN_POLICY_STATUS policyStatus;
162  CERT_CHAIN_CONTEXT chainCopy;
163 
164  /* Clear chain->TrustStatus.dwErrorStatus so
165  * CertVerifyCertificateChainPolicy will verify additional checks
166  * rather than stopping with an existing, ignored error.
167  */
168  memcpy(&chainCopy, chain, sizeof(chainCopy));
169  chainCopy.TrustStatus.dwErrorStatus = 0;
170  sslExtraPolicyPara.u.cbSize = sizeof(sslExtraPolicyPara);
171  sslExtraPolicyPara.dwAuthType = AUTHTYPE_SERVER;
172  sslExtraPolicyPara.pwszServerName = conn->server->name;
173  sslExtraPolicyPara.fdwChecks = conn->security_flags;
174  policyPara.cbSize = sizeof(policyPara);
175  policyPara.dwFlags = 0;
176  policyPara.pvExtraPolicyPara = &sslExtraPolicyPara;
178  &chainCopy, &policyPara, &policyStatus);
179  /* Any error in the policy status indicates that the
180  * policy couldn't be verified.
181  */
182  if(ret) {
183  if(policyStatus.dwError == CERT_E_CN_NO_MATCH) {
184  WARN("CERT_E_CN_NO_MATCH\n");
185  if(conn->mask_errors)
188  }else if(policyStatus.dwError) {
189  WARN("policyStatus.dwError %x\n", policyStatus.dwError);
190  if(conn->mask_errors)
191  WARN("unknown error flags for policy status %x\n", policyStatus.dwError);
193  }
194  }else {
195  err = GetLastError();
196  }
197  }
198 
199  if(err) {
200  WARN("failed %u\n", err);
202  if(conn->server->cert_chain) {
204  conn->server->cert_chain = NULL;
205  }
206  if(conn->mask_errors)
208  return err;
209  }
210 
211  /* FIXME: Reuse cached chain */
212  if(conn->server->cert_chain)
214  else
215  conn->server->cert_chain = chain;
216  return ERROR_SUCCESS;
217 }
BOOL WINAPI CertGetCertificateChain(HCERTCHAINENGINE hChainEngine, PCCERT_CONTEXT pCertContext, LPFILETIME pTime, HCERTSTORE hAdditionalStore, PCERT_CHAIN_PARA pChainPara, DWORD dwFlags, LPVOID pvReserved, PCCERT_CHAIN_CONTEXT *ppChainContext)
Definition: chain.c:2879
#define ERROR_INTERNET_SEC_CERT_CN_INVALID
Definition: wininet.h:2026
CERT_ENHKEY_USAGE Usage
Definition: wincrypt.h:1048
#define SECURITY_FLAG_IGNORE_UNKNOWN_CA
Definition: winhttp.h:281
#define CERT_TRUST_IS_NOT_TIME_VALID
Definition: wincrypt.h:870
#define ERROR_SUCCESS
Definition: deptool.c:10
#define ERROR_INTERNET_SEC_CERT_REV_FAILED
Definition: wininet.h:2044
#define WARN(fmt,...)
Definition: debug.h:112
const CERT_CHAIN_CONTEXT * cert_chain
Definition: internet.h:50
CERT_USAGE_MATCH RequestedUsage
Definition: wincrypt.h:1070
#define assert(x)
Definition: debug.h:53
DWORD WINAPI GetLastError(VOID)
Definition: except.c:1040
#define szOID_PKIX_KP_SERVER_AUTH
Definition: wincrypt.h:3294
VOID WINAPI CertFreeCertificateChain(PCCERT_CHAIN_CONTEXT pChainContext)
Definition: chain.c:2960
#define CERT_E_CN_NO_MATCH
Definition: winerror.h:3131
BOOL WINAPI CertVerifyCertificateChainPolicy(LPCSTR szPolicyOID, PCCERT_CHAIN_CONTEXT pChainContext, PCERT_CHAIN_POLICY_PARA pPolicyPara, PCERT_CHAIN_POLICY_STATUS pPolicyStatus)
Definition: chain.c:3716
#define SECURITY_FLAG_IGNORE_REVOCATION
Definition: wininet.h:829
#define CERT_CHAIN_POLICY_SSL
Definition: wincrypt.h:965
unsigned int BOOL
Definition: ntddk_ex.h:94
#define debugstr_w
Definition: kernel32.h:32
#define ERROR_INTERNET_SEC_CERT_ERRORS
Definition: wininet.h:2042
struct sock * chain
Definition: tcpcore.h:1164
static BYTE cert[]
Definition: msg.c:1437
DWORD security_flags
Definition: internet.h:81
CERT_TRUST_STATUS TrustStatus
Definition: wincrypt.h:939
#define _SECURITY_ERROR_FLAGS_MASK
Definition: internet.h:477
#define TRACE(s)
Definition: solgame.cpp:4
DWORD security_flags
Definition: internet.h:49
unsigned long DWORD
Definition: ntddk_ex.h:95
#define _SECURITY_FLAG_CERT_INVALID_CN
Definition: internet.h:474
#define CERT_TRUST_IS_NOT_SIGNATURE_VALID
Definition: wincrypt.h:873
int ret
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
WCHAR * name
Definition: internet.h:36
#define err(...)
#define SECURITY_FLAG_IGNORE_CERT_DATE_INVALID
Definition: winhttp.h:282
BOOL mask_errors
Definition: internet.h:82
#define ERROR_INTERNET_SEC_CERT_DATE_INVALID
Definition: wininet.h:2025
#define ERROR_INTERNET_INVALID_CA
Definition: wininet.h:2033
#define CERT_TRUST_IS_NOT_VALID_FOR_USAGE
Definition: wincrypt.h:874
#define ERROR_INTERNET_SEC_INVALID_CERT
Definition: wininet.h:2077
DWORD cUsageIdentifier
Definition: wincrypt.h:719
#define SECURITY_FLAG_IGNORE_WRONG_USAGE
Definition: wininet.h:831
#define _SECURITY_FLAG_CERT_INVALID_DATE
Definition: internet.h:475
#define NULL
Definition: types.h:112
#define CERT_TRUST_IS_UNTRUSTED_ROOT
Definition: wincrypt.h:875
LPSTR * rgpszUsageIdentifier
Definition: wincrypt.h:720
#define _SECURITY_FLAG_CERT_INVALID_CA
Definition: internet.h:473
#define AUTHTYPE_SERVER
Definition: wincrypt.h:1035
server_t * server
Definition: internet.h:74
#define CERT_TRUST_IS_PARTIAL_CHAIN
Definition: wincrypt.h:891
#define _SECURITY_FLAG_CERT_REV_FAILED
Definition: internet.h:472

Referenced by netcon_secure_connect_setup().

◆ read_ssl_chunk()

static BOOL read_ssl_chunk ( netconn_t conn,
void buf,
SIZE_T  buf_size,
BOOL  blocking,
SIZE_T ret_size,
BOOL eof 
)
static

Definition at line 701 of file netconnection.c.

702 {
703  const SIZE_T ssl_buf_size = conn->ssl_sizes.cbHeader+conn->ssl_sizes.cbMaximumMessage+conn->ssl_sizes.cbTrailer;
704  SecBuffer bufs[4];
706  SSIZE_T size, buf_len = 0;
707  int i;
709 
710  assert(conn->extra_len < ssl_buf_size);
711 
712  if(conn->extra_len) {
713  memcpy(conn->ssl_buf, conn->extra_buf, conn->extra_len);
714  buf_len = conn->extra_len;
715  conn->extra_len = 0;
716  heap_free(conn->extra_buf);
717  conn->extra_buf = NULL;
718  }
719 
720  set_socket_blocking(conn, blocking && !buf_len);
721  size = sock_recv(conn->socket, conn->ssl_buf+buf_len, ssl_buf_size-buf_len, 0);
722  if(size < 0) {
723  if(!buf_len) {
725  TRACE("would block\n");
726  return WSAEWOULDBLOCK;
727  }
728  WARN("recv failed\n");
730  }
731  }else {
732  buf_len += size;
733  }
734 
735  if(!buf_len) {
736  TRACE("EOF\n");
737  *eof = TRUE;
738  *ret_size = 0;
739  return ERROR_SUCCESS;
740  }
741 
742  *eof = FALSE;
743 
744  do {
745  memset(bufs, 0, sizeof(bufs));
746  bufs[0].BufferType = SECBUFFER_DATA;
747  bufs[0].cbBuffer = buf_len;
748  bufs[0].pvBuffer = conn->ssl_buf;
749 
750  res = DecryptMessage(&conn->ssl_ctx, &buf_desc, 0, NULL);
751  switch(res) {
752  case SEC_E_OK:
753  break;
755  TRACE("context expired\n");
756  *eof = TRUE;
757  return ERROR_SUCCESS;
759  assert(buf_len < ssl_buf_size);
760 
761  set_socket_blocking(conn, blocking);
762  size = sock_recv(conn->socket, conn->ssl_buf+buf_len, ssl_buf_size-buf_len, 0);
763  if(size < 1) {
764  if(size < 0 && WSAGetLastError() == WSAEWOULDBLOCK) {
765  TRACE("would block\n");
766 
767  /* FIXME: Optimize extra_buf usage. */
768  conn->extra_buf = heap_alloc(buf_len);
769  if(!conn->extra_buf)
771 
772  conn->extra_len = buf_len;
773  memcpy(conn->extra_buf, conn->ssl_buf, conn->extra_len);
774  return WSAEWOULDBLOCK;
775  }
776 
778  }
779 
780  buf_len += size;
781  continue;
782  default:
783  WARN("failed: %08x\n", res);
785  }
786  } while(res != SEC_E_OK);
787 
788  for(i = 0; i < ARRAY_SIZE(bufs); i++) {
789  if(bufs[i].BufferType == SECBUFFER_DATA) {
790  size = min(buf_size, bufs[i].cbBuffer);
791  memcpy(buf, bufs[i].pvBuffer, size);
792  if(size < bufs[i].cbBuffer) {
793  assert(!conn->peek_len);
794  conn->peek_msg_mem = conn->peek_msg = heap_alloc(bufs[i].cbBuffer - size);
795  if(!conn->peek_msg)
797  conn->peek_len = bufs[i].cbBuffer-size;
798  memcpy(conn->peek_msg, (char*)bufs[i].pvBuffer+size, conn->peek_len);
799  }
800 
801  *ret_size = size;
802  }
803  }
804 
805  for(i = 0; i < ARRAY_SIZE(bufs); i++) {
806  if(bufs[i].BufferType == SECBUFFER_EXTRA) {
807  conn->extra_buf = heap_alloc(bufs[i].cbBuffer);
808  if(!conn->extra_buf)
810 
811  conn->extra_len = bufs[i].cbBuffer;
812  memcpy(conn->extra_buf, bufs[i].pvBuffer, conn->extra_len);
813  }
814  }
815 
816  return ERROR_SUCCESS;
817 }
size_t extra_len
Definition: internet.h:77
#define ERROR_INTERNET_CONNECTION_ABORTED
Definition: wininet.h:2019
CtxtHandle ssl_ctx
Definition: internet.h:72
#define ERROR_SUCCESS
Definition: deptool.c:10
const GLenum * bufs
Definition: glext.h:6026
#define TRUE
Definition: types.h:120
#define SEC_I_CONTEXT_EXPIRED
Definition: winerror.h:2933
#define WARN(fmt,...)
Definition: debug.h:112
int sock_recv(int fd, void *msg, size_t len, int flags)
#define WSAEWOULDBLOCK
Definition: winerror.h:1948
#define ERROR_NOT_ENOUGH_MEMORY
Definition: dderror.h:7
#define SECBUFFER_DATA
Definition: sspi.h:160
#define assert(x)
Definition: debug.h:53
LONG_PTR SSIZE_T
Definition: basetsd.h:183
size_t peek_len
Definition: internet.h:80
int socket
Definition: internet.h:69
static void * heap_alloc(size_t len)
Definition: appwiz.h:65
#define SECBUFFER_EXTRA
Definition: sspi.h:164
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
#define FALSE
Definition: types.h:117
LONG SECURITY_STATUS
Definition: sspi.h:34
#define TRACE(s)
Definition: solgame.cpp:4
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
GLsizeiptr size
Definition: glext.h:5919
char * peek_msg_mem
Definition: internet.h:79
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
#define SEC_E_OK
Definition: winerror.h:2356
_Check_return_ _CRTIMP int __cdecl __cdecl eof(_In_ int _FileHandle)
ULONG_PTR SIZE_T
Definition: typedefs.h:80
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define SECBUFFER_VERSION
Definition: sspi.h:187
#define ARRAY_SIZE(a)
Definition: main.h:24
#define min(a, b)
Definition: monoChain.cc:55
#define NULL
Definition: types.h:112
SECURITY_STATUS WINAPI DecryptMessage(PCtxtHandle phContext, PSecBufferDesc pMessage, ULONG MessageSeqNo, PULONG pfQOP)
Definition: wrapper.c:1036
static void set_socket_blocking(netconn_t *conn, BOOL is_blocking)
char * peek_msg
Definition: internet.h:78
char * ssl_buf
Definition: internet.h:75
GLuint res
Definition: glext.h:9613
char * extra_buf
Definition: internet.h:76
#define memset(x, y, z)
Definition: compat.h:39
SecPkgContext_StreamSizes ssl_sizes
Definition: internet.h:73
#define SEC_E_INCOMPLETE_MESSAGE
Definition: winerror.h:2934
static BOOL heap_free(void *mem)
Definition: appwiz.h:75

Referenced by NETCON_recv().

◆ send_ssl_chunk()

static BOOL send_ssl_chunk ( netconn_t conn,
const void msg,
size_t  size 
)
static

Definition at line 638 of file netconnection.c.

639 {
640  SecBuffer bufs[4] = {
642  {size, SECBUFFER_DATA, conn->ssl_buf+conn->ssl_sizes.cbHeader},
644  {0, SECBUFFER_EMPTY, NULL}
645  };
648 
649  memcpy(bufs[1].pvBuffer, msg, size);
650  res = EncryptMessage(&conn->ssl_ctx, 0, &buf_desc, 0);
651  if(res != SEC_E_OK) {
652  WARN("EncryptMessage failed\n");
653  return FALSE;
654  }
655 
656  if(sock_send(conn->socket, conn->ssl_buf, bufs[0].cbBuffer+bufs[1].cbBuffer+bufs[2].cbBuffer, 0) < 1) {
657  WARN("send failed\n");
658  return FALSE;
659  }
660 
661  return TRUE;
662 }
CtxtHandle ssl_ctx
Definition: internet.h:72
#define SECBUFFER_STREAM_HEADER
Definition: sspi.h:166
const GLenum * bufs
Definition: glext.h:6026
#define TRUE
Definition: types.h:120
#define WARN(fmt,...)
Definition: debug.h:112
#define SECBUFFER_DATA
Definition: sspi.h:160
int socket
Definition: internet.h:69
#define FALSE
Definition: types.h:117
#define SECBUFFER_EMPTY
Definition: sspi.h:159
int sock_send(int fd, const void *msg, size_t len, int flags)
LONG SECURITY_STATUS
Definition: sspi.h:34
GLsizeiptr size
Definition: glext.h:5919
#define SECBUFFER_STREAM_TRAILER
Definition: sspi.h:165
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
#define SEC_E_OK
Definition: winerror.h:2356
#define SECBUFFER_VERSION
Definition: sspi.h:187
#define ARRAY_SIZE(a)
Definition: main.h:24
#define NULL
Definition: types.h:112
#define msg(x)
Definition: auth_time.c:54
char * ssl_buf
Definition: internet.h:75
GLuint res
Definition: glext.h:9613
SecPkgContext_StreamSizes ssl_sizes
Definition: internet.h:73
SECURITY_STATUS WINAPI EncryptMessage(PCtxtHandle phContext, ULONG fQOP, PSecBufferDesc pMessage, ULONG MessageSeqNo)
Definition: wrapper.c:1006

Referenced by NETCON_send().

◆ set_socket_blocking()

static void set_socket_blocking ( netconn_t conn,
BOOL  is_blocking 
)
static

Definition at line 287 of file netconnection.c.

288 {
289  if(conn->is_blocking != is_blocking) {
290  ULONG arg = !is_blocking;
291  ioctlsocket(conn->socket, FIONBIO, &arg);
292  }
293  conn->is_blocking = is_blocking;
294 }
#define ioctlsocket
Definition: ncftp.h:481
int socket
Definition: internet.h:69
BOOL is_blocking
Definition: internet.h:71
#define FIONBIO
Definition: winsock.h:149
unsigned int ULONG
Definition: retypes.h:1

Referenced by create_netconn_socket(), NETCON_is_alive(), NETCON_recv(), netcon_secure_connect_setup(), NETCON_send(), and read_ssl_chunk().

◆ sock_recv()

int sock_recv ( int  fd,
void msg,
size_t  len,
int  flags 
)

Definition at line 429 of file netconnection.c.

430 {
431  int ret;
432  do
433  {
434  ret = recv(fd, msg, len, flags);
435  }
436  while(ret == -1 && WSAGetLastError() == WSAEINTR);
437  return ret;
438 }
static int fd
Definition: io.c:51
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
GLbitfield flags
Definition: glext.h:7161
int ret
GLenum GLsizei len
Definition: glext.h:6722
#define msg(x)
Definition: auth_time.c:54
INT WSAAPI recv(IN SOCKET s, OUT CHAR FAR *buf, IN INT len, IN INT flags)
Definition: recv.c:23
#define WSAEINTR
Definition: winerror.h:1942

Referenced by NETCON_is_alive(), NETCON_recv(), netcon_secure_connect_setup(), and read_ssl_chunk().

◆ sock_send()

int sock_send ( int  fd,
const void msg,
size_t  len,
int  flags 
)

Definition at line 418 of file netconnection.c.

419 {
420  int ret;
421  do
422  {
423  ret = send(fd, msg, len, flags);
424  }
425  while(ret == -1 && WSAGetLastError() == WSAEINTR);
426  return ret;
427 }
static int fd
Definition: io.c:51
INT WSAAPI WSAGetLastError(VOID)
Definition: dllmain.c:112
INT WSAAPI send(IN SOCKET s, IN CONST CHAR FAR *buf, IN INT len, IN INT flags)
Definition: send.c:23
GLbitfield flags
Definition: glext.h:7161
int ret
GLenum GLsizei len
Definition: glext.h:6722
#define msg(x)
Definition: auth_time.c:54
#define WSAEINTR
Definition: winerror.h:1942

Referenced by netcon_secure_connect_setup(), NETCON_send(), and send_ssl_chunk().

◆ WINE_DEFAULT_DEBUG_CHANNEL()

WINE_DEFAULT_DEBUG_CHANNEL ( wininet  )

◆ winsock_startup()

static BOOL WINAPI winsock_startup ( INIT_ONCE once,
void param,
void **  context 
)
static

Definition at line 268 of file netconnection.c.

269 {
270  WSADATA wsa_data;
271  DWORD res;
272 
273  res = WSAStartup(MAKEWORD(2,2), &wsa_data);
274  if(res == ERROR_SUCCESS)
276  else
277  ERR("WSAStartup failed: %u\n", res);
278  return TRUE;
279 }
#define ERROR_SUCCESS
Definition: deptool.c:10
#define MAKEWORD(a, b)
Definition: typedefs.h:248
#define TRUE
Definition: types.h:120
static BOOL winsock_loaded
INT WINAPI WSAStartup(IN WORD wVersionRequested, OUT LPWSADATA lpWSAData)
Definition: startup.c:113
unsigned long DWORD
Definition: ntddk_ex.h:95
#define ERR(fmt,...)
Definition: debug.h:110
GLuint res
Definition: glext.h:9613

Referenced by init_winsock().

Variable Documentation

◆ compat_cred_handle

SecHandle compat_cred_handle
static

◆ cred_handle

◆ cred_handle_initialized

BOOL cred_handle_initialized
static

Definition at line 220 of file netconnection.c.

Referenced by ensure_cred_handle(), NETCON_unload(), and tcp_disconnect().

◆ have_compat_cred_handle

BOOL have_compat_cred_handle
static

◆ init_sechandle_cs

static CRITICAL_SECTION init_sechandle_cs = { &init_sechandle_cs_debug, -1, 0, 0, 0, 0 }
static

Definition at line 222 of file netconnection.c.

Referenced by ensure_cred_handle(), and NETCON_unload().

◆ init_sechandle_cs_debug

CRITICAL_SECTION_DEBUG init_sechandle_cs_debug
static
Initial value:
= {
0, 0, { (DWORD_PTR)(__FILE__ ": init_sechandle_cs") }
}
#define DWORD_PTR
Definition: treelist.c:76
static CRITICAL_SECTION init_sechandle_cs
static CRITICAL_SECTION_DEBUG init_sechandle_cs_debug
LIST_ENTRY ProcessLocksList
Definition: winbase.h:877

Definition at line 223 of file netconnection.c.

◆ winsock_loaded

BOOL winsock_loaded = FALSE
static

Definition at line 266 of file netconnection.c.

Referenced by NETCON_unload(), and winsock_startup().