主要是,程式寫好後用模擬器 (S51DEMO) 怎麼跑都OK,但一燒上 AT89S51 就不會動,hang 在 serial_init() 的位置。動用 /* 註解 */ 大法,終於找到問題出在一行 char str[] = {} 宣告:
__code unsigned char str[] = {
0x12, 0x33, 0xf0, 0x33, 0xf0, 0x12, // H
0x24, 0xf0, 0x24, // e
// ...
0x00 } ;
重點在 __code。如果不加的話,SDCC 會把它 compile 成 __DATA 很詭異地賦予初值,然後 AT89S51 就當在這了:
; kbd.c:168: unsigned char str[] = {
mov _main_str_1_1,#0x12
mov (_main_str_1_1 + 0x0001),#0x33
mov (_main_str_1_1 + 0x0002),#0xF0
mov (_main_str_1_1 + 0x0003),#0x33
mov (_main_str_1_1 + 0x0004),#0xF0
; ...
mov (_main_str_1_1 + 0x0024),#0x00
; 誰能告訴我為什麼 8051 執行過這邊就當掉 =.=
加了之後,就會是和其他字串常數一樣正常的 assembly code:
_main_str_1_1:
.db #0x12 ; 18
.db #0x33 ; 51
.db #0xF0 ; 240 ?
.db #0x33 ; 51
.db #0xF0 ; 240 ?
.db #0x12 ; 18
; ...
.db #0x00 ; 0