From db2d8b11e91e1f89c2210040e300e408fb390e2b Mon Sep 17 00:00:00 2001 From: Kobi Mizrachi Date: Tue, 7 Jul 2020 10:16:28 +0300 Subject: [PATCH] libfreerdp: core: add ServerHeartbeat callback (cherry picked from commit 2096ede5cc8caa209c532438e3a1173f6b47e2c4) --- include/freerdp/freerdp.h | 5 ++++- include/freerdp/heartbeat.h | 46 +++++++++++++++++++++++++++++++++++++++++++++ libfreerdp/core/freerdp.c | 1 + libfreerdp/core/heartbeat.c | 31 ++++++++++++++++++++++++++++++ libfreerdp/core/heartbeat.h | 8 +------- 5 files changed, 83 insertions(+), 8 deletions(-) create mode 100644 include/freerdp/heartbeat.h diff --git a/include/freerdp/freerdp.h b/include/freerdp/freerdp.h index c5b8f0f..2302341 100644 --- a/include/freerdp/freerdp.h +++ b/include/freerdp/freerdp.h @@ -54,6 +54,7 @@ typedef RDP_CLIENT_ENTRY_POINTS_V1 RDP_CLIENT_ENTRY_POINTS; #include #include #include +#include #ifdef __cplusplus extern "C" @@ -309,7 +310,9 @@ extern "C" ALIGN64 rdpAutoDetect* autodetect; /* (offset 19) Auto-Detect handle for the connection. Will be initialized by a call to freerdp_context_new() */ - UINT64 paddingB[32 - 20]; /* 20 */ + ALIGN64 rdpHeartbeat* heartbeat; /* (offset 21) */ + + UINT64 paddingB[32 - 21]; /* 21 */ ALIGN64 size_t ContextSize; /* (offset 32) diff --git a/include/freerdp/heartbeat.h b/include/freerdp/heartbeat.h new file mode 100644 index 0000000..10710f5 --- /dev/null +++ b/include/freerdp/heartbeat.h @@ -0,0 +1,46 @@ +/** + * FreeRDP: A Remote Desktop Protocol Implementation + * Heartbeat PDUs + * + * Copyright 2014 Dell Software + * + * 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_HEARTBEAT_H +#define FREERDP_HEARTBEAT_H + +#include + +typedef struct rdp_heartbeat rdpHeartbeat; + +typedef BOOL (*pServerHeartbeat)(freerdp* instance, BYTE period, BYTE count1, BYTE count2); + +struct rdp_heartbeat +{ + pServerHeartbeat ServerHeartbeat; +}; + +#ifdef __cplusplus +extern "C" +{ +#endif + + FREERDP_API BOOL freerdp_heartbeat_send_heartbeat_pdu(freerdp_peer* peer, BYTE period, + BYTE count1, BYTE count2); + +#ifdef __cplusplus +} +#endif + +#endif /* FREERDP_HEARTBEAT_H */ diff --git a/libfreerdp/core/freerdp.c b/libfreerdp/core/freerdp.c index 6eddefe..9094bc3 100644 --- a/libfreerdp/core/freerdp.c +++ b/libfreerdp/core/freerdp.c @@ -672,6 +672,7 @@ BOOL freerdp_context_new(freerdp* instance) instance->update = rdp->update; instance->settings = rdp->settings; instance->autodetect = rdp->autodetect; + instance->heartbeat = rdp->heartbeat; context->graphics = graphics_new(context); if (!context->graphics) diff --git a/libfreerdp/core/heartbeat.c b/libfreerdp/core/heartbeat.c index 31af05f..8418ba3 100644 --- a/libfreerdp/core/heartbeat.c +++ b/libfreerdp/core/heartbeat.c @@ -31,6 +31,7 @@ int rdp_recv_heartbeat_packet(rdpRdp* rdp, wStream* s) BYTE period; BYTE count1; BYTE count2; + BOOL rc; if (Stream_GetRemainingLength(s) < 4) return -1; @@ -44,9 +45,39 @@ int rdp_recv_heartbeat_packet(rdpRdp* rdp, wStream* s) "received Heartbeat PDU -> period=%" PRIu8 ", count1=%" PRIu8 ", count2=%" PRIu8 "", period, count1, count2); + rc = IFCALLRESULT(TRUE, rdp->heartbeat->ServerHeartbeat, rdp->instance, period, count1, count2); + if (!rc) + { + WLog_ERR(HEARTBEAT_TAG, "heartbeat->ServerHeartbeat callback failed!"); + return -1; + } + return 0; } +BOOL freerdp_heartbeat_send_heartbeat_pdu(freerdp_peer* peer, BYTE period, BYTE count1, BYTE count2) +{ + rdpRdp* rdp = peer->context->rdp; + wStream* s = rdp_message_channel_pdu_init(rdp); + + if (!s) + return FALSE; + + Stream_Seek_UINT8(s); /* reserved (1 byte) */ + Stream_Write_UINT8(s, period); /* period (1 byte) */ + Stream_Write_UINT8(s, count1); /* count1 (1 byte) */ + Stream_Write_UINT8(s, count2); /* count2 (1 byte) */ + + WLog_DBG(HEARTBEAT_TAG, + "sending Heartbeat PDU -> period=%" PRIu8 ", count1=%" PRIu8 ", count2=%" PRIu8 "", + period, count1, count2); + + if (!rdp_send_message_channel_pdu(rdp, s, SEC_HEARTBEAT)) + return FALSE; + + return TRUE; +} + rdpHeartbeat* heartbeat_new(void) { rdpHeartbeat* heartbeat = (rdpHeartbeat*)calloc(1, sizeof(rdpHeartbeat)); diff --git a/libfreerdp/core/heartbeat.h b/libfreerdp/core/heartbeat.h index 53dfe63..f7cf634 100644 --- a/libfreerdp/core/heartbeat.h +++ b/libfreerdp/core/heartbeat.h @@ -20,21 +20,15 @@ #ifndef FREERDP_LIB_CORE_HEARTBEET_H #define FREERDP_LIB_CORE_HEARTBEET_H -typedef struct rdp_heartbeat rdpHeartbeat; - #include "rdp.h" +#include #include #include #include #include -struct rdp_heartbeat -{ - UINT32 placeholder; -}; - int rdp_recv_heartbeat_packet(rdpRdp* rdp, wStream* s); FREERDP_LOCAL rdpHeartbeat* heartbeat_new(void); -- 2.7.4