调用函数时有如下约定:
●寄存器W0~W7由调用函数保存。为保存寄存器的值,调用函数必须将这些值压入堆栈。
●寄存器W8~W14由被调用函数保存。被调用函数必须保存它会修改的任何这些寄存器。
●寄存器W0~W4用于存放函数返回值。
●如果使用-fno-short-double,则double等价于longdouble。
参数存放到可用的第一批(个)对齐的邻近寄存器中。如果需要的话,调用函数必须保存参数。结构没有任何对齐限制;如果有足够的寄存器来保存整个结构,结构参数将占用寄存器。函数结果存储在从W0开始的连续寄存器中。
1.函数参数
前8个工作寄存器(W0~W7)用于存储函数参数。参数以自左向右的顺序分配到寄存器中,且参数被分配到对齐适当的第一个可用寄存器中。
下面的示例中,所有参数都通过寄存器传递,尽管这些参数不是以在声明中出现的顺序存放在寄存器中。这种格式允许MPLAB C30编译器最高效地使用可用的参数寄存器。
【例2-1】函数调用模型。
下面这个示例说明如何传递结构给函数。如果整个结构都可以存放在可用的寄存器中,那么就通过寄存器来传递结构,否则结构参数将存放在堆栈中。
【例2-2】函数调用模型,传递结构。(www.xing528.com)
与长度可变参数列表中的省略号(…)对应的参数不分配到寄存器中。任何不分配到寄存器的参数都以自右向左的顺序压入堆栈。
下面的示例中,由于结构参数太大而不能存放到寄存器中。但是,这并不会禁止使用寄存器来存放下一个参数。
【例2-3】函数调用模型,基于堆栈的参数。
typedefstructbar{
对存放到堆栈的参数的访问与是否创建了帧指针有关。编译器一般情况下都创建帧指针(除非已另外指示编译器不要这样做),将通过帧指针寄存器(W14)访问基于堆栈的参数。在上面的示例中,通过W14~22访问b。通过减去上一个FP的2字节,返回地址的4字节,和b的16字节,可计算出相对于帧指针的偏移量为-22
不使用帧指针时,汇编编程人员必须知晓自过程的入口开始使用了多少堆栈空间。如果没有额外使用堆栈空间,计算与上面类似。将通过W15~W20访问b,其中,4字节用于返回地址,16字节用于访问b的首地址。
2.返回值
8位或16位标量的函数返回值返回到W0中,32位标量的函数返回值返回到W1:W0中,而64位标量的函数返回值返回到W3:W2:W1:W0中。结果通过W0间接返回,W0由调用函数设置为包含结果值的地址。
3.调用函数时保存寄存器
对于一般的函数调用,编译器指定函数调用时保护寄存器W8~W15。寄存器W0~W7可用做暂存寄存器。对于中断函数,编译器指定保护所有必需的寄存器,即W0~W15和RCOUNT。
免责声明:以上内容源自网络,版权归原作者所有,如有侵犯您的原创版权请告知,我们将尽快删除相关内容。