From 2c9bee265596bb29092e833a1d326c3dc71b4e41 Mon Sep 17 00:00:00 2001 From: wolframw <5099115+wolframw@users.noreply.github.com> Date: Sun, 13 Apr 2025 19:24:17 +0200 Subject: [PATCH 1/7] fix heap-use-after-free for _HAS_EXCEPTIONS=0 --- stl/inc/chrono | 11 ++++++++++ stl/inc/system_error | 6 ++++++ tests/std/test.lst | 1 + .../env.lst | 6 ++++++ .../test.cpp | 21 +++++++++++++++++++ 5 files changed, 45 insertions(+) create mode 100644 tests/std/tests/GH_005276_system_error_heap-use-after-free/env.lst create mode 100644 tests/std/tests/GH_005276_system_error_heap-use-after-free/test.cpp diff --git a/stl/inc/chrono b/stl/inc/chrono index 2a86c9aded5..d6558177e2f 100644 --- a/stl/inc/chrono +++ b/stl/inc/chrono @@ -1725,9 +1725,15 @@ namespace chrono { _EXPORT_STD class _NODISCARD nonexistent_local_time : public runtime_error { public: +#if _HAS_EXCEPTIONS template nonexistent_local_time(const local_time<_Duration>& _Tp, const local_info& _Info) : runtime_error(_Make_string(_Tp, _Info)) {} +#else // ^^^ _HAS_EXCEPTIONS / !_HAS_EXCEPTIONS vvv + template + nonexistent_local_time(const local_time<_Duration>&, const local_info&) + : runtime_error("nonexistent local time") {} +#endif // ^^^ !_HAS_EXCEPTIONS ^^^ private: template @@ -1741,9 +1747,14 @@ namespace chrono { _EXPORT_STD class _NODISCARD ambiguous_local_time : public runtime_error { public: +#if _HAS_EXCEPTIONS template ambiguous_local_time(const local_time<_Duration>& _Tp, const local_info& _Info) : runtime_error(_Make_string(_Tp, _Info)) {} +#else // ^^^ _HAS_EXCEPTIONS / !_HAS_EXCEPTIONS vvv + template + ambiguous_local_time(const local_time<_Duration>&, const local_info&) : runtime_error("ambiguous local time") {} +#endif // ^^^ !_HAS_EXCEPTIONS ^^^ private: template diff --git a/stl/inc/system_error b/stl/inc/system_error index bcf2ca0d88f..4a263e93ee5 100644 --- a/stl/inc/system_error +++ b/stl/inc/system_error @@ -470,10 +470,16 @@ private: } protected: +#if _HAS_EXCEPTIONS _System_error(error_code _Errcode) : runtime_error(_Errcode.message()), _Mycode(_Errcode) {} _System_error(error_code _Errcode, const string& _Message) : runtime_error(_Makestr(_Errcode, _Message)), _Mycode(_Errcode) {} +#else // ^^^ _HAS_EXCEPTIONS / !_HAS_EXCEPTIONS vvv + _System_error(error_code _Errcode) : runtime_error("system error"), _Mycode(_Errcode) {} + + _System_error(error_code _Errcode, const string&) : runtime_error("system error"), _Mycode(_Errcode) {} +#endif // ^^^ !_HAS_EXCEPTIONS ^^^ error_code _Mycode; // the stored error code }; diff --git a/tests/std/test.lst b/tests/std/test.lst index 292e4255c97..8031c5bda57 100644 --- a/tests/std/test.lst +++ b/tests/std/test.lst @@ -257,6 +257,7 @@ tests\GH_004930_char_traits_user_specialization tests\GH_005090_stl_hardening tests\GH_005204_regex_collating_ranges tests\GH_005244_regex_escape_sequences +tests\GH_005276_system_error_heap-use-after-free tests\GH_005315_destructor_tombstones tests\LWG2381_num_get_floating_point tests\LWG2597_complex_branch_cut diff --git a/tests/std/tests/GH_005276_system_error_heap-use-after-free/env.lst b/tests/std/tests/GH_005276_system_error_heap-use-after-free/env.lst new file mode 100644 index 00000000000..ebe0f92582a --- /dev/null +++ b/tests/std/tests/GH_005276_system_error_heap-use-after-free/env.lst @@ -0,0 +1,6 @@ +# Copyright (c) Microsoft Corporation. +# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception + +RUNALL_INCLUDE ..\usual_20_matrix.lst +RUNALL_CROSSLIST +* PM_CL="/D_HAS_EXCEPTIONS=0" diff --git a/tests/std/tests/GH_005276_system_error_heap-use-after-free/test.cpp b/tests/std/tests/GH_005276_system_error_heap-use-after-free/test.cpp new file mode 100644 index 00000000000..511a8fba6cb --- /dev/null +++ b/tests/std/tests/GH_005276_system_error_heap-use-after-free/test.cpp @@ -0,0 +1,21 @@ +// Copyright (c) Microsoft Corporation. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception + +#include +#include +#include +#include +using namespace std; +using namespace chrono; + +int main() { + string str{"abc"}; + error_code ec{2, system_category()}; + system_error syserr{ec}; + + ambiguous_local_time alt{local_time{}, local_info{}}; + + nonexistent_local_time nlt{local_time{}, local_info{}}; + + printf("%s\n%s\n%s\n", syserr.what(), alt.what(), nlt.what()); +} From 39444b6b9649e8cceeb4d1cb5ab88bc0fe6b2bca Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 15 Apr 2025 23:16:08 -0700 Subject: [PATCH 2/7] Rename test directory to use underscores. --- tests/std/test.lst | 2 +- .../env.lst | 0 .../test.cpp | 0 3 files changed, 1 insertion(+), 1 deletion(-) rename tests/std/tests/{GH_005276_system_error_heap-use-after-free => GH_005276_system_error_heap_use_after_free}/env.lst (100%) rename tests/std/tests/{GH_005276_system_error_heap-use-after-free => GH_005276_system_error_heap_use_after_free}/test.cpp (100%) diff --git a/tests/std/test.lst b/tests/std/test.lst index 8031c5bda57..969295ae89c 100644 --- a/tests/std/test.lst +++ b/tests/std/test.lst @@ -257,7 +257,7 @@ tests\GH_004930_char_traits_user_specialization tests\GH_005090_stl_hardening tests\GH_005204_regex_collating_ranges tests\GH_005244_regex_escape_sequences -tests\GH_005276_system_error_heap-use-after-free +tests\GH_005276_system_error_heap_use_after_free tests\GH_005315_destructor_tombstones tests\LWG2381_num_get_floating_point tests\LWG2597_complex_branch_cut diff --git a/tests/std/tests/GH_005276_system_error_heap-use-after-free/env.lst b/tests/std/tests/GH_005276_system_error_heap_use_after_free/env.lst similarity index 100% rename from tests/std/tests/GH_005276_system_error_heap-use-after-free/env.lst rename to tests/std/tests/GH_005276_system_error_heap_use_after_free/env.lst diff --git a/tests/std/tests/GH_005276_system_error_heap-use-after-free/test.cpp b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp similarity index 100% rename from tests/std/tests/GH_005276_system_error_heap-use-after-free/test.cpp rename to tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp From 018687684ad339bdee8b8ebfb33f9587ec8d6d04 Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 15 Apr 2025 23:37:41 -0700 Subject: [PATCH 3/7] Use `local_seconds`. --- .../tests/GH_005276_system_error_heap_use_after_free/test.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp index 511a8fba6cb..133fb638af3 100644 --- a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp +++ b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp @@ -13,9 +13,9 @@ int main() { error_code ec{2, system_category()}; system_error syserr{ec}; - ambiguous_local_time alt{local_time{}, local_info{}}; + ambiguous_local_time alt{local_seconds{}, local_info{}}; - nonexistent_local_time nlt{local_time{}, local_info{}}; + nonexistent_local_time nlt{local_seconds{}, local_info{}}; printf("%s\n%s\n%s\n", syserr.what(), alt.what(), nlt.what()); } From b984ff72559a2ea08a084d4e025d58d4fe48dc61 Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 15 Apr 2025 23:42:46 -0700 Subject: [PATCH 4/7] printf => assert. --- .../GH_005276_system_error_heap_use_after_free/test.cpp | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp index 133fb638af3..cd30e3aaead 100644 --- a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp +++ b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp @@ -1,9 +1,10 @@ // Copyright (c) Microsoft Corporation. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +#include #include -#include #include +#include #include using namespace std; using namespace chrono; @@ -12,10 +13,11 @@ int main() { string str{"abc"}; error_code ec{2, system_category()}; system_error syserr{ec}; + assert(syserr.what() == "system error"sv); ambiguous_local_time alt{local_seconds{}, local_info{}}; + assert(alt.what() == "ambiguous local time"sv); nonexistent_local_time nlt{local_seconds{}, local_info{}}; - - printf("%s\n%s\n%s\n", syserr.what(), alt.what(), nlt.what()); + assert(nlt.what() == "nonexistent local time"sv); } From 7993ced76d94d00adef88d1278d9f7a670e05d4c Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 15 Apr 2025 23:52:45 -0700 Subject: [PATCH 5/7] Test more `system_error` ctors, add braces to restrict scope. --- .../test.cpp | 39 +++++++++++++++---- 1 file changed, 32 insertions(+), 7 deletions(-) diff --git a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp index cd30e3aaead..e0a46e96ff1 100644 --- a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp +++ b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp @@ -12,12 +12,37 @@ using namespace chrono; int main() { string str{"abc"}; error_code ec{2, system_category()}; - system_error syserr{ec}; - assert(syserr.what() == "system error"sv); + { + system_error syserr1{ec}; + assert(syserr1.what() == "system error"sv); + } + { + system_error syserr2{ec, str}; + assert(syserr2.what() == "system error"sv); + } + { + system_error syserr3{ec, "meow"}; + assert(syserr3.what() == "system error"sv); + } + { + system_error syserr4{2, system_category()}; + assert(syserr4.what() == "system error"sv); + } + { + system_error syserr5{2, system_category(), str}; + assert(syserr5.what() == "system error"sv); + } + { + system_error syserr6{2, system_category(), "meow"}; + assert(syserr6.what() == "system error"sv); + } - ambiguous_local_time alt{local_seconds{}, local_info{}}; - assert(alt.what() == "ambiguous local time"sv); - - nonexistent_local_time nlt{local_seconds{}, local_info{}}; - assert(nlt.what() == "nonexistent local time"sv); + { + ambiguous_local_time alt{local_seconds{}, local_info{}}; + assert(alt.what() == "ambiguous local time"sv); + } + { + nonexistent_local_time nlt{local_seconds{}, local_info{}}; + assert(nlt.what() == "nonexistent local time"sv); + } } From afdb8fbb6afef5dfaef325e82bf419e68026bfdb Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 15 Apr 2025 23:53:57 -0700 Subject: [PATCH 6/7] Add const. --- .../tests/GH_005276_system_error_heap_use_after_free/test.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp index e0a46e96ff1..202060d60a2 100644 --- a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp +++ b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp @@ -10,8 +10,8 @@ using namespace std; using namespace chrono; int main() { - string str{"abc"}; - error_code ec{2, system_category()}; + const string str{"abc"}; + const error_code ec{2, system_category()}; { system_error syserr1{ec}; assert(syserr1.what() == "system error"sv); From 24bd550a50a7720a15972868fb6cec4ea37b5c82 Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 15 Apr 2025 23:59:07 -0700 Subject: [PATCH 7/7] Add issue title. --- .../tests/GH_005276_system_error_heap_use_after_free/test.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp index 202060d60a2..a1444a99678 100644 --- a/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp +++ b/tests/std/tests/GH_005276_system_error_heap_use_after_free/test.cpp @@ -9,6 +9,7 @@ using namespace std; using namespace chrono; +// GH-5276 : heap-use-after-free for _HAS_EXCEPTIONS=0 int main() { const string str{"abc"}; const error_code ec{2, system_category()};