⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lcd_1602_text.asm

📁 AVR单片机通过4位总线访问LCD1602
💻 ASM
字号:
;LCD 1602 使用4位数据总线测试
;2008-1-3~2008-1-5 --by BG1
.include "m48def.inc"
		.EQU    PD_1602_RS = 0
		.EQU    PD_1602_RW = 1
		.EQU    PD_1602_E = 2
		.EQU    PD_1602_D4 = 4
		.EQU    PD_1602_D5 = 5
		.EQU    PD_1602_D6 = 6
		.EQU    PD_1602_D7 = 7
		.EQU    LCD_1602_BF_BIT = 7

		.EQU    LCD_1602_COM_CLR = $1
		.EQU    LCD_1602_COM_CURSORRESET = $2
		.EQU    LCD_1602_COM_DISPALYMODE = $4
;			.EQU    LCD_1602_MOVE_TO = 1    ;0-LEFT,1-RIGHT
;			.EQU    LCD_1602_S_C_MOVE = 0    ;0-CURSOR MOVE,1-SCREEN MOVE
		.EQU    LCD_1602_COM_DISPLAYSTATE = $8
;			.EQU    LCD_1602_DISPLAY = 2		 ;1-ON,0-OFF
;			.EQU    LCD_1602_CURSOR = 1		 ;1-ON,0-OFF
;			.EQU    LCD_1602_CURSOR_BLINK = 0    ;1-BLINK,0-STATIC
		.EQU    LCD_1602_COM_DISPLAYMOVE = $10
;			;|LCD_1602_S_C_MOVE<<3|LCD_1602_MOVE_TO<<2
		.EQU    LCD_1602_COM_DISPLAYSETTING = $20
;			.EQU    LCD_1602_BUS_WIDTH_8 = 4    ;0-4BIT(D4~D7),1-8BIT
;			.EQU    LCD_1602_TWO_LINE = 3		 ;1-TWO LINE,0-ONE LINE
;			.EQU    LCD_1602_CHR_10 = 2		 ;0-5*7 CHAR(TWO LINE),1-5*10 CHAR(ONE LINE)
		.EQU    LCD_1602_COM_USERCHAR = $40
		.EQU    LCD_1602_COM_LOCATE = $80

.DSEG
		.EQU    LCD_1602_SETTINGS = $120
			.EQU    LCD_1602_BUS_WIDTH_8 = 4    ;0-4BIT(D4~D7),1-8BIT
			.EQU    LCD_1602_TWO_LINE = 3		 ;1-TWO LINE,0-ONE LINE
			.EQU    LCD_1602_CHR_10 = 2		 ;0-5*7 CHAR(TWO LINE),1-5*10 CHAR(ONE LINE)
			.EQU    LCD_1602_MOVE_TO = 1    ;0-LEFT,1-RIGHT
			.EQU    LCD_1602_S_C_MOVE = 0    ;0-CURSOR MOVE,1-SCREEN MOVE
		.EQU    LCD_1602_STATE = $121
			.EQU    LCD_1602_DISPLAY = 2		 ;1-ON,0-OFF
			.EQU    LCD_1602_CURSOR = 1		 ;1-ON,0-OFF
			.EQU    LCD_1602_CURSOR_BLINK = 0    ;1-BLINK,0-STATIC
		.EQU    LCD_1602_LOC = $122
.ESEG
.CSEG
		rjmp    RESET		 ;复位处理		 
		rjmp    EXT_INT0    ;IRQ0处理    
		rjmp    EXT_INT1    ;IRQ1处理    
		rjmp    PCINT0_INT    ;PCINT0处理    
		rjmp    PCINT1_INT    ;PCINT1处理    
		rjmp    PCINT2_INT    ;PCINT2处理    
		rjmp    WDT_INT		 ;看门狗定时器处理		 
		rjmp    TIM2_COMPA    ;定时器2    比较A处理
		rjmp    TIM2_COMPB    ;定时器2    比较B处理
		rjmp    TIM2_OVF    ;定时器2    溢出处理    
		rjmp    TIM1_CAPT    ;定时器1    捕获处理    
		rjmp    TIM1_COMPA    ;定时器1    比较A处理
		rjmp    TIM1_COMPB    ;定时器1    比较B处理
		rjmp    TIM1_OVF    ;定时器1    溢出处理    
		rjmp    TIM0_COMPA    ;定时器0    比较A处理
		rjmp    TIM0_COMPB    ;定时器0    比较B处理
		rjmp    TIM0_OVF    ;定时器0    溢出处理		 
		rjmp    SPI_STC		 ;SPI传输结束处理		 
		rjmp    USART_RXC    ;USART,RX    结束处理    
		rjmp    USART_UDRE    ;USART,UDR    空处理    
		rjmp    USART_TXC    ;USART,TX Complete处理
		rjmp    ADC_INT		 ;ADC转换结束处理		 
		rjmp    EE_RDY		 ;EEPROM    就绪处理		 
		rjmp    ANA_COMP    ;模拟比较器处理		     
		rjmp    TWI_INT		 ;两线串行接口处理		     
		rjmp    SPM_RDY		 ;SPM就绪处理		 

RESET:    
		ldi    r16,high(RAMEND)    ;主程序		 
		out    SPH,r16				  ;设置堆栈指针为RAM的顶部
		ldi    r16,low(RAMEND)
		out    SPL,r16
		sei						   ;使能中断
		RJMP START
ADC_INT:
		RETI
;====================================================
EXT_INT0:
		RETI
;====================================================
EXT_INT1:
		RETI
;====================================================
PCINT0_INT:
		RETI
;====================================================
PCINT1_INT:
		RETI
;====================================================
PCINT2_INT:
		RETI
;====================================================
WDT_INT:
		RETI
;====================================================
TIM2_COMPA:
		RETI
;====================================================
TIM2_COMPB:
		RETI
;====================================================
TIM2_OVF:
		RETI
;====================================================
TIM1_CAPT:
		RETI
;====================================================
TIM1_COMPA:
		RETI
;====================================================
TIM1_COMPB:
		RETI
;====================================================
TIM1_OVF:
		RETI
;====================================================
TIM0_COMPA:
		RETI
;====================================================
TIM0_COMPB:
		RETI
;====================================================
TIM0_OVF:
		RETI
;====================================================
SPI_STC:
		RETI
;====================================================
USART_RXC:
		RETI
;====================================================
USART_UDRE:
		RETI
;====================================================
USART_TXC:
		RETI
;====================================================
EE_RDY:
		RETI
;====================================================
ANA_COMP:
		RETI
;====================================================
TWI_INT:
		RETI
;====================================================
SPM_RDY:
		RETI
;====================================================
LCD_1602_GET_4BIT_BF:    ;BF IN R16.7
		PUSH R17
		IN R16,DDRD
		CBR R16,1<<PD_1602_D4|1<<PD_1602_D5|1<<PD_1602_D6|1<<PD_1602_D7
		OUT DDRD,R16
		IN R16,PORTD
		SBR R16,1<<PD_1602_RW
		CBR R16,1<<PD_1602_RS|1<<PD_1602_E|1<<PD_1602_D4|1<<PD_1602_D5|1<<PD_1602_D6|1<<PD_1602_D7
		OUT PORTD,R16
		SBR R16,1<<PD_1602_E
		OUT PORTD,R16
		NOP
		IN R17,PIND
		ANDI R17,$F0
		CBR R16,1<<PD_1602_E
		OUT PORTD,R16
		SBR R16,1<<PD_1602_E
		OUT PORTD,R16
		NOP
		PUSH R17
		IN R17,PIND
		CBR R16,1<<PD_1602_E
		OUT PORTD,R16
		MOV R16,R17
		POP R17
		SWAP R16
		ANDI R16,$F
		OR R17,R16
		IN R16,DDRD
		SBR R16,1<<PD_1602_D4|1<<PD_1602_D5|1<<PD_1602_D6|1<<PD_1602_D7
		OUT DDRD,R16
		MOV R16,R17
		POP R17
		RET
;====================================================
LCD_1602_WAIT_BF_CLEAR:
		RCALL LCD_1602_GET_4BIT_BF
		SBRC R16,LCD_1602_BF_BIT
		RJMP LCD_1602_WAIT_BF_CLEAR
		RET
;====================================================
LCD_1602_4BIT_INIT:
		IN R16,DDRD
		SBR R16,1<<PD_1602_RS|1<<PD_1602_RW|1<<PD_1602_E|1<<PD_1602_D4|1<<PD_1602_D5|1<<PD_1602_D6|1<<PD_1602_D7
		OUT DDRD,R16
   LCD_1602_4BIT_INIT_1:
		LDI R16,LCD_1602_COM_DISPLAYSETTING|1<<LCD_1602_BUS_WIDTH_8    ;8BIT
		RCALL LCD_1602_W_4BIT_CMD
		RCALL LCD_1602_GET_4BIT_BF
		SBRS R16,LCD_1602_BF_BIT
		RJMP LCD_1602_4BIT_INIT_1
		LDI R16,LCD_1602_COM_DISPLAYSETTING|0<<LCD_1602_BUS_WIDTH_8|1<<LCD_1602_TWO_LINE    ;4BIT
		RCALL LCD_1602_W_CMD
		LDI R16,LCD_1602_COM_DISPLAYSTATE|0<<LCD_1602_DISPLAY|0<<LCD_1602_CURSOR|0<<LCD_1602_CURSOR_BLINK
		RCALL LCD_1602_W_CMD
		LDI R16,LCD_1602_COM_CLR
		RCALL LCD_1602_W_CMD
		LDI R16,LCD_1602_COM_DISPALYMODE|1<<LCD_1602_MOVE_TO|0<<LCD_1602_S_C_MOVE
		RCALL LCD_1602_W_CMD
		LDI R16,LCD_1602_COM_DISPLAYSTATE|1<<LCD_1602_DISPLAY|0<<LCD_1602_CURSOR|0<<LCD_1602_CURSOR_BLINK
		RCALL LCD_1602_W_CMD
		LDI R16,0
		LDI R30,LOW(USER_CHAR*2)
		LDI R31,HIGH(USER_CHAR*2)
		RCALL LCD_1602_USER_CHAR
		RET
;====================================================
LCD_1602_W_CMD:
		PUSH R16
		RCALL LCD_1602_WAIT_BF_CLEAR
		POP R16
		RCALL LCD_1602_W_4BIT_CMD
		SWAP R16
		RCALL LCD_1602_W_4BIT_CMD
		RET
;====================================================
LCD_1602_W_RAM_STRING:    ;R30:R31 POINT TO STRING,$FF FOR END
		LD R16,Z+
		CPI R16,$FF
		BREQ LCD_1602_W_RAM_STRING_END
		PUSH R16
		PUSH R17
		LDS R16,LCD_1602_LOC
		INC R16
		STS LCD_1602_LOC,R16
		LDI R17,0
		BST R16,6
		BLD R17,0
		ANDI R16,$3F
		CPI R16,$11
		BRNE LCD_1602_W_RAM_STRING_1
		CPI R17,1
		BREQ LCD_1602_W_RAM_STRING_1
		LDI R17,1
		LDI R16,0
		RCALL LCD_1602_SET_LOC
   LCD_1602_W_RAM_STRING_1:
		POP R17
		POP R16
		RCALL LCD_1602_W_DATA
		RJMP LCD_1602_W_RAM_STRING
   LCD_1602_W_RAM_STRING_END:
		RET
;====================================================
LCD_1602_W_FLASH_STRING:    ;R30:R31 POINT TO STRING,$FF FOR END
		LPM R16,Z+
		CPI R16,$FF
		BREQ LCD_1602_W_FLASH_STRING_END
	   PUSH R16
		PUSH R17
		LDS R16,LCD_1602_LOC
		INC R16
		STS LCD_1602_LOC,R16
		LDI R17,0
		BST R16,6
		BLD R17,0
		ANDI R16,$3F
		CPI R16,$11
		BRNE LCD_1602_W_FLASH_STRING_1
		CPI R17,1
		BREQ LCD_1602_W_FLASH_STRING_1
		LDI R17,1
		LDI R16,0
		RCALL LCD_1602_SET_LOC
   LCD_1602_W_FLASH_STRING_1:
		POP R17
		POP R16
		RCALL LCD_1602_W_DATA
		RJMP LCD_1602_W_FLASH_STRING
   LCD_1602_W_FLASH_STRING_END:
		RET
;====================================================
LCD_1602_W_DATA:
		PUSH R16
		RCALL LCD_1602_WAIT_BF_CLEAR
		POP R16
		RCALL LCD_1602_W_4BIT_DATA
		SWAP R16
		RCALL LCD_1602_W_4BIT_DATA
		RET
;====================================================
LCD_1602_W_4BIT_CMD:
		PUSH R17
		PUSH R16
		IN R17,PORTD
		CBR R17,1<<PD_1602_D4|1<<PD_1602_D5|1<<PD_1602_D6|1<<PD_1602_D7|1<<PD_1602_RS|1<<PD_1602_E|1<<PD_1602_RW
		ANDI R16,$F0
		OR R17,R16
		OUT PORTD,R17
		SBR R17,1<<PD_1602_E
		OUT PORTD,R17
		CBR R17,1<<PD_1602_E
		OUT PORTD,R17
		POP R16
		POP R17
		RET
;====================================================
LCD_1602_W_4BIT_DATA:
		PUSH R17
		PUSH R16
		IN R17,PORTD
		CBR R17,1<<PD_1602_D4|1<<PD_1602_D5|1<<PD_1602_D6|1<<PD_1602_D7|1<<PD_1602_E|1<<PD_1602_RW
		SBR R17,1<<PD_1602_RS
		ANDI R16,$F0
		OR R17,R16
		OUT PORTD,R17
		SBR R17,1<<PD_1602_E
		OUT PORTD,R17
		CBR R17,1<<PD_1602_E
		OUT PORTD,R17
		POP R16
		POP R17
		RET
;====================================================
LCD_1602_USER_CHAR:	;R16:BEGIN CHAR,Z:POINT
		LSL R16
		LSL R16
		LSL R16
		ORI R16,LCD_1602_COM_USERCHAR
		RCALL LCD_1602_W_CMD
	LCD_1602_USER_CHAR_LOOP:
		LPM R16,Z+
		CPI R16,$FF
		BREQ LCD_1602_USER_CHAR_END
		RCALL LCD_1602_W_DATA
		RJMP LCD_1602_USER_CHAR_LOOP
	LCD_1602_USER_CHAR_END:
		RET
;====================================================
LCD_1602_SET_LOC:    ;X IN R16(0~$28),Y IN R17(0~1)
		BST R17,0
		BLD R16,6
		STS LCD_1602_LOC,R16
		ORI R16,LCD_1602_COM_LOCATE
		RCALL LCD_1602_W_CMD
		RET
;====================================================
START:
		LDI R16,0<<LCD_1602_BUS_WIDTH_8|1<<LCD_1602_TWO_LINE|0<<LCD_1602_CHR_10|1<<LCD_1602_MOVE_TO|0<<LCD_1602_S_C_MOVE
		STS LCD_1602_SETTINGS,R16
		RCALL LCD_1602_4BIT_INIT
		LDI R16,0
		LDI R17,0
		RCALL LCD_1602_SET_LOC
		LDI R30,LOW(TEST_MSG1*2)
		LDI R31,HIGH(TEST_MSG1*2)
		RCALL LCD_1602_W_FLASH_STRING
		LDI R16,0
		LDI R30,LOW(BATTERY_CHAR*2)
		LDI R31,HIGH(BATTERY_CHAR*2)
		RCALL LCD_1602_USER_CHAR		;NOTE AFTER SET USER CHAR ,LOCATE WILL AUTO GOTO 0,0
		LDI R16,8
		LDI R17,0
		RCALL LCD_1602_SET_LOC
		LDI R30,LOW(TEST_MSG1*2)
		LDI R31,HIGH(TEST_MSG1*2)
		RCALL LCD_1602_W_FLASH_STRING

		RJMP MAIN_LOOP
;====================================================
MAIN_LOOP:
		RJMP MAIN_LOOP
;====================================================
TEST_MSG:
		.DB '1','6','0','2',' ','t','e','s','t',' ','4','b','i','t',' ','D','a','t','a','B','u','s','.',' ','-','-','b','y',' ','B','G','1',$ff,0
USER_CHAR:
LINE_CHAR:
		.DB $00,$00,$00,$00,$00,$00,$1F,$00
		.DB $00,$1F,$00,$00,$00,$00,$00,$00
BATTERY_CHAR:
		.DB $E,$1B,$11,$11,$11,$11,$1F,$00
		.DB $E,$1B,$11,$11,$11,$1F,$1F,$00
		.DB $E,$1B,$11,$11,$1F,$1F,$1F,$00
		.DB $E,$1B,$11,$1F,$1F,$1F,$1F,$00
		.DB $E,$1B,$1F,$1F,$1F,$1F,$1F,$00
		.DB $E,$1F,$1F,$1F,$1F,$1F,$1F,$00,$FF,0
TEST_MSG1:
		.DB 0,1,2,3,4,5,6,7,$FF,0
;====================================================
      .EXIT
 
 

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -