根据 Patterson & Hennessy 的 计算机组织和设计(MIPS 版),
所以,如果我想在堆栈指针中压入 1 个单词,比如
0xCAFEBABE
,我会
0xCAFEBABE
存储到堆栈指针指向的地址。现在,
0x7FFFFFF8
、0x7FFFFFF9
、0x7FFFFFFA
、0x7FFFFFFB
处的字节将是 0xCA
、0xFE
、0xBA
、0xBE
(顺序取决于字节顺序)。但是 0x7FFFFFFC
、0x7FFFFFFD
、0x7FFFFFFE
、0x7FFFFFFF
处的字节永远不会被使用!
我认为这浪费了记忆中的1个单词。如果
$sp
的初始值为 0x80000000
,那 1 个单词就不会被浪费。
https://www.dyncall.org/docs/manual/manualse11.html:
MIPS指令集存在多个版本,即MIPS I、MIPS II、MIPS III、MIPS IV、MIPS32和MIPS64。如今,MIPS32 和 MIPS64 分别是用于 32 位和 64 位指令集的主要指令集。 鉴于 MIPS 处理器通常用于嵌入式设备,MIPS 系列存在多种附加扩展,例如:
不幸的是,实际上并不存在“MIPS 调用约定”这样的东西。许多不同的环境使用许多可能的约定,例如 O32[38]、O64[39]、N32[40]、N64[40]、EABI[41] 和 NUBI[42]。
https://courses.cs.washington.edu/courses/cse410/09sp/examples/MIPSCallingConventionsSummary.pdf:
堆栈指针的值必须始终是 8 的倍数。
您从书中引用的材料比所有人都遵循的要求更具信息性。我敢说操作系统可以自由使用 0x8000000(或 0x7ffffff0,比 0x7fffffc 更对齐的地址)。让我们注意,0x7fffffc 仅是字对齐,而不是双字对齐,但双浮点加载和存储需要双字对齐,因此从字面上遵循此文本是有问题的,这导致了它是暗示性的而不是规范的论点。
书籍中对调用约定的描述是原始 MIPS 的,或者已经过时了,这取决于如何看待它。虽然该书已重印,最新版本为2020年第6版,但文字内容保持不变。我们还可以在 RISC-V 版本中看到相同的文本(使用完全相同的措辞,即 MIPS 和 0x7fffffc 等)。在 RISC-V 书中,0x7FFFFFFC 和 MIPS 的使用显然暗示了 RISC-V 的一种方法,而不是这种较新的后续处理器的规则。
另一个答案涉及两种流行的 MIPS 模拟器的工作方式:https://stackoverflow.com/a/64654885/471129
这种堆栈使用模型称为完全降序。启动引用实际自由字(或双字)的堆栈指针允许替代堆栈使用模型,称为空降序。
每个进程浪费一个字(或双字)是无害的。