?? 9821h620.asm
字號:
;Use RAM: WORK
S_DecOffTime:
BTFSC R_OffTimerH,7
GOTO L_DecOffTimeRet ;[R_OffTimerH].7=1(不自動關機) 轉
MOVFW R_OffTimerH
IORWF R_OffTimerL,0
BTFSC STATUS,Z
GOTO L_DecOffTimeOver ;[R_OffTimerH:R_OffTimerL]=0 轉,準備關機
MOVLW 1 ;\
SUBWF R_OffTimerL,1 ; | [R_OffTimerH:R_OffTimerL]-1
MOVLW 0 ; | ->R_OffTimerH:R_OffTimerL
SUBWFC R_OffTimerH,1 ;/
GOTO L_DecOffTimeRet
L_DecOffTimeOver:
MOVLW 40H
MOVWF R_WorkStatus ;40H->R_WorkStatus 準備關機
L_DecOffTimeRet:
RETURN
;------------------------------------------------------------------------------
;子程序S_CaliCodeProc ;[R_PubCnt1].7:4=0 處理重量標定數據
;Input: R_CaliMarkH:R_CaliMarkL
; R_CaliCode0H:R_CaliCode0L
; R_SteadyCodeH:R_SteadyCodeL
;Output: R_CaliDataH:R_CaliDataL
;Call: S_AddSub1,S_Mul2Sub1
; S_CalcABS
; S_Divis
;Use RAM: WORK,R_Count,R_PubCnt0
; R_PubReg1:R_PubReg0,R_PubReg3:R_PubReg2,R_PubReg5:R_PubReg4
S_CaliCodeProc:
MOVFW R_CaliMarkL ;\
MOVWF R_PubReg0 ; | [R_CaliMarkH:R_CaliMarkL]
MOVFW R_CaliMarkH ; | ->R_PubReg1:R_PubReg0
MOVWF R_PubReg1 ;/
S_CaliCodeComm: ;標定時計算每個內碼相當于重量的分度數×65536->R_CaliDataH:R_CaliDataL
MOVFW R_PubReg1
ANDLW 0FFH
BTFSC STATUS,Z
GOTO L__CaliCodeP_Ret ;[R_PubReg1]=0(標定分度值<1000) 轉,返回
;下面的程序將4位BCD碼[R_PubReg1:R_PubReg0]轉換為二進制數->R_PubReg3:R_PubReg2
CLRF R_PubReg2 ;0->R_PubReg2
CLRF R_PubReg3 ;0->R_PubReg3
MOVLW 4
MOVWF R_PubCnt0 ;4->R_PubCnt0
L_BCD2HexLoop:
CLRF R_PubReg4 ;0->R_PubReg4
CLRF R_PubReg5 ;0->R_PubReg5
MOVLW 4
MOVWF R_Count ;4->R_Count
L_BCD2HexL_1:
RLF R_PubReg0,1
RLF R_PubReg1,1
RLF R_PubReg4,1
DECFSZ R_Count,1
GOTO L_BCD2HexL_1
;
CALL S_AddSub1 ;[R_PubReg3:R_PubReg2]+[R_PubReg5:R_PubReg4]->R_PubReg3:R_PubReg2
CALL S_Mul2Sub1 ;[R_PubReg3:R_PubReg2]×2->R_PubReg3:R_PubReg2
MOVFW R_PubReg2 ;\
MOVWF R_PubReg4 ; | [R_PubReg3:R_PubReg2]
MOVFW R_PubReg3 ; | ->R_PubReg5:R_PubReg4
MOVWF R_PubReg5 ;/
CALL S_Mul2Sub1 ;[R_PubReg3:R_PubReg2]×2->R_PubReg3:R_PubReg2
CALL S_Mul2Sub1 ;[R_PubReg3:R_PubReg2]×2->R_PubReg3:R_PubReg2
CALL S_AddSub1 ;[R_PubReg3:R_PubReg2]+[R_PubReg5:R_PubReg4]->R_PubReg3:R_PubReg2
; 以上17行相當于[R_PubReg3:R_PubReg2]×10
L_BCD2Hex_Next:
DECFSZ R_PubCnt0,1
GOTO L_BCD2HexLoop
;上面的程序將4位BCD碼[R_PubReg1:R_PubReg0]轉換為二進制數->R_PubReg3:R_PubReg2
MOVFW R_CaliCode0L ;\
MOVWF R_PubReg0 ; | [R_CaliCode0H:R_CaliCode0L]
MOVFW R_CaliCode0H ; | ->R_PubReg1:R_PubReg0
MOVWF R_PubReg1 ;/
MOVFW R_SteadyCodeL ;\
MOVWF R_PubReg4 ; | [R_SteadyCodeH:R_SteadyCodeL]
MOVFW R_SteadyCodeH ; | ->R_PubReg5:R_PubReg4
MOVWF R_PubReg5 ;/
CALL S_CalcABS ;計算[R_PubReg5:R_PubReg4]-[R_PubReg1:R_PubReg0]絕對值->R_PubReg5:R_PubReg4
MOVFW R_PubReg4
SUBWF R_PubReg2,0
MOVFW R_PubReg5
SUBWFC R_PubReg3,0
BTFSC STATUS,C
GOTO L__CaliCodeP_Ret ;[R_PubReg3:R_PubReg2]≥[R_PubReg5:R_PubReg4] 轉,返回
CALL S_Divis ;[R_PubReg3:R_PubReg2]×65536÷[R_PubReg5:R_PubReg4]->R_PubReg1:R_PubReg0
BTFSC R_PubReg1,7
GOTO L__CaliCodeP_Ret ;[R_PubReg1]≥80H(每個內碼對應的重量≥0.5d) 轉,返回
MOVFW R_PubReg0 ;\
MOVWF R_CaliDataL ; | [R_PubReg1:R_PubReg0]
MOVFW R_PubReg1 ; | ->R_CaliDataH:R_CaliDataL
MOVWF R_CaliDataH ;/
MOVLW D_CaliMark2
MOVWF R_CaliCodeFlag ;D_CaliMark2->R_CaliCodeFlag 重量標定成功
L__CaliCodeP_Ret:
RETURN
;子程序S_AddSub1 ;[R_PubReg3:R_PubReg2]+[R_PubReg5:R_PubReg4]->R_PubReg3:R_PubReg2
S_AddSub1:
MOVFW R_PubReg4 ;\
ADDWF R_PubReg2,1 ; | [R_PubReg3:R_PubReg2]+[R_PubReg5:R_PubReg4]
MOVFW R_PubReg5 ; | ->R_PubReg3:R_PubReg2
ADDWFC R_PubReg3,1 ;/
RETURN
;子程序S_Mul2Sub1 ;[R_PubReg3:R_PubReg2]×2->R_PubReg3:R_PubReg2
S_Mul2Sub1:
BCF STATUS,C ;\
RLF R_PubReg2,1 ; | [R_PubReg3:R_PubReg2]×2->R_PubReg3:R_PubReg2
RLF R_PubReg3,1 ;/
RETURN
;------------------------------------------------------------------------------
;子程序S_RdParaMaxV ;讀出當前參數的最大值
S_RdParaMaxV:
ADDPCW
RETLW 99H ;P0.1、P0.0的最大值
RETLW 29H ;P0.3、P0.2的最大值
RETLW 7FH ;P1.1、P1.0的最大值
RETLW 93H ;P1.3、P1.2的最大值
RETLW 97H ;P2.1、P2.0的最大值
RETLW 39H ;P2.3、P2.2的最大值
;------------------------------------------------------------------------------
;子程序S_RR4Work ;[WORK]右移4位->WORK,0->WORK.7:4
S_RR4Work: RRF WORK,0
RRF WORK,0
RRF WORK,0
RRF WORK,0
ANDLW 0FH
RETURN
;------------------------------------------------------------------------------
;子程序S_ReadKey ;讀按鍵,并作簡單判斷處理
;Output: R_KeyStatus,R_KeyCode
;Call: S_RdKeyCode
;Use RAM: WORK,R_PubCnt2,R_PubCnt3
S_ReadKey: MOVFW PT2
XORLW 07H
ANDLW 07H
MOVWF R_PubCnt2 ;PT.2:0取反->R_PubCnt2.2:0,R_PubCnt2:7:3=00000B
BTFSS STATUS,Z
GOTO L_ReadKey2 ;[R_PubCnt2]≠0(有鍵按下) 轉
BCF R_PubFlag1,0 ;0->R_PubFlag1.0
MOVFW R_KeyStatus
ANDLW 0F0H
BTFSS STATUS,Z
GOTO L_ReadKey1 ;[R_KeyStatus].7:4≠0 轉
BSF R_KeyCode,3 ;1->R_KeyCode.3 (按鍵釋放)
BSF R_KeyStatus,7 ;1->R_KeyStatus.7
BSF R_KeyStatus,4 ;1->R_KeyStatus.4
GOTO L_ReadKeyRet
L_ReadKey1:
MOVLW 1FH
ANDWF R_KeyStatus,1 ;0->R_KeyStatus.7:5
BSF R_KeyStatus,4 ;1->R_KeyStatus.4
GOTO L_ReadKeyRet
L_ReadKey2:
MOVFW R_KeyStatus
ANDLW 0F0H
XORLW 70H
BTFSC STATUS,Z
GOTO L_ReadKeyRet ;[R_KeyStatus].7:4=7 轉
DECF R_PubCnt2,0
CALL S_RdKeyCode ;讀鍵碼
MOVWF R_PubCnt3 ;鍵碼->R_PubCnt3
BTFSC R_KeyStatus,4
GOTO L_ReadKey3 ;[R_KeyStatus].4=1 轉
MOVFW R_KeyStatus
ANDLW 0FH
XORWF R_PubCnt2,0
BTFSC STATUS,Z
GOTO L_ReadKey4 ;[R_PubCnt2]=[R_KeyStatus].3:0 (按鍵狀態未變) 轉
L_ReadKey3:
MOVLW 0F0H
ANDWF R_KeyStatus,0
IORWF R_PubCnt2,0
MOVWF R_KeyStatus ;[R_PubCnt2]->[R_KeyStatus].3:0 保存按鍵狀態
MOVFW R_PubCnt3
MOVWF R_KeyCode ;[R_PubCnt3]->R_KeyCode 保存鍵碼
MOVFW R_KeyStatus
ANDLW 0F0H
XORLW 30H
BTFSS STATUS,Z
BSF R_KeyStatus,7 ;[R_KeyStatus].7:4≠3,1->R_KeyStatus.7
BCF R_KeyStatus,4 ;0->R_KeyStatus.4
BCF R_KeyStatus,6 ;0->R_KeyStatus.6
MOVLW 10H ;10H=2秒
ADDWF R_TimerCnt,0
MOVWF R_KeyTimer1 ;[R_TimerCnt]+10H(2秒)->R_KeyTimer1
MOVLW 28H ;28H=5秒
ADDWF R_TimerCnt,0
MOVWF R_KeyTimer2 ;[R_TimerCnt]+28H(5秒)->R_KeyTimer2
MOVLW 05H
SUBWF R_KeyCode,0
BTFSS STATUS,Z
GOTO L_ReadKey4 ;[R_KeyCode]≠05H(不是"UNIT"鍵按下) 轉
MOVLW 50H ;50H=10秒,按住"UNIT"鍵進入快速標定的時間為10秒
ADDWF R_TimerCnt,0
MOVWF R_KeyTimer2 ;[R_TimerCnt]+50H(10秒)->R_KeyTimer2
L_ReadKey4:
MOVFW R_TimerCnt
SUBWF R_KeyTimer1,0
BTFSS STATUS,Z
GOTO L_ReadKey5 ;[R_KeyTimer1]≠[R_TimerCnt] 轉
INCF R_TimerCnt,0
MOVWF R_KeyTimer1 ;[R_TimerCnt]+1->R_KeyTimer1
BSF R_KeyStatus,5 ;1->R_KeyStatus.5
BSF R_KeyStatus,7 ;1->R_KeyStatus.7
MOVLW 0FH
SUBWF R_KeyCode,0
BTFSC STATUS,Z
GOTO L_ReadKey5 ;[R_KeyCode]=0FH 轉
MOVLW 07H
ANDWF R_KeyCode,1 ;[R_KeyCode]&07H->R_KeyCode
L_ReadKey5:
BTFSC R_KeyStatus,6
GOTO L_ReadKeyRet ;[R_KeyStatus].6=1 轉,返回
MOVFW R_TimerCnt
SUBWF R_KeyTimer2,0
BTFSS STATUS,Z
GOTO L_ReadKeyRet ;[R_KeyTimer2]≠[R_TimerCnt] 轉,返回
BSF R_KeyStatus,6 ;1->R_KeyStatus.6
BSF R_KeyStatus,7 ;1->R_KeyStatus.7
BSF R_KeyCode,4 ;1->R_KeyCode.4
MOVLW 04H
SUBWF R_PubReg2,0
BTFSC STATUS,Z
BSF R_PubFlag1,0 ;[R_PubReg2]=04H("TARE"鍵按下),1->R_PubFlag1.0
L_ReadKeyRet:
RETURN
S_RdKeyCode: ;讀鍵碼
ADDPCW
RETLW 4 ;[R_PubCnt2]=001B,鍵碼=100B
RETLW 5 ;[R_PubCnt2]=010B,鍵碼=101B
RETLW 7 ;[R_PubCnt2]=011B,鍵碼=111B
RETLW 6 ;[R_PubCnt2]=100B,鍵碼=110B
RETLW 7 ;[R_PubCnt2]=101B,鍵碼=111B
RETLW 7 ;[R_PubCnt2]=110B,鍵碼=111B
RETLW 7 ;[R_PubCnt2]=111B,鍵碼=111B
;------------------------------------------------------------------------------
;子程序S_ReadCode ;計算最近X次的內碼的平均值->R_PubReg1:R_PubReg0,X=[WORK]
;Input: R_CodeBuffer[0:F],R_CodePointer,WORK
;Output: R_PubReg1:R_PubReg0
;Use RAM: WORK,FSR0,IND0,R_Count,R_PubReg3:R_PubReg2,R_PubReg5:R_PubReg4
;Goto: S_DivisM
S_ReadCode: MOVWF R_Count
MOVWF R_PubReg4
CLRF R_PubReg5
CLRF R_PubReg0
CLRF R_PubReg1
CLRF R_PubReg2
CLRF R_PubReg3
DECF R_CodePointer,0 ;\
ANDLW 07H ; |
BCF STATUS,C ; | 計算當前內碼存放的地址
RLF WORK,0 ; | ->FSR0
ADDLW R_CodeBuffer ; |
MOVWF FSR0 ;/
L_RdCodeLoop:
MOVFW IND0
ADDWF R_PubReg0,1
INCF FSR0,1
MOVFW IND0
ADDWFC R_PubReg1,1
MOVLW 0
ADDWFC R_PubReg2,1
INCF FSR0,0
BTFSC STATUS,Z
MOVLW R_CodeBuffer
MOVWF FSR0
DECFSZ R_Count,1
GOTO L_RdCodeLoop ;次數未到,轉L_RdCodeLoop繼續
GOTO S_DivisM ;[R_PubReg3:R_PubReg0]÷[R_PubReg5:R_PubReg4]->R_PubReg1:R_PubReg0
;------------------------------------------------------------------------------
;子程序S_CalcABS ;計算[R_PubReg5:R_PubReg4]-[R_PubReg1:R_PubReg0]絕對值->R_PubReg5:R_PubReg4
;Input: R_PubReg1:R_PubReg0
; R_PubReg5:R_PubReg4
;Output: R_PubReg5:R_PubReg4
; R_PubFlag1.3 =1時減法結果為負數
S_CalcABS:
BCF R_PubFlag1,3 ;0->R_PubFlag1.3
MOVFW R_PubReg0 ;\
SUBWF R_PubReg4,1 ; | [R_PubReg5:R_PubReg4]-[R_PubReg1:R_PubReg0]
MOVFW R_PubReg1 ; | ->R_PubReg5:R_PubReg4
SUBWFC R_PubReg5,1 ;/
BTFSC STATUS,C ;
GOTO L_CalcABS_Ret ;結果為正數,轉,返回
BSF R_PubFlag1,3 ;1->R_PubFlag1.3
S_CalcABS1: ;計算[R_PubReg5:R_PubReg4]的補碼->R_PubReg5:R_PubReg4
COMF R_PubReg4,1 ;\
COMF R_PubReg5,1 ; \
MOVLW 1 ; | 計算[R_PubReg5:R_PubReg4]的補碼
ADDWF R_PubReg4,1 ; | ->R_PubReg5:R_PubReg4
MOVLW 0 ; /
ADDWFC R_PubReg5,1 ;/
L_CalcABS_Ret:
RETURN
;------------------------------------------------------------------------------
;子程序S_CalcUnitData ;計算1d對應的不同計量單位的值(浮點數),
; 結果->R_UnitData2(2的指數)、R_UnitData1:R_UnitData0(有效數字)
;Input: R_CaliP1H,R_CaliP1L
;Output: R_UnitData1:R_UnitData0
; R_UnitData2
;Call: S_RdScaleMarkV
; S_InitUnitRate
; S_Multi
; S_LeftMove
;Use RAM: WORK,R_Temp
S_CalcUnitData:
MOVFW R_CaliP1H ;標定參數,D3:D0=P1.2(分度值)
ANDLW 03H ;P1.2=0-3
CALL S_RdScaleMarkV ;讀出分度值
MOVWF R_ScaleMarkV ;分度值->R_ScaleMarkV
MOVWF R_PubReg4 ;
CLRF R_PubReg5 ;分度值->R_PubReg5:R_PubReg4
MOVFW R_CaliP1L ;標定參數,D7:D4=P1.1
CALL S_RR4Work ;[WORK]右移4位->WORK,0->WORK.7:4
ANDLW 03H
MOVWF R_DecimalDigits ;小數位數->R_DecimalDigits
MOVWF R_Temp ;小數位數->R_Temp 暫存
CALL S_InitUnitRate ;初始化計量單位的相關計算用數據->R_PubReg3:R_PubReg2等
MOVWF R_ScaleMarkV
ANDLW 03H
MOVWF R_DecimalDigits
MOVFW R_ScaleMarkV
CALL S_RR4Work ;[WORK]右移4位->WORK,0->WORK.7:4
ANDLW 07H
MOVWF R_ScaleMarkV
MOVLW 10H
SUBWF R_PubCnt3,1 ;[R_PubCnt3]-10H->R_PubCnt3
CALL S_Multi ;[R_PubReg3:R_PubReg2]×[R_PubReg5:R_PubReg4]->R_PubReg3:R_PubReg0
CALL S_LeftMove ;[R_PubReg3:R_PubReg0]左移,直到[R_PubReg3]≥80H,最多移16次
; 實際移位次數加入[R_PubCnt3]
MOVFW R_DecimalDigits
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -