diff --git a/arcanist/linter/LocaleDependenceLinter.php b/arcanist/linter/LocaleDependenceLinter.php --- a/arcanist/linter/LocaleDependenceLinter.php +++ b/arcanist/linter/LocaleDependenceLinter.php @@ -4,6 +4,38 @@ * Check for locale dependent functions. * Unnecessary locale dependence can cause bugs that are very tricky to isolate * and fix. + * + * Be aware that bitcoind and bitcoin-qt differ in terms of localization: Qt + * opts in to POSIX localization by running setlocale(LC_ALL, "") on startup, + * whereas no such call is made in bitcoind. + * + * Qt runs setlocale(LC_ALL, "") on initialization. This installs the locale + * specified by the user's LC_ALL (or LC_*) environment variable as the new + * C locale. + * + * In contrast, bitcoind does not opt in to localization -- no call to + * setlocale(LC_ALL, "") is made and the environment variables LC_* are + * thus ignored. + * + * This results in situations where bitcoind is guaranteed to be running + * with the classic locale ("C") whereas the locale of bitcoin-qt will vary + * depending on the user's environment variables. + * + * An example: Assuming the environment variable LC_ALL=de_DE then the + * call std::to_string(1.23) will return "1.230000" in bitcoind but + * "1,230000" in bitcoin-qt. + * + * From the Qt documentation: + * "On Unix/Linux Qt is configured to use the system locale settings by default. + * This can cause a conflict when using POSIX functions, for instance, when + * converting between data types such as floats and strings, since the notation + * may differ between locales. To get around this problem, call the POSIX + * function setlocale(LC_NUMERIC,"C") right after initializing QApplication, + * QGuiApplication or QCoreApplication to reset the locale that is used for + * number formatting to "C"-locale." + * + * See https://doc.qt.io/qt-5/qcoreapplication.html#locale-settings and + * https://stackoverflow.com/a/34878283 for more details. */ final class LocaleDependenceLinter extends ArcanistLinter { diff --git a/src/qt/bitcoin.cpp b/src/qt/bitcoin.cpp --- a/src/qt/bitcoin.cpp +++ b/src/qt/bitcoin.cpp @@ -219,6 +219,7 @@ : QApplication(qt_argc, const_cast(&qt_argv)), coreThread(nullptr), optionsModel(nullptr), clientModel(nullptr), window(nullptr), pollShutdownTimer(nullptr), returnValue(0), platformStyle(nullptr) { + // Qt runs setlocale(LC_ALL, "") on initialization. RegisterMetaTypes(); setQuitOnLastWindowClosed(false); }