Merge remote-tracking branch 'upstream/master' into mh-stream-fix
Conflicts: client/Windows/wf_cliprdr.c
This commit is contained in:
commit
6e4e1c2773
@ -26,6 +26,10 @@ if(NOT DEFINED VENDOR)
|
||||
set(VENDOR "FreeRDP" CACHE STRING "FreeRDP package vendor")
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED PRODUCT)
|
||||
set(PRODUCT "FreeRDP" CACHE STRING "FreeRDP package name")
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED FREERDP_VENDOR)
|
||||
set(FREERDP_VENDOR 1)
|
||||
endif()
|
||||
@ -284,8 +288,8 @@ if(WIN32)
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DWIN32_LEAN_AND_MEAN")
|
||||
|
||||
# Set product and vendor for dll and exe version information.
|
||||
set(RC_VERSION_VENDOR "FreeRDP")
|
||||
set(RC_VERSION_PRODUCT "FreeRDP")
|
||||
set(RC_VERSION_VENDOR ${VENDOR})
|
||||
set(RC_VERSION_PRODUCT ${PRODUCT})
|
||||
set(RC_VERSION_PATCH ${BUILD_NUMBER})
|
||||
set(RC_VERSION_DESCRIPTION ${GIT_REVISION})
|
||||
|
||||
|
@ -1080,7 +1080,7 @@ static WIN32ERROR cliprdr_virtual_channel_event_disconnected(cliprdrPlugin* clip
|
||||
{
|
||||
UINT rc;
|
||||
|
||||
MessageQueue_PostQuit(cliprdr->queue, 0);
|
||||
if (MessageQueue_PostQuit(cliprdr->queue, 0))
|
||||
WaitForSingleObject(cliprdr->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(cliprdr->queue);
|
||||
|
@ -1305,7 +1305,7 @@ static WIN32ERROR drdynvc_virtual_channel_event_disconnected(drdynvcPlugin* drdy
|
||||
{
|
||||
WIN32ERROR status;
|
||||
|
||||
MessageQueue_PostQuit(drdynvc->queue, 0);
|
||||
if (MessageQueue_PostQuit(drdynvc->queue, 0))
|
||||
WaitForSingleObject(drdynvc->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(drdynvc->queue);
|
||||
|
@ -658,7 +658,7 @@ static void drive_free(DEVICE* device)
|
||||
{
|
||||
DRIVE_DEVICE* drive = (DRIVE_DEVICE*) device;
|
||||
|
||||
MessageQueue_PostQuit(drive->IrpQueue, 0);
|
||||
if (MessageQueue_PostQuit(drive->IrpQueue, 0))
|
||||
WaitForSingleObject(drive->thread, INFINITE);
|
||||
|
||||
CloseHandle(drive->thread);
|
||||
|
@ -1092,7 +1092,8 @@ static WIN32ERROR encomsp_virtual_channel_event_connected(encomspPlugin* encomsp
|
||||
static WIN32ERROR encomsp_virtual_channel_event_disconnected(encomspPlugin* encomsp)
|
||||
{
|
||||
UINT rc;
|
||||
MessageQueue_PostQuit(encomsp->queue, 0);
|
||||
|
||||
if (MessageQueue_PostQuit(encomsp->queue, 0))
|
||||
WaitForSingleObject(encomsp->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(encomsp->queue);
|
||||
|
@ -328,7 +328,7 @@ static void parallel_free(DEVICE* device)
|
||||
{
|
||||
PARALLEL_DEVICE* parallel = (PARALLEL_DEVICE*) device;
|
||||
|
||||
MessageQueue_PostQuit(parallel->queue, 0);
|
||||
if (MessageQueue_PostQuit(parallel->queue, 0))
|
||||
WaitForSingleObject(parallel->thread, INFINITE);
|
||||
CloseHandle(parallel->thread);
|
||||
|
||||
|
@ -586,7 +586,7 @@ static WIN32ERROR rail_virtual_channel_event_connected(railPlugin* rail, LPVOID
|
||||
static void rail_virtual_channel_event_disconnected(railPlugin* rail)
|
||||
{
|
||||
UINT rc;
|
||||
MessageQueue_PostQuit(rail->queue, 0);
|
||||
if (MessageQueue_PostQuit(rail->queue, 0))
|
||||
WaitForSingleObject(rail->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(rail->queue);
|
||||
|
@ -1206,7 +1206,7 @@ static WIN32ERROR rdpdr_virtual_channel_event_disconnected(rdpdrPlugin* rdpdr)
|
||||
{
|
||||
WIN32ERROR error;
|
||||
|
||||
MessageQueue_PostQuit(rdpdr->queue, 0);
|
||||
if (MessageQueue_PostQuit(rdpdr->queue, 0))
|
||||
WaitForSingleObject(rdpdr->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(rdpdr->queue);
|
||||
|
@ -745,7 +745,7 @@ static void remdesk_virtual_channel_event_disconnected(remdeskPlugin* remdesk)
|
||||
{
|
||||
UINT rc;
|
||||
|
||||
MessageQueue_PostQuit(remdesk->queue, 0);
|
||||
if (MessageQueue_PostQuit(remdesk->queue, 0))
|
||||
WaitForSingleObject(remdesk->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(remdesk->queue);
|
||||
|
@ -111,7 +111,7 @@ void smartcard_context_free(SMARTCARD_CONTEXT* pContext)
|
||||
/* cancel blocking calls like SCardGetStatusChange */
|
||||
SCardCancel(pContext->hContext);
|
||||
|
||||
MessageQueue_PostQuit(pContext->IrpQueue, 0);
|
||||
if (MessageQueue_PostQuit(pContext->IrpQueue, 0))
|
||||
WaitForSingleObject(pContext->thread, INFINITE);
|
||||
CloseHandle(pContext->thread);
|
||||
|
||||
@ -126,7 +126,7 @@ static void smartcard_free(DEVICE* device)
|
||||
|
||||
if (smartcard->IrpQueue)
|
||||
{
|
||||
MessageQueue_PostQuit(smartcard->IrpQueue, 0);
|
||||
if (MessageQueue_PostQuit(smartcard->IrpQueue, 0))
|
||||
WaitForSingleObject(smartcard->thread, INFINITE);
|
||||
|
||||
MessageQueue_Free(smartcard->IrpQueue);
|
||||
|
@ -607,7 +607,7 @@ disconnect:
|
||||
wMessageQueue* input_queue = freerdp_get_message_queue(instance, FREERDP_INPUT_MESSAGE_QUEUE);
|
||||
if (input_queue)
|
||||
{
|
||||
MessageQueue_PostQuit(input_queue, 0);
|
||||
if (MessageQueue_PostQuit(input_queue, 0))
|
||||
WaitForSingleObject(input_thread, INFINITE);
|
||||
}
|
||||
CloseHandle(input_thread);
|
||||
|
@ -779,7 +779,7 @@ DWORD WINAPI wf_client_thread(LPVOID lpParam)
|
||||
{
|
||||
wMessageQueue* input_queue;
|
||||
input_queue = freerdp_get_message_queue(instance, FREERDP_INPUT_MESSAGE_QUEUE);
|
||||
MessageQueue_PostQuit(input_queue, 0);
|
||||
if (MessageQueue_PostQuit(input_queue, 0))
|
||||
WaitForSingleObject(input_thread, INFINITE);
|
||||
CloseHandle(input_thread);
|
||||
}
|
||||
|
@ -107,14 +107,14 @@ HRESULT STDMETHODCALLTYPE CliprdrStream_Read(IStream* This, void *pv, ULONG cb,
|
||||
*pcbRead = 0;
|
||||
|
||||
if (instance->m_lOffset.QuadPart >= instance->m_lSize.QuadPart)
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
|
||||
ret = cliprdr_send_request_filecontents(clipboard, (void*) This,
|
||||
instance->m_lIndex, FILECONTENTS_RANGE,
|
||||
instance->m_lOffset.HighPart, instance->m_lOffset.LowPart, cb);
|
||||
|
||||
if (ret < 0)
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
|
||||
if (clipboard->req_fdata)
|
||||
{
|
||||
@ -126,7 +126,7 @@ HRESULT STDMETHODCALLTYPE CliprdrStream_Read(IStream* This, void *pv, ULONG cb,
|
||||
instance->m_lOffset.QuadPart += clipboard->req_fsize;
|
||||
|
||||
if (clipboard->req_fsize < cb)
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
@ -157,11 +157,11 @@ HRESULT STDMETHODCALLTYPE CliprdrStream_Seek(IStream* This, LARGE_INTEGER dlibMo
|
||||
newoffset = instance->m_lSize.QuadPart + dlibMove.QuadPart;
|
||||
break;
|
||||
default:
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (newoffset < 0 || newoffset >= instance->m_lSize.QuadPart)
|
||||
return FALSE;
|
||||
return E_FAIL;
|
||||
|
||||
instance->m_lOffset.QuadPart = newoffset;
|
||||
|
||||
@ -739,7 +739,7 @@ HRESULT STDMETHODCALLTYPE CliprdrEnumFORMATETC_Next(IEnumFORMATETC* This, ULONG
|
||||
if (pceltFetched != 0)
|
||||
*pceltFetched = copied;
|
||||
|
||||
return (copied == celt) ? S_OK : S_FALSE;
|
||||
return (copied == celt) ? S_OK : E_FAIL;
|
||||
}
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CliprdrEnumFORMATETC_Skip(IEnumFORMATETC* This, ULONG celt)
|
||||
@ -747,7 +747,7 @@ HRESULT STDMETHODCALLTYPE CliprdrEnumFORMATETC_Skip(IEnumFORMATETC* This, ULONG
|
||||
CliprdrEnumFORMATETC* instance = (CliprdrEnumFORMATETC*) This;
|
||||
|
||||
if (instance->m_nIndex + (LONG) celt > instance->m_nNumFormats)
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
|
||||
instance->m_nIndex += celt;
|
||||
|
||||
@ -1579,7 +1579,7 @@ static WIN32ERROR wf_cliprdr_server_format_data_request(CliprdrClientContext* co
|
||||
|
||||
result = OleGetClipboard(&dataObj);
|
||||
|
||||
if (!SUCCEEDED(result))
|
||||
if (FAILED(result))
|
||||
return ERROR_INTERNAL_ERROR;
|
||||
|
||||
ZeroMemory(&format_etc, sizeof(FORMATETC));
|
||||
@ -1618,7 +1618,7 @@ static WIN32ERROR wf_cliprdr_server_format_data_request(CliprdrClientContext* co
|
||||
|
||||
result = IDataObject_GetData(dataObj, &format_etc, &stg_medium);
|
||||
|
||||
if (!SUCCEEDED(result)) {
|
||||
if (FAILED(result)) {
|
||||
DEBUG_CLIPRDR("dataObj->GetData failed.");
|
||||
}
|
||||
|
||||
@ -1785,7 +1785,7 @@ WIN32ERROR wf_cliprdr_server_file_contents_request(CliprdrClientContext* context
|
||||
|
||||
hRet = OleGetClipboard(&pDataObj);
|
||||
|
||||
if (!SUCCEEDED(hRet))
|
||||
if (FAILED(hRet))
|
||||
{
|
||||
WLog_ERR(TAG, "filecontents: get ole clipboard failed.");
|
||||
goto error;
|
||||
|
@ -1093,9 +1093,11 @@ BOOL xf_post_connect(freerdp* instance)
|
||||
|
||||
gdi = context->gdi;
|
||||
xfc->primary_buffer = gdi->primary_buffer;
|
||||
xfc->palette = gdi->palette;
|
||||
}
|
||||
else
|
||||
{
|
||||
xfc->palette = xfc->palette_hwgdi;
|
||||
xfc->srcBpp = settings->ColorDepth;
|
||||
xf_gdi_register_update_callbacks(update);
|
||||
}
|
||||
@ -1532,7 +1534,7 @@ void* xf_client_thread(void* param)
|
||||
if (settings->AsyncInput)
|
||||
{
|
||||
wMessageQueue* inputQueue = freerdp_get_message_queue(instance, FREERDP_INPUT_MESSAGE_QUEUE);
|
||||
MessageQueue_PostQuit(inputQueue, 0);
|
||||
if (MessageQueue_PostQuit(inputQueue, 0))
|
||||
WaitForSingleObject(inputThread, INFINITE);
|
||||
CloseHandle(inputThread);
|
||||
}
|
||||
|
@ -470,6 +470,7 @@ static BOOL xf_rail_window_common(rdpContext* context, WINDOW_ORDER_INFO* orderI
|
||||
|
||||
if (fieldFlags & WINDOW_ORDER_FIELD_TITLE)
|
||||
{
|
||||
if (appWindow->title)
|
||||
xf_SetWindowText(xfc, appWindow, appWindow->title);
|
||||
}
|
||||
|
||||
|
@ -127,7 +127,8 @@ struct xf_context
|
||||
HANDLE mutex;
|
||||
BOOL UseXThreads;
|
||||
BOOL cursorHidden;
|
||||
BYTE palette[256 * 4];
|
||||
BYTE* palette;
|
||||
BYTE palette_hwgdi[256 * 4];
|
||||
|
||||
HGDI_DC hdc;
|
||||
UINT32 bitmap_size;
|
||||
|
@ -14,6 +14,9 @@
|
||||
#define CMAKE_SHARED_LIBRARY_SUFFIX "${CMAKE_SHARED_LIBRARY_SUFFIX}"
|
||||
#define CMAKE_SHARED_LIBRARY_PREFIX "${CMAKE_SHARED_LIBRARY_PREFIX}"
|
||||
|
||||
#define FREERDP_VENDOR_STRING "${VENDOR}"
|
||||
#define FREERDP_PRODUCT_STRING "${PRODUCT}"
|
||||
|
||||
/* Include files */
|
||||
#cmakedefine HAVE_FCNTL_H
|
||||
#cmakedefine HAVE_UNISTD_H
|
||||
|
@ -42,6 +42,13 @@ struct _H264_CONTEXT_SUBSYSTEM
|
||||
};
|
||||
typedef struct _H264_CONTEXT_SUBSYSTEM H264_CONTEXT_SUBSYSTEM;
|
||||
|
||||
enum _H264_RATECONTROL_MODE
|
||||
{
|
||||
H264_RATECONTROL_VBR = 0,
|
||||
H264_RATECONTROL_CQP
|
||||
};
|
||||
typedef enum _H264_RATECONTROL_MODE H264_RATECONTROL_MODE;
|
||||
|
||||
struct _H264_CONTEXT
|
||||
{
|
||||
BOOL Compressor;
|
||||
@ -49,8 +56,10 @@ struct _H264_CONTEXT
|
||||
UINT32 width;
|
||||
UINT32 height;
|
||||
|
||||
H264_RATECONTROL_MODE RateControlMode;
|
||||
UINT32 BitRate;
|
||||
FLOAT FrameRate;
|
||||
UINT32 QP;
|
||||
UINT32 NumberOfThreads;
|
||||
|
||||
int iStride[3];
|
||||
|
@ -35,14 +35,17 @@ typedef struct rdp_certificate_store rdpCertificateStore;
|
||||
struct rdp_certificate_data
|
||||
{
|
||||
char* hostname;
|
||||
UINT16 port;
|
||||
char* subject;
|
||||
char* issuer;
|
||||
char* fingerprint;
|
||||
};
|
||||
|
||||
struct rdp_certificate_store
|
||||
{
|
||||
FILE* fp;
|
||||
char* path;
|
||||
char* file;
|
||||
char* legacy_file;
|
||||
rdpSettings* settings;
|
||||
rdpCertificateData* certificate_data;
|
||||
};
|
||||
@ -51,13 +54,29 @@ struct rdp_certificate_store
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
FREERDP_API rdpCertificateData* certificate_data_new(char* hostname, char* fingerprint);
|
||||
FREERDP_API void certificate_data_free(rdpCertificateData* certificate_data);
|
||||
FREERDP_API rdpCertificateStore* certificate_store_new(rdpSettings* settings);
|
||||
FREERDP_API void certificate_data_replace(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data);
|
||||
FREERDP_API void certificate_store_free(rdpCertificateStore* certificate_store);
|
||||
FREERDP_API int certificate_data_match(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data);
|
||||
FREERDP_API void certificate_data_print(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data);
|
||||
FREERDP_API rdpCertificateData* certificate_data_new(
|
||||
char* hostname, UINT16 port, char*subject,
|
||||
char*issuer, char* fingerprint);
|
||||
FREERDP_API void certificate_data_free(
|
||||
rdpCertificateData* certificate_data);
|
||||
FREERDP_API rdpCertificateStore* certificate_store_new(
|
||||
rdpSettings* settings);
|
||||
FREERDP_API BOOL certificate_data_replace(
|
||||
rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data);
|
||||
FREERDP_API void certificate_store_free(
|
||||
rdpCertificateStore* certificate_store);
|
||||
FREERDP_API int certificate_data_match(
|
||||
rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data);
|
||||
FREERDP_API BOOL certificate_data_print(
|
||||
rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data);
|
||||
FREERDP_API BOOL certificate_get_stored_data(
|
||||
rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data,
|
||||
char** subject, char** issuer,
|
||||
char** fingerprint);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
@ -133,7 +133,7 @@ FREERDP_API void crypto_cert_print_info(X509* xcert);
|
||||
FREERDP_API void crypto_cert_free(CryptoCert cert);
|
||||
|
||||
FREERDP_API BOOL x509_verify_certificate(CryptoCert cert, char* certificate_store_path);
|
||||
FREERDP_API rdpCertificateData* crypto_get_certificate_data(X509* xcert, char* hostname);
|
||||
FREERDP_API rdpCertificateData* crypto_get_certificate_data(X509* xcert, char* hostname, UINT16 port);
|
||||
FREERDP_API BOOL crypto_cert_get_public_key(CryptoCert cert, BYTE** PublicKey, DWORD* PublicKeyLength);
|
||||
|
||||
#define TSSK_KEY_LENGTH 64
|
||||
|
@ -98,8 +98,11 @@ FREERDP_API int tls_set_alert_code(rdpTls* tls, int level, int description);
|
||||
|
||||
FREERDP_API BOOL tls_match_hostname(char *pattern, int pattern_length, char *hostname);
|
||||
FREERDP_API int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int port);
|
||||
FREERDP_API void tls_print_certificate_error(char* hostname, char* fingerprint, char* hosts_file);
|
||||
FREERDP_API void tls_print_certificate_name_mismatch_error(char* hostname, char* common_name, char** alt_names, int alt_names_count);
|
||||
FREERDP_API void tls_print_certificate_error(char* hostname, UINT16 port,
|
||||
char* fingerprint, char* hosts_file);
|
||||
FREERDP_API void tls_print_certificate_name_mismatch_error(
|
||||
char* hostname, UINT16 port, char* common_name, char** alt_names,
|
||||
int alt_names_count);
|
||||
|
||||
FREERDP_API BOOL tls_print_error(char* func, SSL* connection, int value);
|
||||
|
||||
|
@ -67,7 +67,10 @@ typedef BOOL (*pPostConnect)(freerdp* instance);
|
||||
typedef void (*pPostDisconnect)(freerdp* instance);
|
||||
typedef BOOL (*pAuthenticate)(freerdp* instance, char** username, char** password, char** domain);
|
||||
typedef BOOL (*pVerifyCertificate)(freerdp* instance, char* subject, char* issuer, char* fingerprint);
|
||||
typedef BOOL (*pVerifyChangedCertificate)(freerdp* instance, char* subject, char* issuer, char* new_fingerprint, char* old_fingerprint);
|
||||
typedef BOOL (*pVerifyChangedCertificate)(freerdp* instance, char* subject,
|
||||
char* issuer, char* new_fingerprint,
|
||||
char* old_subject, char* old_issuer,
|
||||
char* old_fingerprint);
|
||||
typedef int (*pVerifyX509Certificate)(freerdp* instance, BYTE* data, int length, const char* hostname, int port, DWORD flags);
|
||||
|
||||
typedef int (*pLogonErrorInfo)(freerdp* instance, UINT32 data, UINT32 type);
|
||||
|
@ -1512,12 +1512,19 @@ int freerdp_image_copy_from_pointer_data(BYTE* pDstData, UINT32 DstFormat, int n
|
||||
|
||||
return 1;
|
||||
}
|
||||
else if (xorBpp == 24 || xorBpp == 32)
|
||||
else if (xorBpp == 24 || xorBpp == 32 || xorBpp == 16 || xorBpp == 8)
|
||||
{
|
||||
int xorBytesPerPixel = xorBpp >> 3;
|
||||
xorStep = nWidth * xorBytesPerPixel;
|
||||
pDstPixel = (UINT32*) &pDstData[(nYDst * nDstStep) + (nXDst * 4)];
|
||||
|
||||
if (xorBpp == 8 && !palette)
|
||||
{
|
||||
WLog_ERR(TAG, "null palette in convertion from %d bpp to %d bpp",
|
||||
xorBpp, dstBitsPerPixel);
|
||||
return -1;
|
||||
}
|
||||
|
||||
for (y = 0; y < nHeight; y++)
|
||||
{
|
||||
andBit = 0x80;
|
||||
@ -1536,9 +1543,23 @@ int freerdp_image_copy_from_pointer_data(BYTE* pDstData, UINT32 DstFormat, int n
|
||||
for (x = 0; x < nWidth; x++)
|
||||
{
|
||||
if (xorBpp == 32)
|
||||
{
|
||||
xorPixel = *((UINT32*) xorBits);
|
||||
}
|
||||
else if (xorBpp == 16)
|
||||
{
|
||||
UINT16 r, g, b;
|
||||
GetRGB16(r, g, b, *(UINT16*)xorBits);
|
||||
xorPixel = ARGB32(0xFF, r, g, b);
|
||||
}
|
||||
else if (xorBpp == 8)
|
||||
{
|
||||
xorPixel = 0xFF << 24 | ((UINT32*)palette)[xorBits[0]];
|
||||
}
|
||||
else
|
||||
{
|
||||
xorPixel = xorBits[0] | xorBits[1] << 8 | xorBits[2] << 16 | 0xFF << 24;
|
||||
}
|
||||
|
||||
xorBits += xorBytesPerPixel;
|
||||
|
||||
|
@ -179,8 +179,6 @@ static int openh264_compress(H264_CONTEXT* h264, BYTE** ppDstData, UINT32* pDstS
|
||||
sys->EncParamExt.iUsageType = SCREEN_CONTENT_REAL_TIME;
|
||||
sys->EncParamExt.iPicWidth = h264->width;
|
||||
sys->EncParamExt.iPicHeight = h264->height;
|
||||
sys->EncParamExt.iTargetBitrate = h264->BitRate;
|
||||
sys->EncParamExt.iRCMode = RC_BITRATE_MODE;
|
||||
sys->EncParamExt.fMaxFrameRate = h264->FrameRate;
|
||||
sys->EncParamExt.iMaxBitrate = UNSPECIFIED_BIT_RATE;
|
||||
sys->EncParamExt.bEnableDenoise = 0;
|
||||
@ -191,8 +189,19 @@ static int openh264_compress(H264_CONTEXT* h264, BYTE** ppDstData, UINT32* pDstS
|
||||
sys->EncParamExt.sSpatialLayers[0].fFrameRate = h264->FrameRate;
|
||||
sys->EncParamExt.sSpatialLayers[0].iVideoWidth = sys->EncParamExt.iPicWidth;
|
||||
sys->EncParamExt.sSpatialLayers[0].iVideoHeight = sys->EncParamExt.iPicHeight;
|
||||
sys->EncParamExt.sSpatialLayers[0].iSpatialBitrate = sys->EncParamExt.iTargetBitrate;
|
||||
sys->EncParamExt.sSpatialLayers[0].iMaxSpatialBitrate = sys->EncParamExt.iMaxBitrate;
|
||||
switch (h264->RateControlMode)
|
||||
{
|
||||
case H264_RATECONTROL_VBR:
|
||||
sys->EncParamExt.iRCMode = RC_BITRATE_MODE;
|
||||
sys->EncParamExt.iTargetBitrate = h264->BitRate;
|
||||
sys->EncParamExt.sSpatialLayers[0].iSpatialBitrate = sys->EncParamExt.iTargetBitrate;
|
||||
break;
|
||||
case H264_RATECONTROL_CQP:
|
||||
sys->EncParamExt.iRCMode = RC_OFF_MODE;
|
||||
sys->EncParamExt.sSpatialLayers[0].iDLayerQp = h264->QP;
|
||||
break;
|
||||
}
|
||||
|
||||
if (sys->EncParamExt.iMultipleThreadIdc > 1)
|
||||
{
|
||||
@ -206,9 +215,21 @@ static int openh264_compress(H264_CONTEXT* h264, BYTE** ppDstData, UINT32* pDstS
|
||||
WLog_ERR(TAG, "Failed to initialize OpenH264 encoder (status=%ld)", status);
|
||||
return status;
|
||||
}
|
||||
|
||||
status = (*sys->pEncoder)->GetOption(sys->pEncoder, ENCODER_OPTION_SVC_ENCODE_PARAM_EXT,
|
||||
&sys->EncParamExt);
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to get initial OpenH264 encoder parameters (status=%ld)", status);
|
||||
return status;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
switch (h264->RateControlMode)
|
||||
{
|
||||
case H264_RATECONTROL_VBR:
|
||||
if (sys->EncParamExt.iTargetBitrate != h264->BitRate)
|
||||
{
|
||||
sys->EncParamExt.iTargetBitrate = h264->BitRate;
|
||||
@ -237,6 +258,23 @@ static int openh264_compress(H264_CONTEXT* h264, BYTE** ppDstData, UINT32* pDstS
|
||||
return status;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case H264_RATECONTROL_CQP:
|
||||
if (sys->EncParamExt.sSpatialLayers[0].iDLayerQp != h264->QP)
|
||||
{
|
||||
sys->EncParamExt.sSpatialLayers[0].iDLayerQp = h264->QP;
|
||||
|
||||
status = (*sys->pEncoder)->SetOption(sys->pEncoder, ENCODER_OPTION_SVC_ENCODE_PARAM_EXT,
|
||||
&sys->EncParamExt);
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to set encoder parameters (status=%ld)", status);
|
||||
return status;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
memset(&info, 0, sizeof(SFrameBSInfo));
|
||||
|
@ -161,7 +161,12 @@ int freerdp_assistance_parse_address_list(rdpAssistanceFile* file, char* list)
|
||||
file->MachinePorts = (UINT32*) calloc(count, sizeof(UINT32));
|
||||
|
||||
if (!file->MachineAddresses || !file->MachinePorts)
|
||||
{
|
||||
free(file->MachineAddresses);
|
||||
free(file->MachinePorts);
|
||||
free(tokens);
|
||||
return -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
|
@ -73,7 +73,7 @@ static BOOL autodetect_send_rtt_measure_request(rdpContext* context, UINT16 sequ
|
||||
Stream_Write_UINT16(s, sequenceNumber); /* sequenceNumber (2 bytes) */
|
||||
Stream_Write_UINT16(s, requestType); /* requestType (2 bytes) */
|
||||
|
||||
context->rdp->autodetect->rttMeasureStartTime = GetTickCount();
|
||||
context->rdp->autodetect->rttMeasureStartTime = GetTickCountPrecise();
|
||||
|
||||
return rdp_send_message_channel_pdu(context->rdp, s, SEC_AUTODETECT_REQ);
|
||||
}
|
||||
@ -257,7 +257,7 @@ static BOOL autodetect_send_bandwidth_measure_results(rdpRdp* rdp, UINT16 respon
|
||||
UINT32 timeDelta;
|
||||
|
||||
/* Compute the total time */
|
||||
timeDelta = GetTickCount() - rdp->autodetect->bandwidthMeasureStartTime;
|
||||
timeDelta = GetTickCountPrecise() - rdp->autodetect->bandwidthMeasureStartTime;
|
||||
|
||||
/* Send the result PDU to the server */
|
||||
|
||||
@ -361,7 +361,7 @@ static BOOL autodetect_recv_rtt_measure_response(rdpRdp* rdp, wStream* s, AUTODE
|
||||
|
||||
WLog_VRB(AUTODETECT_TAG, "received RTT Measure Response PDU");
|
||||
|
||||
rdp->autodetect->netCharAverageRTT = GetTickCount() - rdp->autodetect->rttMeasureStartTime;
|
||||
rdp->autodetect->netCharAverageRTT = GetTickCountPrecise() - rdp->autodetect->rttMeasureStartTime;
|
||||
if (rdp->autodetect->netCharBaseRTT == 0 || rdp->autodetect->netCharBaseRTT > rdp->autodetect->netCharAverageRTT)
|
||||
rdp->autodetect->netCharBaseRTT = rdp->autodetect->netCharAverageRTT;
|
||||
|
||||
@ -375,10 +375,10 @@ static BOOL autodetect_recv_bandwidth_measure_start(rdpRdp* rdp, wStream* s, AUT
|
||||
if (autodetectReqPdu->headerLength != 0x06)
|
||||
return FALSE;
|
||||
|
||||
WLog_VRB(AUTODETECT_TAG, "received Bandwidth Measure Start PDU - time=%lu", GetTickCount());
|
||||
WLog_VRB(AUTODETECT_TAG, "received Bandwidth Measure Start PDU - time=%lu", GetTickCountPrecise());
|
||||
|
||||
/* Initialize bandwidth measurement parameters */
|
||||
rdp->autodetect->bandwidthMeasureStartTime = GetTickCount();
|
||||
rdp->autodetect->bandwidthMeasureStartTime = GetTickCountPrecise();
|
||||
rdp->autodetect->bandwidthMeasureByteCount = 0;
|
||||
|
||||
/* Continuous Auto-Detection: mark the start of the measurement */
|
||||
|
@ -376,7 +376,6 @@ void rdp_write_bitmap_capability_set(wStream* s, rdpSettings* settings)
|
||||
{
|
||||
int header;
|
||||
BYTE drawingFlags = 0;
|
||||
UINT16 desktopResizeFlag;
|
||||
UINT16 preferredBitsPerPixel;
|
||||
|
||||
Stream_EnsureRemainingCapacity(s, 64);
|
||||
@ -406,7 +405,6 @@ void rdp_write_bitmap_capability_set(wStream* s, rdpSettings* settings)
|
||||
else
|
||||
preferredBitsPerPixel = 8;
|
||||
|
||||
desktopResizeFlag = settings->DesktopResize;
|
||||
|
||||
Stream_Write_UINT16(s, preferredBitsPerPixel); /* preferredBitsPerPixel (2 bytes) */
|
||||
Stream_Write_UINT16(s, 1); /* receive1BitPerPixel (2 bytes) */
|
||||
@ -415,7 +413,7 @@ void rdp_write_bitmap_capability_set(wStream* s, rdpSettings* settings)
|
||||
Stream_Write_UINT16(s, settings->DesktopWidth); /* desktopWidth (2 bytes) */
|
||||
Stream_Write_UINT16(s, settings->DesktopHeight); /* desktopHeight (2 bytes) */
|
||||
Stream_Write_UINT16(s, 0); /* pad2Octets (2 bytes) */
|
||||
Stream_Write_UINT16(s, desktopResizeFlag); /* desktopResizeFlag (2 bytes) */
|
||||
Stream_Write_UINT16(s, settings->DesktopResize); /* desktopResizeFlag (2 bytes) */
|
||||
Stream_Write_UINT16(s, 1); /* bitmapCompressionFlag (2 bytes) */
|
||||
Stream_Write_UINT8(s, 0); /* highColorFlags (1 byte) */
|
||||
Stream_Write_UINT8(s, drawingFlags); /* drawingFlags (1 byte) */
|
||||
|
@ -666,7 +666,8 @@ UINT VCAPITYPE FreeRDP_VirtualChannelWrite(DWORD openHandle, LPVOID pData, ULONG
|
||||
pChannelOpenEvent->UserData = pUserData;
|
||||
pChannelOpenEvent->pChannelOpenData = pChannelOpenData;
|
||||
|
||||
MessageQueue_Post(channels->queue, (void*) channels, 0, (void*) pChannelOpenEvent, NULL);
|
||||
if (!MessageQueue_Post(channels->queue, (void*) channels, 0, (void*) pChannelOpenEvent, NULL))
|
||||
return CHANNEL_RC_NO_MEMORY;
|
||||
|
||||
return CHANNEL_RC_OK;
|
||||
}
|
||||
|
@ -43,7 +43,7 @@ BOOL ntlm_client_init(rdpNtlm* ntlm, BOOL http, char* user, char* domain, char*
|
||||
ntlm->http = http;
|
||||
ntlm->Bindings = Bindings;
|
||||
|
||||
ntlm->table = InitSecurityInterfaceEx(SSPI_INTERFACE_WINPR);
|
||||
ntlm->table = InitSecurityInterface();
|
||||
|
||||
if (!ntlm->table)
|
||||
return FALSE;
|
||||
|
@ -323,6 +323,7 @@ wStream* rdg_build_http_request(rdpRdg* rdg, char* method)
|
||||
s = http_request_write(rdg->http, request);
|
||||
http_request_free(request);
|
||||
|
||||
if (s)
|
||||
Stream_SealLength(s);
|
||||
return s;
|
||||
}
|
||||
@ -435,9 +436,7 @@ BOOL rdg_process_in_channel_response(rdpRdg* rdg, HttpResponse* response)
|
||||
s = rdg_build_http_request(rdg, "RDG_IN_DATA");
|
||||
|
||||
if (!s)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
status = tls_write_all(rdg->tlsIn, Stream_Buffer(s), Stream_Length(s));
|
||||
|
||||
@ -489,13 +488,16 @@ BOOL rdg_process_handshake_response(rdpRdg* rdg, wStream* s)
|
||||
{
|
||||
HRESULT errorCode;
|
||||
|
||||
WLog_DBG(TAG, "Handshake response recieved");
|
||||
WLog_DBG(TAG, "Handshake response received");
|
||||
|
||||
if (rdg->state != RDG_CLIENT_STATE_HANDSHAKE)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (Stream_GetRemainingLength(s) < 12)
|
||||
return FALSE;
|
||||
|
||||
Stream_Seek(s, 8);
|
||||
Stream_Read_UINT32(s, errorCode);
|
||||
|
||||
@ -519,6 +521,9 @@ BOOL rdg_process_tunnel_response(rdpRdg* rdg, wStream* s)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (Stream_GetRemainingLength(s) < 14)
|
||||
return FALSE;
|
||||
|
||||
Stream_Seek(s, 10);
|
||||
Stream_Read_UINT32(s, errorCode);
|
||||
|
||||
@ -542,6 +547,9 @@ BOOL rdg_process_tunnel_authorization_response(rdpRdg* rdg, wStream* s)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (Stream_GetRemainingLength(s) < 12)
|
||||
return FALSE;
|
||||
|
||||
Stream_Seek(s, 8);
|
||||
Stream_Read_UINT32(s, errorCode);
|
||||
|
||||
@ -565,6 +573,9 @@ BOOL rdg_process_channel_response(rdpRdg* rdg, wStream* s)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (Stream_GetRemainingLength(s) < 12)
|
||||
return FALSE;
|
||||
|
||||
Stream_Seek(s, 8);
|
||||
Stream_Read_UINT32(s, errorCode);
|
||||
|
||||
@ -585,8 +596,11 @@ BOOL rdg_process_packet(rdpRdg* rdg, wStream* s)
|
||||
UINT16 type;
|
||||
|
||||
Stream_SetPosition(s, 0);
|
||||
Stream_Read_UINT16(s, type);
|
||||
Stream_SetPosition(s, 0);
|
||||
|
||||
if (Stream_GetRemainingLength(s) < 2)
|
||||
return FALSE;
|
||||
|
||||
Stream_Peek_UINT16(s, type);
|
||||
|
||||
switch (type)
|
||||
{
|
||||
|
@ -321,7 +321,8 @@ int rpc_client_recv_fragment(rdpRpc* rpc, wStream* fragment)
|
||||
|
||||
if (rpc->VirtualConnection->DefaultOutChannel->ReceiverAvailableWindow < (rpc->ReceiveWindow / 2))
|
||||
{
|
||||
rts_send_flow_control_ack_pdu(rpc);
|
||||
if (rts_send_flow_control_ack_pdu(rpc) < 0)
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!rpc_get_stub_data_info(rpc, buffer, &StubOffset, &StubLength))
|
||||
@ -412,7 +413,8 @@ int rpc_client_recv_fragment(rdpRpc* rpc, wStream* fragment)
|
||||
return -1;
|
||||
Stream_Write(pdu->s, buffer, Stream_Length(fragment));
|
||||
Stream_SealLength(pdu->s);
|
||||
rpc_client_recv_pdu(rpc, pdu);
|
||||
if (rpc_client_recv_pdu(rpc, pdu) < 0)
|
||||
return -1;
|
||||
rpc_pdu_reset(pdu);
|
||||
}
|
||||
else
|
||||
@ -420,7 +422,8 @@ int rpc_client_recv_fragment(rdpRpc* rpc, wStream* fragment)
|
||||
if (rpc->VirtualConnection->State < VIRTUAL_CONNECTION_STATE_OPENED)
|
||||
WLog_ERR(TAG, "warning: unhandled RTS PDU");
|
||||
|
||||
rts_recv_out_of_sequence_pdu(rpc, buffer, header->common.frag_length);
|
||||
if (rts_recv_out_of_sequence_pdu(rpc, buffer, header->common.frag_length) < 0)
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 1;
|
||||
@ -434,7 +437,8 @@ int rpc_client_recv_fragment(rdpRpc* rpc, wStream* fragment)
|
||||
return -1;
|
||||
Stream_Write(pdu->s, buffer, Stream_Length(fragment));
|
||||
Stream_SealLength(pdu->s);
|
||||
rpc_client_recv_pdu(rpc, pdu);
|
||||
if (rpc_client_recv_pdu(rpc, pdu) < 0)
|
||||
return -1;
|
||||
rpc_pdu_reset(pdu);
|
||||
|
||||
return 1;
|
||||
|
@ -41,17 +41,14 @@
|
||||
|
||||
static BOOL update_message_BeginPaint(rdpContext* context)
|
||||
{
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, BeginPaint), NULL, NULL);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_EndPaint(rdpContext* context)
|
||||
{
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, EndPaint), NULL, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SetBounds(rdpContext* context, rdpBounds* bounds)
|
||||
@ -66,23 +63,20 @@ static BOOL update_message_SetBounds(rdpContext* context, rdpBounds* bounds)
|
||||
CopyMemory(wParam, bounds, sizeof(rdpBounds));
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SetBounds), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_Synchronize(rdpContext* context)
|
||||
{
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, Synchronize), NULL, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DesktopResize(rdpContext* context)
|
||||
{
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, DesktopResize), NULL, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_BitmapUpdate(rdpContext* context, BITMAP_UPDATE* bitmap)
|
||||
@ -125,10 +119,9 @@ static BOOL update_message_BitmapUpdate(rdpContext* context, BITMAP_UPDATE* bitm
|
||||
wParam->rectangles[index].bitmapLength);
|
||||
#endif
|
||||
}
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, BitmapUpdate), (void*) wParam, NULL);
|
||||
|
||||
return TRUE;
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, BitmapUpdate), (void*) wParam, NULL);
|
||||
}
|
||||
|
||||
static BOOL update_message_Palette(rdpContext* context, PALETTE_UPDATE* palette)
|
||||
@ -140,9 +133,8 @@ static BOOL update_message_Palette(rdpContext* context, PALETTE_UPDATE* palette)
|
||||
return FALSE;
|
||||
CopyMemory(wParam, palette, sizeof(PALETTE_UPDATE));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, Palette), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_PlaySound(rdpContext* context, PLAY_SOUND_UPDATE* playSound)
|
||||
@ -154,16 +146,14 @@ static BOOL update_message_PlaySound(rdpContext* context, PLAY_SOUND_UPDATE* pla
|
||||
return FALSE;
|
||||
CopyMemory(wParam, playSound, sizeof(PLAY_SOUND_UPDATE));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, PlaySound), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SetKeyboardIndicators(rdpContext* context, UINT16 led_flags)
|
||||
{
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SetKeyboardIndicators), (void*)(size_t)led_flags, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_RefreshRect(rdpContext* context, BYTE count, RECTANGLE_16* areas)
|
||||
@ -175,9 +165,8 @@ static BOOL update_message_RefreshRect(rdpContext* context, BYTE count, RECTANGL
|
||||
return FALSE;
|
||||
CopyMemory(lParam, areas, sizeof(RECTANGLE_16) * count);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, RefreshRect), (void*) (size_t) count, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SuppressOutput(rdpContext* context, BYTE allow, RECTANGLE_16* area)
|
||||
@ -192,9 +181,8 @@ static BOOL update_message_SuppressOutput(rdpContext* context, BYTE allow, RECTA
|
||||
CopyMemory(lParam, area, sizeof(RECTANGLE_16));
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SuppressOutput), (void*) (size_t) allow, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SurfaceCommand(rdpContext* context, wStream* s)
|
||||
@ -215,9 +203,8 @@ static BOOL update_message_SurfaceCommand(rdpContext* context, wStream* s)
|
||||
|
||||
wParam->pointer = wParam->buffer;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SurfaceCommand), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SurfaceBits(rdpContext* context, SURFACE_BITS_COMMAND* surfaceBitsCommand)
|
||||
@ -241,9 +228,8 @@ static BOOL update_message_SurfaceBits(rdpContext* context, SURFACE_BITS_COMMAND
|
||||
CopyMemory(wParam->bitmapData, surfaceBitsCommand->bitmapData, wParam->bitmapDataLength);
|
||||
#endif
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SurfaceBits), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SurfaceFrameMarker(rdpContext* context, SURFACE_FRAME_MARKER* surfaceFrameMarker)
|
||||
@ -255,18 +241,14 @@ static BOOL update_message_SurfaceFrameMarker(rdpContext* context, SURFACE_FRAME
|
||||
return FALSE;
|
||||
CopyMemory(wParam, surfaceFrameMarker, sizeof(SURFACE_FRAME_MARKER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SurfaceFrameMarker), (void*) wParam, NULL);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SurfaceFrameAcknowledge(rdpContext* context, UINT32 frameId)
|
||||
{
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(Update, SurfaceFrameAcknowledge), (void*) (size_t) frameId, NULL);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Primary Update */
|
||||
@ -280,9 +262,8 @@ static BOOL update_message_DstBlt(rdpContext* context, DSTBLT_ORDER* dstBlt)
|
||||
return FALSE;
|
||||
CopyMemory(wParam, dstBlt, sizeof(DSTBLT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, DstBlt), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_PatBlt(rdpContext* context, PATBLT_ORDER* patBlt)
|
||||
@ -296,9 +277,8 @@ static BOOL update_message_PatBlt(rdpContext* context, PATBLT_ORDER* patBlt)
|
||||
|
||||
wParam->brush.data = (BYTE*) wParam->brush.p8x8;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, PatBlt), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_ScrBlt(rdpContext* context, SCRBLT_ORDER* scrBlt)
|
||||
@ -310,10 +290,8 @@ static BOOL update_message_ScrBlt(rdpContext* context, SCRBLT_ORDER* scrBlt)
|
||||
return FALSE;
|
||||
CopyMemory(wParam, scrBlt, sizeof(SCRBLT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, ScrBlt), (void*) wParam, NULL);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_OpaqueRect(rdpContext* context, OPAQUE_RECT_ORDER* opaqueRect)
|
||||
@ -325,9 +303,8 @@ static BOOL update_message_OpaqueRect(rdpContext* context, OPAQUE_RECT_ORDER* op
|
||||
return FALSE;
|
||||
CopyMemory(wParam, opaqueRect, sizeof(OPAQUE_RECT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, OpaqueRect), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawNineGrid(rdpContext* context, DRAW_NINE_GRID_ORDER* drawNineGrid)
|
||||
@ -339,9 +316,8 @@ static BOOL update_message_DrawNineGrid(rdpContext* context, DRAW_NINE_GRID_ORDE
|
||||
return FALSE;
|
||||
CopyMemory(wParam, drawNineGrid, sizeof(DRAW_NINE_GRID_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, DrawNineGrid), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MultiDstBlt(rdpContext* context, MULTI_DSTBLT_ORDER* multiDstBlt)
|
||||
@ -353,9 +329,8 @@ static BOOL update_message_MultiDstBlt(rdpContext* context, MULTI_DSTBLT_ORDER*
|
||||
return FALSE;
|
||||
CopyMemory(wParam, multiDstBlt, sizeof(MULTI_DSTBLT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, MultiDstBlt), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MultiPatBlt(rdpContext* context, MULTI_PATBLT_ORDER* multiPatBlt)
|
||||
@ -369,9 +344,8 @@ static BOOL update_message_MultiPatBlt(rdpContext* context, MULTI_PATBLT_ORDER*
|
||||
|
||||
wParam->brush.data = (BYTE*) wParam->brush.p8x8;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, MultiPatBlt), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MultiScrBlt(rdpContext* context, MULTI_SCRBLT_ORDER* multiScrBlt)
|
||||
@ -383,9 +357,8 @@ static BOOL update_message_MultiScrBlt(rdpContext* context, MULTI_SCRBLT_ORDER*
|
||||
return FALSE;
|
||||
CopyMemory(wParam, multiScrBlt, sizeof(MULTI_SCRBLT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, MultiScrBlt), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MultiOpaqueRect(rdpContext* context, MULTI_OPAQUE_RECT_ORDER* multiOpaqueRect)
|
||||
@ -397,9 +370,8 @@ static BOOL update_message_MultiOpaqueRect(rdpContext* context, MULTI_OPAQUE_REC
|
||||
return FALSE;
|
||||
CopyMemory(wParam, multiOpaqueRect, sizeof(MULTI_OPAQUE_RECT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, MultiOpaqueRect), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MultiDrawNineGrid(rdpContext* context, MULTI_DRAW_NINE_GRID_ORDER* multiDrawNineGrid)
|
||||
@ -413,9 +385,8 @@ static BOOL update_message_MultiDrawNineGrid(rdpContext* context, MULTI_DRAW_NIN
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, MultiDrawNineGrid), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_LineTo(rdpContext* context, LINE_TO_ORDER* lineTo)
|
||||
@ -427,9 +398,8 @@ static BOOL update_message_LineTo(rdpContext* context, LINE_TO_ORDER* lineTo)
|
||||
return FALSE;
|
||||
CopyMemory(wParam, lineTo, sizeof(LINE_TO_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, LineTo), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_Polyline(rdpContext* context, POLYLINE_ORDER* polyline)
|
||||
@ -449,9 +419,8 @@ static BOOL update_message_Polyline(rdpContext* context, POLYLINE_ORDER* polylin
|
||||
}
|
||||
CopyMemory(wParam->points, polyline->points, sizeof(DELTA_POINT) * wParam->numDeltaEntries);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, Polyline), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MemBlt(rdpContext* context, MEMBLT_ORDER* memBlt)
|
||||
@ -463,10 +432,8 @@ static BOOL update_message_MemBlt(rdpContext* context, MEMBLT_ORDER* memBlt)
|
||||
return FALSE;
|
||||
CopyMemory(wParam, memBlt, sizeof(MEMBLT_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, MemBlt), (void*) wParam, NULL);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_Mem3Blt(rdpContext* context, MEM3BLT_ORDER* mem3Blt)
|
||||
@ -480,9 +447,8 @@ static BOOL update_message_Mem3Blt(rdpContext* context, MEM3BLT_ORDER* mem3Blt)
|
||||
|
||||
wParam->brush.data = (BYTE*) wParam->brush.p8x8;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, Mem3Blt), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SaveBitmap(rdpContext* context, SAVE_BITMAP_ORDER* saveBitmap)
|
||||
@ -494,9 +460,8 @@ static BOOL update_message_SaveBitmap(rdpContext* context, SAVE_BITMAP_ORDER* sa
|
||||
return FALSE;
|
||||
CopyMemory(wParam, saveBitmap, sizeof(SAVE_BITMAP_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, SaveBitmap), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_GlyphIndex(rdpContext* context, GLYPH_INDEX_ORDER* glyphIndex)
|
||||
@ -510,9 +475,8 @@ static BOOL update_message_GlyphIndex(rdpContext* context, GLYPH_INDEX_ORDER* gl
|
||||
|
||||
wParam->brush.data = (BYTE*) wParam->brush.p8x8;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, GlyphIndex), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_FastIndex(rdpContext* context, FAST_INDEX_ORDER* fastIndex)
|
||||
@ -524,9 +488,8 @@ static BOOL update_message_FastIndex(rdpContext* context, FAST_INDEX_ORDER* fast
|
||||
return FALSE;
|
||||
CopyMemory(wParam, fastIndex, sizeof(FAST_INDEX_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, FastIndex), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_FastGlyph(rdpContext* context, FAST_GLYPH_ORDER* fastGlyph)
|
||||
@ -553,9 +516,8 @@ static BOOL update_message_FastGlyph(rdpContext* context, FAST_GLYPH_ORDER* fast
|
||||
wParam->glyphData.aj = NULL;
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, FastGlyph), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_PolygonSC(rdpContext* context, POLYGON_SC_ORDER* polygonSC)
|
||||
@ -575,9 +537,8 @@ static BOOL update_message_PolygonSC(rdpContext* context, POLYGON_SC_ORDER* poly
|
||||
}
|
||||
CopyMemory(wParam->points, polygonSC, sizeof(DELTA_POINT) * wParam->numPoints);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, PolygonSC), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_PolygonCB(rdpContext* context, POLYGON_CB_ORDER* polygonCB)
|
||||
@ -599,9 +560,8 @@ static BOOL update_message_PolygonCB(rdpContext* context, POLYGON_CB_ORDER* poly
|
||||
|
||||
wParam->brush.data = (BYTE*) wParam->brush.p8x8;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, PolygonCB), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_EllipseSC(rdpContext* context, ELLIPSE_SC_ORDER* ellipseSC)
|
||||
@ -613,9 +573,8 @@ static BOOL update_message_EllipseSC(rdpContext* context, ELLIPSE_SC_ORDER* elli
|
||||
return FALSE;
|
||||
CopyMemory(wParam, ellipseSC, sizeof(ELLIPSE_SC_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, EllipseSC), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_EllipseCB(rdpContext* context, ELLIPSE_CB_ORDER* ellipseCB)
|
||||
@ -629,9 +588,8 @@ static BOOL update_message_EllipseCB(rdpContext* context, ELLIPSE_CB_ORDER* elli
|
||||
|
||||
wParam->brush.data = (BYTE*) wParam->brush.p8x8;
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PrimaryUpdate, EllipseCB), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Secondary Update */
|
||||
@ -653,9 +611,8 @@ static BOOL update_message_CacheBitmap(rdpContext* context, CACHE_BITMAP_ORDER*
|
||||
}
|
||||
CopyMemory(wParam->bitmapDataStream, cacheBitmapOrder, wParam->bitmapLength);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheBitmap), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CacheBitmapV2(rdpContext* context, CACHE_BITMAP_V2_ORDER* cacheBitmapV2Order)
|
||||
@ -675,9 +632,8 @@ static BOOL update_message_CacheBitmapV2(rdpContext* context, CACHE_BITMAP_V2_OR
|
||||
}
|
||||
CopyMemory(wParam->bitmapDataStream, cacheBitmapV2Order->bitmapDataStream, wParam->bitmapLength);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheBitmapV2), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CacheBitmapV3(rdpContext* context, CACHE_BITMAP_V3_ORDER* cacheBitmapV3Order)
|
||||
@ -697,9 +653,8 @@ static BOOL update_message_CacheBitmapV3(rdpContext* context, CACHE_BITMAP_V3_OR
|
||||
}
|
||||
CopyMemory(wParam->bitmapData.data, cacheBitmapV3Order->bitmapData.data, wParam->bitmapData.length);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheBitmapV3), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CacheColorTable(rdpContext* context, CACHE_COLOR_TABLE_ORDER* cacheColorTableOrder)
|
||||
@ -711,9 +666,8 @@ static BOOL update_message_CacheColorTable(rdpContext* context, CACHE_COLOR_TABL
|
||||
return FALSE;
|
||||
CopyMemory(wParam, cacheColorTableOrder, sizeof(CACHE_COLOR_TABLE_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheColorTable), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CacheGlyph(rdpContext* context, CACHE_GLYPH_ORDER* cacheGlyphOrder)
|
||||
@ -725,9 +679,8 @@ static BOOL update_message_CacheGlyph(rdpContext* context, CACHE_GLYPH_ORDER* ca
|
||||
return FALSE;
|
||||
CopyMemory(wParam, cacheGlyphOrder, sizeof(CACHE_GLYPH_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheGlyph), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CacheGlyphV2(rdpContext* context, CACHE_GLYPH_V2_ORDER* cacheGlyphV2Order)
|
||||
@ -739,9 +692,8 @@ static BOOL update_message_CacheGlyphV2(rdpContext* context, CACHE_GLYPH_V2_ORDE
|
||||
return FALSE;
|
||||
CopyMemory(wParam, cacheGlyphV2Order, sizeof(CACHE_GLYPH_V2_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheGlyphV2), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CacheBrush(rdpContext* context, CACHE_BRUSH_ORDER* cacheBrushOrder)
|
||||
@ -753,9 +705,8 @@ static BOOL update_message_CacheBrush(rdpContext* context, CACHE_BRUSH_ORDER* ca
|
||||
return FALSE;
|
||||
CopyMemory(wParam, cacheBrushOrder, sizeof(CACHE_BRUSH_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(SecondaryUpdate, CacheBrush), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Alternate Secondary Update */
|
||||
@ -779,9 +730,8 @@ static BOOL update_message_CreateOffscreenBitmap(rdpContext* context, CREATE_OFF
|
||||
}
|
||||
CopyMemory(wParam->deleteList.indices, createOffscreenBitmap->deleteList.indices, wParam->deleteList.cIndices);
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, CreateOffscreenBitmap), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_SwitchSurface(rdpContext* context, SWITCH_SURFACE_ORDER* switchSurface)
|
||||
@ -793,9 +743,8 @@ static BOOL update_message_SwitchSurface(rdpContext* context, SWITCH_SURFACE_ORD
|
||||
return FALSE;
|
||||
CopyMemory(wParam, switchSurface, sizeof(SWITCH_SURFACE_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, SwitchSurface), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_CreateNineGridBitmap(rdpContext* context, CREATE_NINE_GRID_BITMAP_ORDER* createNineGridBitmap)
|
||||
@ -807,9 +756,8 @@ static BOOL update_message_CreateNineGridBitmap(rdpContext* context, CREATE_NINE
|
||||
return FALSE;
|
||||
CopyMemory(wParam, createNineGridBitmap, sizeof(CREATE_NINE_GRID_BITMAP_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, CreateNineGridBitmap), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_FrameMarker(rdpContext* context, FRAME_MARKER_ORDER* frameMarker)
|
||||
@ -821,9 +769,8 @@ static BOOL update_message_FrameMarker(rdpContext* context, FRAME_MARKER_ORDER*
|
||||
return FALSE;
|
||||
CopyMemory(wParam, frameMarker, sizeof(FRAME_MARKER_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, FrameMarker), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_StreamBitmapFirst(rdpContext* context, STREAM_BITMAP_FIRST_ORDER* streamBitmapFirst)
|
||||
@ -837,9 +784,8 @@ static BOOL update_message_StreamBitmapFirst(rdpContext* context, STREAM_BITMAP_
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, StreamBitmapFirst), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_StreamBitmapNext(rdpContext* context, STREAM_BITMAP_NEXT_ORDER* streamBitmapNext)
|
||||
@ -853,9 +799,8 @@ static BOOL update_message_StreamBitmapNext(rdpContext* context, STREAM_BITMAP_N
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, StreamBitmapNext), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawGdiPlusFirst(rdpContext* context, DRAW_GDIPLUS_FIRST_ORDER* drawGdiPlusFirst)
|
||||
@ -869,9 +814,8 @@ static BOOL update_message_DrawGdiPlusFirst(rdpContext* context, DRAW_GDIPLUS_FI
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, DrawGdiPlusFirst), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawGdiPlusNext(rdpContext* context, DRAW_GDIPLUS_NEXT_ORDER* drawGdiPlusNext)
|
||||
@ -885,9 +829,8 @@ static BOOL update_message_DrawGdiPlusNext(rdpContext* context, DRAW_GDIPLUS_NEX
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, DrawGdiPlusNext), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawGdiPlusEnd(rdpContext* context, DRAW_GDIPLUS_END_ORDER* drawGdiPlusEnd)
|
||||
@ -901,9 +844,8 @@ static BOOL update_message_DrawGdiPlusEnd(rdpContext* context, DRAW_GDIPLUS_END_
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, DrawGdiPlusEnd), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawGdiPlusCacheFirst(rdpContext* context, DRAW_GDIPLUS_CACHE_FIRST_ORDER* drawGdiPlusCacheFirst)
|
||||
@ -917,9 +859,8 @@ static BOOL update_message_DrawGdiPlusCacheFirst(rdpContext* context, DRAW_GDIPL
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, DrawGdiPlusCacheFirst), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawGdiPlusCacheNext(rdpContext* context, DRAW_GDIPLUS_CACHE_NEXT_ORDER* drawGdiPlusCacheNext)
|
||||
@ -933,9 +874,8 @@ static BOOL update_message_DrawGdiPlusCacheNext(rdpContext* context, DRAW_GDIPLU
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, DrawGdiPlusCacheNext), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_DrawGdiPlusCacheEnd(rdpContext* context, DRAW_GDIPLUS_CACHE_END_ORDER* drawGdiPlusCacheEnd)
|
||||
@ -949,9 +889,8 @@ static BOOL update_message_DrawGdiPlusCacheEnd(rdpContext* context, DRAW_GDIPLUS
|
||||
|
||||
/* TODO: complete copy */
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(AltSecUpdate, DrawGdiPlusCacheEnd), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Window Update */
|
||||
@ -974,9 +913,8 @@ static BOOL update_message_WindowCreate(rdpContext* context, WINDOW_ORDER_INFO*
|
||||
}
|
||||
CopyMemory(lParam, windowState, sizeof(WINDOW_STATE_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, WindowCreate), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_WindowUpdate(rdpContext* context, WINDOW_ORDER_INFO* orderInfo, WINDOW_STATE_ORDER* windowState)
|
||||
@ -997,9 +935,8 @@ static BOOL update_message_WindowUpdate(rdpContext* context, WINDOW_ORDER_INFO*
|
||||
}
|
||||
CopyMemory(lParam, windowState, sizeof(WINDOW_STATE_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, WindowUpdate), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_WindowIcon(rdpContext* context, WINDOW_ORDER_INFO* orderInfo, WINDOW_ICON_ORDER* windowIcon)
|
||||
@ -1046,9 +983,8 @@ static BOOL update_message_WindowIcon(rdpContext* context, WINDOW_ORDER_INFO* or
|
||||
CopyMemory(lParam->iconInfo->colorTable, windowIcon->iconInfo->colorTable, windowIcon->iconInfo->cbColorTable);
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, WindowIcon), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
|
||||
out_fail:
|
||||
free(lParam->iconInfo->bitsColor);
|
||||
@ -1078,9 +1014,8 @@ static BOOL update_message_WindowCachedIcon(rdpContext* context, WINDOW_ORDER_IN
|
||||
}
|
||||
CopyMemory(lParam, windowCachedIcon, sizeof(WINDOW_CACHED_ICON_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, WindowCachedIcon), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_WindowDelete(rdpContext* context, WINDOW_ORDER_INFO* orderInfo)
|
||||
@ -1092,9 +1027,8 @@ static BOOL update_message_WindowDelete(rdpContext* context, WINDOW_ORDER_INFO*
|
||||
return FALSE;
|
||||
CopyMemory(wParam, orderInfo, sizeof(WINDOW_ORDER_INFO));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, WindowDelete), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_NotifyIconCreate(rdpContext* context, WINDOW_ORDER_INFO* orderInfo, NOTIFY_ICON_STATE_ORDER* notifyIconState)
|
||||
@ -1115,9 +1049,8 @@ static BOOL update_message_NotifyIconCreate(rdpContext* context, WINDOW_ORDER_IN
|
||||
}
|
||||
CopyMemory(lParam, notifyIconState, sizeof(NOTIFY_ICON_STATE_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, NotifyIconCreate), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_NotifyIconUpdate(rdpContext* context, WINDOW_ORDER_INFO* orderInfo, NOTIFY_ICON_STATE_ORDER* notifyIconState)
|
||||
@ -1138,9 +1071,8 @@ static BOOL update_message_NotifyIconUpdate(rdpContext* context, WINDOW_ORDER_IN
|
||||
}
|
||||
CopyMemory(lParam, notifyIconState, sizeof(NOTIFY_ICON_STATE_ORDER));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, NotifyIconUpdate), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_NotifyIconDelete(rdpContext* context, WINDOW_ORDER_INFO* orderInfo)
|
||||
@ -1152,9 +1084,8 @@ static BOOL update_message_NotifyIconDelete(rdpContext* context, WINDOW_ORDER_IN
|
||||
return FALSE;
|
||||
CopyMemory(wParam, orderInfo, sizeof(WINDOW_ORDER_INFO));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, NotifyIconDelete), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_MonitoredDesktop(rdpContext* context, WINDOW_ORDER_INFO* orderInfo, MONITORED_DESKTOP_ORDER* monitoredDesktop)
|
||||
@ -1183,9 +1114,8 @@ static BOOL update_message_MonitoredDesktop(rdpContext* context, WINDOW_ORDER_IN
|
||||
CopyMemory(lParam->windowIds, monitoredDesktop->windowIds, lParam->numWindowIds);
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, MonitoredDesktop), (void*) wParam, (void*) lParam);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_NonMonitoredDesktop(rdpContext* context, WINDOW_ORDER_INFO* orderInfo)
|
||||
@ -1197,9 +1127,8 @@ static BOOL update_message_NonMonitoredDesktop(rdpContext* context, WINDOW_ORDER
|
||||
return FALSE;
|
||||
CopyMemory(wParam, orderInfo, sizeof(WINDOW_ORDER_INFO));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(WindowUpdate, NonMonitoredDesktop), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Pointer Update */
|
||||
@ -1213,9 +1142,8 @@ static BOOL update_message_PointerPosition(rdpContext* context, POINTER_POSITION
|
||||
return FALSE;
|
||||
CopyMemory(wParam, pointerPosition, sizeof(POINTER_POSITION_UPDATE));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PointerUpdate, PointerPosition), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_PointerSystem(rdpContext* context, POINTER_SYSTEM_UPDATE* pointerSystem)
|
||||
@ -1227,9 +1155,8 @@ static BOOL update_message_PointerSystem(rdpContext* context, POINTER_SYSTEM_UPD
|
||||
return FALSE;
|
||||
CopyMemory(wParam, pointerSystem, sizeof(POINTER_SYSTEM_UPDATE));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PointerUpdate, PointerSystem), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL update_message_PointerColor(rdpContext* context, POINTER_COLOR_UPDATE* pointerColor)
|
||||
@ -1259,9 +1186,8 @@ static BOOL update_message_PointerColor(rdpContext* context, POINTER_COLOR_UPDAT
|
||||
CopyMemory(wParam->xorMaskData, pointerColor->xorMaskData, wParam->lengthXorMask);
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PointerUpdate, PointerColor), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
|
||||
out_fail:
|
||||
free(wParam->andMaskData);
|
||||
@ -1297,9 +1223,8 @@ static BOOL update_message_PointerNew(rdpContext* context, POINTER_NEW_UPDATE* p
|
||||
CopyMemory(wParam->colorPtrAttr.xorMaskData, pointerNew->colorPtrAttr.xorMaskData, wParam->colorPtrAttr.lengthXorMask);
|
||||
}
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PointerUpdate, PointerNew), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
|
||||
out_fail:
|
||||
free(wParam->colorPtrAttr.andMaskData);
|
||||
@ -1317,9 +1242,8 @@ static BOOL update_message_PointerCached(rdpContext* context, POINTER_CACHED_UPD
|
||||
return FALSE;
|
||||
CopyMemory(wParam, pointerCached, sizeof(POINTER_CACHED_UPDATE));
|
||||
|
||||
MessageQueue_Post(context->update->queue, (void*) context,
|
||||
return MessageQueue_Post(context->update->queue, (void*) context,
|
||||
MakeMessageId(PointerUpdate, PointerCached), (void*) wParam, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Message Queue */
|
||||
@ -2563,7 +2487,7 @@ void update_message_proxy_free(rdpUpdateProxy* message)
|
||||
{
|
||||
if (message)
|
||||
{
|
||||
MessageQueue_PostQuit(message->update->queue, 0);
|
||||
if (MessageQueue_PostQuit(message->update->queue, 0))
|
||||
WaitForSingleObject(message->thread, INFINITE);
|
||||
CloseHandle(message->thread);
|
||||
free(message);
|
||||
@ -2574,55 +2498,48 @@ void update_message_proxy_free(rdpUpdateProxy* message)
|
||||
|
||||
static BOOL input_message_SynchronizeEvent(rdpInput* input, UINT32 flags)
|
||||
{
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, SynchronizeEvent), (void*) (size_t) flags, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL input_message_KeyboardEvent(rdpInput* input, UINT16 flags, UINT16 code)
|
||||
{
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, KeyboardEvent), (void*) (size_t) flags, (void*) (size_t) code);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL input_message_UnicodeKeyboardEvent(rdpInput* input, UINT16 flags, UINT16 code)
|
||||
{
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, UnicodeKeyboardEvent), (void*) (size_t) flags, (void*) (size_t) code);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL input_message_MouseEvent(rdpInput* input, UINT16 flags, UINT16 x, UINT16 y)
|
||||
{
|
||||
UINT32 pos = (x << 16) | y;
|
||||
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, MouseEvent), (void*) (size_t) flags, (void*) (size_t) pos);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL input_message_ExtendedMouseEvent(rdpInput* input, UINT16 flags, UINT16 x, UINT16 y)
|
||||
{
|
||||
UINT32 pos = (x << 16) | y;
|
||||
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, ExtendedMouseEvent), (void*) (size_t) flags, (void*) (size_t) pos);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL input_message_FocusInEvent(rdpInput* input, UINT16 toggleStates)
|
||||
{
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, FocusInEvent), (void*) (size_t) toggleStates, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static BOOL input_message_KeyboardPauseEvent(rdpInput* input)
|
||||
{
|
||||
MessageQueue_Post(input->queue, (void*) input,
|
||||
return MessageQueue_Post(input->queue, (void*) input,
|
||||
MakeMessageId(Input, KeyboardPauseEvent), NULL, NULL);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Event Queue */
|
||||
|
@ -211,7 +211,7 @@ int nla_client_init(rdpNla* nla)
|
||||
nla->ServicePrincipalName = spn;
|
||||
#endif
|
||||
|
||||
nla->table = InitSecurityInterfaceEx(SSPI_INTERFACE_WINPR);
|
||||
nla->table = InitSecurityInterface();
|
||||
nla->status = nla->table->QuerySecurityPackageInfo(NLA_PKG_NAME, &nla->pPackageInfo);
|
||||
|
||||
if (nla->status != SEC_E_OK)
|
||||
@ -498,7 +498,7 @@ int nla_server_init(rdpNla* nla)
|
||||
}
|
||||
else
|
||||
{
|
||||
nla->table = InitSecurityInterfaceEx(0);
|
||||
nla->table = InitSecurityInterface();
|
||||
}
|
||||
|
||||
nla->status = nla->table->QuerySecurityPackageInfo(NLA_PKG_NAME, &nla->pPackageInfo);
|
||||
|
@ -222,7 +222,7 @@ static BOOL freerdp_peer_initialize(freerdp_peer* client)
|
||||
|
||||
if (!settings->RdpServerRsaKey)
|
||||
{
|
||||
WLog_ERR(TAG, "inavlid RDP key file %s", settings->RdpKeyFile);
|
||||
WLog_ERR(TAG, "invalid RDP key file %s", settings->RdpKeyFile);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
@ -85,22 +85,24 @@ static rdpPeerChannel* wts_get_dvc_channel_by_id(WTSVirtualChannelManager* vcm,
|
||||
return found ? channel : NULL;
|
||||
}
|
||||
|
||||
static void wts_queue_receive_data(rdpPeerChannel* channel, const BYTE* Buffer, UINT32 Length)
|
||||
static BOOL wts_queue_receive_data(rdpPeerChannel* channel, const BYTE* Buffer, UINT32 Length)
|
||||
{
|
||||
BYTE* buffer;
|
||||
wtsChannelMessage* messageCtx;
|
||||
|
||||
messageCtx = (wtsChannelMessage*) malloc(sizeof(wtsChannelMessage) + Length);
|
||||
if (!messageCtx)
|
||||
return FALSE;
|
||||
messageCtx->channelId = channel->channelId;
|
||||
messageCtx->length = Length;
|
||||
messageCtx->offset = 0;
|
||||
buffer = (BYTE*) (messageCtx + 1);
|
||||
CopyMemory(buffer, Buffer, Length);
|
||||
|
||||
MessageQueue_Post(channel->queue, messageCtx, 0, NULL, NULL);
|
||||
return MessageQueue_Post(channel->queue, messageCtx, 0, NULL, NULL);
|
||||
}
|
||||
|
||||
static void wts_queue_send_item(rdpPeerChannel* channel, BYTE* Buffer, UINT32 Length)
|
||||
static BOOL wts_queue_send_item(rdpPeerChannel* channel, BYTE* Buffer, UINT32 Length)
|
||||
{
|
||||
BYTE* buffer;
|
||||
UINT32 length;
|
||||
@ -110,7 +112,7 @@ static void wts_queue_send_item(rdpPeerChannel* channel, BYTE* Buffer, UINT32 Le
|
||||
length = Length;
|
||||
channelId = channel->channelId;
|
||||
|
||||
MessageQueue_Post(channel->vcm->queue, (void*) (UINT_PTR) channelId, 0, (void*) buffer, (void*) (UINT_PTR) length);
|
||||
return MessageQueue_Post(channel->vcm->queue, (void*) (UINT_PTR) channelId, 0, (void*) buffer, (void*) (UINT_PTR) length);
|
||||
}
|
||||
|
||||
static int wts_read_variable_uint(wStream* s, int cbLen, UINT32* val)
|
||||
@ -137,12 +139,12 @@ static int wts_read_variable_uint(wStream* s, int cbLen, UINT32* val)
|
||||
}
|
||||
}
|
||||
|
||||
static void wts_read_drdynvc_capabilities_response(rdpPeerChannel* channel, UINT32 length)
|
||||
static BOOL wts_read_drdynvc_capabilities_response(rdpPeerChannel* channel, UINT32 length)
|
||||
{
|
||||
UINT16 Version;
|
||||
|
||||
if (length < 3)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
Stream_Seek_UINT8(channel->receiveData); /* Pad (1 byte) */
|
||||
Stream_Read_UINT16(channel->receiveData, Version);
|
||||
@ -150,14 +152,15 @@ static void wts_read_drdynvc_capabilities_response(rdpPeerChannel* channel, UINT
|
||||
DEBUG_DVC("Version: %d", Version);
|
||||
|
||||
channel->vcm->drdynvc_state = DRDYNVC_STATE_READY;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void wts_read_drdynvc_create_response(rdpPeerChannel* channel, wStream* s, UINT32 length)
|
||||
static BOOL wts_read_drdynvc_create_response(rdpPeerChannel* channel, wStream* s, UINT32 length)
|
||||
{
|
||||
UINT32 CreationStatus;
|
||||
|
||||
if (length < 4)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
Stream_Read_UINT32(s, CreationStatus);
|
||||
|
||||
@ -171,50 +174,55 @@ static void wts_read_drdynvc_create_response(rdpPeerChannel* channel, wStream* s
|
||||
DEBUG_DVC("ChannelId %d creation succeeded", channel->channelId);
|
||||
channel->dvc_open_state = DVC_OPEN_STATE_SUCCEEDED;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void wts_read_drdynvc_data_first(rdpPeerChannel* channel, wStream* s, int cbLen, UINT32 length)
|
||||
static BOOL wts_read_drdynvc_data_first(rdpPeerChannel* channel, wStream* s, int cbLen, UINT32 length)
|
||||
{
|
||||
int value;
|
||||
|
||||
value = wts_read_variable_uint(s, cbLen, &channel->dvc_total_length);
|
||||
|
||||
if (value == 0)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
length -= value;
|
||||
|
||||
if (length > channel->dvc_total_length)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
Stream_SetPosition(channel->receiveData, 0);
|
||||
Stream_EnsureRemainingCapacity(channel->receiveData, (int) channel->dvc_total_length);
|
||||
if (!Stream_EnsureRemainingCapacity(channel->receiveData, (int) channel->dvc_total_length))
|
||||
return FALSE;
|
||||
Stream_Write(channel->receiveData, Stream_Pointer(s), length);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void wts_read_drdynvc_data(rdpPeerChannel* channel, wStream* s, UINT32 length)
|
||||
static BOOL wts_read_drdynvc_data(rdpPeerChannel* channel, wStream* s, UINT32 length)
|
||||
{
|
||||
BOOL ret;
|
||||
if (channel->dvc_total_length > 0)
|
||||
{
|
||||
if (Stream_GetPosition(channel->receiveData) + length > channel->dvc_total_length)
|
||||
{
|
||||
channel->dvc_total_length = 0;
|
||||
WLog_ERR(TAG, "incorrect fragment data, discarded.");
|
||||
return;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
Stream_Write(channel->receiveData, Stream_Pointer(s), length);
|
||||
|
||||
if (Stream_GetPosition(channel->receiveData) >= (int) channel->dvc_total_length)
|
||||
{
|
||||
wts_queue_receive_data(channel, Stream_Buffer(channel->receiveData), channel->dvc_total_length);
|
||||
ret = wts_queue_receive_data(channel, Stream_Buffer(channel->receiveData), channel->dvc_total_length);
|
||||
channel->dvc_total_length = 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
wts_queue_receive_data(channel, Stream_Pointer(s), length);
|
||||
ret = wts_queue_receive_data(channel, Stream_Pointer(s), length);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void wts_read_drdynvc_close_response(rdpPeerChannel* channel)
|
||||
@ -223,7 +231,7 @@ static void wts_read_drdynvc_close_response(rdpPeerChannel* channel)
|
||||
channel->dvc_open_state = DVC_OPEN_STATE_CLOSED;
|
||||
}
|
||||
|
||||
static void wts_read_drdynvc_pdu(rdpPeerChannel* channel)
|
||||
static BOOL wts_read_drdynvc_pdu(rdpPeerChannel* channel)
|
||||
{
|
||||
UINT32 length;
|
||||
int value;
|
||||
@ -236,7 +244,7 @@ static void wts_read_drdynvc_pdu(rdpPeerChannel* channel)
|
||||
length = Stream_GetPosition(channel->receiveData);
|
||||
|
||||
if (length < 1)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
Stream_SetPosition(channel->receiveData, 0);
|
||||
Stream_Read_UINT8(channel->receiveData, value);
|
||||
@ -248,14 +256,14 @@ static void wts_read_drdynvc_pdu(rdpPeerChannel* channel)
|
||||
|
||||
if (Cmd == CAPABILITY_REQUEST_PDU)
|
||||
{
|
||||
wts_read_drdynvc_capabilities_response(channel, length);
|
||||
return wts_read_drdynvc_capabilities_response(channel, length);
|
||||
}
|
||||
else if (channel->vcm->drdynvc_state == DRDYNVC_STATE_READY)
|
||||
{
|
||||
value = wts_read_variable_uint(channel->receiveData, cbChId, &ChannelId);
|
||||
|
||||
if (value == 0)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
length -= value;
|
||||
|
||||
@ -267,16 +275,13 @@ static void wts_read_drdynvc_pdu(rdpPeerChannel* channel)
|
||||
switch (Cmd)
|
||||
{
|
||||
case CREATE_REQUEST_PDU:
|
||||
wts_read_drdynvc_create_response(dvc, channel->receiveData, length);
|
||||
break;
|
||||
return wts_read_drdynvc_create_response(dvc, channel->receiveData, length);
|
||||
|
||||
case DATA_FIRST_PDU:
|
||||
wts_read_drdynvc_data_first(dvc, channel->receiveData, Sp, length);
|
||||
break;
|
||||
return wts_read_drdynvc_data_first(dvc, channel->receiveData, Sp, length);
|
||||
|
||||
case DATA_PDU:
|
||||
wts_read_drdynvc_data(dvc, channel->receiveData, length);
|
||||
break;
|
||||
return wts_read_drdynvc_data(dvc, channel->receiveData, length);
|
||||
|
||||
case CLOSE_REQUEST_PDU:
|
||||
wts_read_drdynvc_close_response(dvc);
|
||||
@ -296,6 +301,7 @@ static void wts_read_drdynvc_pdu(rdpPeerChannel* channel)
|
||||
{
|
||||
WLog_ERR(TAG, "received Cmd %d but channel is not ready.", Cmd);
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static int wts_write_variable_uint(wStream* s, UINT32 val)
|
||||
@ -344,14 +350,17 @@ static BOOL wts_write_drdynvc_create_request(wStream *s, UINT32 ChannelId, const
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void WTSProcessChannelData(rdpPeerChannel* channel, UINT16 channelId, BYTE* data, int size, int flags, int totalSize)
|
||||
static BOOL WTSProcessChannelData(rdpPeerChannel* channel, UINT16 channelId, BYTE* data, int size, int flags, int totalSize)
|
||||
{
|
||||
BOOL ret = TRUE;
|
||||
|
||||
if (flags & CHANNEL_FLAG_FIRST)
|
||||
{
|
||||
Stream_SetPosition(channel->receiveData, 0);
|
||||
}
|
||||
|
||||
Stream_EnsureRemainingCapacity(channel->receiveData, size);
|
||||
if (!Stream_EnsureRemainingCapacity(channel->receiveData, size))
|
||||
return FALSE;
|
||||
Stream_Write(channel->receiveData, data, size);
|
||||
|
||||
if (flags & CHANNEL_FLAG_LAST)
|
||||
@ -362,14 +371,16 @@ static void WTSProcessChannelData(rdpPeerChannel* channel, UINT16 channelId, BYT
|
||||
}
|
||||
if (channel == channel->vcm->drdynvc_channel)
|
||||
{
|
||||
wts_read_drdynvc_pdu(channel);
|
||||
ret = wts_read_drdynvc_pdu(channel);
|
||||
}
|
||||
else
|
||||
{
|
||||
wts_queue_receive_data(channel, Stream_Buffer(channel->receiveData), Stream_GetPosition(channel->receiveData));
|
||||
ret = wts_queue_receive_data(channel, Stream_Buffer(channel->receiveData), Stream_GetPosition(channel->receiveData));
|
||||
}
|
||||
Stream_SetPosition(channel->receiveData, 0);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int WTSReceiveChannelData(freerdp_peer* client, UINT16 channelId, BYTE* data, int size, int flags, int totalSize)
|
||||
@ -1191,6 +1202,7 @@ BOOL WINAPI FreeRDP_WTSVirtualChannelWrite(HANDLE hChannelHandle, PCHAR Buffer,
|
||||
UINT32 length;
|
||||
UINT32 written;
|
||||
rdpPeerChannel* channel = (rdpPeerChannel*) hChannelHandle;
|
||||
BOOL ret = TRUE;
|
||||
|
||||
if (!channel)
|
||||
return FALSE;
|
||||
@ -1199,9 +1211,11 @@ BOOL WINAPI FreeRDP_WTSVirtualChannelWrite(HANDLE hChannelHandle, PCHAR Buffer,
|
||||
{
|
||||
length = Length;
|
||||
buffer = (BYTE *)malloc(length);
|
||||
if (!buffer)
|
||||
return FALSE;
|
||||
CopyMemory(buffer, Buffer, length);
|
||||
|
||||
wts_queue_send_item(channel, buffer, length);
|
||||
ret = wts_queue_send_item(channel, buffer, length);
|
||||
}
|
||||
else if (!channel->vcm->drdynvc_channel || (channel->vcm->drdynvc_state != DRDYNVC_STATE_READY))
|
||||
{
|
||||
@ -1220,6 +1234,7 @@ BOOL WINAPI FreeRDP_WTSVirtualChannelWrite(HANDLE hChannelHandle, PCHAR Buffer,
|
||||
WLog_ERR(TAG, "Stream_New failed!");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
buffer = Stream_Buffer(s);
|
||||
|
||||
Stream_Seek_UINT8(s);
|
||||
@ -1248,14 +1263,14 @@ BOOL WINAPI FreeRDP_WTSVirtualChannelWrite(HANDLE hChannelHandle, PCHAR Buffer,
|
||||
Length -= written;
|
||||
Buffer += written;
|
||||
|
||||
wts_queue_send_item(channel->vcm->drdynvc_channel, buffer, length);
|
||||
ret = wts_queue_send_item(channel->vcm->drdynvc_channel, buffer, length);
|
||||
}
|
||||
}
|
||||
|
||||
if (pBytesWritten)
|
||||
*pBytesWritten = Length;
|
||||
|
||||
return TRUE;
|
||||
return ret;
|
||||
}
|
||||
|
||||
BOOL WINAPI FreeRDP_WTSVirtualChannelPurgeInput(HANDLE hChannelHandle)
|
||||
|
@ -28,6 +28,8 @@
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
#include <ctype.h>
|
||||
|
||||
#include <winpr/crt.h>
|
||||
#include <winpr/file.h>
|
||||
#include <winpr/path.h>
|
||||
@ -202,6 +204,7 @@ void settings_get_computer_name(rdpSettings* settings)
|
||||
|
||||
rdpSettings* freerdp_settings_new(DWORD flags)
|
||||
{
|
||||
char* base;
|
||||
rdpSettings* settings;
|
||||
|
||||
settings = (rdpSettings*) calloc(1, sizeof(rdpSettings));
|
||||
@ -471,7 +474,34 @@ rdpSettings* freerdp_settings_new(DWORD flags)
|
||||
settings->HomePath = GetKnownPath(KNOWN_PATH_HOME);
|
||||
if (!settings->HomePath)
|
||||
goto out_fail;
|
||||
settings->ConfigPath = GetKnownSubPath(KNOWN_PATH_XDG_CONFIG_HOME, "freerdp");
|
||||
|
||||
/* For default FreeRDP continue using same config directory
|
||||
* as in old releases.
|
||||
* Custom builds use <Vendor>/<Product> as config folder. */
|
||||
if (_stricmp(FREERDP_VENDOR_STRING, FREERDP_PRODUCT_STRING))
|
||||
{
|
||||
base = GetKnownSubPath(KNOWN_PATH_XDG_CONFIG_HOME,
|
||||
FREERDP_VENDOR_STRING);
|
||||
if (base)
|
||||
{
|
||||
settings->ConfigPath = GetCombinedPath(
|
||||
base,
|
||||
FREERDP_PRODUCT_STRING);
|
||||
}
|
||||
free (base);
|
||||
} else {
|
||||
int i;
|
||||
char product[sizeof(FREERDP_PRODUCT_STRING)];
|
||||
|
||||
memset(product, 0, sizeof(product));
|
||||
for (i=0; i<sizeof(product); i++)
|
||||
product[i] = tolower(FREERDP_PRODUCT_STRING[i]);
|
||||
|
||||
settings->ConfigPath = GetKnownSubPath(
|
||||
KNOWN_PATH_XDG_CONFIG_HOME,
|
||||
product);
|
||||
}
|
||||
|
||||
if (!settings->ConfigPath)
|
||||
goto out_fail;
|
||||
|
||||
|
@ -26,6 +26,7 @@
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <winpr/crypto.h>
|
||||
#include <winpr/crt.h>
|
||||
#include <winpr/file.h>
|
||||
#include <winpr/path.h>
|
||||
@ -35,13 +36,18 @@
|
||||
|
||||
static const char certificate_store_dir[] = "certs";
|
||||
static const char certificate_server_dir[] = "server";
|
||||
static const char certificate_known_hosts_file[] = "known_hosts";
|
||||
static const char certificate_known_hosts_file[] = "known_hosts2";
|
||||
static const char certificate_legacy_hosts_file[] = "known_hosts";
|
||||
|
||||
#include <freerdp/log.h>
|
||||
#include <freerdp/crypto/certificate.h>
|
||||
|
||||
#define TAG FREERDP_TAG("crypto")
|
||||
|
||||
static BOOL certificate_split_line(char* line, char** host, UINT16* port,
|
||||
char**subject, char**issuer,
|
||||
char** fingerprint);
|
||||
|
||||
BOOL certificate_store_init(rdpCertificateStore* certificate_store)
|
||||
{
|
||||
char* server_path = NULL;
|
||||
@ -51,7 +57,7 @@ BOOL certificate_store_init(rdpCertificateStore* certificate_store)
|
||||
|
||||
if (!PathFileExistsA(settings->ConfigPath))
|
||||
{
|
||||
if (!CreateDirectoryA(settings->ConfigPath, 0))
|
||||
if (!PathMakePathA(settings->ConfigPath, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "error creating directory '%s'", settings->ConfigPath);
|
||||
goto fail;
|
||||
@ -64,7 +70,7 @@ BOOL certificate_store_init(rdpCertificateStore* certificate_store)
|
||||
|
||||
if (!PathFileExistsA(certificate_store->path))
|
||||
{
|
||||
if (!CreateDirectoryA(certificate_store->path, 0))
|
||||
if (!PathMakePathA(certificate_store->path, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "error creating directory [%s]", certificate_store->path);
|
||||
goto fail;
|
||||
@ -77,7 +83,7 @@ BOOL certificate_store_init(rdpCertificateStore* certificate_store)
|
||||
|
||||
if (!PathFileExistsA(server_path))
|
||||
{
|
||||
if (!CreateDirectoryA(server_path, 0))
|
||||
if (!PathMakePathA(server_path, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "error creating directory [%s]", server_path);
|
||||
goto fail;
|
||||
@ -88,16 +94,9 @@ BOOL certificate_store_init(rdpCertificateStore* certificate_store)
|
||||
if (!(certificate_store->file = GetCombinedPath(settings->ConfigPath, (char*) certificate_known_hosts_file)))
|
||||
goto fail;
|
||||
|
||||
if (!PathFileExistsA(certificate_store->file))
|
||||
certificate_store->fp = fopen((char*) certificate_store->file, "w+");
|
||||
else
|
||||
certificate_store->fp = fopen((char*) certificate_store->file, "r+");
|
||||
|
||||
if (!certificate_store->fp)
|
||||
{
|
||||
WLog_ERR(TAG, "error opening [%s]", certificate_store->file);
|
||||
if (!(certificate_store->legacy_file = GetCombinedPath(settings->ConfigPath,
|
||||
(char*) certificate_legacy_hosts_file)))
|
||||
goto fail;
|
||||
}
|
||||
|
||||
free(server_path);
|
||||
|
||||
@ -113,16 +112,111 @@ fail:
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
int certificate_data_match(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data)
|
||||
static int certificate_data_match_legacy(rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data)
|
||||
{
|
||||
FILE* fp;
|
||||
int match = 1;
|
||||
char* data;
|
||||
char* mdata;
|
||||
char* pline;
|
||||
char* hostname;
|
||||
long size;
|
||||
size_t length;
|
||||
|
||||
fp = fopen(certificate_store->legacy_file, "rb");
|
||||
if (!fp)
|
||||
return match;
|
||||
|
||||
fseek(fp, 0, SEEK_END);
|
||||
size = ftell(fp);
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
|
||||
if (size < 1)
|
||||
{
|
||||
fclose(fp);
|
||||
return match;
|
||||
}
|
||||
|
||||
mdata = (char*) malloc(size + 2);
|
||||
if (!mdata)
|
||||
{
|
||||
fclose(fp);
|
||||
return match;
|
||||
}
|
||||
|
||||
data = mdata;
|
||||
if (fread(data, size, 1, fp) != 1)
|
||||
{
|
||||
free(data);
|
||||
fclose(fp);
|
||||
return match;
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
|
||||
data[size] = '\n';
|
||||
data[size + 1] = '\0';
|
||||
pline = StrSep(&data, "\r\n");
|
||||
|
||||
while (pline != NULL)
|
||||
{
|
||||
length = strlen(pline);
|
||||
|
||||
if (length > 0)
|
||||
{
|
||||
hostname = StrSep(&pline, " \t");
|
||||
if (!hostname || !pline)
|
||||
WLog_WARN(TAG, "Invalid %s entry %s %s!", certificate_legacy_hosts_file,
|
||||
hostname, pline);
|
||||
else if (strcmp(hostname, certificate_data->hostname) == 0)
|
||||
{
|
||||
match = strcmp(pline, certificate_data->fingerprint);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
pline = StrSep(&data, "\r\n");
|
||||
}
|
||||
free(mdata);
|
||||
|
||||
/* Found a valid fingerprint in legacy file,
|
||||
* copy to new file in new format. */
|
||||
if (0 == match)
|
||||
{
|
||||
rdpCertificateData* data = certificate_data_new(hostname,
|
||||
certificate_data->port,
|
||||
NULL, NULL,
|
||||
pline);
|
||||
if (data)
|
||||
match = certificate_data_print(certificate_store, data) ? 0 : 1;
|
||||
certificate_data_free(data);
|
||||
}
|
||||
|
||||
return match;
|
||||
|
||||
}
|
||||
|
||||
static int certificate_data_match_raw(rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data,
|
||||
char** psubject, char** pissuer,
|
||||
char** fprint)
|
||||
{
|
||||
BOOL found = FALSE;
|
||||
FILE* fp;
|
||||
int length;
|
||||
char* data;
|
||||
char* mdata;
|
||||
char* pline;
|
||||
int match = 1;
|
||||
long int size;
|
||||
char* hostname = NULL;
|
||||
char* subject = NULL;
|
||||
char* issuer = NULL;
|
||||
char* fingerprint = NULL;
|
||||
unsigned short port = 0;
|
||||
|
||||
fp = certificate_store->fp;
|
||||
fp = fopen(certificate_store->file, "rb");
|
||||
|
||||
if (!fp)
|
||||
return match;
|
||||
@ -132,19 +226,30 @@ int certificate_data_match(rdpCertificateStore* certificate_store, rdpCertificat
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
|
||||
if (size < 1)
|
||||
return match;
|
||||
|
||||
data = (char*) malloc(size + 2);
|
||||
|
||||
if (fread(data, size, 1, fp) != 1)
|
||||
{
|
||||
free(data);
|
||||
fclose(fp);
|
||||
return match;
|
||||
}
|
||||
|
||||
mdata = (char*) malloc(size + 2);
|
||||
if (!mdata)
|
||||
{
|
||||
fclose(fp);
|
||||
return match;
|
||||
}
|
||||
|
||||
data = mdata;
|
||||
if (fread(data, size, 1, fp) != 1)
|
||||
{
|
||||
fclose(fp);
|
||||
free(data);
|
||||
return match;
|
||||
}
|
||||
fclose(fp);
|
||||
|
||||
data[size] = '\n';
|
||||
data[size + 1] = '\0';
|
||||
pline = strtok(data, "\n");
|
||||
pline = StrSep(&data, "\r\n");
|
||||
|
||||
while (pline != NULL)
|
||||
{
|
||||
@ -152,40 +257,74 @@ int certificate_data_match(rdpCertificateStore* certificate_store, rdpCertificat
|
||||
|
||||
if (length > 0)
|
||||
{
|
||||
length = strcspn(pline, " \t");
|
||||
pline[length] = '\0';
|
||||
|
||||
if (strcmp(pline, certificate_data->hostname) == 0)
|
||||
if (!certificate_split_line(pline, &hostname, &port,
|
||||
&subject, &issuer, &fingerprint))
|
||||
WLog_WARN(TAG, "Invalid %s entry %s!",
|
||||
certificate_known_hosts_file, pline);
|
||||
else if (strcmp(pline, certificate_data->hostname) == 0)
|
||||
{
|
||||
pline = &pline[length + 1];
|
||||
int outLen;
|
||||
|
||||
if (strcmp(pline, certificate_data->fingerprint) == 0)
|
||||
match = 0;
|
||||
else
|
||||
match = -1;
|
||||
if (port == certificate_data->port)
|
||||
{
|
||||
found = TRUE;
|
||||
match = strcmp(certificate_data->fingerprint, fingerprint);
|
||||
if (fingerprint && fprint)
|
||||
*fprint = _strdup(fingerprint);
|
||||
if (subject && psubject)
|
||||
crypto_base64_decode(subject, strlen(subject), (BYTE**)psubject, &outLen);
|
||||
if (issuer && pissuer)
|
||||
crypto_base64_decode(issuer, strlen(issuer), (BYTE**)pissuer, &outLen);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
pline = strtok(NULL, "\n");
|
||||
}
|
||||
free(data);
|
||||
|
||||
pline = StrSep(&data, "\r\n");
|
||||
}
|
||||
free(mdata);
|
||||
|
||||
if ((match != 0) && !found)
|
||||
match = certificate_data_match_legacy(certificate_store, certificate_data);
|
||||
|
||||
return match;
|
||||
}
|
||||
|
||||
void certificate_data_replace(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data)
|
||||
BOOL certificate_get_stored_data(rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data,
|
||||
char** subject, char** issuer,
|
||||
char** fingerprint)
|
||||
{
|
||||
int rc = certificate_data_match_raw(certificate_store, certificate_data,
|
||||
subject, issuer, fingerprint);
|
||||
|
||||
if ((rc == 0) || (rc == -1))
|
||||
return TRUE;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
int certificate_data_match(rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data)
|
||||
{
|
||||
return certificate_data_match_raw(certificate_store, certificate_data,
|
||||
NULL, NULL, NULL);
|
||||
}
|
||||
|
||||
BOOL certificate_data_replace(rdpCertificateStore* certificate_store,
|
||||
rdpCertificateData* certificate_data)
|
||||
{
|
||||
FILE* fp;
|
||||
BOOL rc = FALSE;
|
||||
int length;
|
||||
char* data;
|
||||
char* sdata;
|
||||
char* pline;
|
||||
long int size;
|
||||
|
||||
fp = certificate_store->fp;
|
||||
fp = fopen(certificate_store->file, "rb");
|
||||
|
||||
if (!fp)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
/* Read the current contents of the file. */
|
||||
fseek(fp, 0, SEEK_END);
|
||||
@ -193,21 +332,40 @@ void certificate_data_replace(rdpCertificateStore* certificate_store, rdpCertifi
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
|
||||
if (size < 1)
|
||||
return;
|
||||
{
|
||||
fclose(fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
data = (char*) malloc(size + 2);
|
||||
if (!data)
|
||||
{
|
||||
fclose(fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (fread(data, size, 1, fp) != 1)
|
||||
{
|
||||
fclose(fp);
|
||||
free(data);
|
||||
return;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
|
||||
fp = fopen(certificate_store->file, "wb");
|
||||
|
||||
if (!fp)
|
||||
{
|
||||
free(data);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* Write the file back out, with appropriate fingerprint substitutions */
|
||||
fp = fopen(certificate_store->file, "w+");
|
||||
data[size] = '\n';
|
||||
data[size + 1] = '\0';
|
||||
pline = strtok(data, "\n"); // xxx: use strsep
|
||||
sdata = data;
|
||||
pline = StrSep(&sdata, "\r\n");
|
||||
|
||||
while (pline != NULL)
|
||||
{
|
||||
@ -215,60 +373,135 @@ void certificate_data_replace(rdpCertificateStore* certificate_store, rdpCertifi
|
||||
|
||||
if (length > 0)
|
||||
{
|
||||
char* hostname = pline, *fingerprint;
|
||||
UINT16 port = 0;
|
||||
char* hostname = NULL;
|
||||
char* fingerprint = NULL;
|
||||
char* subject = NULL;
|
||||
char* issuer = NULL;
|
||||
|
||||
length = strcspn(pline, " \t");
|
||||
hostname[length] = '\0';
|
||||
|
||||
/* If this is the replaced hostname, use the updated fingerprint. */
|
||||
if (strcmp(hostname, certificate_data->hostname) == 0)
|
||||
fingerprint = certificate_data->fingerprint;
|
||||
if (!certificate_split_line(pline, &hostname, &port, &subject, &issuer, &fingerprint))
|
||||
WLog_WARN(TAG, "Skipping invalid %s entry %s!",
|
||||
certificate_known_hosts_file, pline);
|
||||
else
|
||||
fingerprint = &hostname[length + 1];
|
||||
|
||||
fprintf(fp, "%s %s\n", hostname, fingerprint);
|
||||
{
|
||||
/* If this is the replaced hostname, use the updated fingerprint. */
|
||||
if ((strcmp(hostname, certificate_data->hostname) == 0) &&
|
||||
(port == certificate_data->port))
|
||||
{
|
||||
fingerprint = certificate_data->fingerprint;
|
||||
rc = TRUE;
|
||||
}
|
||||
fprintf(fp, "%s %hu %s %s %s\n", hostname, port, fingerprint, subject, issuer);
|
||||
}
|
||||
}
|
||||
|
||||
pline = strtok(NULL, "\n");
|
||||
pline = StrSep(&sdata, "\r\n");
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
free(data);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
void certificate_data_print(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data)
|
||||
BOOL certificate_split_line(char* line, char** host, UINT16* port, char** subject,
|
||||
char** issuer, char** fingerprint)
|
||||
{
|
||||
char* cur;
|
||||
size_t length = strlen(line);
|
||||
|
||||
if (length <= 0)
|
||||
return FALSE;
|
||||
|
||||
cur = StrSep(&line, " \t");
|
||||
if (!cur)
|
||||
return FALSE;
|
||||
*host = cur;
|
||||
|
||||
cur = StrSep(&line, " \t");
|
||||
if (!cur)
|
||||
return FALSE;
|
||||
|
||||
if(sscanf(cur, "%hu", port) != 1)
|
||||
return FALSE;
|
||||
|
||||
cur = StrSep(&line, " \t");
|
||||
if (!cur)
|
||||
return FALSE;
|
||||
|
||||
*fingerprint = cur;
|
||||
|
||||
cur = StrSep(&line, " \t");
|
||||
if (!cur)
|
||||
return FALSE;
|
||||
|
||||
*subject = cur;
|
||||
|
||||
cur = StrSep(&line, " \t");
|
||||
if (!cur)
|
||||
return FALSE;
|
||||
|
||||
*issuer = cur;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL certificate_data_print(rdpCertificateStore* certificate_store, rdpCertificateData* certificate_data)
|
||||
{
|
||||
FILE* fp;
|
||||
|
||||
/* reopen in append mode */
|
||||
fp = fopen(certificate_store->file, "a");
|
||||
fp = fopen(certificate_store->file, "ab");
|
||||
|
||||
if (!fp)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
fprintf(fp, "%s %hu %s %s %s\n", certificate_data->hostname, certificate_data->port,
|
||||
certificate_data->fingerprint, certificate_data->subject,
|
||||
certificate_data->issuer);
|
||||
|
||||
fprintf(fp, "%s %s\n", certificate_data->hostname, certificate_data->fingerprint);
|
||||
fclose(fp);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
rdpCertificateData* certificate_data_new(char* hostname, char* fingerprint)
|
||||
rdpCertificateData* certificate_data_new(char* hostname, UINT16 port, char* subject, char* issuer, char* fingerprint)
|
||||
{
|
||||
rdpCertificateData* certdata;
|
||||
|
||||
if (!hostname)
|
||||
return NULL;
|
||||
|
||||
if (!fingerprint)
|
||||
return NULL;
|
||||
|
||||
certdata = (rdpCertificateData *)calloc(1, sizeof(rdpCertificateData));
|
||||
if (!certdata)
|
||||
return NULL;
|
||||
|
||||
certdata->port = port;
|
||||
certdata->hostname = _strdup(hostname);
|
||||
if (!certdata->hostname)
|
||||
goto out_free;
|
||||
if (subject)
|
||||
certdata->subject = crypto_base64_encode((BYTE*)subject, strlen(subject));
|
||||
else
|
||||
certdata->subject = crypto_base64_encode((BYTE*)"", 0);
|
||||
if (issuer)
|
||||
certdata->issuer = crypto_base64_encode((BYTE*)issuer, strlen(subject));
|
||||
else
|
||||
certdata->issuer = crypto_base64_encode((BYTE*)"", 0);
|
||||
certdata->fingerprint = _strdup(fingerprint);
|
||||
if (!certdata->fingerprint)
|
||||
goto out_free_hostname;
|
||||
|
||||
if (!certdata->hostname || !certdata->subject ||
|
||||
!certdata->issuer || !certdata->fingerprint)
|
||||
goto fail;
|
||||
|
||||
return certdata;
|
||||
|
||||
out_free_hostname:
|
||||
fail:
|
||||
free(certdata->hostname);
|
||||
out_free:
|
||||
free(certdata->subject);
|
||||
free(certdata->issuer);
|
||||
free(certdata->fingerprint);
|
||||
free(certdata);
|
||||
return NULL;
|
||||
}
|
||||
@ -278,6 +511,8 @@ void certificate_data_free(rdpCertificateData* certificate_data)
|
||||
if (certificate_data != NULL)
|
||||
{
|
||||
free(certificate_data->hostname);
|
||||
free(certificate_data->subject);
|
||||
free(certificate_data->issuer);
|
||||
free(certificate_data->fingerprint);
|
||||
free(certificate_data);
|
||||
}
|
||||
@ -307,9 +542,6 @@ void certificate_store_free(rdpCertificateStore* certstore)
|
||||
{
|
||||
if (certstore != NULL)
|
||||
{
|
||||
if (certstore->fp != NULL)
|
||||
fclose(certstore->fp);
|
||||
|
||||
free(certstore->path);
|
||||
free(certstore->file);
|
||||
free(certstore);
|
||||
|
@ -555,8 +555,10 @@ end:
|
||||
return status;
|
||||
}
|
||||
|
||||
rdpCertificateData* crypto_get_certificate_data(X509* xcert, char* hostname)
|
||||
rdpCertificateData* crypto_get_certificate_data(X509* xcert, char* hostname, UINT16 port)
|
||||
{
|
||||
char* issuer;
|
||||
char* subject;
|
||||
char* fp;
|
||||
rdpCertificateData* certdata;
|
||||
|
||||
@ -564,7 +566,13 @@ rdpCertificateData* crypto_get_certificate_data(X509* xcert, char* hostname)
|
||||
if (!fp)
|
||||
return NULL;
|
||||
|
||||
certdata = certificate_data_new(hostname, fp);
|
||||
issuer = crypto_cert_issuer(xcert);
|
||||
subject = crypto_cert_subject(xcert);
|
||||
|
||||
certdata = certificate_data_new(hostname, port, issuer, subject, fp);
|
||||
|
||||
free(subject);
|
||||
free(issuer);
|
||||
free(fp);
|
||||
|
||||
return certdata;
|
||||
|
@ -5,6 +5,7 @@ set(MODULE_PREFIX "TEST_FREERDP_CRYPTO")
|
||||
set(${MODULE_PREFIX}_DRIVER ${MODULE_NAME}.c)
|
||||
|
||||
set(${MODULE_PREFIX}_TESTS
|
||||
TestKnownHosts.c
|
||||
TestBase64.c)
|
||||
|
||||
create_test_sourcelist(${MODULE_PREFIX}_SRCS
|
||||
|
322
libfreerdp/crypto/test/TestKnownHosts.c
Normal file
322
libfreerdp/crypto/test/TestKnownHosts.c
Normal file
@ -0,0 +1,322 @@
|
||||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Implementation
|
||||
*
|
||||
* Copyright 2015 Thincast Technologies GmbH
|
||||
* Copyright 2015 Armin Novak <armin.novak@thincast.com>
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include <winpr/path.h>
|
||||
#include <winpr/file.h>
|
||||
#include <freerdp/crypto/certificate.h>
|
||||
|
||||
static int prepare(const char* currentFileV2, const char* legacyFileV2, const char* legacyFile)
|
||||
{
|
||||
char* legacy[] = {
|
||||
"someurl ff:11:22:dd\r\n",
|
||||
"otherurl aa:bb:cc:dd\r",
|
||||
"legacyurl aa:bb:cc:dd\n"
|
||||
};
|
||||
char* hosts[] = {
|
||||
"someurl 3389 ff:11:22:dd subject issuer\r\n",
|
||||
"otherurl\t3389\taa:bb:cc:dd\tsubject2\tissuer2\r",
|
||||
};
|
||||
FILE* fl = NULL;
|
||||
FILE* fc = NULL;
|
||||
size_t i;
|
||||
|
||||
fc = fopen(currentFileV2, "w+");
|
||||
if (!fc)
|
||||
goto finish;
|
||||
|
||||
fl = fopen(legacyFileV2, "w+");
|
||||
if (!fl)
|
||||
goto finish;
|
||||
|
||||
for (i=0; i<sizeof(hosts)/sizeof(hosts[0]); i++)
|
||||
{
|
||||
fwrite(hosts[i], strlen(hosts[i]), sizeof(char), fl);
|
||||
fwrite(hosts[i], strlen(hosts[i]), sizeof(char), fc);
|
||||
}
|
||||
|
||||
fclose(fc);
|
||||
fc = NULL;
|
||||
|
||||
fclose(fl);
|
||||
fl = NULL;
|
||||
|
||||
fl = fopen(legacyFile, "w+");
|
||||
if (!fl)
|
||||
goto finish;
|
||||
|
||||
for (i=0; i<sizeof(legacy)/sizeof(legacy[0]); i++)
|
||||
fwrite(legacy[i], strlen(legacy[i]), sizeof(char), fl);
|
||||
|
||||
fclose(fl);
|
||||
return 0;
|
||||
|
||||
finish:
|
||||
fclose(fl);
|
||||
fclose(fc);
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
int TestKnownHosts(int argc, char* argv[])
|
||||
{
|
||||
int rc = -1;
|
||||
rdpSettings current;
|
||||
rdpSettings legacy;
|
||||
rdpCertificateData* data = NULL;
|
||||
rdpCertificateStore* store = NULL;
|
||||
char* currentFileV2 = NULL;
|
||||
char* legacyFileV2 = NULL;
|
||||
char* legacyFile = NULL;
|
||||
char* subject = NULL;
|
||||
char* issuer = NULL;
|
||||
char* fp = NULL;
|
||||
|
||||
current.ConfigPath = GetKnownSubPath(KNOWN_PATH_TEMP, "TestKnownHostsCurrent");
|
||||
legacy.ConfigPath = GetKnownSubPath(KNOWN_PATH_TEMP, "TestKnownHostsLegacy");
|
||||
|
||||
if (!PathFileExistsA(current.ConfigPath))
|
||||
{
|
||||
if (!CreateDirectoryA(current.ConfigPath, NULL))
|
||||
{
|
||||
fprintf(stderr, "Could not create %s!\n", current.ConfigPath);
|
||||
goto finish;
|
||||
}
|
||||
}
|
||||
|
||||
if (!PathFileExistsA(legacy.ConfigPath))
|
||||
{
|
||||
if (!CreateDirectoryA(legacy.ConfigPath, NULL))
|
||||
{
|
||||
fprintf(stderr, "Could not create %s!\n", legacy.ConfigPath);
|
||||
goto finish;
|
||||
}
|
||||
}
|
||||
|
||||
currentFileV2 = GetCombinedPath(current.ConfigPath, "known_hosts2");
|
||||
if (!currentFileV2)
|
||||
{
|
||||
fprintf(stderr, "Could not get file path!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
legacyFileV2 = GetCombinedPath(legacy.ConfigPath, "known_hosts2");
|
||||
if (!legacyFileV2)
|
||||
{
|
||||
fprintf(stderr, "Could not get file path!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
legacyFile = GetCombinedPath(legacy.ConfigPath, "known_hosts");
|
||||
if (!legacyFile)
|
||||
{
|
||||
fprintf(stderr, "Could not get file path!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
store = certificate_store_new(¤t);
|
||||
if (!store)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate store!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (prepare(currentFileV2, legacyFileV2, legacyFile))
|
||||
goto finish;
|
||||
|
||||
/* Test if host is found in current file. */
|
||||
data = certificate_data_new("someurl", 3389, "subject", "issuer", "ff:11:22:dd");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 != certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Could not find data in v2 file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
/* Test if we can read out the old fingerprint. */
|
||||
if (!certificate_get_stored_data(store, data, &subject, &issuer, &fp))
|
||||
{
|
||||
fprintf(stderr, "Could not read old fingerprint!\n");
|
||||
goto finish;
|
||||
}
|
||||
printf("Got %s, %s '%s'\n", subject, issuer, fp);
|
||||
free(subject);
|
||||
free(issuer);
|
||||
free(fp);
|
||||
subject = NULL;
|
||||
issuer = NULL;
|
||||
fp = NULL;
|
||||
certificate_data_free(data);
|
||||
|
||||
/* Test if host not found in current file. */
|
||||
data = certificate_data_new("somehost", 1234, "", "", "ff:aa:bb:cc");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 == certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Invalid host found in v2 file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
/* Test if we read out the old fingerprint fails. */
|
||||
if (certificate_get_stored_data(store, data, &subject, &issuer, &fp))
|
||||
{
|
||||
fprintf(stderr, "Read out not existing old fingerprint succeeded?!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
certificate_data_free(data);
|
||||
|
||||
/* Test host add current file. */
|
||||
data = certificate_data_new("somehost", 1234, "", "", "ff:aa:bb:cc");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (!certificate_data_print(store, data))
|
||||
{
|
||||
fprintf(stderr, "Could not add host to file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 != certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Could not find host written in v2 file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
certificate_data_free(data);
|
||||
|
||||
/* Test host replace current file. */
|
||||
data = certificate_data_new("somehost", 1234, "", "", "ff:aa:bb:dd:ee");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (!certificate_data_replace(store, data))
|
||||
{
|
||||
fprintf(stderr, "Could not replace data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 != certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Invalid host found in v2 file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
certificate_data_free(data);
|
||||
|
||||
/* Test host replace invalid entry in current file. */
|
||||
data = certificate_data_new("somehostXXXX", 1234, "", "", "ff:aa:bb:dd:ee");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (certificate_data_replace(store, data))
|
||||
{
|
||||
fprintf(stderr, "Invalid return for replace invalid entry!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 == certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Invalid host found in v2 file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
certificate_data_free(data);
|
||||
|
||||
|
||||
certificate_store_free(store);
|
||||
|
||||
store = certificate_store_new(&legacy);
|
||||
if (!store)
|
||||
{
|
||||
fprintf(stderr, "could not create certificate store!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
/* test if host found in legacy file. */
|
||||
data = certificate_data_new("legacyurl", 1234, "", "", "aa:bb:cc:dd");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 != certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Could not find host in file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
certificate_data_free(data);
|
||||
|
||||
/* test if host not found. */
|
||||
data = certificate_data_new("somehost-not-in-file", 1234, "", "", "ff:aa:bb:cc");
|
||||
if (!data)
|
||||
{
|
||||
fprintf(stderr, "Could not create certificate data!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (0 == certificate_data_match(store, data))
|
||||
{
|
||||
fprintf(stderr, "Invalid host found in file!\n");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
rc = 0;
|
||||
|
||||
finish:
|
||||
if (store)
|
||||
certificate_store_free(store);
|
||||
if (data)
|
||||
certificate_data_free(data);
|
||||
DeleteFileA(currentFileV2);
|
||||
//RemoveDirectoryA(current.ConfigPath);
|
||||
|
||||
DeleteFileA(legacyFileV2);
|
||||
DeleteFileA(legacyFile);
|
||||
//RemoveDirectoryA(legacy.ConfigPath);
|
||||
|
||||
free (currentFileV2);
|
||||
free (legacyFileV2);
|
||||
free (legacyFile);
|
||||
free(subject);
|
||||
free(issuer);
|
||||
free(fp);
|
||||
|
||||
return rc;
|
||||
}
|
2
libfreerdp/crypto/test/known_hosts/known_hosts
Normal file
2
libfreerdp/crypto/test/known_hosts/known_hosts
Normal file
@ -0,0 +1,2 @@
|
||||
someurl ff:11:22:dd
|
||||
otherurl aa:bb:cc:dd
|
2
libfreerdp/crypto/test/known_hosts/known_hosts.v2
Normal file
2
libfreerdp/crypto/test/known_hosts/known_hosts.v2
Normal file
@ -0,0 +1,2 @@
|
||||
someurl 3389 ff:11:22:dd
|
||||
otherurl 3389 aa:bb:cc:dd
|
@ -1082,7 +1082,7 @@ int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int por
|
||||
certificate_status = x509_verify_certificate(cert, tls->certificate_store->path);
|
||||
|
||||
/* verify certificate name match */
|
||||
certificate_data = crypto_get_certificate_data(cert->px509, hostname);
|
||||
certificate_data = crypto_get_certificate_data(cert->px509, hostname, port);
|
||||
|
||||
/* extra common name and alternative names */
|
||||
common_name = crypto_cert_subject_common_name(cert->px509, &common_name_length);
|
||||
@ -1124,7 +1124,9 @@ int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int por
|
||||
|
||||
/* if the certificate is valid but the certificate name does not match, warn user, do not accept */
|
||||
if (certificate_status && !hostname_match)
|
||||
tls_print_certificate_name_mismatch_error(hostname, common_name, alt_names, alt_names_count);
|
||||
tls_print_certificate_name_mismatch_error(hostname, port,
|
||||
common_name, alt_names,
|
||||
alt_names_count);
|
||||
|
||||
/* verification could not succeed with OpenSSL, use known_hosts file and prompt user for manual verification */
|
||||
|
||||
@ -1147,7 +1149,10 @@ int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int por
|
||||
{
|
||||
/* no entry was found in known_hosts file, prompt user for manual verification */
|
||||
if (!hostname_match)
|
||||
tls_print_certificate_name_mismatch_error(hostname, common_name, alt_names, alt_names_count);
|
||||
tls_print_certificate_name_mismatch_error(
|
||||
hostname, port,
|
||||
common_name, alt_names,
|
||||
alt_names_count);
|
||||
|
||||
if (instance->VerifyCertificate)
|
||||
{
|
||||
@ -1162,20 +1167,35 @@ int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int por
|
||||
else
|
||||
{
|
||||
/* user accepted certificate, add entry in known_hosts file */
|
||||
certificate_data_print(tls->certificate_store, certificate_data);
|
||||
verification_status = TRUE; /* success! */
|
||||
verification_status = certificate_data_print(tls->certificate_store, certificate_data);
|
||||
}
|
||||
}
|
||||
else if (match == -1)
|
||||
{
|
||||
char* old_subject = NULL;
|
||||
char* old_issuer = NULL;
|
||||
char* old_fingerprint = NULL;
|
||||
|
||||
/* entry was found in known_hosts file, but fingerprint does not match. ask user to use it */
|
||||
tls_print_certificate_error(hostname, fingerprint, tls->certificate_store->file);
|
||||
tls_print_certificate_error(hostname, port, fingerprint,
|
||||
tls->certificate_store->file);
|
||||
|
||||
if (!certificate_get_stored_data(tls->certificate_store,
|
||||
certificate_data, &old_subject,
|
||||
&old_issuer, &old_fingerprint))
|
||||
WLog_WARN(TAG, "Failed to get certificate entry for %s:hu",
|
||||
hostname, port);
|
||||
|
||||
if (instance->VerifyChangedCertificate)
|
||||
{
|
||||
accept_certificate = instance->VerifyChangedCertificate(instance, subject, issuer, fingerprint, "");
|
||||
accept_certificate = instance->VerifyChangedCertificate(
|
||||
instance, subject, issuer,
|
||||
fingerprint, old_subject, old_issuer,
|
||||
old_fingerprint);
|
||||
}
|
||||
|
||||
free(old_fingerprint);
|
||||
|
||||
if (!accept_certificate)
|
||||
{
|
||||
/* user did not accept, abort and do not change known_hosts file */
|
||||
@ -1184,8 +1204,7 @@ int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int por
|
||||
else
|
||||
{
|
||||
/* user accepted new certificate, add replace fingerprint for this host in known_hosts file */
|
||||
certificate_data_replace(tls->certificate_store, certificate_data);
|
||||
verification_status = TRUE; /* success! */
|
||||
verification_status = certificate_data_replace(tls->certificate_store, certificate_data);
|
||||
}
|
||||
}
|
||||
else if (match == 0)
|
||||
@ -1216,9 +1235,10 @@ int tls_verify_certificate(rdpTls* tls, CryptoCert cert, char* hostname, int por
|
||||
return (verification_status == 0) ? 0 : 1;
|
||||
}
|
||||
|
||||
void tls_print_certificate_error(char* hostname, char* fingerprint, char *hosts_file)
|
||||
void tls_print_certificate_error(char* hostname, UINT16 port, char* fingerprint,
|
||||
char *hosts_file)
|
||||
{
|
||||
WLog_ERR(TAG, "The host key for %s has changed", hostname);
|
||||
WLog_ERR(TAG, "The host key for %s:%hu has changed", hostname, port);
|
||||
WLog_ERR(TAG, "@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
|
||||
WLog_ERR(TAG, "@ WARNING: REMOTE HOST IDENTIFICATION HAS CHANGED! @");
|
||||
WLog_ERR(TAG, "@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
|
||||
@ -1232,7 +1252,9 @@ void tls_print_certificate_error(char* hostname, char* fingerprint, char *hosts_
|
||||
WLog_ERR(TAG, "Host key verification failed.");
|
||||
}
|
||||
|
||||
void tls_print_certificate_name_mismatch_error(char* hostname, char* common_name, char** alt_names, int alt_names_count)
|
||||
void tls_print_certificate_name_mismatch_error(char* hostname, UINT16 port,
|
||||
char* common_name, char** alt_names,
|
||||
int alt_names_count)
|
||||
{
|
||||
int index;
|
||||
|
||||
@ -1240,8 +1262,10 @@ void tls_print_certificate_name_mismatch_error(char* hostname, char* common_name
|
||||
WLog_ERR(TAG, "@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
|
||||
WLog_ERR(TAG, "@ WARNING: CERTIFICATE NAME MISMATCH! @");
|
||||
WLog_ERR(TAG, "@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
|
||||
WLog_ERR(TAG, "The hostname used for this connection (%s) ", hostname);
|
||||
WLog_ERR(TAG, "does not match %s given in the certificate:", alt_names_count < 1 ? "the name" : "any of the names");
|
||||
WLog_ERR(TAG, "The hostname used for this connection (%s:%hu) ",
|
||||
hostname, port);
|
||||
WLog_ERR(TAG, "does not match %s given in the certificate:",
|
||||
alt_names_count < 1 ? "the name" : "any of the names");
|
||||
WLog_ERR(TAG, "Common Name (CN):");
|
||||
WLog_ERR(TAG, "\t%s", common_name ? common_name : "no CN found in certificate");
|
||||
if (alt_names_count > 0)
|
||||
|
@ -1,4 +1,6 @@
|
||||
opt/freerdp-nightly/lib/*.a
|
||||
opt/freerdp-nightly/lib/*.so
|
||||
opt/freerdp-nightly/lib/freerdp/*.a
|
||||
opt/freerdp-nightly/lib/pkgconfig
|
||||
opt/freerdp-nightly/lib/cmake
|
||||
opt/freerdp-nightly/include
|
||||
|
@ -35,8 +35,6 @@ override_dh_strip:
|
||||
dh_strip --dbg-package=freerdp-nightly-dbg
|
||||
|
||||
override_dh_install:
|
||||
rm -f debian/tmp/opt/freerdp-nightly/lib/libwinpr-makecert-tool.a
|
||||
rm -f debian/tmp/opt/freerdp-nightly/lib/freerdp/*.a
|
||||
mkdir -p debian/tmp/opt/freerdp-nightly/lib/cmake/
|
||||
|
||||
dh_install --fail-missing
|
||||
|
@ -362,9 +362,7 @@ int x11_shadow_pointer_position_update(x11ShadowSubsystem* subsystem)
|
||||
msg->xPos = subsystem->pointerX;
|
||||
msg->yPos = subsystem->pointerY;
|
||||
|
||||
MessageQueue_Post(MsgPipe->Out, NULL, msgId, (void*) msg, NULL);
|
||||
|
||||
return 1;
|
||||
return MessageQueue_Post(MsgPipe->Out, NULL, msgId, (void*) msg, NULL) ? 1 : -1;
|
||||
}
|
||||
|
||||
int x11_shadow_pointer_alpha_update(x11ShadowSubsystem* subsystem)
|
||||
@ -395,9 +393,7 @@ int x11_shadow_pointer_alpha_update(x11ShadowSubsystem* subsystem)
|
||||
CopyMemory(msg->pixels, subsystem->cursorPixels, msg->scanline * msg->height);
|
||||
msg->premultiplied = TRUE;
|
||||
|
||||
MessageQueue_Post(MsgPipe->Out, NULL, msgId, (void*) msg, NULL);
|
||||
|
||||
return 1;
|
||||
return MessageQueue_Post(MsgPipe->Out, NULL, msgId, (void*) msg, NULL) ? 1 : -1;
|
||||
}
|
||||
|
||||
int x11_shadow_query_cursor(x11ShadowSubsystem* subsystem, BOOL getImage)
|
||||
@ -1295,7 +1291,7 @@ int x11_shadow_subsystem_stop(x11ShadowSubsystem* subsystem)
|
||||
|
||||
if (subsystem->thread)
|
||||
{
|
||||
MessageQueue_PostQuit(subsystem->MsgPipe->In, 0);
|
||||
if (MessageQueue_PostQuit(subsystem->MsgPipe->In, 0))
|
||||
WaitForSingleObject(subsystem->thread, INFINITE);
|
||||
CloseHandle(subsystem->thread);
|
||||
subsystem->thread = NULL;
|
||||
|
@ -251,17 +251,17 @@ BOOL shadow_client_post_connect(freerdp_peer* peer)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void shadow_client_refresh_rect(rdpShadowClient* client, BYTE count, RECTANGLE_16* areas)
|
||||
BOOL shadow_client_refresh_rect(rdpShadowClient* client, BYTE count, RECTANGLE_16* areas)
|
||||
{
|
||||
wMessage message = { 0 };
|
||||
SHADOW_MSG_IN_REFRESH_OUTPUT* wParam;
|
||||
wMessagePipe* MsgPipe = client->subsystem->MsgPipe;
|
||||
|
||||
if (!areas)
|
||||
return;
|
||||
if (count && !areas)
|
||||
return FALSE;
|
||||
|
||||
if (!(wParam = (SHADOW_MSG_IN_REFRESH_OUTPUT*) calloc(1, sizeof(SHADOW_MSG_IN_REFRESH_OUTPUT))))
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
wParam->numRects = (UINT32) count;
|
||||
|
||||
@ -272,11 +272,11 @@ void shadow_client_refresh_rect(rdpShadowClient* client, BYTE count, RECTANGLE_1
|
||||
if (!wParam->rects)
|
||||
{
|
||||
free (wParam);
|
||||
return;
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
CopyMemory(wParam->rects, areas, wParam->numRects * sizeof(RECTANGLE_16));
|
||||
}
|
||||
|
||||
message.id = SHADOW_MSG_IN_REFRESH_OUTPUT_ID;
|
||||
message.wParam = (void*) wParam;
|
||||
@ -284,19 +284,18 @@ void shadow_client_refresh_rect(rdpShadowClient* client, BYTE count, RECTANGLE_1
|
||||
message.context = (void*) client;
|
||||
message.Free = shadow_client_message_free;
|
||||
|
||||
MessageQueue_Dispatch(MsgPipe->In, &message);
|
||||
return MessageQueue_Dispatch(MsgPipe->In, &message);
|
||||
}
|
||||
|
||||
void shadow_client_suppress_output(rdpShadowClient* client, BYTE allow, RECTANGLE_16* area)
|
||||
BOOL shadow_client_suppress_output(rdpShadowClient* client, BYTE allow, RECTANGLE_16* area)
|
||||
{
|
||||
wMessage message = { 0 };
|
||||
SHADOW_MSG_IN_SUPPRESS_OUTPUT* wParam;
|
||||
wMessagePipe* MsgPipe = client->subsystem->MsgPipe;
|
||||
|
||||
wParam = (SHADOW_MSG_IN_SUPPRESS_OUTPUT*) calloc(1, sizeof(SHADOW_MSG_IN_SUPPRESS_OUTPUT));
|
||||
|
||||
if (!wParam)
|
||||
return;
|
||||
return FALSE;
|
||||
|
||||
wParam->allow = (UINT32) allow;
|
||||
|
||||
@ -309,7 +308,7 @@ void shadow_client_suppress_output(rdpShadowClient* client, BYTE allow, RECTANGL
|
||||
message.context = (void*) client;
|
||||
message.Free = shadow_client_message_free;
|
||||
|
||||
MessageQueue_Dispatch(MsgPipe->In, &message);
|
||||
return MessageQueue_Dispatch(MsgPipe->In, &message);
|
||||
}
|
||||
|
||||
BOOL shadow_client_activate(freerdp_peer* peer)
|
||||
@ -334,12 +333,10 @@ BOOL shadow_client_activate(freerdp_peer* peer)
|
||||
|
||||
shadow_encoder_reset(client->encoder);
|
||||
|
||||
shadow_client_refresh_rect(client, 0, NULL);
|
||||
|
||||
return TRUE;
|
||||
return shadow_client_refresh_rect(client, 0, NULL);
|
||||
}
|
||||
|
||||
void shadow_client_surface_frame_acknowledge(rdpShadowClient* client, UINT32 frameId)
|
||||
BOOL shadow_client_surface_frame_acknowledge(rdpShadowClient* client, UINT32 frameId)
|
||||
{
|
||||
SURFACE_FRAME* frame;
|
||||
wListDictionary* frameList;
|
||||
@ -352,6 +349,7 @@ void shadow_client_surface_frame_acknowledge(rdpShadowClient* client, UINT32 fra
|
||||
ListDictionary_Remove(frameList, (void*) (size_t) frameId);
|
||||
free(frame);
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
int shadow_client_send_surface_frame_marker(rdpShadowClient* client, UINT32 action, UINT32 id)
|
||||
@ -445,6 +443,7 @@ int shadow_client_send_surface_bits(rdpShadowClient* client, rdpShadowSurface* s
|
||||
cmd.bpp = 32;
|
||||
cmd.width = surface->width;
|
||||
cmd.height = surface->height;
|
||||
cmd.skipCompression = TRUE;
|
||||
|
||||
if (numMessages > 0)
|
||||
messageRects = messages[0].rects;
|
||||
|
@ -28,7 +28,6 @@ rdpShadowScreen* shadow_screen_new(rdpShadowServer* server)
|
||||
{
|
||||
int x, y;
|
||||
int width, height;
|
||||
MONITOR_DEF* primary;
|
||||
rdpShadowScreen* screen;
|
||||
rdpShadowSubsystem* subsystem;
|
||||
|
||||
@ -45,12 +44,21 @@ rdpShadowScreen* shadow_screen_new(rdpShadowServer* server)
|
||||
|
||||
region16_init(&(screen->invalidRegion));
|
||||
|
||||
if (server->shareSubRect) {
|
||||
x = server->subRect.left;
|
||||
y = server->subRect.top;
|
||||
width = server->subRect.right - server->subRect.left;
|
||||
height = server->subRect.bottom - server->subRect.top;
|
||||
} else {
|
||||
MONITOR_DEF* primary;
|
||||
|
||||
primary = &(subsystem->monitors[subsystem->selectedMonitor]);
|
||||
|
||||
x = primary->left;
|
||||
y = primary->top;
|
||||
width = primary->right - primary->left;
|
||||
height = primary->bottom - primary->top;
|
||||
}
|
||||
|
||||
screen->width = width;
|
||||
screen->height = height;
|
||||
|
@ -346,11 +346,13 @@ void* shadow_server_thread(rdpShadowServer* server)
|
||||
|
||||
/* Signal to the clients that server is being stopped and wait for them
|
||||
* to disconnect. */
|
||||
MessageQueue_PostQuit(subsystem->MsgPipe->Out, 0);
|
||||
if (MessageQueue_PostQuit(subsystem->MsgPipe->Out, 0))
|
||||
{
|
||||
while(ArrayList_Count(server->clients) > 0)
|
||||
{
|
||||
Sleep(100);
|
||||
}
|
||||
}
|
||||
|
||||
ExitThread(0);
|
||||
|
||||
@ -443,7 +445,7 @@ int shadow_server_init_config_path(rdpShadowServer* server)
|
||||
if (userLibraryPath)
|
||||
{
|
||||
if (!PathFileExistsA(userLibraryPath) &&
|
||||
!CreateDirectoryA(userLibraryPath, 0))
|
||||
!PathMakePathA(userLibraryPath, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to create directory '%s'", userLibraryPath);
|
||||
free(userLibraryPath);
|
||||
@ -455,7 +457,7 @@ int shadow_server_init_config_path(rdpShadowServer* server)
|
||||
if (userApplicationSupportPath)
|
||||
{
|
||||
if (!PathFileExistsA(userApplicationSupportPath) &&
|
||||
!CreateDirectoryA(userApplicationSupportPath, 0))
|
||||
!PathMakePathA(userApplicationSupportPath, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to create directory '%s'", userApplicationSupportPath);
|
||||
free(userLibraryPath);
|
||||
@ -480,7 +482,7 @@ int shadow_server_init_config_path(rdpShadowServer* server)
|
||||
if (configHome)
|
||||
{
|
||||
if (!PathFileExistsA(configHome) &&
|
||||
!CreateDirectoryA(configHome, 0))
|
||||
!PathMakePathA(configHome, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to create directory '%s'", configHome);
|
||||
free(configHome);
|
||||
@ -514,7 +516,7 @@ int shadow_server_init_certificate(rdpShadowServer* server)
|
||||
int makecert_argc = (sizeof(makecert_argv) / sizeof(char*));
|
||||
|
||||
if (!PathFileExistsA(server->ConfigPath) &&
|
||||
!CreateDirectoryA(server->ConfigPath, 0))
|
||||
!PathMakePathA(server->ConfigPath, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to create directory '%s'", server->ConfigPath);
|
||||
return -1;
|
||||
@ -524,7 +526,7 @@ int shadow_server_init_certificate(rdpShadowServer* server)
|
||||
return -1;
|
||||
|
||||
if (!PathFileExistsA(filepath) &&
|
||||
!CreateDirectoryA(filepath, 0))
|
||||
!PathMakePathA(filepath, 0))
|
||||
{
|
||||
WLog_ERR(TAG, "Failed to create directory '%s'", filepath);
|
||||
free(filepath);
|
||||
|
@ -477,9 +477,9 @@ WINPR_API HANDLE MessageQueue_Event(wMessageQueue* queue);
|
||||
WINPR_API BOOL MessageQueue_Wait(wMessageQueue* queue);
|
||||
WINPR_API int MessageQueue_Size(wMessageQueue* queue);
|
||||
|
||||
WINPR_API void MessageQueue_Dispatch(wMessageQueue* queue, wMessage* message);
|
||||
WINPR_API void MessageQueue_Post(wMessageQueue* queue, void* context, UINT32 type, void* wParam, void* lParam);
|
||||
WINPR_API void MessageQueue_PostQuit(wMessageQueue* queue, int nExitCode);
|
||||
WINPR_API BOOL MessageQueue_Dispatch(wMessageQueue* queue, wMessage* message);
|
||||
WINPR_API BOOL MessageQueue_Post(wMessageQueue* queue, void* context, UINT32 type, void* wParam, void* lParam);
|
||||
WINPR_API BOOL MessageQueue_PostQuit(wMessageQueue* queue, int nExitCode);
|
||||
|
||||
WINPR_API int MessageQueue_Get(wMessageQueue* queue, wMessage* message);
|
||||
WINPR_API int MessageQueue_Peek(wMessageQueue* queue, wMessage* message, BOOL remove);
|
||||
|
@ -291,6 +291,9 @@ WINPR_API BOOL FindClose(HANDLE hFindFile);
|
||||
WINPR_API BOOL CreateDirectoryA(LPCSTR lpPathName, LPSECURITY_ATTRIBUTES lpSecurityAttributes);
|
||||
WINPR_API BOOL CreateDirectoryW(LPCWSTR lpPathName, LPSECURITY_ATTRIBUTES lpSecurityAttributes);
|
||||
|
||||
WINPR_API BOOL RemoveDirectoryA(LPCSTR lpPathName);
|
||||
WINPR_API BOOL RemoveDirectoryW(LPCWSTR lpPathName);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
@ -302,6 +305,7 @@ WINPR_API BOOL CreateDirectoryW(LPCWSTR lpPathName, LPSECURITY_ATTRIBUTES lpSecu
|
||||
#define FindFirstFileEx FindFirstFileExW
|
||||
#define FindNextFile FindNextFileW
|
||||
#define CreateDirectory CreateDirectoryW
|
||||
#define RemoveDirectory RemoveDirectoryW
|
||||
#else
|
||||
#define CreateFile CreateFileA
|
||||
#define DeleteFile DeleteFileA
|
||||
@ -309,6 +313,7 @@ WINPR_API BOOL CreateDirectoryW(LPCWSTR lpPathName, LPSECURITY_ATTRIBUTES lpSecu
|
||||
#define FindFirstFileEx FindFirstFileExA
|
||||
#define FindNextFile FindNextFileA
|
||||
#define CreateDirectory CreateDirectoryA
|
||||
#define RemoveDirectory RemoveDirectoryA
|
||||
#endif
|
||||
|
||||
|
||||
|
@ -285,6 +285,8 @@ WINPR_API char* GetEnvironmentPath(char* name);
|
||||
WINPR_API char* GetEnvironmentSubPath(char* name, const char* path);
|
||||
WINPR_API char* GetCombinedPath(const char* basePath, const char* subPath);
|
||||
|
||||
WINPR_API BOOL PathMakePathA(LPCSTR path, LPSECURITY_ATTRIBUTES lpAttributes);
|
||||
|
||||
WINPR_API BOOL PathFileExistsA(LPCSTR pszPath);
|
||||
WINPR_API BOOL PathFileExistsW(LPCWSTR pszPath);
|
||||
|
||||
|
@ -186,6 +186,8 @@ WINPR_API void ByteSwapUnicode(WCHAR* wstr, int length);
|
||||
WINPR_API int ConvertLineEndingToLF(char* str, int size);
|
||||
WINPR_API char* ConvertLineEndingToCRLF(const char* str, int* size);
|
||||
|
||||
WINPR_API char* StrSep(char** stringp, const char* delim);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
@ -295,6 +295,8 @@ WINPR_API ULONGLONG GetTickCount64(void);
|
||||
|
||||
#endif
|
||||
|
||||
WINPR_API DWORD GetTickCountPrecise(void);
|
||||
|
||||
WINPR_API BOOL IsProcessorFeaturePresentEx(DWORD ProcessorFeature);
|
||||
|
||||
/* extended flags */
|
||||
|
@ -154,8 +154,9 @@ typedef unsigned int UINT32;
|
||||
typedef unsigned __int64 UINT64;
|
||||
typedef ULONG *PULONG;
|
||||
|
||||
typedef ULONG HRESULT;
|
||||
typedef ULONG SCODE;
|
||||
typedef LONG HRESULT;
|
||||
typedef LONG SCODE;
|
||||
typedef SCODE *PSCODE;
|
||||
|
||||
typedef ULONG_PTR DWORD_PTR, *PDWORD_PTR;
|
||||
typedef ULONG_PTR SIZE_T;
|
||||
|
@ -463,3 +463,22 @@ char* ConvertLineEndingToCRLF(const char* str, int* size)
|
||||
return newStr;
|
||||
}
|
||||
|
||||
char* StrSep(char** stringp, const char* delim)
|
||||
{
|
||||
char* start = *stringp;
|
||||
char* p;
|
||||
|
||||
p = (start != NULL) ? strpbrk(start, delim) : NULL;
|
||||
|
||||
if (!p)
|
||||
*stringp = NULL;
|
||||
else
|
||||
{
|
||||
*p = '\0';
|
||||
*stringp = p + 1;
|
||||
}
|
||||
|
||||
return start;
|
||||
}
|
||||
|
||||
|
||||
|
@ -788,7 +788,20 @@ BOOL CreateDirectoryA(LPCSTR lpPathName, LPSECURITY_ATTRIBUTES lpSecurityAttribu
|
||||
|
||||
BOOL CreateDirectoryW(LPCWSTR lpPathName, LPSECURITY_ATTRIBUTES lpSecurityAttributes)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL RemoveDirectoryA(LPCSTR lpPathName)
|
||||
{
|
||||
if (!rmdir(lpPathName))
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL RemoveDirectoryW(LPCWSTR lpPathName)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -6,6 +6,18 @@
|
||||
#define PATH_ALLOC_COMBINE PathAllocCombineA
|
||||
*/
|
||||
|
||||
/**
|
||||
* FIXME: These implementations of the PathAllocCombine functions have
|
||||
* several issues:
|
||||
* - pszPathIn or pszMore may be NULL (but not both)
|
||||
* - no check if pszMore is fully qualified (if so, it must be directly
|
||||
* copied to the output buffer without being combined with pszPathIn.
|
||||
* - if pszMore begins with a _single_ backslash it must be combined with
|
||||
* only the root of the path pointed to by pszPathIn and there's no code
|
||||
* to extract the root of pszPathIn.
|
||||
* - the function will crash with some short string lengths of the parameters
|
||||
*/
|
||||
|
||||
#if DEFINE_UNICODE
|
||||
|
||||
HRESULT PATH_ALLOC_COMBINE(PCWSTR pszPathIn, PCWSTR pszMore, unsigned long dwFlags, PWSTR* ppszPathOut)
|
||||
@ -18,14 +30,26 @@ HRESULT PATH_ALLOC_COMBINE(PCWSTR pszPathIn, PCWSTR pszMore, unsigned long dwFla
|
||||
int pszPathInLength;
|
||||
int pszPathOutLength;
|
||||
|
||||
if (!pszPathIn)
|
||||
return S_FALSE;
|
||||
WLog_WARN(TAG, "%s: has known bugs and needs fixing.", __FUNCTION__);
|
||||
|
||||
if (!ppszPathOut)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszPathIn && !pszMore)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszMore)
|
||||
return S_FALSE;
|
||||
return E_FAIL; /* valid but not implemented, see top comment */
|
||||
|
||||
pszPathInLength = lstrlenW(pszPathIn);
|
||||
pszMoreLength = lstrlenW(pszMore);
|
||||
if (!pszPathIn)
|
||||
return E_FAIL; /* valid but not implemented, see top comment */
|
||||
|
||||
pszPathInLength = lstrlenA(pszPathIn);
|
||||
pszMoreLength = lstrlenA(pszMore);
|
||||
|
||||
/* prevent segfaults - the complete implementation below is buggy */
|
||||
if (pszPathInLength < 3)
|
||||
return E_FAIL;
|
||||
|
||||
backslashIn = (pszPathIn[pszPathInLength - 1] == _PATH_SEPARATOR_CHR) ? TRUE : FALSE;
|
||||
backslashMore = (pszMore[0] == _PATH_SEPARATOR_CHR) ? TRUE : FALSE;
|
||||
@ -40,6 +64,9 @@ HRESULT PATH_ALLOC_COMBINE(PCWSTR pszPathIn, PCWSTR pszMore, unsigned long dwFla
|
||||
sizeOfBuffer = (pszPathOutLength + 1) * 2;
|
||||
|
||||
pszPathOut = (PWSTR) HeapAlloc(GetProcessHeap(), 0, sizeOfBuffer * 2);
|
||||
if (!pszPathOut)
|
||||
return E_OUTOFMEMORY;
|
||||
|
||||
swprintf_s(pszPathOut, sizeOfBuffer, L"%c:%s", pszPathIn[0], pszMore);
|
||||
|
||||
*ppszPathOut = pszPathOut;
|
||||
@ -55,6 +82,8 @@ HRESULT PATH_ALLOC_COMBINE(PCWSTR pszPathIn, PCWSTR pszMore, unsigned long dwFla
|
||||
sizeOfBuffer = (pszPathOutLength + 1) * 2;
|
||||
|
||||
pszPathOut = (PWSTR) HeapAlloc(GetProcessHeap(), 0, sizeOfBuffer * 2);
|
||||
if (!pszPathOut)
|
||||
return E_OUTOFMEMORY;
|
||||
|
||||
if (backslashIn)
|
||||
swprintf_s(pszPathOut, sizeOfBuffer, L"%s%s", pszPathIn, pszMore);
|
||||
@ -67,7 +96,7 @@ HRESULT PATH_ALLOC_COMBINE(PCWSTR pszPathIn, PCWSTR pszMore, unsigned long dwFla
|
||||
}
|
||||
#endif
|
||||
|
||||
return S_OK;
|
||||
return E_FAIL;
|
||||
}
|
||||
|
||||
#else
|
||||
@ -81,15 +110,27 @@ HRESULT PATH_ALLOC_COMBINE(PCSTR pszPathIn, PCSTR pszMore, unsigned long dwFlags
|
||||
int pszPathInLength;
|
||||
int pszPathOutLength;
|
||||
|
||||
if (!pszPathIn)
|
||||
return S_FALSE;
|
||||
WLog_WARN(TAG, "%s: has known bugs and needs fixing.", __FUNCTION__);
|
||||
|
||||
if (!ppszPathOut)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszPathIn && !pszMore)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszMore)
|
||||
return S_FALSE;
|
||||
return E_FAIL; /* valid but not implemented, see top comment */
|
||||
|
||||
if (!pszPathIn)
|
||||
return E_FAIL; /* valid but not implemented, see top comment */
|
||||
|
||||
pszPathInLength = lstrlenA(pszPathIn);
|
||||
pszMoreLength = lstrlenA(pszMore);
|
||||
|
||||
/* prevent segfaults - the complete implementation below is buggy */
|
||||
if (pszPathInLength < 3)
|
||||
return E_FAIL;
|
||||
|
||||
backslashIn = (pszPathIn[pszPathInLength - 1] == _PATH_SEPARATOR_CHR) ? TRUE : FALSE;
|
||||
backslashMore = (pszMore[0] == _PATH_SEPARATOR_CHR) ? TRUE : FALSE;
|
||||
|
||||
@ -103,6 +144,9 @@ HRESULT PATH_ALLOC_COMBINE(PCSTR pszPathIn, PCSTR pszMore, unsigned long dwFlags
|
||||
sizeOfBuffer = (pszPathOutLength + 1) * 2;
|
||||
|
||||
pszPathOut = (PSTR) HeapAlloc(GetProcessHeap(), 0, sizeOfBuffer * 2);
|
||||
if (!pszPathOut)
|
||||
return E_OUTOFMEMORY;
|
||||
|
||||
sprintf_s(pszPathOut, sizeOfBuffer, "%c:%s", pszPathIn[0], pszMore);
|
||||
|
||||
*ppszPathOut = pszPathOut;
|
||||
@ -118,6 +162,8 @@ HRESULT PATH_ALLOC_COMBINE(PCSTR pszPathIn, PCSTR pszMore, unsigned long dwFlags
|
||||
sizeOfBuffer = (pszPathOutLength + 1) * 2;
|
||||
|
||||
pszPathOut = (PSTR) HeapAlloc(GetProcessHeap(), 0, sizeOfBuffer * 2);
|
||||
if (!pszPathOut)
|
||||
return E_OUTOFMEMORY;
|
||||
|
||||
if (backslashIn)
|
||||
sprintf_s(pszPathOut, sizeOfBuffer, "%s%s", pszPathIn, pszMore);
|
||||
@ -129,7 +175,7 @@ HRESULT PATH_ALLOC_COMBINE(PCSTR pszPathIn, PCSTR pszMore, unsigned long dwFlags
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
return E_FAIL;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -17,10 +17,10 @@ HRESULT PATH_CCH_ADD_EXTENSION(PWSTR pszPath, size_t cchPath, PCWSTR pszExt)
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszExt)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszExtLength = lstrlenW(pszExt);
|
||||
pszPathLength = lstrlenW(pszPath);
|
||||
@ -45,7 +45,7 @@ HRESULT PATH_CCH_ADD_EXTENSION(PWSTR pszPath, size_t cchPath, PCWSTR pszExt)
|
||||
return S_OK;
|
||||
}
|
||||
#endif
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
}
|
||||
|
||||
#else
|
||||
@ -59,10 +59,10 @@ HRESULT PATH_CCH_ADD_EXTENSION(PSTR pszPath, size_t cchPath, PCSTR pszExt)
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszExt)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszExtLength = lstrlenA(pszExt);
|
||||
pszPathLength = lstrlenA(pszPath);
|
||||
@ -87,7 +87,7 @@ HRESULT PATH_CCH_ADD_EXTENSION(PSTR pszPath, size_t cchPath, PCSTR pszExt)
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -12,7 +12,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR(PWSTR pszPath, size_t cchPath)
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszPathLength = lstrlenW(pszPath);
|
||||
|
||||
@ -27,7 +27,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR(PWSTR pszPath, size_t cchPath)
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
}
|
||||
|
||||
#else
|
||||
@ -37,7 +37,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR(PSTR pszPath, size_t cchPath)
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszPathLength = lstrlenA(pszPath);
|
||||
|
||||
@ -52,7 +52,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR(PSTR pszPath, size_t cchPath)
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -12,7 +12,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR_EX(PWSTR pszPath, size_t cchPath, PWSTR* ppszEnd,
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszPathLength = lstrlenW(pszPath);
|
||||
|
||||
@ -27,7 +27,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR_EX(PWSTR pszPath, size_t cchPath, PWSTR* ppszEnd,
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
}
|
||||
|
||||
#else
|
||||
@ -37,7 +37,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR_EX(PSTR pszPath, size_t cchPath, PSTR* ppszEnd, s
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszPathLength = lstrlenA(pszPath);
|
||||
|
||||
@ -52,7 +52,7 @@ HRESULT PATH_CCH_ADD_SEPARATOR_EX(PSTR pszPath, size_t cchPath, PSTR* ppszEnd, s
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -17,10 +17,13 @@ HRESULT PATH_CCH_APPEND(PWSTR pszPath, size_t cchPath, PCWSTR pszMore)
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszMore)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (cchPath == 0 || cchPath > PATHCCH_MAX_CCH)
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszMoreLength = lstrlenW(pszMore);
|
||||
pszPathLength = lstrlenW(pszPath);
|
||||
@ -54,7 +57,7 @@ HRESULT PATH_CCH_APPEND(PWSTR pszPath, size_t cchPath, PCWSTR pszMore)
|
||||
}
|
||||
#endif
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_FILENAME_EXCED_RANGE);
|
||||
}
|
||||
|
||||
#else
|
||||
@ -67,10 +70,13 @@ HRESULT PATH_CCH_APPEND(PSTR pszPath, size_t cchPath, PCSTR pszMore)
|
||||
size_t pszPathLength;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!pszMore)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (cchPath == 0 || cchPath > PATHCCH_MAX_CCH)
|
||||
return E_INVALIDARG;
|
||||
|
||||
pszMoreLength = lstrlenA(pszMore);
|
||||
pszPathLength = lstrlenA(pszPath);
|
||||
@ -103,7 +109,7 @@ HRESULT PATH_CCH_APPEND(PSTR pszPath, size_t cchPath, PCSTR pszMore)
|
||||
}
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return HRESULT_FROM_WIN32(ERROR_FILENAME_EXCED_RANGE);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -63,6 +63,9 @@
|
||||
#define SHARED_LIBRARY_EXT SHARED_LIBRARY_EXT_SO
|
||||
#endif
|
||||
|
||||
#include "../log.h"
|
||||
#define TAG WINPR_TAG("path")
|
||||
|
||||
/*
|
||||
* PathCchAddBackslash
|
||||
*/
|
||||
@ -127,12 +130,14 @@
|
||||
|
||||
HRESULT PathCchRemoveBackslashA(PSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchRemoveBackslashW(PWSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -195,12 +200,14 @@ HRESULT PathCchRemoveBackslashW(PWSTR pszPath, size_t cchPath)
|
||||
|
||||
HRESULT PathCchRemoveBackslashExA(PSTR pszPath, size_t cchPath, PSTR* ppszEnd, size_t* pcchRemaining)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchRemoveBackslashExW(PWSTR pszPath, size_t cchPath, PWSTR* ppszEnd, size_t* pcchRemaining)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -337,12 +344,14 @@ HRESULT PathCchRemoveBackslashExW(PWSTR pszPath, size_t cchPath, PWSTR* ppszEnd,
|
||||
|
||||
HRESULT PathCchAppendExA(PSTR pszPath, size_t cchPath, PCSTR pszMore, unsigned long dwFlags)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchAppendExW(PWSTR pszPath, size_t cchPath, PCWSTR pszMore, unsigned long dwFlags)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -351,12 +360,14 @@ HRESULT PathCchAppendExW(PWSTR pszPath, size_t cchPath, PCWSTR pszMore, unsigned
|
||||
|
||||
HRESULT PathCchCanonicalizeA(PSTR pszPathOut, size_t cchPathOut, PCSTR pszPathIn)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchCanonicalizeW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPathIn)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -365,12 +376,14 @@ HRESULT PathCchCanonicalizeW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPath
|
||||
|
||||
HRESULT PathCchCanonicalizeExA(PSTR pszPathOut, size_t cchPathOut, PCSTR pszPathIn, unsigned long dwFlags)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchCanonicalizeExW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPathIn, unsigned long dwFlags)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -379,12 +392,14 @@ HRESULT PathCchCanonicalizeExW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPa
|
||||
|
||||
HRESULT PathAllocCanonicalizeA(PCSTR pszPathIn, unsigned long dwFlags, PSTR* ppszPathOut)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathAllocCanonicalizeW(PCWSTR pszPathIn, unsigned long dwFlags, PWSTR* ppszPathOut)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -393,12 +408,14 @@ HRESULT PathAllocCanonicalizeW(PCWSTR pszPathIn, unsigned long dwFlags, PWSTR* p
|
||||
|
||||
HRESULT PathCchCombineA(PSTR pszPathOut, size_t cchPathOut, PCSTR pszPathIn, PCSTR pszMore)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchCombineW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPathIn, PCWSTR pszMore)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -407,12 +424,14 @@ HRESULT PathCchCombineW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPathIn, P
|
||||
|
||||
HRESULT PathCchCombineExA(PSTR pszPathOut, size_t cchPathOut, PCSTR pszPathIn, PCSTR pszMore, unsigned long dwFlags)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchCombineExW(PWSTR pszPathOut, size_t cchPathOut, PCWSTR pszPathIn, PCWSTR pszMore, unsigned long dwFlags)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -493,6 +512,9 @@ HRESULT PathCchFindExtensionA(PCSTR pszPath, size_t cchPath, PCSTR* ppszExt)
|
||||
{
|
||||
char* p = (char*) pszPath;
|
||||
|
||||
if (!pszPath || !cchPath || !ppszExt)
|
||||
return E_INVALIDARG;
|
||||
|
||||
/* find end of string */
|
||||
|
||||
while (*p && cchPath)
|
||||
@ -501,6 +523,15 @@ HRESULT PathCchFindExtensionA(PCSTR pszPath, size_t cchPath, PCSTR* ppszExt)
|
||||
p++;
|
||||
}
|
||||
|
||||
if (*p)
|
||||
{
|
||||
/* pszPath is not null terminated within the cchPath range */
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
/* If no extension is found, ppszExt must point to the string's terminating null */
|
||||
*ppszExt = p;
|
||||
|
||||
/* search backwards for '.' */
|
||||
|
||||
while (p > pszPath)
|
||||
@ -508,21 +539,22 @@ HRESULT PathCchFindExtensionA(PCSTR pszPath, size_t cchPath, PCSTR* ppszExt)
|
||||
if (*p == '.')
|
||||
{
|
||||
*ppszExt = (PCSTR) p;
|
||||
return S_OK;
|
||||
break;
|
||||
}
|
||||
|
||||
if ((*p == '\\') || (*p == '/') || (*p == ':'))
|
||||
return S_FALSE;
|
||||
break;
|
||||
|
||||
p--;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT PathCchFindExtensionW(PCWSTR pszPath, size_t cchPath, PCWSTR* ppszExt)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -531,12 +563,14 @@ HRESULT PathCchFindExtensionW(PCWSTR pszPath, size_t cchPath, PCWSTR* ppszExt)
|
||||
|
||||
HRESULT PathCchRenameExtensionA(PSTR pszPath, size_t cchPath, PCSTR pszExt)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchRenameExtensionW(PWSTR pszPath, size_t cchPath, PCWSTR pszExt)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -545,12 +579,14 @@ HRESULT PathCchRenameExtensionW(PWSTR pszPath, size_t cchPath, PCWSTR pszExt)
|
||||
|
||||
HRESULT PathCchRemoveExtensionA(PSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchRemoveExtensionW(PWSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -559,12 +595,14 @@ HRESULT PathCchRemoveExtensionW(PWSTR pszPath, size_t cchPath)
|
||||
|
||||
BOOL PathCchIsRootA(PCSTR pszPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
BOOL PathCchIsRootW(PCWSTR pszPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -605,12 +643,14 @@ BOOL PathIsUNCExW(PCWSTR pszPath, PCWSTR* ppszServer)
|
||||
|
||||
HRESULT PathCchSkipRootA(PCSTR pszPath, PCSTR* ppszRootEnd)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchSkipRootW(PCWSTR pszPath, PCWSTR* ppszRootEnd)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -619,12 +659,14 @@ HRESULT PathCchSkipRootW(PCWSTR pszPath, PCWSTR* ppszRootEnd)
|
||||
|
||||
HRESULT PathCchStripToRootA(PSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchStripToRootW(PWSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -634,27 +676,29 @@ HRESULT PathCchStripToRootW(PWSTR pszPath, size_t cchPath)
|
||||
HRESULT PathCchStripPrefixA(PSTR pszPath, size_t cchPath)
|
||||
{
|
||||
BOOL hasPrefix;
|
||||
BOOL deviceNamespace;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (cchPath < 4)
|
||||
return S_FALSE;
|
||||
if (cchPath < 4 || cchPath > PATHCCH_MAX_CCH)
|
||||
return E_INVALIDARG;
|
||||
|
||||
hasPrefix = ((pszPath[0] == '\\') && (pszPath[1] == '\\') &&
|
||||
(pszPath[2] == '?') && (pszPath[3] == '\\')) ? TRUE : FALSE;
|
||||
|
||||
if (hasPrefix)
|
||||
{
|
||||
if (cchPath < 7)
|
||||
if (cchPath < 6)
|
||||
return S_FALSE;
|
||||
|
||||
deviceNamespace = ((pszPath[5] == ':') && (pszPath[6] == '\\')) ? TRUE : FALSE;
|
||||
|
||||
if (deviceNamespace)
|
||||
if (IsCharAlpha(pszPath[4]) && (pszPath[5] == ':')) /* like C: */
|
||||
{
|
||||
memmove_s(pszPath, cchPath, &pszPath[4], cchPath - 4);
|
||||
/* since the passed pszPath must not necessarily be null terminated
|
||||
* and we always have enough space after the strip we can always
|
||||
* ensure the null termination of the stripped result
|
||||
*/
|
||||
pszPath[cchPath - 4] = 0;
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
@ -665,27 +709,32 @@ HRESULT PathCchStripPrefixA(PSTR pszPath, size_t cchPath)
|
||||
HRESULT PathCchStripPrefixW(PWSTR pszPath, size_t cchPath)
|
||||
{
|
||||
BOOL hasPrefix;
|
||||
BOOL deviceNamespace;
|
||||
|
||||
if (!pszPath)
|
||||
return S_FALSE;
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (cchPath < 4)
|
||||
return S_FALSE;
|
||||
if (cchPath < 4 || cchPath > PATHCCH_MAX_CCH)
|
||||
return E_INVALIDARG;
|
||||
|
||||
hasPrefix = ((pszPath[0] == '\\') && (pszPath[1] == '\\') &&
|
||||
(pszPath[2] == '?') && (pszPath[3] == '\\')) ? TRUE : FALSE;
|
||||
|
||||
if (hasPrefix)
|
||||
{
|
||||
if (cchPath < 7)
|
||||
if (cchPath < 6)
|
||||
return S_FALSE;
|
||||
|
||||
deviceNamespace = ((pszPath[5] == ':') && (pszPath[6] == '\\')) ? TRUE : FALSE;
|
||||
if (cchPath < (lstrlenW(&pszPath[4]) + 1))
|
||||
return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
|
||||
|
||||
if (deviceNamespace)
|
||||
if (IsCharAlpha(pszPath[4]) && (pszPath[5] == ':')) /* like C: */
|
||||
{
|
||||
wmemmove_s(pszPath, cchPath, &pszPath[4], cchPath - 4);
|
||||
/* since the passed pszPath must not necessarily be null terminated
|
||||
* and we always have enough space after the strip we can always
|
||||
* ensure the null termination of the stripped result
|
||||
*/
|
||||
pszPath[cchPath - 4] = 0;
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
@ -699,12 +748,14 @@ HRESULT PathCchStripPrefixW(PWSTR pszPath, size_t cchPath)
|
||||
|
||||
HRESULT PathCchRemoveFileSpecA(PSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
HRESULT PathCchRemoveFileSpecW(PWSTR pszPath, size_t cchPath)
|
||||
{
|
||||
return 0;
|
||||
WLog_ERR(TAG, "%s: not implemented", __FUNCTION__);
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -760,13 +811,13 @@ HRESULT PathCchConvertStyleA(PSTR pszPath, size_t cchPath, unsigned long dwFlags
|
||||
else
|
||||
{
|
||||
/* Unexpected error */
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Gangnam style? */
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
@ -817,13 +868,13 @@ HRESULT PathCchConvertStyleW(PWSTR pszPath, size_t cchPath, unsigned long dwFlag
|
||||
else
|
||||
{
|
||||
/* Unexpected error */
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Gangnam style? */
|
||||
return S_FALSE;
|
||||
return E_FAIL;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
|
@ -28,11 +28,19 @@
|
||||
|
||||
#include <winpr/crt.h>
|
||||
#include <winpr/heap.h>
|
||||
#include <winpr/file.h>
|
||||
#include <winpr/tchar.h>
|
||||
#include <winpr/environment.h>
|
||||
|
||||
#include <winpr/path.h>
|
||||
|
||||
#if defined(WIN32)
|
||||
#include <Shlobj.h>
|
||||
#endif
|
||||
|
||||
static char* GetPath_XDG_CONFIG_HOME(void);
|
||||
static char* GetPath_XDG_RUNTIME_DIR(void);
|
||||
|
||||
/**
|
||||
* SHGetKnownFolderPath function:
|
||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/bb762188/
|
||||
@ -43,7 +51,7 @@
|
||||
* http://standards.freedesktop.org/basedir-spec/basedir-spec-latest.html
|
||||
*/
|
||||
|
||||
char* GetEnvAlloc(LPCSTR lpName)
|
||||
static char* GetEnvAlloc(LPCSTR lpName)
|
||||
{
|
||||
DWORD length;
|
||||
char* env = NULL;
|
||||
@ -62,7 +70,7 @@ char* GetEnvAlloc(LPCSTR lpName)
|
||||
return env;
|
||||
}
|
||||
|
||||
char* GetPath_HOME()
|
||||
static char* GetPath_HOME(void)
|
||||
{
|
||||
char* path = NULL;
|
||||
|
||||
@ -80,7 +88,7 @@ char* GetPath_HOME()
|
||||
return path;
|
||||
}
|
||||
|
||||
char* GetPath_TEMP()
|
||||
static char* GetPath_TEMP(void)
|
||||
{
|
||||
char* path = NULL;
|
||||
|
||||
@ -96,11 +104,14 @@ char* GetPath_TEMP()
|
||||
return path;
|
||||
}
|
||||
|
||||
char* GetPath_XDG_DATA_HOME()
|
||||
static char* GetPath_XDG_DATA_HOME(void)
|
||||
{
|
||||
char* path = NULL;
|
||||
char* home = NULL;
|
||||
|
||||
#if defined(WIN32)
|
||||
path = GetPath_XDG_CONFIG_HOME();
|
||||
#else
|
||||
char* home = NULL;
|
||||
/**
|
||||
* There is a single base directory relative to which user-specific data files should be written.
|
||||
* This directory is defined by the environment variable $XDG_DATA_HOME.
|
||||
@ -127,15 +138,28 @@ char* GetPath_XDG_DATA_HOME()
|
||||
sprintf(path, "%s%s", home, "/.local/share");
|
||||
|
||||
free(home);
|
||||
#endif
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
char* GetPath_XDG_CONFIG_HOME()
|
||||
static char* GetPath_XDG_CONFIG_HOME(void)
|
||||
{
|
||||
char* path = NULL;
|
||||
char* home = NULL;
|
||||
|
||||
#if defined(WIN32)
|
||||
path = calloc(MAX_PATH, sizeof(char));
|
||||
if (!path)
|
||||
return NULL;
|
||||
|
||||
if (SHGetFolderPathA(0, CSIDL_APPDATA, NULL,
|
||||
SHGFP_TYPE_CURRENT, path) != S_OK)
|
||||
{
|
||||
free(path);
|
||||
return NULL;
|
||||
}
|
||||
#else
|
||||
char* home = NULL;
|
||||
/**
|
||||
* There is a single base directory relative to which user-specific configuration files should be written.
|
||||
* This directory is defined by the environment variable $XDG_CONFIG_HOME.
|
||||
@ -166,15 +190,27 @@ char* GetPath_XDG_CONFIG_HOME()
|
||||
sprintf(path, "%s%s", home, "/.config");
|
||||
|
||||
free(home);
|
||||
#endif
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
char* GetPath_XDG_CACHE_HOME()
|
||||
static char* GetPath_XDG_CACHE_HOME(void)
|
||||
{
|
||||
char* path = NULL;
|
||||
char* home = NULL;
|
||||
|
||||
#if defined(WIN32)
|
||||
home = GetPath_XDG_RUNTIME_DIR();
|
||||
if (home)
|
||||
{
|
||||
path = GetCombinedPath(home, "cache");
|
||||
if (!PathFileExistsA(path))
|
||||
if (!CreateDirectoryA(path, NULL))
|
||||
path = NULL;
|
||||
}
|
||||
free(home);
|
||||
#else
|
||||
/**
|
||||
* There is a single base directory relative to which user-specific non-essential (cached) data should be written.
|
||||
* This directory is defined by the environment variable $XDG_CACHE_HOME.
|
||||
@ -201,14 +237,26 @@ char* GetPath_XDG_CACHE_HOME()
|
||||
sprintf(path, "%s%s", home, "/.cache");
|
||||
|
||||
free(home);
|
||||
#endif
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
char* GetPath_XDG_RUNTIME_DIR()
|
||||
char* GetPath_XDG_RUNTIME_DIR(void)
|
||||
{
|
||||
char* path = NULL;
|
||||
#if defined(WIN32)
|
||||
path = calloc(MAX_PATH, sizeof(char));
|
||||
if (!path)
|
||||
return NULL;
|
||||
|
||||
if (SHGetFolderPathA(0, CSIDL_LOCAL_APPDATA, NULL,
|
||||
SHGFP_TYPE_CURRENT, path) != S_OK)
|
||||
{
|
||||
free(path);
|
||||
return NULL;
|
||||
}
|
||||
#else
|
||||
/**
|
||||
* There is a single base directory relative to which user-specific runtime files and other file objects should be placed.
|
||||
* This directory is defined by the environment variable $XDG_RUNTIME_DIR.
|
||||
@ -237,6 +285,7 @@ char* GetPath_XDG_RUNTIME_DIR()
|
||||
*/
|
||||
|
||||
path = GetEnvAlloc("XDG_RUNTIME_DIR");
|
||||
#endif
|
||||
|
||||
if (path)
|
||||
return path;
|
||||
@ -372,6 +421,50 @@ char* GetCombinedPath(const char* basePath, const char* subPath)
|
||||
return path;
|
||||
}
|
||||
|
||||
BOOL PathMakePathA(LPCSTR path, LPSECURITY_ATTRIBUTES lpAttributes)
|
||||
{
|
||||
size_t length;
|
||||
const char delim = PathGetSeparatorA(0);
|
||||
char* cur;
|
||||
char* copy_org = _strdup(path);
|
||||
char* copy = copy_org;
|
||||
|
||||
if (!copy_org)
|
||||
return FALSE;
|
||||
|
||||
length = strlen(copy_org);
|
||||
|
||||
/* Find first path element that exists. */
|
||||
while (copy)
|
||||
{
|
||||
if (!PathFileExistsA(copy))
|
||||
{
|
||||
cur = strrchr(copy, delim);
|
||||
if (cur)
|
||||
*cur = '\0';
|
||||
}
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
/* Create directories. */
|
||||
while(copy)
|
||||
{
|
||||
if (!PathFileExistsA(copy))
|
||||
{
|
||||
if (!CreateDirectoryA(copy, NULL))
|
||||
break;
|
||||
}
|
||||
if (strlen(copy) < length)
|
||||
copy[strlen(copy)] = delim;
|
||||
else
|
||||
break;
|
||||
}
|
||||
free (copy_org);
|
||||
|
||||
return PathFileExistsA(path);
|
||||
}
|
||||
|
||||
BOOL PathFileExistsA(LPCSTR pszPath)
|
||||
{
|
||||
struct stat stat_info;
|
||||
|
@ -27,7 +27,8 @@ set(${MODULE_PREFIX}_TESTS
|
||||
TestPathCchStripToRoot.c
|
||||
TestPathCchStripPrefix.c
|
||||
TestPathCchRemoveFileSpec.c
|
||||
TestPathShell.c)
|
||||
TestPathShell.c
|
||||
TestPathMakePath.c)
|
||||
|
||||
create_test_sourcelist(${MODULE_PREFIX}_SRCS
|
||||
${${MODULE_PREFIX}_DRIVER}
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathAllocCanonicalize(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,12 @@ int TestPathCchAddBackslash(int argc, char* argv[])
|
||||
HRESULT status;
|
||||
TCHAR Path[PATHCCH_MAX_CCH];
|
||||
|
||||
/**
|
||||
* PathCchAddBackslash returns S_OK if the function was successful,
|
||||
* S_FALSE if the path string already ends in a backslash,
|
||||
* or an error code otherwise.
|
||||
*/
|
||||
|
||||
_tcscpy(Path, testPathNoBackslash);
|
||||
|
||||
/* Add a backslash to a path without a trailing backslash, expect S_OK */
|
||||
@ -21,7 +27,7 @@ int TestPathCchAddBackslash(int argc, char* argv[])
|
||||
|
||||
if (status != S_OK)
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslash status: 0x%08X\n"), (int) status);
|
||||
_tprintf(_T("PathCchAddBackslash status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -39,7 +45,7 @@ int TestPathCchAddBackslash(int argc, char* argv[])
|
||||
|
||||
if (status != S_FALSE)
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslash status: 0x%08X\n"), (int) status);
|
||||
_tprintf(_T("PathCchAddBackslash status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -49,6 +55,40 @@ int TestPathCchAddBackslash(int argc, char* argv[])
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Use NULL PSTR, expect FAILED(status) */
|
||||
|
||||
status = PathCchAddBackslash(NULL, PATHCCH_MAX_CCH);
|
||||
|
||||
if (SUCCEEDED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslash unexpectedly succeded with null buffer. Status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Use insufficient size value, expect FAILED(status) */
|
||||
|
||||
_tcscpy(Path, _T("C:\\tmp"));
|
||||
|
||||
status = PathCchAddBackslash(Path, 7);
|
||||
|
||||
if (SUCCEEDED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslash unexpectedly succeded with insufficient buffer size. Status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Use minimum required size value, expect S_OK */
|
||||
|
||||
_tcscpy(Path, _T("C:\\tmp"));
|
||||
|
||||
status = PathCchAddBackslash(Path, 8);
|
||||
|
||||
if (status != S_OK)
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslash failed with status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -15,6 +15,12 @@ int TestPathCchAddBackslashEx(int argc, char* argv[])
|
||||
size_t cchRemaining;
|
||||
TCHAR Path[PATHCCH_MAX_CCH];
|
||||
|
||||
/**
|
||||
* PathCchAddBackslashEx returns S_OK if the function was successful,
|
||||
* S_FALSE if the path string already ends in a backslash,
|
||||
* or an error code otherwise.
|
||||
*/
|
||||
|
||||
_tcscpy(Path, testPathNoBackslash);
|
||||
|
||||
/* Add a backslash to a path without a trailing backslash, expect S_OK */
|
||||
@ -51,6 +57,41 @@ int TestPathCchAddBackslashEx(int argc, char* argv[])
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Use NULL PSTR, expect FAILED(status) */
|
||||
|
||||
status = PathCchAddBackslashEx(NULL, PATHCCH_MAX_CCH, NULL, NULL);
|
||||
|
||||
if (SUCCEEDED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslashEx unexpectedly succeded with null buffer. Status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Use insufficient size value, expect FAILED(status) */
|
||||
|
||||
_tcscpy(Path, _T("C:\\tmp"));
|
||||
|
||||
status = PathCchAddBackslashEx(Path, 7, NULL, NULL);
|
||||
|
||||
if (SUCCEEDED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslashEx unexpectedly succeded with insufficient buffer size. Status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Use minimum required size value, expect S_OK */
|
||||
|
||||
_tcscpy(Path, _T("C:\\tmp"));
|
||||
|
||||
status = PathCchAddBackslashEx(Path, 8, NULL, NULL);
|
||||
|
||||
if (status != S_OK)
|
||||
{
|
||||
_tprintf(_T("PathCchAddBackslashEx failed with status: 0x%08X\n"), (unsigned) status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -87,6 +87,45 @@ int TestPathCchAddExtension(int argc, char* argv[])
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Path: NULL */
|
||||
|
||||
status = PathCchAddExtension(NULL, PATHCCH_MAX_CCH, testExtDot);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchAddExtension with null buffer returned status: 0x%08X (expected E_INVALIDARG)\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Extension: NULL */
|
||||
|
||||
status = PathCchAddExtension(Path, PATHCCH_MAX_CCH, NULL);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchAddExtension with null extension returned status: 0x%08X (expected E_INVALIDARG)\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Insufficient Buffer size */
|
||||
|
||||
_tcscpy(Path, _T("C:\\456789"));
|
||||
status = PathCchAddExtension(Path, 9 + 4, _T(".jpg"));
|
||||
if (SUCCEEDED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAddExtension with insufficient buffer unexpectedly succeeded with status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Minimum required buffer size */
|
||||
|
||||
_tcscpy(Path, _T("C:\\456789"));
|
||||
status = PathCchAddExtension(Path, 9 + 4 + 1, _T(".jpg"));
|
||||
if (FAILED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAddExtension with sufficient buffer unexpectedly failed with status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -15,6 +15,7 @@ int TestPathCchAppend(int argc, char* argv[])
|
||||
{
|
||||
HRESULT status;
|
||||
TCHAR Path[PATHCCH_MAX_CCH];
|
||||
size_t i;
|
||||
|
||||
/* Base Path: Backslash, More Path: No Backslash */
|
||||
|
||||
@ -88,6 +89,53 @@ int TestPathCchAppend(int argc, char* argv[])
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* According to msdn a NULL Path is an invalid argument */
|
||||
status = PathCchAppend(NULL, PATHCCH_MAX_CCH, testMorePathNoBackslash);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchAppend with NULL path unexpectedly returned status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* According to msdn a NULL pszMore is an invalid argument (although optional !?) */
|
||||
_tcscpy(Path, testBasePathNoBackslash);
|
||||
status = PathCchAppend(Path, PATHCCH_MAX_CCH, NULL);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchAppend with NULL pszMore unexpectedly returned status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* According to msdn cchPath must be > 0 and <= PATHCCH_MAX_CCH */
|
||||
_tcscpy(Path, testBasePathNoBackslash);
|
||||
status = PathCchAppend(Path, 0, testMorePathNoBackslash);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchAppend with cchPath value 0 unexpectedly returned status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
_tcscpy(Path, testBasePathNoBackslash);
|
||||
status = PathCchAppend(Path, PATHCCH_MAX_CCH + 1, testMorePathNoBackslash);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchAppend with cchPath value > PATHCCH_MAX_CCH unexpectedly returned status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Resulting file must not exceed PATHCCH_MAX_CCH */
|
||||
|
||||
for (i = 0; i < PATHCCH_MAX_CCH - 1; i++)
|
||||
Path[i] = _T('X');
|
||||
|
||||
Path[PATHCCH_MAX_CCH - 1] = 0;
|
||||
|
||||
status = PathCchAppend(Path, PATHCCH_MAX_CCH, _T("\\This cannot be appended to Path"));
|
||||
if (SUCCEEDED(status))
|
||||
{
|
||||
_tprintf(_T("PathCchAppend unexepectedly succeeded with status: 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchAppendEx(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchCanonicalize(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchCanonicalizeEx(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchCombine(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchCombineEx(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -10,13 +10,95 @@ static const char testPathExtension[] = "C:\\Windows\\System32\\cmd.exe";
|
||||
int TestPathCchFindExtension(int argc, char* argv[])
|
||||
{
|
||||
PCSTR pszExt;
|
||||
PCSTR pszTmp;
|
||||
HRESULT hr;
|
||||
|
||||
/* Test invalid args */
|
||||
|
||||
hr = PathCchFindExtensionA(NULL, sizeof(testPathExtension), &pszExt);
|
||||
if (SUCCEEDED(hr))
|
||||
{
|
||||
printf("PathCchFindExtensionA unexpectedly succeeded with pszPath = NULL. result: 0x%08X\n", (ULONG)hr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
hr = PathCchFindExtensionA(testPathExtension, 0, &pszExt);
|
||||
if (SUCCEEDED(hr))
|
||||
{
|
||||
printf("PathCchFindExtensionA unexpectedly succeeded with cchPath = 0. result: 0x%08X\n", (ULONG)hr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
hr = PathCchFindExtensionA(testPathExtension, sizeof(testPathExtension), NULL);
|
||||
if (SUCCEEDED(hr))
|
||||
{
|
||||
printf("PathCchFindExtensionA unexpectedly succeeded with ppszExt = NULL. result: 0x%08X\n", (ULONG)hr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
/* Test missing null-termination of pszPath */
|
||||
|
||||
hr = PathCchFindExtensionA(_T("c:\\456.789"), 9, &pszExt);
|
||||
if (SUCCEEDED(hr))
|
||||
{
|
||||
printf("PathCchFindExtensionA unexpectedly succeeded with unterminated pszPath. result: 0x%08X\n", (ULONG)hr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
/* Test passing of an empty terminated string (must succeed) */
|
||||
|
||||
pszExt = NULL;
|
||||
pszTmp = _T("");
|
||||
hr = PathCchFindExtensionA(pszTmp, 1, &pszExt);
|
||||
if (hr != S_OK)
|
||||
{
|
||||
printf("PathCchFindExtensionA failed with an empty terminated string. result: 0x%08X\n", (ULONG)hr);
|
||||
return -1;
|
||||
}
|
||||
/* pszExt must point to the strings terminating 0 now */
|
||||
if (pszExt != pszTmp)
|
||||
{
|
||||
printf("PathCchFindExtensionA failed with an empty terminated string: pszExt pointer mismatch\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
/* Test a path without file extension (must succeed) */
|
||||
|
||||
pszExt = NULL;
|
||||
pszTmp = _T("c:\\4.678\\");
|
||||
hr = PathCchFindExtensionA(pszTmp, 10, &pszExt);
|
||||
if (hr != S_OK)
|
||||
{
|
||||
printf("PathCchFindExtensionA failed with a directory path. result: 0x%08X\n", (ULONG)hr);
|
||||
return -1;
|
||||
}
|
||||
/* The extension must not have been found and pszExt must point to the
|
||||
* strings terminating NULL now */
|
||||
if (pszExt != &pszTmp[9])
|
||||
{
|
||||
printf("PathCchFindExtensionA failed with a directory path: pszExt pointer mismatch\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
/* Non-special tests */
|
||||
|
||||
pszExt = NULL;
|
||||
if (PathCchFindExtensionA(testPathExtension, sizeof(testPathExtension), &pszExt) != S_OK)
|
||||
{
|
||||
printf("PathCchFindExtensionA failure: expected S_OK\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!pszExt || _tcscmp(pszExt, _T(".exe")))
|
||||
{
|
||||
printf("PathCchFindExtensionA failure: unexpected extension\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
printf("Extension: %s\n", pszExt);
|
||||
|
||||
return 0;
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchIsRoot(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchRemoveBackslash(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchRemoveBackslashEx(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchRemoveExtension(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchRemoveFileSpec(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchRenameExtension(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchSkipRoot(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -12,6 +12,8 @@
|
||||
|
||||
static const TCHAR testPathPrefixFileNamespace[] = _T("\\\\?\\C:\\Program Files\\");
|
||||
static const TCHAR testPathNoPrefixFileNamespace[] = _T("C:\\Program Files\\");
|
||||
static const TCHAR testPathPrefixFileNamespaceMinimum[] = _T("\\\\?\\C:");
|
||||
static const TCHAR testPathNoPrefixFileNamespaceMinimum[] = _T("C:");
|
||||
|
||||
static const TCHAR testPathPrefixDeviceNamespace[] = _T("\\\\?\\GLOBALROOT");
|
||||
|
||||
@ -19,6 +21,13 @@ int TestPathCchStripPrefix(int argc, char* argv[])
|
||||
{
|
||||
HRESULT status;
|
||||
TCHAR Path[PATHCCH_MAX_CCH];
|
||||
int i;
|
||||
|
||||
/**
|
||||
* PathCchStripPrefix returns S_OK if the prefix was removed, S_FALSE if
|
||||
* the path did not have a prefix to remove, or an HRESULT failure code.
|
||||
*/
|
||||
|
||||
|
||||
/* Path with prefix (File Namespace) */
|
||||
|
||||
@ -56,6 +65,53 @@ int TestPathCchStripPrefix(int argc, char* argv[])
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* NULL Path */
|
||||
status = PathCchStripPrefix(NULL, PATHCCH_MAX_CCH);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchStripPrefix with null path unexpectedly succeeded with status 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Invalid cchPath values: 0, 1, 2, 3 and > PATHCCH_MAX_CCH */
|
||||
for (i = 0; i < 5; i++)
|
||||
{
|
||||
_tcscpy(Path, testPathPrefixFileNamespace);
|
||||
if (i == 4)
|
||||
i = PATHCCH_MAX_CCH + 1;
|
||||
status = PathCchStripPrefix(Path, i);
|
||||
if (status != E_INVALIDARG)
|
||||
{
|
||||
_tprintf(_T("PathCchStripPrefix with invalid cchPath value %d unexpectedly succeeded with status 0x%08X\n"), i, status);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
/* Minimum Path that would get successfully stripped on windows */
|
||||
_tcscpy(Path, testPathPrefixFileNamespaceMinimum);
|
||||
i = sizeof(testPathPrefixFileNamespaceMinimum) / sizeof(TCHAR);
|
||||
i = i - 1; /* include testing of a non-null terminated string */
|
||||
status = PathCchStripPrefix(Path, i);
|
||||
if (status != S_OK)
|
||||
{
|
||||
_tprintf(_T("PathCchStripPrefix with minimum valid strippable path length unexpectedly returned status 0x%08X\n"), status);
|
||||
return -1;
|
||||
}
|
||||
if (_tcscmp(Path, testPathNoPrefixFileNamespaceMinimum))
|
||||
{
|
||||
_tprintf(_T("Path Mismatch: Actual: %s, Expected: %s\n"), Path, testPathNoPrefixFileNamespaceMinimum);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Invalid drive letter symbol */
|
||||
_tcscpy(Path, _T("\\\\?\\5:"));
|
||||
status = PathCchStripPrefix(Path, 6);
|
||||
if (status == S_OK)
|
||||
{
|
||||
_tprintf(_T("PathCchStripPrefix with invalid drive letter symbol unexpectedly succeeded\n"));
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
int TestPathCchStripToRoot(int argc, char* argv[])
|
||||
{
|
||||
printf("Warning: %s is not implemented!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
75
winpr/libwinpr/path/test/TestPathMakePath.c
Normal file
75
winpr/libwinpr/path/test/TestPathMakePath.c
Normal file
@ -0,0 +1,75 @@
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
#include <winpr/crt.h>
|
||||
#include <winpr/file.h>
|
||||
#include <winpr/path.h>
|
||||
|
||||
int TestPathMakePath(int argc, char* argv[])
|
||||
{
|
||||
int x;
|
||||
size_t baseLen;
|
||||
BOOL success;
|
||||
char tmp[64];
|
||||
char* path;
|
||||
char* cur;
|
||||
char delim = PathGetSeparatorA(0);
|
||||
char* base = GetKnownPath(KNOWN_PATH_TEMP);
|
||||
if (!base)
|
||||
{
|
||||
fprintf(stderr, "Failed to get temporary directory!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
baseLen = strlen(base);
|
||||
srand(time(NULL));
|
||||
for (x=0; x<5; x++)
|
||||
{
|
||||
sprintf(tmp, "%08X", rand());
|
||||
path = GetCombinedPath(base, tmp);
|
||||
free(base);
|
||||
if (!path)
|
||||
{
|
||||
fprintf(stderr, "GetCombinedPath failed!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
base = path;
|
||||
}
|
||||
|
||||
printf("Creating path %s\n", path);
|
||||
success = PathMakePathA(path, NULL);
|
||||
if (!success)
|
||||
{
|
||||
fprintf(stderr, "MakePath failed!\n");
|
||||
free (path);
|
||||
return -1;
|
||||
}
|
||||
|
||||
success = PathFileExistsA(path);
|
||||
if (!success)
|
||||
{
|
||||
fprintf(stderr, "MakePath lied about success!\n");
|
||||
free (path);
|
||||
return -1;
|
||||
}
|
||||
|
||||
while (strlen(path) > baseLen)
|
||||
{
|
||||
if (!RemoveDirectoryA(path))
|
||||
{
|
||||
fprintf(stderr, "RemoveDirectoryA %s failed!\n", path);
|
||||
free (path);
|
||||
return -1;
|
||||
}
|
||||
cur = strrchr(path, delim);
|
||||
if (cur)
|
||||
*cur = '\0';
|
||||
}
|
||||
|
||||
free (path);
|
||||
printf("%s success!\n", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
|
@ -1276,7 +1276,7 @@ void Inspect_InitLog()
|
||||
return;
|
||||
|
||||
if (!PathFileExistsA(filepath))
|
||||
if (!CreateDirectoryA(filepath, NULL))
|
||||
if (!PathMakePathA(filepath, NULL))
|
||||
return;
|
||||
|
||||
if (!(g_Log = WLog_Get("WinSCard")))
|
||||
|
@ -21,6 +21,8 @@
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
#include "ntlm.h"
|
||||
#include "../sspi.h"
|
||||
|
||||
@ -143,6 +145,7 @@ NTLM_AV_PAIR* ntlm_av_pair_add(NTLM_AV_PAIR* pAvPairList, NTLM_AV_ID AvId, PBYTE
|
||||
if (!pAvPair)
|
||||
return NULL;
|
||||
|
||||
assert(Value != NULL);
|
||||
pAvPair->AvId = AvId;
|
||||
pAvPair->AvLen = AvLen;
|
||||
CopyMemory(ntlm_av_pair_get_value_pointer(pAvPair), Value, AvLen);
|
||||
|
@ -37,9 +37,10 @@
|
||||
|
||||
#ifdef HAVE_EVENTFD_H
|
||||
#include <sys/eventfd.h>
|
||||
#include <errno.h>
|
||||
#endif
|
||||
|
||||
#include <errno.h>
|
||||
|
||||
#include "../handle/handle.h"
|
||||
#include "../pipe/pipe.h"
|
||||
|
||||
@ -219,7 +220,6 @@ BOOL SetEvent(HANDLE hEvent)
|
||||
|
||||
status = (length == 0) ? TRUE : FALSE;
|
||||
#else
|
||||
|
||||
if (WaitForSingleObject(hEvent, 0) != WAIT_OBJECT_0)
|
||||
{
|
||||
length = write(event->pipe_fd[1], "-", 1);
|
||||
@ -243,36 +243,29 @@ BOOL ResetEvent(HANDLE hEvent)
|
||||
ULONG Type;
|
||||
PVOID Object;
|
||||
int length;
|
||||
BOOL status;
|
||||
BOOL status = TRUE;
|
||||
WINPR_EVENT* event;
|
||||
status = FALSE;
|
||||
|
||||
if (winpr_Handle_GetInfo(hEvent, &Type, &Object))
|
||||
{
|
||||
if (!winpr_Handle_GetInfo(hEvent, &Type, &Object))
|
||||
return FALSE;
|
||||
|
||||
event = (WINPR_EVENT*) Object;
|
||||
|
||||
while (WaitForSingleObject(hEvent, 0) == WAIT_OBJECT_0)
|
||||
while (status && WaitForSingleObject(hEvent, 0) == WAIT_OBJECT_0)
|
||||
{
|
||||
do
|
||||
{
|
||||
#ifdef HAVE_EVENTFD_H
|
||||
eventfd_t value;
|
||||
|
||||
do
|
||||
{
|
||||
length = eventfd_read(event->pipe_fd[0], &value);
|
||||
#else
|
||||
length = read(event->pipe_fd[0], &length, 1);
|
||||
#endif
|
||||
}
|
||||
while ((length < 0) && (errno == EINTR));
|
||||
|
||||
if ((length > 0) && (!status))
|
||||
status = TRUE;
|
||||
|
||||
#else
|
||||
length = read(event->pipe_fd[0], &length, 1);
|
||||
|
||||
if ((length == 1) && (!status))
|
||||
status = TRUE;
|
||||
|
||||
#endif
|
||||
}
|
||||
if (length < 0)
|
||||
status = FALSE;
|
||||
}
|
||||
|
||||
return status;
|
||||
|
@ -5,6 +5,19 @@
|
||||
int TestSynchEvent(int argc, char* argv[])
|
||||
{
|
||||
HANDLE event;
|
||||
int i;
|
||||
|
||||
if (ResetEvent(NULL))
|
||||
{
|
||||
printf("ResetEvent(NULL) unexpectedly succeeded\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (SetEvent(NULL))
|
||||
{
|
||||
printf("SetEvent(NULL) unexpectedly succeeded\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
event = CreateEvent(NULL, TRUE, TRUE, NULL);
|
||||
|
||||
@ -16,23 +29,62 @@ int TestSynchEvent(int argc, char* argv[])
|
||||
|
||||
if (WaitForSingleObject(event, INFINITE) != WAIT_OBJECT_0)
|
||||
{
|
||||
printf("WaitForSingleObject(event, INFINITE) failure\n");
|
||||
printf("WaitForSingleObject failure 1\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
ResetEvent(event);
|
||||
if (!ResetEvent(event))
|
||||
{
|
||||
printf("ResetEvent failure with signaled event object\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (WaitForSingleObject(event, 0) != WAIT_TIMEOUT)
|
||||
{
|
||||
printf("WaitForSingleObject(event, 0) failure\n");
|
||||
printf("WaitForSingleObject failure 2\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
SetEvent(event);
|
||||
if (!ResetEvent(event))
|
||||
{
|
||||
/* Note: ResetEvent must also succeed if event is currently nonsignaled */
|
||||
printf("ResetEvent failure with nonsignaled event object\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!SetEvent(event))
|
||||
{
|
||||
printf("SetEvent failure with nonsignaled event object\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (WaitForSingleObject(event, 0) != WAIT_OBJECT_0)
|
||||
{
|
||||
printf("WaitForSingleObject(event, 0) failure\n");
|
||||
printf("WaitForSingleObject failure 3\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < 10000; i++)
|
||||
{
|
||||
if (!SetEvent(event))
|
||||
{
|
||||
printf("SetEvent failure with signaled event object (i = %d)\n", i);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if (!ResetEvent(event))
|
||||
{
|
||||
printf("ResetEvent failure after multiple SetEvent calls\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Independent of the amount of the previous SetEvent calls, a single
|
||||
ResetEvent must be sufficient to get into nonsignaled state */
|
||||
|
||||
if (WaitForSingleObject(event, 0) != WAIT_TIMEOUT)
|
||||
{
|
||||
printf("WaitForSingleObject failure 4\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
@ -678,6 +678,21 @@ BOOL IsProcessorFeaturePresent(DWORD ProcessorFeature)
|
||||
|
||||
#endif //_WIN32
|
||||
|
||||
DWORD GetTickCountPrecise(void)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
LARGE_INTEGER freq;
|
||||
LARGE_INTEGER current;
|
||||
|
||||
QueryPerformanceFrequency(&freq);
|
||||
QueryPerformanceCounter(¤t);
|
||||
|
||||
return (DWORD) (current.QuadPart * 1000LL / freq.QuadPart);
|
||||
#else
|
||||
return GetTickCount();
|
||||
#endif
|
||||
}
|
||||
|
||||
BOOL IsProcessorFeaturePresentEx(DWORD ProcessorFeature)
|
||||
{
|
||||
BOOL ret = FALSE;
|
||||
|
@ -67,8 +67,9 @@ BOOL MessageQueue_Wait(wMessageQueue* queue)
|
||||
return status;
|
||||
}
|
||||
|
||||
void MessageQueue_Dispatch(wMessageQueue* queue, wMessage* message)
|
||||
BOOL MessageQueue_Dispatch(wMessageQueue* queue, wMessage* message)
|
||||
{
|
||||
BOOL ret = FALSE;
|
||||
EnterCriticalSection(&queue->lock);
|
||||
|
||||
if (queue->size == queue->capacity)
|
||||
@ -82,7 +83,7 @@ void MessageQueue_Dispatch(wMessageQueue* queue, wMessage* message)
|
||||
|
||||
new_arr = (wMessage*) realloc(queue->array, sizeof(wMessage) * new_capacity);
|
||||
if (!new_arr)
|
||||
return;
|
||||
goto out;
|
||||
queue->array = new_arr;
|
||||
queue->capacity = new_capacity;
|
||||
ZeroMemory(&(queue->array[old_capacity]), old_capacity * sizeof(wMessage));
|
||||
@ -104,10 +105,13 @@ void MessageQueue_Dispatch(wMessageQueue* queue, wMessage* message)
|
||||
if (queue->size > 0)
|
||||
SetEvent(queue->event);
|
||||
|
||||
ret = TRUE;
|
||||
out:
|
||||
LeaveCriticalSection(&queue->lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
void MessageQueue_Post(wMessageQueue* queue, void* context, UINT32 type, void* wParam, void* lParam)
|
||||
BOOL MessageQueue_Post(wMessageQueue* queue, void* context, UINT32 type, void* wParam, void* lParam)
|
||||
{
|
||||
wMessage message;
|
||||
|
||||
@ -117,12 +121,12 @@ void MessageQueue_Post(wMessageQueue* queue, void* context, UINT32 type, void* w
|
||||
message.lParam = lParam;
|
||||
message.Free = NULL;
|
||||
|
||||
MessageQueue_Dispatch(queue, &message);
|
||||
return MessageQueue_Dispatch(queue, &message);
|
||||
}
|
||||
|
||||
void MessageQueue_PostQuit(wMessageQueue* queue, int nExitCode)
|
||||
BOOL MessageQueue_PostQuit(wMessageQueue* queue, int nExitCode)
|
||||
{
|
||||
MessageQueue_Post(queue, NULL, WMQ_QUIT, (void*) (size_t) nExitCode, NULL);
|
||||
return MessageQueue_Post(queue, NULL, WMQ_QUIT, (void*) (size_t) nExitCode, NULL);
|
||||
}
|
||||
|
||||
int MessageQueue_Get(wMessageQueue* queue, wMessage* message)
|
||||
@ -187,43 +191,34 @@ wMessageQueue* MessageQueue_New(const wObject *callback)
|
||||
{
|
||||
wMessageQueue* queue = NULL;
|
||||
|
||||
queue = (wMessageQueue*) malloc(sizeof(wMessageQueue));
|
||||
|
||||
if (queue)
|
||||
{
|
||||
queue->head = 0;
|
||||
queue->tail = 0;
|
||||
queue->size = 0;
|
||||
queue = (wMessageQueue*) calloc(1, sizeof(wMessageQueue));
|
||||
if (!queue)
|
||||
return NULL;
|
||||
|
||||
queue->capacity = 32;
|
||||
queue->array = (wMessage*) calloc(1, sizeof(wMessage) * queue->capacity);
|
||||
queue->array = (wMessage*) calloc(queue->capacity, sizeof(wMessage));
|
||||
if (!queue->array)
|
||||
{
|
||||
free(queue);
|
||||
return NULL;
|
||||
}
|
||||
goto error_array;
|
||||
|
||||
if (!InitializeCriticalSectionAndSpinCount(&queue->lock, 4000))
|
||||
{
|
||||
free(queue);
|
||||
return NULL;
|
||||
}
|
||||
goto error_spinlock;
|
||||
|
||||
queue->event = CreateEvent(NULL, TRUE, FALSE, NULL);
|
||||
if (!queue->event)
|
||||
{
|
||||
free(queue->array);
|
||||
DeleteCriticalSection(&queue->lock);
|
||||
free(queue);
|
||||
return NULL;
|
||||
}
|
||||
goto error_event;
|
||||
|
||||
if (callback)
|
||||
queue->object = *callback;
|
||||
else
|
||||
ZeroMemory(&queue->object, sizeof(queue->object));
|
||||
}
|
||||
|
||||
return queue;
|
||||
|
||||
error_event:
|
||||
DeleteCriticalSection(&queue->lock);
|
||||
error_spinlock:
|
||||
free(queue->array);
|
||||
error_array:
|
||||
free(queue);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void MessageQueue_Free(wMessageQueue* queue)
|
||||
|
@ -17,23 +17,38 @@ static void *read_image(const char *src, size_t *size)
|
||||
FILE *fsrc = fopen(src, "r");
|
||||
|
||||
if (!fsrc)
|
||||
{
|
||||
fprintf(stderr, "Failed to open file %s\n", src);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (fseek(fsrc, 0, SEEK_END))
|
||||
{
|
||||
fprintf(stderr, "Failed to seek to file end\n");
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
src_size = ftell(fsrc);
|
||||
|
||||
if (fseek(fsrc, 0, SEEK_SET))
|
||||
{
|
||||
fprintf(stderr, "Failed to seek to SEEK_SET\n");
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
a = malloc(src_size);
|
||||
|
||||
if (!a)
|
||||
{
|
||||
fprintf(stderr, "Failed malloc %zd bytes\n", src_size);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (fread(a, sizeof(char), src_size, fsrc) != src_size)
|
||||
{
|
||||
fprintf(stderr, "Failed read %zd bytes\n", src_size);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
success = 1;
|
||||
*size = src_size;
|
||||
@ -50,51 +65,50 @@ cleanup:
|
||||
return a;
|
||||
}
|
||||
|
||||
|
||||
static int compare(const char *src, const char *dst)
|
||||
{
|
||||
int cmp = -1;
|
||||
size_t asize, bsize;
|
||||
void *a, *b;
|
||||
|
||||
a = read_image(src, &asize);
|
||||
b = read_image(dst, &bsize);
|
||||
|
||||
if (!a || !b || (asize != bsize))
|
||||
goto cleanup;
|
||||
|
||||
cmp = memcmp(a, b, asize);
|
||||
|
||||
cleanup:
|
||||
free(a);
|
||||
free(b);
|
||||
|
||||
return cmp;
|
||||
}
|
||||
|
||||
static int img_compare(wImage *image, wImage *image2)
|
||||
static int img_compare(wImage *image, wImage *image2, BOOL ignoreType)
|
||||
{
|
||||
int rc = -1;
|
||||
if (image->type != image2->type)
|
||||
if ((image->type != image2->type) && !ignoreType)
|
||||
{
|
||||
fprintf(stderr, "Image type mismatch %d:%d\n", image->type, image2->type);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (image->width != image2->width)
|
||||
{
|
||||
fprintf(stderr, "Image width mismatch %d:%d\n", image->width, image2->width);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (image->height != image2->height)
|
||||
{
|
||||
fprintf(stderr, "Image height mismatch %d:%d\n", image->height, image2->height);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (image->scanline != image2->scanline)
|
||||
{
|
||||
fprintf(stderr, "Image scanline mismatch %d:%d\n", image->scanline, image2->scanline);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (image->bitsPerPixel != image2->bitsPerPixel)
|
||||
{
|
||||
fprintf(stderr, "Image bitsPerPixel mismatch %d:%d\n", image->bitsPerPixel, image2->bitsPerPixel);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
if (image->bytesPerPixel != image2->bytesPerPixel)
|
||||
{
|
||||
fprintf(stderr, "Image bytesPerPixel mismatch %d:%d\n", image->bytesPerPixel, image2->bytesPerPixel);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
rc = memcmp(image->data, image2->data, image->scanline * image->height);
|
||||
|
||||
if (rc)
|
||||
fprintf(stderr, "Image data mismatch!\n");
|
||||
|
||||
cleanup:
|
||||
return rc;
|
||||
}
|
||||
@ -107,12 +121,16 @@ static wImage *get_image(const char *src)
|
||||
image = winpr_image_new();
|
||||
|
||||
if (!image)
|
||||
{
|
||||
fprintf(stderr, "Failed to create image!");
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
status = winpr_image_read(image, src);
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
fprintf(stderr, "Failed to read image %s!", src);
|
||||
winpr_image_free(image, TRUE);
|
||||
image = NULL;
|
||||
}
|
||||
@ -132,7 +150,10 @@ static int create_test(const char *src, const char *dst_png, const char *dst_bmp
|
||||
wImage* image = NULL, *image2 = NULL, *image3 = NULL, *image4 = NULL;
|
||||
|
||||
if (!PathFileExistsA(src))
|
||||
{
|
||||
fprintf(stderr, "File %s does not exist!", src);
|
||||
return -1;
|
||||
}
|
||||
|
||||
image = get_image(src);
|
||||
|
||||
@ -145,30 +166,45 @@ static int create_test(const char *src, const char *dst_png, const char *dst_bmp
|
||||
status = winpr_image_write(image, dst_bmp);
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
fprintf(stderr, "Failed to write image %s!\n", dst_bmp);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
image->type = WINPR_IMAGE_PNG;
|
||||
status = winpr_image_write(image, dst_png);
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
fprintf(stderr, "Failed to write image %s!\n", dst_png);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
/* Read image from buffer, compare. */
|
||||
buffer = read_image(src, &bsize);
|
||||
if (!buffer)
|
||||
{
|
||||
fprintf(stderr, "Failed to read image %s!\n", src);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
image2 = winpr_image_new();
|
||||
|
||||
if (!image2)
|
||||
{
|
||||
fprintf(stderr, "Failed to create image!\n");
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
status = winpr_image_read_buffer(image2, buffer, bsize);
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
fprintf(stderr, "Failed to read buffer!\n");
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
rc = img_compare(image, image2);
|
||||
rc = img_compare(image, image2, TRUE);
|
||||
if (rc)
|
||||
goto cleanup;
|
||||
|
||||
@ -176,7 +212,7 @@ static int create_test(const char *src, const char *dst_png, const char *dst_bmp
|
||||
if (!image3)
|
||||
goto cleanup;
|
||||
|
||||
rc = img_compare(image, image3);
|
||||
rc = img_compare(image, image3, TRUE);
|
||||
if (rc)
|
||||
goto cleanup;
|
||||
|
||||
@ -184,8 +220,7 @@ static int create_test(const char *src, const char *dst_png, const char *dst_bmp
|
||||
if (!image4)
|
||||
goto cleanup;
|
||||
|
||||
image->type = WINPR_IMAGE_BITMAP;
|
||||
rc = img_compare(image, image4);
|
||||
rc = img_compare(image, image4, TRUE);
|
||||
if (rc)
|
||||
goto cleanup;
|
||||
|
||||
@ -235,21 +270,13 @@ int test_image_png_to_bmp()
|
||||
if (create_test(src_bmp, dst_png2, dst_bmp2))
|
||||
return -1;
|
||||
|
||||
#if 0
|
||||
if (compare(dst_png2, dst_png))
|
||||
return -1;
|
||||
|
||||
if (compare(dst_bmp2, dst_bmp))
|
||||
return -1;
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int TestImage(int argc, char* argv[])
|
||||
{
|
||||
test_image_png_to_bmp();
|
||||
int rc = test_image_png_to_bmp();
|
||||
|
||||
return 0;
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
@ -15,7 +15,8 @@ static void* message_echo_pipe_client_thread(void* arg)
|
||||
|
||||
while (index < 100)
|
||||
{
|
||||
MessageQueue_Post(pipe->In, NULL, 0, (void*) (size_t) index, NULL);
|
||||
if (!MessageQueue_Post(pipe->In, NULL, 0, (void*) (size_t) index, NULL))
|
||||
break;
|
||||
|
||||
if (!MessageQueue_Wait(pipe->Out))
|
||||
break;
|
||||
@ -56,7 +57,8 @@ static void* message_echo_pipe_server_thread(void* arg)
|
||||
|
||||
count = (int) (size_t) message.wParam;
|
||||
|
||||
MessageQueue_Dispatch(pipe->Out, &message);
|
||||
if (!MessageQueue_Dispatch(pipe->Out, &message))
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -42,12 +42,12 @@ int TestMessageQueue(int argc, char* argv[])
|
||||
return 1;
|
||||
}
|
||||
|
||||
MessageQueue_Post(queue, NULL, 123, NULL, NULL);
|
||||
MessageQueue_Post(queue, NULL, 456, NULL, NULL);
|
||||
MessageQueue_Post(queue, NULL, 789, NULL, NULL);
|
||||
MessageQueue_PostQuit(queue, 0);
|
||||
|
||||
WaitForSingleObject(thread, INFINITE);
|
||||
if (!MessageQueue_Post(queue, NULL, 123, NULL, NULL) ||
|
||||
!MessageQueue_Post(queue, NULL, 456, NULL, NULL) ||
|
||||
!MessageQueue_Post(queue, NULL, 789, NULL, NULL) ||
|
||||
!MessageQueue_PostQuit(queue, 0) ||
|
||||
WaitForSingleObject(thread, INFINITE) != WAIT_OBJECT_0)
|
||||
return -1;
|
||||
|
||||
MessageQueue_Free(queue);
|
||||
CloseHandle(thread);
|
||||
|
@ -98,7 +98,7 @@ int WLog_BinaryAppender_Open(wLog* log, wLogBinaryAppender* appender)
|
||||
|
||||
if (!PathFileExistsA(appender->FilePath))
|
||||
{
|
||||
if (!CreateDirectoryA(appender->FilePath, 0))
|
||||
if (!PathMakePathA(appender->FilePath, 0))
|
||||
return -1;
|
||||
UnixChangeFileMode(appender->FilePath, 0xFFFF);
|
||||
}
|
||||
|
@ -95,7 +95,7 @@ int WLog_FileAppender_Open(wLog* log, wLogFileAppender* appender)
|
||||
|
||||
if (!PathFileExistsA(appender->FilePath))
|
||||
{
|
||||
if (!CreateDirectoryA(appender->FilePath, 0))
|
||||
if (!PathMakePathA(appender->FilePath, 0))
|
||||
return -1;
|
||||
UnixChangeFileMode(appender->FilePath, 0xFFFF);
|
||||
}
|
||||
|
@ -44,7 +44,7 @@ char* WLog_Message_GetOutputFileName(int id, const char* ext)
|
||||
|
||||
if (!PathFileExistsA(FilePath))
|
||||
{
|
||||
if (!CreateDirectoryA(FilePath, NULL))
|
||||
if (!PathMakePathA(FilePath, NULL))
|
||||
{
|
||||
free(FileName);
|
||||
free(FilePath);
|
||||
|
@ -4,7 +4,7 @@ set(MODULE_PREFIX "TEST_WINPR")
|
||||
|
||||
set(${MODULE_PREFIX}_DRIVER ${MODULE_NAME}.c)
|
||||
|
||||
set(${MODULE_PREFIX}_TESTS TestIntrinsics.c)
|
||||
set(${MODULE_PREFIX}_TESTS TestIntrinsics.c TestTypes.c)
|
||||
|
||||
create_test_sourcelist(${MODULE_PREFIX}_SRCS
|
||||
${${MODULE_PREFIX}_DRIVER}
|
||||
|
117
winpr/test/TestTypes.c
Normal file
117
winpr/test/TestTypes.c
Normal file
@ -0,0 +1,117 @@
|
||||
/**
|
||||
* CTest for winpr types and macros
|
||||
*
|
||||
* Copyright 2015 Thincast Technologies GmbH
|
||||
* Copyright 2015 Norbert Federa <norbert.federa@thincast.com>
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include <winpr/crt.h>
|
||||
#include <winpr/error.h>
|
||||
|
||||
BOOL TestSucceededFailedMacros(HRESULT hr, char *sym, BOOL isSuccess)
|
||||
{
|
||||
BOOL rv = TRUE;
|
||||
|
||||
if (SUCCEEDED(hr) && !isSuccess)
|
||||
{
|
||||
printf("Error: SUCCEEDED with \"%s\" must be false\n", sym);
|
||||
rv = FALSE;
|
||||
}
|
||||
if (!SUCCEEDED(hr) && isSuccess)
|
||||
{
|
||||
printf("Error: SUCCEEDED with \"%s\" must be true\n", sym);
|
||||
rv = FALSE;
|
||||
}
|
||||
if (!FAILED(hr) && !isSuccess)
|
||||
{
|
||||
printf("Error: FAILED with \"%s\" must be true\n", sym);
|
||||
rv = FALSE;
|
||||
}
|
||||
if (FAILED(hr) && isSuccess)
|
||||
{
|
||||
printf("Error: FAILED with \"%s\" must be false\n", sym);
|
||||
rv = FALSE;
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
int TestTypes(int argc, char* argv[])
|
||||
{
|
||||
BOOL ok = TRUE;
|
||||
HRESULT hr;
|
||||
|
||||
if (S_OK != (HRESULT)0L)
|
||||
{
|
||||
printf("Error: S_OK should be 0\n");
|
||||
goto err;
|
||||
}
|
||||
if (S_FALSE != (HRESULT)1L)
|
||||
{
|
||||
printf("Error: S_FALSE should be 1\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* Test HRESULT success codes */
|
||||
ok &= TestSucceededFailedMacros(S_OK, "S_OK", TRUE);
|
||||
ok &= TestSucceededFailedMacros(S_FALSE, "S_FALSE", TRUE);
|
||||
|
||||
/* Test some HRESULT error codes */
|
||||
ok &= TestSucceededFailedMacros(E_NOTIMPL, "E_NOTIMPL", FALSE);
|
||||
ok &= TestSucceededFailedMacros(E_OUTOFMEMORY, "E_OUTOFMEMORY", FALSE);
|
||||
ok &= TestSucceededFailedMacros(E_INVALIDARG, "E_INVALIDARG", FALSE);
|
||||
ok &= TestSucceededFailedMacros(E_FAIL, "E_FAIL", FALSE);
|
||||
ok &= TestSucceededFailedMacros(E_ABORT, "E_ABORT", FALSE);
|
||||
|
||||
/* Test some WIN32 error codes converted to HRESULT*/
|
||||
hr = HRESULT_FROM_WIN32(ERROR_SUCCESS);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_SUCCESS)", TRUE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_INVALID_FUNCTION);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_INVALID_FUNCTION)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_NOACCESS);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_NOACCESS)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_NOT_FOUND);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_NOT_FOUND)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_TIMEOUT);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_TIMEOUT)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(RPC_S_ZERO_DIVIDE);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(RPC_S_ZERO_DIVIDE)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_STATIC_INIT);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_STATIC_INIT)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(ERROR_ENCRYPTION_FAILED);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(ERROR_ENCRYPTION_FAILED)", FALSE);
|
||||
|
||||
hr = HRESULT_FROM_WIN32(WSAECANCELLED);
|
||||
ok &= TestSucceededFailedMacros(hr, "HRESULT_FROM_WIN32(WSAECANCELLED)", FALSE);
|
||||
|
||||
if (ok) {
|
||||
printf("Test completed successfully\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
err:
|
||||
printf("Error: Test failed\n");
|
||||
return -1;
|
||||
}
|
Loading…
Reference in New Issue
Block a user