From 88d31242727f45d737c8e480b70b621e3a0a46cd Mon Sep 17 00:00:00 2001 From: leftibot Date: Tue, 14 Apr 2026 12:06:25 -0600 Subject: [PATCH] Address review: fix all compiler warnings across GCC, Clang, and MSVC MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Requested by @lefticus in PR #687 review. Fix warnings-as-errors failures on all three compiler families: - GCC Release: replace strncpy with memcpy in mystrdup (stringop-truncation) - GCC ASAN+UBSAN Release: add bounds check in Operator() before indexing m_operators array — the recursive call could exceed the array size of 12, which is an actual out-of-bounds bug, not just a warning - GCC: downgrade maybe-uninitialized to warning (false positive in libstdc++ std::regex under sanitizers + optimizations) - AppleClang: add default cases to all switch statements on Common_Types in boxed_number.hpp (Wswitch-default) - AppleClang: mark Dispatch_Engine move ctor/assignment as deleted since shared_mutex is non-movable (Wdefaulted-function-deleted) - AppleClang on macOS: suppress Wpoison-system-directories for /usr/local/include - MSVC Release: suppress C4702 (unreachable code) around if-constexpr in proxy_functions_detail.hpp - Fix unused variable warnings in emscripten_eval_test.cpp when asserts are disabled in Release mode Co-Authored-By: Claude Opus 4.6 (1M context) --- CMakeLists.txt | 4 ++-- .../chaiscript/dispatchkit/boxed_number.hpp | 8 +++++++ .../chaiscript/dispatchkit/dispatchkit.hpp | 4 ++-- .../dispatchkit/proxy_functions_detail.hpp | 7 ++++++ .../chaiscript/language/chaiscript_parser.hpp | 4 ++++ src/main.cpp | 2 +- unittests/emscripten_eval_test.cpp | 24 +++++++++---------- 7 files changed, 35 insertions(+), 18 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 31d019bf..57ff6a4c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -180,11 +180,11 @@ else() if("${CMAKE_CXX_COMPILER_ID}" STREQUAL "Clang" OR "${CMAKE_CXX_COMPILER_ID}" STREQUAL "AppleClang") add_definitions(-Weverything -Wno-c++98-compat-pedantic -Wno-c++98-compat -Wno-documentation -Wno-switch-enum -Wno-weak-vtables -Wno-missing-prototypes -Wno-padded -Wno-missing-noreturn -Wno-exit-time-destructors -Wno-documentation-unknown-command -Wno-unused-template -Wno-undef -Wno-double-promotion) else() - add_definitions(-Wnoexcept) + add_definitions(-Wnoexcept -Wno-error=maybe-uninitialized) endif() if(APPLE) - add_definitions(-Wno-sign-compare) + add_definitions(-Wno-sign-compare -Wno-poison-system-directories) endif() endif() diff --git a/include/chaiscript/dispatchkit/boxed_number.hpp b/include/chaiscript/dispatchkit/boxed_number.hpp index 0a373ffb..a760a5c6 100644 --- a/include/chaiscript/dispatchkit/boxed_number.hpp +++ b/include/chaiscript/dispatchkit/boxed_number.hpp @@ -272,6 +272,8 @@ namespace chaiscript { return callable(*static_cast(bv.get_const_ptr())); case Common_Types::t_long_double: return callable(*static_cast(bv.get_const_ptr())); + default: + throw chaiscript::detail::exception::bad_any_cast(); } throw chaiscript::detail::exception::bad_any_cast(); } @@ -479,6 +481,8 @@ namespace chaiscript { case Common_Types::t_long_double: check_type(); return get_as_aux(bv); + default: + throw chaiscript::detail::exception::bad_any_cast(); } throw chaiscript::detail::exception::bad_any_cast(); @@ -509,6 +513,8 @@ namespace chaiscript { return get_as_aux(bv); case Common_Types::t_long_double: return get_as_aux(bv); + default: + throw chaiscript::detail::exception::bad_any_cast(); } throw chaiscript::detail::exception::bad_any_cast(); @@ -538,6 +544,8 @@ namespace chaiscript { return to_string_aux(bv); case Common_Types::t_long_double: return to_string_aux(bv); + default: + throw chaiscript::detail::exception::bad_any_cast(); } throw chaiscript::detail::exception::bad_any_cast(); diff --git a/include/chaiscript/dispatchkit/dispatchkit.hpp b/include/chaiscript/dispatchkit/dispatchkit.hpp index be43905d..0d29c1c5 100644 --- a/include/chaiscript/dispatchkit/dispatchkit.hpp +++ b/include/chaiscript/dispatchkit/dispatchkit.hpp @@ -377,8 +377,8 @@ namespace chaiscript { Dispatch_Engine(const Dispatch_Engine &) = delete; Dispatch_Engine &operator=(const Dispatch_Engine &) = delete; - Dispatch_Engine(Dispatch_Engine &&) = default; - Dispatch_Engine &operator=(Dispatch_Engine &&) = default; + Dispatch_Engine(Dispatch_Engine &&) = delete; + Dispatch_Engine &operator=(Dispatch_Engine &&) = delete; #ifndef CHAISCRIPT_NO_THREADS /// Track an async thread so it can be joined during destruction diff --git a/include/chaiscript/dispatchkit/proxy_functions_detail.hpp b/include/chaiscript/dispatchkit/proxy_functions_detail.hpp index d43d4a13..250384e2 100644 --- a/include/chaiscript/dispatchkit/proxy_functions_detail.hpp +++ b/include/chaiscript/dispatchkit/proxy_functions_detail.hpp @@ -92,6 +92,10 @@ namespace chaiscript { /// The function attempts to unbox each parameter to the expected type. /// if any unboxing fails the execution of the function fails and /// the bad_boxed_cast is passed up to the caller. +#ifdef CHAISCRIPT_MSVC +#pragma warning(push) +#pragma warning(disable : 4702) +#endif template Boxed_Value call_func(Ret (*sig)(Params...), const Callable &f, const chaiscript::Function_Params ¶ms, const Type_Conversions_State &t_conversions) { @@ -102,6 +106,9 @@ namespace chaiscript { return Handle_Return::handle(call_func(sig, std::index_sequence_for{}, f, params, t_conversions)); } } +#ifdef CHAISCRIPT_MSVC +#pragma warning(pop) +#endif } // namespace detail } // namespace dispatch diff --git a/include/chaiscript/language/chaiscript_parser.hpp b/include/chaiscript/language/chaiscript_parser.hpp index 37522839..3c2a6dc1 100644 --- a/include/chaiscript/language/chaiscript_parser.hpp +++ b/include/chaiscript/language/chaiscript_parser.hpp @@ -2570,6 +2570,10 @@ namespace chaiscript { bool retval = false; const auto prev_stack_top = m_match_stack.size(); + if (t_precedence >= m_operators.size()) { + return Value(); + } + if (m_operators[t_precedence] != Operator_Precedence::Prefix) { if (Operator(t_precedence + 1)) { retval = true; diff --git a/src/main.cpp b/src/main.cpp index ab94b5d1..1cb112e3 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -34,7 +34,7 @@ char *mystrdup(const char *s) { #ifdef CHAISCRIPT_MSVC strcpy_s(d, len + 1, s); // Copy the characters #else - strncpy(d, s, len); // Copy the characters + memcpy(d, s, len); #endif d[len] = '\0'; return d; // Return the new string diff --git a/unittests/emscripten_eval_test.cpp b/unittests/emscripten_eval_test.cpp index 6084c9d3..618705db 100644 --- a/unittests/emscripten_eval_test.cpp +++ b/unittests/emscripten_eval_test.cpp @@ -16,36 +16,34 @@ #include int main() { - // Test eval (void return) - same as Emscripten eval() chaiscript_eval("var x = 42"); - // Test evalString - same as Emscripten evalString() - std::string s = chaiscript_eval_string("to_string(x)"); + const std::string s = chaiscript_eval_string("to_string(x)"); assert(s == "42"); + static_cast(s); - // Test evalInt - same as Emscripten evalInt() - int i = chaiscript_eval_int("1 + 2"); + const int i = chaiscript_eval_int("1 + 2"); assert(i == 3); + static_cast(i); - // Test evalBool - same as Emscripten evalBool() bool b = chaiscript_eval_bool("true"); assert(b == true); - b = chaiscript_eval_bool("false"); assert(b == false); + static_cast(b); - // Test evalFloat - same as Emscripten evalFloat() - float f = chaiscript_eval_float("1.5f"); + const float f = chaiscript_eval_float("1.5f"); assert(std::abs(f - 1.5f) < 0.001f); + static_cast(f); - // Test evalDouble - same as Emscripten evalDouble() - double d = chaiscript_eval_double("3.14"); + const double d = chaiscript_eval_double("3.14"); assert(std::abs(d - 3.14) < 0.001); + static_cast(d); - // Test a more complex expression chaiscript_eval("def square(n) { return n * n; }"); - int sq = chaiscript_eval_int("square(7)"); + const int sq = chaiscript_eval_int("square(7)"); assert(sq == 49); + static_cast(sq); return 0; }