打印
[PIC®/AVR®/dsPIC®产品]

检测按键并输出至数码管显示不正确

[复制链接]
1083|2
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
JLennon|  楼主 | 2018-2-1 15:52 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 JLennon 于 2018-2-1 15:53 编辑

程序如下,proteus代码见附件,按键K8,K12,K16无法显示,请教是哪里出错了?实在没找到原因,谢谢赐教。
  LIST P=18F4520                                            ;--- 器件型号定义 ---
                #include <P18F4520.INC>                            ;--- 器件的寄存器头文件包含 ---
                ;--------------------------------------------------------------------------------
                ;--- 单片机配置字配置区 ---
                CONFIG OSC = INTIO67                        ;--- 配置时钟源为内部RC振荡器 ---
                CONFIG WDT = OFF                                     ;--- 禁止看门狗功能 ---
                CONFIG DEBUG = OFF                            ;--- 禁止调试功能 ---
                CONFIG LVP = OFF                                ;--- 禁止低电压编程功能 ---
                CONFIG PBADEN = OFF                                   ;--- 配置RB端口全为数字IO引脚 ---
                ;--------------------------------------------------------------------------------
                ;--- 全局变量定义区 ---
                CBLOCK 0x10
                        KEYTEMP
                        KEY
                        DELAY_A
                        DELAY_B
                        DELAY_C
                ENDC
                ;--------------------------------------------------------------------------------
                ;--- 程序的开始执行处 ---
                ORG 0                                                                   ;--- 单片机复位地址 ---
                GOTO START                                                        ;--- 跳到主程序 ---
                ORG 0x30                                                        ;--- 主程序入口地址 ---
START:        NOP
                ;--------------------------------------------------------------------------------
                ;--- 初始化内部时钟源 ---
                MOVLW 0x70
                MOVWF OSCCON                                                ;--- 选择内部8MHZ的RC振荡器 ---
                BCF OSCTUNE,PLLEN                                        ;--- 禁止内部4倍PLL功能 ---
                ;--------------------------------------------------------------------------------
                ;--- 初始化GPIO引脚 ---
                CLRF WREG
                MOVWF TRISD                                                        ;--- 配置RD端口为输出方向 ---
                MOVWF LATD                                                        ;--- 让RD端口输出全为低电平 ---
                BCF INTCON2,RBPU                                        ;--- 使能RB端口的内部弱上拉功能 ---
                ;--------------------------------------------------------------------------------
                ;--- 初始化相关变量 ---               
                MOVLW 0x0F
                MOVWF TRISB                                                        ;--- 配置RB7..4为输出引脚,RB3..0为输入引脚 ---
                MOVWF LATB                                                        ;--- RB7..4输出低电平 ---
                ;--------------------------------------------------------------------------------
                ;--- 主程序:实现4X4矩阵键盘,将按键值送到LED数码管上显示 ---
MAIN:        NOP
                MOVF PORTB,W                                                ;--- 检测是否有键按下 ---
                ANDLW 0x0F
                MOVWF KEYTEMP
                MOVLW 0x0F
                CPFSEQ KEYTEMP
                GOTO KEYA                                                        ;--- 有键按下,则跳到指定处 ---
                GOTO MAIN                                                        ;--- 无键按下,则继续检测 ---
KEYA:        CALL DELAY                                                        ;--- 去按键抖动 ---
                MOVF PORTB,W                                                ;--- 检测是否真得有键按下 ---
                ANDLW 0x0F
                MOVWF KEYTEMP
                MOVLW 0x0F
                CPFSEQ KEYTEMP
                GOTO KEYB                                                        ;--- 真得有键按下,则跳到指定处 ---
                GOTO MAIN                                                        ;--- 表示无键按下 ---
KEYB:        MOVLW 0xF0                                                        ;--- 读取当前值之后,将行和列方向交换 ---
                MOVWF TRISB
                MOVWF LATB
                MOVF PORTB,W                                                ;--- 读取当前按键的代码值 ---
                ANDLW 0xF0
                IORWF KEYTEMP                                                ;--- 和上次读到的按键代码值组合 ---
                CLRF KEY
KEYD:        MOVF KEY,W                                                        ;--- 将读取的按键代码值与KEYTAB表中值比较 ---
                ADDWF WREG,W
                CALL KEYTAB
                CPFSEQ KEYTEMP
                GOTO KEYC                                                        ;--- 没有找到,则找下一个按键代码值 ---
                GOTO FIND                                                        ;--- 找到键值代码,跳到指定处 ---
KEYC:        INCF KEY
                MOVLW 0x10
                CPFSLT KEY
                GOTO NOFIND                                                        ;--- 在按键代码值中没有找到,跳到指定处 ---
                GOTO KEYD
FIND:        MOVF KEY,W                                                        ;--- 将找到的键值通过查找数码管显示代码值 ---
                ADDWF WREG,W
                CALL LEDSEG
                MOVWF LATD                                                        ;--- 送出去显示 ---
NOFIND:        NOP
WAIT:        MOVF PORTB,W                                                ;--- 等待按键释放 ---
                ANDLW 0xF0
                MOVWF KEYTEMP
                MOVLW 0xF0
                CPFSEQ KEYTEMP
                GOTO WAIT
                MOVLW 0x0F                                                        ;--- 将行和列方向交换 ---
                MOVWF TRISB
                MOVWF LATB
                GOTO MAIN                                                        ;--- 跳到主程序开始处 ---
                ;--------------------------------------------------------------------------------
                ;--- 4x4矩阵键盘代码值 ---
KEYTAB:        ADDWF PCL,F
                DT 0xEE,0xED,0xEB,0xE7
                DT 0xDE,0xDD,0xDB,0xD7
                DT 0xBE,0xBD,0xBB,0xB7
                DT 0x7E,0x7D,0x7B,0x77
                ;--------------------------------------------------------------------------------
                ;--- 定义数码管显示0-9,A-F的笔段代码 ---
LEDSEG:        ADDWF PCL,F
                DT 0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F
                DT 0x77,0x7C,0x39,0x5E,0x79,0x71
                ;--------------------------------------------------------------------------------
                ;--- 延时子程序 ---
DELAY:        MOVLW 0x01
                MOVWF DELAY_A
DLY_A:        MOVLW 0x10
                MOVWF DELAY_B
DLY_B:        MOVLW 0xFF
                MOVWF DELAY_C
DLY_C:        DECFSZ DELAY_C
                GOTO DLY_C
                DECFSZ DELAY_B
                GOTO DLY_B
                DECFSZ DELAY_A
                GOTO DLY_A
                RETURN               
                END
               


KEY_4X4_ASM.zip

56.73 KB

沙发
郑朝清| | 2018-2-1 17:13 | 只看该作者
汇编!牛人啊

使用特权

评论回复
板凳
JLennon|  楼主 | 2018-2-2 14:36 | 只看该作者
搞定了,错误定位在LINE101,DEF的段码存放在0x100处,超过了BSR默认的地址范围(0x00~0xFF),把代码上移调整到地址0xFF之内,问题解决。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

147

主题

689

帖子

8

粉丝