[libvirt] [PATCH] remote generator: Allow to annotate arrays with typecasts

Matthias Bolte matthias.bolte at googlemail.com
Thu Jun 16 09:44:19 UTC 2011


Removes special case code from the generator and handle additional
methods.

The generated version of remoteDispatchDomainPinVcpu(Flags) has no
length check, but this check was useless anyway as it was applied to
data that was already deserialized from its XDR form.
---
 daemon/remote.c              |   82 --------------------------------------
 daemon/remote_generator.pl   |   90 ++++++++++++++++++++++++++++++------------
 src/remote/remote_protocol.x |   17 +++++---
 3 files changed, 74 insertions(+), 115 deletions(-)

diff --git a/daemon/remote.c b/daemon/remote.c
index f2e193d..37fbed0 100644
--- a/daemon/remote.c
+++ b/daemon/remote.c
@@ -1269,88 +1269,6 @@ cleanup:
 }
 
 static int
-remoteDispatchDomainPinVcpu(struct qemud_server *server ATTRIBUTE_UNUSED,
-                            struct qemud_client *client ATTRIBUTE_UNUSED,
-                            virConnectPtr conn,
-                            remote_message_header *hdr ATTRIBUTE_UNUSED,
-                            remote_error *rerr,
-                            remote_domain_pin_vcpu_args *args,
-                            void *ret ATTRIBUTE_UNUSED)
-{
-    virDomainPtr dom = NULL;
-    int rv = -1;
-
-    if (!conn) {
-        virNetError(VIR_ERR_INTERNAL_ERROR, "%s", _("connection not open"));
-        goto cleanup;
-    }
-
-    if (!(dom = get_nonnull_domain(conn, args->dom)))
-        goto cleanup;
-
-    if (args->cpumap.cpumap_len > REMOTE_CPUMAP_MAX) {
-        virNetError(VIR_ERR_INTERNAL_ERROR, "%s", _("cpumap_len > REMOTE_CPUMAP_MAX"));
-        goto cleanup;
-    }
-
-    if (virDomainPinVcpu(dom, args->vcpu,
-                         (unsigned char *) args->cpumap.cpumap_val,
-                         args->cpumap.cpumap_len) < 0)
-        goto cleanup;
-
-    rv = 0;
-
-cleanup:
-    if (rv < 0)
-        remoteDispatchError(rerr);
-    if (dom)
-        virDomainFree(dom);
-    return rv;
-}
-
-static int
-remoteDispatchDomainPinVcpuFlags(struct qemud_server *server ATTRIBUTE_UNUSED,
-                                 struct qemud_client *client ATTRIBUTE_UNUSED,
-                                 virConnectPtr conn,
-                                 remote_message_header *hdr ATTRIBUTE_UNUSED,
-                                 remote_error *rerr,
-                                 remote_domain_pin_vcpu_flags_args *args,
-                                 void *ret ATTRIBUTE_UNUSED)
-{
-    virDomainPtr dom = NULL;
-    int rv = -1;
-
-    if (!conn) {
-        virNetError(VIR_ERR_INTERNAL_ERROR, "%s", _("connection not open"));
-        goto cleanup;
-    }
-
-    if (!(dom = get_nonnull_domain(conn, args->dom)))
-        goto cleanup;
-
-    if (args->cpumap.cpumap_len > REMOTE_CPUMAP_MAX) {
-        virNetError(VIR_ERR_INTERNAL_ERROR, "%s", _("cpumap_len > REMOTE_CPUMAP_MAX"));
-        goto cleanup;
-    }
-
-    if (virDomainPinVcpuFlags(dom,
-                              args->vcpu,
-                              (unsigned char *) args->cpumap.cpumap_val,
-                              args->cpumap.cpumap_len,
-                              args->flags) < 0)
-        goto cleanup;
-
-    rv = 0;
-
-cleanup:
-    if (rv < 0)
-        remoteDispatchError(rerr);
-    if (dom)
-        virDomainFree(dom);
-    return rv;
-}
-
-static int
 remoteDispatchDomainGetMemoryParameters(struct qemud_server *server
                                         ATTRIBUTE_UNUSED,
                                         struct qemud_client *client
diff --git a/daemon/remote_generator.pl b/daemon/remote_generator.pl
index d9d9ded..146c56b 100755
--- a/daemon/remote_generator.pl
+++ b/daemon/remote_generator.pl
@@ -403,20 +403,32 @@ elsif ($opt_b) {
                          "        virDomainSnapshotFree(snapshot);\n" .
                          "    if (dom)\n" .
                          "        virDomainFree(dom);");
-                } elsif ($args_member =~ m/^(remote_string|remote_nonnull_string|remote_uuid|opaque) (\S+)<\S+>;/) {
+                } elsif ($args_member =~ m/^(?:remote_string|remote_uuid) (\S+)<\S+>;/) {
                     if (! @args_list) {
                         push(@args_list, "conn");
                     }
 
-                    if ($call->{ProcName} eq "SecretSetValue") {
-                        push(@args_list, "(const unsigned char *)args->$2.$2_val");
-                    } elsif ($call->{ProcName} eq "CPUBaseline") {
-                        push(@args_list, "(const char **)args->$2.$2_val");
-                    } else {
-                        push(@args_list, "args->$2.$2_val");
+                    push(@args_list, "args->$1.$1_val");
+                    push(@args_list, "args->$1.$1_len");
+                } elsif ($args_member =~ m/^(?:opaque|remote_nonnull_string) (\S+)<\S+>;(.*)$/) {
+                    if (! @args_list) {
+                        push(@args_list, "conn");
+                    }
+
+                    my $cast = "";
+                    my $arg_name = $1;
+                    my $annotation = $2;
+
+                    if ($annotation ne "") {
+                        if ($annotation =~ m/\s*\/\*\s*(.*)\s*\*\//) {
+                            $cast = $1;
+                        } else {
+                            die "malformed cast annotation for argument: $args_member";
+                        }
                     }
 
-                    push(@args_list, "args->$2.$2_len");
+                    push(@args_list, "${cast}args->$arg_name.${arg_name}_val");
+                    push(@args_list, "args->$arg_name.${arg_name}_len");
                 } elsif ($args_member =~ m/^(?:unsigned )?int (\S+)<\S+>;/) {
                     if (! @args_list) {
                         push(@args_list, "conn");
@@ -998,37 +1010,63 @@ elsif ($opt_k) {
                 } elsif ($args_member =~ m/^remote_string (\S+);/) {
                     push(@args_list, "const char *$1");
                     push(@setters_list, "args.$1 = $1 ? (char **)&$1 : NULL;");
-                } elsif ($args_member =~ m/^remote_nonnull_string (\S+)<(\S+)>;/) {
-                    push(@args_list, "const char **$1");
-                    push(@args_list, "unsigned int ${1}len");
-                    push(@setters_list, "args.$1.${1}_val = (char **)$1;");
-                    push(@setters_list, "args.$1.${1}_len = ${1}len;");
-                    push(@args_check_list, { name => "\"$1\"", arg => "${1}len", limit => $2 });
+                } elsif ($args_member =~ m/^remote_nonnull_string (\S+)<(\S+)>;(.*)$/) {
+                    my $type_name = "const char **";
+                    my $arg_name = $1;
+                    my $limit = $2;
+                    my $annotation = $3;
+
+                    if ($annotation ne "") {
+                        if ($annotation =~ m/\s*\/\*\s*\((.*)\)\s*\*\//) {
+                            $type_name = $1;
+                        } else {
+                            die "malformed cast annotation for argument: $args_member";
+                        }
+                    }
+
+                    push(@args_list, "$type_name$arg_name");
+                    push(@args_list, "unsigned int ${arg_name}len");
+                    push(@setters_list, "args.$arg_name.${arg_name}_val = (char **)$arg_name;");
+                    push(@setters_list, "args.$arg_name.${arg_name}_len = ${arg_name}len;");
+                    push(@args_check_list, { name => "\"$arg_name\"", arg => "${arg_name}len", limit => $2 });
                 } elsif ($args_member =~ m/^remote_nonnull_string (\S+);/) {
                     push(@args_list, "const char *$1");
                     push(@setters_list, "args.$1 = (char *)$1;");
-                } elsif ($args_member =~ m/^(remote_string|opaque) (\S+)<(\S+)>;/) {
-                    my $type_name = $1;
-                    my $arg_name = $2;
-                    my $limit = $3;
+                } elsif ($args_member =~ m/^opaque (\S+)<(\S+)>;(.*)$/) {
+                    my $type_name = "const char *";
+                    my $arg_name = $1;
+                    my $limit = $2;
+                    my $annotation = $3;
+
+                    if ($annotation ne "") {
+                        if ($annotation =~ m/\s*\/\*\s*\((.*)\)\s*\*\//) {
+                            $type_name = $1;
+                        } else {
+                            die "malformed cast annotation for argument: $args_member";
+                        }
+                    }
+
+                    push(@args_list, "$type_name$arg_name");
 
                     if ($call->{ProcName} eq "SecretSetValue") {
-                        push(@args_list, "const unsigned char *$arg_name");
+                        # SPECIAL: virSecretSetValue uses size_t instead of int
                         push(@args_list, "size_t ${arg_name}len");
-                    } elsif ($call->{ProcName} eq "DomainPinVcpu") {
-                        push(@args_list, "unsigned char *$arg_name");
-                        push(@args_list, "int ${arg_name}len");
-                    } elsif ($call->{ProcName} eq "DomainPinVcpuFlags") {
-                        push(@args_list, "unsigned char *$arg_name");
-                        push(@args_list, "int ${arg_name}len");
                     } else {
-                        push(@args_list, "const char *$arg_name");
                         push(@args_list, "int ${arg_name}len");
                     }
 
                     push(@setters_list, "args.$arg_name.${arg_name}_val = (char *)$arg_name;");
                     push(@setters_list, "args.$arg_name.${arg_name}_len = ${arg_name}len;");
                     push(@args_check_list, { name => "\"$arg_name\"", arg => "${arg_name}len", limit => $limit });
+                } elsif ($args_member =~ m/^remote_string (\S+)<(\S+)>;/) {
+                    my $arg_name = $1;
+                    my $limit = $2;
+
+                    push(@args_list, "const char *$arg_name");
+                    push(@args_list, "int ${arg_name}len");
+                    push(@setters_list, "args.$arg_name.${arg_name}_val = (char *)$arg_name;");
+                    push(@setters_list, "args.$arg_name.${arg_name}_len = ${arg_name}len;");
+                    push(@args_check_list, { name => "\"$arg_name\"", arg => "${arg_name}len", limit => $limit });
                 } elsif ($args_member =~ m/^((?:unsigned )?int) (\S+)<(\S+)>;/) {
                     my $type_name = $1;
                     my $arg_name = $2;
diff --git a/src/remote/remote_protocol.x b/src/remote/remote_protocol.x
index 0aa3dfb..a77fd81 100644
--- a/src/remote/remote_protocol.x
+++ b/src/remote/remote_protocol.x
@@ -357,7 +357,10 @@ struct remote_node_get_memory_stats {
  * If the 'remote_CALL_ret' maps to a struct in the public API then it is
  * also filled via call-by-reference and must be annotated with a
  * insert@<offset> comment to indicate the offset in the parameter list of
- * the function to be called. */
+ * the function to be called.
+ *
+ * Dynamic opaque and remote_nonnull_string arrays can be annotated with an
+ * optional typecast */
 
 struct remote_open_args {
     /* NB. "name" might be NULL although in practice you can't
@@ -890,13 +893,13 @@ struct remote_domain_get_vcpus_flags_ret {
 struct remote_domain_pin_vcpu_args {
     remote_nonnull_domain dom;
     unsigned int vcpu;
-    opaque cpumap<REMOTE_CPUMAP_MAX>;
+    opaque cpumap<REMOTE_CPUMAP_MAX>; /* (unsigned char *) */
 };
 
 struct remote_domain_pin_vcpu_flags_args {
     remote_nonnull_domain dom;
     unsigned int vcpu;
-    opaque cpumap<REMOTE_CPUMAP_MAX>;
+    opaque cpumap<REMOTE_CPUMAP_MAX>; /* (unsigned char *) */
     unsigned int flags;
 };
 
@@ -1701,7 +1704,7 @@ struct remote_secret_get_xml_desc_ret {
 
 struct remote_secret_set_value_args {
     remote_nonnull_secret secret;
-    opaque value<REMOTE_SECRET_VALUE_MAX>;
+    opaque value<REMOTE_SECRET_VALUE_MAX>; /* (const unsigned char *) */
     unsigned int flags;
 };
 
@@ -1819,7 +1822,7 @@ struct remote_cpu_compare_ret {
 
 
 struct remote_cpu_baseline_args {
-    remote_nonnull_string xmlCPUs<REMOTE_CPU_BASELINE_MAX>;
+    remote_nonnull_string xmlCPUs<REMOTE_CPU_BASELINE_MAX>; /* (const char **) */
     unsigned int flags;
 };
 
@@ -2182,7 +2185,7 @@ enum remote_procedure {
     REMOTE_PROC_DOMAIN_LOOKUP_BY_NAME = 23, /* autogen autogen */
     REMOTE_PROC_DOMAIN_LOOKUP_BY_UUID = 24, /* autogen autogen */
     REMOTE_PROC_NUM_OF_DEFINED_DOMAINS = 25, /* autogen autogen */
-    REMOTE_PROC_DOMAIN_PIN_VCPU = 26, /* skipgen autogen */
+    REMOTE_PROC_DOMAIN_PIN_VCPU = 26, /* autogen autogen */
     REMOTE_PROC_DOMAIN_REBOOT = 27, /* autogen autogen */
     REMOTE_PROC_DOMAIN_RESUME = 28, /* autogen autogen */
     REMOTE_PROC_DOMAIN_SET_AUTOSTART = 29, /* autogen autogen */
@@ -2401,7 +2404,7 @@ enum remote_procedure {
     REMOTE_PROC_INTERFACE_CHANGE_ROLLBACK = 222, /* autogen autogen */
     REMOTE_PROC_DOMAIN_GET_SCHEDULER_PARAMETERS_FLAGS = 223, /* skipgen autogen */
     REMOTE_PROC_DOMAIN_EVENT_CONTROL_ERROR = 224, /* skipgen skipgen */
-    REMOTE_PROC_DOMAIN_PIN_VCPU_FLAGS = 225, /* skipgen autogen */
+    REMOTE_PROC_DOMAIN_PIN_VCPU_FLAGS = 225, /* autogen autogen */
     REMOTE_PROC_DOMAIN_SEND_KEY = 226, /* autogen autogen */
     REMOTE_PROC_NODE_GET_CPU_STATS = 227, /* skipgen skipgen */
     REMOTE_PROC_NODE_GET_MEMORY_STATS = 228, /* skipgen skipgen */
-- 
1.7.0.4




More information about the libvir-list mailing list