5.1. EM78 系列八位微控器特色指令用法
5.1.1. 查表指令与用法
EM78 系列八位微控器是利用 (1)“call",(2) 改变PC (或“tbl"),(3)“retl k" 三个步骤来查表的。其中“retl k" 是将常数 k 的值传至工作寄存器 "A" 中。
步骤 (2) 中若利用“mov 0x2,a",或“add 0x2,a" 等等指令来改变PC,则因为此等指令会將 PC (R2) 的位 8、9 清除 (在 EM78056 只清除位 8),所以查表的内容只能放在程序每个 PAGE 的較低的 256 个位址。步骤 (2) 中若利用“tbl" 指令来改变PC,则因为此指令不会將PC (R2) 的位 8、9 清除,而保留“tbl" 所在位址的位 8、9,所以查表的内容可以放在程序每个 PAGE 中的任何位址。
例:查表
table add 0x02,a ;將相对位置加入 PC 而改变了PC
retl @0x19 ;传回常数内容 19h 至 "A"
retl @0x74 ;传回常数内容 74h 至 "A"
retl @0x2e ;传回常数内容 2eh 至 "A"
retl @0x54 ;传回常数内容 54h 至 "A"
retl @0x4b ;传回常数内容 4bh 至 "A"
inc 0x18
mov a,0x18 ;欲查的内容的相对位置放在"A"
call table ;查表
mov 0x10,a ;查表得到的内容移至 R10 中
5.1.2. 分 PAGE 的用法
1. 程序跳 PAGE 的用法:
EM78 系列八位微控器將其 Program Memory (ROM) 分成数个 PAGE,每个 PAGE 的长度是 1K (EM78056 除外)。R3 寄存器的位 5 (6) 是 "PAGE 选择位",当执行 "jmp" 或 "call" 指令时,"PAGE 选择位" 会被载入 Program Counter 的位 10 (11),因此当程序超过 1K (EM78056 为 0.5K)时,执行 "jmp" 或"call" 指令时,"PAGE 选择位" 正确的设定是非常重要的。下面将以 EM78256 为例来说明跳 PAGE 的方法。
例
例:从PAGE 1 跳转到PAGE 0
例:从PAGE 1 跳转到PAGE 0
; PAGE 0, begin at 000h
049 add 0x11,a
050 mov a,@0x55
051 mov 0x05,a ;port5<-- 0x55
052 bs 0x03,5 ;select PAGE 1
053 jmp lab1 ;PAGE jump
054
; PAGE 1, begin at 400h
447
448 mov a,@0x3f
449 xor 0x12,a
450 Lab1 bc 0x06,3
451 mov a,0x05
说明:
052: 将 R3 寄存器的位 5 设为 "1" (选择 PAGE 1)。
053: Lab1 会被编译 为 "50",程序跳转至 PAGE 1 中 "Lab1" (450) 的位址。
注意:
此例中 "052" 和 "053" 是用来跳 PAGE 的,假如沒有 "052" 这行指令,则程序将跳转至"050" 的位址 (在 PAGE 0中),如此將沒有达到預期的目的。
2. 不同 PAGE 子程序呼叫的方法:
如第 1 项所述,当程序超过 1K 時,执行 "call" 指令时,"PAGE 选择位" 的设定就必须加以考虑。下面將以 EM78256 为例来说明呼叫不同 PAGE 子程序的方法。
例: 从PAGE 0调用PAGE 1中的子程序
; PAGE 0, begin at 000h
049 add 0x11,a
050 mov a,@0x55
051 mov 0x05,a ;port5<-- 0x55
052 bs 0x03,5 ;select PAGE 1
053 call Lab2 ;PAGE jump
054 bc 0x03,5 ;restore
055 jbs 0x15,2
056
; PAGE 1, begin at 400h
417
418 mov a,@0x3f
419 xor 0x12,a
450 Lab2 bc 0x06,3
451 mov a,0x05
45f ret
說明:
052: 將 R3 寄存器的位 5設为 "1" (选择 PAGE 1)。
053: Lab2 將会被編译为 "50",呼叫 PAGE 1 中 "Lab2" 子程序。
054: 將 R3 寄存器的位5 还原为 "0"。
注意:
此例中 "052" 和 "053" 是用来呼叫 PAGE 1 中 "Lab2" 的子程序,假如果沒有 "052" 這行指令,則程序將呼叫 "050" 的位址 (在 PAGE 0中),而非 "450" 的位址 (在 PAGE 1中),如此將发生錯誤。
5.1.3. "BS","BC" 等指令对 I/O Port 的作用:
"BS","BC" 等指令会先有 "读" 再 "写" 的动作,例如 "bc 0x06,3" 指令是將整个 Port 6 (8 pin) 读進 CPU,执行位运算后再写至 Port 6 上。假如 Port 6 有一些 pin 是双向 I/O pin (如 P65) 時,假設当执行 "bc 0x06,3" 時P65 是输入 pin,則 P65 pin 上的内容会被读入再写至 Latch 上,覆蓋原先 Latch 上的内容。因此只要 P65 一直是输入 pin 將不会有問題,一旦 P65 切換为输出,則 Latch 上的内容將是不可預知的。
5.1.4. I/O Port读取的路径:
若仔細研究EM78系列八位微控器的I/O Port构造,就可发現在做"读"I/O Port的动作時(如"mov a,0x06"),所读入内容有两个路径来源,一是I/O pin上的内容,另一是输出Latch上的内容,而由I/O控制寄存器決定此读入的路径。
例如I/O pin设计为输入pin時(对应的I/O控制寄存器为"1"),对I/O Port做"读"的动作時,是读到pin上的内容。若I/O pin设计为输出pin時(对应的I/O控制寄存器为"0"),对I/O Port做"读"的动作時,是读到输出Latch上的内容。
5.1.5. WDT (Watchdog Timer)的使用:
WDT是微控器內部RC自振的计時器,其超時溢位(Time-out)的基本周期約18ms,WDT有与TCC共用的倍除器,使得超時溢位(Time-out)的最大周期可至約2.2sec。WDT计時的使能或禁止是可隨時由指令控制的(控制位在IOCE寄存器)。当WDT使能時,其超時溢位將使微控器发生RESET(或喚醒),"wdtc"指令是用来清除WDT,令WDT再从头计時,因此适当的使用"wdtc"指令,可使WDT不会发生RESET。当WDT被禁止時,WDT不会使微控器RESET或喚醒。要特別注意的是,Power-on之後WDT是使能的,如果該应用中並沒有使用WDT,必須在程序的前头用指令將WDT计時禁止。EM78156/256/456就是依上述所設计。
在EM78247/447/248/448/056/P156除了上述的設计外,另有一Code Option決定使能或禁止WDT,其功能如下:
1. 假如应用中有使用WDT,WDT必須以Code Option使能,則在程序中隨時可以用指令使能或禁止WDT计時。注意:Power-on之後WDT是使能的。
2. 假如应用中並沒有使用WDT,WDT可以以Code Option禁止,則WDT是永遠被禁止的,如此可省去須在程序的前头用指令將WDT计時禁止的麻煩。
5.2. 基本设计规则
5.2.1. 设定I/O口的模式:
用户可以单独设定任一支I/O脚为输出模式(Output Mode),或是输入模式(Input Mode)。只要將每个I/O的设定写入累加器(A)中,再將累加器的内容写到I/O控制寄存器中,设定就算完成了。
例1:將PORT6设定为OUTPUT PORT。
PORT6 == 6 ;定义。
MOV A, @0X00 ;设定A = 0。
IOW PORT6, A ;將PORT6设定为输出模式。
例2:將PORT6的低四位设成INPUT PORT;高四位设定为OUTPUT PORT。
PORT6 == 6 ;定义。
MOV A, @0X0F ;设定A= 0X0F,高四位为
IOW PORT6, A ;OUTPUT PORT,低四位为
;INPUT PORT。
5.2.2. 检查寄存器的内容:
检查寄存器的内容有很多种方法,可以用AND的功能,或SUB的功能…等。在做完AND或SUB的功能之后,可以检验状态标志(STATUS FLAG),然后写一个判断式,針对状态标志的結果, 处理个別的情形。
例:判断寄存器0X20內含值是否为0。
CHECK:
MOV A, @0XFF ;设定A = 0XFF。
AND A, 0X20 ;寄存器0X20,和A中的值做and
JBS 0X03, 2 ;若是寄存器0x20为0,则寄存
JMP CHECK ;器0X03的bit2位为1。
;若是寄存器0X20不为零则产生循环。
5.2.3. 简易的循环设计
1.FOR LOOP的设计:
如果用户想让同一段程序执行N次,用户可以利用一个寄存器为计数器,在程序执行前,先將计数寄存器设为N,然后每执行一次,计数器就減一,再跳为原區段执行,直到计数器被減至零。
例:设计一个FOR LOOP循环,让循环連續执行10次。
MOV A, @0X0A ;设A = 0X0A。
MOV 0X10, A ;设定计数值。计数寄存器
LOOP: ;为0X10。
;
;
;
DJZ 0X10 ;递減计数寄存器,若计数
JMP LOOP ;值为0,则跳出循环。
2.IF…THEN… 程序设计:
IF…THEN…的说法就是,如果…就做…。用户可以利用检查两个数值是否相等,例如”IF X = Y THEN GOTO ELSE” 的格式,来完成这种功能。
l 例:判断两个寄存器(0X20, 0X21)的数值是否相等,如果相等,就將标志寄存器设为1。
BUFFER1 == 0X20 ;定义。
BUFFER2 == 0X21
FLAG == 0X22
MOV A, BUFFER ;將BUFFER1的值存入A中。
XOR A, BUFFER2 ;將A的值和BUFFER2的值做xor
JBC 0X03, 2 ;IF BUFFER1 = BUFFER2
JMP FLAG_1 ;THEN
JMP FLAG_0 ;ELSE
FLAG_0:
MOV A, @0
MOV FLAG, A ;设定FLAG为0。
JMP PROCESS
FLAG_1:
MOV A, @1
MOV FLAG, A ;设定FLAG为1。
JMP PROCESS
PROCESS:
5.2.4. 查表程序设计:
在一个沒有規则性的内容转换中,查表程序是相当有用的,用户可以使用查表程序很快速的得到相关内容的转换。
例:设计一个程序,將如下图所示中的PORT5读到的一个数值,将输入内容做转换,然后输出到PORT6的7段显示器上。

上图中开关关闭,I/O引脚可以得到一个低电位,若是开关开启则I/O引脚可以得到一个高电位。

图 5.2 数码管八段说明
7段显示器的接线图如上,我們要編一个表做为读入内容以及输出内容的对映。
|
7段显示器各脚位电位状态 |
PORT6输出 |
PORT5输入 | |||||||
|
H |
G |
F |
E |
D |
C |
B |
A |
16进位数值 |
10进位数值 |
|
0 |
0 |
1 |
1 |
1 |
1 |
1 |
1 |
0X3F |
0 |
|
0 |
0 |
0 |
0 |
0 |
1 |
1 |
0 |
0X06 |
1 |
|
0 |
1 |
0 |
1 |
1 |
0 |
1 |
1 |
0X5B |
2 |
|
0 |
1 |
0 |
0 |
1 |
1 |
1 |
1 |
0X4F |
3 |
|
0 |
1 |
1 |
0 |
0 |
1 |
1 |
0 |
0X66 |
4 |
|
0 |
1 |
1 |
0 |
0 |
1 |
1 |
0 |
0X6D |
5 |
|
0 |
1 |
1 |
1 |
1 |
1 |
0 |
1 |
0X7D |
6 |
|
0 |
0 |
0 |
0 |
0 |
1 |
1 |
1 |
0X07 |
7 |
|
0 |
1 |
1 |
1 |
1 |
1 |
1 |
1 |
0X7F |
8 |
|
0 |
1 |
1 |
0 |
1 |
1 |
1 |
1 |
0X6F |
9 |
|
0 |
1 |
1 |
1 |
0 |
1 |
1 |
1 |
0X77 |
10 |
|
0 |
1 |
1 |
1 |
1 |
1 |
0 |
0 |
0X7C |
11 |
|
0 |
1 |
0 |
1 |
1 |
0 |
0 |
0 |
0X58 |
12 |
|
0 |
1 |
0 |
1 |
1 |
1 |
1 |
0 |
0X5E |
13 |
|
0 |
1 |
1 |
1 |
1 |
0 |
0 |
1 |
0X79 |
14 |
|
0 |
1 |
1 |
1 |
0 |
0 |
0 |
1 |
0X71 |
15 |
程序清单如下:
PC == 0X02 ;定义。
PORT5 == 5
PORT6 == 6
ORG 0X10 ;设定程序起始位址。
MOV A, @0
IOW PORT6 ;设定PORT6为Output口。
MOV A, @0XFF
IOW PORT5 ;设定PORT5为Input口。
JMP START ;跳转到主程序中。
TABLE:;输入及输出对映表。
ADD PC, A
RETL @0X3F
RETL @0X06
RETL @0X5B
RETL @0X4F
RETL @0X66
RETL @0X6D
RETL @0X7D
RETL @0X07
RETL @0X7F
RETL @0X6F
RETL @0X77
RETL @0X7C
RETL @0X58
RETL @0X5E
RETL @0X79
RETL @0X71
START:
MOV A, PORT5
AND A, @0X0F
CALL TABLE
MOV PORT6, A
JMP START
5.2.5. 中断程序的设计
在EM78X56系列的IC中有三种中断信号,分別是:
TCC溢位中断。
PORT6 Change 中断。
外部信号中断。
在说明中断使用方式之前,用户要了解中断寄存器,及与中断息息相关的控制寄存器( Control Register),另外在芯片中預除器( Prescalar )的使用方法,用户也需要住意。
中断信号显示寄存器0X0F各位安排如下:
|
|
BIT7 |
BIT6 |
BIT5 |
BIT4 |
BIT3 |
BIT2 |
BIT1 |
BIT0 |
|
中断信号 |
- |
- |
- |
- |
- |
外部中断标志 |
PORT6 Change |
TCC 溢位标志。 |
寄存器0X0F使用到的有BIT0 ~ BIT2。BIT0在TCC计時器计数溢位時就会被设定,用户可以根据0X0F的BIT0被设定而判定TCC计数溢位。跟TCC配合的还有另一个寄存器---控制寄存器(Control Register,简称CONT)。控制寄存器0X0F各位安排如下:
|
|
BIT7 |
BIT6 |
BIT5 |
BIT4 |
BIT3 |
BIT2 |
BIT1 |
BIT0 |
|
控制信号 |
- |
INT |
TS |
TE |
PAB |
PSR2 |
PSR1 |
PSR0 |
各位的代表意义如下:
□ PSR2 ~ PSR0:TCC/WDT 預除器设定。
|
PSR2 |
PSR1 |
PSR0 |
TCC 比例 |
WDT 比例 |
|
0 |
0 |
0 |
1:2 |
1:1 |
|
0 |
0 |
1 |
1:4 |
1:2 |
|
0 |
1 |
0 |
1:8 |
1:4 |
|
0 |
1 |
1 |
1:16 |
1:8 |
|
1 |
0 |
0 |
1:32 |
1:16 |
|
1 |
0 |
1 |
1:64 |
1:32 |
|
1 |
1 |
0 |
1:128 |
1:64 |
|
1 |
1 |
1 |
1:256 |
1:128 |
FIGURE3.5 PS0 ~ PS2的设定值与預除器和TCC及WDT的比例关係。
□ Bit3預除器配置:
0:TCC
1:WDT
□ Bit4 TCC递增時机:
0:外部信号,触发边沿为正沿触发。
1:外部信号,触发边沿为負沿触发。
□ Bit5 TCC信号来源:
0:內部指令周期触发。
1:外部引脚(第三脚)触发。
□ Bit6 INT使能标志:
0:禁止所有中断产生。
1:使能中断信号。
□ Bit7 无使用。
三种中断产生都有其先前的设定值,接下来会以示例说明。
l 例:写一个程序,將寄存器0X20当做计数器,每当TCC中断产生,就自动加1。
MOV A, @0X0 ;设定 A = 0。
IOW 0X0E ;关闭Watch Dog。
ORG 6 ;设定接下来的程序位址。
CLR 0X20 ;清除寄存器0X20。
JMP TCC_PRO ;跳转到TCC_PRO。
INT_PRO: DISI ;关闭各項中断功能。
CLR 0X0F ;清除中断寄存器。
INC 0X20 ;计数器加1。
RETI ;返回主程序,並使能中断。
TCC_PRO: CLR 0X0F ;清除中断寄存器。
MOV A, @0X01 ;设定 A = 1。
IOW 0X0F ;使能TCC溢位中断产生。
MOV A, 0X40 ;设定 A = 0X40。
CONTW ;將A的值写入控制寄存器。
ENI ;使能中断。
TCC_WAIT: NOP ;等待TCC计数器计数溢位。
NOP ;等待TCC计数器计数溢位。
JMP TCC_WAIT ;等待TCC计数器计数溢位。
TCC中断产生有几个设计的重点:
1. 关闭看门狗计時器(Watch Dog Timer)。
2. 设定控制寄存器(包括預除器、TCC信号来源、触发時机…)。
3. 使能中断(下ENI指令)。
4. 使能TCC中断(设定中断控制寄存器的bit0为1)。
5. 中断服务位址为0X08。
6. 进入中断服务程序首先要將中断禁止,否则会产生重复中断。
7. 中断寄存器0X0F,在进入中断服务程序時可以提供用户判断为何种中断,判断完成之后用户必須自行清除。
8. 由中断服务程序返回主程序应使用指令RETI。
l 例:写一个程序,將寄存器0X20当做计数器,每当PORT6 Change中断产生,就自动加1。
PORT6 == 6 ;定义。
DISI ;中断禁止。
ORG 6 ;设定下一个位址为0X06。
CLR 0X20 ;清除计数寄存器。
JMP PORT6_CH ;跳转到主程序。
DISI
INT_PRO: ;0X08为中断服务程序起始。
NOP
CLR 0X0F ;清除中断标志寄存器。
INC 0X20 ;计数器遞增。
MOV PORT6, PORT6 ;將PORT6的值存入正反器。
RETI ;回主程序。
PORT6_CH:
CLR 0X0F ;清除中断标志寄存器。
MOV A, @0XFF ;设定 A = 0XFF。
IOW PORT6 ;將PORT6设成输入口。
MOV PORT6, PORT6 ;將PORT6的值存入正反器。
ENI ;使能中断。
MOV A, @0X02 ;设定 A = 0X02。
IOW 0X0F ;使能PORT6 Change中
WAIT_INT:
WDTC ;清除Watch Dog Timer。
NOP ;等待PORT6 Change。
NOP ;等待PORT6 Change。
JMP WAIT_INT ;循环。
使用PORT6 Change中断有下列几个步骤。
1. 关闭看门狗计時器(Watch Dog Timer),若看门狗计時器未关闭,用户要定時下WDTC的指令。
2. 清除中断寄存器。
3. 设定PORT6为输出口。
4. 將PORT6的值存入触发器中(这很重要)。
5. 使能中断(下ENI的指令)。
6. 使能PORT6 Change中断(设定中断控制寄存器的bit1为1)。
7. 中断服务程序的启始位址在0X08。
8. 进入中断服务程序首先要將中断禁止,否则会产生嵌套中断。
9. 中断寄存器0X0F,在进入中断服务程序時可以提供用户判断为何种中断,判断完成之后用户必須自行清除。
10. 由中断服务程序返回主程序应使用指令RETI。
l 例:写一个程序,將寄存器0X20当做计数器,每当外部中断产生,就自动加1。
所謂的外部中断就是利用IC外部引脚,針对单片机外部的信号做为信号源来产生中断。EM78系列的外部中断引脚是第4脚,是和PORT6位0合用,所以再使用前要先设定PORT6 , BIT0是要单純用做I/O引脚,或是中断输入引脚。
ORG 6 ;设定启始位址为0X06。
CLR 0X20 ;清除计数器。
JMP EXT_PRO ;跳转到主程序。
INT_EXT:
DISI ;中断禁止。
CLR 0X0F ;清除中断标志。
INC 0X20 ;递增计数寄存器。
RETI ;返回主程序。
EXT_PRO:
CLR 0X0F ;清除中断标志。
MOV A, @0X04 ;A = 0X04。
IOW 0X0F ;使能外部中断信号产生。
MOV A, @0X40 ;A = 0X40。
IOW 0X0E ;设定PORT6, BIT0为中断输入脚
ENI ;返回主程序。
EXT_WAIT:
NOP ;等待外部中断输入。
NOP ;等待外部中断输入。
JMP EX_WAIT ;循环。
外部中断显然比較容易了解。所需注意的項目有:
1. 禁止中断。
2. 设定中断服务程序的地址在0X08。
3. 清除中断标志寄存器。
4. 使能外部中断信号产生(设定中断控制寄存器为0X04)。
5. 將PORT6, BIT0设定成外部中断引脚(设定控制寄存器0X0E, BIT6为1)。
6. 使能中断信号(ENI)。
7. 用户在进入中断服务程序(0X08)時,首先要記得禁止中断(DISI)。
8. 可以由中断标志寄存器判断中段的信号为何产生,判断完之后应自行清除中断标志。
9. 返回主程序時用指令RETI。
以上三支中断程序的写法都是利用无穷循环,所以用户想要看到結果只有結束程序,然后查看计数寄存器(0X20)的计数状況。
5.2.6. 延迟子程序的编写:
在許多程序设计的場合,我們時常会利用到时间延迟子程序,接下来就介紹一个可以控制延迟时间的延迟子程序。
开下面是利用发工具E8-ICE来演示的一个精确的控制延迟时间的程序,选择使用石英振荡器,可以精确的算准延迟时间,时间可以到nanosecond(十亿分之一秒),很神奇。
LP_CNT0 == 0X20 ;定义。
LP_CNT1 == 0X21
MOV A, @2 ;A = 2。
MOV LP_CNT0, A ;设定延迟寄存器0(LP_CNT0)=2
CALL P0_DLY ;呼叫时间延迟子程序。
P0_DLY:
NOP ;调节延迟时间。
MOV A, @200 ;设定 A = 200。
MOV LP_CNT1, A ;设定寄存器LP_CNT1 = 200。
P0_LP:
NOP ;调节延迟时间。
NOP ;调节延迟时间。
NOP ;调节延迟时间。
DJZ LP_CNT1 ;递減LP_CNT1,为0就跳过下一行
JMP P0_LP ;循环。
DJZ LP_CNT0 ;递減LP_CNT0,为0就跳过下一行
JMP P0_DLY ;循环。
RET ;返回主程序。
假设用户所使用的开发工具是E8-ICE,而且所采用的振荡器为石英振荡(4M Hz),並选择指令执行周期为1 Cycle, 2 Clock。这時每执行一个指令的时间为0.5 uS.
用户可以看出在程序中用了两个寄存器来计数(LP_CNT0、LPCNT1),另外也使用了两个循环(P0_DLY、P0_LP),其中在P0_LP中有5个指令,所以在P0_LP这个循环中,执行了有1000个指令。
5X 200= 1000 P0_LP循环总共执行指令数目。
5 + 1000 = 1005 P0_DLY循环总共执行指令数目。
1005 X 2 = 2010
2010 + 1 + 1 = 2012 延迟程序总共执行指令数目
在整个P0_DLY循环中就有2012个指令,每个指令的执行时间为0.5 us。
2012 (instructions) x 0.5 (us/instruction) = 1.006 ms
所以用户可以精确的计算出延迟的时间,用户可以在LP_CNT0设定不同的值,如此可以有各种不同的延迟时间。
l 例:设计一个延迟时间为2ms的程序。
只要在上述程序中在呼叫P0_DEL延迟子程序之前,將LP_CNT0设成4就可以了。
MOV A, @4
MOV LP_CNT0, A
CALL P0_DLY
其余不变。
1005 X 4 = 4020。
4020 + 1 + 1 = 4022。
4022 (instructions) X 0.5 (us) = 2.011 ms
5.3. 应用程序设计实例
5.3.1. 马达控制程序的设计
PORT5输出动作的控制,而且外部接有一推动STEP MOTOR的电路。写一程序驱动STEP MOTOR。
在写程序之前,先介紹STEP MOTOR的动作原理。

图5.3 PORT5步进马达控制图。
P50 0 0 1 1
P51 1 1 0 0
P52 1 0 0 1
P53 0 1 1 0
图5.4 PORT5步进马达控制時序图。
图5.3中可以看出,PORT5接到STEP MOTOR的对应引脚,图5.4可以看出PORT5应該送出的信号。图5.3中P50和P51的输出必須反相,P52和P53的输出必須反相,而P50和P52必須有相位差,假设P50和P52的相位差为90度,于是导出图5.4 的時序图。
图5.4的時序图中,可以看出有四个相位会一直循环,分別是:
|
|
Phase 0 |
Phase 1 |
Phase 2 |
Phase 3 |
|
P50 |
0 |
0 |
1 |
1 |
|
P51 |
1 |
1 |
0 |
0 |
|
P52 |
1 |
0 |
0 |
1 |
|
P53 |
0 |
1 |
1 |
0 |
|
Value |
0x06 |
0x0A |
0x09 |
0x05 |
上表中有四个基本相位数值。所以只要不停的送出这四个相位,STEP MOTOR就会不停的旋转,送出的速度快,STEP MOTOR的转速就快,但是要在STEP MOTOR的旋转极限之內。
PORT5 == 5 ; 定义
; 程序开始
MOV A, @0X0 ;將A设成0X0。
IOW PORT5 ;设定PORT5为输出口。
AGAIN:
MOV A, @0X06 ;设定A的值为0X06。
MOV PORT5, A ;將A的值输出到PORT5。
MOV A, @0X0A ;设定A的值为0X0A。
MOV PORT5, A
MOV A, @0X09 ;设定A = 0X09。
MOV PORT5, A
MOV A, @0X05 ;设定A = 0X05。
MOV PORT5, A ;设定PORT5 = 5。
JMP AGAIN ;循环。
5.3.2. 数码管LED显示
PORT6输出动作的控制,而且外部接有一推动8个七段显示器的电路。编写一程序在8个七段显示器上轮流显示1,2,3,4,5,6,7,8。
下图为控制电路的方块图。

由PORT6单独控制8个七段显示器,利用时间分割(time slice)的显示方式,就可以同時让多个七段显示器同時显示。上图可以看出,若是要让第一个七段显示器显示一个0的值,在PORT6输出的内容值为0X00,前四个位控制要显示的七段显示器,后四个位控制显示的数字。所以要选第0个七段显示器,前四个位要为0;若要显示的值为0,后四个位的值也是为0。
PORT6 == 6 ;定义PORT6
MOV A, @0 ;將A设成0。
IOW PORT6 ;设定PORT6为OUTPUT口
AGAIN:
MOV A, @0X01 ;將A设成0X01
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X12 ;將A设成0X12。
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X23
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X34
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X45
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X56
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X67
MOV PORT6, A ;输出内容到PORT6。
MOV A, @0X78
MOV PORT6, A ;输出内容到PORT6。
JMP AGAIN
5.3.3. D/A变换程序的设计
PORT6的输出接有一个数模转换器(D/A convert)。写一程序产生一个鋸此波。
本例的D/A Convert所采用的方式为R – 2R的方式,所使用的电阻为20K的同一品牌的排阻。因PORT6有8个位,所以在0V-VCC一共有256个阶层。
PORT6 == 6;定义。
MOV A, @0 ;將A设成0。
IOW PORT6 ;將PORT6设成OUTPUT口。
MOV PORT6, A ;PORT6输出内容为0。
AGAIN:
INC PORT6 ;PORT6的值依序递增1。
JMP AGAIN