Analog Comparator (Assembler): wo ist der Fehler?
Bin so langsam am verzweifeln. Sitze hier nun Stunden bei und kann den fehler nicht finden.
Code:
;-------Analog Comparator Test----------------------------
.include "m8def.inc" ;Definitionsdatei einbinden
rjmp reset ; Reset Handler
reti ; IRQ0 Handler
reti ; IRQ1 Handler
reti ; Timer1 Capture Handler
reti ; Timer1 compare Handler
reti ; Timer1 Overflow Handler
reti ; Timer0 Overflow Handler
reti ; SPI Transfer Complete Handler
reti ; UART RX Complete Handler : RXCIE
reti ; UDR Empty Handler
reti ; UART TX Complete Handler
reti ; ADC Conversion Complete Interrupt Handler
reti ; EEPROM Ready Handler
;rjmp comparator ; Analog Comparator Handler
reset:
; sbi ACSR, ACIS1
; sbi ACSR, ACIS0
; sbi ACSR, ACIE
; sei
ldi r16, 0xFF
out DDRC, r16
ldi r16, 0x00
out PORTC, r16 ;LED aus
ldi r17, ACSR
SBRS r17, 5 ;5=ACO Bitabfrage wenn Comparator schaltet
rjmp reset
ledan:
ldi r16, 0xFF ;LED an
out PORTC, r16
ldi r17, ACSR
SBRC r17, 5 ;5=ACO Bitabfrage wenn Comparator schaltet
rjmp ledan
rjmp reset
;comparator:
; ldi r16, 0x00 ;LED an
; out PORTC, r16
;reti
Das ist das Programm. In der Mega8 Doku steht:"When the voltage on the positive pin AIN0 is higher than the voltage on
the negative pin AIN1, the Analog Comparator Output, ACO, is set." Es muß also auch ohne Interrupt gehen. Habe also mal den Interruptteil auskommentiert.
Das Programm läuft in so weit, dass die richtige LED bei einem vollen Potianschlag leuchtet wenn ich das Programm überspielt habe. Drehe ich den Poti zum anderen Anschlag ist die LED immernoch an. Überspiele ich das Programm erneut bei dem gleichen Potianschlag, so geht die LED aus. Und das kann man wieder anders herum wiederholen. Kann es mir irgendwie nicht mehr erklären. Der Comparator scheint also zu funktionieren, aber nur wenn das Programm überspielt wird. Während der Laufzeit funktioniert es nicht.
Woran liegt es?
Liste der Anhänge anzeigen (Anzahl: 1)
Vielleicht bekommst du aus folgendem Code ne Anregung. Ist zwar C (AT90S2313), sollte aber zu verstehen sein. Ich hatte den AC nicht direkt benutzt um eine IRQ auszulösen, sondern zur Zeitmessung via InputCapture von Timer1 (Kapazitätsmessung).
Für deinen Fall einfach den AC-IRQ aktivieren und die gewünschte Flanke einstellen, sollte dann gehen.
Code:
#include "use.h"
#include <AVR.h>
#include "ports.h"
#include "capacity.h"
//#include "morse.h"
extern void ioinit();
extern void wait_10ms (const byte);
#include <math.h>
// Multiplikator:
// k = (ny * R * ln 2)^{-1}
// mit ny = 8MHz und R = 10k:
// k = 18pF / Einheit
word measure_time (byte loadTime)
{
// Load capacity via AIN+ push-pull
SET (PORT_AIN_POS); MAKE_OUT (PORT_AIN_POS);
wait_10ms (loadTime);
// disable all interrupts
cli();
// stop timer1
TCCR1B = 0;
// enable AC (ACD = 0)
// AC Input Capture on -> connect to Input Capture of Timer/Counter1
// AC Interrupt on Falling Output Edge
ACSR = _BV(ACIC) | _BV (ACIS1);
// disconnect timer1 from output pin OC, no PWM
TCCR1A = 0;
// reset timer1 to 0
TCNT1 = 0;
// clear Timer1 OVerflow and Input Capture Flag
TIFR |= _BV (TOV1) | _BV (ICF1);
// start timer 1 at full speed
// no clear on compare match
// no noise cancel
// input capture edge = falling
TCCR1B = _BV (CS10);
// here we go!
// start discharging via external resistor
// AIN+ to high Z
MAKE_IN (PORT_AIN_POS); CLR (PORT_AIN_POS);
byte flag;
do
{
flag = TIFR & (_BV (TOV1) | _BV (ICF1));
} while (flag == 0);
if (flag & _BV (TOV1))
return 0xffff;
// if (flag & _BV (ICF1))
return (word) ICR1;
// restore status of machine
// ioinit();
// morse (_O_);
// if (flag & _BV (ICF1))
// morse_dec (capture-4);
// morse (_FRAGE_);
}
-------------------------------------------------------
Als Temperaturdifferenzschaltung hatte ich mal die Schaltung unten gebastelt. Mit µC schien mit da mit Spatzen auf Kanonen geschossen, ausserdem lässt sich eine µC-Schaltung nicht so simpel über Potis nachtrimmen.
- Komparator D schaltet, wenn T_innen > T_aussen ist.
- Komparator A schaltet, wenn T_aussen > T_const (zB T_const über Frostgrenze).
- Komparator B funktioniert als Und-Glied
- danach ein Zeitglied und Komparator C als Schmitt-Trigger
Die T-Abhängigen Widerstände sind NTCs.