编译时asm中不可能的约束
impossible constraint in asm while compilation
在我的 Atmel ASF 项目中,我正在尝试构建以下内联 asm 代码。但是我在编译时遇到了不可能的约束。
编译器指向这一行__asm__ __volatile__
,
我错过了什么吗?
#define OUTPORT PORTD
#define OUTBIT 3 // PD.3
uint8_t rport ,rbits;
uint8_t *buf = message;
asm volatile( "in __tmp_reg__, __SREG__ \n\t" // 1 Save SREG for later
"cli \n\t" // 1 Clear interrupts
"in %[rport], %[port] \n\t" // 1 Move PORTB adress to rport
: //Outputs
[rport] "=&r" (rport)
: //Inputs
[port] "I" (_SFR_IO_ADDR(OUTPORT)) // Adress to port register, 6-bit positive constant
: //Clobber list (compiler must restore)
"r0" // This is __tmp_reg__
);
- 是什么破坏了这个构建?
- 请问是不是asm语法不对?我一直在关注 this manual
PORTD,在 ATxmega128A4U 上,地址为 0x0660,如其
datasheet,
第 62 页。因此 in
指令无法访问该端口。
您应该使用 lds
来代替约束
[port] "i" (_SFR_MEM_ADDR(OUTPORT))
注意小写 "i"。
附录:我刚刚尝试编译以下内容:
#include <avr/io.h>
void test(void)
{
uint8_t rport;
asm volatile(
"in __tmp_reg__, __SREG__ \n\t"
"cli \n\t"
"lds %[rport], %[port] \n\t"
: [rport] "=&r" (rport) // output
: [port] "i" (_SFR_MEM_ADDR(PORTD)) // input
: "r0" // clobber
);
}
使用带有选项 -mmcu=atxmega128a4u -c
的 avr-gcc 4.9.2 我得到了
生成的代码正确且没有警告,即使使用 -Wall -Wextra
.
"i" 约束是
documented
表示“立即整数操作数”,而 "I"
意思是
“常数大于-1,小于64”。
在我的 Atmel ASF 项目中,我正在尝试构建以下内联 asm 代码。但是我在编译时遇到了不可能的约束。
编译器指向这一行__asm__ __volatile__
,
我错过了什么吗?
#define OUTPORT PORTD
#define OUTBIT 3 // PD.3
uint8_t rport ,rbits;
uint8_t *buf = message;
asm volatile( "in __tmp_reg__, __SREG__ \n\t" // 1 Save SREG for later
"cli \n\t" // 1 Clear interrupts
"in %[rport], %[port] \n\t" // 1 Move PORTB adress to rport
: //Outputs
[rport] "=&r" (rport)
: //Inputs
[port] "I" (_SFR_IO_ADDR(OUTPORT)) // Adress to port register, 6-bit positive constant
: //Clobber list (compiler must restore)
"r0" // This is __tmp_reg__
);
- 是什么破坏了这个构建?
- 请问是不是asm语法不对?我一直在关注 this manual
PORTD,在 ATxmega128A4U 上,地址为 0x0660,如其
datasheet,
第 62 页。因此 in
指令无法访问该端口。
您应该使用 lds
来代替约束
[port] "i" (_SFR_MEM_ADDR(OUTPORT))
注意小写 "i"。
附录:我刚刚尝试编译以下内容:
#include <avr/io.h>
void test(void)
{
uint8_t rport;
asm volatile(
"in __tmp_reg__, __SREG__ \n\t"
"cli \n\t"
"lds %[rport], %[port] \n\t"
: [rport] "=&r" (rport) // output
: [port] "i" (_SFR_MEM_ADDR(PORTD)) // input
: "r0" // clobber
);
}
使用带有选项 -mmcu=atxmega128a4u -c
的 avr-gcc 4.9.2 我得到了
生成的代码正确且没有警告,即使使用 -Wall -Wextra
.
"i" 约束是 documented 表示“立即整数操作数”,而 "I" 意思是 “常数大于-1,小于64”。