Tag: x86

C和C ++中float和double的大小是多少?

我正在寻找是否有任何类似于uint32_t标准类型,它总是会映射到32位无符号整数类型但我找不到任何类型。 float的大小在所有平台上总是4个字节吗? double大小总是8? 这两个标准是否有任何关于此事的说法? 我想确保我的大小在所有平台(x86和x64)上总是相同的,所以我使用的是标准的int类型,但是我找不到任何类似的float和double typedef。

关于在C / C ++ / Assembly中返回多个值

我已经阅读了一些关于返回多个值的问题,例如在C ++和Java中只有一个返回值的原因是什么? , 从C ++函数和https://softwareengineering.stackexchange.com/questions/203471/why-do-most-programming-languages-only-support-returning-a-single-value-from-af 返回多个值 。 我同意用于certificate多个返回值不是绝对必要的大多数参数,我理解为什么没有实现这样的function,但我仍然无法理解为什么我们不能使用多个调用者保存的寄存器例如ECX和EDX返回这样的值。 使用寄存器而不是创建一个Class / Struct来存储这些值或通过引用/指针传递参数不是更快,两者都使用内存来存储它们吗? 如果可以做这样的事情,那么任何C / C ++编译器是否都使用此function来加速代码? 编辑:理想的代码是这样的: (int, int) getTwoValues(void) { return 1, 2; } int main(int argc, char** argv) { (int a, int b) = getTwoValues();//a and b are actually returned in registers so future operations with a and b are faster //do something with […]

除非Haswell指明,否则GCC会很难编制前导零数

GCC支持__builtin_clz(int x) builtin,它计算参数中前导零 (连续最重要的零)的数量。 除了0之外 ,这对于有效地实现lg(unsigned int x)函数非常有用,它取lg(unsigned int x)的基数为2的对数,向下舍入为1 : /** return the base-2 log of x, where x > 0 */ unsigned lg(unsigned x) { return 31U – (unsigned)__builtin_clz(x); } 这是直截了当的方式 – 特别是考虑情况x == 1和clz(x) == 31 – 然后x == 2^0所以lg(x) == 0和31 – 31 == 0我们得到正确的结果。 较高的x值类似地起作用。 假设内置程序有效实现,这比其他纯C解决方案更好。 现在,它发生了, 计数前导零操作本质上是x86中bsr指令的双重。 返回参数中最重要的1位2的索引。 因此,如果有10个前导零,则第一个1位位于参数的第21位。 […]

具有Core 2 CPU(SSSE3)的大缓冲区的位popcount

我正在寻找在512或更多字节的大缓冲区上popcount的最快方法。 我可以保证任何所需的对齐,缓冲区大小始终是2的幂。缓冲区对应于块分配,因此通常位是全部设置,没有设置,或者大多数设置有利于缓冲区的“左”,偶尔出洞。 我考虑过的一些解决方案是: 海湾合作委员会的__builtin_popcount Bitslice popcount_24words 计算位数,Brian Kernighan的方式 我对最快的解决方案感兴趣,它必须适用于属于core2或更新版本的32位x86芯片组。 SSE和SIMD引起了极大的兴趣。 我将在以下四核CPU上进行测试: matt@stanley:~/anacrolix/public/stackoverflow$ cat /proc/cpuinfo processor : 0 vendor_id : GenuineIntel cpu family : 6 model : 15 model name : Intel(R) Core(TM)2 Quad CPU Q6600 @ 2.40GHz stepping : 11 cpu MHz : 1600.000 cache size : 4096 KB physical id : 0 siblings : […]

X86程序集 – 处理IDIV指令

我目前正在编写一个简单的C编译器,它将.c文件作为输入并生成汇编代码(X86,AT&T语法)。 一切都很好,但是当我尝试执行IDIVQ指令时,我得到一个浮点exception。 这是我的意见: int mymain(int x){ int d; int e; d = 3; e = 6 / d; return e; } 这是我生成的代码: mymain: .LFB1: .cfi_startproc pushq %rbp .cfi_def_cfa_offset 16 movq %rsp, %rbp .cfi_offset 6, -16 .cfi_def_cfa_register 6 movq %rdi, -40(%rbp) movq $3, -8(%rbp) movq $6, %rax movq -8(%rbp), %rdx movq %rdx, %rbx idivq %rbx movq […]

内联x86程序集中是否未定义整数溢出?

说我有以下C代码: int32_t foo(int32_t x) { return x + 1; } 当x == INT_MAX时,这是未定义的行为。 现在说我用内联汇编代替了: int32_t foo(int32_t x) { asm(“incl %0” : “+g”(x)); return x; } 问题:当x == INT_MAX时,内联汇编版本是否仍会调用未定义的行为? 或者未定义的行为仅适用于C代码?

适用于Windows的硬件性能计数器API

我想使用硬件性能计数器 ,特别是x86 CPU来获取缓存未命中或分支错误预测。 性能计数器在英特尔VTune等高级分析器中大量使用。 请不要在Windows操作系统上混淆性能计数器。 为了在C / C ++程序中使用这些计数器,可以使用PAPI: http : //icl.cs.utk.edu/papi/ 这使您可以轻松使用性能计数器,但仅限Linux。 PAPI曾经支持Windows,但现在不支持。 是否有人最近尝试使用PAPI或其他API在Windows上使用硬件性能计数器?

为什么复杂的memcpy / memset优越?

在调试时,我经常进入memcpy和memset的手写程序集实现。 这些通常使用流指令(如果可用),循环展开,对齐优化等实现…我最近也遇到了由于glibc中的memcpy优化而导致的“错误” 。 问题是:为什么硬件制造商(英特尔,AMD)不能优化具体情况 rep stos 和 rep movs 被认可,并尽可能快地填写和复制他们自己的架构?

是否有针对8086的C编译器?

我有一个8086 CPU仿真器。 它仅模拟8086条指令。 我正在寻找一个C编译器来定位这个模拟器。 有没有可以做到这一点的C编译器? 此外,拥有一个可用的libc等对我来说并不重要。 模拟器使用自定义(即非PC)硬件,因此任何libc甚至ctr0都可能不得不重写

退出的Syscall实现()

我写了一个简单的C程序,只调用exit()函数,但是strace说二进制文件实际上是调用exit_group,exit()是一个exit_group()包装器吗? 这两个function是否相同? 如果是这样,为什么编译器会选择exit_group()而不是exit()?