1、关于在 KEIL C51 中嵌入汇编以及 C51 与 A51 间的相互调用如何在 KEIL C51(v6.21) 中调用汇编函数的一个示例 ycong_kuang有关 c51调用汇编的方法已经有很多帖子讲到,但是一般只讲要点,很少有对整个过程作详细描述,对于初学者是不够的,这里笔者通过一个简单例子对这个过程进行描述,希望能对初学者有所帮助。几年来,在这个论坛里笔者得到很多热心人指导,因此也希望藉此尽一点绵薄之力。在这个例子里,阐述了编写 c51程序调用汇编函数的一种方法,这个外部函数的入口参数是一个字符型变量和一个位变量,返回值是一个整型变量。例中,先用 c51写出这个函数的主体,然后用 SR
2、C控制指令编译产生 asm文件,进一步修改这个 asm文件就得到我们所要的汇编函数。该方法让编译器自动完成各种段的安排,提高了汇编程序的编写效率。step1. 按写普通 c51程序方法,建立工程,在里面导入 main.c文件和 CFUNC.c文件。相关文件如下:/main.c文件#include #define uchar unsigned char#define uint unsigned intextern uint AFUNC(uchar v_achr,bit v_bflag);void main()bit BFLAG;uchar mav_chr;uint mvintrslt;mav_c
3、hr=0xd4; BFLAG=1;mvintrslt=AFUNC(mav_chr,BFLAG);/CFUNC.c文件#define uchar unsigned char#define uint unsigned intuint AFUNC(uchar v_achr,bit v_bflag)uchar tmp_vchr;uint tp_vint;tmp_vchr=v_achr;tp_vint=(uint)v_bflag;return tmp_vchr+(tp_vint#define uchar unsigned char#define uint unsigned intextern uint
4、AFUNC(uchar v_achr,bit v_bflag);void main()bit BFLAG;uchar mav_chr;uint mvintrslt;mav_chr=0xd4; BFLAG=1;mvintrslt=AFUNC(mav_chr,BFLAG);/a51FUNC.c#define uchar unsigned char#define uint unsigned intextern uint CFUNC(uint);uint AFUNC(uchar v_achr,bit v_bflag) /c51写的汇编函数,最终要变成汇编代码uchar tmp_vchr;uint tp
5、_vint;tmp_vchr=v_achr;tp_vint=(uint)v_bflag;return CFUNC(tp_vint); /这里调用一个 c51函数/c51FUNC.c#define uchar unsigned char#define uint unsigned intuint CFUNC(uint v_int) /被汇编函数调用 c51函数return v_int2;第二步是按 89852帖子的 step2,3,4把用 c51写的(汇编)函数变成 a51文件(今天我试了一下step3可以不要)例程编译结果如下:; .a51func.SRC generated from: a51
6、func.cNAME A51FUNC?PR?_AFUNC?A51FUNC SEGMENT CODE?DT?_AFUNC?A51FUNC SEGMENT DATA OVERLAYABLE?BI?_AFUNC?A51FUNC SEGMENT BIT OVERLAYABLEEXTRN CODE (_CFUNC)PUBLIC ?_AFUNC?BITPUBLIC _AFUNCRSEG ?DT?_AFUNC?A51FUNC?_AFUNC?BYTE:tmp_vchr?042: DS 1RSEG ?BI?_AFUNC?A51FUNC?_AFUNC?BIT:v_bflag?041: DBIT 1; /a51FU
7、NC.c; #define uchar unsigned char; #define uint unsigned int; extern uint CFUNC(uint); uint AFUNC(uchar v_achr,bit v_bflag)RSEG ?PR?_AFUNC?A51FUNC_AFUNC: ;c51所写的函数产生的汇编代码从这里开始USING 0; SOURCE LINE # 8;- Variable v_achr?040 assigned to Register R7 -; ; SOURCE LINE # 9; uchar tmp_vchr; uint tp_vint; tm
8、p_vchr=v_achr; SOURCE LINE # 13MOV tmp_vchr?042,R7; tp_vint=(uint)v_bflag; SOURCE LINE # 14MOV C,v_bflag?041CLR AMOV R6,ARLC AMOV R7,A;- Variable tp_vint?043 assigned to Register R6/R7 -; 这里说明 R6,R7内容就是 tp_vint; return CFUNC(tp_vint); SOURCE LINE # 16LCALL _CFUNC ;这里调用了用 c51写的函数; ; SOURCE LINE # 17?
9、C0001:RET; END OF _AFUNCEND这个文件就是你的汇编函数所在文件,把函数里面的汇编代码修改成你所需的汇编函数就 ok了。建议参考 徐爱钧,彭秀华所写的单片机高级语言 C51windows环境编程与应用或马忠梅所写的单片机的 c语言应用程序设计有关混合语言编程有关章节.关于在 KEIL C51 中直接嵌入汇编。 Youth有时在 C51程序中需要嵌入一些汇编代码,这时当然可以用通常的作法:按照 C51 与汇编的接口写一个汇编函数,然后在 C51 程序中调用该函数。(此种方法可在论坛里搜索,以前有很多帖子讲到,不再重复)下面介绍直接嵌入汇编代码的方法:1、在 C 文件中要嵌入
10、汇编代码片以如下方式加入汇编代码:#pragma ASM; Assembler Code Here#pragma ENDASM2、在 Project 窗口中包含汇编代码的 C 文件上右键,选择“Options for .”,点击右边的“Generate Assembler SRC File”和“Assemble SRC File”,使检查框由灰色变成黑色(有效)状态;3、根据选择的编译模式,把相应的库文件(如 Small 模式时,是 KeilC51LibC51S.Lib)加入工程中, 该文件必须作为工程的最后文件;4、编译,即可生成目标代码。MOTO 的不太清楚,我这有 keilc51 的:看
11、了许多 keil c51 中嵌入汇编的帖子,根据自己的经验在 keil7.01 环境中总结如下:1、把“xx.c“加入工程中,右击“xx.c“选择“options for file“xx.c“ 选择“Generate Assembler SRC File”和“Assemble SRC File”打上黑勾有效;2、根据选择的编译模式,把相应的库文件象加“xx.c“一样加入工程中并放在“xx.c“下面,如smail 模式下选择“keilc51libc51s.lib“加入工程中,如果要进行浮点运算把“keilc51libc51fpl.lib“也加入工程中。3、在“xx.c“头文件中加入优化:比如#pragma OT(4,speed)4、在“xx.c“中加入汇编代码#pragma ASM;Assembler Code Here#pragma ENDASM5、编译生成 xx.hex注意:没有做第一步会有如下警告:asm/endasm requires src-control to be active没有做第二步会有如下警告:UNRESOLVED EXTERNAL SYMBOL;REFERENCE MADE TO UNRESOLVED EXTERNAL 等没有做第三步会有如下警告:UNDEFINED SYMBOL (PASS-2)