You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
When converting a double value larger than INT_MAX to an integer using the Blackboard system, the program encounters undefined behavior, leading to a SIGILL (illegal instruction). This occurs in the checkTruncation function when attempting to validate numeric conversions.
The function attempts to detect truncation by converting back and forth between types, but does so without first checking if the value is within the target type's limits, leading to undefined behavior.
Program crash (SIGILL) when converting large floating-point values to integers
Potential security implications in parsing untrusted data
Can affect any system using the Blackboard for numeric type conversions
throwstd::runtime_error("Floating point truncated");
}
}
The issue occurs because static_cast<To>(from) is undefined behavior when from exceeds the limits of To. This undefined value is then used in another cast and comparison operation.
template <typename From, typename To>
inlinevoidcheckTruncation(const From& from)
{
// Handle integer to floating pointifconstexpr(std::is_integral_v<From> && std::is_floating_point_v<To>) {
// Check if value can be represented exactly in the target type
To as_float = static_cast<To>(from);
From back_conv = static_cast<From>(as_float);
if(back_conv != from) {
throwstd::runtime_error("Loss of precision in conversion");
}
}
// Handle floating point to integerelseifconstexpr(std::is_floating_point_v<From> && std::is_integral_v<To>) {
if (from > static_cast<From>(std::numeric_limits<To>::max()) ||
from < static_cast<From>(std::numeric_limits<To>::min()) ||
from != std::trunc(from)) {
throwstd::runtime_error("Invalid floating point to integer conversion");
}
}
// Handle other conversionselse {
if (from > static_cast<From>(std::numeric_limits<To>::max()) ||
from < static_cast<From>(std::numeric_limits<To>::min())) {
throwstd::runtime_error("Value outside numeric limits");
}
To as_target = static_cast<To>(from);
From back_to_source = static_cast<From>(as_target);
if(from != back_to_source) {
throwstd::runtime_error("Value truncated in conversion");
}
}
}
cktii
changed the title
SIGILL in SafeAny::details::checkTruncation due to undefined behavior in floating-point to integer conversion
Multiple SIGILL crashes in SafeAny::details::checkTruncation due to undefined behavior in type conversions
Jan 31, 2025
Description
When converting a double value larger than
INT_MAX
to an integer using the Blackboard system, the program encounters undefined behavior, leading to a SIGILL (illegal instruction). This occurs in thecheckTruncation
function when attempting to validate numeric conversions.The function attempts to detect truncation by converting back and forth between types, but does so without first checking if the value is within the target type's limits, leading to undefined behavior.
Found in commit: 48f6c5b
Bug Class
Integer/Type Conversion Vulnerability - Undefined Behavior
Impact
Program crash (SIGILL) when converting large floating-point values to integers
Potential security implications in parsing untrusted data
Can affect any system using the Blackboard for numeric type conversions
Reproducer
Root Cause
In convert_impl.hpp:91:
BehaviorTree.CPP/include/behaviortree_cpp/utils/convert_impl.hpp
Lines 88 to 95 in 48f6c5b
The issue occurs because
static_cast<To>(from)
is undefined behavior when from exceeds the limits of To. This undefined value is then used in another cast and comparison operation.Stack trace
Proposed Fix
Replace the current implementation with a bounds check before attempting the conversion:
Additional Notes
This was found via fuzzing with AFL++. The crash is reproducible in both Debug and Release builds.
The text was updated successfully, but these errors were encountered: