[gnome-remote-desktop] rdp: Relieve CLIPRDR filename restriction when possible



commit 406ade74fd1689eeadf3c1bc952ce5f6a92899a3
Author: Pascal Nowack <Pascal Nowack gmx de>
Date:   Wed Jul 6 12:48:55 2022 +0200

    rdp: Relieve CLIPRDR filename restriction when possible
    
    Microsoft Windows imposes strict filename restrictions on its platform.
    As RDP is developed by Microsoft and the RDS in MS Windows is typically
    used as remote desktop server for the RDP protocol, these filename
    restrictions are also enforced in WinPR, when copy-pasting files over
    the clipboard.
    However, in some connections no peer on MS Windows is involved and in
    these situations, these filename restrictions are just an annoyance.
    
    With a recent API addition in WinPR, it is now possible to override the
    callback, where the filename is checked, whether it is valid.
    So, use this new API to relieve the filename restriction, when the
    connected remote desktop client is not on MS Windows.

 src/grd-clipboard-rdp.c | 36 +++++++++++++++++++++++++++++++++++-
 src/grd-clipboard-rdp.h |  3 ++-
 src/grd-session-rdp.c   |  5 ++++-
 3 files changed, 41 insertions(+), 3 deletions(-)
---
diff --git a/src/grd-clipboard-rdp.c b/src/grd-clipboard-rdp.c
index 8abbd8f0..cc512d12 100644
--- a/src/grd-clipboard-rdp.c
+++ b/src/grd-clipboard-rdp.c
@@ -80,6 +80,8 @@ struct _GrdClipboardRdp
   CliprdrServerContext *cliprdr_context;
   HANDLE stop_event;
 
+  gboolean relieve_filename_restriction;
+
   wClipboard *system;
   wClipboardDelegate *delegate;
   gboolean has_file_list;
@@ -2256,6 +2258,27 @@ cliprdr_file_range_failure (wClipboardDelegate               *delegate,
                                               file_range_request->streamId);
 }
 
+static BOOL
+is_valid_unix_filename (LPCWSTR filename)
+{
+  LPCWSTR c;
+
+  if (!filename)
+    return FALSE;
+
+  if (filename[0] == L'\0')
+    return FALSE;
+
+  /* Reserved characters */
+  for (c = filename; *c; ++c)
+    {
+      if (*c == L'/')
+        return FALSE;
+    }
+
+  return TRUE;
+}
+
 static void
 create_new_winpr_clipboard (GrdClipboardRdp *clipboard_rdp)
 {
@@ -2270,13 +2293,17 @@ create_new_winpr_clipboard (GrdClipboardRdp *clipboard_rdp)
   clipboard_rdp->delegate->basePath = NULL;
   clipboard_rdp->delegate->custom = clipboard_rdp;
 
+  if (clipboard_rdp->relieve_filename_restriction)
+    clipboard_rdp->delegate->IsFileNameComponentValid = is_valid_unix_filename;
+
   clipboard_rdp->has_file_list = FALSE;
 }
 
 GrdClipboardRdp *
 grd_clipboard_rdp_new (GrdSessionRdp *session_rdp,
                        HANDLE         vcm,
-                       HANDLE         stop_event)
+                       HANDLE         stop_event,
+                       gboolean       relieve_filename_restriction)
 {
   g_autoptr (GrdClipboardRdp) clipboard_rdp = NULL;
   GrdClipboard *clipboard;
@@ -2292,6 +2319,7 @@ grd_clipboard_rdp_new (GrdSessionRdp *session_rdp,
 
   clipboard_rdp->cliprdr_context = cliprdr_context;
   clipboard_rdp->stop_event = stop_event;
+  clipboard_rdp->relieve_filename_restriction = relieve_filename_restriction;
 
   clipboard = GRD_CLIPBOARD (clipboard_rdp);
   grd_clipboard_initialize (clipboard, GRD_SESSION (session_rdp));
@@ -2314,6 +2342,12 @@ grd_clipboard_rdp_new (GrdSessionRdp *session_rdp,
   cliprdr_context->ClientFileContentsResponse = cliprdr_client_file_contents_response;
   cliprdr_context->custom = clipboard_rdp;
 
+  if (relieve_filename_restriction)
+    {
+      g_message ("[RDP.CLIPRDR] Relieving CLIPRDR filename restriction");
+      clipboard_rdp->delegate->IsFileNameComponentValid = is_valid_unix_filename;
+    }
+
   if (cliprdr_context->Start (cliprdr_context))
     {
       g_warning ("[RDP.CLIPRDR] Failed to open CLIPRDR channel");
diff --git a/src/grd-clipboard-rdp.h b/src/grd-clipboard-rdp.h
index abb8b45e..6594c005 100644
--- a/src/grd-clipboard-rdp.h
+++ b/src/grd-clipboard-rdp.h
@@ -32,7 +32,8 @@ G_DECLARE_FINAL_TYPE (GrdClipboardRdp,
 
 GrdClipboardRdp *grd_clipboard_rdp_new (GrdSessionRdp *session_rdp,
                                         HANDLE         vcm,
-                                        HANDLE         stop_event);
+                                        HANDLE         stop_event,
+                                        gboolean       relieve_filename_restriction);
 
 void grd_clipboard_rdp_lock_remote_clipboard_data (GrdClipboardRdp *clipboard_rdp,
                                                    uint32_t         clip_data_id);
diff --git a/src/grd-session-rdp.c b/src/grd-session-rdp.c
index dad54717..d5626542 100644
--- a/src/grd-session-rdp.c
+++ b/src/grd-session-rdp.c
@@ -2637,9 +2637,12 @@ initialize_remaining_virtual_channels (GrdSessionRdp *session_rdp)
   if (WTSVirtualChannelManagerIsChannelJoined (rdp_peer_context->vcm,
                                                "cliprdr"))
     {
+      gboolean peer_is_on_ms_windows;
+
+      peer_is_on_ms_windows = rdp_settings->OsMajorType == OSMAJORTYPE_WINDOWS;
       rdp_peer_context->clipboard_rdp =
         grd_clipboard_rdp_new (session_rdp, rdp_peer_context->vcm,
-                               session_rdp->stop_event);
+                               session_rdp->stop_event, !peer_is_on_ms_windows);
     }
   if (rdp_settings->AudioPlayback && !rdp_settings->RemoteConsoleAudio)
     {


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]