New upstream version 2.6.1+dfsg1

This commit is contained in:
Mike Gabriel 2022-03-08 07:34:48 +01:00
parent 45f744e4b0
commit f2ecc9e1e9
23 changed files with 346 additions and 141 deletions

View File

@ -85,7 +85,7 @@ if ($ENV{BUILD_NUMBER})
endif()
set(WITH_LIBRARY_VERSIONING "ON")
set(RAW_VERSION_STRING "2.6.0")
set(RAW_VERSION_STRING "2.6.1")
if(EXISTS "${CMAKE_SOURCE_DIR}/.source_tag")
file(READ ${CMAKE_SOURCE_DIR}/.source_tag RAW_VERSION_STRING)
elseif(USE_VERSION_FROM_GIT_TAG)
@ -111,6 +111,24 @@ else()
endif()
message("FREERDP_VERSION=${FREERDP_VERSION_FULL}")
if(EXISTS "${PROJECT_SOURCE_DIR}/.source_version" )
file(READ ${PROJECT_SOURCE_DIR}/.source_version GIT_REVISION)
string(STRIP ${GIT_REVISION} GIT_REVISION)
elseif(USE_VERSION_FROM_GIT_TAG)
git_get_exact_tag(GIT_REVISION --tags --always)
if (${GIT_REVISION} STREQUAL "n/a")
git_rev_parse (GIT_REVISION --short)
endif()
endif()
if (NOT GIT_REVISION)
set(GIT_REVISION ${FREERDP_VERSION})
endif()
message(STATUS "Git Revision ${GIT_REVISION}")
set(FREERDP_INCLUDE_DIR "include/freerdp${FREERDP_VERSION_MAJOR}/")
# Compatibility options
@ -147,25 +165,11 @@ if(CCACHE AND WITH_CCACHE)
endif()
endif(CCACHE AND WITH_CCACHE)
if(EXISTS "${CMAKE_SOURCE_DIR}/.source_version" )
file(READ ${CMAKE_SOURCE_DIR}/.source_version GIT_REVISION)
string(STRIP ${GIT_REVISION} GIT_REVISION)
else()
git_get_exact_tag(GIT_REVISION --tags --always)
if (${GIT_REVISION} STREQUAL "n/a")
git_rev_parse (GIT_REVISION --short)
endif()
endif()
if(CMAKE_CROSSCOMPILING)
SET (CMAKE_FIND_ROOT_PATH_MODE_PROGRAM ONLY)
endif(CMAKE_CROSSCOMPILING)
# /Allow to search the host machine for git/ccache
message(STATUS "Git Revision ${GIT_REVISION}")
# Turn on solution folders (2.8.4+)
set_property(GLOBAL PROPERTY USE_FOLDERS ON)

View File

@ -1,3 +1,18 @@
# 2022-03-07 Version 2.6.1
Noteworthy changes:
* Decreased logging verbosity, now freerdp is much less verbose by default
Fixed issues:
* Backported freerdp_abort_connect during freerdp_connect fix (#7700)
* Backported improved version dection see docs/version_detection.md for details
* Backported various rdpsnd fixes (#7695)
Important notes:
For a complete and detailed change log since the last release run:
git log 2.0.0..2.6.1
# 2022-02-22 Version 2.6.0
Noteworthy changes:

View File

@ -182,7 +182,7 @@ static void rdpsnd_select_supported_audio_formats(rdpsndPlugin* rdpsnd)
rdpsnd->ClientFormats = audio_formats_new(rdpsnd->NumberOfServerFormats);
if (!rdpsnd->ClientFormats)
if (!rdpsnd->ClientFormats || !rdpsnd->device)
return;
for (index = 0; index < rdpsnd->NumberOfServerFormats; index++)
@ -213,6 +213,10 @@ static UINT rdpsnd_send_client_audio_formats(rdpsndPlugin* rdpsnd)
UINT16 length;
UINT32 dwVolume;
UINT16 wNumberOfFormats;
if (!rdpsnd->device || (!rdpsnd->dynamic && (rdpsnd->OpenHandle == 0)))
return CHANNEL_RC_INITIALIZATION_ERROR;
dwVolume = IFCALLRESULT(0, rdpsnd->device->GetVolume, rdpsnd->device);
wNumberOfFormats = rdpsnd->NumberOfClientFormats;
length = 4 + 20;
@ -695,7 +699,7 @@ static void rdpsnd_recv_close_pdu(rdpsndPlugin* rdpsnd)
*/
static UINT rdpsnd_recv_volume_pdu(rdpsndPlugin* rdpsnd, wStream* s)
{
BOOL rc;
BOOL rc = FALSE;
UINT32 dwVolume;
if (Stream_GetRemainingLength(s) < 4)
@ -704,7 +708,8 @@ static UINT rdpsnd_recv_volume_pdu(rdpsndPlugin* rdpsnd, wStream* s)
Stream_Read_UINT32(s, dwVolume);
WLog_Print(rdpsnd->log, WLOG_DEBUG, "%s Volume: 0x%08" PRIX32 "",
rdpsnd_is_dyn_str(rdpsnd->dynamic), dwVolume);
rc = IFCALLRESULT(FALSE, rdpsnd->device->SetVolume, rdpsnd->device, dwVolume);
if (rdpsnd->device)
rc = IFCALLRESULT(FALSE, rdpsnd->device->SetVolume, rdpsnd->device, dwVolume);
if (!rc)
{
@ -1182,38 +1187,51 @@ static UINT rdpsnd_virtual_channel_event_connected(rdpsndPlugin* rdpsnd, LPVOID
UINT32 dataLength)
{
UINT32 status;
DWORD opened = 0;
WINPR_UNUSED(pData);
WINPR_UNUSED(dataLength);
status = rdpsnd->channelEntryPoints.pVirtualChannelOpenEx(
rdpsnd->InitHandle, &rdpsnd->OpenHandle, rdpsnd->channelDef.name,
rdpsnd_virtual_channel_open_event_ex);
rdpsnd->InitHandle, &opened, rdpsnd->channelDef.name, rdpsnd_virtual_channel_open_event_ex);
if (status != CHANNEL_RC_OK)
{
WLog_ERR(TAG, "%s pVirtualChannelOpenEx failed with %s [%08" PRIX32 "]",
rdpsnd_is_dyn_str(rdpsnd->dynamic), WTSErrorToString(status), status);
return status;
goto fail;
}
rdpsnd->dsp_context = freerdp_dsp_context_new(FALSE);
if (!rdpsnd->dsp_context)
if (rdpsnd_process_connect(rdpsnd) != CHANNEL_RC_OK)
goto fail;
rdpsnd->pool = StreamPool_New(TRUE, 4096);
if (!rdpsnd->pool)
goto fail;
return rdpsnd_process_connect(rdpsnd);
rdpsnd->OpenHandle = opened;
return CHANNEL_RC_OK;
fail:
freerdp_dsp_context_free(rdpsnd->dsp_context);
StreamPool_Free(rdpsnd->pool);
if (opened != 0)
rdpsnd->channelEntryPoints.pVirtualChannelCloseEx(rdpsnd->InitHandle, opened);
return CHANNEL_RC_NO_MEMORY;
}
static void cleanup_internals(rdpsndPlugin* rdpsnd)
{
if (!rdpsnd)
return;
if (rdpsnd->pool)
StreamPool_Return(rdpsnd->pool, rdpsnd->data_in);
audio_formats_free(rdpsnd->ClientFormats, rdpsnd->NumberOfClientFormats);
audio_formats_free(rdpsnd->ServerFormats, rdpsnd->NumberOfServerFormats);
rdpsnd->NumberOfClientFormats = 0;
rdpsnd->ClientFormats = NULL;
rdpsnd->NumberOfServerFormats = 0;
rdpsnd->ServerFormats = NULL;
rdpsnd->data_in = NULL;
}
/**
* Function description
*
@ -1223,33 +1241,25 @@ static UINT rdpsnd_virtual_channel_event_disconnected(rdpsndPlugin* rdpsnd)
{
UINT error;
if (rdpsnd->OpenHandle == 0)
return CHANNEL_RC_OK;
if (rdpsnd->device)
IFCALL(rdpsnd->device->Close, rdpsnd->device);
error =
rdpsnd->channelEntryPoints.pVirtualChannelCloseEx(rdpsnd->InitHandle, rdpsnd->OpenHandle);
if (CHANNEL_RC_OK != error)
if (rdpsnd->OpenHandle != 0)
{
WLog_ERR(TAG, "%s pVirtualChannelCloseEx failed with %s [%08" PRIX32 "]",
rdpsnd_is_dyn_str(rdpsnd->dynamic), WTSErrorToString(error), error);
return error;
DWORD opened = rdpsnd->OpenHandle;
rdpsnd->OpenHandle = 0;
if (rdpsnd->device)
IFCALL(rdpsnd->device->Close, rdpsnd->device);
error = rdpsnd->channelEntryPoints.pVirtualChannelCloseEx(rdpsnd->InitHandle, opened);
if (CHANNEL_RC_OK != error)
{
WLog_ERR(TAG, "%s pVirtualChannelCloseEx failed with %s [%08" PRIX32 "]",
rdpsnd_is_dyn_str(rdpsnd->dynamic), WTSErrorToString(error), error);
return error;
}
}
rdpsnd->OpenHandle = 0;
freerdp_dsp_context_free(rdpsnd->dsp_context);
StreamPool_Return(rdpsnd->pool, rdpsnd->data_in);
StreamPool_Free(rdpsnd->pool);
audio_formats_free(rdpsnd->ClientFormats, rdpsnd->NumberOfClientFormats);
rdpsnd->NumberOfClientFormats = 0;
rdpsnd->ClientFormats = NULL;
audio_formats_free(rdpsnd->ServerFormats, rdpsnd->NumberOfServerFormats);
rdpsnd->NumberOfServerFormats = 0;
rdpsnd->ServerFormats = NULL;
cleanup_internals(rdpsnd);
if (rdpsnd->device)
{
@ -1266,6 +1276,36 @@ static void _queue_free(void* obj)
Stream_Release(s);
}
static void free_internals(rdpsndPlugin* rdpsnd)
{
if (!rdpsnd)
return;
freerdp_dsp_context_free(rdpsnd->dsp_context);
StreamPool_Free(rdpsnd->pool);
rdpsnd->pool = NULL;
rdpsnd->dsp_context = NULL;
}
static BOOL allocate_internals(rdpsndPlugin* rdpsnd)
{
if (!rdpsnd->pool)
{
rdpsnd->pool = StreamPool_New(TRUE, 4096);
if (!rdpsnd->pool)
return FALSE;
}
if (!rdpsnd->dsp_context)
{
rdpsnd->dsp_context = freerdp_dsp_context_new(FALSE);
if (!rdpsnd->dsp_context)
return FALSE;
}
return TRUE;
}
static DWORD WINAPI play_thread(LPVOID arg)
{
UINT error = CHANNEL_RC_OK;
@ -1311,17 +1351,22 @@ static UINT rdpsnd_virtual_channel_event_initialized(rdpsndPlugin* rdpsnd)
if (!rdpsnd->queue)
return CHANNEL_RC_NO_MEMORY;
if (!allocate_internals(rdpsnd))
return CHANNEL_RC_NO_MEMORY;
rdpsnd->thread = CreateThread(NULL, 0, play_thread, rdpsnd, 0, NULL);
if (!rdpsnd->thread)
return CHANNEL_RC_INITIALIZATION_ERROR;
return CHANNEL_RC_OK;
}
static void rdpsnd_virtual_channel_event_terminated(rdpsndPlugin* rdpsnd)
void rdpsnd_virtual_channel_event_terminated(rdpsndPlugin* rdpsnd)
{
if (rdpsnd)
{
MessageQueue_PostQuit(rdpsnd->queue, 0);
if (rdpsnd->queue)
MessageQueue_PostQuit(rdpsnd->queue, 0);
if (rdpsnd->thread)
{
WaitForSingleObject(rdpsnd->thread, INFINITE);
@ -1329,6 +1374,7 @@ static void rdpsnd_virtual_channel_event_terminated(rdpsndPlugin* rdpsnd)
}
MessageQueue_Free(rdpsnd->queue);
free_internals(rdpsnd);
audio_formats_free(rdpsnd->fixed_format, 1);
free(rdpsnd->subsystem);
free(rdpsnd->device_name);
@ -1370,6 +1416,7 @@ static VOID VCAPITYPE rdpsnd_virtual_channel_init_event_ex(LPVOID lpUserParam, L
case CHANNEL_EVENT_TERMINATED:
rdpsnd_virtual_channel_event_terminated(plugin);
plugin = NULL;
break;
case CHANNEL_EVENT_ATTACHED:
@ -1401,6 +1448,27 @@ rdpContext* freerdp_rdpsnd_get_context(rdpsndPlugin* plugin)
return plugin->rdpcontext;
}
static rdpsndPlugin* allocatePlugin(void)
{
rdpsndPlugin* rdpsnd = (rdpsndPlugin*)calloc(1, sizeof(rdpsndPlugin));
if (!rdpsnd)
goto fail;
rdpsnd->fixed_format = audio_format_new();
if (!rdpsnd->fixed_format)
goto fail;
rdpsnd->log = WLog_Get("com.freerdp.channels.rdpsnd.client");
if (!rdpsnd->log)
goto fail;
rdpsnd->attached = TRUE;
return rdpsnd;
fail:
if (rdpsnd)
audio_format_free(rdpsnd->fixed_format);
return NULL;
}
/* rdpsnd is always built-in */
BOOL VCAPITYPE rdpsnd_VirtualChannelEntryEx(PCHANNEL_ENTRY_POINTS pEntryPoints, PVOID pInitHandle)
{
@ -1411,12 +1479,11 @@ BOOL VCAPITYPE rdpsnd_VirtualChannelEntryEx(PCHANNEL_ENTRY_POINTS pEntryPoints,
if (!pEntryPoints)
return FALSE;
rdpsnd = (rdpsndPlugin*)calloc(1, sizeof(rdpsndPlugin));
rdpsnd = allocatePlugin();
if (!rdpsnd)
return FALSE;
rdpsnd->attached = TRUE;
rdpsnd->channelDef.options = CHANNEL_OPTION_INITIALIZED | CHANNEL_OPTION_ENCRYPT_RDP;
sprintf_s(rdpsnd->channelDef.name, ARRAYSIZE(rdpsnd->channelDef.name), "rdpsnd");
pEntryPointsEx = (CHANNEL_ENTRY_POINTS_FREERDP_EX*)pEntryPoints;
@ -1427,15 +1494,6 @@ BOOL VCAPITYPE rdpsnd_VirtualChannelEntryEx(PCHANNEL_ENTRY_POINTS pEntryPoints,
rdpsnd->rdpcontext = pEntryPointsEx->context;
}
rdpsnd->fixed_format = audio_format_new();
if (!rdpsnd->fixed_format)
{
free(rdpsnd);
return FALSE;
}
rdpsnd->log = WLog_Get("com.freerdp.channels.rdpsnd.client");
CopyMemory(&(rdpsnd->channelEntryPoints), pEntryPoints,
sizeof(CHANNEL_ENTRY_POINTS_FREERDP_EX));
rdpsnd->InitHandle = pInitHandle;
@ -1447,7 +1505,7 @@ BOOL VCAPITYPE rdpsnd_VirtualChannelEntryEx(PCHANNEL_ENTRY_POINTS pEntryPoints,
{
WLog_ERR(TAG, "%s pVirtualChannelInitEx failed with %s [%08" PRIX32 "]",
rdpsnd_is_dyn_str(FALSE), WTSErrorToString(rc), rc);
free(rdpsnd);
rdpsnd_virtual_channel_event_terminated(rdpsnd);
return FALSE;
}
@ -1459,19 +1517,10 @@ static UINT rdpsnd_on_open(IWTSVirtualChannelCallback* pChannelCallback)
RDPSND_CHANNEL_CALLBACK* callback = (RDPSND_CHANNEL_CALLBACK*)pChannelCallback;
rdpsndPlugin* rdpsnd = (rdpsndPlugin*)callback->plugin;
rdpsnd->dsp_context = freerdp_dsp_context_new(FALSE);
if (!rdpsnd->dsp_context)
goto fail;
rdpsnd->pool = StreamPool_New(TRUE, 4096);
if (!rdpsnd->pool)
goto fail;
if (!allocate_internals(rdpsnd))
return ERROR_OUTOFMEMORY;
return rdpsnd_process_connect(rdpsnd);
fail:
freerdp_dsp_context_free(rdpsnd->dsp_context);
StreamPool_Free(rdpsnd->pool);
return CHANNEL_RC_NO_MEMORY;
}
static UINT rdpsnd_on_data_received(IWTSVirtualChannelCallback* pChannelCallback, wStream* data)
@ -1479,7 +1528,9 @@ static UINT rdpsnd_on_data_received(IWTSVirtualChannelCallback* pChannelCallback
RDPSND_CHANNEL_CALLBACK* callback = (RDPSND_CHANNEL_CALLBACK*)pChannelCallback;
rdpsndPlugin* plugin;
wStream* copy;
size_t len = Stream_GetRemainingLength(data);
size_t len;
len = Stream_GetRemainingLength(data);
if (!callback || !callback->plugin)
return ERROR_INVALID_PARAMETER;
@ -1508,22 +1559,16 @@ static UINT rdpsnd_on_close(IWTSVirtualChannelCallback* pChannelCallback)
if (rdpsnd->device)
IFCALL(rdpsnd->device->Close, rdpsnd->device);
freerdp_dsp_context_free(rdpsnd->dsp_context);
StreamPool_Return(rdpsnd->pool, rdpsnd->data_in);
StreamPool_Free(rdpsnd->pool);
audio_formats_free(rdpsnd->ClientFormats, rdpsnd->NumberOfClientFormats);
rdpsnd->NumberOfClientFormats = 0;
rdpsnd->ClientFormats = NULL;
audio_formats_free(rdpsnd->ServerFormats, rdpsnd->NumberOfServerFormats);
rdpsnd->NumberOfServerFormats = 0;
rdpsnd->ServerFormats = NULL;
cleanup_internals(rdpsnd);
if (rdpsnd->device)
{
IFCALL(rdpsnd->device->Free, rdpsnd->device);
rdpsnd->device = NULL;
}
free_internals(rdpsnd);
free(pChannelCallback);
return CHANNEL_RC_OK;
}
@ -1622,7 +1667,7 @@ UINT rdpsnd_DVCPluginEntry(IDRDYNVC_ENTRY_POINTS* pEntryPoints)
if (!rdpsnd)
{
rdpsnd = (rdpsndPlugin*)calloc(1, sizeof(rdpsndPlugin));
rdpsnd = allocatePlugin();
if (!rdpsnd)
{
WLog_ERR(TAG, "%s calloc failed!", rdpsnd_is_dyn_str(TRUE));
@ -1633,14 +1678,10 @@ UINT rdpsnd_DVCPluginEntry(IDRDYNVC_ENTRY_POINTS* pEntryPoints)
rdpsnd->iface.Connected = NULL;
rdpsnd->iface.Disconnected = NULL;
rdpsnd->iface.Terminated = rdpsnd_plugin_terminated;
rdpsnd->attached = TRUE;
rdpsnd->dynamic = TRUE;
rdpsnd->fixed_format = audio_format_new();
if (!rdpsnd->fixed_format)
goto fail;
rdpsnd->log = WLog_Get("com.freerdp.channels.rdpsnd.client");
rdpsnd->channelEntryPoints.pExtendedData = pEntryPoints->GetPluginData(pEntryPoints);
/* user data pointer is not const, cast to avoid warning. */
rdpsnd->channelEntryPoints.pExtendedData = (void*)pEntryPoints->GetPluginData(pEntryPoints);
error = pEntryPoints->RegisterPlugin(pEntryPoints, "rdpsnd", &rdpsnd->iface);
}
@ -1650,8 +1691,5 @@ UINT rdpsnd_DVCPluginEntry(IDRDYNVC_ENTRY_POINTS* pEntryPoints)
return CHANNEL_RC_BAD_CHANNEL;
}
return error;
fail:
rdpsnd_plugin_terminated(&rdpsnd->iface);
return error;
}

View File

@ -1461,7 +1461,7 @@ static BOOL handle_window_events(freerdp* instance)
{
if (!xf_process_x_events(instance))
{
WLog_INFO(TAG, "Closed from X11");
WLog_DBG(TAG, "Closed from X11");
return FALSE;
}
}

View File

@ -1570,7 +1570,7 @@ xf_cliprdr_server_format_data_response(CliprdrClientContext* context,
{
if (SrcSize == 0)
{
WLog_INFO(TAG, "skipping, empty data detected!!!");
WLog_DBG(TAG, "skipping, empty data detected!");
free(clipboard->respond);
clipboard->respond = NULL;
return CHANNEL_RC_OK;

View File

@ -152,8 +152,8 @@ int xf_input_init(xfContext* xfc, Window window)
if (xfc->context.settings->MultiTouchInput)
{
WLog_INFO(TAG, "%s (%d) \"%s\" id: %d", xf_input_get_class_string(class->type),
class->type, dev->name, dev->deviceid);
WLog_DBG(TAG, "%s (%d) \"%s\" id: %d", xf_input_get_class_string(class->type),
class->type, dev->name, dev->deviceid);
}
evmasks[nmasks].mask = masks[nmasks];
@ -166,9 +166,9 @@ int xf_input_init(xfContext* xfc, Window window)
{
if (xfc->context.settings->MultiTouchInput)
{
WLog_INFO(TAG, "%s %s touch device (id: %d, mode: %d), supporting %d touches.",
dev->name, (t->mode == XIDirectTouch) ? "direct" : "dependent",
dev->deviceid, t->mode, t->num_touches);
WLog_DBG(TAG, "%s %s touch device (id: %d, mode: %d), supporting %d touches.",
dev->name, (t->mode == XIDirectTouch) ? "direct" : "dependent",
dev->deviceid, t->mode, t->num_touches);
}
XISetMask(masks[nmasks], XI_TouchBegin);
@ -182,8 +182,8 @@ int xf_input_init(xfContext* xfc, Window window)
if (!touch && (class->type == XIButtonClass) &&
strcmp(dev->name, "Virtual core pointer"))
{
WLog_INFO(TAG, "%s button device (id: %d, mode: %d)", dev->name, dev->deviceid,
t->mode);
WLog_DBG(TAG, "%s button device (id: %d, mode: %d)", dev->name, dev->deviceid,
t->mode);
XISetMask(masks[nmasks], XI_ButtonPress);
XISetMask(masks[nmasks], XI_ButtonRelease);
XISetMask(masks[nmasks], XI_Motion);

View File

@ -355,7 +355,7 @@ BOOL xf_GetWindowProperty(xfContext* xfc, Window window, Atom property, int leng
if (actual_type == None)
{
WLog_INFO(TAG, "Property %lu does not exist", (unsigned long)property);
WLog_DBG(TAG, "Property %lu does not exist", (unsigned long)property);
return FALSE;
}

View File

@ -730,6 +730,7 @@ BOOL client_auto_reconnect(freerdp* instance)
BOOL client_auto_reconnect_ex(freerdp* instance, BOOL (*window_events)(freerdp* instance))
{
BOOL retry = TRUE;
UINT32 error;
UINT32 maxRetries;
UINT32 numRetries = 0;
@ -765,7 +766,7 @@ BOOL client_auto_reconnect_ex(freerdp* instance, BOOL (*window_events)(freerdp*
}
/* Perform an auto-reconnect. */
while (TRUE)
while (retry)
{
UINT32 x;
@ -781,12 +782,21 @@ BOOL client_auto_reconnect_ex(freerdp* instance, BOOL (*window_events)(freerdp*
if (freerdp_reconnect(instance))
return TRUE;
switch (freerdp_get_last_error(instance))
{
case FREERDP_ERROR_CONNECT_CANCELLED:
WLog_WARN(TAG, "Autoreconnect aborted by user");
retry = FALSE;
break;
default:
break;
}
for (x = 0; x < 50; x++)
{
if (!IFCALLRESULT(TRUE, window_events, instance))
return FALSE;
Sleep(100);
Sleep(10);
}
}

View File

@ -3499,7 +3499,7 @@ static BOOL freerdp_client_load_static_channel_addin(rdpChannels* channels, rdpS
{
if (freerdp_channels_client_load_ex(channels, settings, entryEx, data) == 0)
{
WLog_INFO(TAG, "loading channelEx %s", name);
WLog_DBG(TAG, "loading channelEx %s", name);
return TRUE;
}
}
@ -3507,7 +3507,7 @@ static BOOL freerdp_client_load_static_channel_addin(rdpChannels* channels, rdpS
{
if (freerdp_channels_client_load(channels, settings, entry, data) == 0)
{
WLog_INFO(TAG, "loading channel %s", name);
WLog_DBG(TAG, "loading channel %s", name);
return TRUE;
}
}

35
docs/version_detection.md Normal file
View File

@ -0,0 +1,35 @@
As FreeRDPs is build on different OS with different build tools and methods the
"version detection" has grown historically.
This document quickly describes how it's currently used.
When doing a `xfreerdp /version` for example the following is shown
`This is FreeRDP version 3.0.0-dev (c99c4cecddee4e5b914b122bc1531d47a668bb8e)`
The first part ist the Version as defined in `RAW_VERSION_STRING` and the second part, in braces,
the `GIT_REVISON` of this version.
`RAW_VERSION_STRING` is very vital as it determines the version used for libraries as well also for
all sub-projects as WinPR.
As default both variables are equal.
For nightly or development builds it is often of advantage to have the actual version from git
instead of having the hard coded value set in CMakeLists.txt. For this the cmake variable `USE_VERSION_FROM_GIT_TAG`
can be set. In order for this to work you need a) source checkout and b) git command line utility.
If enabled the information from the last git tag (in the format major.minor.patch-extra like
2.6.0-android12) will be used.
If you are building FreeRDP and can't use git because it's not available or the source is not in an
git repository - for example when building packages - the files `.source_tag` and `.source_version`
in the top-level source directory can be used. `.source_tag` is equal to `RAW_VERSION_STRING` and
need to contain the version in the same format as the git tag. `.source_version` is used to pre-fill
`GIT_REVISON`. Although mostly used for that it must not contain a git commit or tag - it can be
used to set additional arbitrary information. Our recommendation for packagers is to create
`.source_version` when importing and set it to the upstream commit or tag to simplify issue
tracking.
As summary the different mechanisms are applied in that order:
* `.source_tag` and `.source_version` if found
* version set from the last git tag if `RAW_VERSION_STRING` is set
* hard coded version in CMakeLists.txt

View File

@ -115,6 +115,21 @@ static int openh264_decompress(H264_CONTEXT* h264, const BYTE* pSrcData, UINT32
}
}
if (state != dsErrorFree)
{
WLog_Print(h264->log, WLOG_WARN, "DecodeFrame2 state: 0x%02X", state);
return -2003;
}
#if OPENH264_MAJOR >= 2
state = (*sys->pDecoder)->FlushFrame(sys->pDecoder, pYUVData, &sBufferInfo);
if (state != dsErrorFree)
{
WLog_Print(h264->log, WLOG_WARN, "FlushFrame state: 0x%02X", state);
return -2003;
}
#endif
pSystemBuffer = &sBufferInfo.UsrData.sSystemBuffer;
iStride[0] = pSystemBuffer->iStride[0];
iStride[1] = pSystemBuffer->iStride[1];

View File

@ -131,7 +131,10 @@ set(${MODULE_PREFIX}_SRCS
peer.c
peer.h
display.c
display.h)
display.h
utils.c
utils.h
)
set(${MODULE_PREFIX}_SRCS ${${MODULE_PREFIX}_SRCS} ${${MODULE_PREFIX}_GATEWAY_SRCS})

View File

@ -39,6 +39,8 @@
#include <freerdp/listener.h>
#include <freerdp/cache/pointer.h>
#include "utils.h"
#define TAG FREERDP_TAG("core.connection")
/**
@ -411,10 +413,13 @@ BOOL rdp_client_disconnect_and_clear(rdpRdp* rdp)
return FALSE;
context = rdp->context;
if (freerdp_get_last_error(context) == FREERDP_ERROR_CONNECT_CANCELLED)
return FALSE;
context->LastError = FREERDP_ERROR_SUCCESS;
clearChannelError(context);
ResetEvent(context->abortEvent);
return TRUE;
return utils_reset_abort(context);
}
static BOOL rdp_client_reconnect_channels(rdpRdp* rdp, BOOL redirect)

View File

@ -52,6 +52,7 @@
#include <freerdp/cache/pointer.h>
#include "settings.h"
#include "utils.h"
#define TAG FREERDP_TAG("core")
@ -168,7 +169,9 @@ BOOL freerdp_connect(freerdp* instance)
#endif
freerdp_set_last_error_log(instance->context, FREERDP_ERROR_SUCCESS);
clearChannelError(instance->context);
ResetEvent(instance->context->abortEvent);
if (!utils_reset_abort(instance->context))
return FALSE;
rdp = instance->context->rdp;
settings = instance->settings;
@ -308,7 +311,8 @@ BOOL freerdp_abort_connect(freerdp* instance)
if (!instance || !instance->context)
return FALSE;
return SetEvent(instance->context->abortEvent);
freerdp_set_last_error_if_not(instance->context, FREERDP_ERROR_CONNECT_CANCELLED);
return utils_abort_connect(instance->context);
}
BOOL freerdp_get_fds(freerdp* instance, void** rfds, int* rcount, void** wfds, int* wcount)
@ -540,11 +544,16 @@ BOOL freerdp_disconnect_before_reconnect(freerdp* instance)
BOOL freerdp_reconnect(freerdp* instance)
{
BOOL status;
rdpRdp* rdp = instance->context->rdp;
ResetEvent(instance->context->abortEvent);
status = rdp_client_reconnect(rdp);
return status;
rdpRdp* rdp;
if (freerdp_get_last_error(instance->context) == FREERDP_ERROR_CONNECT_CANCELLED)
return FALSE;
rdp = instance->context->rdp;
if (!utils_reset_abort(instance->context))
return FALSE;
return rdp_client_reconnect(rdp);
}
BOOL freerdp_shall_disconnect(freerdp* instance)
@ -886,7 +895,7 @@ void freerdp_set_last_error_ex(rdpContext* context, UINT32 lastError, const char
if (lastError == FREERDP_ERROR_SUCCESS)
{
WLog_INFO(TAG, "%s:%s resetting error state", fkt, __FUNCTION__);
WLog_DBG(TAG, "%s:%s resetting error state", fkt, __FUNCTION__);
}
else if (context->LastError != FREERDP_ERROR_SUCCESS)
{

View File

@ -38,6 +38,7 @@
#include "rpc_client.h"
#include "rts_signature.h"
#include "../utils.h"
#include "../rdp.h"
#include "../proxy.h"
@ -362,7 +363,7 @@ static int rpc_client_recv_fragment(rdpRpc* rpc, wStream* fragment)
Stream_SetPosition(fragment, StubOffset);
Stream_Read_UINT32(fragment, rpc->result);
freerdp_abort_connect(context->instance);
utils_abort_connect(context);
tsg_set_state(tsg, TSG_STATE_TUNNEL_CLOSE_PENDING);
EventArgsInit(&e, "freerdp");
e.code = 0;

View File

@ -27,6 +27,7 @@
#include "rdp.h"
#include "info.h"
#include "utils.h"
#include "redirection.h"
#include <freerdp/crypto/per.h>
@ -414,7 +415,7 @@ BOOL rdp_read_header(rdpRdp* rdp, wStream* s, UINT16* length, UINT16* channelId)
{
if (code == X224_TPDU_DISCONNECT_REQUEST)
{
freerdp_abort_connect(rdp->instance);
utils_abort_connect(rdp->instance->context);
return TRUE;
}
@ -471,7 +472,7 @@ BOOL rdp_read_header(rdpRdp* rdp, wStream* s, UINT16* length, UINT16* channelId)
}
WLog_DBG(TAG, "DisconnectProviderUltimatum: reason: %d", reason);
freerdp_abort_connect(rdp->instance);
utils_abort_connect(context);
EventArgsInit(&e, "freerdp");
e.code = 0;
PubSub_OnTerminate(context->pubSub, context, &e);

View File

@ -844,12 +844,7 @@ static BOOL freerdp_tcp_connect_timeout(rdpContext* context, int sockfd, struct
status = WaitForMultipleObjects(count, handles, FALSE, tout);
if (WAIT_OBJECT_0 != status)
{
if (status == WAIT_OBJECT_0 + 1)
freerdp_set_last_error_log(context, FREERDP_ERROR_CONNECT_CANCELLED);
goto fail;
}
status = recv(sockfd, NULL, 0, 0);
@ -1235,9 +1230,6 @@ int freerdp_tcp_connect(rdpContext* context, rdpSettings* settings, const char*
if (WaitForSingleObject(context->abortEvent, 0) == WAIT_OBJECT_0)
{
close(sockfd);
freerdp_set_last_error_if_not(context, FREERDP_ERROR_CONNECT_CANCELLED);
return -1;
}

47
libfreerdp/core/utils.c Normal file
View File

@ -0,0 +1,47 @@
/**
* FreeRDP: A Remote Desktop Protocol Implementation
* Terminal Server Gateway (utils)
*
* Copyright 2021 Armin Novak <armin.novak@thincast.com>
* Copyright 2021 Thincast Technologies GmbH
*
* 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.
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <assert.h>
#include <freerdp/freerdp.h>
#include <freerdp/log.h>
#define TAG FREERDP_TAG("core.gateway.utils")
#include "utils.h"
#define WINPR_ASSERT(x) assert(x)
BOOL utils_abort_connect(rdpContext* context)
{
WINPR_ASSERT(context);
return SetEvent(context->abortEvent);
}
BOOL utils_reset_abort(rdpContext* context)
{
WINPR_ASSERT(context);
return ResetEvent(context->abortEvent);
}

30
libfreerdp/core/utils.h Normal file
View File

@ -0,0 +1,30 @@
/**
* FreeRDP: A Remote Desktop Protocol Implementation
* Terminal Server Gateway (utils)
*
* Copyright 2021 Armin Novak <armin.novak@thincast.com>
* Copyright 2021 Thincast Technologies GmbH
*
* 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.
*/
#ifndef FREERDP_LIB_CORE_UTILS_H
#define FREERDP_LIB_CORE_UTILS_H
#include <winpr/winpr.h>
#include <freerdp/freerdp.h>
BOOL utils_reset_abort(rdpContext* context);
BOOL utils_abort_connect(rdpContext* context);
#endif /* FREERDP_LIB_CORE_UTILS_H */

View File

@ -866,7 +866,7 @@ int tls_connect(rdpTls* tls, BIO* underlying)
#else
if (!tls_prepare(tls, underlying, TLS_client_method(), options, TRUE))
#endif
return FALSE;
return 0;
#if !defined(OPENSSL_NO_TLSEXT) && !defined(LIBRESSL_VERSION_NUMBER)
SSL_set_tlsext_host_name(tls->ssl, tls->hostname);

View File

@ -260,7 +260,7 @@ static BOOL primitives_autodetect_best(primitives_t* prims)
/* finally compute the results */
*prims = *best->prims;
WLog_INFO(TAG, "primitives autodetect, using %s", best->name);
WLog_DBG(TAG, "primitives autodetect, using %s", best->name);
ret = TRUE;
out:
if (!ret)

View File

@ -51,7 +51,7 @@ if (NOT WIN32)
endif()
# Soname versioning
set(RAW_VERSION_STRING "2.6.0")
set(RAW_VERSION_STRING "2.6.1")
if(EXISTS "${CMAKE_SOURCE_DIR}/.source_tag")
file(READ ${CMAKE_SOURCE_DIR}/.source_tag RAW_VERSION_STRING)
elseif(USE_VERSION_FROM_GIT_TAG)

View File

@ -528,7 +528,7 @@ static void ClipboardInitLocalFileSubsystem(wClipboard* clipboard)
#ifdef WITH_WCLIPBOARD_POSIX
if (ClipboardInitPosixFileSubsystem(clipboard))
{
WLog_INFO(TAG, "initialized POSIX local file subsystem");
WLog_DBG(TAG, "initialized POSIX local file subsystem");
return;
}
else