mirror of
https://github.com/Motorhead1991/qemu.git
synced 2025-07-27 04:13:53 -06:00
qapi: merge QInt and QFloat in QNum
We would like to use a same QObject type to represent numbers, whether they are int, uint, or floats. Getters will allow some compatibility between the various types if the number fits other representations. Add a few more tests while at it. Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com> Message-Id: <20170607163635.17635-7-marcandre.lureau@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> [parse_stats_intervals() simplified a bit, comment in test_visitor_in_int_overflow() tidied up, suppress bogus warnings] Signed-off-by: Markus Armbruster <armbru@redhat.com>
This commit is contained in:
parent
58634047b7
commit
01b2ffcedd
65 changed files with 630 additions and 664 deletions
|
@ -466,16 +466,16 @@ static QObject *parse_escape(JSONParserContext *ctxt, va_list *ap)
|
|||
} else if (!strcmp(token->str, "%i")) {
|
||||
return QOBJECT(qbool_from_bool(va_arg(*ap, int)));
|
||||
} else if (!strcmp(token->str, "%d")) {
|
||||
return QOBJECT(qint_from_int(va_arg(*ap, int)));
|
||||
return QOBJECT(qnum_from_int(va_arg(*ap, int)));
|
||||
} else if (!strcmp(token->str, "%ld")) {
|
||||
return QOBJECT(qint_from_int(va_arg(*ap, long)));
|
||||
return QOBJECT(qnum_from_int(va_arg(*ap, long)));
|
||||
} else if (!strcmp(token->str, "%lld") ||
|
||||
!strcmp(token->str, "%I64d")) {
|
||||
return QOBJECT(qint_from_int(va_arg(*ap, long long)));
|
||||
return QOBJECT(qnum_from_int(va_arg(*ap, long long)));
|
||||
} else if (!strcmp(token->str, "%s")) {
|
||||
return QOBJECT(qstring_from_str(va_arg(*ap, const char *)));
|
||||
} else if (!strcmp(token->str, "%f")) {
|
||||
return QOBJECT(qfloat_from_double(va_arg(*ap, double)));
|
||||
return QOBJECT(qnum_from_double(va_arg(*ap, double)));
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
@ -491,24 +491,22 @@ static QObject *parse_literal(JSONParserContext *ctxt)
|
|||
case JSON_STRING:
|
||||
return QOBJECT(qstring_from_escaped_str(ctxt, token));
|
||||
case JSON_INTEGER: {
|
||||
/* A possibility exists that this is a whole-valued float where the
|
||||
* fractional part was left out due to being 0 (.0). It's not a big
|
||||
* deal to treat these as ints in the parser, so long as users of the
|
||||
* resulting QObject know to expect a QInt in place of a QFloat in
|
||||
* cases like these.
|
||||
/*
|
||||
* Represent JSON_INTEGER as QNUM_I64 if possible, else as
|
||||
* QNUM_DOUBLE. Note that strtoll() fails with ERANGE when
|
||||
* it's not possible.
|
||||
*
|
||||
* However, in some cases these values will overflow/underflow a
|
||||
* QInt/int64 container, thus we should assume these are to be handled
|
||||
* as QFloats/doubles rather than silently changing their values.
|
||||
*
|
||||
* strtoll() indicates these instances by setting errno to ERANGE
|
||||
* qnum_get_int() will then work for any signed 64-bit
|
||||
* JSON_INTEGER, and qnum_get_double() both for any
|
||||
* JSON_INTEGER and any JSON_FLOAT (with precision loss for
|
||||
* integers beyond 53 bits)
|
||||
*/
|
||||
int64_t value;
|
||||
|
||||
errno = 0; /* strtoll doesn't set errno on success */
|
||||
value = strtoll(token->str, NULL, 10);
|
||||
if (errno != ERANGE) {
|
||||
return QOBJECT(qint_from_int(value));
|
||||
return QOBJECT(qnum_from_int(value));
|
||||
}
|
||||
/* fall through to JSON_FLOAT */
|
||||
}
|
||||
|
@ -516,7 +514,7 @@ static QObject *parse_literal(JSONParserContext *ctxt)
|
|||
/* FIXME dependent on locale; a pervasive issue in QEMU */
|
||||
/* FIXME our lexer matches RFC 7159 in forbidding Inf or NaN,
|
||||
* but those might be useful extensions beyond JSON */
|
||||
return QOBJECT(qfloat_from_double(strtod(token->str, NULL)));
|
||||
return QOBJECT(qnum_from_double(strtod(token->str, NULL)));
|
||||
default:
|
||||
abort();
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue