- 12V Akku mit 280 Ah bauen         
Seite 1 von 2 12 LetzteLetzte
Ergebnis 1 bis 10 von 12

Thema: Probleme mit Taster zum Auslösen des externen Interrupts

  1. #1
    Neuer Benutzer Öfters hier
    Registriert seit
    08.11.2009
    Beiträge
    6

    Probleme mit Taster zum Auslösen des externen Interrupts

    Anzeige

    LiFePo4 Akku selber bauen - Video
    Hallo!

    Ich habe ein RN-Minicontrol Board (mit Atmega16 und ein RN-Speak, das über I2C mit dem Controller verbunden ist. Am Controllerboard hängt auch ein Ultraschallsensor. Ab einer bestimmten Entfernung werden die Abstandswerte als Sprachnachrichten über das RNSpeak ausgegeben. Programmiert ist das ganze unter BASCOM.

    Das hat bisher super funktioniert.

    Jetzt möchte ich, dass die Messung und Ausgabe nur dann durchgeführt wird, wenn ich einen Taster betätige, der an JP1 angeschlossen ist. Und ab jetzt funktioniert gar nichts mehr. Prinzipiell ist mein Programm folgendermaßen aufgebaut:
    .
    .
    .
    config pind.2=input
    config int0=rising
    enable interrupts
    enable int0
    on int0 ausgabe
    portd.2=0

    do
    NOP
    loop
    end

    Ausgabe:

    ...
    return


    meinen drucktaster habe ich zwischen 5V und Signalpin an JP1 geschalten. der interrupt wird scheinbar total willkürlich ausgelöst auch wenn ich den taster nicht drücke und wenn ich den taster drücke wird er auch manchmal nicht ausgelöst. manchmal gibt rn-speak auch einfach die letzte message aus, was so im programm gar nicht auftaucht. außerdem wird das Programm zwischendurch einfach hin und wieder neu gestartet. Einen Kurzschluss habe ich aber sicher nirgendwo.
    Ich bin mir nicht sicher ob es sich um ein Hardware- oder Softwareproblem handelt. Kann es am Taster liegen? Oder an den Kabeln? Oder muss ich für den externen Interrupt noch zusätzliche Einstellungen machen? In der Bascom Hilfe habe ich gelesen dass ich beim atmega168 das r23 sichern muss??


    Hilfe!! Ich bin wirklich verzweifelt. Hat jemad eine Idee?

  2. #2
    Moderator Robotik Einstein Avatar von Kampi
    Registriert seit
    21.11.2009
    Ort
    Monheim, Nordrhein-Westfalen, Germany
    Alter
    34
    Beiträge
    3.501
    Blog-Einträge
    9
    Entprell mal den Taster im Programm also einfach schreiben:

    If Pin(Taster) = 0 then ....
    Waitms100
    If Pin(Taster) = 0 then....

    und schalt den Taster mal nicht gegen 5V sondern gegen Ground. Also 5V mit einem 10k Ohm Widerstand an Interrupt dazu parallel den Taster gegen Ground, soass wenn der TAster gedrückt wird eine Verbindung von Vcc und GND besteht. So haste nämlich zwei fest definierte Pegel. EInmal die 5V und einmal 0V

  3. #3
    Neuer Benutzer Öfters hier
    Registriert seit
    11.02.2010
    Beiträge
    29
    Mit Interrupts kann man viel Spaß haben - vorallem wenn man mehrere hat und diese nur zu bestimmten Zeiten aktiviert oder deaktiviert

    Als Tip habe ich noch für dich:
    -In der Interruptroutine nur ein Bit setzen und dann in der Hauptschleife dieses Bit auswerten und rücksetzen. Das vermeidet viele Probleme weil wenn gerade ein Interrupt ausgeführt wird kein anderer Interrupt greifen kann bzw. nur ein Interrupt mit höherer Priorität greifen kann.
    -Ein debouncen des Tasters kannst du dir Sparen, wenn du nach der Auswertung in der Hauptschleife den Interrupt ausschaltest und nach Abarbeitung wieder einschaltest.
    Code:
    do
    If Bit = 1 then
       Disable Int 0
       Auswertung......
    
       .... Auswertung ende
       Reset Bit
       Enable Int 0
    end if
    loop
    end
    
    interrupt:
    set bit
    return
    Als Grundregel gilt: Interrupts so kurz wie möglich.

    Grüße Stefan

  4. #4
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    08.01.2006
    Beiträge
    4.555
    Entweder an JP.1 den internen Pull up einschalten oder
    einen externen 10k gegen vcc anschließen. Den Taster
    dann von JP.1 nach GND schalten UND config int0=rising
    ändern auf = falling. Man kann noch parallel zum Taster
    einen 100 nF setzen.

    Gruß Richard

  5. #5
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    16.02.2006
    Beiträge
    1.113
    Hallo Stefan,
    in deiner Antwort sind einige Ungenauigkeiten, die so nicht stehen bleiben sollten.
    Zitat Zitat von reinhars
    -In der Interruptroutine nur ein Bit setzen und dann in der Hauptschleife dieses Bit auswerten und rücksetzen. Das vermeidet viele Probleme weil wenn gerade ein Interrupt ausgeführt wird kein anderer Interrupt greifen kann bzw. nur ein Interrupt mit höherer Priorität greifen kann.
    Während ein Interrupt in seiner ISR behandelt wird, kann kein anderer Interrupt ausgeführt werden. Auch ein Interrupt mit höherer Priorität kann diesen nicht unterbrechen.
    Prioritäten sind nur interessant, wenn zu einem Zeitpunkt gleich mehrere Interrupts zur Ausführung anliegen. Dann und nur dann wird tatsächlich nach der Reihenfolge abgearbeitet, die im Datenblatt angegeben ist. Ansonsten verwenden die AVRs keine Prioritäten.
    Zitat Zitat von reinhars
    -Ein debouncen des Tasters kannst du dir Sparen, wenn du nach der Auswertung in der Hauptschleife den Interrupt ausschaltest und nach Abarbeitung wieder einschaltest.
    Das Disablen des Interrupts führt nur dazu, dass momentan keine ISR aufgerufen wird. Trotzdem ist der Interrupt intern vermerkt und führt nach Enable Interrupt sofort zu dessen Ausführung. Ein Prellen kannst du dadurch also nicht beseitigen.


    Zitat Zitat von reinhars
    Als Grundregel gilt: Interrupts so kurz wie möglich.
    Das ist jedenfalls die richtige Vorgehensweise, führt aber nicht unbedingt zu problemloser Ausführung. Man muss die Möglichkeit der Unterbrechung des Ablaufs mit Verstand einsetzen und sich überlegen, wann sollen welche Code Teile ausgeführt werden und welche Teile möchte ich vor Unterbrechung schützen.
    Es macht wenig Sinn, eine ISR auf das Setzen eines Flags zu beschränken um dann in der Hauptschleife sofort die Interrupts zu sperren. Dann lege ich die Befehle lieber gleich in die ISR.

  6. #6
    Erfahrener Benutzer Robotik Visionär Avatar von oberallgeier
    Registriert seit
    01.09.2007
    Ort
    Oberallgäu
    Beiträge
    8.677
    Zitat Zitat von for_ro
    ... Während ein Interrupt in seiner ISR behandelt wird, kann kein anderer Interrupt ausgeführt werden. Auch ein Interrupt mit höherer Priorität kann diesen nicht unterbrechen ...
    Falsch. Beispiel, gilt bei allen Atmel die ich kenne:
    Zitat Zitat von At[size=1
    [/size]mel im doc 8161D–AVR–10/09]... When an interrupt occurs, the Global Interrupt Enable I-bit is cleared and all interrupts are disabled. The user software can write logic one to the I-bit to enable nested interrupts. ...
    Ciao sagt der JoeamBerg

  7. #7
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    16.02.2006
    Beiträge
    1.113
    Guter Hinweis: Wenn man sie explizit in der ISR wieder freigibt, geht es mit allen Interrupts doch. Standardmäßig ist dieses Verhalten abgeschaltet.
    Ist aber eher etwas für den absoluten Fachmann wie dich. Hier gilt noch mehr, das man genau wissen sollte, was man da tut.

  8. #8
    Neuer Benutzer Öfters hier
    Registriert seit
    08.11.2009
    Beiträge
    6
    vielen dank schonmal für die tips! wird durch den befehl portd.2=1 der pull up widerstand gesetzt? oder gibt es da einen anderen befehl unter bascom?

  9. #9
    Neuer Benutzer Öfters hier
    Registriert seit
    08.11.2009
    Beiträge
    6
    Hallo!
    Also mit dem Taster auf GND funktioniert das Schalten jetzt einwandfrei, vielen Dank. Ich habe den Code auch nach dem Vorschlag von reinhars umgestaltet. allerdings wird das interrupt trotzdem bei etwas längerem drücken des Tasters zweimal ausgelöst. Habe schon versucht dies mit einer waitschleife mit bis zu 10 sekunden vor dem erneuten enable des interrupts zu vermeiden. jetzt kommt der zweite Interrupt nach dieser wartezeit!! sieht jemand den fehler?

  10. #10
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    08.01.2006
    Beiträge
    4.555
    Das ist kein Fehler, auch bei ausgeschaltete IRQ werden die
    gespeichert und nach dem Freigeben in der gespeicherten
    Reihenfolge abgearbeitet. Wenn das verhindert werden soll
    muss man vor dem verlassen des IRQ das IRQ Flac löschen.

    Ich habe es nicht genau im Kopf, aber ich glaube das dieses
    Flac gelöscht wird wenn dort eine (1) gesetzt wird?

    Gruß Richard

Seite 1 von 2 12 LetzteLetzte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

LiFePO4 Speicher Test