用arm7做流水燈的設計,用arm7做一個流水燈的設計。

時間 2021-10-15 00:23:12

1樓:匿名使用者

從原理圖可以看出,如果我們想讓接在p1.0口的led1亮起來,那麼我們只要把p1.0口的電平變為低電平就可以了;相反,如果要接在p1.

0口的led1熄滅,就要把p1.0口的電平變為高電平就可以;同理,接在p1.1~p1.

7口的其他7個led的點亮和熄滅方法方法同led1。因此,要實現流水燈功能,我們只要將led2~led8依次點亮、熄滅,依始類推,8只led變會一亮一暗的做流水燈了。

實現8個led流水燈程式用中文表示為:p1.0低、延時、p1.

0高、p1.1低、延時、p1.1高、p1.

2低、延時、p1.2高、p1.3低、延時、p1.

3高、p1.4低、延時、p1.4高、p1.

5低、延時、p1.5高、p1.6低、延時、p1.

6高、p1.7低、延時、p1.7高、返回到開始、程式結束。

從上面中文表示看來實現微控制器流水燈很簡單,但是我們不能說p1.0你變低,它就變低了。因為微控制器聽不懂我們的漢語的,只能接受二進位制的「1、0......

」機器**。我們又怎樣來使微控制器按我們的意思去工作呢?為了讓微控制器工作,只能將程式寫為二進位制**交給其執行;早期微控制器開發人員就是使用人工編寫的二進位制**交給微控制器去工作的。

今天,我們不必用煩人的二進位制去編寫程式,完全可以將我們容易理解的「程式語言」通過「翻譯」軟體「翻譯」成微控制器所需的二進位制**,然後交給微控制器去執行。這裡的「程式語言」目前主要有組合語言和c語言兩種;在這裡我們所說的「翻譯」軟體,同行們都叫它為「編譯器」,將「程式語言」通過編譯器產生微控制器的二進位制**的過程叫編譯。前面說到,要想使led1變亮,只需將對應的微控制器引腳電平變為低電平就可以了。

現在讓我們將上面提到的8只led流水燈實驗寫為組合語言程式。

實現8個led流水燈組合語言源程式 liu01.asm

;----- 主程式開始 -----

start: clr   p1.0       ;p1.0輸出低電平,使led1點亮

acall  delay      ;呼叫延時子程式

setb  p1.0       ;p1.0輸出高電平,使led1熄滅

clr   p1.1       ;p1.1輸出低電平,使led2點亮

acall  delay      ;呼叫延時子程式

setb  p1.1       ;p1.1輸出高電平,使led2熄滅

clr   p1.2       ;p1.2輸出低電平,使led3點亮

acall  delay      ;呼叫延時子程式

setb  p1.2       ;p1.2輸出高電平,使led3熄滅

clr   p1.3       ;p1.3輸出低電平,使led4點亮

acall  delay      ;呼叫延時子程式

setb  p1.3       ;p1.3輸出高電平,使led4熄滅

clr   p1.4       ;p1.4輸出低電平,使led5點亮

acall  delay      ;呼叫延時子程式

setb  p1.4       ;p1.4輸出高電平,使led5熄滅

clr   p1.5       ;p1.5輸出低電平,使led6點亮

acall  delay      ;呼叫延時子程式

setb  p1.5       ;p1.5輸出高電平,使led6熄滅

clr   p1.6       ;p1.6輸出低電平,使led7點亮

acall  delay      ;呼叫延時子程式

setb  p1.6       ;p1.6輸出高電平,使led7熄滅

clr   p1.7       ;p1.7輸出低電平,使led8點亮

acall  delay      ;呼叫延時子程式

setb  p1.7       ;p1.7輸出高電平,使led8熄滅

acall  delay      ;呼叫延時子程式

ajmp  start      ;8個led流了一遍後返回到標號start處再迴圈

;----- 延時子程式 -----

delay: mov   r0,#255     ;延時一段時間

d1:   mov   r1,#255

djnz  r1,$

djnz  r0,d1

ret            ;子程式返回

end           ;程式結束

在上面主程式中用到了五條組合語言指令:clr、acall、setb、ljmp、end。

clr: 是將其後面指定的位清為0,程式中使對應埠輸出低電平

acall:是子程式呼叫指令,程式中呼叫了delay延時子程式

setb:是將其後面指定的位置成1,程式中使對應埠輸出高電平

ajmp:是無條件跳轉指令,意思是:跳轉到指定的標號處繼續執行

end: 是程式結束的偽指令,意思是告訴編譯器,程式到此結束。偽指令只告訴編譯器此程式到此有何要求或條件,它不參與和影響程式的執行。

在上面源程式中"acall  delay"指令的作用是呼叫delay延時子程式。為什麼要使用這指令呢?如果不用該指令能夠實現"流水"效果嗎?

答案是肯定的,一定要用該指令才能看到我們需要的"流水"效果。如果不用該指令,則由於8個led發光與熄滅的時間都很短,我們肉眼無法看到led的熄滅與點亮,憑我們肉眼看到的是led1~led8都同時亮(半亮),而看不到「流水」效果的!注:

初學者可以將上面源程式中所有"acall  delay"指令行刪除後再編譯後燒寫到微控制器進行驗證一下。

產生這種現象主要是因為微控制器執行每條指令的時間很短,我們知道實驗板上微控制器的時鐘高達11.0592mhz,在這個時鐘訊號(即晶體振盪訊號)下,一個「機器週期」僅大約1.08us(微秒)。

本程式中我們用到的setb p.x和clr p.x均屬於單週期指令,也就是說,執行一句 setb p.

x 用時僅1.08us(微秒),clr p.x 也是1.

08us(微秒);也就是點亮和熄滅時間都為1.08us(微秒),在如此高速的流水速度下,8個led發光與熄滅的時間都很短,當然憑我們的肉眼看不到「流水」效果了!

這裡需要說明的是,按彙編語法要求,所編制的程式(下稱源程式)之格式和書寫要求必須依下列原則:

2、源程式的副檔名應是 *.asm;

3、一行只能寫一條語句,以回車作為本句的結束,每一語句行長度應少於80個字元(即40個漢字)。

4、每行的格式應為:標號: 命令 引數 ;註釋 。

即一行由四部份組成,各部份的順序不能搞錯,依實際要求可以預設其中的一部份或幾部份,甚至全部省去,即空白行。需要使用標號時標號後面必須有「:」(冒號),而命令語句和引數之間必須用空格分開,如果命令有多個引數,則引數與引數之間必須用「,」(逗號)分開,需要註釋時註釋前必須用「;」(分號),「;」後面的語句可以寫任何字元,包括漢字用於解釋前面的彙編語句,它將不參與彙編,不生成**。

由於彙編程式對我們還不直觀,所以在編寫源程式時,應當養成多寫註釋的習慣,這樣有助於今後源程式的閱讀和維護。

標號是標誌程式中某一行的符號名,編譯後標號的數值就是標號所在行**的地址。在巨集彙編asm51中標號的長度不受限制,但標號中不能包含『:'或其它的一些特殊符號,也不能用漢字,可以用數字作標號,但必須用字母開頭。

當標號作引數用(如標號作轉移地址),在命令後面出現時,必須捨去『:'(如上面程式中的 ajmp start中的start是不能再有:)。

每行只能有一個標號,一個標號只能用在一處,如果有兩行用了同一個標號,則彙編時就會出錯。由於標號的長度沒有限制,可以用有意義的英文或漢語拼音來說明行,使源程式讀起來更方便。在源程式中的字母不區分大小寫,也就是說 start 和 start 是一樣的,請不要用大小寫方式去區分不同的標號。

好啦!我們知道了組合語言程式的規則,現在就動手編輯源程式吧。馬上啟動keil微控制器整合開發環境,建立新工程liu01.

uv2,將上面的源程式liu01.asm匯入到工程中,設定好keil工程的編譯引數,編譯得到hex格式的目標檔案liu01.hex,用 isp程式設計器 將目標檔案liu01.

hex燒寫到at89s51微控制器中,接下來就是將燒寫好的at89s51從程式設計器上取下,放到「 s51增強型微控制器實驗板 」上通電,我們就看到了led1~led8的"流水"效果了。

到此,我們做的流水燈已成功,工作原理也清楚啦,若你完全掌握了上面程式,那麼你就可以將「流水燈」的流向改變一下,可以將從"左向右流"改為從"右向左流",也可以改為"兩邊向內流"、"內部向外流"......,我想你一定能用前面學到的方法實現這些功能。可能有些高手說,前面的程式設計方法是最最笨的!

不錯!但初學微控制器初期可以不必講究語言的簡練,只要能實現預先要求就好,最主要的是學好基本指令(111條)的用法,清楚各個指令的功能,這是初學者要知道的。那麼還有更好的程式設計思路嗎?

當然有!請跟隨站長繼續學習下面的內容。

在前面學習的程式中我們讓led流水是去逐個控制p1埠的每個位來實現的,因此程式顯得有點複雜,下面我們就採用新的思路來程式設計。新的程式設計思路如下:我們在程式一開始就給p1口送一個數,這個數本身就讓p1.

0先低,其他位為高,然後讓這個資料向高位移動不就實現「流水」效果啦?的確如此!8051指令中沒有讓p1資料移動的指令,但有對累加器acc中資料左移或右移的指令,acc在指令中常寫為a,累加器a資料左移指令為"rl a",累加器資料右移指令為"rr a",累加器在資料傳輸和資料處理過程中作用十分重要,累加器acc為8位。

他可與片內所有單位元組暫存器交換資料,實際上p1和其他埠在微控制器中也是一個暫存器。這樣我們可以將需移動的資料先放到acc中,讓其移動,然後將acc移動後的資料再轉送到p1口,這樣同樣可以實現「流水」效果。下面程式就是採用新的程式設計思路源程式liu02.

asm。

實現8個led流水燈組合語言程式 liu02.asm

;----- 主程式開始 -----

start: mov   acc,#0feh   ;acc中先裝入led1亮的資料(二進位制的11111110)

mov   p1,acc     ;將acc的資料送p1口

mov   r0,#7     ;將資料再移動7次就完成一個8位流水過程

loop:  rl   a       ;將acc中的資料左移一位

mov   p1,a      ;把acc移動過的資料送p1口顯示

acall  delay     ;呼叫延時子程式

djnz  r0,loop    ;沒有移動夠7次繼續移動

ajmp  start     ;移動完7次後跳到開始重來,以達到迴圈流動效果

;----- 延時子程式 -----

delay: mov   r0,#255    ;延時一段時間

d1:   mov   r1,#255

djnz  r1,$

djnz  r0,d1

ret          ;子程式返回

end          ;程式結束

接下來,我們將上述程式編譯,並燒寫到實驗晶片中,放到實驗板上可以看到程式的"流水"效果是一樣的,但源程式看起來更加簡潔,直觀。其實8051微控制器有111條指令,有的指令常用,有的指令不常用,只要遵守語法規則,你可以用這些指令「組合」成你想象到的任何程式。當然,有時一條指令可以替代很多條指令,這樣會使程式簡潔,程式**減少,在編寫較大程式時可以讓程式儲存器放得下你需要的**,這也是微控制器高手所追求的「程式簡潔高效」。

當然,初學者不必刻意去追求程式的簡潔高效,主要是要全面地掌握各種指令的應用,只要你對基本指令都熟悉了,那麼你也就可以編出簡潔高效的程式了,不過這程式設計「內功」是需要你勤學苦練,日積月累的練習、實驗才能達到的哦!馬上拿起你的實驗板,現在就開始動手吧:)

上面我們學習的兩個程式都是比較簡單的流水燈程式,"流水"花樣只能實現單一的"從左到右"流方式。下面介紹一個實用的流水燈程式,程式能夠實現任意方式流水,而且流水花樣無限,只要更改流水花樣資料表的流水資料就可以隨意新增或改變流水花樣,真正實現隨心所欲的流水。只要將下面的程式稍稍修改一下,通過s51增強型微控制器實驗板的擴充套件介面連線到霓虹燈高壓驅動介面板就可以驅動真正的霓虹燈了。

實用的查表方式多功能流水燈程式 liu03.asm

;----- 主程式開始 -----

org   0000h       ;上電覆位,程式從0000h開始執行

start: mov   sp,#60h      ;堆疊初始化為60h

mov   dptr,#liu_tab   ;流水花樣表首地址送dptr

loop:  clr   a

movc  a,@a+dptr

cjne  a,#0ffh,show   ;檢查流水結束標誌

ajmp  start       ;所有花樣流完,則從頭開始重複流

show:  mov   p1,a       ;將資料送到p1口

acall  delay

inc   dptr

ajmp  loop

;----- 延時子程式 -----

delay: mov   r0,#255     ;延時一段時間

d1:   mov   r1,#255

djnz  r1,$

djnz  r0,d1

ret            ;子程式返回

;----- 下面是流水花樣資料表 -----

liu_tab:

db 01111111b       ;二進位制表示的流水花樣資料

db 10111111b

db 11011111b

db 11101111b

db 11110111b

db 11111011b

db 11111101b

db 11111110b

db 11111110b

db 11111101b

db 11111011b

db 11110111b

db 11101111b

db 11011111b

db 10111111b

db 01111111b

db 7fh,0bfh,0dfh,0efh,0f7h,0fbh,0fdh,0feh ;十六進位制表示

db 0feh,0fdh,0fbh,0f7h,0efh,0dfh,0bfh,7fh

db 7eh,0bdh,0dbh,0e7h,0e7h,0dbh,0bdh,7eh

db 7fh,3fh,1fh,0fh,07h,03h,01h,00h

db 0ffh          ;流水花樣結束標誌0ffh

end           ;程式結束

為什麼微控制器上流水燈的程式設計定義用char型不用int型

呵呵,這麼簡單的一個問題,回答居然五花八門 那我也來湊湊熱鬧吧。首先,並不確定你的定義是指什麼定義,不過應該是指 顯示暫存器 的定義吧,以後提問最好能把你的 貼出來,這樣更方便的解答。現在假設你指的就是 顯示暫存器 的定義。那可以明確的說,這裡考慮的就是記憶體佔用。這裡一樓的說法差不多正確,不過in...

玩具公司的設計人員用什麼軟體做設計

對於玩具製造來說 一般都是用實體造型一類的軟體,caxa只是其中一種,並且是比較新興的國產軟體,現在用的很成熟的,有pro e,或者ug,這兩種比caxa更加成熟和完善,而且玩具一般有很多的塑料外殼件,這些都涉及到模具的設計,而pro e和ug在這方面是強項。以上說的是製造,例如很多車輛模型類的玩具...

求做設計用的電腦高階配置單

intel 奔騰雙核 e5200 盒裝 480主機板 技嘉p43 610 或者捷波p43 399記憶體 金邦 2gb ddr2 800 千禧條 1234 150硬碟 希捷 320g 330顯示卡 藍寶4830 699元 或者雙敏 昂達4830 599元 或者藍寶石 hd4650 海外版 hm1gb ...