Inhaltsverzeichnis:

Leseschalter mit ATtiny2313 - Gunook
Leseschalter mit ATtiny2313 - Gunook

Video: Leseschalter mit ATtiny2313 - Gunook

Video: Leseschalter mit ATtiny2313 - Gunook
Video: Сенсор почтового ящика для Home Assistant и WhatsAPP 2024, Juli
Anonim
Leseschalter mit ATtiny2313
Leseschalter mit ATtiny2313

Es gab mehrere Instructables, die sich mit Ausgängen des ATtiny2313 und ähnlichen AVR-Geräten befassen. Zum Beispiel https://www.instructables.com/id/Ghetto-Programming%3a-Getting-started-with-AVR-micro/, https://www.instructables.com/id/Drive-a-Stepper- Motor-mit-einem-AVR-Mikroprozessor/. Als ich an dem neuesten von The Real Elliot arbeitete, der zeigte, wie man Schrittmotoren steuert, fand ich, dass es sehr hilfreich wäre, alternative Codeabschnitte im selben Programm ausführen zu können, damit ich nicht jeden ATtiny2313 neu programmieren musste Mal wollte ich eine leichte Codevariation ausprobieren (z. B. Halbschritte oder den Stepper rückwärts laufen lassen). Während es einfach ist, Code mit einer switch/case-Anweisung zu schreiben, um die Auswahl alternativer Variationen zu ermöglichen, ist eine Möglichkeit zur Auswahl der Groß-/Kleinschreibung erforderlich. Das bedeutet, dass eine Art Eingabegerät gelesen werden muss, um das Gehäuse zu steuern. Glücklicherweise verfügt der ATtiny2313 über viele I/O-Pins und ist gut für das Lesen von Eingaben von Schaltern ausgelegt. Dieses Instructable zeigt, wie man Eingaben liest und Entscheidungen basierend auf ihrem Zustand trifft. Da dies allein ein ziemlich langweiliges Instructable machen würde, erkläre ich eine einfache Möglichkeit, die Timer- / Zählerfähigkeit des ATtiny2313 zu verwenden, um einen kleinen Lautsprecher als Piepser anzusteuern. Es wird auch einen kleinen Exkurs über einfache Debugging-Techniken geben.

Schritt 1: Das Eingabegerät

Das Eingabegerät
Das Eingabegerät
Das Eingabegerät
Das Eingabegerät

Dieses Instructable baut auf der hervorragenden Arbeit von The Real Elliot auf und verwendet das von ihm beschriebene ATtiny2313 Ghetto-Entwicklungssystem. Das Datenblatt ATtiny2313 von Atmel ist die ultimative Referenz für alle Funktionen, allerdings nicht unbedingt einfach zu lesen. https://www.atmel.com/dyn/products/datasheets.asp?family_id=607 (Link hat alle AVR-Datenblätter, suchen Sie den 2313.) Die Abbildung zeigt einen einfachen Satz von Eingangsschaltern. Dies ist einfach ein Paket von vier Ein/Aus-Schaltern; auch bekannt als einpolige Einwegschalter (SPST). Typischerweise ist eine Verbindung oder ein Pol jedes Schalters mit Masse verbunden, während die andere Verbindung durch einen Strombegrenzungswiderstand (etwa 10 K) hochgezogen wird. An den Pol mit dem Widerstand ist ein Mikrocontroller-Eingang angeschlossen. Wenn der Schalter geöffnet ist, liest der Mikrocontroller den Eingang als HI. Wenn der Schalter geschlossen ist, liest der Mikrocontroller den Eingang LO. Weitere Informationen finden Sie im Schaltplan. Der ATtiny2313 vereinfacht die Dinge, indem er programmierbare Pullup-Widerstände an den E/A-Pins bereitstellt, wenn sie als Eingänge konfiguriert sind. Dies bedeutet, dass die Schalter einfach einen Pol mit Masse (LO) und den anderen Pol mit einem Prozessoreingang verbinden können. Das erste Beispiel zeigt nur zwei Schalter. Die Schalter werden mit folgendem Code gelesen und konfiguriert. Konfigurieren Sie die Schalter als Eingänge: (Kein Code erforderlich; dies ist die Standardeinstellung.)Schalten Sie die Pullup-Widerstände ein: PORTB = _BV(PB0) | _BV(PB1);Lesen Sie die Eingänge: but1 = ~PINB & 0x03; Beachten Sie die Verwendung von Inversion und Maskierung, um den richtigen Wert zu erhalten.

Schritt 2: Blinkenlights für ein Signal

Wir verwenden diese beiden Schalter, um eine LED eine programmierbare Anzahl von Malen zu blinken. Die LEDs, die wir verwenden werden, sind die Blinkenlights, die The Real Elliot berühmt gemacht hat. Schalter 1 und 2 werden als zwei Binärziffern behandelt, sodass die Kombination die Zahlen 0, 1, 2 und 3 darstellen kann. Unser Programm liest die beiden Schalter und blinkt die LED entsprechend oft, aber nur, wenn der Schalter Einstellungen haben sich geändert. Die Schalter werden für 500 Millisekunden entprellt (nicht optimiert). Der Entprell-Algorithmus ist ziemlich einfach. Die Schalter werden gelesen und das Lesen wird notiert. Unterscheidet er sich vom Wert oldBut (der letzte gespeicherte Wert), dann wird das Programm um 500 Millisekunden verzögert und die Schalter werden erneut gelesen. Wenn der Wert mit dem zuvor gelesenen übereinstimmt, wird der Wert von oldBut aktualisiert und die LED blinkt so oft, wie der Binärwert der beiden Schalter impliziert. Beachten Sie die Invertierung des Wertes, da ein Schalter, der "ein" ist, LO liest. Die Schalter werden kontinuierlich auf weitere Änderungen gescannt. Bitte beziehen Sie sich auf frühere Instructables von The Real Elliot, um mehr über Blinkenlights zu erfahren. Sehen Sie sich diese https://www.ganssle.com/debouncing.pdf an, um mehr über das Entprellen von Schaltern zu erfahren. Hier ist der ATtiny2313-Code für dieses Beispiel. Im Betrieb blinkt dieses Programm die LED an PB4 (physikalischer Pin 8) zweimal, um anzuzeigen, dass es initialisiert ist. Es liest dann die Schalter eins und zwei und blinkt ein- bis dreimal, je nach Schalterstellung, wenn sie geändert werden. Wenn sich die Schalter nicht ändern, blinkt die LED langsam. Um diesen Code auszuführen, erstellen Sie ein neues Verzeichnis (nennen Sie es "Basic", wenn Sie möchten) und laden Sie die folgende C-Code-Datei und das Makefile herunter. Benennen Sie Makefile1.txt in Makefile um. Kompilieren Sie das Programm mit WinAVR und laden Sie es in Ihren ATtiny2313.

Schritt 3: Ein kleiner Exkurs zum Debugging

Wenn Sie wie ich (und jeder andere Programmierer auf der Welt) sind, haben Sie wahrscheinlich Zeiten erlebt, in denen der "fehlerfreie" Code, den Sie sorgfältig eingegeben und kompiliert haben, nicht das tut, was Sie von ihm erwarten. Vielleicht tut es einfach nichts! Also, was ist das Problem? Wie werden Sie es herausfinden? Glücklicherweise gibt es mehrere Ansätze, um Dinge zum Laufen zu bringen. (Besorgen Sie sich dieses Buch für eine hervorragende Behandlung des Themas Debugging. https://www.debuggingrules.com/) Ich möchte ein paar einfache Vorschläge zum Thema Debuggen von Mikrocontroller-Anwendungen machen. Der erste Schritt besteht darin, darauf aufzubauen was du weißt. Wenn Sie einmal ein Blinklicht zum Laufen gebracht haben, verwenden Sie es erneut, um zu sehen, wo Sie sich in Ihrem Programm befinden. Ich möchte, dass die LED zweimal blinkt, um den Start des Programms zu signalisieren. Sie können den Code dazu zunächst beim Start Ihres Programms einfügen. Sobald Sie wissen, dass mit Ihrer Hardware nichts in Ordnung ist, erstellen Sie eine Funktion zum Blinken. Hier ist die Funktion, die ich verwende./*------------------------------------------------------ ------------------------------** blinkEm - Funktion zum Blinken der LED mit PD4** PD4 muss als Ausgang konfiguriert werden. ** ------------------------------------------------ ---------*/void blinkEm(uint8_t count){ while (count > 0){ PORTD = _BV(PD4); _verzögerung_ms(1000); PORTD = ~_BV(PD4); _verzögerung_ms(1000); zählen--; }}Es ist jetzt möglich, diese Funktion an verschiedenen Stellen in Ihrem Code als Signal dafür zu verwenden, dass der Code so weit ausgeführt wurde. Wenn Sie wissen, dass der Code ausgeführt wird, können Sie jeden Abschnitt, der ausgeführt wurde, aber nicht das erwartete Ergebnis ausgeführt hat, sorgfältig untersuchen, um Fehler zu finden. Das Ändern einer Sache nach der anderen ist auch eine Schlüsseltechnik für das Debuggen (beschrieben in der obigen Referenz). Diese klassische Methode funktioniert zusammen mit „Teilen und Herrschen“: In kleinen Schritten werden Funktionen schrittweise hinzugefügt. Dies mag wie ein langsamer Ansatz erscheinen, ist aber nicht annähernd so langsam wie der Versuch, einen großen Abschnitt von nicht funktionierendem Code auf einmal zu debuggen.

Schritt 4: Mehr Debugging

Es gibt viele Fälle, in denen wir einen Codeabschnitt überprüfen möchten, indem wir die meisten Zeilen darin überspringen und sie dann einzeln aktivieren, während wir überprüfen, ob jeder funktioniert. Normalerweise tun wir dies, indem wir Zeilen "auskommentieren", die wir überspringen möchten. Eine Erweiterung dieser Technik ist das Ausschneiden und Einfügen eines Codeblocks, das Auskommentieren des Originals (damit wir es nicht verlieren) und das Hacken der Kopie. C bietet vier einfache Möglichkeiten, Zeilen auskommentieren zu können. Wenn Sie "//" vor eine Zeile setzen, kommentieren Sie diese Zeile aus. Wenn Sie eine oder mehrere Zeilen in "/*" und "*/" einschließen, wird ein ganzer Abschnitt auskommentiert. Damit diese Methode effektiv funktioniert, darf im Codeblock kein anderes "*/" vorhanden sein (außer dem abschließenden). Eine effektive Disziplin besteht also darin, // für Kommentare innerhalb von Codeblöcken zu verwenden und das Konstrukt /* */ für Kommentarblöcke und zum Auskommentieren von Codeabschnitten zu reservieren und den Abschnitt mit "#endif" beenden. Eine gezieltere Steuerung ist mit "#ifdef (identifier)" am Anfang eines Blocks und "#endif" am Ende möglich. Wenn der Baustein übersetzt werden soll, verwenden Sie "#define (Bezeichner)" weiter oben im Programm. Beachten Sie, dass die Anführungszeichen nur zur Hervorhebung dienen und nicht eingefügt werden dürfen. Die Kombination dieser Techniken sollte einen nützlichen Ansatz zum Debuggen Ihrer ATtiny2313-Programme bieten. Sie können diese Tools nützlich finden, während wir dieses Instructable durchlaufen.

Schritt 5: Timer/Zähler 0 für Signaltöne verwenden

Verwenden von Timer/Zähler 0 für Signaltöne
Verwenden von Timer/Zähler 0 für Signaltöne

Der ATtiny2313 verfügt über zwei leistungsstarke Timer/Counter-Ressourcen: eine 8-Bit- und eine 16-Bit-Ressource. Diese können als Frequenzgeneratoren, variable Pulsweitenmodulations-Controller und Ausgangsvergleichsregister konfiguriert sein. Deren volle Funktionalität ist auf 49 Seiten des Datenblattes beschrieben. Wir verwenden jedoch einen einfachen Fall. Es wird nur Timer/Counter 0 (der 8-Bit) verwendet und er wird einfach als Frequenzgenerator verwendet. Die Frequenz wird an einen kleinen Lautsprecher geleitet, um einen Piepton zu erzeugen. Timer/Counter 0 ist auf den Seiten 66 bis 83 des ATtiny2313-Datenblatts ausführlich beschrieben. Eine genaue Lektüre dieses Materials wird einem ein vollständiges Verständnis von Zeit/Zähler 0 vermitteln. Glücklicherweise ist ein ziemlich einfacher Modus, Clear Timer on Compare (CTC), alles, was erforderlich ist, um den gewünschten Piepton zu erzeugen.

Für den von uns verwendeten Modus ist die Bedienung des Timers/Zählers unkompliziert. Wenn ein Taktsignal ausgewählt wird, beginnt der Zähler bei Null und inkrementiert jeden Taktimpuls. Wenn der Zählerwert den Wert im Ausgangsvergleichsregister (TOP) erreicht, wird der Zähler auf Null zurückgesetzt und die Zählung beginnt erneut. Das dem Zeitgeber/Zähler zugeordnete Ausgangsbit wird umgeschaltet, um eine Rechteckwellenausgabe zu erzeugen. Dies treibt direkt einen Audiowandler an, um einen Piepton zu erzeugen. Ein kleiner TDK Audio Transducer erzeugt den Piepton. Ein geeignetes Gerät ist Digikey 445-2530-ND, TDK SD1209T3-A1 (ich habe eine frühe Version davon verwendet). Dies ist eine 3-Volt-Version; die 5-Volt-Version wird auch funktionieren, erwarte ich. Ich fahre dies direkt vom Ausgangsport des Attiny2313 und es scheint gut zu funktionieren. Sparkfun hat ein ähnliches Gerät.

Schritt 6: Konfigurieren von Timer/Zähler 0

Der CTC-Modus kann verwendet werden, um den Ausgang OC0A auf Pin 2, Port B (physikalischer Pin 14) umzuschalten. Um die Ausgabe an diesem Pin zu aktivieren, muss DDRB entsprechend eingestellt werden. Der C-Code dafür ist wie das Einrichten eines Ausgangs für ein Blinkenlight. DDRB = _BV(PB2); // Port B2 ist ein Ausgang. Der nächste Schritt besteht darin, ein Taktsignal bereitzustellen und das Ausgangsvergleichsregister zu laden, um eine Wellenform als Frequenz zu erzeugen. Die Gleichung für die resultierende Frequenz ist im Datenblatt (Seite 72) angegeben. Terme in der Gleichung werden unten beschrieben. Hier ist die Gleichung: fOC0A = fclk_I/O / 2*N*(1+OCR0A)Wo fOC0A:= Ausgangsfrequenz fclk_I/O:= Taktquellenfrequenz N:= Taktvorskalierungsfaktor OCR0A:= Wert im Ausgangsvergleichsregister für Timer/ Zähler 0A. Clock Source Frequency, fclk_I/ODies ist die Frequenz des Systemtakts. Der Standardwert ist 1MHz. Die Bits CS00, CS01 und CS02 von TCCR0B steuern diese Auswahl. Da diese Bits auch den Wert von N auswählen, wird er als nächstes beschrieben. Prescaler Value, NN ist der Wert, der zum Teilen oder Vorskalieren des Systemtakts verwendet wird. Die Bits CS00, CS01 und CS02 von TCCR0B steuern diese Auswahl. Tabelle 41 auf Seite 81 des ATtiny2313-Datenblatts beschreibt die Kombinationen. Da eine Frequenz nahe 1 kHz erwünscht ist, werden die Bits CS00 und CS01 von TCCR0B gesetzt. Beachten Sie, dass das Setzen aller drei Bits auf 0, wodurch keine Taktquelle ausgewählt wird, die Ausgabe effektiv stoppt. Dies ist die Methode, die verwendet wird, um den Signalton zu starten und zu stoppen. TOP-Wert, OCR0ADieser Wert ist der TOP-Wert für den Zähler, der in das Ausgangsvergleichsregister für Timer/Zähler 0A geladen wird. Wenn dieser Wert erreicht ist, wird der Zähler auf Null zurückgesetzt und die Zählung beginnt erneut, bis TOP erreicht ist und der Zyklus wiederholt wird. TOP lässt sich leicht ändern, so dass die Frequenz des Piepsers leicht geändert werden kann. Da eine Frequenz nahe 1 kHz erwünscht ist, wird TOP auf 7 gesetzt. (Beachten Sie, dass der Vorteiler auf 8 und TOP auf 63 gesetzt sein könnte. Gleiches Ergebnis - Ihre Wahl.)Ausgangsfrequenz, fOC0AVerwenden der Gleichung zur Berechnung der Ausgangsfrequenzergebnisse in: fOC0A = 1, 000, 000 / 2 * 64 * (1+7) fOC0A = 977HzNah genug! Hier ist der Code zum Laden des Ausgangsvergleichsregisters und des Timerzählersteuerregisters 0B. Bitte sehen Sie sich den aktuellen Programmcode an, um zu verstehen, wie diese verwendet werden. OCR0A = 7; // Zeitwert TCCR0B = _BV(CS01) | _BV(CS00); // Interne Uhr auswählen & prescale=8 TCCR0B = 0; // keine Taktquelle schaltet den Ton aus Einstellen des Zeit-/Zählermodus Als letztes Detail werden wir den gewünschten Timer-/Zählermodus angeben, indem wir die entsprechenden Bits im Timer-/Zählersteuerregister 0A setzen. Der CTC-Modus wird durch Setzen des Bits WGM01 wie in Tabelle 40, Seite 79 des Datenblatts beschrieben, ausgewählt. Da der Ausgang jeden Zyklus umschalten soll, muss auch das Bit COM0A0 gesetzt werden, wie in Tabelle 34 auf Seite 77 beschrieben. Hier ist der Code: TCCR0A = _BV(COM0A0) | _BV(WGM01); // CTC-Umschaltmodus

Schritt 7: Verwenden von vier Schaltern

Während wir den Piepser implementieren, erweitern wir unsere Hardware und Software, um vier Schalter zu handhaben. Da der Ausgang von Timer Counter 0A auf Port B, Pin 2 liegt, können wir nicht einfach sequentiell weitere Schalter an Port B anschließen. Eine einfache Lösung wäre die Verwendung von Port D, aber lassen Sie uns diesen Port für andere Funktionen verfügbar (vielleicht ein Schrittmotor). Schließen wir also die zusätzlichen Switches an PB3 und PB4 an. Das Lesen der Switches ist größtenteils unverändert. Der Maskenwert wird in 0x1B (00011011 binär) geändert, um Bit 2 zusammen mit 5, 6 und 7 zu maskieren. Ein weiterer Trick wird verwendet, um eine 4-Bit-Binärzahl zu erstellen. Verschiebe die Bits 3 und 4 um ein Bit nach rechts und kombiniere sie mit den Bits 0 und 1 zu einer 4-Bit-Binärzahl. Dies ist die Standard-C-Syntax zum Verschieben und Kombinieren von Bits, ist aber dem Neuling möglicherweise nicht gut bekannt. but1a = (but1 & 0x03) | ((aber1 & 0x18) >> 1); // but1 hat Switch ReadingIm Betrieb blinkt das Programm zweimal und piept zweimal, um die Initialisierung zu signalisieren. Jedes Mal, wenn die Schalter geändert werden, ertönt die Nummer, die sie darstellen. Wenn sich die Schalter nicht ändern, blinkt die LED. Um diesen Code auszuführen, erstellen Sie ein neues Verzeichnis (nennen Sie es Beep, wenn Sie möchten) und laden Sie die folgende C-Codedatei und das Makefile herunter. Benennen Sie Makefile2.txt in Makefile um. Kompilieren Sie das Programm mit WinAVR und laden Sie es in Ihren Attiny2313.

Schritt 8: Verwenden des Schalter- / Gehäusekonstrukts

Der letzte Schritt ist „nur Software“: Wie versprochen implementieren wir das Switch/Case-Konstrukt. Obwohl dieses Beispiel nur zwei alternative Aktionen zeigt, sollte es sehr klar sein, wie dieses Konstrukt verwendet wird, um einen von mehreren alternativen Codeabschnitten auszuwählen. Im Betrieb überwacht dieses Programm die Schalter und piept bei einer Änderung die entsprechende Zahl, wenn sie ungerade ist; es blinkt, wenn die Zahl gerade ist. Es tut nichts, es sei denn, ein Schalter ändert sich.

Um diesen Code auszuführen, erstellen Sie ein neues Verzeichnis (benennen Sie es Switch, wenn Sie möchten) und laden Sie die folgende C-Codedatei und das Makefile herunter. Benennen Sie Makefile3.txt in Makefile um. Kompilieren Sie das Programm mit WinAVR und laden Sie es in Ihren Attiny2313.

Schritt 9: Fazit

Abschluss
Abschluss

Das war's! Jetzt wissen Sie, wie Sie Schalter verwenden, um die Ausführung Ihres Programms zu steuern, indem Sie sie einlesen und eine Aktion basierend auf der Schaltereinstellung auswählen. Sie wissen auch, wie man einen Piepton erzeugt und haben auch einige Debug-Strategien gelernt.

Wenn Sie Ihr Verständnis testen möchten, ändern Sie das letzte Programm so, dass es bei geraden Tönen mit hoher Tonhöhe piept, bei ungeraden Tönen eine tiefe Note ausgibt und die LED kontinuierlich blinkt, wenn sich die Schalter nicht ändern. Vielleicht möchten Sie nachsehen zurück zum Abschnitt zum Debuggen, um Hilfe zu erhalten.

Empfohlen: