main
movlwb'00000000' ;初始化前禁止所有中断
movwfINTCON
;Bank1 初始化ADC端口/中断/输出PORT口
;***************
bankselADCON1
movlwb'00001000'
movwfADCON1
movlwb'00000001'
movwfPIE1
bcf TRISD,1
;Bank0 初始化常量
;****************
bankselSTATUS
bcf PORTD,1
; PPM每个通道的固定间隔宽度65536-488us(0xFE18)
movlw0x18
movwfppm_interval_origin
movlw0xFE
movwfppm_interval_origin+1
;初始化通道选择;在中断中使用
clrfch_ppm_sel
bsf ch_ppm_sel,0
; PPM通道脉冲头标志位,首先输出脉冲头
clrfppm_head_flag
comfppm_head_flag,f
;Bank0 初始化ADC端口
;****************
movlwb'00000001'
movwfADCON0
movlwb'00000001'
movwfT1CON
;全部初始化完成后开中断
;****************
movlwb'11000000'
movwfINTCON
ADC_catch
clrfad_data_point ;复位ADC数据缓冲区指针
ADC_ch0;****
;采样并保存
callADC_doing ;第一次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
callADC_doing ;第二次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
;选择下一个通道-通道1
movlwb'00001001'
movwfADCON0
;数据校验
;***************************************************************
movfad_data_buff+ch0,w ;第一次数据->w
subwfad_data_buff+ch0+1,w;第二次数据-第一次数据->w
sublwad_check_no ;最大误差值-w,若C=0有借位,数据不合格需要处理
bc Figure_ch0ppm ;C=1则表明数据正确,下一通道采样
;处理不合格数据
movfad_data_buff+ch0,w ;第一次数据->w
addwfad_data_buff+ch0+1,f;第二次数据+第一次数据->第二次数据位
rrf ad_data_buff+ch0+1,f ;两次数据和/2求平均,放入第二次数据位
;***************************************************************
Figure_ch0ppm ;计算PPM通道脉冲宽度
movfad_data_buff+ch0+1,w;取最终合格的ADC数据
clrfch_ppm+1 ;高8位清0
movwfch_ppm ;数据送到PPM计算临时区低8位
bcf STATUS,C
rlf ch_ppm ;连续两次左移位将ADC结果×4
rlf ch_ppm+1
bcf STATUS,C
rlf ch_ppm
rlf ch_ppm+1
;***************************
;用常数减计数值求TMR1计数初值
movfch_ppm,w ;低位计算
subwfppm_interval_origin,w ; ppm_interval_origin减ch_ppm
movwfch_ppm ;保存结果
skpc ;C=1没有借位跳过下面一条指令
incfch_ppm+1,f ;有借位高位有借位,补被低位借掉的1
movfch_ppm+1,w ;高位计算
subwfppm_interval_origin+1,w; ppm_interval_origin+1减ch_ppm+1
movwfch_ppm+1 ;保存结果
;***************************
bcf INTCON,GIE ;禁止中断,保证数据的完整
;***************************
movwfch_ppm_buff+ch0+1 ;将数据最终存入PPM计数缓存区
movfch_ppm,w
movwfch_ppm_buff+ch0
;***************************
bsf INTCON,GIE ;打开中断
;***************************
;通道0采样PPM计数转换完成
ADC_ch1;****
;采样并保存
callADC_doing ;第一次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
callADC_doing ;第二次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
;选择下一个通道-通道2
movlwb'00101001'
movwfADCON0
;数据校验
;***************************************************************
movfad_data_buff+ch1,w ;第一次数据->w
subwfad_data_buff+ch1+1,w;第二次数据-第一次数据->w
sublwad_check_no ;最大误差值-w,若C=0有借位,数据不合格需要处理
bc Figure_ch1ppm ;C=1则表明数据正确,下一通道采样
;处理不合格数据
movfad_data_buff+ch1,w ;第一次数据->w
addwfad_data_buff+ch1+1,f;第二次数据+第一次数据->第二次数据位
rrf ad_data_buff+ch1+1,f ;两次数据和/2求平均,放入第二次数据位
;***************************************************************
Figure_ch1ppm ;计算PPM通道脉冲宽度
movfad_data_buff+ch1+1,w;取最终合格的ADC数据
clrfch_ppm+1 ;高8位清0
movwfch_ppm ;数据送到PPM计算临时区低8位
bcf STATUS,C
rlf ch_ppm ;连续两次左移位将ADC结果×4
rlf ch_ppm+1
bcf STATUS,C
rlf ch_ppm
rlf ch_ppm+1
;***************************
;用常数减计数值求TMR1计数初值
movfch_ppm,w ;低位计算
subwfppm_interval_origin,w ; ppm_interval_origin减ch_ppm
movwfch_ppm ;保存结果
skpc ;C=1没有借位跳过下面一条指令
incfch_ppm+1,f ;有借位高位有借位,补被低位借掉的1
movfch_ppm+1,w ;高位计算
subwfppm_interval_origin+1,w; ppm_interval_origin+1减ch_ppm+1
movwfch_ppm+1 ;保存结果
;***************************
bcf INTCON,GIE ;禁止中断,保证数据的完整
;***************************
movwfch_ppm_buff+ch1+1 ;将数据最终存入PPM计数缓存区
movfch_ppm,w
movwfch_ppm_buff+ch1
;***************************
bsf INTCON,GIE ;打开中断
;***************************
;通道1采样PPM计数转换完成
ADC_ch2;****
;采样并保存
callADC_doing ;第一次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
callADC_doing ;第二次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
;选择下一个通道-通道3
movlwb'00110001'
movwfADCON0
;数据校验
;***************************************************************
movfad_data_buff+ch2,w ;第一次数据->w
subwfad_data_buff+ch2+1,w;第二次数据-第一次数据->w
sublwad_check_no ;最大误差值-w,若C=0有借位,数据不合格需要处理
bc Figure_ch2ppm ;C=1则表明数据正确,下一通道采样
;处理不合格数据
movfad_data_buff+ch2,w ;第一次数据->w
addwfad_data_buff+ch2+1,f;第二次数据+第一次数据->第二次数据位
rrf ad_data_buff+ch2+1,f ;两次数据和/2求平均,放入第二次数据位
;***************************************************************
Figure_ch2ppm ;计算PPM通道脉冲宽度
movfad_data_buff+ch2+1,w;取最终合格的ADC数据
clrfch_ppm+1 ;高8位清0
movwfch_ppm ;数据送到PPM计算临时区低8位
bcf STATUS,C
rlf ch_ppm ;连续两次左移位将ADC结果×4
rlf ch_ppm+1
bcf STATUS,C
rlf ch_ppm
rlf ch_ppm+1
;***************************
;用常数减计数值求TMR1计数初值
movfch_ppm,w ;低位计算
subwfppm_interval_origin,w ; ppm_interval_origin减ch_ppm
movwfch_ppm ;保存结果
skpc ;C=1没有借位跳过下面一条指令
incfch_ppm+1,f ;有借位高位有借位,补被低位借掉的1
movfch_ppm+1,w ;高位计算
subwfppm_interval_origin+1,w; ppm_interval_origin+1减ch_ppm+1
movwfch_ppm+1 ;保存结果
;***************************
bcf INTCON,GIE ;禁止中断,保证数据的完整
;***************************
movwfch_ppm_buff+ch2+1 ;将数据最终存入PPM计数缓存区
movfch_ppm,w
movwfch_ppm_buff+ch2
;***************************
bsf INTCON,GIE ;打开中断
;***************************
;通道2采样PPM计数转换完成
ADC_ch3;****
;采样并保存
callADC_doing ;第一次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
callADC_doing ;第二次ADC转换
incfad_data_point,f ;指针位移+1指向下一个缓冲单元
;选择下一个通道-通道0
movlwb'00000001'
movwfADCON0
;数据校验
;***************************************************************
movfad_data_buff+ch3,w ;第一次数据->w
subwfad_data_buff+ch3+1,w;第二次数据-第一次数据->w
sublwad_check_no ;最大误差值-w,若C=0有借位,数据不合格需要处理
bc Figure_ch3ppm ;C=1则表明数据正确,下一通道采样
;处理不合格数据
movfad_data_buff+ch3,w ;第一次数据->w
addwfad_data_buff+ch3+1,f;第二次数据+第一次数据->第二次数据位
rrf ad_data_buff+ch3+1,f ;两次数据和/2求平均,放入第二次数据位
;***************************************************************
Figure_ch3ppm ;计算PPM通道脉冲宽度
movfad_data_buff+ch3+1,w;取最终合格的ADC数据
clrfch_ppm+1 ;高8位清0
movwfch_ppm ;数据送到PPM计算临时区低8位
bcf STATUS,C
rlf ch_ppm ;连续两次左移位将ADC结果×4
rlf ch_ppm+1
bcf STATUS,C
rlf ch_ppm
rlf ch_ppm+1
;***************************
;用常数减计数值求TMR1计数初值
movfch_ppm,w ;低位计算
subwfppm_interval_origin,w ; ppm_interval_origin减ch_ppm
movwfch_ppm ;保存结果
skpc ;C=1没有借位跳过下面一条指令
incfch_ppm+1,f ;有借位高位有借位,补被低位借掉的1
movfch_ppm+1,w ;高位计算
subwfppm_interval_origin+1,w; ppm_interval_origin+1减ch_ppm+1
movwfch_ppm+1 ;保存结果
;***************************
bcf INTCON,GIE ;禁止中断,保证数据的完整
;***************************
movwfch_ppm_buff+ch3+1 ;将数据最终存入PPM计数缓存区
movfch_ppm,w
movwfch_ppm_buff+ch3
;***************************
bsf INTCON,GIE ;打开中断
;***************************
;通道3采样PPM计数转换完成
;
gotoADC_catch
;ADC转换子程序
;**********************************************************************
ADC_doing
bsf ADCON0,GO ;开始ADC
btfscADCON0,GO ;ADC是否结束
goto$-1 ;等待ADC结束
;保存ADC结果
movlwad_data_buff ;取ADC数据缓冲区首地址
movwfFSR ;FSR相对寻址
movfad_data_point,w ;取相对位移指针
addwfFSR,f ;相对地址+位移指针
movfADRESH,w ;取ADC转换结果
movwfINDF ;放入ADC转换结果
;incfad_data_point,f ;指针位移+1指向下一个缓冲单元
;这一步在每个通道的主程序中完成
return
;***********************************************************************
END ; directive 'end of program'
页:
1
[2]