PIC 汇编函数调用
我正在用 PIC18 汇编编写一个非常基本的程序。它要求我编写一个子程序来将两个 16 位数字相乘。这就是我现在所拥有的:
;***********************************************************************
; mul_16bit: subroutine that multiplies two 16 bit numbers stored in
; addresses mul_16ptr1, mul_16ptr1+1 and mul_16ptr2,mul_16ptr2+1 and
; returns the 32-bit result in addresses mul_16res1 to mul_16res1+3
;***********************************************************************
mul_16bit:
movf mul_16ptr2, W ;multiply the lower bytes
mulwf mul_16ptr1, W
movff PRODH, mul_16res+1
movff PRODL, mul_16res
movf mul_16ptr2+1, W ;multiply upper bytes
mulwf mul_16ptr1+1, W
movff PRODH, mul_16res+3
movff PRODL, mul_16res+2
movf mul_16ptr2, W ;multiply lower byte of num2
mulwf mul_16ptr1+1, W ; and upper byte of num1
movf PRODL, W
addwf mul_16res+1, F
movf PRODH, W
addwfc mul_16res+2, F
movlw 0 ; add carry
addwfc mul_16res+3, F
movf mul_16ptr2+1, W ;multiply upper byte
;of num1 and lower
mulwf mul_16ptr1, W ; byte of num2
movf PRODL, W ;add the result to mul_16res
addwf mul_16res+1, F ;...
movf PRODH, W ;...
addwfc mul_16res+2, F ;...
movlw 0 ; add carry
addwfc mul_16res+3, F
return
我现在编写的方式是将第一个注释中提到的寄存器中存储的数字相乘,并将它们存储在注释中的 4 个寄存器中。如果我只需要进行一次或两次乘法,这很有效,即我可以这样说:
mul_16ptr1 set 0x45
mul_16ptr2 set 0x47
mul_16res set 0x50
call mul_16bit
将 0x45
和 0x47
相乘并将其存储在 0x50 中
。问题是当我需要对不同的数据多次调用它时,因为汇编器不会让我“设置”任何指针两次。我尝试过使用间接访问(即使用 LFSR1、LFSR2 和 LFSR0 来存储被乘数和结果),但后来我陷入了 POSTINC0 等的混乱之中。有没有办法让这个函数调用变得更好?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
PIC18 下的函数通常使用专用输入变量,例如 RegA、RegB 和 RegR。
所以有声明:
调用suchlike函数看起来像:
Functions under PIC18 normaly use dedicated input variables such as RegA, RegB and RegR.
So there are declarated:
Calling suchlike function looks like:
是的,PIC 汇编语言使许多事情变得不必要地复杂。
我假设您将这样做作为学习体验的一部分 - 否则您将使用 基本数学函数库,例如 Roger Froud 或 Fr. 的函数库。 Thomas McGahee,或者也许切换到一种更高级的语言,其中上述所有语言都可以用“*”替换(BASIC、C、Pyastra、JAL、Forth 等)。
GJ 演示的调用约定非常常见,特别是在从 PIC16 移植的代码中,该代码只有一个 FSR 寄存器并且没有“PLUSW”寄存器。
由于 PIC18 具有“PLUSWx”寄存器,因此可以使用各种更好的调用约定。
有没有办法稍微调整一下以获得 R.里斯推荐?
Yes, PIC assembly language makes many things unnecessarily complicated.
I'm assuming you are doing this as part of a learning experience -- otherwise you would either use a basic math function library such as the one by Roger Froud or Fr. Thomas McGahee, or perhaps switch to a higher-level language where all of the above can be replaced by "*" (BASIC, C, Pyastra, JAL, Forth, etc.).
The calling convention GJ demonstrates is extremely common, especially in code ported from PIC16 which only had one FSR register and no "PLUSW" registers.
Since the PIC18 has the "PLUSWx" registers, it's possible to use a variety of nicer calling conventions.
Is there a way to tweak this a little more to get the "re-entrant" code that R. Reese recommends?
您能否安排一些事情,以便它们在 FSR0-FSR2 指向您的操作数和结果寄存器时表现得更加明智? EG
LFSR 比手动移动大量数据更便宜。
Can you arrange things so that they'll behave sensibly with FSR0-FSR2 pointing at your operand and result registers? E.G.
LFSR is cheaper than manually moving around large amounts of data.