Forum: Mikrocontroller und Digitale Elektronik IR-Schalter mit tiny 13


von Michael K. (micha_k)


Lesenswert?

Hallo zusammen,
mein Vorhaben:
Ich möchte mit einer Fernbedienung einem tiny13 mitteilen, dass er ein 
Relais (oder zwei) schaltet.
Ich habe minimales Vorwissen zur c-Programmierung und möchte es gerne 
ausbauen.
In meinen Vortests habe ich mit einem Arduino herrumgespielt und bin mit 
dieser Anleitung (http://deskfactory.de/arduino-infrarot-fernbedienung) 
ganz gut klargekommen.
Jetzt möchte ich dies so in meinen tiny13 übertragen. Ich habe ein 
ähnliches Projekt im Netz gefunden, das aber in assembler geschrieben 
wurde.http://www.avr-asm-tutorial.net/avr_de/ir/ir_rx/ir_rx.html
Kann mir jemand bei der "Übersetzung" helfen?
Gruß Micha

von L&L (Gast)


Lesenswert?

Michael K. schrieb:
> Kann mir jemand bei der "Übersetzung" helfen?

Lerne und mach es selbst. Wenn du da nicht weiterkommst kannst du sicher 
hier nachfragen. Ob dir das hier jemand komplett übersetzt wage ich zu 
bezweifeln.

von Wolfgang (Gast)


Lesenswert?

Michael K. schrieb:
> Kann mir jemand bei der "Übersetzung" helfen?

Der Assembler Quelltext passt doch für deinen ATtiny13. Denn Rest macht 
hoffentlich dein PC mit dem Assembler (Programm) selbständig. Den 
erzeugten Hex-File musst du dann nur noch mit dem Programmer auf deinen 
ATtiny schieben.

von Axel S. (a-za-z0-9)


Lesenswert?

Michael K. schrieb:
> Ich möchte mit einer Fernbedienung einem tiny13 mitteilen, dass er ein
> Relais (oder zwei) schaltet.

Warum der tiny13? Der hat sehr wenig Flash, das macht es schwieriger.

> In meinen Vortests habe ich mit einem Arduino herrumgespielt und bin mit
> dieser Anleitung (http://deskfactory.de/arduino-infrarot-fernbedienung)
> ganz gut klargekommen.

Naja. Mehr als rudimentäre Grundlagen hast du da nicht gelernt. Es ist 
ein Anfang, ja. Aber noch ein weiter Weg zu gehen.

> Jetzt möchte ich dies so in meinen tiny13 übertragen. Ich habe ein
> ähnliches Projekt im Netz gefunden, das aber in assembler geschrieben
> wurde.http://www.avr-asm-tutorial.net/avr_de/ir/ir_rx/ir_rx.html
> Kann mir jemand bei der "Übersetzung" helfen?

Nein.

Ich halte dieses Programm auch nicht für geeignet, um das Programmieren 
eines IR-Empfängers zu erlernen. Da fängst du besser bei 0 an. Überhaupt 
mußt du erstmal wissen, welches Protokoll deine Fernbedienung sendet und 
welche Tastencodes dein µC erkennen können soll.

Ist aber kein schlechtes Projekt für einen nicht-mehr-ganz Anfänger. Um 
überhaupt erst mal zum Startpunkt zu kommen, lies den Artikel IRMP 
und dort insbesondere die Informationen zu den verschiedenen 
Fernsteuer-Protokollen.

Wenn du nur schnell zu einem Ergebnis kommen willst, kannst du die IRMP 
Software verwenden. Allerdings brauchst du dafür einen ATtiny85 (tiny45 
könnte auch reichen, kostet aber kaum weniger).

von Michael K. (micha_k)


Lesenswert?

Hallo Wolfgang,
da ich aber kein assembler verstehe (noch weniger als C-code) kann ich 
ihn auch nicht für meine Fernbedienung anpassen :-(
ich bräuchte solch ein Projekt in C.
Wie lese ich den IR-Code in meinen tiny ein bzw. frage ihn ab?
eigendlich sind es ja nur zwei oder vier verschiedene code´s die ich 
abfragen muss.
Habt ihr einen Vorschlag wie ich dies angehen soll?
Gruß Micha

von Rene Z. (rzimmermann)


Lesenswert?

Nimm einen Tiny45/85 und IRMP. Dann wird es sehr einfach und du kommst 
schnell zu einem Ergebnis. Gruß Rene

von Michael K. (micha_k)


Lesenswert?

Hallo Axel,
danke für deinen Beitrag.
Meine Wahl für den Tiny 13 ist durch drei Dinge gekommen.
1. ich habe noch welche in der Schublade ;-)
2. er hat nur acht Beinchen, somit hängt nicht so viel Bein nutzlos in 
der Gegend rum.
3. Jemand hat es schon einmal gemacht (leider in Assembler)

Leider bin ich auch immer sehr ungeduldig wenn ich mit etwas beginne ;-)
Die ganze LED-Blinkerei, Tastereinlesen und so weiter habe ich schon 
durch und dachte mir "jo, warum nicht mal mit der Fernbedienung 
rumspielen!?". Da die Sache dann mit dem Arduino so einfach schien, 
hatte ich die Hoffnung, es ließe sich auf dem kleinen fortsetzen :-(.

Möglicherweise hat dies hier schon vor mir jemand umgesetzt, der sein 
Ergebniss teilen möchte!?

Noch einmal Danke!!!

Gruß Micha

von renezimmermann (Gast)


Lesenswert?

Na ja der Euro für einen Tiny45 wird dich nicht umbringen.
Ist wie der Tiny13 auch im Dil8 oder So8 Gehäuse.
Und bedenke keiner weiß welchen Code deine FB benutzt.

http://www.mikrocontroller.net/articles/IRMP

Da steht alles was du brauchst. Den Rest macht dann der Compiler.

Gruß

von Michael K. (micha_k)


Lesenswert?

Hallo Rene,
wie gesagt die Ungeduld...
Ich habe gerade den 85-er bestellt ;-)!!!
Ich werde dann meine Ergebnisse mitteilen, damit dann auch andere 
Anfänger was davon haben!
so long

Micha

von renezimmermann (Gast)


Lesenswert?

Na dann frohes Basteln. Denk dran wenn du dein Protokoll nicht kennst 
brauchst du noch ein IR-Empfänger wie z.B. TSOP31236 auch ein grösserer 
Controller mit USART ist dann ganz praktisch. Ich benutze zum finden des 
FB Codes einen Arduino Nano weil da an Hardware (Mega328 + Usb2Uart) 
alles drauf ist was man braucht. Gruß

von gerd (Gast)


Lesenswert?

Hallo.

Für einen IR-Empfänger mit zwei oder drei Schaltstufen (Relais) braucht 
man drei Ausgabepins, einen INT0- oder PCINT-Pin mit einem 
Empfängermodul dran und einen 8-Bit-Timer. Und ein paar dutzend (!) 
Worte interrupt-gesteuertes Programm. Also wozu sollen irgendwelche 
Riesen-AVRs gut sein, außer zur Beschäftigung mit lauter selbst 
generierten Problemchen?

Und wer zu faul ist, die Protokolle von irgendwelchen Fernsteuerungen zu 
untersuchen, nimmt einfach einen weiteren ATtiny13, eine IR-LED mit 
einem Vorwiderstand, zwei oder drei Tasten und wiederum einige dutzend 
Programmworte (!) und strickt sich sein eigenes unverwechselbares 
Protoköllchen zusammen. Vorschlag: eine lange Pause mit 5 ms Dauer, eine 
weitere mit 2 ms, dazwischen jeweils eine ms LED-Flackern, dann drei 
Bits aus 200 µs LED-Flackern und 200 µs Pause bei Null (Relais aus) und 
400 µs Pause bei Eins (Relais an). So einfach kann die Welt sein, wenn 
man nur die richtigen Werkzeuge dafür ansetzt.

Kann es sein, dass C einfach die falsche Programmiersprache für solche 
super-einfachen Aufgaben ist? Und dass das dauernde Rumsuchen nach immer 
größerem Flashspeicher den AVR nur mit immer mehr überflüssigem 
Datenmüll im riesigen Speicher befüllt statt die eigentlichen Aufgaben 
effizient und zielgerichtet zu lösen? Kann es sein, dass hier versucht 
wird mit einem 10-kg-Vorschlaghammer eine kleine Beule an einer 10 cm 
großen Metallvase auszubessern? Und dass der Vorschlag, nun besser von 
10 auf 20 kg umzusteigen den Frager irgendwie in die falsche Richtung 
und jedenfalls weit weg von einer Lösung für sein Problem führt? 
Irgendwie drollig, diese abgehobenen C-Freaks.

Das von mir geschriebene und veröffentlichte Programm in Assembler ist 
für die eigentliche Aufgabe auch eigentlich noch viel zu umfangreich 
(275 Programmworte), weil es außer dem einen Relais auch noch zwei 
digitale Lautstärkeregler ansteuert. Die Vase hier braucht aber nicht 
mal einen 100 g Hammer. Ich kann nur abraten, den Assembler-Quellcode 
anpassen (oder in C übersetzen) zu wollen, weil das unnötig kompliziert 
würde und das meiste von der eigentlichen, ganz einfachen Aufgabe 
wegführen würde.

Ich schreibe gerade an einem längeren Kursscript, mit dem man an 
praktischen Beispielen Assembler lernen kann. In Lektion 12, die ich 
schon fertig habe, gibt es alles über Infrarot-Fernsteuerungen, einen 
ATtiny24 mit einer 4*20-LCD-Anzeige zum Analysieren von 
IR-Fernsteuersignalen (wenn man die ganze LCD-Mimik weglässt, werden 
daraus "einige Dutzend" Programmworte für den eigentlichen Empfang), und 
einen ATtiny13, der 16-Bit-Worte über eine IR-LED sendet. Aber natürlich 
alles in Assembler, nix mit 10-kg-Hammer.

Die eigentlichen Aufgaben, das 40kHz-Sendesignal im ATtiny13 zu 
generieren und mit dem Empfängermodul an einem PCINT-Eingang vom 
ATtiny24 zu empfangen und mit dem Timer auszuzählen, sind dort aber viel 
klarer und einfacher beschrieben.

Obwohl das noch nicht ganz fertig ist, würde ich das PDF Micha K schon 
mal vorab schicken. Es sei denn, er kriegt beim Wort Assembler rote 
Pickel. Meine Email-Adresse gibt es auf der Webseite (die mit info@ in 
nicht-maschinenlesbarem Format). Alle anderen müssen warten, bis Kapitel 
14 auch noch fertig ist.

mfg
gerd

von Rene Z. (rzimmermann)


Lesenswert?

Zu dem "Riesen Avr" habe ich geraten da das fertige Hardware (Arduino) 
ist und keine 5€ kostet. Ir Empfänger dran und fertig. Das ganze wie 
gesagt nur um herauszufinden welchen Code die FB nutzt. Für die Relais 
zu schalten reicht dann der Tiny45. Das habe ich oben ja auch so 
geschrieben. Man müsste das nur mal lesen. Die Software gibt es fertig. 
Nennt sich IRMP. Warum das Rad immer neu erfinden? Assembler ist hier 
einfach nicht nötig, egal ob rote Pickel oder auch nicht. Gruß

: Bearbeitet durch User
von Harry L. (mysth)


Lesenswert?

Ich kann -ehrlich gesagt- dieses dumme Gelaber von den "ach so 
effizienten Assemblerprogrammen" langsam nicht mehr hören/lesen!

Klar gibt es -wenige- Situationen, wo sowas erforderlich sein "kann" 
(dafür gibt es die Möglichkeit, Assembler als inline im Code 
einzufügen), aber ich hab mich lange genug mit Assembler rum geärgert 
(noch zu Z80-Zeiten), um die Vorteile einer "les- und portier-baren 
Hochsprache" schätzen zu lernen.

Bei den Verfechtern der Assembler-Programmierung scheint es sich eher um 
Menschen zu handeln, die vor 20,30 oder 40J mal programmieren gelernt 
haben (wie ich auch), aber zu faul waren Neues zu erlernen.

Die Hardware kostet fast nichts mehr, und warum sollte ich mir sowas 
heute noch ohne Not antun?

Moderne CPUs sind ohnehin auf den Code, den moderne Compiler produzieren 
optimiert.
Speicher kostet auch praktisch kein Geld mehr, und die Chip-Hersteller 
schicken einem keinen Scheck, wenn man einige Bytes sparen kann.

Was soll der Schwachsinn?

Es macht einfach keinen Sinn, für Anfänger die Einstiegs-Hürden 
künstlich hoch zu halten, nur um sich selbst als "Experten" zu 
präsentieren.

just my2cent

Harry

: Bearbeitet durch User
von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

gerd schrieb:
> Also wozu sollen irgendwelche
> Riesen-AVRs gut sein, außer zur Beschäftigung mit lauter selbst
> generierten Problemchen?

Warum schreibst Du dann über dieses doch so triviale Problemchen dann 
gefühlte 1000 Zeilen hier im Thread? Das passt nicht zusammen. Wenn es 
doch so einfach ist, hätten 2 Sätze genügt. Das ganze sieht daher doch 
stark nach einer Selbstdarstellung aus.

> In Lektion 12, die ich schon fertig habe, gibt es alles über Infrarot-
> Fernsteuerungen

Da steht wirklich "alles"?!?

Wo kann ich Lektion 12 nachlesen? Dann zeige ich Dir gern, was Du 
"alles" vergessen hast ;-)

von lars (Gast)


Lesenswert?

Harry L. schrieb:
> just my2cent

Wohl wie alles andere auch irgendwo aufgschnappt?

von Michael K. (micha_k)


Lesenswert?

Hallo zusammen,
es ist sehr schön eine kontroverse Diskusion zu verfolgen, aber bleibt 
soch bitte sachlich.
Es ist für Leute wie mich (Anfänger) immer sehr schwer aus einem Thread 
mit ansprechender Überschrift die eigentliche Antwort herauszufiltern.
In Fachkreisen spricht man von offtopic glaube ich ;-)

So, gestern war der Postbote da und hat neue Tiny85 gebracht. Nun noch 
einmal die vorsichtige Frage wie ich die Datei IRMP in mein Atmel Studio 
6.2 eingebunden bekomme?

Bitte seit gnädig und sachlich!

Gruß Micha

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Michael K. schrieb:
> So, gestern war der Postbote da und hat neue Tiny85 gebracht. Nun noch
> einmal die vorsichtige Frage wie ich die Datei IRMP in mein Atmel Studio
> 6.2 eingebunden bekomme?

Ich habe zwar kein Atmel Studio 6.2, aber das sollte man mit der Info

    https://www.mikrocontroller.net/articles/IRMP#Source-Code

im Artikel hinbekommen.

Also:

  - neues Projekt für Tiny85 anlegen

  - Eine leere Datei main.c dem Projekt hinzufügen, falls noch nicht
    geschehen

  - Datei imrp.c dem Projekt hinzufügen

  - Includes
      irmpprotocols.h
      irmpsystem.h
      irmp.h
      irmpconfig.h
    zum Projekt hinzufügen.

Dann main.c mit Leben füllen, z.B. den Beispiel-Code von irmp-main-avr.c 
ins main.c kopieren.

Als nächstes irmpconfig.h anpassen und den Pin eintragen, den Du 
verwenden willst.

An der Stelle:
1
        if (irmp_get_data (&irmp_data))
2
        {
3
            ;                                                               // got an IR message, do something
4
        }

in main.c ist dann Dein Einsatz gefragt.

: Bearbeitet durch Moderator
von gerd (Gast)


Lesenswert?

> Da steht wirklich alles?!?

> Wo kann ich Lektion 12 nachlesen? Dann zeige ich Dir gern, was Du
> alles vergessen hast ;-)

Bitte schön:

http://www.gsc-elektronic.net/mikroelektronik/12_IR-Rx-Tx/12_IR-Rx-Tx.html#schalter. 
Hier geht es nun zu einem selbstprogrammierenden ATtiny13, der 
Fernsteuercodes lernt und damit drei Ausgänge schaltet. Das Ganze 
braucht etwa 50% des Flashspeichers eines Tiny13.

Natürlich alles in Assembler.

> Ich kann -ehrlich gesagt- dieses dumme Gelaber von den ach so
> effizienten Assemblerprogrammen langsam nicht mehr hören/lesen!

Kann es denn sein, dass es einfach so ist?

mfg
gerd

von Michael K. (micha_k)


Lesenswert?

Hallo Gerd,
ich bin begeistert!!!
Trotz, dass ich vom Verständnis deines Quellcodes noch weit entfernt 
bin, habe ich ihn durch mein Atmelstudio auf einen Tiny13  gedrückt.
Und siehe da es schaltet!!! – freu!!!

Ich habe einige Fragen:

-  Mein Taster funktioniert nicht so wie ich das verstanden habe. Ist 
die Fernbedienung eingelernt, so bringt ein Tasten nicht den Effekt, 
dass der kleine wieder in den Lernmodus geht.

-  Die eingelernten Codes gehen beim Reset (Spannungsausfall) verloren. 
Das ist richtig da der Speicher nur flüchtig ist, oder?

-  Wie kann ich die Codes der FB dauerhaft abspeichern, damit sie auch 
nach einem Stromausfall funktionieren? (Ich habe im Code ganz unten 
gesehen, dass es sowas wie default gibt??? – Ist das so etwas?

Wenn ich diese Hürden doch gemeistert bekomme, kann ich mein kleines 
Projekt zum Abschluss bringen und meine Tochter freut sich über die 
schaltbare Wandlampe;-)

Herzlichen Dank für deine Mühe. Es ist wirklich toll wenn das sich noch 
jemand für andere Leute Probleme interessiert. In der Regel ist das so 
wie bei deinem 15-jährigen (genau so erlebe ich es in allen Foren)
Gruß Micha

von Marc V. (Firma: Vescomp) (logarithmus)


Lesenswert?

gerd schrieb:
> Natürlich alles in Assembler.

 So natürlich ist das auch wieder nicht.
 Normallerweise schreibt man sich zeitkritische Routinen in Assembler,
 bindet das Ganze als library ein und das wars dann.


>
>> Ich kann -ehrlich gesagt- dieses dumme Gelaber von den ach so
>> effizienten Assemblerprogrammen langsam nicht mehr hören/lesen!
>
> Kann es denn sein, dass es einfach so ist?

 Nein.
 Assemblerroutinen sind effizient, Assemblerprogramme dagegen nicht.
 Sieht man bei deinem Programm - anstatt mit Routinen zu arbeiten,
 wird das meistens in Blocks abgearbeitet - unübersichtlich, schwer
 zu pflegen und zu ändern. Ein Kommentar vor dem Aufruf irgendeiner
 Routine hilft sehr - ein Kommentar vor einem Block mit 123 Zeilen
 dagegen wenig.
 Beim Assembler sollte Programm:Kommentare 60:40 sein, damit man nach
 ein oder zwei Wochen überhaupt noch weiss worum es geht, warum etwas
 so und nicht anders gemacht worden ist.
 In Assembler geht nur ein Befehl nach dem anderen, jede beliebige
 Hochsprache hat mehrere dutzend Assemblerbefehle in einem einzigen
 Befehl.
 Plus Optimierung.
 Plus Error warning.
 Plus...


 P.S.
 Auch sollte ein .endif in der Zeile dort anfangen, wo auch .if
 angefangen hat.

von gerd (Gast)


Lesenswert?

Hallo Micha.

> Ich habe einige Fragen:

> -  Mein Taster funktioniert nicht so wie ich das verstanden habe. Ist
> die Fernbedienung eingelernt, so bringt ein Tasten nicht den Effekt,
> dass der kleine wieder in den Lernmodus geht.

Die Taste wird nur beim Reset einmal abgefragt. Den musst Du vor und 
während dem Hochfahren der Betriebsspannung drücken. Hinterher ginge 
auch, dann muss da aber noch ein PCINT drauf programmiert werden, der 
die Lernmodusflagge setzt und die Speichercodes löscht.

> -  Die eingelernten Codes gehen beim Reset (Spannungsausfall) verloren.
> Das ist richtig da der Speicher nur flüchtig ist, oder?

Nein, die sollten erhalten werden, da sie nach dem Programmieren im 
EEPROM abgelegt (nur wenn alle sechs Tasten programmiert sind) und beim 
Prozessorstart von dort herausgelesen werden. Bei mir hat das 
einwandfrei funktioniert, bei Dir nicht?

> -  Wie kann ich die Codes der FB dauerhaft abspeichern, damit sie auch
> nach einem Stromausfall funktionieren? (Ich habe im Code ganz unten
> gesehen, dass es sowas wie default gibt??? – Ist das so etwas?

Die Tabelle unten ist ein beispielhaftes EEPROM-Segment. Das kriegt man 
nach dem Assemblieren als eep-Datei und kann damit das EEPROM 
programmieren. Braucht man aber eigentlich gar nicht, weil es nach dem 
Lernvorgang sowieso schon automatisch im EEPROM landet.

Man kann nach dem Beenden des Lernmodus auch einfach das EEPROM mit den 
Programmiertools auslesen und diese Datei wieder in das EEPROM 
reinschreiben.

> Wenn ich diese Hürden doch gemeistert bekomme, kann ich mein kleines
> Projekt zum Abschluss bringen und meine Tochter freut sich über die
> schaltbare Wandlampe;-)

Na dann weiß ich jetzt endlich wozu es gut war ...

@Marc:

> Assemblerroutinen sind effizient, Assemblerprogramme dagegen nicht.

Das ist jetzt aber die reine graue Theorie, oder? Ich habe dem Micha 
sein Problem in Assembler gelöst. Was hätte ich da irgendwie anders 
machen sollen, um diesen eigenartigen Effizienzbegriff zu erfüllen?

Klingt irgendwie nach "Was nicht sein kann darf auch nicht".

>> Natürlich alles in Assembler.

> So natürlich ist das auch wieder nicht.
> Normallerweise schreibt man sich zeitkritische Routinen in Assembler,
> bindet das Ganze als library ein und das wars dann.

Klingt jetzt arg nach Lehrbuch und auswendig gelernt. Bei einer 
Fernbedienung ist so ziemlich alles irgendwie zeitkritisch, außer sie 
sendet gerade mal rein gar nichts. Also was nun genau wäre nach Deinem 
Geschmack anders und besser zu lösen gewesen? Und warum soll ich nicht 
alles gleich in Assembler machen? Und wofür genau und mit welchem Sinn 
zwischen Assembler und irgendetwas anderem hin- und herswitchen? Nur 
damit die Theorie im Lehrbuch wieder stimmt?

> Sieht man bei deinem Programm - anstatt mit Routinen zu arbeiten,
> wird das meistens in Blocks abgearbeitet - unübersichtlich, schwer
> zu pflegen und zu ändern.

Was ist denn wohl der Unterschied zwischen Routinen und Blocks, außer 
die reine Theorie? Die Routinen, nach denen Du rufst, gibt es weder in 
irgendeiner Bibliothek noch werden sie im Programm irgendwie mehrfach 
gebraucht. Sie sind exakt auf das zugeschnitten, was an dieser Stelle 
passieren und gemacht werden muss. Es gibt keinen vernünftigen Grund, 
irgendetwas als "Routine" zu verpacken, außer man ist hirnlos darauf 
getrimmt immer nur in dieser Weise genau so und nicht anders zu denken. 
Entweder der Code tut das was er soll oder er tut das nicht. Da gibt es 
auch nix zu pflegen oder zu ändern. Das ist die funktionierende Maschine 
für genau diesen Zweck. Und für nix anderes.

> In Assembler geht nur ein Befehl nach dem anderen, jede beliebige
> Hochsprache hat mehrere dutzend Assemblerbefehle in einem einzigen
> Befehl.

Jau, das ist jetzt aber eines der allerschwächsten Argumente. Wozu soll 
das gut sein? Wenn die Maschine jetzt gerade im Lernmodus ist, und wenn 
die Interruptroutine meldet, dass die Fernbedienung für x ms lang Ruhe 
gegeben hat und dass die letzten 16 gesammelten Bits zur Abholung 
bereitstehen, was ist dann zu tun? In der Liste im SRAM nachschlagen, ob 
der Wert in dieser Liste schon mal vorhanden ist. Und wie macht der 
famose Hochsprachenprogrammierer das eleganter als jeweils zwei Bytes 
nacheinander auf Gleichheit zu prüfen? Das macht jetzt aber einen 
Riesenunterschied aus, weil der Assembler nur 8-Bit-Vergleiche, die 
Hochsprache aber auch 16-Bit-Vergleiche kann (die sie dann beim 
Assemblieren doch wieder in zwei 8-Bit-Vergleiche zerlegt)!

Die Frage ist doch nicht, ob eine Zeile Code mehrere Prozessorschritte 
auslöst. Die Frage ist doch, ob die mehreren Prozessorschritte genau das 
tun, was jetzt genau an dieser Stelle nötig ist.

>  Plus Optimierung.

Die gehört bei Assembler schon zum Grundkonzept! Weil in Assembler jeder 
einzelne Schritt so zu machen ist und nicht anders gemacht werden kann. 
Da gibt es nichts mehr zu optimieren, das ist schon per se optimal. Was 
Du daran siehst, dass der ganze Code mühelos in den kleinen 
Flashspeicher vom Tiny13 passt. Optimierung ist nur bei Hochsprachen 
sinnvoll (und nötig), weil die eine Riesenmenge unnützen Codes mit 
einschleppen, den sie dann mühsam wieder rausoptimieren müssen. Ich 
werde einen Teufel tun,irgendwelche unnützen Programmzeilen da rein zu 
friemeln, die dann da irgendwie wieder raus zu optimieren sind.

> Plus Error warning.

Was soll denn das sein? Was für Error sind denn genau hier gemeint? Bei 
Denkfehlern funktioniert die Maschine einfach nicht und macht nicht, zu 
was man sie programmiert hat. Merkt man ganz schnell. Manchmal auch 
nicht, das sind dann die ganz gemeinen Denkfehler, weil die nur alle 
Nase lang zum Versagen führen. Und die kriegt man auch nicht vom 
Compiler gemeldet. Alle anderen Fehler sind gaga und Kleinkram.

> Plus...

Tja was denn noch alles?


mfg
gerd

von Michael K. (micha_k)


Angehängte Dateien:

Lesenswert?

Moin Gerd,
ich habe meine Schaltung (aufgebaut auf einem Breadboard) noch einmal 
überprüft. Sie ist so wie du auf deiner Seite beschrieben hast. Der 
einzige Unterschied ist der IR-Sensor. Ich habe einen TSOP4836, dies 
spielt aber keine Rolle.
Den Tiny13 habe ich auch schon ausgetauscht, um einen Defekt 
auszuschließen.
Die Fuses habe ich auch wie beschrieben gesetzt und schon ein Pull-Up 
auf den Taster-Eingang gesetzt, um eventuell Irgendwas auszuschließen.
Sobald ich die Spannung kurz wegnehme, startet der Kleine im Lernmodus. 
Dies ist ebenso der Fall wenn ich mit dem Progger auf den Tiny zugreife. 
Es reicht schon um nur die Signatur auszulesen.
Ich habe auch nach dem Einlernen mal das EEPROM ausgelesen; hier finde 
ich aber keine Codes! – Möglicherweise werden sie schon beim Zugriff 
gelöscht?!

Im Anhang das EEPROM nach dem Einlernen.

Gruß Micha

von gerd (Gast)


Lesenswert?

Hallo Micha.

Eigenartigerweise stehen Deine gemessenen Daten im EEPROM ab Adresse 
30hex, der vordere Teil des EEPROMs ist jungfräulich. Die Software legt 
die Codes aber eigentlich ab Adresse 00hex ab, nicht ab 30hex. Da er 
beim Lesen aus dem EEPROM auf ein FF als Null/Eins-Schwellenwert stößt, 
startet er das Lernen neu.

Was verursacht, dass das Ablegen der Codes bei Dir erst ab 30h beginnt? 
Ich habe mir noch mal den Quellcode angeschaut, da wird beim Schreiben 
zu Beginn die Adresse eindeutig gesetzt:
;
; Schreibe Codes ins EEPROM
SchreibeCodes:
  ldi ZH,0 ; Zeiger auf EEPROM-Adresse
  ldi ZL,0
  ldi XH,High(sCodes) ; Zeiger auf SRAM
  ldi XL,Low(sCodes)
  ldi rmp,sCodesEnde-sCodes
  mov rCtr,rmp
[...]

Da scheint bei Dir beim Assemblieren einiges schief gelaufen zu sein. 
Solange die Codes im EEPROM hinten erscheinen, wird das nichts.

Das EEPROM wird nur beim Löschen des Flash-Speichers gelöscht. Wenn Du 
die EESAVE-Fuse gesetzt hast, wird beim Flash-Programmieren der Inhalt 
des EEPROMs nicht mehr mitgelöscht. Auslesen des EEPROMs verändert 
seinen Inhalt definitiv nicht. Bei Dir ist ja tatsächlich korrekter 
Inhalt geschrieben worden, nur halt an die falsche Adresse. Wie Du das 
hingekriegt hast, ist mir ein echtes Rätsel.

mfg
gerd

von Marc V. (Firma: Vescomp) (logarithmus)


Lesenswert?

gerd schrieb:
>> So natürlich ist das auch wieder nicht.
>> Normallerweise schreibt man sich zeitkritische Routinen in Assembler,
>> bindet das Ganze als library ein und das wars dann.
>
> Klingt jetzt arg nach Lehrbuch und auswendig gelernt. Bei einer
> Fernbedienung ist so ziemlich alles irgendwie zeitkritisch, außer sie
> sendet gerade mal rein gar nichts. Also was nun genau wäre nach Deinem
> Geschmack anders und besser zu lösen gewesen? Und warum soll ich nicht
> alles gleich in Assembler machen? Und wofür genau und mit welchem Sinn
> zwischen Assembler und irgendetwas anderem hin- und herswitchen? Nur
> damit die Theorie im Lehrbuch wieder stimmt?

 Du merkst es spätestens dann, wenn die Programmgröße 2KB übersteigt.
 Mal angenommen, du bist so gut in Assembler, dass jeder Compiler für
 irgendeine Hochsprache für deine 4KB Code 10KB erzeugt - OK ?
 Deine 4KB Code in Assembler brauchen über den Daumen gepeilt mindestens
 3000 Zeilen ( ohne Kommentare, defines usw. ).
 In C/Basic/Pascal brauchen 10KB Code 300-500 Zeilen.
 Was ist deiner Meinung nach leichter zu ändern/pflegen ?

 Ich habe hier ein KnightRider mit T4313 und IR-Fernsteuerung -
 funktioniert wunderbar, alle sind begeistert, aber irgendetwas jetzt
 daran zu ändern - nein, Danke.
 Die IR- und WS2812-Ausgabe Routinen selbst hab ich natürlich als
 Library-funktionen behalten.


gerd schrieb:
> Was ist denn wohl der Unterschied zwischen Routinen und Blocks, außer
> die reine Theorie? Die Routinen, nach denen Du rufst, gibt es weder in

 Routinen kann man mehrfach aufrufen.
 Mit Routinen kann man sich z.B. eine StateMachine viel übersichtlicher
 aufbauen als mit Blocks. Auch andere Sachen lassen sich viel einfacher
 mit Routinen machen als mit Blocks, z.B. if-else, switch usw.
 'branch' Befehle gehen bei AVR nur +/- 63, da ist mit einem langen
 Block schlecht etwas zu machen, aber es passen 30 Routinen dazwischen.
 Dabei ist es ziemlich unerheblich ob sich diese Blocks wiederholen
 oder nicht.
 Wenn ich bei Statemachine 200-300 Zeilen rauf- oder runterscrollen
 muss um die vorherige/nachste Bedingung zu finden, habe ich, wenn ich
 es endlich gefunden habe, meistens schon vergessen was ich eigentlich
 kontrollieren wollte.

von Michael K. (micha_k)


Lesenswert?

Hallo Gerd,
ich habe vielseitige Talente ;-) ,das umschreiben eines Assembler-codes 
gehört (noch) definitiv nicht dazu.
Ich benutze das Atmel-Studio 6.2
Ich habe deinen Code in ein neues Projekt kopiert, dann mit F7 (Build 
Solution) die Datei erzeugt. Danach habe ich mit "Device Programming" 
mein Tool und den Tiny13 ausgewählt, bei Memory die *.hex-Datei 
ausgewählt.
Jetzt nur noch "Program" gedrückt und das Schicksal nahm seinen Lauf.
Gibt es möglicherweise Defaulteinstellungen die noch nicht richtig 
sitzen? Ich habe gelesen, dass du auch das Studio benutzt.
Wie kann ich noch das Beschreiben des Speichers beeinflussen?

Danke für deine Mühe
Gruß Micha

von Michael K. (micha_k)


Lesenswert?

Hallo Marc,
es ist ganz toll das du die Unterschiede aufzeigen kannst. Unbestritten 
kann auch jeder das am besten was er gelernt hat bzw. was er „lebt“.
Die Sache ist nur die, deine Ausführungen passen überhaupt nicht zur 
Überschrift und helfen auch überhaupt nicht bei meinem Problem.
Das einzige was mich interessieren würde ist ein in C geschriebener 
Code, mit den gleichen Funktionalitäten. Solltest du das hinbekommen, so 
können wir gerne beide Quellcodes nebeneinanderlegen und jeder darf 
darüber philosophieren was besser ist.
Zur Zeit juckt mich nicht welche Farbe das Auto hat, es ist nur wichtig 
das es fährt!!
Danke für deine Anteilnahme.
Gruß Micha

von Pastor Braune (Gast)


Lesenswert?

Nimm Bascom ,die Demo Version ist ausreichend .

von gerd (Gast)


Lesenswert?

Hallo Micha,

ich habe noch keine vernünftige Idee, wie die Adressverschiebung bei Dir 
zustande kommt. Es gibt so gar keinen Weg, wie man so einen verrückten 
Effekt hinkriegt.

Poste doch mal das Assembler-Listing, wäre meine allerletzte Hoffnung 
(musst Du im Studio in den Assembler-Einstellungen einstellen, wird 
nicht per default erzeugt). Die Datei hat die Endung .lst und liegt im 
gleichen Verzeichnis wie der Quellcode.

mfg
gerd

von gerd (Gast)


Angehängte Dateien:

Lesenswert?

Ich habe mal eine ausschließlich für den ATtiny13 geschriebene Version 
gemacht und alle Schalter aus dem Quelltext entfernt. Falls die Ursache 
dort liegen sollte ...

mfg
gerd

von Marc V. (Firma: Vescomp) (logarithmus)


Lesenswert?

Michael K. schrieb:
> Das einzige was mich interessieren würde ist ein in C geschriebener
> Code, mit den gleichen Funktionalitäten. Solltest du das hinbekommen,

 Ich habe es schon hinbekommen.

> so können wir gerne beide Quellcodes nebeneinanderlegen und jeder darf
> darüber philosophieren was besser ist.

 Und du machst...  was ?
 Nöö, so geht das nicht.

von gerd (Gast)


Lesenswert?

Hallo.

Noch ein Nachtrag zu der geposteten Version: sie enthält noch einen Bug. 
Die korrigierte Version bitte bei Bedarf neu von der Webseite 
http://www.gsc-elektronic.net/mikroelektronik/index.html herunterladen.

@Frank M.

Na, was habe ich alles vergessen?

@Marc V.

Und, auf welcher Webseite können wir denn nun Deinen Code bestaunen? Wer 
den Mund so voll nimmt, sollte dann auch mal Butter bei die Fische tun, 
oder?

mfg
gerd

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

gerd schrieb:
> Noch ein Nachtrag zu der geposteten Version: sie enthält noch einen Bug.
> Die korrigierte Version bitte bei Bedarf neu von der Webseite
> http://www.gsc-elektronic.net/mikroelektronik/index.html herunterladen.
>
> @Frank M.
>
> Na, was habe ich alles vergessen?

Ich habe das Kapitel 12 mal aus obigem Link mal quergelesen. Das 
eigentliche Verfahren, wie Du Puls/Pausen-Zeiten speicherst und 
wiedererkennst, ist leider nicht erklärt. Du hast den Schwerpunkt da 
eher auf die technische Realisierung - d.h. Assemblertechniken - gelegt. 
Das interessiert mich aber als Nicht-mehr-Assembler-Programmierer schon 
lange nicht mehr. Außerdem tue ich mir diese Rattenschwänze von 
Assembler-Listings nicht an, um das Programm zu verstehen. Dieses ist 
nämlich alles andere als selbsterklärend. Zum Verständnis bräuchte ich 
mehr Zeit, als diesen Beitrag zu schreiben. Und der wird so schon 
ziemlich lang...

Genug der Vorrede: Ich kann Dir nur zu den Themen etwas sagen, was ich 
rauslesen konnte.

Protokoll mit speziellen Repetition Frames

(z.B. NEC mit Anteil von über 70% im Haushalt)

Bei längeren Tastendrücken werden sogenannte Repetition-Frames gesandt, 
die mit dem ursprünglichen Kommando, was nur einmal geschickt wurde, 
nichts mehr zu tun haben. Diese kannst Du nicht interpretieren und dem 
ursprünglichen Kommando zuordnen. D.h. bei längeren Tastendrücken 
scheitert das Programm, denn alle Tasten senden ein- und denselben 
Repetition-Frame. Du kannst daher das simple längere Drücken einer 
Lautstärketaste nicht mehr verarbeiten können. Das macht man aber 
alltäglich - zum Beispiel beim Fernsehen. Da hat niemand Lust, gefühlte 
50 mal auf eine Taste zu hämmern, um die Lautstärke hoch- oder 
runterzudrehen.

Protokolle mit Toggle-Bit:

Hier wechselt ein- und dieselbe Taste bei jedem erneuten Tastendruck das 
Toggle-Bit, um lange und kurze Tastendrücke zu unterscheiden. Dein 
Programm versteht diese als zwei verschiedene Tasten und versteht auch 
die Semantik, nämlich ob es sich um einen langen oder zwei kurze 
Tastendrücke handelt, nicht. Die prominentesten Vertreter von 
Protokollen mit Toggle-Bit sind RECS80, Thomson, RC5 und RC6, z.B. 
letzeres bei der XBOX.

Protokolle mit Sync-Bits:

Vertreter sind hier das SAMSUNG-, NEC16- und Daewoo-Protokoll. Hier 
werden mitten im Frame Pausen von bis zu 4500µsec eingelegt, um den 
Empfänger neu zu synchronisieren. Soweit ich Deinen Text verstanden 
habe, steigst Du aber bereits nach Pausenzeiten von 2048µsec aus und 
erkennst vorzeitig ein Ende - gerade dann, wenns am interessantesten 
wird. Du erhältst also den einen Frame als zwei Frames - also 2 
Tastendrücke. Nehme ich dann eine zweite Fernbedienung desselben 
Herstellers, aber mit einer abweichenden Adressierung (z.B. eine für CD 
und ein für DVD-Player, Fernseher etc), kann Dein Programm die 
Kommando-Daten beider FBs nicht mehr auseinanderhalten, denn der 
Unterschied steckt in den Daten vor dem Sync-Bit. Da ist dann die 
Geräteadresse gespeichert. Nach dem Sync-Bit folgt dann das eigentliche 
Kommando. Eindeutig kann man das nur zuordnen, wenn man beide Teile in 
der Gesamtheit sieht.

SIRCS-Protokoll von Sony:

Dieses schickt für einen Tastendruck zunächst zwei Frames, bei längeren 
Tastendrücken dann weitere identische Frames bis zum Loslassen. Wieviele 
Tastendrücke erkennt daraus Dein Programm? Wie kannst Du mit einer Taste 
eine Lampe abwechselnd sicher ein- und wieder ausschalten?

Protokolle mit automatischer Frame-Wiederholung - aber gekippten Bits

Diese kommen als zwei bis drei komplett verschiedene Frames bei Deinem 
Programm an, obwohl ich nur eine Taste nur ganz kurz gedrückt habe.

Protokolle mit CRCs

Fast alle Protokolle verwenden redundante Daten wie Wiederholung von 
Bits (teilweise invertiert im darauffolgenden Frame oder in demselben 
Frame) oder Bits, in denen eine CRC gebildet wird. Da Du die Protokolle 
nicht inhaltlich auswertest, sondern nur Längen misst, kannst Du keine 
Fehlübertragungen erkennen.

Das wars fürs erste. Obige Punkte wirst Du mit der simplen Längenmessung 
auch nicht in den Griff bekommen, weil das Programm das eigentliche 
Protokoll nicht erkennt und deshalb auch nicht "versteht".

Auszug aus Deinem Kapitel:

"Das hier ist so eine Tabelle mit den Tastenzuordnungen der 
TV-Fernsteuerung. Was sich der Entwickler dabei gedacht haben mag, 
erschließt sich dem normalverständigen Bürger nicht so ganz."

Das kann man mit der simplen Methode, die Du anwendest, auch nicht 
verstehen. Bei IRMP ist es anders: Es erkennt das Protokoll und stellt 
sich daher darauf ein. Daher sind CRC-Prüfungen, Toggle-Bits, 
Repetition-Frames, Sync-Bits und andere Besonderheiten auch überhaupt 
kein Problem. Und dann erkennt man auch plötzlich das System! Dann haben 
die Tasten 1 bis 9 auch die Codes 1 bis 9 und nicht irgendeinen 
Bit-Salat - egal wie kompliziert der Frame sonst noch aussieht.

Okay, Deine Methode reicht selbstverständlich, um einen oder auch zwei 
Ein-/Aus-Taster zu realisieren. Aber alles weitere, z.B. eine 
Helligkeitsregelung, wo Du nicht 50mal drücken willst, um einen Dimmer 
hochzuregeln, sondern einfach eine Taste länger runterdrückst, wirst Du 
zum Beispiel bei den gebräuchlichsten Protokollen schon scheitern.

Daher kann ich nur sagen: Man nehme für die richtige Anwendung auch das 
richtige Programm. Ich würde aber immer eher den Mercedes nehmen. Dann 
muss ich micht nicht in verschiedene Programme, Bibliotheken 
einarbeiten. Ob ich einen Tiny13 benutze oder wegen IRMP auf zumindest 
einen Tiny45 wechseln muss, ist mir schnurzpiepe. Die paar Cent, die ich 
bei einem Tiny45 mehr bezahle, habe ich nach 5 Minuten Arbeit mit IRMP 
mehrfach wieder raus.

Sobald Du mir erklärst, wie Du die Puls-/Pausen-Längen speicherst und 
mit wieviel verschiedenen(!) Längen innerhalb eines Frames zurechtkommst 
und welche Toleranzen du eingebaut hast, damit du auch nach Wechsel der 
FB durch eine baugleiche noch die Signale erkennst, die Du mit der alten 
FB angelernt hast, werde ich Dir bestimmt noch weitere Punkte nennen 
können, die Du "vergessen" hast.

Eins würde mich noch interessieren. Wieviele Bytes brauchst Du zum 
Speichern und damit Wiedererkennen eines einzelnen Frames? IRMP 
braucht dafür konstant 5 Bytes - egal wieviele Bits der Frame hat (ich 
kenne welche mit bis zu 80 Bits/Frame) oder aus wievielen Frames sich 
ein Tastendruck zusammensetzt. Damit lassen sich in einem ATTiny85 mit 
512 Bytes EEPROM 100 verschiedene IR-Frames speichern - bei 
Optimierungen sogar noch mehr.

Als letztes: Assembler... schön und gut, kann jeder machen, wie er will. 
Aber mir ist Plattformunabhängigkeit lieber. IRMP läuft auf ATmegas, 
ATtinys, ATXMegas, PICs, STM8, STM32, LPCxxx und sogar ESP8266. Mit 
Assembler steckt man da in einer ziemlichen Sackgasse.

: Bearbeitet durch Moderator
von gerd (Gast)


Lesenswert?

Hallo.
@Frank M

Das geht mir als eher praktisch orientiertem Bastler etwas zu seltene 
Abwege.

Das Ziel des gesamten Kurses ist, die Hardware von Prozessoren 
vorzustellen und, für Anfänger, an Beispielen nutzbar zu machen. Das 
Kapitel 12 in dem Kurs sollte zeigen, wie man die Signaldauer und 
Signalzusammensetzung mit einem AVR messen und auf einer LCD anzeigen 
kann. Als praktische Aufgabenstellung, bei der diese Zeitmessung eine 
Rolle spielt, habe ich das Thema Infrarot gewählt. Ich habe Infrarot 
gewählt, weil das in der Lebenswelt aller Programmieranfänger vorkommt. 
Ich hätte auch jedes andere Timing-Problem wählen können, es gibt nur 
nicht sehr viele andere praktische Beispiele. Mein Ziel war nicht, die 
letzte ultimative, vollständige, exakte Untersuchtung aller 
IR-Fernbedienungen dieser Welt vorzunehmen, sondern zu zeigen, wie man 
mit einem Timer und einem externen Interrupt Zeitmessungen recht genau 
und auf einer LCD dargestellte aufschlussreiche Messungen veranstalten 
kann.

Auf meinem Wohnzimmertisch liegen sechs verschiedene IR-Fernbedienungen. 
Bei zweien ist die Batterie leer, weil die auch seit Jahren gar nicht 
mehr verwendet werden. Meine Software habe ich mit den restlichen vier 
getestet, drei davon habe ich dokumentiert. Mir reicht es völlig aus, 
wenn ich mit meiner Software rauskriege, wie diese vier arbeiten. Ende, 
aus, fertig. Der User kann sich mit den 5% anders gebauten 
Fernbedienungen herumschlagen, wenn es denn nötig sein sollte. Dann muss 
er die Software entsprechend seiner Bedingungen modifizieren, erweitern, 
etc. Das ist dann aber nicht mehr mein Ding. Die eierlegende 
IR-Wollmichsau war einfach nicht mein Ziel.

Nachdem ich die IR-Analyse-Software im Kapitel 12 schon fast fertig 
hatte, kam die Frage von Michael nach dem Tiny13 als IR-Empfänger hier 
im Forum auf. Und mir war klar, dass seine Aufgabe sehr einfach und 
komfortabel lösbar war, wenn man nur die letzten 16 Bits eines 
Fernsteuersignals identifiziert und zum Schalten benutzt. Wie 
geschrieben: mir reicht es, wenn die Software mit meinen drei 
Fernbedienungen auf dem Wohnzimmertisch einwandfrei funktioniert. Die 
Software funktioniert nicht mit Fernbedienungen, bei denen sich die 
letzten 16 Bits gar nicht unterscheiden. Das ist ein klarer Nachteil, 
betrifft aber allenfalls 5% aller praktischen Fälle. Bei mir zu Hause 
gibt es keine solche. Dann nimmt man eben einfach eine andere, jeder 
Mensch hat genug andere mit leeren Batterien herumliegen. Für das 
Schalten von drei Relais braucht man auch keine 170 Kombinationen zu 
speichern, nur sechs Stück 16-Bit-Zahlen (drei für das Einschalten, drei 
für das Ausschalten, deshalb braucht die Software auch keine großartigen 
Unterscheidungen machen, Tasten hat jede ordinäre Fernbedienung genug).

Der Vorteil der von mir geschriebenen Lösung ist, dass kein separates 
Ausmessen des Signals, Protokolle, etc., nötig ist, weil das in der 
Lernphase vom Prozessor (zugegeben rudimentär) erledigt wird. Soll eine 
andere Fernbedienung verwendet werden, wird der Lernmodus eben einfach 
erneut durchlaufen. Und fertig isses.

>Daher kann ich nur sagen: Man nehme für die richtige Anwendung auch das
richtige Programm. Ich würde aber immer eher den Mercedes nehmen.

Der erste Satz widerspricht dem zweiten diametral. Ich brauche keinen 
Mercedes, wenn ich nur ein Relais schalten möchte. Warum sollte ich für 
diese einfache Aufgabe auch noch gleich das Diummerproblem lösen, das 
ich bei Relaisschaltungen gar nicht habe.

Die Software braucht einen 8-Bit-Zähler und einen externen Interrupt für 
den IR-Empfänger (INT0, INT1 oder PCINT), das hat so (fast) jeder AVR 
seit 2004. Da gibt es nicht so arg viel umzubauen, wenn jemand einen 
anderen Typ verwenden möchte. Einfacher Umbau der Reset- und 
Intvektortabelle und Ändern der Clock-Konstante, das war es, der Rest 
bleibt gleich. Auch das ist für mich kein Argument, die Aufgabenstellung 
nicht in Assembler zu programmieren.

Es geht mir auch nicht darum, was für einen Typ von AVR man dafür 
braucht. Die nötige Software, um das gestellte Problem (minimalistisch 
und auf den Regelfall optimiert) zu lösen, ist klitzeklein. Wenn man 
natürlich ein ganz anderes Problem lösen möchte (die eierlegende 
IR-Wollmichsau), dann passt das natürlich nicht in einen Tiny13. Aber 
das war hier auch gar nicht die Aufgabe.

mfg
gerd

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.