background image

printf 函数是调用 putchar 函数,从串口发送字符串的,可以从 keil 反汇编看出这一点。在
C51 程序中 printf 的位置设一个断点,运行到断点处后,再一步步执行程序,可以看出,
跳转到 PRINTF 执行。
 

 
PRINTF 有很长一大段汇编,一步步执行。
 

 
运行到 PUTCHAR 处,这个就是串口发送字符串的函数。
 

 

可以看到有这么一句 C:0521    JNB TI0,C:0521”
第一次运行到这的时候,如果前面没有 TI0=1,那么程序指针 PC 就一直在这条语句上判
断,也就死在这里等待。
所以要使用 printf,开头必须要先置 TI0(传统 51 为 TI)为 1。那么发送了第一个字节后,发
送中断标志位 TI0 自动置 1

,再回到 C:0521    JNB 

TI0,C:0521”,接着发送第二个字节。
 

 
因为 TI0 为中断标志位,但如果程序使用了 UAR0 中断,那么在 printf 函数执行过程中就
会不断调用中断函数(UART0_Interrupt),所以每次使用 printf 之前要先禁止串口中断
(ES0=0)。
 
3.      由上面可以看到使用 printf 非常麻烦,其实可以用 sprintf 代替 printf,只要在前面先
定义一个存放字符串的数组。
……
unsigned char PrintChar[15]
……
SFRPAGE_SAVE = SFRPAGE;   //C8051F120 特殊功能寄存器分页
SFRPAGE = UART0_PAGE;      //传统 51 单片机没有 SFR 分页
sprintf (PrintChar,"\nTest complete.");
send_string_com(s, 15);
SFRPAGE = SFRPAGE_SAVE;
 
 
上面总结得都是经验教训啊,在这个小小的 bug 上浪费了几天,记录下来,希望对大家
有点帮助。
 
4.      当使用 printf 循环打印时要注意,下面程序是有问题的
   pchar = XRAM_START;