[Spice-devel] [PATCH 34/35] migration: new api

Gerd Hoffmann kraxel at redhat.com
Wed May 12 04:32:28 PDT 2010


Add new API for migration, based on what RHEL-6 has.
---
 server/reds.c         |  107 ++++++++++++++++++++++++++++++++++---------------
 server/spice.h        |   12 +++++
 server/vd_interface.h |    7 ---
 3 files changed, 87 insertions(+), 39 deletions(-)

diff --git a/server/reds.c b/server/reds.c
index 7a8cada..6275cf0 100644
--- a/server/reds.c
+++ b/server/reds.c
@@ -241,6 +241,8 @@ typedef struct RedsStatValue {
 
 #endif
 
+typedef struct RedsMigSpice RedsMigSpice;
+
 typedef struct RedsState {
     int listen_socket;
     int secure_listen_socket;
@@ -258,6 +260,7 @@ typedef struct RedsState {
     int mig_wait_disconnect;
     int mig_inprogress;
     int mig_target;
+    RedsMigSpice *mig_spice;
     int num_of_channels;
     IncomingHandler in_handler;
     RedsOutgoingData outgoing;
@@ -3206,7 +3209,7 @@ static void set_one_channel_security(int id, uint32_t security)
 
 #define REDS_SAVE_VERSION 1
 
-typedef struct RedsMigSpice {
+struct RedsMigSpice {
     char pub_key[SPICE_TICKET_PUBKEY_BYTES];
     uint32_t mig_key;
     char *host;
@@ -3215,7 +3218,7 @@ typedef struct RedsMigSpice {
     uint16_t cert_pub_key_type;
     uint32_t cert_pub_key_len;
     uint8_t* cert_pub_key;
-} RedsMigSpice;
+};
 
 typedef struct RedsMigSpiceMessage {
     uint32_t link_id;
@@ -3226,8 +3229,9 @@ typedef struct RedsMigCertPubKeyInfo {
     uint32_t len;
 } RedsMigCertPubKeyInfo;
 
-static void reds_mig_continue(RedsMigSpice *s)
+static void reds_mig_continue(void)
 {
+    RedsMigSpice *s = reds->mig_spice;
     SpiceMsgMainMigrationBegin *migrate;
     SimpleOutItem *item;
     int host_len;
@@ -3248,15 +3252,16 @@ static void reds_mig_continue(RedsMigSpice *s)
     memcpy((uint8_t*)(migrate) + migrate->pub_key_offset, s->cert_pub_key, s->cert_pub_key_len);
     reds_push_pipe_item(&item->base);
 
-    free(s);
+    free(reds->mig_spice->host);
+    free(reds->mig_spice);
+    reds->mig_spice = NULL;
+
     reds->mig_wait_connect = TRUE;
     core->timer_start(reds->mig_timer, MIGRATE_TIMEOUT);
 }
 
-static void reds_mig_started(void *opaque)
+static void reds_mig_started(void)
 {
-    RedsMigSpice *spice_migration = NULL;
-
     red_printf("");
 
     reds->mig_inprogress = TRUE;
@@ -3280,30 +3285,19 @@ static void reds_mig_started(void *opaque)
         goto error;
     }
 
-    spice_migration = spice_new0(RedsMigSpice, 1);
-    spice_migration->port = -1;
-    spice_migration->sport = -1;
-
-    /* FIXME */
-
-    if ((spice_migration->sport == -1 && spice_migration->port == -1) || !spice_migration->host) {
-        red_printf("invalid args port %d sport %d host %s",
-                   spice_migration->port,
-                   spice_migration->sport,
-                   (spice_migration->host) ? spice_migration->host : "NULL");
-        goto error;
-    }
-
-    /* FIXME: send SPICE_MSG_MAIN_MIGRATE_BEGIN ??? */
-    reds_mig_continue(spice_migration);
+    reds_mig_continue();
     return;
 
 error:
-    free(spice_migration);
+    if (reds->mig_spice) {
+        free(reds->mig_spice->host);
+        free(reds->mig_spice);
+        reds->mig_spice = NULL;
+    }
     reds_mig_disconnect();
 }
 
-static void reds_mig_finished(void *opaque, int completed)
+static void reds_mig_finished(int completed)
 {
     SimpleOutItem *item;
 
@@ -3471,13 +3465,6 @@ __visible__ int spice_server_add_interface(SpiceServer *s,
             return -1;
         }
         mig = (MigrationInterface *)interface;
-        reds->mig_notifier = mig->register_notifiers(mig,
-                                                     reds_mig_started,
-                                                     reds_mig_finished,
-                                                     NULL);
-        if (reds->mig_notifier == INVALID_VD_OBJECT_REF) {
-            red_error("migration register failed");
-        }
 
     } else if (strcmp(interface->type, SPICE_INTERFACE_QXL) == 0) {
         QXLInstance *qxl;
@@ -3962,3 +3949,59 @@ __visible__ int spice_server_kbd_leds(SpiceKbdInstance *sin, int leds)
     reds_on_keyboard_leds_change(NULL, leds);
     return 0;
 }
+
+__visible__ int spice_server_migrate_info(SpiceServer *s, const char* dest,
+                                          int port, int secure_port,
+                                          const char* cert_subject)
+{
+    RedsMigSpice *spice_migration = NULL;
+
+    ASSERT(reds == s);
+
+    if ((port == -1 && secure_port == -1) || !dest)
+        return -1;
+
+    spice_migration = spice_new0(RedsMigSpice, 1);
+    spice_migration->port = port;
+    spice_migration->sport = secure_port;
+    spice_migration->host = strdup(dest);
+
+    if (cert_subject) {
+        /* TODO */
+    }
+
+    reds->mig_spice = spice_migration;
+    return 0;
+}
+
+__visible__ int spice_server_migrate_start(SpiceServer *s)
+{
+    ASSERT(reds == s);
+
+    if (!reds->mig_spice) {
+        return -1;
+    }
+    reds_mig_started();
+    return 0;
+}
+
+__visible__ int spice_server_migrate_client_state(SpiceServer *s)
+{
+    ASSERT(reds == s);
+
+    if (!reds->peer) {
+        return SPICE_MIGRATE_CLIENT_NONE;
+    } else if (reds->mig_wait_connect) {
+        return SPICE_MIGRATE_CLIENT_WAITING;
+    } else {
+        return SPICE_MIGRATE_CLIENT_READY;
+    }
+    return 0;
+}
+
+__visible__ int spice_server_migrate_end(SpiceServer *s, int completed)
+{
+    ASSERT(reds == s);
+    reds_mig_finished(completed);
+    return 0;
+}
diff --git a/server/spice.h b/server/spice.h
index 80291b9..70434c2 100644
--- a/server/spice.h
+++ b/server/spice.h
@@ -69,4 +69,16 @@ int spice_server_add_renderer(SpiceServer *s, const char *name);
 int spice_server_get_sock_info(SpiceServer *s, struct sockaddr *sa, socklen_t *salen);
 int spice_server_get_peer_info(SpiceServer *s, struct sockaddr *sa, socklen_t *salen);
 
+enum {
+    SPICE_MIGRATE_CLIENT_NONE = 1,
+    SPICE_MIGRATE_CLIENT_WAITING,
+    SPICE_MIGRATE_CLIENT_READY,
+};
+
+int spice_server_migrate_info(SpiceServer *s, const char* dest, int port, int secure_port,
+                              const char* cert_subject);
+int spice_server_migrate_start(SpiceServer *s);
+int spice_server_migrate_client_state(SpiceServer *s);
+int spice_server_migrate_end(SpiceServer *s, int completed);
+
 #endif
diff --git a/server/vd_interface.h b/server/vd_interface.h
index 7c7c202..a5a20ec 100644
--- a/server/vd_interface.h
+++ b/server/vd_interface.h
@@ -268,17 +268,10 @@ struct SpiceTabletInstance {
 #define VD_INTERFACE_MIGRATION_MAJOR 1
 #define VD_INTERFACE_MIGRATION_MINOR 1
 typedef struct MigrationInterface MigrationInterface;
-typedef void (*migration_notify_started_t)(void *opaque);
-typedef void (*migration_notify_finished_t)(void *opaque, int completed);
 
 struct MigrationInterface {
     SpiceBaseInterface base;
 
-    VDObjectRef (*register_notifiers)(MigrationInterface* mig,
-                                      migration_notify_started_t,
-                                      migration_notify_finished_t,
-                                      void *opaque);
-    void (*unregister_notifiers)(MigrationInterface* mig, VDObjectRef notifier);
     void (*notifier_done)(MigrationInterface *mig, VDObjectRef notifier);
 };
 
-- 
1.6.6.1



More information about the Spice-devel mailing list