6502/bins/lcd.s
2022-05-12 21:36:39 +09:30

86 lines
1.6 KiB
ArmAsm

PORTB = $6000
PORTA = $6001
DDRB = $6002
DDRA = $6003
E = %10000000
RW = %01000000
RS = %00100000
.org $8000
reset:
lda #%11111111 ; set all pins on port B to output
sta DDRB
lda #%11100000 ; set top 3 pins on port A to output
sta DDRA
lda #%00111000 ; set 8-bit mode, 2 line display, 5x8 font.
jsr command_to_lcd
lda #%00001110 ; set display and curson on, do not blink
jsr command_to_lcd
lda #%00000110 ; set entry mode increment and display shift off
jsr command_to_lcd
lda #%00000001
jsr command_to_lcd
ldx #0
print:
lda message,x
beq loop ; load sets zero flag (checked by beq) when it loads a zero byte.
jsr ASCII_to_lcd
inx
jmp print
loop:
jmp loop
; asciiz appends a 0 byte to the string
message: .asciiz "Hello, world! :D"
lcd_wait:
pha ; save porta to stack
lda #%00000000 ; set PORTB to input
sta DDRB
lcdbusy:
lda #RW
sta PORTA
lda #(RW | E)
sta PORTA
lda PORTB
and #%10000000 ; check LCD busy flag
bne lcdbusy ; branch if it is NOT set
lda #RW
sta PORTA
lda #%11111111 ; set PORTB to output again
sta DDRB
pla ; load stack value back to porta
rts ; RETURN
command_to_lcd:
jsr lcd_wait ; ensure LCD is not busy before sending instruction
sta PORTB
lda #0 ; clear RS/RW/E bits
sta PORTA
lda #E ; set enable bit to send instruction
sta PORTA
lda #0 ; clear RS/RW/E bits
sta PORTA
rts ; RETURN
ASCII_to_lcd:
jsr lcd_wait ; ensure LCD is not busy before sending instruction
sta PORTB
lda #RS ; RS set
sta PORTA
lda #(RS | E) ; RS and E set
sta PORTA
lda #RS ; RS set
sta PORTA
rts ; RETURN
.org $fffc
.word reset
.word $0000