C 在内核中使用寄存器类型变量是否有问题?

C 在内核中使用寄存器类型变量是否有问题?,c,kernel,C,Kernel,我在看书。在第5章中,他谈到了寄存器,指出在内核代码中使用寄存器是个坏主意 这是否也意味着在编程内核时,在C中使用带有关键字register的变量也是一个坏主意?不,这并不意味着在内核模式C代码中使用register关键字是一个坏主意:关键字只是编译器的提示,而不是命令*。最后,是编译器为变量选择存储空间。当您通过传递适当的标志(在将为/kernel的窗口上)告诉编译器您正在编译内核模式代码时,编译器知道它不能使用哪些寄存器,因此它不会将变量放入这些寄存器中,即使您请求变量的寄存器存储 话虽如此

我在看书。在第5章中,他谈到了寄存器,指出在内核代码中使用寄存器是个坏主意


这是否也意味着在编程内核时,在
C
中使用带有关键字
register
的变量也是一个坏主意?

不,这并不意味着在内核模式C代码中使用
register
关键字是一个坏主意:关键字只是编译器的提示,而不是命令*。最后,是编译器为变量选择存储空间。当您通过传递适当的标志(在将为
/kernel
的窗口上)告诉编译器您正在编译内核模式代码时,编译器知道它不能使用哪些寄存器,因此它不会将变量放入这些寄存器中,即使您请求变量的
寄存器
存储

话虽如此,使用
register
不太可能给您带来太多好处:现代优化编译器非常擅长选择寄存器的最佳用途,因此很难通过
register
关键字提供分配提示来改进寄存器的分配


*实际上比这更糟糕的是:当您使用
register
关键字时,您向编译器保证您不会获取您声明的
register
变量的地址。因此,合同对您有约束力,但对编译器没有约束力。感谢您指出这一点。

不,这并不意味着在内核模式C代码中使用
register
关键字是一个坏主意:关键字对于编译器来说只是一个提示,而不是一个顺序*。最后,是编译器为变量选择存储空间。当您通过传递适当的标志(在将为
/kernel
的窗口上)告诉编译器您正在编译内核模式代码时,编译器知道它不能使用哪些寄存器,因此它不会将变量放入这些寄存器中,即使您请求变量的
寄存器
存储

话虽如此,使用
register
不太可能给您带来太多好处:现代优化编译器非常擅长选择寄存器的最佳用途,因此很难通过
register
关键字提供分配提示来改进寄存器的分配


*实际上比这更糟糕的是:当您使用
register
关键字时,您向编译器保证您不会获取您声明的
register
变量的地址。因此,合同对您有约束力,但对编译器没有约束力。感谢您指出这一点。

由于工具集的库通常依赖于操作系统,因此内核的内部调用约定是在库和内核之间,而不是在程序和库之间,因此对程序员来说并不重要。一个例外是在16位实模式下运行的旧代码,如BIOS或MSDOS调用,使用寄存器和INT来“调用”BIOS或MSDOS函数或其他一些操作系统版本。链接文本实际上涉及向量和浮点寄存器。内核代码通常不使用它们(除非您指示编译器这样做)。文本只是说,如果您决定出于任何原因使用这些寄存器,您自己负责保存和恢复它们——这意味着:您将使代码不可中断,有效地抑制抢占(这可能会导致延迟),因此,应该仔细考虑这个决定。由于工具集的库通常依赖于操作系统,内核的内部调用约定是在库和内核之间,而不是在程序和库之间,因此这对程序员来说并不重要。一个例外是在16位实模式下运行的旧代码,如BIOS或MSDOS调用,使用寄存器和INT来“调用”BIOS或MSDOS函数或其他一些操作系统版本。链接文本实际上涉及向量和浮点寄存器。内核代码通常不使用它们(除非您指示编译器这样做)。文本只是说,如果您决定出于任何原因使用这些寄存器,您自己负责保存和恢复它们——这意味着:您将使代码不可中断,有效地抑制抢占(这可能会导致延迟),所以这个决定应该仔细考虑。
register
甚至不是一个暗示。c标准给它的唯一区别是不允许您获取此类变量的地址(
&
)。因此,约束您而不是编译器的不仅仅是一份合同。@JensGustedt感谢您指出这一点!我在答案中添加了一个注释。我认为最初的帖子可能考虑了快速调用约定,其中一些参数在寄存器中传递。这主要是32位模式的问题,因为至少Microsoft编译器只有X64模式的快速调用模型。
register
甚至不是提示。c标准给它的唯一区别是不允许您获取此类变量的地址(
&
)。因此,约束您而不是编译器的不仅仅是一份合同。@JensGustedt感谢您指出这一点!我在答案中添加了一个注释。我认为最初的帖子可能考虑了快速调用约定,其中一些参数在寄存器中传递。这主要是32位模式的问题,因为至少Microsoft编译器只有X64模式的快速调用模型。