N Abend,
Ich hab hier n Atmega32 vor mir und Versuche die Sache mit dem Interrupt
zu lernen. Dazu habe ich ein Script gefunden welches mir gefällt.
http://www.avr-tutorials.com/interrupts/avr-external-interrupt-c-programming
Ich hab die Schaltung aufgebaut und die LED's aber an PORT A gesetzt
weil ich auf Port D den Interupt habe (PD2).
Alles Prima, die LED's blinken im in die Reihe (Register Verschieben)
Aber sobald ich den Button Drücke passiert gar nix. Den hab ich am PD2
von PortD und GND gesetzt.
Hier mein Code:
*************
1
#include<avr/io.h>
2
#include<avr/interrupt.h>
3
4
#define F_CPU 8000000UL
5
#include<util/delay.h>
6
7
#define DataPort PORTA
8
#define DataDDR DDRA
9
10
// GICR hat ohne diese beiden define nicht funktioniert.
11
12
#define GIMSK _SFR_IO8(0x3B)
13
#define GICR GIMSK
14
15
16
ISR(INT0_vect)
17
{
18
unsignedchari,temp;
19
20
_delay_ms(50);// Software debouncing control
21
22
temp=DataPort;// Save current value on DataPort
23
24
/* This for loop blink LEDs on Dataport 5 times*/
25
for(i=0;i<5;i++)
26
{
27
DataPort=0x00;
28
_delay_ms(500);// Wait 5 seconds
29
DataPort=0xFF;
30
_delay_ms(500);// Wait 5 seconds
31
}
32
33
DataPort=temp;//Restore old value to DataPort
34
}
35
36
37
38
intmain(void)
39
{
40
DDRD=1<<PD2;// Set PD2 as input (Using for interupt INT0)
41
PORTD=1<<PD2;// Enable PD2 pull-up resistor
42
DataDDR=0xFF;// Configure Dataport as output
43
DataPort=0x01;// Initialise Dataport to 1
44
45
GICR=1<<INT0;// Enable INT0
46
MCUCR=1<<ISC01|1<<ISC00;// Trigger INT0 on rising edge
47
48
sei();//Enable Global Interrupt
49
50
while(1)
51
{
52
if(DataPort>=0x80)
53
DataPort=1;
54
else
55
DataPort=DataPort<<1;// Shift to the left
56
57
_delay_ms(20);// Wait 5 seconds
58
}
59
}
Was mach ich hier falsch? Wahrscheinlich eine kleinigkeit die ich
übersehen habe?
Liebe Grüsse
Randy T. schrieb:> DDRD = 1<<PD2; // Set PD2 as input (Using for interupt INT0)> PORTD = 1<<PD2; // Enable PD2 pull-up resistor> Was mach ich hier falsch? Wahrscheinlich eine kleinigkeit die ich> übersehen habe?
Das ist jedenfalls übel wenn ein Taster an PD2 nach GND schaltet. Keine
Ahnung was sonst noch alles.
@Randy Tomlinson (peroja)
>// GICR hat ohne diese beiden define nicht funktioniert.
Dann sollte man sich fragen, warum das so ist. Gerade als ANfänger macht
man sowas NICHT!
>#define GIMSK _SFR_IO8(0x3B)>#define GICR GIMSK
Alles IO-Register werden über
#include <avr/io.h>
definiert.
Wenn das nicht funktioniert, hast du ein Problem mit deinem Compiler
bzw. deiner IDE.
>ISR(INT0_vect)>{> unsigned char i, temp;> _delay_ms(50); // Software debouncing control
Für EINFACHSTE Test mag das OK sein, für echte Programme später ist das
Murks. Siehe Entprellung.
> DDRD = 1<<PD2; // Set PD2 as input (Using for interupt INT0)
FALSCH! Damit wird PD2 zum Ausgang!
> PORTD = 1<<PD2; // Enable PD2 pull-up resistor> DataDDR = 0xFF; // Configure Dataport as output> DataPort = 0x01; // Initialise Dataport to 1
Deine Mischung aus direktem Ansprechen von IO-Ports und über #defines
ist Mist.
> while(1)> {> if(DataPort >= 0x80)> DataPort = 1;> else> DataPort = DataPort << 1; // Shift to the left
Das ist ersten saumäßig formatiert, sodaß man die Struktur nicht gut
erkennt (Einrückung!) und zweitens falsch. Denn damit wird dein DataPort
NIE geschoben, das Lauflicht kann nicht funktionieren.
>Alles Prima, die LED's blinken im in die Reihe (Register Verschieben)
Glaub ich nicht.
> _delay_ms(20); // Wait 5 seconds
Der Kommentar stimmt keine Millisekunde 8-0
Strukturierte Programmierung auf Mikrocontrollern
Und ein paar Vorwiderstände für die LEDs wären auch nicht schlecht.
Guten Morgen,
noch etwas wichtiges, Taster prellen und wechseln ihren Zustand
willkürlich beim Drücken.
1
ISR(INT0_vect)
2
{
3
unsignedchari,temp;
4
5
_delay_ms(50);// Software debouncing control
6
7
temp=DataPort;// Save current value on DataPort
8
9
/* This for loop blink LEDs on Dataport 5 times*/
10
for(i=0;i<5;i++)
11
{
12
DataPort=0x00;
13
_delay_ms(500);// Wait 5 seconds
14
DataPort=0xFF;
15
_delay_ms(500);// Wait 5 seconds
16
}
17
18
DataPort=temp;//Restore old value to DataPort
19
}
Taster werden nicht über warten in Interrupt Service Routine
"verarbeitet".
Hier steht das Programm, durch das Schreiben auf PortA für rund 5
Sekunden !
ich habe auf mein HW nicht getestet aber dass sollte gewesen sein denke
ich.
sicherheitshalber würde ich auch die External Interrupt Flag Resetten am
anfang. Weiß nicht wie dass in ATMega32 heißt.
und delay innerhalb eine ISR, ob dass eine gute practice ist, weiß ich
nicht.
Vielen Dank. Wieder mal etwas gelernt. Nämlich dass man besser seine
Freunde bei Mikrocontroller fragt als dass man sich auf irgendwelche
Tutorials im Web verlässt. Ich werde das nachher mal genauer anschauen.
Lieben Dank für den Input :-)
Randy T. schrieb:> Dazu habe ich ein Script gefunden welches mir gefällt.>> http://www.avr-tutorials.com/interrupts/avr-external-interrupt-c-programming
Dazu könnte man einiges sagen.
1. Wie kommt der Vogel darauf, eine Taktfrequenz von 4MHz anzugeben,
aber mit keinem Wort davon zu erzählen, das man dazu den internen RC
Oszillator umfusen muss? Ein Tutorial muss sowas entweder erwähnen oder
einfach vom Auslieferzustand mit 1 MHz ausgehen.
2. Dann solche Zeilen hier:
1
_delay_ms(500);// Software debouncing control
in einer ISR! Der ganze Mist blockiert also für ne halbe Sekunde die
Maschine.
3. und er sagts noch dreimal und es ist trotzdem falsch:
1
_delay_ms(500);// Wait 5 seconds
4. Die Schaltung verbindet /RST direkt mit +5V, ohne Pullup, sondern per
Draht. Ganz schlecht und man kann den MC so gar nicht programmieren.
Entweder lässt man /RST offen oder legt ihn auf einen Pullup.
Von wegen
> The Best AVR Microcontroller Tutorials on the Web
ist da schon frech.
Da ist man bei den Tutorials hier deutlich besser aufgehoben:
https://www.mikrocontroller.net/articles/AVR-GCC-Tutorial
Randy T. schrieb:> Ich hab hier n Atmega32 vor mir und Versuche die Sache mit dem Interrupt> zu lernen. Dazu habe ich ein Script gefunden welches mir gefällt.>> http://www.avr-tutorials.com/interrupts/avr-external-interrupt-c-programming
Tu dir selber einen Gefallen und wirf diese Seite aus deinen Bookmarks.
Die Hardware ist kaputt (Reset direkt an Vcc, LED ohne Vorwiderstände,
kein Abblockkondensator) und die meisten Fehler in deinem Programm hast
du per copy-and-paste von da bezogen.
Das ist jetzt erst die zweite Seite, die ich mir da anschaue. Aber jedes
Mal war das ganz großer Bockmist.
Matthias S. schrieb:> Von wegen>> The Best AVR Microcontroller Tutorials on the Web> ist da schon frech.
Die Hardware unten ist aber auch nicht von schlechten Eltern:
Keine Vorwiderstände, keine Stützkondansatoren.
Die Seite gehört ganz oben auf den Index für jugendgefährdende
Schriften.
Matthias S. schrieb:> Da ist man bei den Tutorials hier deutlich besser aufgehoben
Eben...so langsam denk ich das auch. Nein im Ernst, ich nehme die
Tutorials hier natürlich ernst, zumal ich gemerkt habe dass diese immer
mal wieder nach Versions Updates angepasst werden. Ich bin ja schon seit
2007 hier, aber ich hatte aufgrund schwersten Erkrankungen (2x Krebs, 4
Herzinfarkte im 2013, Nierenversagen etc) einfach nie die Mentale Kraft
mich auf die Welt der Elektronik zu konzentrieren. Ich hab zwar
zwischendurch einfachere Projekte machen können. z.B. Verstärker bauen
(siehe bilder), aber das Interesse an µC war immer sehr gross. Ich muss
einfach öfters zwei oder 3mal lesen / fragen weil ich schwierigkeiten
habe das eine oder andere sofort zu begreifen (scheiss medis =
konzentrationsprobleme)
Warum ich das hier Schreibe? Weil ich mir vorstellen kann dass sich der
eine oder andere am Kopf kratzt weil ich eine für Ihn komische frage
stelle und er sich dann fragt ob ich die Tutorials nicht lese. Doch
natürlich tue ich das. Ich erhoffe mir dass ich damit auf ein wenig
Verständniss stosse. :-)
Was das Tutorial aus dem Web...dieser Inder, angeht, man muss sich mal
vor Augen führen dass vielleicht Anfänger wie ich von Anfang an solchen
Mist lernen und dann irgendwann Lebensrettende Geräte entwickeln
(hoffentlich nicht!) <-- Etwas sehr hochgegriffen.
So, dann schau ich mir das mal an und melde mich vielleicht wieder wenn
ich nicht weiterkomme. Euch allen ein nettes Dankeschön für die Hilfe
Randy
Axel S. schrieb:> Die Hardware ist kaputt (Reset direkt an Vcc, LED ohne Vorwiderstände,> kein Abblockkondensator) und die meisten Fehler in deinem Programm hast> du per copy-and-paste von da bezogen.
Hab ich erst jetzt gesehen. Nein mein 32er ist noch intakt. Die LED's
hab ich natürlch mit Vorwiderstand betrieben. Reset muste ich nicht
Verbinden denn ein Reset Button hat es auf dem kleinen Programmierer
Falk B. schrieb:> Das ist ersten saumäßig formatiert, sodaß man die Struktur nicht gut> erkennt (Einrückung!) und zweitens falsch. Denn damit wird dein DataPort> NIE geschoben, das Lauflicht kann nicht funktionieren.>>>Alles Prima, die LED's blinken im in die Reihe (Register Verschieben)>> Glaub ich nicht.
Bitteschön :-)
https://www.youtube.com/watch?v=laFzX49xeZs
@ Randy Tomlinson (peroja)
>>>Alles Prima, die LED's blinken im in die Reihe (Register Verschieben)>>> Glaub ich nicht.>Bitteschön :-)
OK, mein Fehler.
1
while(1)
2
{
3
if(DataPort>=0x80)
4
DataPort=1;
5
else
6
DataPort=DataPort<<1;// Shift to the left
7
8
_delay_ms(20);// Wait 5 seconds
9
}
Ich hatte irgendwie das >= 0x80 anders herum interpretiert 8-0
Matthias S. schrieb:>> http://www.avr-tutorials.com/...> Dazu könnte man einiges sagen.> 1. Wie kommt der Vogel ...
Diese Seite hatten wir doch neulich erst, mit der Aussage, AVR-Ausgänge
würden LEDs mit definiertem (begrenztem) Strom treiben.
Wir solltem dem Betreiber eine Kiste Bananen schicken.