以下C代码:
int main()
{
float f;
f = 3.0;
}
转换为以下装配说明:
main:
pushl %ebp
movl %esp, %ebp
subl $16, %esp
flds .LC0
fstps -4(%ebp)
movl $0, %eax
leave
ret
.LC0:
.long 1077936128
计算.long
字面值的int
/ float
表示的正确方法是什么?
1077936128
生成的 例如 3.0
对于此示例,
gcc
与-m32 -S -O0 -fno-stack-protector -fno-asynchronous-unwind-tables
标志一起使用,使用intel设置生成程序集输出。
参考:
带有编译标志和其他设置的答案 0 :(得分:4)
x86 FPU硬件使用float
/ double
的{{3}} / binary64表示。
确定浮点数的IEEE 754表示对于人类来说并非无足轻重。在手写汇编代码中,使用.float
或.double
指令通常是个好主意:
.float 3.0 # generates 3.0 as a 32 bit float
.double 3.0 # generates 3.0 as a 64 bit float
如果您确实想手动计算,请参阅IEEE754 binary32。作为练习这样做可能很有趣,但对于实际的编程来说,它很乏味且几乎没用。
编译器在内部进行转换(舍入到最接近的可表示FP值),因为FP值通常不直接来自源中的文字;它们可以来自不断折叠。例如1.23 * 4.56
在编译时进行评估,因此编译器已经以浮点数或双二进制表示形式的FP值结束。将它们打印回十进制以使汇编程序解析并重新转换为二进制文件会更慢并且可能需要很多小数位。
要计算32位浮点数作为32位整数的表示形式,可以使用explanations on Wikipedia或类似的程序:
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <inttypes.h>
int main(int argc, char *argv[])
{
union { uint32_t u32; float f32; } intfloat;
if (argc != 2) {
fprintf(stderr, "Usage: %s some-number\n", argv[0]);
return EXIT_FAILURE;
}
intfloat.f32 = atof(argv[1]);
printf("0x%08" PRIx32 "\n", intfloat.u32);
return EXIT_SUCCESS;
}