單片機是靠程序來運行的,程序是通過編程器(本站的STC編程實驗一體板也可以)燒寫進單片機芯片中去的,我們編寫不同的燒寫文件,單片機就會按照我們的意愿來完成不同的功能,但是如何寫程序和獲得燒寫文件,并且燒寫成功,這一個部分卻是很多教科書上忽略的,即使有介紹也可能因為他們介紹的編程器或者匯編軟件我們無法獲得,而使初學者無所適從。站長在自學單片機的過程中也花了不少精力才搞懂這一個部分。
第一步,我們用WINDOWS自帶記事本程序來寫匯編語言程序,例如,在D盤下新建一個001.TXT文檔

然后將程序寫入,比如將下面的一個LED跑馬燈的程序部分用“復制”“粘貼”命令將加粗文字的部分復制到001.TXT文檔中,然后保存。
ORG 0000H START:MOV P1,#01111111B LCALL DELAY MOV P1,#10111111B LCALL DELAY MOV P1,#11011111B LCALL DELAY MOV P1,#11101111B LCALL DELAY MOV P1,#11110111B LCALL DELAY MOV P1,#11111011B LCALL DELAY MOV P1,#11111101B LCALL DELAY MOV P1,#11111110B LCALL DELAY MOV P1,#11111111B;完成第一次LED跳燈循環 AJMP START;反復循環
DELAY:MOV R4,#02H;延時子程序,12M晶振延時約1秒 L3: MOV R2 ,#0FAH L1: MOV R3 ,#0FAH L2: DJNZ R3 ,L2 DJNZ R2 ,L1 DJNZ R4 ,L3 RET
END
第二步,我們需要使用一個匯編軟件:宏匯編軟件MASM51 點擊這里可以下載這個軟件 軟件下載成功后經過ZIP解壓后獲得MAS51.EXE和MAS51.OVI兩個文件,我們將它們放到D盤根目錄下,然后雙擊MAS51.EXE文件,進入DOS界面的匯編程序,如下圖:

我們通過鍵盤敲入asm51 d:\001.txt后回車,如果出現00 Errors (0000)的話,表示匯編沒有任何錯誤,成功了!
如果出現別的文字提示,說明匯編有錯誤,您可以根據提示的內容找出錯誤的語句,一一改正,再重新匯編,直到出現00 Errors (0000)。這時在D盤的根目錄下自動會產生001.HEX的編程器燒寫文件,這就是最終寫入單片機的文件。
在學習單片機的過程中您可以在理解的基礎上修改我網站的程序范例,然后:軟件匯編--編程器燒寫--AT89C51實驗板驗證,這樣可以快速掌握單片機技術。
編寫匯編語言常見錯誤分析:
一、 MAS51匯編軟件匯編失敗原因分析:
單片機的匯編語言編寫時要注意一定的語法,詳細介紹可以參考相關參考書,語法錯誤匯會造成匯編失敗,常見的匯編錯誤如下:
1.標號重復 常見于復制、粘貼程序時忘記修改標號,造成出現多個相同的標號,標號是不允許重復的。 2.標點符號以全角方式輸入 MAS51程序要求標點符號為半角方式,否則匯編失敗?梢栽谳斎:,;時切換到半角方式,或者在大寫狀態輸入標點符號,這也是很容易犯而且不容易發覺的錯誤。 3.注釋太長 有時為了以后讀懂程序,寫了很長的注釋,站長發現超過20個漢子時也會造成匯編失敗,解決辦法可以將太長的注釋分成多個注釋。 4.數值#FFH 前遺漏0,根據要求應該在a~f前加0,寫成#0FFH 5.字母O和數字0搞混 有時候這兩個字看上去完全相同,要注意哦~~ 6.標號后邊遺漏":" 7.標號使用了特殊字符,比如:T1、T2、A、B這些字符有特定的含義,不允許用于標號。 8.AJMP跳轉超過2K地址,AJMP屬于短跳轉命令,有2K地址范圍的限制。 9.JB P3.2,EXIT跳轉超過-128~127個地址范圍。這個是最容易出現的錯誤!你有可能程序剛才還能匯編編譯成功,你加了一段程序后程序就提示出錯了,你可以把 JB P3.2,EXIT 轉換成 JNB P3.2,UUU AJMP EXIT UUU: 10.字母I和數字1混淆,冒失鬼的常見問題。 11.創造發明不存在的匯編語言指令,在編寫程序程序的過程中可不歡迎這種創新,這種指令匯編程序不支持,芯片也不認可。 12.符號“:”“;”最好用半角書寫。
使用匯編軟件常見問題解答:
1.如果匯編軟件出現** Unrecongnized Command **提示字樣說明是匯編命令輸入錯誤。正確的匯編命令是asm51 d:\001.txt 注意asm51后面要加空格。
2.如果匯編軟件出現**Dos File I/O error **提示字樣說明是匯編文件的路徑出錯。第一要注意MASM51軟件的安裝路徑中不能出現中文名稱,例如匯編軟件安裝在D:\單片機\下面,第二要匯編的文件的路徑中也不能出現中文名稱,例如D:\單片機\001.TXT。當文件后綴不是asm時,后綴不能省略。
二、程序出錯:
1.寄存器重復調用 比如主程序中設定了R4=5,表示主程序循環執行5次,而其中的一個延時子程序又用到R4,使R4的值發生紊亂,造成程序無法正常執行。 2.硬件不熟悉 單片機一般采用下拉輸出,往往端口輸出0驅動外設工作,和常見的正邏輯相反,容易搞錯。
以上是站長學單片機時發生的不止一次的錯誤!!
編寫匯編語言的忠告:
要養成良好的程序書寫習慣,比如標號對齊、參數對齊、注釋對齊,這樣看起來賞心悅目,也不容易出錯。標號最好采用有意義的英文,這樣比較直觀,注釋盡量詳細準確,便于以后讀懂,而且有利于其它程序中作為子程序模塊的調用。還有要注意典型程序模塊的積累,再復雜的程序也是由一個個小程序模塊組成的,在初學階段可以對典型程序比如:延時子程序、查表子程序、按鍵消抖子程序等編寫實踐一次,這樣印象深刻,便于以后引用。
常見匯編語言指令解釋:
1.Rn 表示R0~R7中的一個 2.#data 表示8位的數值 00H~FFH 3.direct 表示8位的地址 00H~FFH 4.@Ri 表示寄存器間接尋址 只能是R0或者R1 5.@DPTR 表示數據指針間接尋址 6.bit 表示位地址 7.$ 表示當前地址
寄存器尋址 MOV A,R1 將R1中的數值賦予A 直接尋址 MOV A,3AH 將地址3AH中的數值賦予A 立即尋址 MOV A,#3AH 將3AH數值賦予A 寄存器間址 MOV A,@R0 將 R0中地址的數值賦予A 變址尋址 MOVC A,@A+DPTR 以A中的數值為地址偏移量進行查表 相對尋址 AJMP MATN 跳轉到行號為MATNC處 位尋址 MOV C,7FH 將位地址7FH的數值賦予C
MOV A,#3AH 數據傳輸、賦值命令 PUSH direct 將direct為地址的數值壓入堆棧中 POP direct 將direct為地址的數值彈出堆棧 XCH A,direct 將direct中的數值與A進行交換 ADD A,direct 將direct中的數值與 INC direct 將direct中的數值加1 SUBB A,direct 將A中的數值減去direct中的數值和Cy值,并保存在A中,如果想使用不帶Cy減法,可以在運算前對Cy清零 CLR C DEC direct 將direct中的數值減1 DA A 用于對BCD碼加減法后進行10進制調整 MUL AB 將A和B相乘,并把高八位放在B中,低八位放在A中 DIV AB 將A和B相除,并把商放在A中,余數放在B中 ANL A,direct 將A與direct中的數值進行與運算,結果保留在A中(與運算規律:有0出0,全1出1) ORL A,direct 將A與direct中的數值進行或運算,結果保留在A中(或運算規律:有1出1,全0出0) XRL A,direct 將A與direct中的數值進行異或運算,結果保留在A中(異或運算規律:全0出0,全1出0,01、10出1) CRL A 對A清零 CPL A 對A取反 RL A 對A中數右移 RR A 對A中數左移 RLC A 對A中數帶Cy右移 RRC A 對A中數帶Cy左移 SWAP A 對A中的數高4位低4位互相交換 LJMP 長跳轉指令,64K地址范圍 AJMP 短跳轉指令,2K地址范圍 JZ rel 如果A為0就跳轉到rel行號處 JNZ rel 如果A不為0就跳轉到rel行號處 CJNE A,#data,rel 如果A不等于data就跳轉到rel行號處 DJNZ R1,rel 如果R1減1后不為0就跳轉到rel行號處 ACALL rel 調用rel子程序,2K地址以內 LCALL rel 調用rel子程序,64K地址以內 RET 子程序返回指令 RETI 中斷程序返回指令 NOP 空操作指令 MOV C,bit 將位地址bit中的值賦予C CRL bit 將bit位地址清0 SETB bit 將bit位地址置1 CPL bit 將bit位地址取反 ANL C,bit 將地址bit中的值和C做與運算,結果存放在C中 ORL C,bit 將地址bit中的值和C做或運算,結果存放在C中 JC rel 如果Cy為1,就跳轉到rel行號處 JNC rel 如果Cy為0,就跳轉到rel行號處
|