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

📄 ade7759.asm

📁 实现对ADE7759电能芯片的读写和校准,AVR单片机源码与电路图,单相电能表读写程序和初始化程序
💻 ASM
📖 第 1 页 / 共 2 页
字号:
;==============================================================================
;  Projekt:	Miernik energii i mocy na ADE7759
;  Autor:	Grzesiek Gajewski (gayos@interia.pl)
;  Koniec:	22.04.2003
;  Wersja:	1.0
;  Kompilacja w AVRStudio 4.04
;  wielkosc Tabsize w edytorze: 12
;
;  kilka informacji w equ.asm (na koncu pliku)
;  licencja GPL w licencja.txt
;
;==============================================================================
; Ustawienie bitow konfiguracyjnych "fuse bits"
; BODLEVEL, BODEN, SUT1, SPIEN - zaprogramowane (programmed) czyli wartosc 0
; reszta niezaprogramowana (1)
; konfiguracja odnosi sie do rezonatora kwarcowego 8MHz
;==============================================================================
.nolist
.include "m16def.inc"
.list

.include "equ.asm"		; prawie wszystkie stale i zmienne

.def	temp	=r16
.def	flagi	=r17
  .equ	fKAL	=0	; =1 -> procedura kalibracji
  .equ	fINT2	=1	; informacja o stanie przerwania INT2; =1 -> zezwolenie na zbieranie probek
  .equ	fOVER_I	=2	; =1 -> przepelnienie probki pradu
  .equ	fOVER_U	=3	; =1 -> przepelnienie probki napiecia
  .equ	fKLAW_WCIS	=4	; =1 -> klawisz wcisniety
  .equ	fTARYFY	=5	; =1 -> licznik dwutaryfowy
  .equ	fTARYFA2	=6	; biezaca taryfa (zalezne od pory dnia), =0 -> taryfa 1
  .equ	fMENU	=7	; =1 -> trwa obsluga MENU


;==============================================================================
;======== S T A R T   P R O G R A M U =========================================
;==============================================================================
.cseg
.org 0
	jmp	RESET	; reset
	jmp	INT0_INT	; int0
	jmp	RESET	; int1
	jmp	RESET	; timer2_comp
	jmp	RESET	; timer2_ovf
	jmp	RESET	; timer1_capt
	jmp	RESET	; timer1_compa
	jmp	RESET	; timer1_compb
	jmp	RESET	; timer1_ovf
	jmp	TIMER0_INT	; timer0_ovf
	jmp	RESET	; spi_stc
	jmp	RESET	; usart_rxc
	jmp	RESET	; usart_udre
	jmp	RESET	; usart_txc
	jmp	RESET	; adc
	jmp	RESET	; ee_rdy
	jmp	RESET	; ana_comp
	jmp	RESET	; twi
	jmp	INT2_INT	; int2	przerwanie z ADE7759
	jmp	RESET	; timer0_comp
	jmp	RESET	; spm_rdy


.include "int0.asm"
.include "int2.asm"
.include "spitwi.asm"
.include "init.asm"
.include "klaw.asm"
.include "menu.asm"
.include "math.asm"
.include "inne.asm"


;==============================================================================
;======== P R O G R A M   G L O W N Y =========================================
;==============================================================================
.cseg
RESET:	cli
	clr	r30
	out	EECR, r30
	out	MCUCR, r30
;	; DISABLE WATCHDOG
;	ldi	r31, (1<<WDTOE) | (1<<WDE)
;	out	WDTCR, r31
;	ldi	r31, 1<<WDTOE
;	out	WDTCR, r31
	; watchdog na 1s
	ldi	r31, (1<<WDE) | (1<<WDP2) | (1<<WDP1)
	out	WDTCR, r31
	; inicjalizacja stosu
	ldi	r31, high(RAMEND)
	out	SPH, r31
	ldi	r31,  low(RAMEND)
	out	SPL, r31

	; sprawdzenie czy EEPROM zawiera wlasciwe dane
	rcall	INICJUJ_EEPROM

	; ustawienie timera0 na czas 15ms (odczekanie 15ms)
	ldi	temp, 136
	out	TCNT0, temp
	in	temp, TIFR
	sbr	temp, 1<<TOV0
	out	TIFR, temp		; czyszczenie flagi
	ldi	temp, (1<<CS02) | (1<<CS00)
	out	TCCR0, temp		; Fosc/1024

	; odczyt zmiennych z EEPROMu,  inicjalizacja zmiennych
	; ustawienie rejestrow uC
	call	USTAW_MEGA16
	call	USTAW_SPI
	call	USTAW_KLAWISZE

	; czekanie na koniec odmierzania czasu T0 (15ms)
RST15ms:	in	temp, TIFR
	sbrs	temp, TOV0
	rjmp	RST15ms
	out	TIFR, temp		; czyszczenie flagi
	clr	temp
	out	TCCR0, temp		; wylacz timer

;	rcall	USTAW_DS1307_R7	; ustawienie OUT=1Hz
;test	rcall	DELAY_5_1ms
	rcall	RESET_ADE
	call	USTAW_ADE7759

	; inicjalizacja LCD 15ms po starcie uP
	rcall	LCD_INIT
	ldi	temp, LCD_D1_C0_B0
	rcall	LCD_COMMAND
	ldi	zh, high(2*txt_witaj)
	ldi	zl,  low(2*txt_witaj)
	rcall	LCD_STR_FLASH	; komunikat powitalny
	rcall	LCD_CGRAM		; polskie znaczki

	; sprawdzenie klawisza OK i Anuluj
	sbis	KLAW_PIN, KLAW_NIE	; przeskocz jesli stan wysoki (klawisz zwolniony)
	rcall	KALIBRACJA		; stan niski - procedura kalibracji

	; sprawdzenie stanu linii ADE_SAG
	sbis	ADE_SAG_PIN, ADE_SAG	; przeskocz jesli stan wysoki (poprawne napiecie)
	rjmp	BZ_SAG		; stan niski SAG

	call	CZYTAJ_DS1307	; odczyt czasu
	rcall	SPRAWDZ_TARYFE
	rcall	POROWNAJ_CZAS
	rcall	DELAY_44us
	rcall	CZYT_EN_DS1307	; odczyt energii z DS1307 do RAM

	; wlaczenie odmierzania czasu ~32ms do obslugi klawiatury
	rcall	TIMER0_USTAW
	rcall	TIMER1_ICP

	; ustawienie przerwan sprzetowych
	; przerwanie INT2 musi byc wlaczone zawsze, gdyz tylko tak nastepuje detekcja SAG
	rcall	INT_WLACZ
	rcall	DELAY_1_7ms
	wdr


;------------------------------------------------------------------------------
;---------- glowna petla programu ---------------------------------------------
;------------------------------------------------------------------------------
PETLA_START_0:	; tu skacze sie po wyjsciu z MENU
	sei

PETLA_START:
	; w przerwaniu INT0 (czyli procedurze CZYTAJ_ENERGIE) obliczane sa E i P
	; czekanie na zakonczenie odczytu energii i ustawienie flagi fINT2
PS_0:	; oczekiwanie na fINT2 = 1
	sbrs	flagi, fINT2	; przeskocz, jesli flaga =1
	rjmp	PS_0

	cli
	; przygotowanie rejestrow i zmiennych do zbierania probek
	clr	r2		; r2 zawsze =0
	ldi	zl,  low(Prb_0xff)
	ldi	zh, high(Prb_0xff)
	ldi	yl,  low(Bufor)
	ldi	yh, high(Bufor)
PS_ZER:	st	z+, r2
	cp	zl, yl
	cpc	zh, yh
	brlo	PS_ZER
	cbr	flagi, (1<<fOVER_I) | (1<<fOVER_U)
	clr	probek0
	clr	probek1
	movw	i_suma0, probek0
	movw	i_suma2, probek0
	movw	i_suma4, probek0	; czyszczenie sumy pradu
	movw	u_suma0, probek0
	movw	u_suma2, probek0
	movw	u_suma4, probek0	; czyszczenie sumy napiecia
	movw	prb0, probek0
	clr	okresow
	dec	okresow		; ustaw licznik okresow na -1
	; ustawienie zglaszania przerwania od probek w ADE7759
	rcall	ZBIERANIE_PROBEK_WLACZ
	wdr
	sei

PS_1:	; oczekiwanie na fINT2 = 0
	sbrc	flagi, fINT2	; przeskocz, jesli flaga =0
	rjmp	PS_1

	wdr
	in	temp, GIFR
	sbrs	temp, INTF2
	rjmp	PS_2
	ldi	temp, 1<<INTF2
	out	GIFR, temp		; kasuj flage przerwania
	nop
PS_2:	sei

;--------------------------------------
;	;test! \/
;	cli
;	sts	Prb, probek0
;	sts	Prb+1, probek1
;	sts	Prb_z, prb_znak
;	sts	Okr, okresow
;	sei
;	;test! /\



;--------------------------------------
LICZENIE:	rcall	OBLICZENIA		; liczenie RMS, S, Q, PF, F
	; wyswietlanie wyniku na LCD wybranego parametru (E lub U lub I ...)

	lds	temp, Flagi4
	tst	temp
	brne	PETLA_KAL		; <>0  ==> trwa jakas kalibracja
	
	rcall	WYSWIETL_WYNIK

	sbrc	flagi, fKAL		; przeskocz, jesli tryb zwykly
	rjmp	PETLA_KAL		; KALIBRACJA ==> specjalny tryb


;------------------------------------------------------------------------------
	; sprawdzanie czasu (odczyt z DS1307) co minute
SPR_CZAS:	lds	temp, Sekundy_bin	; wczytanie zliczonej ilosci sekund
	inc	temp
	sts	Sekundy_bin, temp
	cpi	temp, 60
	brne	SPR_TARYF_NIE
	; sprawdzenie czasu z DS1307 i ustawienie taryfy jesli potrzeba
	cli
	call	CZYTAJ_DS1307
	sei
	rcall	SPRAWDZ_TARYFE
	rcall	POROWNAJ_CZAS
	lds	r0, Minuty_bcd
	lds	r1, Godziny_bcd
	clr	temp
	cp	r0, temp
	cpc	r1, temp		; spr czy godz. =00:00
	brne	SPR_TARYF_NIE
	cli
	rcall	ZAP_EN_DS1307	; o godz. 00:00 zapisywany jest stan licznikow energii
	rcall	ZAPISZ_EN_EE
	sei

SPR_TARYF_NIE:

	; i cykl od poczatku...
	wdr
	cbr	flagi, 1<<fINT2	; zeruj bit zezwolenia na zbieranie probek
	rjmp	PETLA_START


;==============================================================================
PETLA_KAL:
	lds	temp, Flagi4
	tst	temp
	brne	PK_KAL
	rjmp	PETLA_START

PK_KAL:	sbrc	temp, f4KAL_ZI
	rjmp	PK_C_Z		; =1 ==> kalibracja offsetow zera pradu
	sbrc	temp, f4KAL_DCI	; =1 ==> trwa kalibracja DC pradu
	rcall	KAL_I

	sbrc	temp, f4KAL_ZU
	rjmp	PK_C_Z		; =1 ==> kalibracja offsetow zera napiecia
	sbrc	temp, f4KAL_DCU	; =1 ==> trwa kalibracja DC napiecia
	rcall	KAL_U

	sbrc	temp, f4KAL_E	; =1 ==> trwa kalibracja zera energii
	rcall	KAL_E
	rjmp	PETLA_START

PK_C_Z:	clr	temp
	sts	Flagi4, temp
	ldi	zl,  low(2*txt_zro)	; komunikat "Zrobione"
	ldi	zh, high(2*txt_zro)
	rcall	LCD_STR_FLASH	; wyswietl linie
	rjmp	PETLA_START


;==============================================================================

.include "lcd8.asm"
.include "kalibr.asm"
.include "obliczenia.asm"
.include "bufor.asm"



;==============================================================================
;======== K O N I E C =========================================================
;==============================================================================
;==============================================================================
txt_witaj:	.db	1,"LICZNIK ENERGII", 2," i WATOMIERZ", 0
txt_kalibr:	.db	"  KALIBRACJA", 2," wejd",15," w MENU", 0
txt_czek:	.db	"Czekaj...", 0
txt_bns:	.db	1,"brak napi",10,"cia", 2,"sieciowego", 0

txt_u_rms:	.db	"Napi",10,"cie RMS  ", 0
txt_u_mav:	.db	"Nap. ",14,"rednie  ", 0
txt_u_ap:	.db	"Nap. ampl.+++ ", 0
txt_u_am:	.db	"Nap. ampl.--- ", 0
txt_i_rms:	.db	"Pr",8,"d RMS      ", 0
txt_i_mav:	.db	"Pr",8,"d ",14,"redni   ", 0
txt_i_ap:	.db	"Pr",8,"d ampl.+++ ", 0
txt_i_am:	.db	"Pr",8,"d ampl.--- ", 0
txt_moc_p:	.db	"Moc czynna    ", 0
txt_moc_q:	.db	"Moc bierna    ", 0
txt_moc_s:	.db	"Moc pozorna   ", 0
txt_wsp_m:	.db	"Wsp. mocy P/S ", 0
txt_czest:	.db	"Cz",10,"stotliwo",14,9," ", 0
txt_en_sum:	.db	"En ca",11,"kowita  ", 0
txt_en_od:	.db	"En od DD.MM.RR", 0
txt_en_oddo: .db	"En DD.MM-DD.MM", 0
txt_en_ses: .db	"En tymczasowa ", 0
txt_en_poz: .db	"En pozorna    ", 0
txt_en_sek: .db	"Energ. SEKUND.", 0

⌨️ 快捷键说明

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