Fixed support for huge files in clipboard
This commit is contained in:
parent
43691d59ee
commit
f3dad4106a
@ -291,6 +291,14 @@ out:
|
||||
UINT cliprdr_serialize_file_list(const FILEDESCRIPTORW* file_descriptor_array,
|
||||
UINT32 file_descriptor_count, BYTE** format_data,
|
||||
UINT32* format_data_length)
|
||||
{
|
||||
return cliprdr_serialize_file_list_ex(CB_STREAM_FILECLIP_ENABLED, file_descriptor_array,
|
||||
file_descriptor_count, format_data, format_data_length);
|
||||
}
|
||||
|
||||
UINT cliprdr_serialize_file_list_ex(UINT32 flags, const FILEDESCRIPTORW* file_descriptor_array,
|
||||
UINT32 file_descriptor_count, BYTE** format_data,
|
||||
UINT32* format_data_length)
|
||||
{
|
||||
UINT result = NO_ERROR;
|
||||
UINT32 i;
|
||||
@ -299,6 +307,12 @@ UINT cliprdr_serialize_file_list(const FILEDESCRIPTORW* file_descriptor_array,
|
||||
if (!file_descriptor_array || !format_data || !format_data_length)
|
||||
return ERROR_BAD_ARGUMENTS;
|
||||
|
||||
if ((flags & CB_STREAM_FILECLIP_ENABLED) == 0)
|
||||
{
|
||||
WLog_WARN(TAG, "No file clipboard support annouonced!");
|
||||
return ERROR_BAD_ARGUMENTS;
|
||||
}
|
||||
|
||||
s = Stream_New(NULL, 4 + file_descriptor_count * CLIPRDR_FILEDESCRIPTOR_SIZE);
|
||||
if (!s)
|
||||
return ERROR_NOT_ENOUGH_MEMORY;
|
||||
@ -318,11 +332,14 @@ UINT cliprdr_serialize_file_list(const FILEDESCRIPTORW* file_descriptor_array,
|
||||
*
|
||||
* https://support.microsoft.com/en-us/help/2258090
|
||||
*/
|
||||
if ((file->nFileSizeHigh > 0) || (file->nFileSizeLow >= CLIPRDR_MAX_FILE_SIZE))
|
||||
if ((flags & CB_HUGE_FILE_SUPPORT_ENABLED) == 0)
|
||||
{
|
||||
WLog_ERR(TAG, "cliprdr does not support files over 2 GB");
|
||||
result = ERROR_FILE_TOO_LARGE;
|
||||
goto error;
|
||||
if ((file->nFileSizeHigh > 0) || (file->nFileSizeLow >= CLIPRDR_MAX_FILE_SIZE))
|
||||
{
|
||||
WLog_ERR(TAG, "cliprdr does not support files over 2 GB");
|
||||
result = ERROR_FILE_TOO_LARGE;
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
Stream_Write_UINT32(s, file->dwFlags); /* flags (4 bytes) */
|
||||
|
@ -37,18 +37,36 @@
|
||||
#include "../cliprdr_common.h"
|
||||
|
||||
#ifdef WITH_DEBUG_CLIPRDR
|
||||
static const char* const CB_MSG_TYPE_STRINGS[] = { "",
|
||||
"CB_MONITOR_READY",
|
||||
"CB_FORMAT_LIST",
|
||||
"CB_FORMAT_LIST_RESPONSE",
|
||||
"CB_FORMAT_DATA_REQUEST",
|
||||
"CB_FORMAT_DATA_RESPONSE",
|
||||
"CB_TEMP_DIRECTORY",
|
||||
"CB_CLIP_CAPS",
|
||||
"CB_FILECONTENTS_REQUEST",
|
||||
"CB_FILECONTENTS_RESPONSE",
|
||||
"CB_LOCK_CLIPDATA",
|
||||
"CB_UNLOCK_CLIPDATA" };
|
||||
static const char* CB_MSG_TYPE_STRINGS(UINT32 type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case CB_MONITOR_READY:
|
||||
return "CB_MONITOR_READY";
|
||||
case CB_FORMAT_LIST:
|
||||
return "CB_FORMAT_LIST";
|
||||
case CB_FORMAT_LIST_RESPONSE:
|
||||
return "CB_FORMAT_LIST_RESPONSE";
|
||||
case CB_FORMAT_DATA_REQUEST:
|
||||
return "CB_FORMAT_DATA_REQUEST";
|
||||
case CB_FORMAT_DATA_RESPONSE:
|
||||
return "CB_FORMAT_DATA_RESPONSE";
|
||||
case CB_TEMP_DIRECTORY:
|
||||
return "CB_TEMP_DIRECTORY";
|
||||
case CB_CLIP_CAPS:
|
||||
return "CB_CLIP_CAPS";
|
||||
case CB_FILECONTENTS_REQUEST:
|
||||
return "CB_FILECONTENTS_REQUEST";
|
||||
case CB_FILECONTENTS_RESPONSE:
|
||||
return "CB_FILECONTENTS_RESPONSE";
|
||||
case CB_LOCK_CLIPDATA:
|
||||
return "CB_LOCK_CLIPDATA";
|
||||
case CB_UNLOCK_CLIPDATA:
|
||||
return "CB_UNLOCK_CLIPDATA";
|
||||
default:
|
||||
return "UNKNOWN";
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
CliprdrClientContext* cliprdr_get_client_interface(cliprdrPlugin* cliprdr)
|
||||
@ -446,7 +464,7 @@ static UINT cliprdr_order_recv(cliprdrPlugin* cliprdr, wStream* s)
|
||||
|
||||
#ifdef WITH_DEBUG_CLIPRDR
|
||||
WLog_DBG(TAG, "msgType: %s (%" PRIu16 "), msgFlags: %" PRIu16 " dataLen: %" PRIu32 "",
|
||||
CB_MSG_TYPE_STRINGS[msgType], msgType, msgFlags, dataLen);
|
||||
CB_MSG_TYPE_STRINGS(msgType), msgType, msgFlags, dataLen);
|
||||
winpr_HexDump(TAG, WLOG_DEBUG, Stream_Buffer(s), dataLen + 8);
|
||||
#endif
|
||||
|
||||
|
@ -171,6 +171,7 @@ struct xf_clipboard
|
||||
/* File clipping */
|
||||
BOOL streams_supported;
|
||||
BOOL file_formats_registered;
|
||||
UINT32 file_capability_flags;
|
||||
#ifdef WITH_FUSE
|
||||
/* FUSE related**/
|
||||
HANDLE fuse_thread;
|
||||
@ -697,7 +698,8 @@ static void xf_cliprdr_process_requested_data(xfClipboard* clipboard, BOOL hasDa
|
||||
UINT32 file_count = DstSize / sizeof(FILEDESCRIPTORW);
|
||||
pDstData = NULL;
|
||||
DstSize = 0;
|
||||
error = cliprdr_serialize_file_list(file_array, file_count, &pDstData, &DstSize);
|
||||
error = cliprdr_serialize_file_list_ex(clipboard->file_capability_flags, file_array,
|
||||
file_count, &pDstData, &DstSize);
|
||||
|
||||
if (error)
|
||||
WLog_ERR(TAG, "failed to serialize CLIPRDR_FILELIST: 0x%08X", error);
|
||||
@ -1189,6 +1191,7 @@ static UINT xf_cliprdr_send_client_capabilities(xfClipboard* clipboard)
|
||||
generalCapabilitySet.generalFlags |=
|
||||
CB_STREAM_FILECLIP_ENABLED | CB_FILECLIP_NO_FILE_PATHS | CB_HUGE_FILE_SUPPORT_ENABLED;
|
||||
|
||||
clipboard->file_capability_flags = generalCapabilitySet.generalFlags;
|
||||
return clipboard->context->ClientCapabilities(clipboard->context, &capabilities);
|
||||
}
|
||||
|
||||
|
@ -101,6 +101,10 @@ extern "C"
|
||||
FREERDP_API UINT cliprdr_serialize_file_list(const FILEDESCRIPTORW* file_descriptor_array,
|
||||
UINT32 file_descriptor_count, BYTE** format_data,
|
||||
UINT32* format_data_length);
|
||||
FREERDP_API UINT cliprdr_serialize_file_list_ex(UINT32 flags,
|
||||
const FILEDESCRIPTORW* file_descriptor_array,
|
||||
UINT32 file_descriptor_count,
|
||||
BYTE** format_data, UINT32* format_data_length);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
@ -317,7 +317,6 @@ static BOOL fastpath_recv_update_common(rdpFastPath* fastpath, wStream* s)
|
||||
return FALSE;
|
||||
|
||||
Stream_Read_UINT16(s, updateType); /* updateType (2 bytes) */
|
||||
|
||||
switch (updateType)
|
||||
{
|
||||
case UPDATE_TYPE_BITMAP:
|
||||
|
@ -54,20 +54,13 @@ char* _strdup(const char* strSource)
|
||||
|
||||
WCHAR* _wcsdup(const WCHAR* strSource)
|
||||
{
|
||||
size_t len = _wcslen(strSource);
|
||||
WCHAR* strDestination;
|
||||
|
||||
if (strSource == NULL)
|
||||
return NULL;
|
||||
|
||||
#if defined(__APPLE__) && defined(__MACH__) || defined(ANDROID) || defined(sun)
|
||||
strDestination = malloc(wcslen((wchar_t*)strSource));
|
||||
strDestination = calloc(len + 1, sizeof(WCHAR));
|
||||
|
||||
if (strDestination != NULL)
|
||||
wcscpy((wchar_t*)strDestination, (const wchar_t*)strSource);
|
||||
|
||||
#else
|
||||
strDestination = (WCHAR*)wcsdup((wchar_t*)strSource);
|
||||
#endif
|
||||
memcpy(strDestination, strSource, len * sizeof(WCHAR));
|
||||
|
||||
if (strDestination == NULL)
|
||||
WLog_ERR(TAG, "wcsdup");
|
||||
|
Loading…
Reference in New Issue
Block a user