Merge branch 'master' of github.com:mrthebunny/FreeRDP

This commit is contained in:
Marc-André Moreau 2013-12-18 21:52:41 -05:00
commit 5e4f77b05f
12 changed files with 187 additions and 55 deletions

View File

@ -916,10 +916,7 @@ void mf_Pointer_New(rdpContext* context, rdpPointer* pointer)
freerdp_alpha_cursor_convert(cursor_data, pointer->xorMaskData, pointer->andMaskData,
pointer->width, pointer->height, pointer->xorBpp, context->gdi->clrconv);
// TODO if xorBpp is > 24 need to call freerdp_image_swap_color_order
// see file df_graphics.c
/* store cursor bitmap image in representation - required by NSImage */
bmiRep = [[NSBitmapImageRep alloc] initWithBitmapDataPlanes:(unsigned char **) &cursor_data
pixelsWide:rect.size.width

View File

@ -195,7 +195,7 @@ void AppDelegate_ConnectionResultEventHandler(void* ctx, ConnectionResultEventAr
NSString* message = nil;
if (connectErrorCode == AUTHENTICATIONERROR)
{
message = [NSString stringWithFormat:@"%@:\n%@", message, @"Authentication failure, check credentials."];
message = [NSString stringWithFormat:@"%@", @"Authentication failure, check credentials."];
}

View File

@ -49,7 +49,7 @@ static WCHAR CR_LF_STR_W[] = { '\r', '\n', '\0' };
#define INVALID_INTEGER_VALUE 0xFFFFFFFF
BOOL freerdp_client_rdp_file_set_integer(rdpFile* file, char* name, int value, int index)
BOOL freerdp_client_rdp_file_set_integer(rdpFile* file, const char* name, int value, int index)
{
BOOL bStandard = TRUE;
@ -229,13 +229,13 @@ void freerdp_client_parse_rdp_file_integer_unicode(rdpFile* file, WCHAR* name, W
free(valueA);
}
void freerdp_client_parse_rdp_file_integer_ascii(rdpFile* file, char* name, char* value, int index)
void freerdp_client_parse_rdp_file_integer_ascii(rdpFile* file, const char* name, const char* value, int index)
{
int ivalue = atoi(value);
freerdp_client_rdp_file_set_integer(file, name, ivalue, index);
}
BOOL freerdp_client_rdp_file_set_string(rdpFile* file, char* name, char* value, int index)
BOOL freerdp_client_rdp_file_set_string(rdpFile* file, const char* name, const char* value, int index)
{
BOOL bStandard = TRUE;
@ -436,8 +436,6 @@ BOOL freerdp_client_parse_rdp_file_buffer_ascii(rdpFile* file, const BYTE* buffe
if ((d2 - d1) != 2)
goto next_line; /* improper type length */
if (d2 == end)
goto next_line; /* no value */
*d1 = 0;
*d2 = 0;
@ -514,8 +512,6 @@ BOOL freerdp_client_parse_rdp_file_buffer_unicode(rdpFile* file, const BYTE* buf
if ((d2 - d1) != 2)
goto next_line; /* improper type length */
if (d2 == end)
goto next_line; /* no value */
*d1 = 0;
*d2 = 0;
@ -881,7 +877,7 @@ BOOL freerdp_client_populate_settings_from_rdp_file(rdpFile* file, rdpSettings*
}
if (~file->PromptCredentialOnce)
freerdp_set_param_bool(settings, FreeRDP_GatewayUseSameCredentials, TRUE);
freerdp_set_param_bool(settings, FreeRDP_GatewayUseSameCredentials, file->PromptCredentialOnce);
if (~file->RemoteApplicationMode)
freerdp_set_param_bool(settings, FreeRDP_RemoteApplicationMode, file->RemoteApplicationMode);
@ -1067,7 +1063,7 @@ int freerdp_client_rdp_file_set_string_option(rdpFile* file, const char* name, c
index = freerdp_client_parse_rdp_file_add_line(file, text, -1);
line = freerdp_client_rdp_file_find_line_index(file, index);
freerdp_client_rdp_file_set_string(file, (char*) name, (char*) value, index);
freerdp_client_rdp_file_set_string(file, name, value, index);
free(text);
}

View File

@ -173,6 +173,7 @@ FREERDP_API extern int connectErrorCode;
#define TLSCONNECTERROR ERRORSTART + 8
#define AUTHENTICATIONERROR ERRORSTART + 9
#define INSUFFICIENTPRIVILEGESERROR ERRORSTART + 10
#define CANCELEDBYUSER ERRORSTART + 11
#ifdef __cplusplus
}

View File

@ -27,6 +27,7 @@
#include <winpr/tchar.h>
#include <winpr/stream.h>
#include <winpr/dsparse.h>
#include <winpr/winhttp.h>
#include <openssl/rand.h>
@ -98,12 +99,15 @@ int rpc_ncacn_http_recv_in_channel_response(rdpRpc* rpc)
http_response = http_response_recv(rpc->TlsIn);
ntlm_token_data = NULL;
crypto_base64_decode((BYTE*) http_response->AuthParam, strlen(http_response->AuthParam),
&ntlm_token_data, &ntlm_token_length);
if (http_response->AuthParam)
{
ntlm_token_data = NULL;
crypto_base64_decode((BYTE*) http_response->AuthParam, strlen(http_response->AuthParam),
&ntlm_token_data, &ntlm_token_length);
ntlm->inputBuffer[0].pvBuffer = ntlm_token_data;
ntlm->inputBuffer[0].cbBuffer = ntlm_token_length;
ntlm->inputBuffer[0].pvBuffer = ntlm_token_data;
ntlm->inputBuffer[0].cbBuffer = ntlm_token_length;
}
http_response_free(http_response);
@ -136,7 +140,10 @@ int rpc_ncacn_http_ntlm_init(rdpRpc* rpc, TSG_CHANNEL channel)
&settings->GatewayUsername, &settings->GatewayPassword, &settings->GatewayDomain);
if (!proceed)
{
connectErrorCode = CANCELEDBYUSER;
return 0;
}
if (settings->GatewayUseSameCredentials)
{
@ -147,40 +154,51 @@ int rpc_ncacn_http_ntlm_init(rdpRpc* rpc, TSG_CHANNEL channel)
}
}
ntlm_client_init(ntlm, TRUE, settings->GatewayUsername,
if (!ntlm_client_init(ntlm, TRUE, settings->GatewayUsername,
settings->GatewayDomain, settings->GatewayPassword,
rpc->TlsIn->Bindings);
rpc->TlsIn->Bindings))
{
return 0;
}
//ntlm_client_make_spn(ntlm, NULL, settings->GatewayHostname);
ntlm_client_make_spn(ntlm, _T("HTTP"), settings->GatewayHostname);
if (!ntlm_client_make_spn(ntlm, _T("HTTP"), settings->GatewayHostname))
{
return 0;
}
return 0;
return 1;
}
BOOL rpc_ntlm_http_in_connect(rdpRpc* rpc)
{
rdpNtlm* ntlm = rpc->NtlmHttpIn->ntlm;
BOOL success = FALSE;
rpc_ncacn_http_ntlm_init(rpc, TSG_CHANNEL_IN);
if (rpc_ncacn_http_ntlm_init(rpc, TSG_CHANNEL_IN) == 1)
{
success = TRUE;
/* Send IN Channel Request */
/* Send IN Channel Request */
rpc_ncacn_http_send_in_channel_request(rpc);
rpc_ncacn_http_send_in_channel_request(rpc);
/* Receive IN Channel Response */
/* Receive IN Channel Response */
rpc_ncacn_http_recv_in_channel_response(rpc);
rpc_ncacn_http_recv_in_channel_response(rpc);
/* Send IN Channel Request */
/* Send IN Channel Request */
rpc_ncacn_http_send_in_channel_request(rpc);
rpc_ncacn_http_send_in_channel_request(rpc);
ntlm_client_uninit(ntlm);
}
ntlm_client_uninit(ntlm);
ntlm_free(ntlm);
rpc->NtlmHttpIn->ntlm = NULL;
return TRUE;
return success;
}
int rpc_ncacn_http_send_out_channel_request(rdpRpc* rpc)
@ -230,25 +248,32 @@ int rpc_ncacn_http_recv_out_channel_response(rdpRpc* rpc)
BOOL rpc_ntlm_http_out_connect(rdpRpc* rpc)
{
rdpNtlm* ntlm = rpc->NtlmHttpOut->ntlm;
BOOL success = FALSE;
rpc_ncacn_http_ntlm_init(rpc, TSG_CHANNEL_OUT);
if (rpc_ncacn_http_ntlm_init(rpc, TSG_CHANNEL_OUT) == 1)
{
success = TRUE;
/* Send OUT Channel Request */
/* Send OUT Channel Request */
rpc_ncacn_http_send_out_channel_request(rpc);
rpc_ncacn_http_send_out_channel_request(rpc);
/* Receive OUT Channel Response */
/* Receive OUT Channel Response */
rpc_ncacn_http_recv_out_channel_response(rpc);
rpc_ncacn_http_recv_out_channel_response(rpc);
/* Send OUT Channel Request */
/* Send OUT Channel Request */
rpc_ncacn_http_send_out_channel_request(rpc);
rpc_ncacn_http_send_out_channel_request(rpc);
ntlm_client_uninit(ntlm);
}
ntlm_client_uninit(ntlm);
ntlm_free(ntlm);
return TRUE;
rpc->NtlmHttpOut->ntlm = NULL;
return success;
}
void rpc_ntlm_http_init_channel(rdpRpc* rpc, rdpNtlmHttp* ntlm_http, TSG_CHANNEL channel)

View File

@ -151,7 +151,7 @@ BOOL ntlm_client_make_spn(rdpNtlm* ntlm, LPCTSTR ServiceClass, char* hostname)
status = DsMakeSpn(ServiceClass, hostnameX, NULL, 0, NULL, &SpnLength, ntlm->ServicePrincipalName);
if (status != ERROR_SUCCESS)
return -1;
return FALSE;
return TRUE;
}
@ -229,7 +229,7 @@ BOOL ntlm_authenticate(rdpNtlm* ntlm)
if ((!ntlm) || (!ntlm->table))
{
fprintf(stderr, "rpc_write: invalid ntlm context\n");
fprintf(stderr, "ntlm_authenticate: invalid ntlm context\n");
return FALSE;
}

View File

@ -118,7 +118,10 @@ int rpc_send_bind_pdu(rdpRpc* rpc)
&settings->GatewayUsername, &settings->GatewayPassword, &settings->GatewayDomain);
if (!proceed)
{
connectErrorCode = CANCELEDBYUSER;
return 0;
}
if (settings->GatewayUseSameCredentials)
{

View File

@ -22,6 +22,7 @@
#endif
#include <winpr/crt.h>
#include <winpr/winhttp.h>
#include "ncacn_http.h"
#include "rpc_client.h"
@ -147,11 +148,17 @@ BOOL rts_connect(rdpRpc* rpc)
http_response = http_response_recv(rpc->TlsOut);
if (http_response->StatusCode != 200)
if (http_response->StatusCode != HTTP_STATUS_OK)
{
fprintf(stderr, "rts_connect error! Status Code: %d\n", http_response->StatusCode);
http_response_print(http_response);
http_response_free(http_response);
if (!connectErrorCode && http_response->StatusCode == HTTP_STATUS_DENIED)
{
connectErrorCode = AUTHENTICATIONERROR;
}
return FALSE;
}

View File

@ -1367,6 +1367,9 @@ BOOL tsg_connect(rdpTsg* tsg, const char* hostname, UINT16 port)
pdu = rpc_recv_dequeue_pdu(rpc);
if (!pdu)
return FALSE;
call = rpc_client_call_find_by_id(rpc, pdu->CallId);
if (call->OpNum == TsProxyMakeTunnelCallOpnum)
@ -1409,6 +1412,9 @@ BOOL tsg_connect(rdpTsg* tsg, const char* hostname, UINT16 port)
#if 0
pdu = rpc_recv_dequeue_pdu(rpc);
if (!pdu)
return FALSE;
if (!TsProxySetupReceivePipeReadResponse(tsg, pdu))
{
fprintf(stderr, "TsProxySetupReceivePipe: error reading response\n");

View File

@ -147,7 +147,11 @@ int credssp_ntlm_client_init(rdpCredssp* credssp)
&settings->Username, &settings->Password, &settings->Domain);
if (!proceed)
{
connectErrorCode = CANCELEDBYUSER;
return 0;
}
}
}

View File

@ -248,8 +248,6 @@ rdpSettings* freerdp_settings_new(DWORD flags)
settings->DisableThemes = FALSE;
settings->ConnectionType = CONNECTION_TYPE_LAN;
settings->AutoReconnectionEnabled = TRUE;
settings->EncryptionMethods = ENCRYPTION_METHOD_NONE;
settings->EncryptionLevel = ENCRYPTION_LEVEL_NONE;
@ -380,7 +378,7 @@ rdpSettings* freerdp_settings_new(DWORD flags)
settings->MultifragMaxRequestSize = 0xFFFF;
settings->GatewayUseSameCredentials = TRUE;
settings->GatewayUseSameCredentials = FALSE;
settings->FastPathInput = TRUE;
settings->FastPathOutput = TRUE;

View File

@ -168,7 +168,10 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
PVOID Object;
if (!winpr_Handle_GetInfo(hHandle, &Type, &Object))
{
fprintf(stderr, "WaitForSingleObject failed: invalid hHandle.\n");
return WAIT_FAILED;
}
if (Type == HANDLE_TYPE_THREAD)
{
@ -218,6 +221,7 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if (waitpid(process->pid, &(process->status), 0) != -1)
{
fprintf(stderr, "WaitForSingleObject: waitpid failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
@ -260,14 +264,18 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if ((dwMilliseconds != INFINITE) && (dwMilliseconds != 0))
{
timeout.tv_usec = dwMilliseconds * 1000;
timeout.tv_sec = dwMilliseconds / 1000;
timeout.tv_usec = (dwMilliseconds % 1000) * 1000;
}
status = select(event->pipe_fd[0] + 1, &rfds, NULL, NULL,
(dwMilliseconds == INFINITE) ? NULL : &timeout);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: event select() failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
if (status != 1)
return WAIT_TIMEOUT;
@ -292,14 +300,18 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if ((dwMilliseconds != INFINITE) && (dwMilliseconds != 0))
{
timeout.tv_usec = dwMilliseconds * 1000;
timeout.tv_sec = dwMilliseconds / 1000;
timeout.tv_usec = (dwMilliseconds % 1000) * 1000;
}
status = select(semaphore->pipe_fd[0] + 1, &rfds, 0, 0,
(dwMilliseconds == INFINITE) ? NULL : &timeout);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: semaphore select() failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
if (status != 1)
return WAIT_TIMEOUT;
@ -307,7 +319,10 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
length = read(semaphore->pipe_fd[0], &length, 1);
if (length != 1)
{
fprintf(stderr, "WaitForSingleObject: semaphore read failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
}
#else
@ -339,28 +354,49 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if ((dwMilliseconds != INFINITE) && (dwMilliseconds != 0))
{
timeout.tv_usec = dwMilliseconds * 1000;
timeout.tv_sec = dwMilliseconds / 1000;
timeout.tv_usec = (dwMilliseconds % 1000) * 1000;
}
status = select(timer->fd + 1, &rfds, 0, 0,
(dwMilliseconds == INFINITE) ? NULL : &timeout);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: timer select() failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
if (status != 1)
return WAIT_TIMEOUT;
status = read(timer->fd, (void*) &expirations, sizeof(UINT64));
length = read(timer->fd, (void*) &expirations, sizeof(UINT64));
if (status != 8)
return WAIT_TIMEOUT;
if (length != 8)
{
if (length == -1)
{
if (errno == ETIMEDOUT)
return WAIT_TIMEOUT;
fprintf(stderr, "WaitForSingleObject: timer read() failure [%d] %s\n", errno, strerror(errno));
}
else
{
fprintf(stderr, "WaitForSingleObject: timer read() failure - incorrect number of bytes read");
}
return WAIT_FAILED;
}
}
else
{
fprintf(stderr, "WaitForSingleObject: invalid timer file descriptor\n");
return WAIT_FAILED;
}
#else
fprintf(stderr, "WaitForSingleObject: file descriptors not supported\n");
return WAIT_FAILED;
#endif
}
@ -375,7 +411,11 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
fd = (pipe->ServerMode) ? pipe->serverfd : pipe->clientfd;
if (fd == -1)
{
fprintf(stderr, "WaitForSingleObject: invalid pipe file descriptor\n");
return WAIT_FAILED;
}
FD_ZERO(&rfds);
FD_SET(fd, &rfds);
@ -383,17 +423,23 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if ((dwMilliseconds != INFINITE) && (dwMilliseconds != 0))
{
timeout.tv_usec = dwMilliseconds * 1000;
timeout.tv_sec = dwMilliseconds / 1000;
timeout.tv_usec = (dwMilliseconds % 1000) * 1000;
}
status = select(fd + 1, &rfds, NULL, NULL,
(dwMilliseconds == INFINITE) ? NULL : &timeout);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: named pipe select() failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
if (status != 1)
{
return WAIT_TIMEOUT;
}
}
else
{
@ -422,7 +468,11 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
struct timeval timeout;
if (!nCount)
{
fprintf(stderr, "WaitForMultipleObjects: invalid handles count\n");
return WAIT_FAILED;
}
maxfd = 0;
FD_ZERO(&fds);
@ -437,17 +487,27 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
for (index = 0; index < nCount; index++)
{
if (!winpr_Handle_GetInfo(lpHandles[index], &Type, &Object))
{
fprintf(stderr, "WaitForMultipleObjects: invalid handle\n");
return WAIT_FAILED;
}
if (Type == HANDLE_TYPE_EVENT)
{
fd = ((WINPR_EVENT*) Object)->pipe_fd[0];
if (fd == -1)
{
fprintf(stderr, "WaitForMultipleObjects: invalid event file descriptor\n");
return WAIT_FAILED;
}
}
else if (Type == HANDLE_TYPE_SEMAPHORE)
{
#ifdef WINPR_PIPE_SEMAPHORE
fd = ((WINPR_SEMAPHORE*) Object)->pipe_fd[0];
#else
fprintf(stderr, "WaitForMultipleObjects: semaphore not supported\n");
return WAIT_FAILED;
#endif
}
@ -455,6 +515,12 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
{
WINPR_TIMER* timer = (WINPR_TIMER*) Object;
fd = timer->fd;
if (fd == -1)
{
fprintf(stderr, "WaitForMultipleObjects: invalid timer file descriptor\n");
return WAIT_FAILED;
}
}
else if (Type == HANDLE_TYPE_NAMED_PIPE)
{
@ -462,15 +528,22 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
fd = (pipe->ServerMode) ? pipe->serverfd : pipe->clientfd;
if (fd == -1)
{
fprintf(stderr, "WaitForMultipleObjects: invalid timer file descriptor\n");
return WAIT_FAILED;
}
}
else
{
fprintf(stderr, "WaitForMultipleObjects: unknown handle type %lu\n", Type);
return WAIT_FAILED;
}
if (fd == -1)
{
fprintf(stderr, "WaitForMultipleObjects: invalid file descriptor\n");
return WAIT_FAILED;
}
FD_SET(fd, &fds);
@ -480,14 +553,18 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
if ((dwMilliseconds != INFINITE) && (dwMilliseconds != 0))
{
timeout.tv_usec = dwMilliseconds * 1000;
timeout.tv_sec = dwMilliseconds / 1000;
timeout.tv_usec = (dwMilliseconds % 1000) * 1000;
}
status = select(maxfd + 1, &fds, 0, 0,
(dwMilliseconds == INFINITE) ? NULL : &timeout);
if (status < 0)
{
fprintf(stderr, "WaitForMultipleObjects: select() failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
if (status == 0)
return WAIT_TIMEOUT;
@ -524,7 +601,10 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
length = read(fd, &length, 1);
if (length != 1)
{
fprintf(stderr, "WaitForMultipleObjects: semaphore read() failure [%d] %s\n", errno, strerror(errno));
return WAIT_FAILED;
}
}
else if (Type == HANDLE_TYPE_TIMER)
{
@ -534,13 +614,28 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
length = read(fd, (void*) &expirations, sizeof(UINT64));
if (length != 8)
{
if (length == -1)
{
if (errno == ETIMEDOUT)
return WAIT_TIMEOUT;
fprintf(stderr, "WaitForMultipleObjects: timer read() failure [%d] %s\n", errno, strerror(errno));
}
else
{
fprintf(stderr, "WaitForMultipleObjects: timer read() failure - incorrect number of bytes read");
}
return WAIT_FAILED;
}
}
return (WAIT_OBJECT_0 + index);
}
}
fprintf(stderr, "WaitForMultipleObjects: failed (unknown error)\n");
return WAIT_FAILED;
}