Forum: Mikrocontroller und Digitale Elektronik Hilfe für Beginner Code_Mikrocontroller


von A.B.C (Gast)


Lesenswert?

Hallo,

ich habe ein ATtiny 26 Mikrocontroller und ein LCD, ich möchte diesen 
LCD entsprechen programmieren. Ich habe mir die Seite AVR-Tutorial:LCD 
(http://www.mikrocontroller.net/articles/AVR-Tutorial:_LCD) durch 
gelesen und bin bei der Warteschleife hängen geblieben. Da ich ein 
absoluter Beginner bin und bisher gar keine Erfahrungen auf diesem 
Gebiet habe, verstehe ich nicht was da genau passiert und warum. Kann 
mir jemand diesen Code schrittweise erklären??? ich weiß nicht warum 
beispielsweise $21 oder $C9 genommen wurde? Da ich Attiny26 (8Mhz) 
verwende, müsste ich noch eine Warteschleife dazufügen.
1
 Längere Pause für manche Befehle
2
delay5ms:                               ; 5ms Pause (bei 4 MHz)
3
           ldi  temp1, $21
4
WGLOOP0:   ldi  temp2, $C9
5
WGLOOP1:   dec  temp2
6
           brne WGLOOP1
7
           dec  temp1
8
           brne WGLOOP0
9
           ret                          ; wieder zurück

von Peter (Gast)


Lesenswert?

A.B.C schrieb:
> Da ich ein
> absoluter Beginner bin und bisher gar keine Erfahrungen auf diesem
> Gebiet habe, verstehe ich nicht was da genau passiert und warum.

Da wäre es sinnvoll, wenn Du nicht mit Assembler sondern mit C 
programmierst.

Versuchs mal bei Google: AVR LCD.

von A.B.C (Gast)


Lesenswert?

@Peter: Danke für deine schnelle Antwort. Da ich mich (leider) seit 
einer Woche mit Assembler beschäftige, möchte ich auch mit Assembler 
fortsetzen.

von Ulrich F. (Gast)


Lesenswert?

Peter schrieb:
> Da wäre es sinnvoll, wenn Du nicht mit Assembler sondern mit C
> programmierst.

Einspruch!
Es ist vollkommen scheiXegal, womit man anfängt.
Grundlagen lernen, das ist der Punkt!

Wenn man nicht weiß was die Befehle tun, dann schaut man sie sich im 
Handbuch an. Die Zeiten stehen dabei. Takte zählen also kein Problem.

PS:
Bin selber OOP Fan.

von A.B.C (Gast)


Lesenswert?

@Ulrich: In welchem Handbuch?

Ich habe überall nach einer Erklärung gesucht, jedoch habe ich nichts 
gefunden.

von Blinky (Gast)


Lesenswert?

ldi  temp1, $21    Äußerer Zähler auf 33 setzen
WGLOOP0:   ldi  temp2, $C9    Innerner Zähler auf 201 setzen
WGLOOP1:   dec  temp2         Innerer Zähler um eins verringern
           brne WGLOOP1       Solange bis der innere Zähler auf 0 ist
           dec  temp1         Äußerer Zähler um eins verringern
           brne WGLOOP0       Zurück zur Inneren Schleife bis äußserer
                              Zähler auf 0 ist
           ret                Ende der Warteschleife

Das ganze sind 2 Schleifen die bei 4MHz Taktfrequenz oft genug 
durchlaufen werden (jeder Befehl braucht n Takte zur Abarbeitung) das 
eine 5ms Verzögerung entsteht.
Bei 8MHz müssten also aus der $21 einfach eine $42 vgemacht werden um 
die selbe Verzögerung zu erhalten ($C9 * 2 = $192, passt also nicht mehr 
in ein 8 Bit Register).

von Thomas E. (picalic)


Lesenswert?

A.B.C schrieb:
> @Ulrich: In welchem Handbuch?

im Datenblatt des Prozessors gibt es eine Liste der Befehle, und im 
online-Handbuch zum AVR Assembler (-> Startseite im Atmel-Studio) sind 
die Befehle auch einzeln beschrieben. Sonst gibt auch Google unter "AVR 
Assembler" jede Menge Lesestoff...

von Ulrich F. (Gast)


Lesenswert?

A.B.C schrieb:
> @Ulrich: In welchem Handbuch?
>
> Ich habe überall nach einer Erklärung gesucht, jedoch habe ich nichts
> gefunden.

Hier:
http://www.atmel.com/images/atmel-0856-avr-instruction-set-manual.pdf

Und etwas mundgerechter:
http://avr-asm-download.de/beginner_de.pdf

von A.B.C (Gast)


Lesenswert?

Danke mir ist jetzt klar wie die Befehle funktionieren :dec -> 
dekrementieren also um eins verringern usw...

Ich muss nur noch verstehen, nach welchen Kriterien ich die Durchläufe 
($21, $c9) wähle bzw wie ich diese definiere.....

von npn (Gast)


Lesenswert?

A.B.C schrieb:
> Ich muss nur noch verstehen, nach welchen Kriterien ich die Durchläufe
> ($21, $c9) wähle bzw wie ich diese definiere.....

Einfach so, daß die Ausführungszeit pro Befehl mal die Durchläufe deine 
gewünschte Zeit ergibt. Mehr Geheimnis gibts da nicht :-)
Sicherlich wird es mehrere Möglichkeiten / Kombinationen geben, mit 
denen du auf die gewünschte Zeit kommst. Aber welche du davon nimmst, 
ist dir überlassen.

von P. M. (mikro23)


Lesenswert?

A.B.C schrieb:
> Ich habe mir die Seite AVR-Tutorial:LCD [...]
> durchgelesen und bin bei der Warteschleife hängen geblieben.

und ich bin grade in 'ner Lach-Schleife hängengeblieben. ;)

Danke dafür

von oldmax (Gast)


Lesenswert?

Hi
Vielleicht hilft es, wenn du dir das Datenblatt deines Controllers 
ansiehst. Du bekommst es bei ATMEL oder manchmal führt die Suche über 
Google weiter. Im Teil "Instruction Set Summary" findest du alle Befehle 
und die zur Ausführung erforderlichen Takte. Angenommen, dein Controller 
läuft mit 8 MHz dann ist 1/8000000 die Zeit, die ein Takt braucht, also 
0,000000125 s oder 125 ns. Ein Befehl wie DEC Register benötigt einen 
Takt, die Auswertung auf 0 incl. Sprung 2 Takte. Setzt du das Register 
vor der Schleife auf 100 dann benötigt die Schleife 300 * 125 ns. oder 
eben 37,5 µs. Willst du 5 ms Erreichen, musst du nur richtig rechnen. 
Aber auch alle Befehle berücksichtigen. Dazu brauchst du eben die Info 
aus dem Datenblatt. Der Rest ist eben Mathe.
Gruß oldmax

von A.B.C (Gast)


Angehängte Dateien:

Lesenswert?

Vielen Dank für die Antwort..

Ich bin auch dabei die Berechnung zu verstehen..
ich habe mir zur Hilfe das Flussdiagramm gezeichnet, um die Berechnung 
aus AVR nachzuvollziehen...

von A.B.C (Gast)


Lesenswert?

A.B.C schrieb:

> Ich bin auch dabei die Berechnung zu verstehen..

 ---Das ist die äußere Schleife---
ldi  temp1, $21  ;1 Takt

--- Das ist die innere Schlefe---
ldi  temp2, $C9   ;1 Takt

---Hier wird die innere Schleife abgearbeitet----
dec  temp2         ;1 Takt
brne WGLOOP1       ;Sprung 2 Takte, sonst 1 Takt


---Hier wird äußere Schleife abgearbeitet----
 dec  temp1         ;1 Takt
 brne WGLOOP0       ;Sprung zwei Takte, sonst 1 Takt


Aus AVR : Was geht hier vor? Die innere Schleife benötigt wieder 3 Takte 
pro Durchlauf. Bei $C9 = 201 Durchläufen werden also 201 * 3 = 603 Takte 
verbraucht. In der äußeren Schleife werden pro Durchlauf also 603 + 1 + 
2 = 606 Takte verbraucht und einmal 605 Takte (weil der brne nicht 
genommen wird). Da die äußere Schleife $21 = 33 mal wiederholt wird, 
werden 32 * 606 + 605 = 19997 Takte verbraucht.---????


Innere Schleife benötigt doch 4 Takte (ldi, dec , brne 
(Schleifendurchlaug))?

Dann werden für den äußeren Durchlauf zu den Takte der inneren Schleife 
(603 Takte) drei (1+2) Takte dazu addiert. Um welchen Takten handelt es 
sich bei den dreien?


:-=

von Finn S. (scooter757)


Lesenswert?

Peter M. schrieb:
> A.B.C schrieb:
>> Ich habe mir die Seite AVR-Tutorial:LCD [...]
>> durchgelesen und bin bei der Warteschleife hängen geblieben.
>
> und ich bin grade in 'ner Lach-Schleife hängengeblieben. ;)
>
> Danke dafür

Super :D

von c-hater (Gast)


Lesenswert?

Peter schrieb:

> Da wäre es sinnvoll, wenn Du nicht mit Assembler sondern mit C
> programmierst.

Krasser Unsinn.


Mod
Den üblichen C Bashing entsorgt.

c-hater: eine Warnung. Achte auf deine Wortwahl. Die Mods sind sich 
einig, dass wir deine fäkale Ausdrucksweise nicht mehr länger tolerieren 
werden.

von Matthias S. (Firma: matzetronics) (mschoeldgen)


Lesenswert?

Die ultimative Befehlsliste mit Taktzyklen, beeinflussten Flags usw. ist 
AVR 0856 - 8-Bit AVR Instruction Set:
http://www.atmel.com/Images/Atmel-0856-AVR-Instruction-Set-Manual.pdf
680 lohnenswerte kByte.

Man beachte, das nicht alle AVR auch alle Befehle bereitstellen, auch 
sind z.B. die RAMP Register nicht in allen AVR enthalten.

von Graf Zahl (Gast)


Lesenswert?

Wieso sind das bei mir 1.476.850 bytes?

von PittyJ (Gast)


Lesenswert?

Der Kernighan/Ritchie "The C Programming Language" hat 274 Seiten.
Mehr braucht man nicht.
Damit habe ich bisher alle Prozessoren, und das waren mehr als 1 
Dutzend, bezwungen.

von Matthias S. (Firma: matzetronics) (mschoeldgen)


Lesenswert?

Graf Zahl schrieb:
> Wieso sind das bei mir 1.476.850 bytes?

Oh, ist inzwischen gewachsen - sind wohl auch alle neuen MC mit drin.

von Bastler (Gast)


Lesenswert?

Es ist natürlich auch so, daß man C nur schreiben kann, wenn man ASM 
versteht, oder was? Also ich kann beides und Rate mal, was ich vorziehe.
Für Anfänger haben schnelle Erfolge alá Arduino den Vorteil, daß die 
Hardware funktioniert und ein C-Compiler "etwas mehr" 
Plausibilitätsprüfungen macht, als ein Assembler. Den stört es nämlich 
nicht, wenn man Daten überschreibt, die man eigentlich konstant halten 
wollte, uvm.
Also nicht 332+274, sondern nur ein paar Tutorials zum ersten 
Erfolgserlebnis und wenn dann noch mehr wissen will, dann schaut man 
irgendwann die .lss-Datei an. Lernen braucht nämlich Erfolge, auch wenn 
sich das bei unseren Pädagogen noch nicht rumgesprochen hat.

von Paul B. (paul_baumann)


Lesenswert?

Bastler schrieb:
> ....und ein C-Compiler "etwas mehr"
> Plausibilitätsprüfungen macht, als ein Assembler. Den stört es nämlich
> nicht, wenn man Daten überschreibt, die man eigentlich konstant halten
> wollte, uvm.

Bei Assembler ist man aber komplett für das verantwortlich, was man tut.
Bei Fehlern kann man sich leichter erklären, was passiert sein muß, weil 
der Quelltext gut durchschaubar ist, In C kann bzw. muß man allen 
möglichen Kram inkludieren, den andere Leute geschrieben haben. Das 
kann richtig sein, muß aber nicht.
Da ist mir ein Assembler Quelltext, den ich erst dann in den Rechner 
wämmere, wenn ich ihn von Hand auf dem Papier durchsgespielt habe 10x 
lieber.
(Na, sagen wir 16x, das läßt sich besser handhaben.)

;-)
MfG Paul

von Bastler (Gast)


Lesenswert?

Ja Paul, so hab ich das 1981 mit einem 8048 auch gemacht. Weil ich keine 
besseren Werkzeuge hatte! 34 Jahre sind das jetzt, das war also 
IT-Steinzeit!

von Frank (Gast)


Lesenswert?

Paul B. schrieb:
> In C kann

Das ist richtig. In ASM kann man auch fremden code verwenden.

Paul B. schrieb:
> muß man allen möglichen Kram inkludieren

Das ist falsch.
Wobei gerade das Arduino Zeug zum Einstieg nicht so verkehrt ist.

Ich persönlich habe mit ASM angefangen und hab dann  nach C gewechselt. 
Das ist nun 18 Jahre her.
Beruflich wird mittlerweile alles nur noch in C++ programmiert, ja auch 
uC!
Alleine wegen der Portierbarkeit. Ob Atmel, PIC, TI oder Infineon... 
alles das selbe.

von C > ASM (Gast)


Lesenswert?

Frank schrieb:
> C++
> PIC
Klingt interessant, welchen Kompiler nimmst du dafür?

von Bastler (Gast)


Lesenswert?

PIC gibt's auch in den Geschmacksrichtungen PDP11 (PIC24) oder MIPS 
(PIC32). Beides gestandene Rechner und nicht nur mikroprogrammierbare 
Logikbausteine.

von Frank (Gast)


Lesenswert?

C > ASM schrieb:
> Frank schrieb:
> C++ PIC
>
> Klingt interessant, welchen Kompiler nimmst du dafür?

Stimmt, da hast du mich erwischt. Das einzige Projekt wo wir einen PIC 
einsetzen ist noch Objektive C.

Taugt der MPLAB XC32++ nichts?

von oldmax (Gast)


Lesenswert?

Hi
Leute, was soll die Diskussion um Assembler und C? Gerade diese Aufgabe 
ist doch so simpel und ideal, einmal dei benötigte Zeit zur 
Befehlsausführung zu berechnen. Da muss man nicht einen von C erstellten 
Assemblercode nachvollziehen, sondern kann gleich mit der Berechnung 
loslegen. Jede Programmiersprache hat seine Daseinsberechtigung und es 
ist doch jedem selbst überlassen, was er benutzt. Der sinnlose Quatsch 
über Umfang von Lehrmaterial bringt doch nix. Wer sich mit C beschäftigt 
wird wissen, wieviel Material durchzuarbeiten ist, um brauchbare 
Ergebnisse zu bekommen. Gleiches trifft auf alle anderen Sprachen 
einschließlich Assembler zu. Die einzige Hilfe, die hier geboten werden 
kann ist die Erklärung, warum ein Code bei der Bearbeitung Zeit benötigt 
und wieviel. im gegensatz zu menschlichem Denken ist hier von einer 
festen Größe aus zu gehen. Ein Befehl sind eins. zwei oder  4 Takte und 
wenn alle Befehle erfasst und berechnet sind. läßt sich eine Zykluszeit 
mit den normalen Grundrechenarten bestimmen. Mag ja sin, dasa da 
komfortable C-Compiler unterstützen, mir fehlt da die Erfahrung, aber 
diese missionarischen Ansätze in den Diskussionen um Programmiersprachen 
sind echt überflüssig.
Gruß oldmax

von Karl H. (kbuchegg)


Lesenswert?

c-hater: eine Warnung. Achte auf deine Wortwahl. Die Mods sind sich 
einig, dass wir deine fäkale Ausdrucksweise nicht mehr länger tolerieren 
werden.

Aus der Zone zu kommen ist keine Entschuldigung für unzivilisiertes 
Verhalten. Ich werde in Zukunft deine Postings nicht mehr moderieren 
sondern einfach löschen sollte sich deine allgemeine Ausdrucksweise 
nicht bessern. Wir lassen hier ohnehin so einiges durchgehen, was ich 
bei mir zu Hause nicht tolerieren würde. Aber irgendwann ist jedes Fass 
voll.

gez.
Karl Heinz

von Karl H. (kbuchegg)


Lesenswert?

A.B.C schrieb:

> Aus AVR : Was geht hier vor? Die innere Schleife benötigt wieder 3 Takte
> pro Durchlauf. Bei $C9 = 201 Durchläufen werden also 201 * 3 = 603 Takte
> verbraucht. In der äußeren Schleife werden pro Durchlauf also 603 + 1 +
> 2 = 606 Takte verbraucht und einmal 605 Takte (weil der brne nicht
> genommen wird). Da die äußere Schleife $21 = 33 mal wiederholt wird,
> werden 32 * 606 + 605 = 19997 Takte verbraucht.---????
>
>
> Innere Schleife benötigt doch 4 Takte (ldi, dec , brne
> (Schleifendurchlaug))?

der ldi wird (im Tutorial) nicht zur inneren Schleife dazugerechnet, 
weil diese Instruktion in der inneren Schleife ja nicht dauern 
wiederholt wird. Dieser 1 Takt ist in der Berechnung der äusseren 
Schleife drinnen. (Sollte zumindest, noch kann ich den in der Berechnung 
nicht entdecken. Ich denke da steckt tatsächlich ein Fehler)

Wenn du ausrechnen willst, wieviele Takte eine Schleife benötigt, dann 
darfst du logischerweise auch nur die Befehle zählen, die wiederholt 
abgearbeitet werden.
1
delay5ms:                               ; 5ms Pause (bei 4 MHz)
2
           ldi  temp1, $21
3
WGLOOP0:   ldi  temp2, $C9    ; ------- aeussere Schleife -------+
4
WGLOOP1:   dec  temp2             ; ---- innere Schleife ---+    |
5
           brne WGLOOP1           ; ------------------------+    |
6
           dec  temp1                                            |
7
           brne WGLOOP0       ; ---------------------------------+
8
           ret                          ; wieder zurück

Wenm du wissen willst, wie lange die Fertigung von 1 Million 
Joghurtbecher benötigt, dann rechnest du ja auch nur den Tiefziehvorgang 
mal 1 Million. Die Zeit, die der Maschinenbetreuer benötigt um die Form 
in die Maschine zu spannen wird ja nicht 1 Million mal benötigt sondern 
nur 1 mal.

Fertigst du aber 5 verschiedene Becher jeweils 1 Million mal, dann 
rechnest du die Produktionszeit für 1 Becher mal 5. Die komplette 
Produktionszeit setzt sich aber zusammen aus einmalig der 
Formeinspannzeit und 1 Million Zeiten für das Ziehen der Becher.

von A.B.C (Gast)


Lesenswert?

@Karl Heinz...

Danke Sie (Du) haben (hast) mir sehr geholfen .. Das war die ganze Zeit 
mein Problem...

Danke an allen!

von Karl H. (kbuchegg)


Lesenswert?

Karl H. schrieb:

> Schleife drinnen. (Sollte zumindest, noch kann ich den in der Berechnung
> nicht entdecken. Ich denke da steckt tatsächlich ein Fehler)

Ach klar.
Der 1 Takt ist schon berücksichtigt. Allerdings könnte man das besser 
formulieren.

Der letzte Durchlauf durch die innere Schleife dauert ja 1 Takt weniger, 
weil der brne nicht genommen wird. Genau das ist rechnerisch der 1 Takt, 
der im Gegenzug einmalig für die 'Initialisierung der inneren Schleife' 
durch den ldi drauf geht.

von Karl H. (kbuchegg)


Lesenswert?

A.B.C schrieb:
> @Karl Heinz...
>
> Danke Sie (Du)

Du

von Paul B. (paul_baumann)


Lesenswert?


von Draco (Gast)


Lesenswert?

Karl H. schrieb:
> Aus der Zone zu kommen ist keine Entschuldigung für unzivilisiertes
> Verhalten.

Das zeugt auch nicht gerade von zivilisiertem Verhalten, sorry!

von Karl H. (kbuchegg)


Lesenswert?

Draco schrieb:
> Karl H. schrieb:
>> Aus der Zone zu kommen ist keine Entschuldigung für unzivilisiertes
>> Verhalten.
>
> Das zeugt auch nicht gerade von zivilisiertem Verhalten, sorry!

Du kennst c-hater anscheinend noch nicht lange genug. Das Argument 'Ich 
komme aus der Zone' stammt von ihm.

Abgesehen davon stösst es uns mitlerweile schon sauer auf, dass jedes 3 
Wort 'scheisse' oder 'Drecksding' oder dergleichen ist. Krönung war wohl 
das mitlerweile entsorgte 'Arschloch'. Sorry. wenn das die 
Ausdrucksweise ist, mit der er im Forum zu glänzen gedenkt, dann können 
wir gerne auf ihn verzichten.
Meinungsfreiheit bedeutet nämlich nicht, dass ihm jeder eine Plattform 
zur Verfügung stellen muss.

von A.B.C (Gast)


Lesenswert?

Hi,

den Code aus AVR habe ich verstanden:

Längere Pause für manche Befehle
delay5ms:                               ; 5ms Pause (bei 4 MHz)
           ldi  temp1, $21
WGLOOP0:   ldi  temp2, $C9
WGLOOP1:   dec  temp2
           brne WGLOOP1
           dec  temp1
           brne WGLOOP0
           ret                          ; wieder zurück

Jetzt möchte ich einen ähnlichen Code für 5ms Pause bei 16 MHz 
(Attiny26) schreiben. Ich wollte noch zusätzlich eine dritte Schleife 
einfügen.
16 MHz  entsprechen 16 000000 Takte pro Sekunde.
5ms *16000000= 800000 Takte---> pro schleife werden ca. 3 Take (dec, 
brne) gebraucht--->

Mit dieser Rechnung möchte ich jeweils die Durchläufe ermitteln. Ist 
mein Vorgehensweise richtig ?

von Ulrich F. (Gast)


Lesenswert?

Zu Anfang habe ich gestutzt...
Irgendwo her kannte ich die WGLOOPX Dinger.....

Und dann, dann fiel der Groschen....
1
; ============================= 
2
;   Warteschleifen-Generator 
3
;     800000 Zyklen:
4
; ----------------------------- 
5
; warte 799995 Zyklen:
6
          ldi  R17, $5F
7
WGLOOP0:  ldi  R18, $17
8
WGLOOP1:  ldi  R19, $79
9
WGLOOP2:  dec  R19
10
          brne WGLOOP2
11
          dec  R18
12
          brne WGLOOP1
13
          dec  R17
14
          brne WGLOOP0
15
; ----------------------------- 
16
; warte 3 Zyklen:
17
          ldi  R17, $01
18
WGLOOP3:  dec  R17
19
          brne WGLOOP3
20
; ----------------------------- 
21
; warte 2 Zyklen:
22
          nop
23
          nop
24
; =============================
Quelle: http://www.home.unix-ag.org/tjabo/avr/AVRdelayloop.html

von A.B.C (Gast)


Lesenswert?

Ist es so, dass ich das nicht berechnen brauche?

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.