[spice-gtk,v4,19/29] usb-redir: command-line option to create emulated CD drive

Submitted by Frediano Ziglio on Aug. 27, 2019, 9:22 a.m.

Details

Message ID 20190827092246.10276-20-fziglio@redhat.com
State Superseded
Headers show
Series "added feature of sharing CD image" ( rev: 6 ) in Spice

Not browsing as part of any series.

Commit Message

Frediano Ziglio Aug. 27, 2019, 9:22 a.m.
From: Yuri Benditovich <yuri.benditovich@daynix.com>

Added command-line option for sharing emulated CD devices.
It uses property interface of usb-device-manager to
create CD, this is a temporary solution until public API of
usb-device-manager defined for shared CD management from both
GUI and command line.

Signed-off-by: Yuri Benditovich <yuri.benditovich@daynix.com>
---
 src/spice-option.c       | 17 +++++++++++++++++
 src/usb-device-manager.c | 34 ++++++++++++++++++++++++++++++++++
 2 files changed, 51 insertions(+)

Patch hide | download patch | download mbox

diff --git a/src/spice-option.c b/src/spice-option.c
index 8c4e707c..f0b3b5d6 100644
--- a/src/spice-option.c
+++ b/src/spice-option.c
@@ -32,6 +32,7 @@  static char *smartcard_db = NULL;
 static char *smartcard_certificates = NULL;
 static char *usbredir_auto_redirect_filter = NULL;
 static char *usbredir_redirect_on_connect = NULL;
+static gchar **cd_share_files = NULL;
 static gboolean smartcard = FALSE;
 static gboolean disable_audio = FALSE;
 static gboolean disable_usbredir = FALSE;
@@ -183,6 +184,9 @@  GOptionGroup* spice_get_option_group(void)
           N_("Filter selecting USB devices to be auto-redirected when plugged in"), N_("<filter-string>") },
         { "spice-usbredir-redirect-on-connect", '\0', 0, G_OPTION_ARG_STRING, &usbredir_redirect_on_connect,
           N_("Filter selecting USB devices to redirect on connect"), N_("<filter-string>") },
+        { "spice-share-cd", '\0', 0, G_OPTION_ARG_STRING_ARRAY, &cd_share_files,
+          N_("Name of ISO file or CD/DVD device to share; prefix '!' to delete on eject"),
+          N_("<filename> (repeat allowed)") },
         { "spice-cache-size", '\0', 0, G_OPTION_ARG_INT, &cache_size,
           N_("Image cache size (deprecated)"), N_("<bytes>") },
         { "spice-glz-window-size", '\0', 0, G_OPTION_ARG_INT, &glz_window_size,
@@ -288,6 +292,19 @@  void spice_set_session_option(SpiceSession *session)
                          usbredir_redirect_on_connect, NULL);
         }
     }
+    if (cd_share_files) {
+        SpiceUsbDeviceManager *m =
+                get_usb_device_manager_for_option(session, "--spice-share-cd");
+        if (m) {
+            gchar **name = cd_share_files;
+            while (name && *name) {
+                g_object_set(m, "share-cd", *name, NULL);
+                name++;
+            }
+        }
+        g_strfreev(cd_share_files);
+        cd_share_files = NULL;
+    }
     if (disable_usbredir)
         g_object_set(session, "enable-usbredir", FALSE, NULL);
     if (disable_audio)
diff --git a/src/usb-device-manager.c b/src/usb-device-manager.c
index 5834e032..187ccfa2 100644
--- a/src/usb-device-manager.c
+++ b/src/usb-device-manager.c
@@ -32,6 +32,7 @@ 
 #endif
 
 #include "channel-usbredir-priv.h"
+#include "usb-device-cd.h"
 #endif
 
 #include "spice-session-priv.h"
@@ -74,6 +75,7 @@  enum {
     PROP_AUTO_CONNECT_FILTER,
     PROP_REDIRECT_ON_CONNECT,
     PROP_FREE_CHANNELS,
+    PROP_SHARE_CD
 };
 
 enum
@@ -432,6 +434,26 @@  static void spice_usb_device_manager_set_property(GObject       *gobject,
         priv->redirect_on_connect = g_strdup(filter);
         break;
     }
+    case PROP_SHARE_CD:
+    {
+#ifdef USE_USBREDIR
+        CdEmulationParams param = { 0 };
+        const gchar *name = g_value_get_string(value);
+        /* the string is temporary, no need to keep it */
+        SPICE_DEBUG("share_cd set to %s", name);
+        if (name[0] == '!') {
+            name++;
+            param.delete_on_eject = 1;
+        }
+        param.filename = name;
+        GError *error = NULL;
+        if (!create_emulated_cd(priv->context, &param, &error)) {
+            g_warning(error->message);
+            g_error_free(error);
+        }
+#endif
+        break;
+    }
     default:
         G_OBJECT_WARN_INVALID_PROPERTY_ID(gobject, prop_id, pspec);
         break;
@@ -522,6 +544,18 @@  static void spice_usb_device_manager_class_init(SpiceUsbDeviceManagerClass *klas
     g_object_class_install_property(gobject_class, PROP_REDIRECT_ON_CONNECT,
                                     pspec);
 
+    /**
+    * SpiceUsbDeviceManager:share-cd:
+    *
+    * Set a string specifying a filename (ISO) or physical CD/DVD device
+    * to share via USB after a Spice connection has been established.
+    *
+    */
+    pspec = g_param_spec_string("share-cd", "Share ISO file or device as CD",
+        "File or device name to share", NULL,
+        G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS);
+    g_object_class_install_property(gobject_class, PROP_SHARE_CD, pspec);
+
     /**
      * SpiceUsbDeviceManager:free-channels:
      *

Comments


> 
> Hi,
> 
> On Tue, Aug 27, 2019 at 10:22:36AM +0100, Frediano Ziglio wrote:
> > From: Yuri Benditovich <yuri.benditovich@daynix.com>
> > 
> > Added command-line option for sharing emulated CD devices.
> > It uses property interface of usb-device-manager to
> > create CD, this is a temporary solution until public API of
> > usb-device-manager defined for shared CD management from both
> > GUI and command line.
> > 
> > Signed-off-by: Yuri Benditovich <yuri.benditovich@daynix.com>
> > ---
> >  src/spice-option.c       | 17 +++++++++++++++++
> >  src/usb-device-manager.c | 34 ++++++++++++++++++++++++++++++++++
> >  2 files changed, 51 insertions(+)
> > 
> > diff --git a/src/spice-option.c b/src/spice-option.c
> > index 8c4e707c..f0b3b5d6 100644
> > --- a/src/spice-option.c
> > +++ b/src/spice-option.c
> > @@ -32,6 +32,7 @@ static char *smartcard_db = NULL;
> >  static char *smartcard_certificates = NULL;
> >  static char *usbredir_auto_redirect_filter = NULL;
> >  static char *usbredir_redirect_on_connect = NULL;
> > +static gchar **cd_share_files = NULL;
> >  static gboolean smartcard = FALSE;
> >  static gboolean disable_audio = FALSE;
> >  static gboolean disable_usbredir = FALSE;
> > @@ -183,6 +184,9 @@ GOptionGroup* spice_get_option_group(void)
> >            N_("Filter selecting USB devices to be auto-redirected when
> >            plugged in"), N_("<filter-string>") },
> >          { "spice-usbredir-redirect-on-connect", '\0', 0,
> >          G_OPTION_ARG_STRING, &usbredir_redirect_on_connect,
> >            N_("Filter selecting USB devices to redirect on connect"),
> >            N_("<filter-string>") },
> > +        { "spice-share-cd", '\0', 0, G_OPTION_ARG_STRING_ARRAY,
> > &cd_share_files,
> > +          N_("Name of ISO file or CD/DVD device to share; prefix '!' to
> > delete on eject"),
> > +          N_("<filename> (repeat allowed)") },
> >          { "spice-cache-size", '\0', 0, G_OPTION_ARG_INT, &cache_size,
> >            N_("Image cache size (deprecated)"), N_("<bytes>") },
> >          { "spice-glz-window-size", '\0', 0, G_OPTION_ARG_INT,
> >          &glz_window_size,
> > @@ -288,6 +292,19 @@ void spice_set_session_option(SpiceSession *session)
> >                           usbredir_redirect_on_connect, NULL);
> >          }
> >      }
> > +    if (cd_share_files) {
> > +        SpiceUsbDeviceManager *m =
> > +                get_usb_device_manager_for_option(session,
> > "--spice-share-cd");
> > +        if (m) {
> > +            gchar **name = cd_share_files;
> > +            while (name && *name) {
> > +                g_object_set(m, "share-cd", *name, NULL);
> > +                name++;
> > +            }
> > +        }
> > +        g_strfreev(cd_share_files);
> > +        cd_share_files = NULL;
> > +    }
> >      if (disable_usbredir)
> >          g_object_set(session, "enable-usbredir", FALSE, NULL);
> >      if (disable_audio)
> > diff --git a/src/usb-device-manager.c b/src/usb-device-manager.c
> > index 5834e032..187ccfa2 100644
> > --- a/src/usb-device-manager.c
> > +++ b/src/usb-device-manager.c
> > @@ -32,6 +32,7 @@
> >  #endif
> >  
> >  #include "channel-usbredir-priv.h"
> > +#include "usb-device-cd.h"
> >  #endif
> >  
> >  #include "spice-session-priv.h"
> > @@ -74,6 +75,7 @@ enum {
> >      PROP_AUTO_CONNECT_FILTER,
> >      PROP_REDIRECT_ON_CONNECT,
> >      PROP_FREE_CHANNELS,
> > +    PROP_SHARE_CD
> >  };
> >  
> >  enum
> > @@ -432,6 +434,26 @@ static void
> > spice_usb_device_manager_set_property(GObject       *gobject,
> >          priv->redirect_on_connect = g_strdup(filter);
> >          break;
> >      }
> > +    case PROP_SHARE_CD:
> > +    {
> > +#ifdef USE_USBREDIR
> > +        CdEmulationParams param = { 0 };
> > +        const gchar *name = g_value_get_string(value);
> > +        /* the string is temporary, no need to keep it */
> > +        SPICE_DEBUG("share_cd set to %s", name);
> > +        if (name[0] == '!') {
> > +            name++;
> > +            param.delete_on_eject = 1;
> > +        }
> > +        param.filename = name;
> > +        GError *error = NULL;
> > +        if (!create_emulated_cd(priv->context, &param, &error)) {
> > +            g_warning(error->message);
> > +            g_error_free(error);
> > +        }
> > +#endif
> 
> This was acked before, I think I just asked for an #else
> g_warning("usbredir is not set, can't set share-cd") or something
> like that
> 
> > +        break;
> > +    }
> >      default:
> >          G_OBJECT_WARN_INVALID_PROPERTY_ID(gobject, prop_id, pspec);
> >          break;
> > @@ -522,6 +544,18 @@ static void
> > spice_usb_device_manager_class_init(SpiceUsbDeviceManagerClass *klas
> >      g_object_class_install_property(gobject_class,
> >      PROP_REDIRECT_ON_CONNECT,
> >                                      pspec);
> >  
> > +    /**
> > +    * SpiceUsbDeviceManager:share-cd:
> > +    *
> > +    * Set a string specifying a filename (ISO) or physical CD/DVD device
> > +    * to share via USB after a Spice connection has been established.
> > +    *
> > +    */
> > +    pspec = g_param_spec_string("share-cd", "Share ISO file or device as
> > CD",
> > +        "File or device name to share", NULL,
> > +        G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS);
> > +    g_object_class_install_property(gobject_class, PROP_SHARE_CD, pspec);
> > +
> >      /**
> >       * SpiceUsbDeviceManager:free-channels:
> >       *

Personally for me is a NACK.
Adding an ABI based on property used for dynamic dispatch is a dirty hack
on a public interface which by definition should not be a hack.

Frediano