summaryrefslogtreecommitdiffstats
path: root/src/corelib
diff options
context:
space:
mode:
authorEdward Welbourne <edward.welbourne@qt.io>2022-10-28 17:38:41 +0200
committerEdward Welbourne <edward.welbourne@qt.io>2023-01-19 18:46:35 +0100
commite7c7902e73b0d010f91fad9a4287b8315caa9a2a (patch)
tree43285c7e0d5a97bf7f4ac910fa1ec338bbba8809 /src/corelib
parent2d7b9b02e991aecb51a27467f577b07563fd0e15 (diff)
Let QLocaleData::numberToCLocale() know the type of number
Passing a NumberMode lets it exclude floating-specific details for integer parsing. For now this is only partially exploited, but later work shall make more use of it. Fixes: QTBUG-81756 Change-Id: If11d3a5a122d0714f645e58a51ee0d0c47ebe61d Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
Diffstat (limited to 'src/corelib')
-rw-r--r--src/corelib/text/qlocale.cpp30
-rw-r--r--src/corelib/text/qlocale_p.h2
2 files changed, 20 insertions, 12 deletions
diff --git a/src/corelib/text/qlocale.cpp b/src/corelib/text/qlocale.cpp
index 250f7a1a87..039bd43429 100644
--- a/src/corelib/text/qlocale.cpp
+++ b/src/corelib/text/qlocale.cpp
@@ -3873,9 +3873,16 @@ QString QLocaleData::applyIntegerFormatting(QString &&numStr, bool negative, int
}
/*
- Converts a number in locale to its representation in the C locale.
- Only has to guarantee that a string that is a correct representation of
- a number will be converted.
+ Converts a number in locale representation to the C locale equivalent.
+
+ Only has to guarantee that a string that is a correct representation of a
+ number will be converted. Checks signs, separators and digits appear in all
+ the places they should, and nowhere else.
+
+ Returns true precisely if the number appears to be well-formed, modulo
+ things a parser for C Locale strings (without digit-grouping separators;
+ they're stripped) will catch. When it returns true, it records (and
+ '\0'-terminates) the C locale representation in *result.
Note: only QString integer-parsing methods have a base parameter (hence need
to cope with letters as possible digits); but these are now all routed via
@@ -3884,7 +3891,7 @@ QString QLocaleData::applyIntegerFormatting(QString &&numStr, bool negative, int
other than 0 through 9.
*/
bool QLocaleData::numberToCLocale(QStringView s, QLocale::NumberOptions number_options,
- CharBuff *result) const
+ NumberMode mode, CharBuff *result) const
{
s = s.trimmed();
if (s.size() < 1)
@@ -3909,9 +3916,9 @@ bool QLocaleData::numberToCLocale(QStringView s, QLocale::NumberOptions number_o
char out = numericToCLocale(in);
if (out == 0) {
- // Allow ASCII letters of inf, nan:
- if (in.size() != 1)
+ if (mode == IntegerMode || in.size() != 1)
return false;
+ // Allow ASCII letters of inf, nan:
char16_t ch = in.front().unicode();
if (ch > 'n')
return false;
@@ -3923,7 +3930,7 @@ bool QLocaleData::numberToCLocale(QStringView s, QLocale::NumberOptions number_o
if (decpt_idx != -1 || exponent_idx != -1)
return false;
decpt_idx = idx;
- } else if (out == 'e') {
+ } else if (mode == DoubleScientificMode && out == 'e') {
exponent_idx = idx;
}
@@ -3966,7 +3973,8 @@ bool QLocaleData::numberToCLocale(QStringView s, QLocale::NumberOptions number_o
last_separator_idx = idx;
digitsInGroup = 0;
- } else if ((out == '.' || idx == exponent_idx) && last_separator_idx != -1) {
+ } else if (mode != IntegerMode && (out == '.' || idx == exponent_idx)
+ && last_separator_idx != -1) {
// Were there enough digits since the last group separator?
if (digitsInGroup != m_grouping_least)
return false;
@@ -4094,7 +4102,7 @@ double QLocaleData::stringToDouble(QStringView str, bool *ok,
QLocale::NumberOptions number_options) const
{
CharBuff buff;
- if (!numberToCLocale(str, number_options, &buff)) {
+ if (!numberToCLocale(str, number_options, DoubleScientificMode, &buff)) {
if (ok != nullptr)
*ok = false;
return 0.0;
@@ -4109,7 +4117,7 @@ qlonglong QLocaleData::stringToLongLong(QStringView str, int base, bool *ok,
QLocale::NumberOptions number_options) const
{
CharBuff buff;
- if (!numberToCLocale(str, number_options, &buff)) {
+ if (!numberToCLocale(str, number_options, IntegerMode, &buff)) {
if (ok != nullptr)
*ok = false;
return 0;
@@ -4122,7 +4130,7 @@ qulonglong QLocaleData::stringToUnsLongLong(QStringView str, int base, bool *ok,
QLocale::NumberOptions number_options) const
{
CharBuff buff;
- if (!numberToCLocale(str, number_options, &buff)) {
+ if (!numberToCLocale(str, number_options, IntegerMode, &buff)) {
if (ok != nullptr)
*ok = false;
return 0;
diff --git a/src/corelib/text/qlocale_p.h b/src/corelib/text/qlocale_p.h
index bd7f2be990..831bfe9eda 100644
--- a/src/corelib/text/qlocale_p.h
+++ b/src/corelib/text/qlocale_p.h
@@ -252,7 +252,7 @@ public:
[[nodiscard]] static quint64 bytearrayToUnsLongLong(QByteArrayView num, int base, bool *ok);
[[nodiscard]] bool numberToCLocale(QStringView s, QLocale::NumberOptions number_options,
- CharBuff *result) const;
+ NumberMode mode, CharBuff *result) const;
[[nodiscard]] inline char numericToCLocale(QStringView in) const;
// this function is used in QIntValidator (QtGui)