我已经对C ++进行了高度优化,即使在远离热点的地方进行微小的更改也可以达到高达20%的性能。经过深入调查后发现,热点中使用的寄存器(可能)略有不同。 我可以使用always_inline属性控制内联,但是我可以控制寄存器分配吗?
答案 0 :(得分:6)
如果你真的想搞乱寄存器的分配,你可以强制GCC在某些寄存器中分配本地和全局变量。
您可以使用如下特殊变量声明执行此操作:
register int test_integer asm ("EBX");
也适用于其他架构,只需将EBX替换为目标特定的注册名称。
有关此内容的更多信息,建议您查看gcc文档:
http://gcc.gnu.org/onlinedocs/gcc-4.3.3/gcc/Local-Reg-Vars.html
我建议不要乱用寄存器分配,除非你有非常好的理由。如果您自己分配一些寄存器,那么分配器可以使用较少的寄存器,并且您可能最终得到的代码比您开始使用的代码更糟糕。
如果您的函数性能至关重要,那么在编译之间会有20%的性能差异,那么在内联汇编程序中编写该函数可能是个好主意。
编辑:正如strager所指出的那样,编译器不会强制使用寄存器来表示变量。如果完全使用变量,它只被强制使用寄存器。例如。如果变量不能在优化过程中存活,则不会使用它。寄存器也可以用于其他变量。
答案 1 :(得分:3)
通常,所有现代编译器都会忽略register关键字。唯一的例外是,如果您尝试使用register关键字标记的变量的地址,则(相对)最近添加错误。
我也经历过这种痛苦,并且最终发现唯一真正的方法是查看输出组件以尝试确定导致gcc脱离深层的原因。您还可以执行其他操作,但这取决于您的代码正在尝试执行的操作。我在一个非常大的函数中工作,有大量的计算goto混乱,其中轻微(看似无害)的变化可能导致灾难性的性能命中。如果你正在做类似的事情,你可以做一些事情来尝试和缓解问题,但细节有点icky所以我会放弃在这里讨论它们,除非它实际上是相关的。
答案 2 :(得分:-1)
这取决于您使用的处理器。或者我应该说,是的,您可以使用register关键字,但除非您使用的是没有管道衬里和单核心的简单处理器,否则这是不赞成的。现在,GCC可以比注册分配做得更好。相信它。