On Wed, Sep 02, 2026 at 07:15:38PM -0300, Fabiano Rosas wrote:
> There are a couple of situations where all fields of a
> MigrationParameters object need to be marked as present: when cloning
> an entire object and when creating the transient object in
> qmp_query_migrate(). The query-migrate-parameters QMP command contract
> requires that all parameters, except block-bitmap-mapping, are present
> in the output.
> 
> Validate that a given object has all has_* fields set to true.
> 
> Signed-off-by: Fabiano Rosas <[email protected]>
> ---
>  migration/options.c | 54 +++++++++++++++++++++++++++++++++++++++++++++
>  1 file changed, 54 insertions(+)
> 
> diff --git a/migration/options.c b/migration/options.c
> index bd7be8f9832..5d17acdd881 100644
> --- a/migration/options.c
> +++ b/migration/options.c
> @@ -12,6 +12,7 @@
>   */
>  
>  #include "qemu/osdep.h"
> +#include "qemu/cutils.h"
>  #include "qemu/error-report.h"
>  #include "qemu/units.h"
>  #include "exec/target_page.h"
> @@ -23,8 +24,10 @@
>  #include "qapi/qmp/qerror.h"
>  #include "qapi/qobject-input-visitor.h"
>  #include "qapi/qobject-output-visitor.h"
> +#include "qobject/qbool.h"
>  #include "qobject/qdict.h"
>  #include "qobject/qnull.h"
> +#include "qobject/qstring.h"
>  #include "system/runstate.h"
>  #include "migration/colo.h"
>  #include "migration/cpr.h"
> @@ -1149,12 +1152,63 @@ static void 
> migrate_mark_all_params_present(MigrationParameters *p)
>      }
>  }
>  
> +static bool assert_all_params_present(MigrationParameters *params, Error 
> **errp)
> +{
> +    g_autoptr(QDict) d = migrate_params_to_dict(params, errp);
> +    const QDictEntry *e = NULL;
> +    int i = 0;
> +
> +    if (!d) {
> +        return false;
> +    }
> +
> +    for (e = qdict_first(d); e; e = qdict_next(d, e), i++) {
> +        const char *key = qdict_entry_key(e);
> +        const char *p;
> +
> +        if (strstart(key, "tls-", &p)) {
> +            QString *s = qobject_to(QString, qdict_entry_value(e));
> +
> +            if (!s) {
> +                break;
> +            }
> +        } else if (strstart(key, "has-", &p)) {

Does the qdict contain any has- field?  

visit_type_MigrationParameters_members:

    if (visit_optional(v, "announce-initial", &obj->has_announce_initial)) {
        if (!visit_type_size(v, "announce-initial", &obj->announce_initial, 
errp)) {
            return false;
        }
    }
    ...

It seems the has_* fields are only used to identify existance of objects,
not converted.

> +            if (qdict_haskey(d, p)) {
> +                QBool *b = qobject_to(QBool, qdict_entry_value(e));
> +
> +                if (!b || !qbool_get_bool(b)) {
> +                    break;
> +                }
> +            }
> +        }
> +    }
> +
> +    if (i && !e) {
> +        return true;
> +    }
> +
> +    /*
> +     * Should never happen, but avoid asserting becase this is
> +     * reachable from QMP.

IIUC as long as this fact shouldn't be changed by any possible user input,
we could still assert.  But I understand you want to be careful, maybe
either (1) directly assert, or (2) change the function name,
s/assert/check/?  I vote (1).

Said that, if the qdict trick didn't work it beats the whole patch.. so
IMHO we can also leave this sanity check for later too.  Your call.

> +     */
> +    error_setg(errp, "Missing parameter. Query output will be incomplete.");
> +    return false;
> +}
> +
>  MigrationParameters *qmp_query_migrate_parameters(Error **errp)
>  {
>      MigrationState *s = migrate_get_current();
>      MigrationParameters *params = QAPI_CLONE(MigrationParameters,
>                                               &s->parameters);
>  
> +    /*
> +     * Validate all parameters have their has_* field set to true as
> +     * consequence of the initial migrate_mark_all_params_present().
> +     */
> +    if (!assert_all_params_present(params, errp)) {
> +        return NULL;
> +    }
> +
>      /*
>       * The block-bitmap-mapping breaks the expected API of
>       * query-migrate-parameters of having all members present. To keep
> -- 
> 2.53.0
> 

-- 
Peter Xu


Reply via email to