While working with Berkeley TestFloat I've noticed that testing of floating-point to integer conversion is done by checking (in particular) a specific result values:
在使用Berkeley TestFloat时,我注意到浮点到整数转换的测试是通过检查(特别是)特定的结果值来完成的:
// file: test_a_f32_z_i32_rx.c
// function: test_a_f32_z_i32_rx
...
if ( (trueZ != subjZ) || (trueFlags != subjFlags) ) {
if (
verCases_checkInvInts
|| (trueFlags != softfloat_flag_invalid)
|| (subjFlags != softfloat_flag_invalid)
|| ((subjZ != 0x7FFFFFFF) && (subjZ != -0x7FFFFFFF - 1)
&& (! f32_isNaN( genCases_f32_a ) || (subjZ != 0)))
) {
++verCases_errorCount;
Here we see the specific result values: 0
, 0x7FFFFFFF
(max. signed integer), -0x7FFFFFFF - 1
(min. signed integer).
在这里,我们可以看到具体的结果值:0,0x7FFFFFFFF(max.带符号整数),-0x7FFFFFFF-1(最小值带符号整数)。
However, per C11 (and higher) standard conversion of out of range floating-point to integer leads to UB. Since usually (int)f
leads to generation of hardware instruction (e.g. cvttss2si
for x86_64), I wonder: is there any hardware which converts out of range floating-point to non-zero/min/max integer?
然而,根据C11(和更高版本)的标准,将超出范围的浮点数转换为整数会导致UB。由于通常(Int)f会导致硬件指令的生成(例如x86_64的cvttss2si),我想知道:有没有硬件可以将超出范围的浮点数转换为非零/最小/最大整数?
Extra: Why converting 'out of range integer to integer' leads to IB, but converting 'out of range floating-point to integer' leads to UB?
Extra:为什么将“超出范围的整型”转换为“整型”会导致IB,而将“超范围的浮点型”转换为“整型”则会导致UB?
更多回答
Re: "Not sure what you are asking": is there any hardware which does not return the smallest / largest integer, nor 0
? For example, -6
.
Re:“不知道你在问什么”:有没有硬件不返回最小/最大整数,也不返回0?例如,-6。
OK. 1) Re: "non-IEEE hardware traps": IEEE 754 has so-called "Alternate exception handling" and, as I understand, permits trapping: "NOTE 2 — Immediate alternate exception handling for an exception can be implemented by traps". 2) FYI: if such trap will return -6
(for example), then Berkeley TestFloat will report false positives.
好的。1)Re:“非IEEE硬件陷阱”:IEEE754有所谓的“替代异常处理”,据我所知,它允许陷阱:“注2--异常的即时替代异常处理可以由陷阱实现”。2)仅供参考:如果此类陷阱将返回-6(例如),则Berkeley TestFloat将报告误报。
Is there any hardware which converts out of range floating-point to non-zero/min/max integer?
A note about what is out-of-range.
关于什么是超出范围的说明。
C specifies floating-point to integer conversion as the conversion of the truncated floating point value.
C将浮点到整数的转换指定为截断的浮点值的转换。
For converting to a 32-bit integer, the valid range is slightly more than [-2,147,483,648.0 ... 2,147,483,647.0]. It is (-2,147,483,649.0 ... 2,147,483,648.0). Note the ()
versus []
.
对于转换为32位整数,有效范围略大于[-2,147,483,648.0...2,147,483,647.0]。它是(-2,147,483,649.0...2,147,483,648.0)。请注意()与[]的对比。
Sample code to test a float
before conversion. It takes advantage that INT_MIN
is always a - power-of-2 (C23) and that INT_MAX
is a Mersenne Number.
用于在转换前测试浮点的示例代码。它利用INT_MIN总是2的幂(C23),并且INT_MAX是梅森数。
#define FLT_INT_MIN INT_MIN
#define FLT_INT_MAX_PLUS1 ((INT_MAX/2 + 1)*2.0f)
bool float_to_int_range_test(float f) {
return isgreater(f - FLT_INT_MIN, -1) &&
isless(f, FLT_INT_MAX_PLUS1);
}
The C standard, from C11 onward, treats converting out-of-range floating-point values to integers as undefined behavior (UB). This means compilers aren't bound to specific behavior, aiming to prevent cross-platform issues. While some hardware might handle such conversions uniquely, this isn't standardized or common. The Berkeley TestFloat framework tests compliance with standards, using specific values for testing, but these may not reflect all hardware behavior. Prioritizing portability, follow the C standard's rules and avoid assumptions about hardware behavior. Handle out-of-range cases explicitly or use library functions like isfinite to ensure well-defined behavior before conversions.
从C11开始,C标准将超出范围的浮点值转换为整数视为未定义的行为(UB)。这意味着编译器不受特定行为的限制,旨在防止跨平台问题。虽然有些硬件可能会独一无二地处理此类转换,但这并不是标准化的或常见的。Berkeley TestFloat框架使用特定的测试值来测试与标准的符合性,但这些值可能并不反映所有硬件行为。优先考虑可移植性,遵循C标准的规则,避免对硬件行为的假设。显式处理超出范围的情况或使用诸如isfined之类的库函数,以确保在转换之前定义良好的行为。
更多回答
A good note, thanks. Re: "slightly more than ...": exactly. In my FP tests (still unfinished) there are macros like F2I_FMAX
and F2I_FMIN
, which specify the max and min FP values, for which the behavior of the conversion to integer is well-defined by the C standard.
一张好纸条,谢谢。回答:“略多于……”:完全正确。在我的FP测试中(仍未完成),有F2i_FMAX和F2i_FMIN这样的宏,它们指定最大和最小FP值,C标准很好地定义了将其转换为整数的行为。
@pmor Answer updated.
@pmor答案已更新。
OK. Consider addressing this question.
好的。考虑解决这个问题。
Consider addressing / commenting on this answer.
请考虑对此答案进行说明/评论。
我是一名优秀的程序员,十分优秀!