?? armok0137229.txt
字號:
;******************** 多功能測量計 FOR ATmega8 *****************************************
;*
;* File : 多功能測量計.asm
;* Version : 1.0
;* Compiler : AVR Studio
;* Target : ATmega8
;* Output size : 207 words (414 bytes)
;* Author : 陳海強 ;Email-to: haikang@21cn.com
;* website:
;***************************************************************************************
;***************************************************************************************
;*說明:
;* 1、頻率計(T0計數,T1作1S定時器,PWM輸出(OC1A)作時間閘,
; PC5為外部計數器(74HC393)清零CLEAR。
; 外部計數器bit0-PD2,bit1-PD3,bit2-PD5,bit3-PD4(T0)。)
; 1)0~60MHz直接輸入,VHF_CY(PD7)為1。
; 2)60MHz~1.2GHz經MB501 64分頻輸入,UHF_LC(PD6)為1。
;
; 2、LC與晶振測試輸入,CY&LC(PB0)為1。電容單位為pF,電感單位為nH
; 1)LC測試,UHF_LC(PD6)為1;內部電容CAP校正,CAP(PB2)為1;
; 電容測試,CX(PB5)為1;電感測試,LX(PB4)為1。
; 2)晶振測試,VHF_CY(PD7)為1。
;
; 3、電壓輸入(與頻率共用輸入端),AD0。
; 4、LCD輸出,PC3--LCD_LED_RED,PC2--LCD_DATA,PC1--LCD_CLK。
; 5、編程允許腳,PC4接地(跳線塊接通)。使用AVRprog編程。
;***************************************************************************************
;**************************** 子程序列表 *********************
;1、delay(temp0)時子程序(t=(8+temp0*2)*單系統時間)。使用變量temp0無保護
;2、LCD_BYTESoutput(SRAM(LCDBufferBegin))
; 顯示SRAM緩沖區LCDBufferBegin 10字節的內容.使用變量temp0,temp1,X有保護
;
;3、LCD_BIToutput(temp0) 將temp0 低4Bit內容串行輸出到LCD 顯示.使用變量temp0,temp1有保護
;
;4、HEXtoDEC(R(hData0,hData1,hData2,hData3),R(dData0,dData1,dData2,dData3,dData4))
; 4Bytes(32Bit)十六進制轉成5Bytes(40Bit)十進制子程序將cntxh轉成cntxd. 使用變量temp0,temp1,temp2有保護
;
;5、SendDECtoLCDBuffer(R(dData0,dData1,dData2,dData3,dData4),SRAM(LCDBufferBegin))
; 將5Bytes(40Bit)十進制cntxd送到LCD緩沖區LCDBufferBegin. 使用變量temp0,temp1,X有保護
;
;6、LCDTest LCD測試.
;
;7、InitSRAM 初始化 清空SRAM. 使用變量temp0,temp1,temp2,X有保護
;
;8、InitIOPort 初識化I/O口
;
;9、InitTime 初識化設定T/C0、T/C1、T/C2的工作方式。T0作計數器,
; T1作PWM定時器(1S寬度正脈沖OC1A輸出),T2作CLKio/2頻率OC2輸出
;
;
;
;
;****************************************************************************
;****************************************************
; AVRProg編程定義Mega8識別代碼、電子標簽字節和其它
;****************************************************
.equ DT = 0x77 ; Mega8識別代碼(Mega8 bootloader)
.equ SB1 = 0x07 ; 電子標簽字節 1
.equ SB2 = 0x93 ; 電子標簽字節 2
.equ SB3 = 0x1e ; 電子標簽字節 3
.equ E2END = $1FF ; EEEPROM尾
.equ CLKio = 12000000 ; 晶振 = 12 MHz。
.equ UBR = 38 ; 波特率 = 19.200 bps ,晶振 = 12 MHz。
; AVRProg 能接受的波特率是 19200 和 115200
;***************************************************END
.include "m8def.inc" ; 包含 mega8 器件配置文件
.equ SRAMSTART =96 ;SRAM頭
.equ RAMEND128 =96+127
.equ Tpwm =1 ;T1 PWM正脈沖寬度1S。
;**** I/O初始化定義
.equ InitDDRB =0b00001010 ;PB1(OC1A)、PB3(OC2)輸出
.equ InitPORTB =0b00110100 ;
.equ InitDDRC =0b00101110 ;PC5--CLEAR,PC3、2、1--LCD輸出
.equ InitPORTC =0b00001110 ;PC3=1,點亮LCD_LED_RED,PC1--LCD_CLK=1
.equ InitDDRD =0b00000010 ;TXD輸出
.equ InitPORTD =0b00000000
;**** 定時器初始化定義
.equ InitTIMSK =0b00000101 ;定時器中斷允許(T/C0溢出中斷T允許TOIE0=1,
;T/C1溢出中斷允許TOIE1=1)
.equ InitTCCR0 =0b00000110 ;T/C0控制(外部時鐘T0腳,下降沿驅動)
;.equ InitTCCR0 =0b00000001 ;T/C0控制(內部時鐘CLKio)
;.equ InitTCCR0 =0b00000000 ;T/C0控制(無時鐘)
.equ InitTCCR1A =0b11000010 ;T/C1控制A(快速PWM模式14,匹配置位、TOP時清零,TOP=ICR1)
.equ InitTCCR1B =0b00011100 ;T/C1控制B(內部時鐘(CLKio÷256))
.equ InitOCR1A =1 ;T1 PWM正脈沖寬度1S。
.equ InitICR1 =CLKio/256*Tpwm+1 ;TOP=ICR1=OCR1A+寬度1S正脈沖
.equ InitTCCR2 =0b00011000 ;T/C2控制(無時鐘)
;.equ InitTCCR2 =0b00011001 ;T/C2控制(CTC模式,匹配觸發OC2,內部時鐘(CLKio)
;.equ InitOCR2 =0 ;OC2輸出頻率=Fclkio/2。
;.equ InitTCCR2 =0b00011110 ;T/C2控制(CTC模式,匹配觸發OC2,內部時鐘(CLKio)
.equ InitOCR2 =233 ;OC2輸出頻率=Fclkio/(2*256*(233+1))=100.16Hz。
.equ LCMeter =PINB ;LC與晶振測試
.equ Cx =5 ;
.equ Lx =4 ;
.equ CAP =2 ;
.equ CY_LC =0 ;
.equ LCMeterMask =0b00110101
.equ FMeter =PIND ;頻率計
.equ VHF_CY =7 ;
.equ UHF_LC =6 ;
.equ FMeterMask =0b11000000
.equ LCDoutputport =PORTC ;10位LCD 顯示輸出定義
.equ LCDinputport =PINC
.equ LCD_LED_RED =3 ;
.equ LCD_DATA =2 ;
.equ LCD_CLOCK =1 ;
.equ LCDpinMask =0b00001110 ;LCD掩模
.equ EXTCountControl =PORTC ;外部計數器控制定義
.equ CLEAR =5 ;
.equ EXTCountData =PIND ;外部計數器數據定義
.equ EXTCountDataBit0 =2 ;
.equ EXTCountDataBit1 =3 ;
.equ EXTCountDataBit2 =5 ;
.equ EXTCountDataBit3 =4 ;
.equ EXTCountDataMask =0b00111100 ;外部計數器數據掩模
;************************* 常量 定義 *********************************
.equ MAXLCDBYTES =10 ;LCD 顯示長度10位
.equ CAPData =1000 ;CAP=1000pF
.equ pi =3.141592654
;**** ActionFlag 值
.equ CountDataReady =1
;**** ProgramSelect 值
.equ SelectVHF =0b10110100
.equ SelectUHF =0b01110100
.equ SelectCY =0b10110101
.equ SelectLC =0b01110101
.equ SelectCAP =0b01110001
.equ SelectCx =0b01010101
.equ SelectLx =0b01100101
;************************* 常量 定義 ******************************END
;************************* SRAM 定義 *********************************
;**** LCD數據區
.equ LCDBufferBegin =SRAMSTART ;LCD 緩沖區開始位置
.equ LCDShiftBufferBegin =LCDBufferBegin+MAXLCDBYTES ;LCD 顯示轉換前緩沖區
.equ LCDtestCount =LCDShiftBufferBegin+MAXLCDBYTES
;**** 計數運算數據區
.equ FloatCrefData =LCDtestCount+1 ;內部電容Cref計算浮點值(pF)
.equ FloatCrefDataByte0 =FloatCrefData
.equ FloatCrefDataByte1 =FloatCrefData+1
.equ FloatCrefDataByte2 =FloatCrefData+2
.equ FloatCrefDataByte3 =FloatCrefData+3
.equ FloatLrefData =FloatCrefDataByte3+1 ;內部電感Lref計算浮點值(nH)
.equ FloatLrefDataByte0 =FloatLrefData
.equ FloatLrefDataByte1 =FloatLrefData+1
.equ FloatLrefDataByte2 =FloatLrefData+2
.equ FloatLrefDataByte3 =FloatLrefData+3
.equ LxData =FloatLrefDataByte3+1 ;外部電感Lx計算值(nH)
.equ LxDataByte0 =LxData
.equ LxDataByte1 =LxData+1
.equ LxDataByte2 =LxData+2
.equ LxDataByte3 =LxData+3
.equ CxData =LxDataByte3+1 ;外部電容Cx計算值(pF)
.equ CxDataByte0 =CxData
.equ CxDataByte1 =CxData+1
.equ CxDataByte2 =CxData+2
.equ CxDataByte3 =CxData+3
.equ FloatFLCData =CxDataByte3+1 ;內部LC頻率浮點值(Hz)
.equ FloatFLCDataByte0 =FloatFLCData
.equ FloatFLCDataByte1 =FloatFLCData+1
.equ FloatFLCDataByte2 =FloatFLCData+2
.equ FloatFLCDataByte3 =FloatFLCData+3
.equ FloatFCAPData =FloatFLCDataByte3+1 ;內部校正電容CAP頻率浮點值(Hz)
.equ FloatFCAPDataByte0 =FloatFCAPData
.equ FloatFCAPDataByte1 =FloatFCAPData+1
.equ FloatFCAPDataByte2 =FloatFCAPData+2
.equ FloatFCAPDataByte3 =FloatFCAPData+3
.equ FloatFCxData =FloatFCAPDataByte3+1 ;外部電容Cx頻率浮點值(Hz)
.equ FloatFCxDataByte0 =FloatFCxData
.equ FloatFCxDataByte1 =FloatFCxData+1
.equ FloatFCxDataByte2 =FloatFCxData+2
.equ FloatFCxDataByte3 =FloatFCxData+3
.equ FloatFLxData =FloatFCxDataByte3+1 ;外部電感Lx頻率浮點值(Hz)
.equ FloatFLxDataByte0 =FloatFLxData
.equ FloatFLxDataByte1 =FloatFLxData+1
.equ FloatFLxDataByte2 =FloatFLxData+2
.equ FloatFLxDataByte3 =FloatFLxData+3
.equ Floatpi =FloatFLxDataByte3+1 ;pi的浮點值
.equ FloatpiByte1 =Floatpi+1
.equ FloatpiByte2 =Floatpi+2
.equ FloatpiByte3 =Floatpi+3
.equ Float4Byte0 =FloatpiByte3+1 ;4的浮點值
.equ Float4Byte1 =Float4Byte0+1
.equ Float4Byte2 =Float4Byte0+2
.equ Float4Byte3 =Float4Byte0+3
.equ Float10E0Byte0 =Float4Byte3+1 ;1的浮點值
.equ Float10E0Byte1 =Float10E0Byte0+1
.equ Float10E0Byte2 =Float10E0Byte0+2
.equ Float10E0Byte3 =Float10E0Byte0+3
.equ Float10E3Byte0 =Float10E0Byte3+1 ;1000的浮點值
.equ Float10E3Byte1 =Float10E3Byte0+1
.equ Float10E3Byte2 =Float10E3Byte0+2
.equ Float10E3Byte3 =Float10E3Byte0+3
.equ Float10E8Byte0 =Float10E3Byte3+1 ;10的9次方浮點值
.equ Float10E8Byte1 =Float10E8Byte0+1
.equ Float10E8Byte2 =Float10E8Byte0+2
.equ Float10E8Byte3 =Float10E8Byte0+3
.equ Float10E21Byte0 =Float10E8Byte3+1 ;10的21次方浮點值
.equ Float10E21Byte1 =Float10E21Byte0+1
.equ Float10E21Byte2 =Float10E21Byte0+2
.equ Float10E21Byte3 =Float10E21Byte0+3
.equ DataBuffer =Float10E21Byte3+1 ;
.equ DataBuffer10 =DataBuffer ;計數結果的十六進制
.equ DataBuffer11 =DataBuffer+1
.equ DataBuffer12 =DataBuffer+2
.equ DataBuffer13 =DataBuffer+3
.equ DataBuffer20 =DataBuffer+4
.equ DataBuffer21 =DataBuffer+5
.equ DataBuffer22 =DataBuffer+6
.equ DataBuffer23 =DataBuffer+7
.equ DataBuffer30 =DataBuffer+8
.equ DataBuffer31 =DataBuffer+9
.equ DataBuffer32 =DataBuffer+10
.equ DataBuffer33 =DataBuffer+11
.equ DataBuffer40 =DataBuffer+12
.equ DataBuffer41 =DataBuffer+13
.equ DataBuffer42 =DataBuffer+14
.equ DataBuffer43 =DataBuffer+15
.equ DataStack =DataBuffer43+32
.equ StackBegin =RAMEND ;棧緩沖區
;************************* SRAM 定義 ******************************END
;************************* Rn 定義 *********************************
.def backupSREGTimer0 =R2 ;產生T/C0溢出中斷時保存狀態寄存器(SREG)
.def backupSREGTimer1 =R3 ;產生T/C1溢出中斷時保存狀態寄存器(SREG)
.def Time0OVFCount =R4 ;定時器0 溢出計數
.def Time0OVFCountH =R5 ;
.def CountDataBuffer0 =R6 ;內外計數值
.def CountDataBuffer1 =R7 ;
.def CountDataBuffer2 =R8 ;
.def CountDataBuffer3 =R9 ;
.def ExtCountCap =R10 ;外部計數器(74HC393)值捕捉
.def dData0 =R10 ;存放當前計數結果的十進制
.def dData1 =R11
.def dData2 =R12
.def dData3 =R13
.def dData4 =R14
.def hData0 =R15 ;存放當前計數結果的十六進制
.def hData1 =R24
.def hData2 =R25
.def hData3 =R1
;****
.def temp0 =R16 ;暫存器
.def temp1 =R17 ;暫存器
.def temp2 =R18 ;暫存器
.def temp3 =R19 ;暫存器
.def temp4 =R20 ;暫存器
.def ProgramSelect =R22 ;功能選擇
.def ActionFlag =R23 ;
;******************* Rn定義 ***************************************** end *****
.CSEG
;********************************************************************
;* 中斷表
;********************************************************************
.org 0x000 ;
rjmp reset
.org INT0addr ;
; rjmp INT0Handler
reti
.org INT1addr ;
reti
.org OC2addr ;Time2比較中斷
reti
.org OVF2addr ;Time2溢出中斷。
reti
.org ICP1addr ;
reti
.org OC1Aaddr ;
reti
.org OC1Baddr
reti
.org OVF1addr ;Time1 溢出中斷向量。1S寬度正脈沖PWM
rjmp OVF1Handler
.org OVF0addr ;Time0 溢出中斷。計數器
rjmp OVF0Handler
;.org SPIaddr
; reti
;.org URXCaddr
; reti
;.org UDREaddr
; reti
;.org UTXCaddr
; reti
;.org ADCCaddr
; reti
;.org ERDYaddr
; reti
;.org ACIaddr
; reti
;.org TWIaddr
; reti
;.org SPMaddr
; reti
;******************* 中斷表 ****************************************** end ****
.org 0x013
;**** Time0 溢出中斷。計數器
OVF0Handler:
in backupSREGTimer0,SREG
push temp0
ldi temp0,1
add Time0OVFCount,temp0
clr temp0
adc Time0OVFCountH,temp0
pop temp0
out SREG,backupSREGTimer0
reti
;**** Time1 溢出中斷。1秒定時器
OVF1Handler:
in backupSREGTimer1,SREG
push temp0
sei
in ExtCountCap,EXTCountData
in CountDataBuffer0,TCNT0
mov CountDataBuffer1,Time0OVFCount
mov CountDataBuffer2,Time0OVFCountH
clr CountDataBuffer3
sbi ExtCountControl,CLEAR ;外部計數器清零
cbi ExtCountControl,CLEAR
clr temp0
out TCNT0,temp0 ;T0計數器清零
clr Time0OVFCount ;T0計數器溢出計數清零
clr Time0OVFCountH
;**** CountBuffer 乘16 移位4次***********
ldi temp0,4
CountDataBufferLoop:
lsl CountDataBuffer0
rol CountDataBuffer1
rol CountDataBuffer2
rol CountDataBuffer3
dec temp0
brne CountDataBufferLoop
;**** CountBuffer 乘16 移位4次********END
;**** 取出外部計數器的值 作為CountBuffer0低四位值
bst ExtCountCap,ExtCountDataBit0
bld CountDataBuffer0,0
bst ExtCountCap,ExtCountDataBit1
bld CountDataBuffer0,1
bst ExtCountCap,ExtCountDataBit2
bld CountDataBuffer0,2
bst ExtCountCap,ExtCountDataBit3
bld CountDataBuffer0,3
;**** 取出外部計數器的值*****************END
;***** LCD_LED_RED閃動 ***********
sbis LCDinputport,LCD_LED_RED
rjmp LCD_LED_REDSet1
cbi LCDoutputport,LCD_LED_RED
rjmp LCD_LED_REDSetEnd
LCD_LED_REDSet1:
sbi LCDoutputport,LCD_LED_RED
LCD_LED_REDSetEnd:
;***** LCD_LED_RED閃動 ********END
ldi ActionFlag,CountDataReady
; rcall LCDtest
OVF1HandlerEnd:
pop temp0
out SREG,backupSREGTimer1
reti
;*************************************************************************
; 子函數
;*************************************************************************
;1、**** 延時子程序(t=(8+temp0*2)*單系統時間)。temp0=0,循環256次*******
delay:
dec temp0 ;復位后temp0=0X00
brne delay ;temp0不為0轉,為0按順序執行
ret ;子程序返回
;2、**** 顯示SRAM緩沖區LCDBufferBegin 10字節的內容子程序
LCD_BYTESoutput:
push temp0
push temp1
ldi XL,low(LCDBufferBegin) ;X=顯示緩沖區(10字節)
ldi XH,high(LCDBufferBegin)
ldi temp1,10 ;循環顯示10位緩沖區的內容
LCD_BYTESoutputloop:
ld temp0,X+
;****顯示轉換
;temp :A 1 2 3 4 5 6 7 8 9 B C D E F 0
;轉換前LCD顯示:0 1 2 3 4 5 6 7 8 9 F ┘└ P ─ 空格
;轉換后LCD顯示:空格 1 2 3 4 5 6 7 8 9 F ┘└ P ─ 0
;***************令temp:0,a交換
cpi temp0,0 ;temp =0時,令temp =0x0a;temp ≠ 0時,跳到N2
brne LCD_BYTESoutput1 ;
ldi temp0,0x0a ;
rjmp LCD_BYTESoutput2
LCD_BYTESoutput1:
cpi temp0,0x0a ;temp =0x0a時,令temp =0x00;temp ≠ 0x0a時,跳到N3
brne LCD_BYTESoutput2 ;
ldi temp0,0x00 ;
LCD_BYTESoutput2:
rcall LCD_BIToutput
dec temp1
brne LCD_BYTESoutputloop ;temp1不等于0,則跳到LCD_BYTESoutputloop
pop temp1
pop temp0
ret
;2、**** 顯示SRAM緩沖區LCDBufferBegin 10字節的內容子程序********END
;3、***** 將temp0 內容串行輸出到LCD 顯示(LCD_CLOCK,LCD_DATA)******
LCD_BIToutput: ;LCD 顯示輸出(PC5-LCD CLK,PC4-LCD DATA)
push temp0
push temp1
andi temp0,0x0f ;取低4位
ldi temp1,4 ;循環在PC4口串行輸出4位LCD DATA
LCD_BIToutputloop:
sbrc temp0,3 ;temp0(3位) =0時,PC+1
rjmp LCD_DATAout1
LCD_DATAout0:
cbi LCDoutputport,LCD_DATA ;temp0(3位) =0時,LCD_DATA=0
rjmp LCD_BIToutputloop1
LCD_DATAout1:
sbi LCDoutputport,LCD_DATA ;temp0(3位) =1時,LCD_DATA=1
LCD_BIToutputloop1:
cbi LCDoutputport,LCD_CLOCK ;輸出LCD_CLOCK "L"
push temp0
ldi temp0,0xff ;輸出一定的脈寬(38個系統時間)
rcall delay
pop temp0
sbi LCDoutputport,LCD_CLOCK ;輸出LCD_CLOCK "H"
push temp0
ldi temp0,0xff ;輸出一定的脈寬(38個系統時間)
rcall delay
pop temp0
rol temp0 ;temp0左循環
dec temp1
brne LCD_BIToutputloop ;temp1 ≠ 0時,跳到LCD_BIToutputloop
cbi LCDoutputport,LCD_DATA ;LCD_DATA=0
pop temp1
pop temp0
ret
;3、***** 將temp0 內容串行輸出到LCD 顯示(LCD_CLOCK,LCD_DATA)*****END
;4、**** 4Bytes(32Bit)十六進制轉成5Bytes(40Bit)十進制子程序****************
HEXtoDEC:
push temp0
push temp1
push temp2
clr temp0
clr dData0
clr dData1
clr dData2
clr dData3
clr dData4
ldi temp1,32
clc
HEXtoDECloop:
rol hData0
rol hData1
rol hData2
rol hData3
rol dData0
rol dData1
rol dData2
rol dData3
rol dData4
dec temp1
breq HEXtoDECend
rcall HEXtoDECadjn
rjmp HEXtoDECloop
HEXtoDECend:
pop temp2
pop temp1
pop temp0
ret
;****
HEXtoDECadjn:
mov temp0,dData0
rcall HEXtoDECadjd1
mov dData0,temp0
mov temp0,dData1
rcall HEXtoDECadjd1
mov dData1,temp0
mov temp0,dData2
rcall HEXtoDECadjd1
mov dData2,temp0
mov temp0,dData3
rcall HEXtoDECadjd1
mov dData3,temp0
mov temp0,dData4
rcall HEXtoDECadjd1
mov dData4,temp0
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -