|
|
PIC12C5XX 指令集及程序設(shè)計(jì)技巧 | | §2.1 PIC12C5XX 指令概述 PIC12C5XX每條指令長(zhǎng)12位,指令由操作碼和操作數(shù)組成。PIC12C5XX共有33條指令,按操作分成三大類: 1、面向字節(jié)操作類 2、面向位操作類 3、常數(shù)操作和控制操作類。 全部指令如表2.1所示。 | 面向字節(jié)操作類指令 | (11-6) | (5) | (4-0) | | OPCODE | d | f(FILE#) | | | | | | 二進(jìn)制代碼 HEX 名稱 助記符,操作數(shù) 操作 | | | 狀態(tài)影響 | 注 | 0000 0000 0000 | 000 | 空操作 | NOP | | | | 無 | | 0000 001f ffff | 02f | W送到f | MOVWF f | W→f | | | 無 | 1,4 | 0000 0100 0000 | 040 | W清零 | CLRW - | 0→W | | | Z | | 0000 011f ffff | 06f | f清零 | CLRF f | 0→f | | | Z | 4 | 0000 10df ffff | 08f | f減去W | SUBWF f,d | f-W→d | | | C,DC,Z | 1,2,4 | 0000 11df ffff | 0Cf | f遞減 | DECF f,d | f-1→d | | | Z | 2,4 | 0001 00df ffff | 10f | W和f做或運(yùn)算 | IORWF f,d | W∨f→d | | | Z | 2,4 | 0001 01df ffff | 14f | W和f做與運(yùn)算 | ANDWF f,d | W∧f→d | | | Z | 2,4 | 0001 10df ffff | 18f | W和f做異或運(yùn)算 | XORWF f,d | W〇f→d | | | Z | 2,4 | 0001 11df ffff | 1Cf | W加f | ADDWF f,d | W+f→d | | | C,DC,Z | 1,2,4 | 0010 00df ffff | 20f | 傳送f到d | MOVF f,d | f→d | | | Z | 2,4 | 0010 01df ffff | 24f | f取補(bǔ) | COMF f,d | f→d | | | Z | 2,4 | 0010 10df ffff | 28f | f遞增 | INCF f,d | f+1→d | | | Z | 2,4 | 0010 11df ffff | 2Cf | f遞減,為0則跳 | DECFSZ f,d | f-1→d,skip if zero | Z | 2,4 | 0011 00df ffff | 30f | f循環(huán)右移 | RRF f,d | f(n)→d(n-1),f(0)→C,C→d(7) | C | 2,4 | 0011 01df ffff | 34f | f循環(huán)左移 | RLF f,d | f(n)→d(n+1),f(7)→C,C→d(0) | C | 2,4 | 0011 10df ffff | 38f | f半字節(jié)交換 | SWAPF f,d | f(0.3)←→f(4-7)→d | Z | 2,4 | 0011 11df ffff | 3Cf | f遞增,為0則跳 | INCFSZ f,d | f+1→d,skip if zero | Z | 2,4 | | | | | | 面向位操作類指令 | (11-8) | (7-5) | (4-0) | | OPCODE | b(BIT#) | f(FILE#) | | | | | | 二進(jìn)制代碼 HEX 名稱 助記符,操作數(shù) 操作 | | | 狀態(tài)影響 | 注 | 0100 bbbf ffff | 4bf | 清除f的位b | BCF f,b | 0→f(b) | Z | 2,4 | 0101 bbbf ffff | 5bf | 設(shè)置f的位b | BSF f,b | 1→f(b) | Z | 2,4 | 0110 bbbf ffff | 6bf | 測(cè)試f的位b,為0則跳 | BTFSC f,b | Test bit(b) in file(f):Skip if clear | Z | | 0111 bbbf ffff | 7bf | 測(cè)試f的位b,為0則跳 | BTFSS f,b | Test bit(b) in file(f):Skip if clear | Z | | | | | | 常數(shù)操作和控制操作類指令 | (11-8) | (7-0) | | OPCODE | k(LITERAL) | | | | | | 二進(jìn)制代碼 HEX 名稱 助記符,操作數(shù) 操作 | | | 狀態(tài)影響 | 注 | 0000 0000 0010 | 002 | 寫OPTION寄存器 | OPTION - | W→OPTION register | 無 | | 0000 0000 0011 | 003 | 進(jìn)入睡眠狀態(tài) | SLEEP - | 0→WDT,stop oscillator | TO,PD | | 0000 0000 0100 | 004 | 清除WDT計(jì)時(shí)器 | CLRWDT - | 0→WDT(and prescaler,if assigned) | TO,PD | | 0000 0000 0fff | 00f | 設(shè)置I/O狀態(tài) | TRIS f | W→I/O control register f | 無 | 3 | 1000 kkkk kkkk | 8kk | 子程序帶參數(shù)返回 | RETLW k | k→W,Stack→PC | 無 | | 1001 kkkk kkkk | 9kk | 調(diào)用子程序 | CALL k | PC+1→Stack,K→PC | 無 | 1 | 101k kkkk kkkk | Akk | 跳轉(zhuǎn)(K為9位) | GOTO k | k→PC(9 bits) | 無 | | 1100 kkkk kkkk | Ckk | 常數(shù)置入W | MOVLW k | k→W | Z | | 1101 kkkk kkkk | Dkk | 常數(shù)和W做或運(yùn)算 | IORLW k | k∨W→W | Z | | 1110 kkkk kkkk | Ekk | 常數(shù)和W做與運(yùn)算 | ANDLW k | k∧W→W | Z | | 1111 kkkk kkkk | Fkk | 常數(shù)和W做異或運(yùn)算 | XORLW k | k○W→W | Z | | | | | | | | | | | | | | | | | | 表2.1 PIC12C5XX 指令集 注:1、除GOTO指令外,任何有關(guān)寫PC(F2)的指令(例如 CALL、MOVWF 2)都將會(huì)把PC寄存器的第9位清零。
2、若對(duì)I/O口寄存器進(jìn)行操作,如“SUBWF 6,1”,則使用的F6的值是當(dāng)前GP口上的狀態(tài)值,而非GP口輸出鎖存器里的值。
3、指令“TRIS 6”將W寄存器中的內(nèi)容寫入GP的I/O口控制寄存器中:“1”關(guān)斷對(duì)應(yīng)端口的輸出緩沖器,使其為輸入(高阻)狀態(tài),“0”則使其為輸出態(tài)。
4、當(dāng)預(yù)分頻器(Prescaler)分配給TIMER0后,任何對(duì)TMR0寄存器(F1)寫操作的指令都將使預(yù)分頻器清零。
§2.2 PIC12C5XX 指令尋址方式
PIC12C5XX單片機(jī)尋址方式根據(jù)操作數(shù)的來源,可分為寄存器間接尋址、立即數(shù)尋址、直接尋址和位尋址四種。
一、寄存器間接尋址
這種尋址方式通過寄存器F0(INDF)、F4(FSR)來實(shí)現(xiàn)。實(shí)際的寄存器地址放在FSR中,通過INDF來進(jìn)行間接尋址。
例:
FSR EQU 4
INDF EQU 0
MOVLW 05H ; W=5
MOVWF FSR ; W(=5)→F4
MOVLW 55H ; W=55H
MOVWF INDF ; W(=55H)→F5
上面這段程序把55H送入F5寄存器。間址尋址方式主要用于編寫查表、寫表程序,非常方便。請(qǐng)參考§2.7程序設(shè)計(jì)技巧。
二、立即數(shù)尋址
這種方式就是操作數(shù)為立即數(shù),可直接從指令中獲取。
例: MOVLW 16H ; 16H →W
三、直接尋址
這種方式是對(duì)任何一寄存器直接尋址訪問。對(duì)PIC12C508,寄存器地址(5位)直接包括在指令中,對(duì)PIC12C509,寄存器地址中最高1位由FSR(F4)寄存器中的bit5決定,即體選位。
例: MOVWF 8 ; W→F8寄存器
MOVF 8,W ; F8→W
四、位尋址
這種尋址方式是對(duì)寄存器中的任一位(bit)進(jìn)行操作。
例: BSF 11,0 ; 把F11的第0位置為“1”。
§2.3 面向字節(jié)操作類指令
這類指令共有18條,包括有數(shù)據(jù)傳送、算術(shù)和邏輯運(yùn)算、數(shù)據(jù)移位和交換等操作。它們的操作都是在W數(shù)據(jù)寄存器f之間進(jìn)行,其指令碼結(jié)構(gòu)為:
(11—6) | (5) | (4—0) | OPCODE | d | f(File#) |
高6位是指令操作碼。第6位d是方向位。d=1,則操作結(jié)果存入f(數(shù)據(jù)寄存器),d=0,則操作結(jié)果存入W。低5位是數(shù)據(jù)寄存器地址,可選中32個(gè)寄存器。對(duì)于PIC12C509,則還要參考寄存器體選擇器FSR的bit5選擇存入哪一個(gè)寄存器體(bank0或bank1)。
1、寄存器加法指令
格式: ADDWF f,d
指令碼: | 000111 | d | fffff | 指令周期: 1
操作: W+f→d
影響狀態(tài)位: C,DC,Z
說明: 將f寄存器和w相加,結(jié)果存入f(d=1)或W(d=0)。
例: ADDWF 8,0 ; F8+W→W
─────────────────────────────────
2、寄存器與指令
格式: ANDWF f,d
指令碼: | 000101 | d | fffff | 指令周期: 1
操作: W∧f→d
影響狀態(tài)位: Z
說明: 將f寄存器和w做邏輯與運(yùn)算,結(jié)果存入f(d=1)或W(d=0)。
例: ANDWF 10,0 ; F10∧W→W
ANDWF 10,1 ; F10∧W→F10
─────────────────────────────────
3、寄存器清零指令
格式: CLRF f
指令碼: | 0000011 | fffff | 指令周期: 1
操作: 0→f ,1→z
影響狀態(tài)位:z
說明: 將f寄存器清零,狀態(tài)位Z將被置為1。
例: CLRF 8 ; F8清為零(0→F8)
─────────────────────────────────
4、W清零指令
格式: CLRW
指令碼: | 000001 | 0 | 00000 | 指令周期: 1
操作: 0→W,1→Z
影響狀態(tài)位: Z
說明: 將W寄存器清零,狀態(tài)位Z將被置為1。
例: CLRW ;W清為零,Z置為1
─────────────────────────────────
5、寄存器取反指令
格式: COMF f,d
指令碼: | 00 | d | fffff | 指令周期: 1
操作: f→d
影響狀態(tài)位: Z
說明: 將f寄存器內(nèi)容做邏輯求反運(yùn)算,結(jié)果存入f(d=1)或W(d=0)。
例: COMF 12,0 ; F12取反→F12
COMF 12,1 ; F12取反→W
─────────────────────────────────
6、寄存器減1指令
格式: DECF f,d
指令碼: | 000011 | d | fffff | 指令周期: 1
操作: f-1→d
影響狀態(tài)位: C,DC,Z
說明: f寄存器內(nèi)容減1存入f(d=1)或W(d=0)。
例: DECF 15,1 ; F15-1→F15
DECF 15,0 ; F15-1→W
─────────────────────────────────
7、寄存器減1,結(jié)果為零則跳指令
格式: DECFSZ f,d
指令碼: | 0010 | 11df | ffff | 指令周期: 1或2(產(chǎn)生跳轉(zhuǎn)時(shí)為2)
操作: f-1→d; 結(jié)果為零則跳(PC+1→PC)
影響狀態(tài)位: 無
說明: 將f寄存器內(nèi)容減1存入f(d=1)或W(d=0)。如果結(jié)果為0,則跳過
下一條指令不執(zhí)行。否則順序執(zhí)行下一條指令。
例: ┌───DECFSZ 10,1 ; F10-1→F10,如果F10為0
F10=0 │ MOVLW 55H ; 則跳過MOVLW 55H指令
└──→MOVF 12,0
─────────────────────────────────
8、寄存器加1指令
格式: INCF f,d
指令碼: | 001010 | d | fffff | 指令周期: 1
操作: f+1→d
影響狀態(tài)位: C,DC,Z
說明: f寄存器加1,結(jié)果存入f(d=1)或W(d=0)。
例: INCF 10,0 ; F10+1→W
INCF 10,1 ; F10+1→F10
─────────────────────────────────
9、寄存器加1,結(jié)果為零則跳指令
格式: INCFSZ f,d
指令碼: | 001111 | d | fffff | 指令周期: 1或2(產(chǎn)生跳轉(zhuǎn)時(shí)為2)
操作: f+1→d,結(jié)果為零則跳(PC+1→PC)
影響狀態(tài)位: 無
說明: 將f寄存器內(nèi)容加1存入f(d=1)或W(d=0),如果結(jié)果為零則PC值
加1跳過下一條指令。
例: L00P ┌─INCFSZ 8,1 ; 將F8寄存器加1,結(jié)果存入F8,
│ GOTO LOOP ; 加1后結(jié)果為零則跳到MOVWFF9指令
F8=0 └→MOVWF 9
─────────────────────────────────
10、寄存器或指令
格式: IORWF f,d
指令碼: | 000100 | d | fffff | 指令周期: 1
操作: W∨f→d
影響狀態(tài)位: Z
說明: 將f寄存器內(nèi)容和W內(nèi)容做邏輯或運(yùn)算,結(jié)果存入f(d=1)或W(d=0)。
例: IORWF 18,1 ; F18∨W→F18
IORWF 18,0 ; F18∨W→W
─────────────────────────────────
11、f寄存器傳送指令
格式: MOVF f,d
指令碼: | 001000 | d | fffff | 指令周期: 1
操作: f→d
影響狀態(tài)位: Z
說明: 將f寄存器內(nèi)容傳送至W(d=0)或自己本身f(d=1)。如果是傳給
自己,一般是用來影響狀態(tài)位Z,即可判斷f是否為零。
例: MOVF 10,1 ; F10→F10
BTFSS 3,2 ; 判斷F3的第二位,即Z狀態(tài)位。如果F10=0,則Z=1。
─────────────────────────────────
12、W寄存器傳送指令
格式: MOVWF f
指令碼: | 000000 | 1 | fffff | 指令周期: 1
操作: W→f
影響狀態(tài)位: 無
說明: 將W內(nèi)容傳給f寄存器。
例: MOVWF 6 ; W→F6(B口)
─────────────────────────────────
13、空操作指令
格式: NOP
指令碼: | 000000 | 000000 | 指令周期: 1
操作: 無任何操作
影響狀態(tài)位: 無
說明: 不做任何操作,只有使PC加1。
─────────────────────────────────
14、帶進(jìn)位位左移指令
格式: RLF f,d
指令碼: | 001101 | d | fffff | 指令周期: 1
操作: f(n)→d(n+1),f(7)→c,c→d(0)
影響狀態(tài)位: C
說明: 將f寄存器左移,結(jié)果存入f(d=1)或W(d=0)。f左移時(shí),其最高
位(bit7)移入狀態(tài)位C(進(jìn)位位),如下圖:
進(jìn)位位
┌──┐ ┌──┬──┬──┬──┬──┬──┬──┬──┐
┌─┤ C │← │D7 │ D6 │D5 │ D4 │D3 │ D 2│ D1 │ D0│ ←─┐
│ └──┘ └──┴──┴──┴──┴──┴──┴──┴──┘ │
└──────────────────────────────────┘
例: RLF 8,1 ; F8左移→F8
RLF 8,0 ; F8左移→W
─────────────────────────────────
15、帶進(jìn)位位右移指令
格式: RRF f,d
指令碼: | 001100 | d | fffff | 指令周期: 1
操作: f(n)→d(n-1),f(0)→c,c→d(7)
影響狀態(tài)位: C
說明: 將f寄存器右移,結(jié)果存入f(d=1)或W(d=0)。f右移時(shí),其最低
位(bito)移入狀態(tài)位C,而原來的狀態(tài)位C移入f最高位(bit7),
如下圖:
┌────────────────────────────┐
│進(jìn)位位 │
│ ┌─┐ ┌──┬─┬──┬─┬──┬─┬──┬─┐│
└─→│C │→│D7 │D6│D5 │D4│D3 │D2│ D1 │D0│─┘
└─┘ └──┴─┴──┴─┴──┴─┴──┴─┘
例: RRF 8 ,1 ;F8右移→F8
RRF 8,0 ;F8右移→W
─────────────────────────────────
16、寄存器減法指令
格式: SUBWF f,d
指令碼: | 000010 | d | fffff | 指令周期: 1
操作: f-w→d
影響狀態(tài)位: C,DC,2
說明: 將f寄存器內(nèi)容減去W內(nèi)容,結(jié)果存入f(d=1)或W(d=0)。
例: CLRF 20 ;F20=0
MOVLW 1 ; W=1
SUBWF 20,1 ; F20-W=0-1=-1→F20
; C=0,運(yùn)算結(jié)果為負(fù)。
─────────────────────────────────
17、寄存器交換指令
格式: SWAPF f,d
指令碼: | 001110 | d | fffff | 指令周期: 1
操作: f(0-3)→d(4-7),f(4-7)→d(0-3)
影響狀態(tài)位: 無
說明: 將f寄存器內(nèi)容的高4位(bit7-bit4)和低4位(bit3-bit0)交換
結(jié)果存入f(d=1)或W(d=0)。
例: MOVLW 56H
MOVWF 8 ; F8=56H
SWAPF 8,1 ; F8交換,結(jié)果存入F8,則F8=65H。
─────────────────────────────────
18、寄存器異或運(yùn)算指令
格式: XORWF f,d
指令碼: | 00010 | d | fffff | 指令周期: 1
操作: W○f→d
影響狀態(tài)位: Z
說明: 將f寄存器和W進(jìn)行異或運(yùn)算,結(jié)果存入f(d=1)或W(f=0)。
例: XORWF 5,1 ; F5○W→F5(A口)
XORWF 5,0 ; F5○W→W
§2.4 面向位操作類指令
這類指令共有4條,指令碼基本結(jié)構(gòu)為:
(11—8) | (7—5) | (4—0) | OPCODE | bbb | file# |
高4位是操作碼。bit5-bit7是位地址(可尋址8個(gè)位),bito-bit4是寄存器地址。
19、位清零指令
格式: BCF f,b
指令碼: | 0100 | bbb | fffff | 指令周期: 1
操作: 0→f(b)
影響狀態(tài)位: 無
說明: 將f寄存器的b位清為0。
例: BCF 8,2 ; 將F8的第2位(bif2)清為0。
─────────────────────────────────
20、位置1指令
格式: BSF f,b
指令碼: | 0101 | bbb | fffff | 指令周期: 1
操作: 1→f(b)
影響狀態(tài)位: 無
說明: 將f寄存器的b位置為1。
例: BSF 8,2 ; 將F8的第2位(bif2)清為1。
─────────────────────────────────
21、位測(cè)試,為零則跳指令
格式: BTFSC f,b
指令碼: | 0110 | bbb | fffff | 指令周期: 1或2(產(chǎn)生跳轉(zhuǎn)則為2)
操作: 如果f(b)=0則跳(PC+1→PC)
影響狀態(tài)位: 無
說明: 測(cè)試f寄位器的第b位,如果位b為零則跳過下一條指令,否則順
序執(zhí)行下去 。
例: ┌──BTFSC 8,2 ; 測(cè)試F8的bit2,如果為0
bit2=0 │ MOVF 5,0 ; 則跳到INCF9,1執(zhí)行。
└─→INCF 9,1 ;
─────────────────────────────────
22、位測(cè)試,為1則跳指令
格式: BTFSS f,b
指令碼: | 0 | 11 | bbb | fffff | 指令周期: 1或(產(chǎn)生跳轉(zhuǎn)則為2)
操作: 如果f(b)=1則跳(PC+1→PC)
影響狀態(tài)位: 無
說明: 測(cè)試f寄有器的有第b位,如果位b為1則跳過下一條指令,否則順
序執(zhí)行下去。
例: ┌─BTFSS 8,2 ; 測(cè)試F8的bit2,如果為1
bit2=1 ┤ MOVF 5,0 ; 則跳到INCF9,1
└→INCF 9,1
§2.5 常數(shù)和控制操作類指令
這類指令共有11條,其指令碼結(jié)構(gòu)為:
(11—8) | (7—0) | OPCODE | K |
高4位是操作碼,低8位是常數(shù)K。
23、常數(shù)與指令
格式: ANDLW K
指令碼: | 1110 | KKKKKKKK | 指令周期: 1
操作: W∧K→W
影響狀態(tài)位: Z
說明: 將W寄存器和常數(shù)K做邏輯與運(yùn)算,結(jié)果存入W。
例: ANDLW 55H,0 ; W∧55H→W
─────────────────────────────────
24、子程序調(diào)周指令
格式: CALL K
指令碼: | 1001 | KKKKKKKK | 指令周期: 2
操作: PC+1→堆棧;
K→PC(0-7);‘0’→PC(8);PA1,PA0→PC(10-9)。
影響狀態(tài)位: 無
說明: 將程序計(jì)數(shù)器PC加1后推入堆棧、將常數(shù)K(程序地址的低8位)
置入PC,同時(shí)還把PC的第9位清為0。對(duì)于PIC12C509來論,STATUS
的PA0位(頁面地址)還將被置入PC的最高位(bit9)。所以子程序
可以放在二個(gè)頁面的任何一個(gè)中, 但必須放在每頁的上半部(低
址區(qū)),因?yàn)閳?zhí)行CALL指令將PC的第9位(bit8)清為"0"。
例: CALL DELAY ; 調(diào)用子程序DELAY
:
:
DELAY MOVLW 80H ──┐
: │
: │ ; 子程序其第一條指令須放在每頁面的上半?yún)^(qū)。
RETLW 0 ──┘
注:有關(guān)子程序調(diào)用的一些問題,請(qǐng)參考§2.7程序設(shè)計(jì)技巧。
─────────────────────────────────
25、看門狗計(jì)數(shù)器清零指令
格式: CLRWDT
指令碼: | 0000 | 0000 | 0100 | 指令周期: 1
操作: 0→WDT ,0→WDT預(yù)設(shè)倍數(shù)
影響狀態(tài)位: 1→TO,1→PD
說明: 清除WDT,使之不能計(jì)時(shí)溢出。
─────────────────────────────────
26、無條件跳轉(zhuǎn)指令
格式: GOTO K
指令碼: | 101 | KKKKKKKKK | 指令周期: 2
操作: K→PC(8-0),PA1,PA0→PC(10-9)
影響狀態(tài)位: 無
說明: 常數(shù)K(地址)置入PC低9位。對(duì)于PIC12C509,STATUS中
的PA0位(頁面地址位)將同時(shí)置入PC的最高位(bit9)。
所以GOTO指令可跳到程序區(qū)的任何地方去執(zhí)行。
例: GOTO LOOP ; 跳轉(zhuǎn)到LOOP
:
:
LOOP MOVLW 10 ;
注: 關(guān)于跨頁面跳轉(zhuǎn)的問題,請(qǐng)參閱§2.7程序設(shè)計(jì)技巧。
─────────────────────────────────
27、常數(shù)或指令
格式: IORLW K
指令碼: | 1101 | KKKKKKKK | 指令周期: 1
操作: W∨K→W
影響狀態(tài)位: 2
說明: 將W和常數(shù)K做邏輯或操作,結(jié)果存回W。
例: IORLW 80H ; W∨80H→W
─────────────────────────────────
28、常數(shù)傳送指令
格式: MOVLW K
指令碼: | 1100 | KKKKKKKK | 指令周期: 1
操作: K→W
影響狀態(tài)位: 無
說明: 把常數(shù)K置入W寄存器。注意這條指令并不影響任何狀態(tài)位。
例: MOVLW 0 ; 0→W,注意狀態(tài)位Z不因之
MOVLW 88H ; 而變化。
─────────────────────────────────
29、寫OPTION寄存器指令
格式: OPTION
指令碼: | 0000 | 000000 | 0 | 指令周期: 1
操作: W→OPTION寄存器
影響狀態(tài)位: 無
說明: 將W內(nèi)容置入OPTION寄存器
例: MOVLW 07H ;7→W
OPTION ; OPTION=W=F
─────────────────────────────────
30、子程序返回指令
格式: RETLW K
指令碼: | 1000 | KKKKKKKK | 指令周期: 2
操作: K→W ,堆!鶳C
影響狀態(tài)位: 無
說明: 由子程序帶參數(shù)K返回。返回參數(shù)存在W中。
例: RETLW 0 ; 返回,0→W
─────────────────────────────────
31、由入低功耗狀態(tài)指令
格式: SLEEP
指令碼: | 0000 | 0000 | 0011 | 指令周期: 1
操作: 0→PD,1→TO;
0→WDT ,0→WDT的預(yù)分頻器
影響狀態(tài)位: PD,TO
說明: 停止芯片振蕩,使PIC進(jìn)入低功耗睡眠模式。這條指令還會(huì)
清零WDT和預(yù)分頻器(如果預(yù)分頻器分配給WDT的話),并將
STATUS的PD位清零,TO位置1。進(jìn)入低功耗模式后,I/O狀
態(tài)保持不變,WDT清零后重新計(jì)時(shí),一但計(jì)時(shí)溢出即將把PIC
從SLEEP模式中喚醒(通過RESET)。
─────────────────────────────────
32、設(shè)置I/O控制寄存器指令
格式: TRIS f
指令碼: | 0000 | 00000 | fff | 指令周期: 1
操作: W→I/O控制寄存器TRISf(f=6)
影響狀態(tài)位: 無
說明: 將W寄存器內(nèi)容置入GP口控制寄存器,以設(shè)定GP口的輸入/輸
出方向。f=6,對(duì)應(yīng)于GP口。
例: MOVLW 0FH ; W=OFH
TRIS 6 ; TRISB=OFH
RB5 RB4 RB3 RB2 RB1 RB0
TRISB=OFH │ │ │ │ │ │
└──┬──┘ └──┴┬─┴──┘
│ │
輸出 輸入
─────────────────────────────────
33、常數(shù)異或指令
格式: XORLW k
指令碼: | 1111 | KKKKKKKK | 指令周期: W○K→W
影響狀態(tài)位: Z
說明: 將W和常數(shù)K邏輯異或運(yùn)算,結(jié)果存入W。
例: XORLW 33H ; W○33H→W
§2.6 特殊指令助記符
PIC12C5XX的一些指令還可以用容易記憶的助記符來表示。PIC12C5XX的匯編MPASM可以認(rèn)識(shí)這些助記符,在匯編時(shí)會(huì)將其轉(zhuǎn)譯成相應(yīng)的PIC12C5XX基本指令。
例如指令“BCF 3,0”(清零C)也可以寫成CLRC,“BSF 3,0”(置C=1)也可寫成SETC等。
表2.2列出了這些助記符及其相對(duì)應(yīng)的PIC12C5XX指令。
二進(jìn)制指令代碼(Hex) | 名稱 | 助記符號(hào) | 相對(duì)運(yùn)算 | 狀態(tài)影響 | 0100 0000 0011(403) | 清除C標(biāo)號(hào) | CLRC | BCF 3,0 | - | 0101 0000 0011(503) | 設(shè)置C標(biāo)號(hào) | SETC | BSF 3,0 | - | 0100 0010 0011(423) | 清除輔助進(jìn)位標(biāo)號(hào) | CLRDC | BCF 3,1 | - | 0101 0010 0011(523) | 設(shè)置輔助進(jìn)位標(biāo)號(hào) | SETDC | BSF 3,1 | - | 0100 0100 0011(443) | 清除0標(biāo)號(hào) | CLRZ | BCF 3,2 | - | 0101 0100 0011(543) | 設(shè)置0標(biāo)號(hào) | SETZ | BSF 3,2 | - | 0111 0000 0011(703) | 進(jìn)位則跳 | SKPC | BTFSS 3,0 | - | 0110 0000 0011(603) | 無進(jìn)位則跳 | SKPNC | BTFSC 3,0 | - | 0111 0010 0011(723) | 輔助進(jìn)位為1則跳 | SKPDC | BTFSS 3,1 | - | 0110 0010 0011(623) | 輔助進(jìn)位為0則跳 | SKPNDC | BTFSC 3,1 | - | 0111 0100 0011(743) | 為0則跳 | SKPZ | BTFSS 3,2 | - | 0110 0100 0011(643) | 不為0則跳 | SKPNZ | BTFSC 3,2 | - | 0010 001f ffff(22f) | 測(cè)試寄存器 | TSTF f | MOVF f,1 | Z | 0010 000f ffff(20f) | 搬移寄存器到W | MOVFW f | MOVF f,0 | Z | 0010 011f ffff(26f) | 寄存器取補(bǔ)碼 | NEGF f,d | COMF f,1 | Z | 0010 10df ffff(28f) | | | INCF f,d | | | | | | | 0110 0000 0011(603) | 加進(jìn)位到寄存器 | ADDCF f,d | BTFSC 3,0 | Z | 0010 10df ffff(28f) | | | INCF f,d | | | | | | | 0110 0000 0011(603) | 寄存器減進(jìn)位 | SUBCF f,d | BTFSC 3,0 | Z | 0000 11df ffff(0cf) | | | DECF f,d | | | | | | | 0110 0010 0011(623) | 加輔助進(jìn)位到寄存器 | ADDDCF f,d | BTFSC 3,1 | Z | 0010 10df ffff(28f) | | INCF f,d | | | | | | | 0110 0010 0011(623) | 從寄存器減輔助進(jìn)位 | SUBD CF f,d | BTFSC 3,1 | Z | 0000 11df ffff(0cf) | | | | | | | | | 101k kkkk kkkk(akk) | 分支 | B k | GOTO k | - | | | | | | 0110 0000 0011(603) | 依進(jìn)位分支 | BC k | BTFSC 3,0 | - | 101k kkkk kkkk(akk) | | | GOTO k | | | | | | | 0111 0000 0011(703) | 不進(jìn)位分支 | BMC k | BTFSS 3,0 | - | 101k kkkk kkkk(akk) | | | GOTO k | | | | | | | 0111 0000 0011(703) | 輔助進(jìn)位為1分支 | BDC k | BTFSC 3,1 | - | 101k kkkk kkkk(akk) | | | GOTO k | | | | | | | 0110 0100 0011(643) | 輔助進(jìn)位為0分支 | BNDC k | BTFSS 3,1 | - | 101k kkkk kkkk(akk) | | | GOTO k | | | | | | | 0111 0100 0011(743) | 0分支 | BZ k | BTFSC 3,2 | - | 101k kkkk kkkk(akk) | | | GOTO k | | | | | | | 0111 0100 0011(743) | 不為0分支 | BNZ k | BTFSS 3,2 | - | 101k kkkk kkkk(akk) | | | GOTO k | | 表2.2 特殊指令助記符表 在后面的例子里,你將看到程序中使用了很多的特殊指令助記符。特殊指令助記符容易記憶。使用它程序可讀性也較好。但這取決于每個(gè)人的習(xí)慣,你可以只使用一部分你認(rèn)為好記的助記符,甚至只用基本的指令助記符而不用特殊指令助記符來編寫程序。
§2.7 PIC12C5XX 程序設(shè)計(jì)基礎(chǔ)
上面我們已經(jīng)詳細(xì)介紹了PIC12C5XX的每條指令,F(xiàn)在我們來總結(jié)一下它們的幾個(gè)特點(diǎn):
1、各寄存器的每一個(gè)位都可單獨(dú)地被置位、清零或測(cè)試,無須通過間接比較,可節(jié)省執(zhí)行時(shí)間和程序地址空間。
2、特殊功能寄存器的使用方法和通用寄存器的方法完全一樣,即和通用寄存器一樣看待。這樣使程序執(zhí)行和地址空間都簡(jiǎn)化很多。
3、對(duì)于PIC12C509跨頁面的CALL和GOTO操作,要事先設(shè)置STATUS中的頁面地址位PA0,對(duì)于CALL來論,子程序返回后還要將STATUS中的PA0恢復(fù)到本頁面地址。
§2.7.1 程序的基本格式
先介紹二條偽指令:
(a) EQU──標(biāo)號(hào)賦值偽指令 (b) ORG──地址定義偽指令
PIC12C5XX一旦復(fù)位后指令計(jì)數(shù)器PC被置為全“1”,所以PIC12C5XX 幾種型號(hào)芯片的復(fù)位地址為:
型 號(hào) | RESET 地址 | PIC12C508 | 1FFh | PIC12C509 | 3FFh | 表2.3 復(fù)位地址表 一般說來,PIC12C5XX的源程序并沒有要求統(tǒng)一的格式,大家可以根據(jù)自己的風(fēng)格來編寫。但這里我們推薦一種清晰明了的格式供參考。
TITLE This is..... ; 程序標(biāo)題
;------------------
;名稱定義和變量定義
;------------------
INDF EQU 0
TMR0 EQU 1
PC EQU 2
STATUS EQU 3
FSR EQU 4
GP EQU 6
;--------------------------------
ORG 0 ; 從000H開始存放程序
GOTO MAIN
;--------------------------------
;子程序區(qū)
;--------------------------------
DELAY MOVLW 255
┊
RETLW 0
;--------------------------------
;主程序區(qū)
;--------------------------------
MAIN CLRW
TRIS GP ; GP已由偽指令定義為6。
CALLL DELAY
┊
END ; The End of Program
注: MAIN標(biāo)號(hào)一定要處在0頁面內(nèi)。
另一些指令書寫注意事項(xiàng)請(qǐng)參閱第五章“匯編程序”。
§2.7.2 程序設(shè)計(jì)基礎(chǔ)
一、設(shè)置I/O口的輸入/輸出方向
PIC12C5XX的I/O口皆為雙向可編程,即每一根I/O 端線都可分別單獨(dú)地由程序設(shè)置為輸入或輸出。這個(gè)過程由寫I/O控制寄存器TRISf來實(shí)現(xiàn),寫入值為“1”,則為輸入;寫入值為“0”, 則為輸出。
MOVLW 0FH ; 00 1111 (0FH)
↑ ↑
│ └──輸入
└────輸出
TRIS 6 ; W中的0FH寫入GP口控制器,GP口高2位為輸出,
低4位為輸入 。
二、檢查寄存器是否為零
如果要判斷一個(gè)寄存器內(nèi)容是否為零,很簡(jiǎn)單:
MOVF 10,1 ; F10→F10,結(jié)果影響狀態(tài)位Z
┌─ SKPZ ; F10為零則跳(Z=1否)
Z=1 │ GOTO NZ ; F10不為零
(F10=0)└─→:
:
:
NZ MOVLW 55H
:
:
三、比較二個(gè)寄存器的大小
要比較二個(gè)寄存器的大小,可以將它們做減法運(yùn)算,然后根據(jù)狀態(tài)位C來判斷。注意,相減的結(jié)果放入W,則不會(huì)影響二寄存器原有的值。
例如F8和F9二個(gè)寄存器要比較大。
MOVF 8, 0 ; F8→W
SUBWF 9, 0 ; F9-F8→W
SKPNZ ; 判斷Z=1否(即F9=F8否)
GOTO F8=F9 ; F9=F8
SKPNC ; C=0則跳
GOTO F9>F8 ; C=1,相減1結(jié)果為正,F(xiàn)9>F8
GOTO F8>F9 ; C=0,相減結(jié)果為負(fù),F(xiàn)8>F9
:
:
四、循環(huán)n次的程序
如果要使某段程序循環(huán)執(zhí)行n次,可以用一個(gè)寄存器作計(jì)數(shù)器。下例以F10做計(jì)數(shù)器,使程序循環(huán)8次。
COUNT EQU 10 ; 定義F10名稱為COUNT(計(jì)數(shù)器)
:
:
MOVLW 8 ; 循環(huán)次數(shù)→COUNT
MOVWF COUNT
┌─→LOOP CLRW ; 循環(huán)體
│ :
│ :
│ ┌──DECFSZ COUNT,1 ; COUNT減1,結(jié)果為零則跳
└──┼──GOTO LOOP ; 結(jié)果不為零,繼續(xù)循環(huán)
└─→ : ; 結(jié)果為零,跳出循環(huán)
:
五、 "IF......THEN......"格式的程序
下面以"IF X=Y THEN GOTO NEXT"格式為例。
X EQU ××
Y EQU ×× ;X,Y值由用戶定義(變量)
:
:
MOVLW X
MOVWF 10 ;X→F10
MOVLW Y ;Y→W
SUBWF 10,0 ;X-Y→W
┌─ SKPNZ ;X=Y否
X≠Y │ GOTO NEXT ;X=Y,跳到NEXT去執(zhí)行。
└→ :
:
六、"FOR......NEXT"格式的程序
"FOR......NEXT"程序使循環(huán)在某個(gè)范圍內(nèi)進(jìn)行。下例是"FOR X=0 TO 5"格式的程序。F10放X的初值,F(xiàn)11放X的終值。
START EQU 10
END' EQU 11
:
:
MOVLW 0
MOVWF START ;0→START(F10)
MOVLW 5
MOVWF END' ;5→END'(F11)
┌─→LOOP : ;循環(huán)體
│ :
│ INCF START,1 ;START值加1
│ MOVF START,O
│ SUBWF END',0 ;START=END'?(X=5否)
│ X=5┌─ SKPZ
└──┼─ GOTO LOOP ;X<5,繼續(xù)循環(huán)
└→ : ;X=5,結(jié)束循環(huán)
:
七、“DO WHILE.........END”格式的程序
“DO WHILE.........END”程序是在符合條件下執(zhí)行循環(huán)。下例是“DO WHILE X=1”格式的程序。F10放X的值。
X EQU 10
:
:
MOVLW 1
MOVWF X ;1→X(F10),作為初值
┌─→LOOP :
│ :
│ MOVLW 1
│ SUBWF X,0
│X≠1┌─ SKPNZ ;X=1否?
└──┼─ GOTO LOOP ;X=1 繼續(xù)循環(huán)
└→ : ;X≠1,跳出循環(huán)
:
八、查表程序
查表是程序中經(jīng)常用到的一種操作。
PIC的查表程序可以利用子程序帶值返回的特點(diǎn)來實(shí)現(xiàn)。具體是在主程序中先取表數(shù)據(jù)地址放入W,接著調(diào)用子程序。子程序的第一條指令將W置入PC,則程序跳到數(shù)據(jù)地址的地方,再由“RETLW”指令將數(shù)據(jù)放入W返回到主程序。
下面程序以F10放表頭地址。
MOVLW TABLE ; 表頭地址→F10
MOVWF 10
:
:
MOVLW 1 ; 1→W,準(zhǔn)備取表格中的數(shù)據(jù)。
ADDWF 10,1 ; F10+W=表中第二個(gè)數(shù)據(jù)的地址。
CALL CONVERT
MOVWF 6 ; 送到GP口上。
:
:
CONVERT MOVWF 2 ; W→PC
TABLE RETLW C0H
RETLW F9H
:
:
RETLW 90H
九、“READ......DATA,RESTORE”格式程序
“READ......DATA”程序是每次讀取數(shù)據(jù)表的一個(gè)數(shù)據(jù),然后將數(shù)據(jù)指針加1,準(zhǔn)備下一次取下一個(gè)數(shù)據(jù)。下例程序中以F10被數(shù)據(jù)表起始地址,F(xiàn)11做數(shù)據(jù)指針。
POINTER EQU 11 ; 定義F11名稱為POINTER
:
:
MOVLW DATA
MOVWF 10 ; 數(shù)據(jù)表頭地址→F10
CLRF POINTER ; 數(shù)據(jù)指針清零
:
:
MOVF POINTER,0
ADDWF 10,0 ; W=F10+POINTER
:
:
INCF POINTER,1 ; 指針加1
CALL CONVERT ; 調(diào)子程序,取表格數(shù)據(jù)
:
:
CONVERT MOVWF 2 ; 數(shù)據(jù)地址→PC
DATA RETLW 20H ; 數(shù)據(jù)
:
RETLW 15H ; 數(shù)據(jù)
如果要執(zhí)行“RESTORE”,只要執(zhí)行一條“CLRF POINTER”即可。
十、延時(shí)程序
如果延時(shí)時(shí)間較短,可以讓程序簡(jiǎn)單地連續(xù)執(zhí)行幾條空操作指令“NOP”。如果延時(shí)時(shí)間長(zhǎng),可以用循環(huán)來實(shí)現(xiàn)。下例以F10計(jì)算,使循環(huán)重復(fù)執(zhí)行100次。
MOVLW 100
MOVWF 10
┌─→LOOP┌── DECFSZ 10,1 ;F10-1→F10,結(jié)果為零則跳
└────┼── GOTO LOOP
└─→ :
:
延時(shí)程序中計(jì)算指令執(zhí)行的時(shí)間和即為延時(shí)時(shí)間。如果使用4MHz振蕩,則每個(gè)指令周期為1uS。所以單周期指令執(zhí)行時(shí)間為1uS,雙周期指令為2uS。
在上例的LOOP循環(huán)延時(shí)時(shí)間即為(1+2)*100+2=302(uS)。在循環(huán)中插入空操作指令即可延長(zhǎng)延時(shí)時(shí)間:
MOVLW 100
MOVWF 10
┌─→ LOOP NOP
│ NOP
│ NOP
│ ┌── DECFWZ 10,1
└──┼─ GOTO LOOP
└─→ :
:
延時(shí)時(shí)間=(1+1+1+1+2)*100+2=602(US)。
用幾個(gè)循環(huán)嵌套的方式可以大大延長(zhǎng)延時(shí)時(shí)間。如下例用2個(gè)循環(huán)來做延時(shí)。
MOVLW 100
MOVLW 10 ;第一計(jì)數(shù)值(100)→F10
┌→LOOP MOVLW 16
│ MOVLW 11 ;第二計(jì)數(shù)值(16)→F11
│┌→LOOP1 DECFSZ 11,1
│└────── GOTO LOOP1
│ ┌── DECFSZ 10,1
└────┼── GOTO LOOP2
└──→:
:
延時(shí)時(shí)間= [(1+2)*6+2+]+1+2+1+1 +*100+2=5502(US)
十一、TIMER0計(jì)數(shù)器的使用
TIMER0是一個(gè)脈沖計(jì)數(shù)器,它的計(jì)數(shù)脈沖有二個(gè)來源,一個(gè)是從T0CKI引腳輸入的外部信號(hào),一個(gè)是內(nèi)部的指令時(shí)鐘信號(hào)?梢杂贸绦騺磉x擇其中一個(gè)信號(hào)源做為輸入。TIMER0可被程序用作計(jì)時(shí)之用:程序讀取TMR0寄存器值以計(jì)算時(shí)間。
下例程序以TIMER0做延時(shí)。
TMR0 EQU 1
:
:
CLRF TMR0 ; TMR0清O
MOVLW 07H
OPTION ; 選擇預(yù)設(shè)倍數(shù)1:256→RTCC
┌─→LOOP MOVLW 255 ; TMR0計(jì)數(shù)終位值
│ SUBWF TMR0,0
│ ┌─ SKPZ ; TMR0=255?
└───┼─ GOTO LOOP
│:
└─→:
這個(gè)延時(shí)程序中,每過256個(gè)指令周期TMR0寄存器增1(預(yù)分頻率=1:256,設(shè)芯片使用4MHz振蕩,則:
延時(shí)時(shí)間=256*256=65536(US)
TIMER0是自振式的,在它計(jì)數(shù)時(shí),程序可以去做別的事,只要隔一段時(shí)間去讀取它,檢測(cè)它的計(jì)數(shù)值即可。所以用TIMER0做延時(shí),在延時(shí)期間程序還可以做別的事,這是一般用軟件來延時(shí)做不到的。
十二、寄存器體(Bank)的尋址
對(duì)于PIC12C508,寄存器有32個(gè),只有一個(gè)體(bank0),故不存在體尋址問題,對(duì)于PIC12C509來說,寄存器則分為2個(gè)體(bank0/bank1)。FSR<5>用來進(jìn)行體選擇,其對(duì)應(yīng)關(guān)系如下:
FSR<5> | Bank | 物理地址 | 01 | Bank0 Bank1 | 10H-1FH 30H-3FH |
對(duì)于PIC12C509,當(dāng)芯片上電復(fù)位后,F(xiàn)SR<5>被清為“0”,所以是指向Bank0,而對(duì)于其他類型的復(fù)位則FSR<5>保持原值不變。
下面的例子對(duì)Bank0和Bank1的10H及30H寄存器寫入數(shù)據(jù)。
例1:(設(shè)目前體選為Bank0)
BCF FSR,5 ; 置位FSR<5>=1,選擇Bank0
MOVLW 55H
MOVWF 10H ; 55H→10H寄存器(Bank0)
BSF FSR,5 ; FSR<5>=1,選Bank1
MOVWF 10 ; 55H→30寄存器(Bank1)
十三、程序跨頁面跳轉(zhuǎn)和調(diào)用
在§1.4“程序存貯器”,我們已經(jīng)談了PIC12C509的程序存貯區(qū)的頁面概念和STATUS 寄存器中的頁面選址位PA0。下面我們來看實(shí)例。
1、“GOTO”跨頁面
例:設(shè)目前程序在0頁面(Page0),欲用“GOTO”跳轉(zhuǎn)到1頁面的某個(gè)地方KEY(Page1)。
:
:
STATUS EQU 3
PA0 EQU 5
:
:
跨頁跳轉(zhuǎn) BSF STATUS,PA0 ;PA0=1,選擇page頁面
┌─── GOTO PAGE1 ;跳轉(zhuǎn)到1頁面的KEY
│ :
│ :
└→ KEY CLRW
:
2、“CALL”跨頁面
例:設(shè)目前程序在0頁面(Page 0),現(xiàn)要調(diào)用─-放在1頁面(Page 1)的子程序DELAY。
:
。
跨頁調(diào)用 BSF STATUS,PA0 ; PA0=1,選擇1頁面
┌────CALL DELAY ; 跨頁調(diào)用
│ BCF STATUS,PA0 ; PA0=0,恢復(fù)0頁面地址
│ :
│ 。
│ ;───────────────
│ ; DELAY子程序
│ ;───────────────
└─→ DELAY :
。
注意:程序?yàn)榭珥揅ALL而設(shè)了頁面地址,從子程序返回后一定要恢復(fù)原來的頁面地址。
3、程序跨頁跳轉(zhuǎn)和調(diào)用的編寫
讀者看到這里,一定要問:我寫源程序(.ASM)時(shí),并不去注意每條指令的存放地址,我怎么知道這個(gè)GOTO是要跨頁面的,那個(gè)CALL是需跨頁面的?
問得好!的確,你開始寫源程序時(shí)并不知道何時(shí)會(huì)發(fā)生跨頁面跳轉(zhuǎn)或調(diào)用,不過當(dāng)你將源程序用MPASM匯編時(shí),它會(huì)告訴你。當(dāng)匯編結(jié)果顯示出:
×××(地址)“GOTO out of Range”
×××(地址)“CALL out of Range”
這表明你的程序發(fā)生了跨頁面的跳轉(zhuǎn)和調(diào)用,而你的程序中在這些跨頁GOTO和CALL之前還未設(shè)置好相應(yīng)的頁面地址。這時(shí)你應(yīng)該查看匯編生成的.Lst文件,找到這些GOTO和CALL,并查看它們要跳轉(zhuǎn)去的地址處在什么頁面,然后再回到源程序(.ASM)做必要的修改。一直到你的源程序匯編通過(0 Errors)。
4、程序頁面的連接
PIC12C509程序2個(gè)頁面連接處應(yīng)該做一些處理。一般建議采用下面的格式:
地址 | 指 令 | 000H | : ;Page0(PA0=0) | : | : | 1FFH | | 200H | BSF STATUS,PA0 | 201H | : ;Page1(PA0=1) | 即在進(jìn)入另一個(gè)頁面后,馬上設(shè)置相應(yīng)的頁面地址位(PA0)。