PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : ATmega32 Hilfestellung bei Programm gesucht



m0b0t1x
17.09.2009, 21:57
Hallo,

ich brauche eure Hilfe bei einem Programm für den ATmega32.
Ich habe einen Ablaufplan erstellt damit es verständlicher ist (siehe
Anhang).

Das Programm wie es unten steht funktioniert soweit, nur komm ich jetzt
nicht weiter mit meinem Latein und es entspricht noch nicht meinen
Vorstellungen aus dem Ablaufplan, und deshalb brauch ich nun euer Wissen
:)

Problem:

Lichtschranke 1 startet den Timer, nur ist dieser > 3 Sekunden kommt
kein Abbruch zustande und es wird auch kein "Err" ausgegeben. Erst wenn
Lichtschranke 2 ein Signal sendet erscheint die Fehlermeldung.
Ich habe diverse Möglichkeiten ausprobiert und die "Abbruchmarke"
verschoben. Aber ich komme auf keinen grünen Zweig.

Ich hoffe ihr könnt mir dabei helfen die kleinen Änderungen und
Berichtigungen vorzunehmen.


Mfg, Ben



// Port A: PA0..PA3 BCD Einer
// Port A: PA4..PA7 BCD Zehner
// Port C: PC4..PC7 BCD Hunderter
// Port D: PD2 Start-LS, PD3 Stopp-LS

#include <avr/io.h> // Deklarationen
#include <avr/interrupt.h> // für Interrupt
#define TAKT 15872000 // 15.872 MHz: 256 = 62000:62 = 1000 Hz = 1 ms
unsigned int volatile sek=0, msek=0; // globale Word-Variable
unsigned char volatile izaehl=1, fehl=0; // globale Byte-Variable
float m_Strecke_d=99; // MESSSTRCKE IN CM
ISR (TIMER0_OVF_vect) // Timer0 Überlauf
{
izaehl++;if(izaehl > 62) // Interruptzähler

{
izaehl = 1; msek++;
if(msek >= 1000) { msek=0; sek++; } // Zähler erhöhen
if(sek >= 3) fehl = 1; // Überlauf-Fehlermarke setzen
}
}

void main(void)
{
unsigned char auskmhh, auskmhl;
unsigned int time=0;
int kmh;
DDRA = 0xff; // Port A sind Ausgänge
DDRC = 0xf0; // Port C PD4..PD7 sind Ausgänge
TIMSK |= 1 << TOIE0; // Timer0 Interrupt frei
TCNT0 = 0; // Timer0 löschen
PORTC = 0b00110000; // Anzeige "---"
PORTA = 0b00110011;
while (PIND & (1 << PIND2)); // warte auf erste fallende Flanke PD2
while (1) // Arbeitsschleife
{
TCCR0 = 1 << CS00; sei(); // Timer0 start Teiler=1 Interrupt frei
PORTA = 0b00000000; PORTC = 0b00000000; // Anzeige " " während der Messung
while(PIND & (1 << PIND3)); // wartet auf fallende Flanke PD3
TCCR0 = 0; cli(); // Timer0 stopp Interrupt sperren
time = (sek*1000) + (msek); // Berechnung der Zeit in ms
kmh= (m_Strecke_d/time)*360; // Berechnung der Geschwindigkeit
auskmhh = ((kmh/100) << 4) ; // KM/H Hunderter in BCD
auskmhl = (((kmh%100)/10)<<4) | (kmh%10); // KM/H Zehner und Einer in BCD
TCNT0 = 0; izaehl = 1; msek = 0; sek = 0;
while (PIND & (1 << PIND2)) // warte auf fallende Flanke
{
if (fehl ==1) { PORTA = 0b01000100; PORTC = 0b01010000;} // Fehlermarke "E r r"
if (fehl ==0)
{
if (kmh>=255)
{
PORTC=0b01010000;
PORTA=0b01000100;
}
if (kmh>=100)
{
PORTC=~auskmhh;
PORTA=~auskmhl;
}
if (kmh<=99)
{
PORTC = 0b00000000;
PORTA = ~auskmhl;
}
}
} // Ende while wartet auf fallende Flanke
fehl = 0;
} // Ende while Arbeitsschleife
} // Ende main

cmock
19.09.2009, 09:31
ich glaub, ich hab dein problem erst beim zweiten mal verstanden -- du möchtest, daß das "ERR" nach 3 sek kommt und nicht erst, wenn die messung abgeschlossen wurde?

das kann dann ja so nicht gehen, nicht nach dem code und nicht nach dem ablaufdiagramm. du fragst ja das "fehl"-flag erst ab, nachdem die 2. lichtschranke ausgelöst hat.

einfache lösung:


while (!fehl && (PIND & (1 << PIND2))) // warte auf fallende Flanke

cm.