اتصال 8255 به AT89CX051 در ادامه مطلب
اتصال 8255 به AT89CX051
Using a 8255 to expand the number of io lines for an AT89CX051
Photo showing an 89C2051 on a Dontronics DT104 mounted on a Dontronics DT004 motherboard. The 2051 is driving the 8255 board via a printer port cable. The 8255 is then connected to a Dontronics DT203 switch led board via a prototype board both mounted on another Dontronics DT004.
Another view of the interconnection of the boards. The red clip is supplying power to the 8255 & switch led boards. The white lead is a serial cable to a PC to run the test software below.
On the DT104 board 3 jumpers need to be fitted.
CL to D14
D8 to D12
D9 to D15
Sample program written by Peter Averill.
$mod2051
CR EQU 0dh ; carriage return
LF EQU 0ah ; line feed
BAUD_9600 EQU 0fdh ; 9600 baud
a0 equ p3.5
a1 equ p3.3
notrd equ p3.2
notwr equ p3.4
DSEG AT 20H
databyte: ds 1
ORG 40H ; stack origin
stack: DS 20H ; stack depth
CSEG
ORG 0000H ; power on/reset vector
jmp cold_start
ORG 0003H ; external interrupt 0 vector
reti ; undefined
ORG 000BH ; timer 0 overflow vector
reti
ORG 0013H ; external interrupt 1 vector
reti ; undefined
ORG 001BH ; timer 1 overflow vector
reti ; undefined
ORG 0023H ; serial I/O interrupt vector
jnb RI,exit
mov a,SBUF
setb F0 ;flag used to indicate that a chr
;has been rx ed
clr RI
exit:
reti
ORG 40H ; begin constant data space
mess: DB CR,LF,LF,LF,LF,LF,LF,LF,LF,LF,LF,LF,LF,LF,LF,LF
db LF,LF,LF,LF,LF,LF,LF,LF,LF,LF
db 'Victoria University TAFE',LF,CR
db 'Electronics Technology Sunshine',LF,CR
db '________________________________',LF,CR
db 'Atmel 89C2051 8255 io line expander',LF,CR
db 'Test using Dontronics DT104 processor board',LF,CR
db 'and DT203 switch led board',LF,CR
db 'Written by Peter Averill',LF,LF,LF,CR
db 'Press:-',LF,CR
db ' 0-7 to toggle 8255 port A outputs',CR,LF
db ' w to walk 8255 port A outputs',CR,LF
db ' i to read 8255 port B',CR,LF
db ' r to re-start',CR,LF,LF,LF,0
USING 0 ; register bank zero
cold_start:
mov sp, #(stack-1) ; initialize stack pointer
call initialize ; initialize controller registers
mov p1, #0ffh ;
mov p3, #0ffh ;
mov a,#08ah
call write_control
mov databyte,#0
call write_a
setb TI
mov dptr, #mess
call send_string
top: setb ES
back: orl PCON, #1
jnb F0, back ;check if char has been rx ed
clr ES
cjne a,#30h,one
cpl 0
call write_a
one: cjne a,#31h,two
cpl 1
call write_a
two: cjne a,#32h,three
cpl 2
call write_a
three: cjne a,#33h,four
cpl 3
call write_a
four: cjne a,#34h,five
cpl 4
call write_a
five: cjne a,#35h,six
cpl 5
call write_a
six: cjne a,#36h,seven
cpl 6
call write_a
seven: cjne a,#37h,letter_w
cpl 7
call write_a
letter_w: cjne a,#'w',letter_i
call walk
letter_i: cjne a,#'i',letter_r
call input
letter_r: cjne a,#'r',error
clr F0
jmp cold_start
error:
clr F0 ;clear flag 0 no char waiting
jmp top
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
write_control:
setb a0
setb a1
setb notrd
mov p1,a
clr notwr
nop
nop
setb notwr
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
write_a:
clr a0
clr a1
setb notrd
mov p1,databyte
clr notwr
nop
nop
setb notwr
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
read_b:
mov p1,#0ffh
setb a0
clr a1
setb notwr
clr notrd
nop
nop
mov a,p1
nop
nop
setb notrd
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
disp_hex:
push acc
push acc
rr a
rr a
rr a
rr a
anl a,#0fh
cjne a,#10,dh1
dh1: jb cy,dh2
add a,#07h
dh2: add a,#30h
call send_char
pop acc
anl a,#0fh
cjne a,#10,dh3
dh3: jb cy,dh4
add a,#07h
dh4: add a,#30h
call send_char
pop acc
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
input:
call read_b
call disp_hex
past: mov a,#0ah
call send_char
mov a,#0dh
call send_char
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
walk:
mov a,#01
wloop: mov databyte, a
call write_a
push acc
mov a, #0ffh
call delay_ms
call delay_ms
call delay_ms
pop acc
clr c
rlc a
jnc wloop
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
initialize:
; Initialize controller registers.
mov PCON, #0 ; initialize power control register
mov IE, #0 ; deactivate all interrupts
mov SCON, #01000000b ; serial port mode one
mov TMOD, #00100001b ; timer one 8-bit auto-reload,
; timer zero 16-bit
mov TH1, #BAUD_9600 ; timer one reload value
mov TCON, #01000000b ; start timer one
setb REN ;enable rx int
setb EA ;global int enable
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
send_string:
; Transmit string pointed to by DPTR.
; String may be of any length, but must be null-terminated.
push acc
push dpl
push dph
ss1:
clr a
movc a, @a+dptr ; get character
jz ss2 ; check for terminator
call send_char ; send character
inc dptr ; point to next character
jmp ss1
ss2:
pop dph
pop dpl
pop acc
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
send_char:
; Wait for transmitter to clear, add even parity bit to character
; in accumulator and transmit it. Does not wait for transmitter
; to clear before returning.
jnb TI, $ ; wait here for transmitter to clear
clr TI ; clear transmit flag
push acc ; save char
mov SBUF, a ; load character into transmitter
pop acc ; restore char
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
delay_ms:
; Delay for one mS times the value in the accumulator.
push acc
push b
mov b, #0
dd:
djnz b, $ ; 500 uS @ 12 MHz
djnz b, $ ; 500 uS @ 12 MHz
djnz acc, dd
pop b
pop acc
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
delay_sec:
; Delay for one second times the value in the accumulator.
push acc
push b
mov b, a
ddd:
mov a, #250
call delay_ms ; 250 mS
call delay_ms ; 500 mS
call delay_ms ; 750 mS
call delay_ms ; 1000 mS
djnz b, ddd
pop b
pop acc
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
END

