aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJack Lloyd <[email protected]>2021-04-27 16:50:49 -0400
committerJack Lloyd <[email protected]>2021-04-27 16:50:49 -0400
commit0bed53375c8d7de299d9a4b8f48abe814a672a48 (patch)
tree7fd6b03b2bd37b868f1217b391145ee00198587b
parent4e2d7f744283d3c9113d20741c54dd95befee864 (diff)
Add a test of OID::to_string
This is our canary in the coalmine for std::to_string respecting locale
-rw-r--r--src/tests/test_oid.cpp36
1 files changed, 36 insertions, 0 deletions
diff --git a/src/tests/test_oid.cpp b/src/tests/test_oid.cpp
index 430d4fe4b..f803b2d05 100644
--- a/src/tests/test_oid.cpp
+++ b/src/tests/test_oid.cpp
@@ -16,6 +16,41 @@ namespace {
#if defined(BOTAN_HAS_ASN1)
+Test::Result test_OID_to_string()
+ {
+ /*
+ See #2730 and #2237
+
+ Certain locales format integers with thousands seperators. This
+ caused a subtle bug which caused OID comparisons to fail because
+ OID::to_string(), which used ostringstream, introduced a thousands
+ seperator when the OID component had a value >= 1000. But this
+ only failed in certain locales (pt_BR was reported).
+
+ Nominally C++ requires std::to_string to also be locale-respecting.
+ But, libc++, libstdc++, and MSVC's STL library all implement
+ std::to_string in a way that ignores locales, because adding locale
+ support means std::to_string will be both slow and a serialization
+ point. So as a stopgap we assume this behavior from std::to_string.
+
+ Here we test the original issue of #2237 to verify it works. If
+ the compiler implements std::to_string in a way that respects locale,
+ *and* this test is run in a locale that uses thousands seperators,
+ then it will fail. Which is much better than a very subtle failure.
+ However if it ever does fail then we must replace nearly every
+ call to std::to_string with something else that ignores locale.
+ */
+
+ Botan::OID oid{1,2,1000,1001,1002000};
+
+ Test::Result result("OID::to_string");
+
+ result.test_eq("OID::to_string behaves as we expect",
+ oid.to_string(), "1.2.1000.1001.1002000");
+
+ return result;
+ }
+
Test::Result test_add_have_OID()
{
Test::Result result("OID add");
@@ -83,6 +118,7 @@ class OID_Tests final : public Test
std::vector<std::function<Test::Result()>> fns =
{
+ test_OID_to_string,
test_add_have_OID,
test_add_have_OID_str,
test_add_and_lookup,