#include "qapi/clone-visitor.h"
#include "qapi/visitor-impl.h"
#include "qapi/error.h"
+#include "qapi/qmp/qnull.h"
struct QapiCloneVisitor {
Visitor visitor;
return container_of(v, QapiCloneVisitor, visitor);
}
-static void qapi_clone_start_struct(Visitor *v, const char *name, void **obj,
+static bool qapi_clone_start_struct(Visitor *v, const char *name, void **obj,
size_t size, Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
/* Only possible when visiting an alternate's object
* branch. Nothing further to do here, since the earlier
* visit_start_alternate() already copied memory. */
- return;
+ return true;
}
*obj = g_memdup(*obj, size);
qcv->depth++;
+ return true;
}
static void qapi_clone_end(Visitor *v, void **obj)
}
}
-static void qapi_clone_start_list(Visitor *v, const char *name,
+static bool qapi_clone_start_list(Visitor *v, const char *name,
GenericList **listp, size_t size,
Error **errp)
{
- qapi_clone_start_struct(v, name, (void **)listp, size, errp);
+ return qapi_clone_start_struct(v, name, (void **)listp, size, errp);
}
static GenericList *qapi_clone_next_list(Visitor *v, GenericList *tail,
return tail->next;
}
-static void qapi_clone_start_alternate(Visitor *v, const char *name,
+static bool qapi_clone_start_alternate(Visitor *v, const char *name,
GenericAlternate **obj, size_t size,
- bool promote_int, Error **errp)
+ Error **errp)
{
- qapi_clone_start_struct(v, name, (void **)obj, size, errp);
+ return qapi_clone_start_struct(v, name, (void **)obj, size, errp);
}
-static void qapi_clone_type_int64(Visitor *v, const char *name, int64_t *obj,
- Error **errp)
+static bool qapi_clone_type_int64(Visitor *v, const char *name, int64_t *obj,
+ Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
assert(qcv->depth);
/* Value was already cloned by g_memdup() */
+ return true;
}
-static void qapi_clone_type_uint64(Visitor *v, const char *name,
- uint64_t *obj, Error **errp)
+static bool qapi_clone_type_uint64(Visitor *v, const char *name,
+ uint64_t *obj, Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
assert(qcv->depth);
/* Value was already cloned by g_memdup() */
+ return true;
}
-static void qapi_clone_type_bool(Visitor *v, const char *name, bool *obj,
- Error **errp)
+static bool qapi_clone_type_bool(Visitor *v, const char *name, bool *obj,
+ Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
assert(qcv->depth);
/* Value was already cloned by g_memdup() */
+ return true;
}
-static void qapi_clone_type_str(Visitor *v, const char *name, char **obj,
- Error **errp)
+static bool qapi_clone_type_str(Visitor *v, const char *name, char **obj,
+ Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
* string is intended.
*/
*obj = g_strdup(*obj ?: "");
+ return true;
}
-static void qapi_clone_type_number(Visitor *v, const char *name, double *obj,
- Error **errp)
+static bool qapi_clone_type_number(Visitor *v, const char *name, double *obj,
+ Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
assert(qcv->depth);
/* Value was already cloned by g_memdup() */
+ return true;
}
-static void qapi_clone_type_null(Visitor *v, const char *name, Error **errp)
+static bool qapi_clone_type_null(Visitor *v, const char *name, QNull **obj,
+ Error **errp)
{
QapiCloneVisitor *qcv = to_qcv(v);
assert(qcv->depth);
- /* Nothing to do */
+ *obj = qnull();
+ return true;
}
static void qapi_clone_free(Visitor *v)
return &v->visitor;
}
-void *qapi_clone(const void *src, void (*visit_type)(Visitor *, const char *,
+void *qapi_clone(const void *src, bool (*visit_type)(Visitor *, const char *,
void **, Error **))
{
Visitor *v;
visit_free(v);
return dst;
}
+
+void qapi_clone_members(void *dst, const void *src, size_t sz,
+ bool (*visit_type_members)(Visitor *, void *,
+ Error **))
+{
+ Visitor *v;
+
+ v = qapi_clone_visitor_new();
+ memcpy(dst, src, sz);
+ to_qcv(v)->depth++;
+ visit_type_members(v, dst, &error_abort);
+ visit_free(v);
+}