Keil下STM32的C语言与汇编语言混合编程

一、创建项目并进行调试

1、创建project
在这里插入图片描述

  • 输入project的名字,这里我输入的Func。
    在这里插入图片描述
  • 选择芯片类型,这里我选择的是STM32F103VE。(ps:图片是后面调试的时候在魔法棒页面截的,我做的时候忘记截图了。)
    在这里插入图片描述
  • 一些基本配置,按照图片所示选择就好。
    在这里插入图片描述

2、添加main.c和Func.s文件
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
3、编写代码

  • main.c:
  `# include<stdio.h>

extern void	Init_1(void);

int main(){
	
	Init_1();   
	
	return 0;
}

在这里插入图片描述

  • Func.s

	AREA	MY_FUNCTION,CODE,READONLY
	EXPORT 	Init_1  




Init_1

	MOV R1,#0     
	MOV R2,#0	  
	
LOOP	
	CMP R1,#10	  
	BHS LOOP_END  	 
	ADD R2,#1	  
	ADD R1,#1     
	B LOOP		  
	
LOOP_END
	NOP	
	
	END  

在这里插入图片描述

  • rebuild一下
    在这里插入图片描述
    在这里插入图片描述
    可以从最下面看到没有错误只有一个警告。

二、C语言调用汇编函数

1、无参调用

  • 调试前的一些参数设置
    点击魔法棒,选择Debug页面,勾选Use Simulator,将Dialog DLL下的属性改为DARMSTM.DLL,将Parameter下的属性改为-pSTM32F103VE在这里插入图片描述 - 进入调试界面在这里插入图片描述
  • 设置断点
    在这里插入图片描述
    在这里插入图片描述
  • 按F11进行单步调试观察寄存器的变化情况
    在这里插入图片描述
    这里看到首先会进入Inint_1函数,之后会为R1,R2寄存器赋初值为0。
    在这里插入图片描述
    在这里插入图片描述
    之后会进入LOOP函数,这里是将R1,R2寄存器中的值与10进行比较,如果小于10就加1,一直循环到等于10,该函数才end。
    在这里插入图片描述

2、有参调用

1、修改代码
main.c:

# include<stdio.h>

extern int Init_1(int x);    

int main(){
	
	int s = Init_1(17);
	printf("%d", s);   
	
	return 0;
	
}



在这里插入图片描述
Func.s:

	AREA	MY_FUNCTION,CODE,READONLY
	EXPORT 	Init_1  


Init_1
	ADD R0,#100     
	MOV PC,LR		
	
LOOP	
	CMP R1,#10	  
	BHS LOOP_END  	  
	ADD R2,#1	  
	ADD R1,#1     
	B LOOP		  
	
LOOP_END
	NOP	
	
	END  

在这里插入图片描述

  • rebiuld一下
    在这里插入图片描述
    在ARM中,子函数的参数值传递按顺序存放在r0,r1,r2,r3里,超过4个参数值传递放栈帧里。
    因此Init_1(17)传入的10放到了R0,由MOV PC,LR返回110(十六进制为0x75)。

2、进入调试
照例设置一下断点观察寄存器的变化,断点位置如下图所示。

  • R0返回117(十六进制为0x75):

在这里插入图片描述

  • main函数中s的值返回117(十六进制为0x75):

在这里插入图片描述

三、汇编函数调用C语言

1、改写函数
main.s:

# include<stdio.h>

extern void	Init_1(void);

int svt(void);

int main(){
	
	Init_1();

	return 0;
}

int svt(){
	return 17;
}

在这里插入图片描述
Func.s:

	AREA	MY_Function,CODE,READONLY
	EXPORT 	Init_1  
	IMPORT  svt    




Init_1

	MOV R1,#0     
	MOV R2,#0	  
	
LOOP	
	CMP R1,#10	  
	BHS LOOP_END  	  
	ADD R2,#1	  
	ADD R1,#1     
	BL svt  	  
	B LOOP		  
	
LOOP_END
	NOP	
	
	
	END  

在这里插入图片描述

  • rebuild一下

在这里插入图片描述

  • 设置断点,调试:

在这里插入图片描述
可发现,执行svt后,R0变为了0x11即17,即成功调用。

四、总结

本次实验是关于C语言和汇编语言的混合编程,实验中跟踪寄存器的变化,了解到函数运行过程中的参数变化与寄存器的使用情况。实验只是涵盖了一小部分,下面对寄存器的使用规则进行补充。

寄存器的使用规则:

  • 子程序间通过寄存器R0 ~ R3来传递参数。
  • 在子程序中,使用寄存器R4 ~ R11来保存局部变量。
  • 寄存器R12用于保存SP,在函数返回时使用该寄存器出栈,记作IP。
  • 寄存器R13用于数据栈指针,记作SP,寄存器SP在进入子程序时的值和退出寄存器时的值必须相等。
  • 寄存器R14称为链接寄存器,记作LR,它用于保存子程序的返回地址。
  • 寄存器R15是程序计数器,记作PC。

五、参考资料

STM32的C语言与汇编语言混合编程.

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值