static void make_nonnull_nwfilter(remote_nonnull_nwfilter *net_dst, virNWFilterPtr nwfilter_src);
static void make_nonnull_domain_snapshot(remote_nonnull_domain_snapshot *snapshot_dst, virDomainSnapshotPtr snapshot_src);
-static virTypedParameterPtr
-remoteDeserializeTypedParameters(remote_typed_param *args_params_val,
- u_int args_params_len,
- int limit,
- int *nparams);
-
static int
remoteSerializeTypedParameters(virTypedParameterPtr params,
int nparams,
return rv;
}
-/* Helper to deserialize typed parameters. */
-static virTypedParameterPtr
-remoteDeserializeTypedParameters(remote_typed_param *args_params_val,
- u_int args_params_len,
- int limit,
- int *nparams)
-{
- size_t i = 0;
- int rv = -1;
- virTypedParameterPtr params = NULL;
-
- /* Check the length of the returned list carefully. */
- if (limit && args_params_len > limit) {
- virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("nparams too large"));
- goto cleanup;
- }
- if (VIR_ALLOC_N(params, args_params_len) < 0)
- goto cleanup;
-
- *nparams = args_params_len;
-
- /* Deserialise the result. */
- for (i = 0; i < args_params_len; ++i) {
- if (virStrcpyStatic(params[i].field,
- args_params_val[i].field) == NULL) {
- virReportError(VIR_ERR_INTERNAL_ERROR,
- _("Parameter %s too big for destination"),
- args_params_val[i].field);
- goto cleanup;
- }
- params[i].type = args_params_val[i].value.type;
- switch (params[i].type) {
- case VIR_TYPED_PARAM_INT:
- params[i].value.i =
- args_params_val[i].value.remote_typed_param_value_u.i;
- break;
- case VIR_TYPED_PARAM_UINT:
- params[i].value.ui =
- args_params_val[i].value.remote_typed_param_value_u.ui;
- break;
- case VIR_TYPED_PARAM_LLONG:
- params[i].value.l =
- args_params_val[i].value.remote_typed_param_value_u.l;
- break;
- case VIR_TYPED_PARAM_ULLONG:
- params[i].value.ul =
- args_params_val[i].value.remote_typed_param_value_u.ul;
- break;
- case VIR_TYPED_PARAM_DOUBLE:
- params[i].value.d =
- args_params_val[i].value.remote_typed_param_value_u.d;
- break;
- case VIR_TYPED_PARAM_BOOLEAN:
- params[i].value.b =
- args_params_val[i].value.remote_typed_param_value_u.b;
- break;
- case VIR_TYPED_PARAM_STRING:
- if (VIR_STRDUP(params[i].value.s,
- args_params_val[i].value.remote_typed_param_value_u.s) < 0)
- goto cleanup;
- break;
- default:
- virReportError(VIR_ERR_INTERNAL_ERROR, _("unknown parameter type: %d"),
- params[i].type);
- goto cleanup;
- }
- }
-
- rv = 0;
-
- cleanup:
- if (rv < 0) {
- virTypedParamsFree(params, i);
- params = NULL;
- }
- return params;
-}
-
static int
remoteDispatchDomainGetSchedulerParameters(virNetServerPtr server ATTRIBUTE_UNUSED,
virNetServerClientPtr client ATTRIBUTE_UNUSED,
if (!(dom = get_nonnull_domain(priv->conn, args->dom)))
goto cleanup;
- if (!(params = remoteDeserializeTypedParameters(args->params.params_val,
- args->params.params_len,
- 0, &nparams)))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->params.params_val,
+ args->params.params_len,
+ 0, ¶ms, &nparams) < 0)
goto cleanup;
if (!(xml = virDomainMigrateBegin3Params(dom, params, nparams,
goto cleanup;
}
- if (!(params = remoteDeserializeTypedParameters(args->params.params_val,
- args->params.params_len,
- 0, &nparams)))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->params.params_val,
+ args->params.params_len,
+ 0, ¶ms, &nparams) < 0)
goto cleanup;
/* Wacky world of XDR ... */
goto cleanup;
}
- if (!(params = remoteDeserializeTypedParameters(args->params.params_val,
- args->params.params_len,
- 0, &nparams)))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->params.params_val,
+ args->params.params_len,
+ 0, ¶ms, &nparams) < 0)
goto cleanup;
if (!(st = virStreamNew(priv->conn, VIR_STREAM_NONBLOCK)) ||
if (!(dom = get_nonnull_domain(priv->conn, args->dom)))
goto cleanup;
- if (!(params = remoteDeserializeTypedParameters(args->params.params_val,
- args->params.params_len,
- 0, &nparams)))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->params.params_val,
+ args->params.params_len,
+ 0, ¶ms, &nparams) < 0)
goto cleanup;
dconnuri = args->dconnuri == NULL ? NULL : *args->dconnuri;
goto cleanup;
}
- if (!(params = remoteDeserializeTypedParameters(args->params.params_val,
- args->params.params_len,
- 0, &nparams)))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->params.params_val,
+ args->params.params_len,
+ 0, ¶ms, &nparams) < 0)
goto cleanup;
dom = virDomainMigrateFinish3Params(priv->conn, params, nparams,
if (!(dom = get_nonnull_domain(priv->conn, args->dom)))
goto cleanup;
- if (!(params = remoteDeserializeTypedParameters(args->params.params_val,
- args->params.params_len,
- 0, &nparams)))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->params.params_val,
+ args->params.params_len,
+ 0, ¶ms, &nparams) < 0)
goto cleanup;
if (virDomainMigrateConfirm3Params(dom, params, nparams,
virTypedParameterTypeToString;
virTypedParamsCheck;
virTypedParamsCopy;
+virTypedParamsDeserialize;
virTypedParamsFilter;
virTypedParamsGetStringList;
virTypedParamsReplaceString;
# define HYPER_TO_ULONG(_to, _from) (_to) = (_from)
#endif
-#define remoteDeserializeTypedParameters(ret_params_val, ret_params_len, \
- limit, params, nparams) \
- deserializeTypedParameters(__FUNCTION__, ret_params_val, ret_params_len, \
- limit, params, nparams)
-
static bool inside_daemon;
struct private_data {
return rv;
}
-/* Helper to deserialize typed parameters. */
-static int
-deserializeTypedParameters(const char *funcname,
- remote_typed_param *ret_params_val,
- u_int ret_params_len,
- int limit,
- virTypedParameterPtr *params,
- int *nparams)
-{
- size_t i = 0;
- int rv = -1;
- bool userAllocated = *params != NULL;
-
- if (ret_params_len > limit) {
- virReportError(VIR_ERR_RPC,
- _("%s: too many parameters '%u' for limit '%d'"),
- funcname, ret_params_len, limit);
- goto cleanup;
- }
-
- if (userAllocated) {
- /* Check the length of the returned list carefully. */
- if (ret_params_len > *nparams) {
- virReportError(VIR_ERR_RPC,
- _("%s: too many parameters '%u' for nparams '%d'"),
- funcname, ret_params_len, *nparams);
- goto cleanup;
- }
- } else {
- if (VIR_ALLOC_N(*params, ret_params_len) < 0)
- goto cleanup;
- }
- *nparams = ret_params_len;
-
- /* Deserialise the result. */
- for (i = 0; i < ret_params_len; ++i) {
- virTypedParameterPtr param = *params + i;
- remote_typed_param *ret_param = ret_params_val + i;
-
- if (virStrcpyStatic(param->field,
- ret_param->field) == NULL) {
- virReportError(VIR_ERR_INTERNAL_ERROR,
- _("%s: parameter %s too big for destination"),
- funcname, ret_param->field);
- goto cleanup;
- }
-
- param->type = ret_param->value.type;
- switch (param->type) {
- case VIR_TYPED_PARAM_INT:
- param->value.i =
- ret_param->value.remote_typed_param_value_u.i;
- break;
- case VIR_TYPED_PARAM_UINT:
- param->value.ui =
- ret_param->value.remote_typed_param_value_u.ui;
- break;
- case VIR_TYPED_PARAM_LLONG:
- param->value.l =
- ret_param->value.remote_typed_param_value_u.l;
- break;
- case VIR_TYPED_PARAM_ULLONG:
- param->value.ul =
- ret_param->value.remote_typed_param_value_u.ul;
- break;
- case VIR_TYPED_PARAM_DOUBLE:
- param->value.d =
- ret_param->value.remote_typed_param_value_u.d;
- break;
- case VIR_TYPED_PARAM_BOOLEAN:
- param->value.b =
- ret_param->value.remote_typed_param_value_u.b;
- break;
- case VIR_TYPED_PARAM_STRING:
- if (VIR_STRDUP(param->value.s,
- ret_param->value.remote_typed_param_value_u.s) < 0)
- goto cleanup;
- break;
- default:
- virReportError(VIR_ERR_RPC, _("%s: unknown parameter type: %d"),
- funcname, param->type);
- goto cleanup;
- }
- }
-
- rv = 0;
-
- cleanup:
- if (rv < 0) {
- if (userAllocated) {
- virTypedParamsClear(*params, i);
- } else {
- virTypedParamsFree(*params, i);
- *params = NULL;
- }
- }
- return rv;
-}
-
static int
remoteDeserializeDomainDiskErrors(remote_domain_disk_error *ret_errors_val,
u_int ret_errors_len,
*nparams = ret.params.params_len;
- /* Deserialise the result. */
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_MEMORY_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ /* Deserialize the result. */
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_MEMORY_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
goto cleanup;
}
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_MEMORY_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_MEMORY_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
goto cleanup;
}
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_NUMA_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_NUMA_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
goto cleanup;
}
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_BLKIO_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_BLKIO_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
goto cleanup;
}
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_MEMORY_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_MEMORY_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
virTypedParameterPtr cpu_params = ¶ms[cpu * nparams];
remote_typed_param *stride = &ret.params.params_val[cpu * ret.nparams];
- if (remoteDeserializeTypedParameters(stride, ret.nparams,
- REMOTE_NODE_CPU_STATS_MAX,
- &cpu_params, &tmp) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) stride,
+ ret.nparams,
+ REMOTE_NODE_CPU_STATS_MAX,
+ &cpu_params, &tmp) < 0)
goto cleanup;
}
int nparams = 0;
virObjectEventPtr event = NULL;
- if (remoteDeserializeTypedParameters(msg->params.params_val,
- msg->params.params_len,
- REMOTE_DOMAIN_EVENT_TUNABLE_MAX,
- ¶ms, &nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) msg->params.params_val,
+ msg->params.params_len,
+ REMOTE_DOMAIN_EVENT_TUNABLE_MAX,
+ ¶ms, &nparams) < 0)
return;
dom = get_nonnull_domain(conn, msg->dom);
goto cleanup;
}
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_INTERFACE_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_INTERFACE_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
goto cleanup;
}
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_NODE_MEMORY_PARAMETERS_MAX,
- ¶ms,
- nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_NODE_MEMORY_PARAMETERS_MAX,
+ ¶ms,
+ nparams) < 0)
goto cleanup;
rv = 0;
*type = ret.type;
- if (remoteDeserializeTypedParameters(ret.params.params_val,
- ret.params.params_len,
- REMOTE_DOMAIN_JOB_STATS_MAX,
- params, nparams) < 0)
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.params.params_val,
+ ret.params.params_len,
+ REMOTE_DOMAIN_JOB_STATS_MAX,
+ params, nparams) < 0)
goto cleanup;
rv = 0;
if (!(elem->dom = get_nonnull_domain(conn, rec->dom)))
goto cleanup;
- if (remoteDeserializeTypedParameters(rec->params.params_val,
- rec->params.params_len,
- REMOTE_CONNECT_GET_ALL_DOMAIN_STATS_MAX,
- &elem->params,
- &elem->nparams))
+ if (virTypedParamsDeserialize((virTypedParameterRemotePtr) rec->params.params_val,
+ rec->params.params_len,
+ REMOTE_CONNECT_GET_ALL_DOMAIN_STATS_MAX,
+ &elem->params,
+ &elem->nparams))
goto cleanup;
tmpret[i] = elem;
}
push(@args_list, "$1");
push(@args_list, "n$1");
- push(@getters_list, " if (($1 = remoteDeserializeTypedParameters(args->$1.$1_val,\n" .
- " args->$1.$1_len,\n" .
- " $2,\n" .
- " &n$1)) == NULL)\n" .
+ push(@getters_list, " if (virTypedParamsDeserialize((virTypedParameterRemotePtr) args->$1.$1_val,\n" .
+ " args->$1.$1_len,\n" .
+ " $2,\n" .
+ " &$1,\n" .
+ " &n$1) < 0)\n" .
" goto cleanup;\n");
push(@free_list, " virTypedParamsFree($1, n$1);");
} elsif ($args_member =~ m/<\S+>;/ or $args_member =~ m/\[\S+\];/) {
}
} elsif ($ret_member =~ m/^remote_typed_param (\S+)<(\S+)>;\s*\/\*\s*insert@(\d+)\s*\*\//) {
splice(@args_list, int($3), 0, ("virTypedParameterPtr $1"));
- push(@ret_list2, "if (remoteDeserializeTypedParameters(ret.$1.$1_val,\n" .
- " ret.$1.$1_len,\n" .
- " $2,\n" .
- " &$1,\n" .
- " n$1) < 0)\n" .
+ push(@ret_list2, "if (virTypedParamsDeserialize((virTypedParameterRemotePtr) ret.$1.$1_val,\n" .
+ " ret.$1.$1_len,\n" .
+ " $2,\n" .
+ " &$1,\n" .
+ " n$1) < 0)\n" .
" goto cleanup;\n");
$single_ret_cleanup = 1;
} elsif ($ret_member =~ m/^remote_typed_param (\S+)<\S+>;/) {
virTypedParamsClear(params, nparams);
VIR_FREE(params);
}
+
+
+/**
+ * virTypedParamsDeserialize:
+ * @remote_params: protocol data to be deserialized (obtained from remote side)
+ * @remote_params_len: number of parameters returned in @remote_params
+ * @limit: user specified maximum limit to @remote_params_len
+ * @params: pointer which will hold the deserialized @remote_params data
+ * @nparams: number of entries in @params
+ *
+ * This function will attempt to deserialize protocol-encoded data obtained
+ * from remote side. Two modes of operation are supported, depending on the
+ * caller's design:
+ * 1) Older APIs do not rely on deserializer allocating memory for @params,
+ * thus calling the deserializer twice, once to find out the actual number of
+ * parameters for @params to hold, followed by an allocation of @params and
+ * a second call to the deserializer to actually retrieve the data.
+ * 2) Newer APIs rely completely on the deserializer to allocate the right
+ * ammount of memory for @params to hold all the data obtained in
+ * @remote_params.
+ *
+ * If used with model 1, two checks are performed, first one comparing the user
+ * specified limit to the actual size of remote data and the second one
+ * verifying the user allocated amount of memory is indeed capable of holding
+ * remote data @remote_params.
+ * With model 2, only the first check against @limit is performed.
+ *
+ * Returns 0 on success or -1 in case of an error.
+ */
+int
+virTypedParamsDeserialize(virTypedParameterRemotePtr remote_params,
+ unsigned int remote_params_len,
+ int limit,
+ virTypedParameterPtr *params,
+ int *nparams)
+{
+ size_t i = 0;
+ int rv = -1;
+ bool userAllocated = *params != NULL;
+
+ if (limit && remote_params_len > limit) {
+ virReportError(VIR_ERR_RPC,
+ _("too many parameters '%u' for limit '%d'"),
+ remote_params_len, limit);
+ goto cleanup;
+ }
+
+ if (userAllocated) {
+ /* Check the length of the returned list carefully. */
+ if (remote_params_len > *nparams) {
+ virReportError(VIR_ERR_RPC,
+ _("too many parameters '%u' for nparams '%d'"),
+ remote_params_len, *nparams);
+ goto cleanup;
+ }
+ } else {
+ if (VIR_ALLOC_N(*params, remote_params_len) < 0)
+ goto cleanup;
+ }
+ *nparams = remote_params_len;
+
+ /* Deserialize the result. */
+ for (i = 0; i < remote_params_len; ++i) {
+ virTypedParameterPtr param = *params + i;
+ virTypedParameterRemotePtr remote_param = remote_params + i;
+
+ if (virStrcpyStatic(param->field,
+ remote_param->field) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("parameter %s too big for destination"),
+ remote_param->field);
+ goto cleanup;
+ }
+
+ param->type = remote_param->value.type;
+ switch (param->type) {
+ case VIR_TYPED_PARAM_INT:
+ param->value.i =
+ remote_param->value.remote_typed_param_value.i;
+ break;
+ case VIR_TYPED_PARAM_UINT:
+ param->value.ui =
+ remote_param->value.remote_typed_param_value.ui;
+ break;
+ case VIR_TYPED_PARAM_LLONG:
+ param->value.l =
+ remote_param->value.remote_typed_param_value.l;
+ break;
+ case VIR_TYPED_PARAM_ULLONG:
+ param->value.ul =
+ remote_param->value.remote_typed_param_value.ul;
+ break;
+ case VIR_TYPED_PARAM_DOUBLE:
+ param->value.d =
+ remote_param->value.remote_typed_param_value.d;
+ break;
+ case VIR_TYPED_PARAM_BOOLEAN:
+ param->value.b =
+ remote_param->value.remote_typed_param_value.b;
+ break;
+ case VIR_TYPED_PARAM_STRING:
+ if (VIR_STRDUP(param->value.s,
+ remote_param->value.remote_typed_param_value.s) < 0)
+ goto cleanup;
+ break;
+ default:
+ virReportError(VIR_ERR_RPC, _("unknown parameter type: %d"),
+ param->type);
+ goto cleanup;
+ }
+ }
+
+ rv = 0;
+
+ cleanup:
+ if (rv < 0) {
+ if (userAllocated) {
+ virTypedParamsClear(*params, i);
+ } else {
+ virTypedParamsFree(*params, i);
+ *params = NULL;
+ }
+ }
+ return rv;
+}
char *virTypedParameterToString(virTypedParameterPtr param);
+int virTypedParamsDeserialize(virTypedParameterRemotePtr remote_params,
+ unsigned int remote_params_len,
+ int limit,
+ virTypedParameterPtr *params,
+ int *nparams);
+
VIR_ENUM_DECL(virTypedParameter)
# define VIR_TYPED_PARAMS_DEBUG(params, nparams) \