hihihi - besser als ich - ich bin nur alt, nicht mehr modisch
Druckbare Version
hihihi - besser als ich - ich bin nur alt, nicht mehr modisch
...t=t+1....
dies ist eine gute schreibweise die man von dem anderen c-gewusel gut lokalisieren kann. der compilercode sieht bei beiden varianten gleich aus. also warum solche (t++) unübersichtlichen kürzel schreiben, das das auge weh tut.
....while(1); ......
schau mal in der lss-datei nach ob die schleife oben wegoptimiert wurde.
Hallo
Ich muss zugeben dass ich zu Anfang auch t++; da stehen hatte. Hab aber gedacht versuchst es mal auf die alte Variante als mein Programm nicht funktioniert hat... 8-[ Wollte eben alles ausschließen... :-)
Nun hab ich mal noch den kompletten Code:
Was ich eigentlich wie gesagt will, ist dass die while Schleife 1min läuft, und in dieser Zeit immer wieder der Analogwert eingelesen wird und in Abhängigkeit von diesem (größer oder kleiner eines Referenzwertes) ein Port geschalten wird. Das will aber noch nicht so richtig. Die andere LED benutze ich auch um mir anzuzeigen bis "wohin" das Programm bereits funktioniert. Also nicht irritieren lassen... ;-)Code:#include <avr/io.h>
#include <inttypes.h>
#include <avr/interrupt.h>
#include <stdlib.h>
#include <lcd.h>
#include <util/delay.h>
#define F_CPU = 12000000L
void long_delay(uint16_t ms); //Prototyp der Warteschleifen long_delay
void ADC_init(void); //Prototyp von ADC_init
uint16_t ADC_einlesen(void); //Prototyp der Einlesefunktion
uint16_t result = 0; //Variable result deklarieren
char buffer[8]; //buffer_Array für Umrechnung deklarieren
volatile int t=0; //Variable t für Timer anlegen
int a=0;
int main(void)
{
ADC_init(); //AD Wandler initialisieren
ADC_einlesen();
DDRD &= ~(1<<DDD2); //Pin D2 (INT0) als Eingang deklarieren
PORTD |= (1<<PD2); //Pull Up für D2 einschalten
DDRB = (1<<DDB0)|(1<<DDB1); //Port B0 als Ausgang definieren (LED)
PORTB |= (1<<PB0); //LED aussschalten
PORTB |= (1<<PB1); //LED aussschalten
TCCR0 |= (1<<CS00)|(1<<CS02); //Timer initialisieren und einschalten
TIMSK |= (1<<TOIE0); //TimerOverflow Interrupt freigeben
sei(); //Interrupts freigeben
while(t<2760)
{
ADC_einlesen();
PORTB &= ~(1<<PB0); //Einschalten der LED an B0
if(result<350)
{
PORTB &= ~(1<<PB1); //Einschalten der LED an B1
}
else
{
PORTB |= (1<<PB1); //wenn result größer, LED ausschalten
}
}
t=0;
while(1);
}
void ADC_init(void)
{
ADCSRA = (1<<ADEN) | (1<<ADPS0) | (1<<ADPS2); //ADC amtivieren und Teilungsfaktor auf 32 stellen
ADMUX = (!(1<<MUX0)) | (!(1<<MUX1)) | (!(1<<MUX2)); //Kanal des Multiplexers wählen (ADC 0)
ADMUX |= (1<<REFS1) | (1<<REFS0); //interne Referenzspannung verwenden (2,56V)
ADCSRA |= (1<<ADSC); //Dummyreadout starten
while(ADCSRA & (1<<ADSC));
}
uint16_t ADC_einlesen(void)
{
uint8_t i; //Variable i deklarieren
for (i=0; i<3; i++) //for-Schleife für dreimalige Wandlung
{
ADCSRA |= (1<<ADSC); //Wandlung starten
while(ADCSRA & (1<<ADSC)); //auf Ergebnis warten
result += ADC; //Ergebnis in Variable result schreiben
}
ADCSRA &= ~(1<<ADEN); //ADC deaktivieren
result /=3; //result durch 3 teilen
return result;
}
ISR(TIMER0_OVF_vect)
{
t=t+1;
}
Grüße!!
Bean
Ja also,
warum wird result und der andere Krempel global deklariert ?
Das tut weh und nicht
was ein ganz normaler Schreibstill ist.Zitat:
also warum solche (t++) unübersichtlichen kürzel schreiben, das das auge weh tut.
Und überlege welche Werte Dein result hat nachdem ADC_einlesen paar mal durchgelaufen ist...
2. In ADC_einlesen machst Du zum Schluß den Wandler aus, wo wird es wieder eingeschaltet ?
3. Vermeide so Sachen wie /3 nimm 2-er Potenzen /4 /8 usw.
Gruß Sebastian
Hallo
Danke für die Antwort, ich war der Meinung dass ich die Variable result global anlegen muss, da Sie ja auch in mehreren Methoden verwendet wird... :-(
Im Moment stehe ich etwas auf dem Schlauch, wenn ich in der While Schleife den ADWandler das erstemal aufgerufen hab, dann steht der AD Wert in Result das hab ich mit auch schon auf einem LCD ausgeben lassen. Dann geht es weiter bis zum Ende der whileschleife. Da ist die Bedingung (t<<...) noch nicht erfüllt, also beginnt die Schleife von vorne. AD Wandler wird erneut aufgerufen etc...
Wo hab ich da meinen Denkfehler? Tut mir Leid dass ich so frag... 8-[ Aber nur dadurch lerne ich etwas... ;-)
Grüße!!
PS.: Noch eine Frage, warum soll ich Zweierpotenzen verwenden? Ist das für den Controller besser? Oder aus welchem Grund? :-k
Bean
Das ist wohl wahr...Zitat:
Tut mir Leid dass ich so frag... Anxious Aber nur dadurch lerne ich etwas...
Hab ich mich verguckt ?Zitat:
ich war der Meinung dass ich die Variable result global anlegen muss, da Sie ja auch in mehreren Methoden verwendet wird...
result wird in main gebraucht und von ADC_einlesen geliefert :-k
deklariere dann in der main result mit uint16_t result;
In ADC_einlesen wird auch eine lokale Variable deklariert und eine 0 zugewiesen
Blöd wenn sie den gleichen Namen haben, das stört aber nicht weiter, wenn Du magst kanst Du sie anders benennen.Code:uint16_t result = 0;
So die Sache mit ADC ausschalten, in der ADC_init wird ADC eingeschaltet, gut
In ADC_einlesen zum Schluß abgeschaltet, und wo wird ADC neu eingeschaltet in der 2. 3. ...n. Wandlung ?
ja die 2-er Potenzen.
Wie Teilt man durch 2-er Potenzen...
Indem man die Zahl binärgesehen um eine Stelle nach rechts schiebt, Beispiel:
Das wäre da /2 /4 muß man es noch eine Stelle nach rechts schieben usw.Code:11001100 -> dezimal 204
01100110 -> dezimal 102
und weißt Du wie lange der AVR für dies da ^ braucht ?
1. Takt bei Deiner 16 Bit Variable dann 2 Takte bei Teilen durch 4 4 Takte
burch 8 6 Takte usw.
Wieviel er bei Teilen /3 braucht entzieht sich meiner Kenntnis, aber glaub mal länger und verbraucht auch entsprechend viel Flash.
So klar soweit ?
Gruß Sebastian
Naja also wenn ich result in main deklariere, dann bekomme ich folgende Fehlermeldung beim Compilieren:
Das sieht mir schon sehr danach aus als wenn die Deklaration gar nicht sooooo schlecht war.... :-sZitat:
../Regelung_Reflow_Ofen.c:134: error: 'result' undeclared (first use in this function)
Ok, ich muss noch die Variable in einlesen deklarieren. Aber warum ist es besser das auf diese Weise zu machen anstatt 1 Variable global anzulegen? Naja die anderen Sachen hab ich noch nicht versucht, aber das mit /4 ist ja schnell geändert... ;-)
Grüße!
Bean
Soll das jetzt heissen, mein Gelabber war hier um sonst ? :-sZitat:
Das sieht mir schon sehr danach aus als wenn die Deklaration gar nicht sooooo schlecht war....
Was steht denn bitte schön in der Zeile 134 und um welche Funktion handelt es sich ?
Hast Du alles gelesen, was ich Dir geschrieben habe ?
Hast Du in ADC_lesen auch eine lokale Variable deklariert ?
Hallo Nein Dein "Gelaber" war natürlich nicht umsonst!!!!
Versteh nur noch nicht warum es besser ist zwei Variablen zu deklarieren anstatt eine global zu deklarieren... :-(
hab in ADC_einlesen auch noch eine result_i deklariert. Und result in main...
Glaube ich hab grad nicht den kopf dafür... geh jetzt erstmal ins Training... morgen ist ein neuer Tag mit viel Zeit... :-)
Grüße und Danke!!
BEan