This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] CCS/LAUNCHXL-F2.8377万S:汇编器函数返回

Guru**** 2032800 points
请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/microcontrollers/c2000-microcontrollers-group/c2000/f/c2000-microcontrollers-forum/573787/ccs-launchxl-f28377s-assembler-function-return

部件号:LAUNCHXL-F2.8377万S

工具/软件:Code Composer Studio

您好,

我想从汇编器函数返回两个无符号int值。 这是否可行?

如果可能,第二个无符号int值存储在何处?(第一个存储在AL寄存器中)  

 已参考SPRU514L:

6.被调用的函数返回一个值。 它按照下列惯例存入一个登记册:

16位整数值AL
32位整数值符合
64位整数值ACC/P
32位指针XAR4
结构参考XAR6

//希望类似这样的内容可以返回两个值

//?? 它的外观如何

extern unsigned int unexfunc( unsigned int a, unsigned int b); 
asmvalue = asmfunc (99.95万); 

如果无法返回两个值,请考虑 以下问题。

我编写了一个汇编器函数,其中保存了两个整数值。 一个在XAR4寄存器中,一个在XAR5寄存器中。

如何访问我的c代码中的这些寄存器?

如果我无法访问这些寄存器,我可以在哪里保存值并获取对其的访问权限?

.global _asmfunc

_asmfunc:
	ADDB SP,#3;
	MOV *-SP[1],AL ;| TBPRD
	MOV *-SP[2],AH ;| TBPRDHR
;以下计算对于问题
	UI16TOF32 R2H,*-SP[1]
	UI16TOF32 R3H,*-SP[2]

	MPYF32 R4H,0.5 ,R2H不重要; R4H = 0.5 * R2H | OPTPRD = R4H
	NOP
	F32TOUI16 R5H,R4H;| RH5 ist Uint (OH * TBPRD)
	NOP
	NOP MOV32
	XAR1,R5H
	UI16TOF32 R5H,R5H;| R1H ist float (OT * TBPRD,N3H,N3H,ROP) 0.5
	
	
	
	
	
	R5H = 0.5 * R3H | OD* TBPRDHR
	NOP
	NOP
	MPYF32 R1H,R1H,6.5536万.0 ;|temp*6.5536万
	NOP
	
	NOP ADDF32 R1H,R1H,R7H;TEMP*6.5536万+OD*TBPRDHROP
	
	NOP NOP
	NOP NOP MOV32
	XAR2,R1H
	NOP;任何指令 
;保存值 MOV32 XAR4, R0H;将值保存在XAR4 MOV32 XAR5, R1H中;将值保存在XAR5中
LRETR 

// C code
extern unmexfunc( unsigned int a, unsigned int b);

//
asmfunc (99.95万);
//如何访问XAR4或XAR5?
// unsigned int value_a;
// unsigned int value_B;
// value_a = XAR4
// value_B = XAR5 

我注意到:

为TMS320C28x DSP创建C调用汇编函数的简便方法

TMS320C28x优化C C++编译器

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好,Jonas:

    函数不能返回两个值。 C公约不允许这样做。你可以做两件事之一

    1.制作结构的两个INTS部分,然后传递结构并将其返回到函数-这将通过XAR6寄存器完成

    2.通过引用传递:将指向两个输入的指针作为汇编函数的参数传递,指针将被分配到XAR4和XAR5。您可以使用间接寻址模式来取消引用(*XARn,请参见SPRU430,第5.6 节)

    extern unsigned int unmesfunc( unsigned int *a, unsigned int *b);
    uint16_t a =999,b =500;
    asmvalue = asmfunc(&A,&b);
    

    然后,您可以读取a和b的值(并转换为float),如下所示

    UI16TOF32 R2H,* XAR4
    UI16TOF32 R3H,* XAR5 

    然后在计算结束后,将结果存储为  

    MOV32 *XAR4, R0H;存储值为XAR4
    MOV32 *XAR5, R1H;存储值为XAR5 

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    您好,Vishal,

    我尝试了您的第二个解决方案。 对于*XAR4,它工作正常,但是对于*XAR5,我总是得到0,尽管我计算了另一个值(例如3.32万)。 热化是应该的样子。 我要在*XAR5中存储值(0-6.5535万中的未分配值。

    extern asmfunctest( unsigned int *a, unsigned int *b);
    unsigned int a=999,b=500;




    UI16TOF32 R2H,* XAR4;
    UI16TOF32 R3H,* XAR5;
    ;Duty*TBPRD
    MPYF32 R4H,0.5 ,R2H;R4H = 0.5 * R2H |工作* TBPRD = R4H
    无操作
    F32TOUI16 R5H,R4H;| RH5 ist Uint (Duty * TBPRD)
    无操作
    无操作
    MOV32 * XAR4,R5H;|第一次节省->好!!!!!!
    UI16TOF32 R5H,R5H;| R1H ist float mit dem UINT16 (Duty * TBPRD)
    无操作
    无操作
    SUBF32 R1H,R4H,R5H;=温度
    无操作
    无操作
    MPYF32 R7H,0.5 ,R3H;R5H = 0.5 * R3H |工作* TBPRDHR
    无操作
    无操作
    MPYF32 R1H,R1H,6.5536万.0 ;|temp*6.5536万
    无操作
    无操作
    ADDF32 R1H,R1H,R7H;temp*6.5536万+工作*TBPRDHR
    无操作
    无操作
    F32TOUI16 R5H,R1H;
    无操作
    无操作
    MOV32 *XAR5, R5H ;|保存时始终为0,尽管RH5不是0!!!!!!
    无操作
    无操作
    LRETR


    为什么*XAR5没有得到正确的值? XAR5的范围是否为无符号int (0-6.5535万)或int (-3.2768万-32767)?3.2767万?
    孔子是因为* XAR4似乎是正确的。
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    我刚刚意识到它们是16位类型的指针,所以不要使用MOV32来写入位置,使用MOV16

    MOV16 * XAR5,R5H

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    您好,Vishal,

    MOV16 * XAR5,R5H
    由于非法的间接membadress而无法正常工作。
    您知道为什么*XAR4值正确而*XAR5不正确吗?

    此致,

    Jonas
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    [报价用户="Jonas Hemmer]MOV16 * XAR5,R5H  

    由于非法的间接membadress而无法正常工作。

    这很奇怪。 它应该起作用-尝试MOV16 *+XAR5[0],R5H。 您还应该为早期写入*XAR4执行16位移动。

    Jonas Hemmer 说:
    您知道* XAR4值正确而* XAR5不正确的原因吗?[/QUOT]

    您是如何传递这些指示的? XAR5指向什么位置? XAR4很可能指向一个偶数地址,XAR5指向下一个连续的奇数地址。 当您尝试对奇数地址执行32位写入时,它将自动写入到以前的偶数地址,因此您可能只会覆盖*XAR4,而高位字仍为0。 例如,如果XAR4指向0x8000,XAR5指向0x8001,那么让我们假设R5H是1万 (第一个计算),1.5万 (第二个计算)。

    MOV32 *XAR4,R5H;将1万写入地址0x8000,0x8001 =0 -记住这是32位写入

    ....

    MOV32 *XAR5, R5H;您尝试将1.5万写入0x8001,但32位写入会自动对齐,因此您最终将1.5万写入0x8000地址,将0写入0x8001

    这可能是您在*XAR5时始终看到0的原因

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
    您好,Vishal,
    我通过以下方式传递指针:
    asmfunc_PWM_CMPA (&a,&b);

    XAR4指向0x0000A9C7
    XAR5指向0x0000A9C8

    它适用于:
    MOV16 *+ XAR5[0],R5H

    我还有最后两个问题:
    是否可以调试(查看值),例如*-SP[3]或*-SP[3]。 还是查看堆栈?
    为什么*+XAR5[0]而不是*XAR5[0]?

    非常感谢,

    Jonas
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    Jonas Hemmer 说:
    是否可以调试(查看值),例如*-SP[3]或*-SP[3]。 或者查看堆栈?[/QUOT]

    是的。 在“查看”->“注册”下,您可以看到SP的当前值。 然后在SP设置的地址打开内存浏览器(View-> memory browser);这是堆栈的顶部。 例如,如果SP = 0x8003,*-SP[3]将为位置0x8000

    Jonas Hemmer 说:
    为什么*+XAR5[0]不是*XAR5[0][/QUOT]

    *XAR5[0]语法不正确;*+XARn[3位]语法正确,但*XAR5也应该起作用;它等同于*+XAR5[0]-它可能是汇编程序错误