Hallo Freunde ! Wieder mal komme ich als Anfänger nicht weiter. Ich möchte gerne einen Port"D" bitweise auslesen und die pegel an den Port"B" als Ausgang schreiben, in einer Schleife und bekomme es einfach nicht hin weder in Bascom noch Assembler... Ich habe versucht : ..... ... config PortD = input config PortB = output dim P as bit do P = PortD.0 PortB.0 =P .... .... P= PortD.7 PortB.7 = P loop end ----------------------------------------- in ASSR: ------------ .include "m8515def.inc" ; Definitionsdatei für den Prozessortyp ldi r16, 0xFF ; lade Arbeitsregister r16 mit der Konstanten 0xFF out DDRB, r16 ; Inhalt von r16 ins IO-Register DDRB ausgeben ldi r16, 0b11111111 ; 0b11111111 in r16 laden out PORTB, r16 ; r16 ins IO-Register PORTB ausgeben abfrage: ldi r17, PORTD out PORTB, r17 rjmp abfrage ; Sprung zur Marke "abfrage" -> Endlosschleife ----------------------------------------- es kann ja sein das meine Gedankengänge grundlegende Fehler haben, wie gesagt bin ja noch im Lernen.. Am Port D ist jeder Pin eingangsmässig low-aktiv, d.h. bei Auslösung einer Schaltaktion wird der Pegel von Hi nach Low gezogen. Dann soll der entsprechende Pin im B-Port ebenfalls nach Low gehen. Damit will ich erst mal die Funktion erreichen, später kommen noch programmierte Bedingungen dazu wie sich das mit Eingan -Low- und Ausgang -Hi- verhält, es soll ein Kontrollbaustein werden, der 8 Eingänge überwacht und diese dann Programmbedingt auf den Port B signalisiert.. Als Chip soll der 8515 erst mal in Betracht kommen, aber es geht mir ja erst mal darum die Funktion der Ports so zu erreichen wie oben erwähnt. Gruss und Dank Gerhard
Du willst nicht den Port lesen, sondern den Pin Auszug aus Bascom reading the PORT, will read the latch, that is the value you have written to the PORT. This is not the same as reading the logical values on the pins! When you want to know the logical state of the attached hardware, you MUST use the PIN register.
Auch Dir kann ich nur sagen. Schreibe hinter jeden Befehl was du dir da gedacht hast. So wirst du Merken das Du gar nicht soviel dabei denkst.
1 | ldi r16, 0xFF ; lade Arbeitsregister r16 mit der Konstanten 0xFF |
2 | out DDRB, r16 ; Inhalt von r16 ins IO-Register DDRB ausgeben |
3 | |
4 | ldi r16, 0b11111111 ; 0b11111111 in r16 laden |
5 | out PORTB, r16 ; r16 ins IO-Register PORTB ausgeben |
Nicht beschreiben was der Befehl macht sondern warum Du ihn machst. So wird Dir z.B. auffallen das du r16 nicht mit 0b11111111 laden musst da du ihn ja vorab mit 0xFF geladen hast und er sich seitdem nicht geändert hat. Nein das ist nicht dein Fehler aber Zeigt auf das Du nicht mitdenkst bei dem was Du machst. Also fein hinter jedem Befehl schreiben warum du das machst was du damit bezwecken möchtest. Und schwups die Wups wird Dir geholfen :-)
1 | ldi r16, 0xFF ; lade Arbeitsregister r16 mit der Konstanten 0xFF |
2 | ldi r16, 0b11111111 ; 0b11111111 in r16 laden |
Das sind überhaupt die allerblödsten Kommentare, den es je geben kann. Denn morgen nehme ich diese Zeile, kopiere sie und passe sie an:
1 | ldi r16, 0xFE ; lade Arbeitsregister r16 mit der Konstanten 0xFF |
Und vergesse dabei den Kommentar... Vivil schrieb: > Auch Dir kann ich nur sagen. Schreibe hinter jeden Befehl was du dir da > gedacht hast. > So wird Dir z.B. auffallen... Das Dahinterschreiben hilft da überhaupt nichts, man muß Sehen und Erkennen was man da tut, und da hilft nur Übung...
Für ein Anfänger hilft es sehr viel weil er merkt das er da nicht denkt. Seine Gedanken zu Selektieren, Sortieren ist das a und o.
Vivil schrieb: > Für ein Anfänger hilft es sehr viel weil er merkt das er da nicht denkt. Nein, denn die Pattern-Erkennung bei einem Anfänger funktioniert noch nicht so gut, dass er automatisch erkennt FF == 11111111
Wenn er hinter seinen befehl schreibt warum er das macht was er sich dabei denkt wird ihm auffallen das es zwei die gleichen gedankengänge sind. lass sie doch mal überlegen. und da der E da schon nicht mit anfängt mitzuarbeiten warum sollten ihm dan user aus dem forum alles vorkauen?
Vivil schrieb: > Für ein Anfänger hilft es sehr viel weil er merkt das er da nicht denkt. > Seine Gedanken zu Selektieren, Sortieren ist das a und o. Das ist im Prinzip ja auch nicht falsch. Nur in dem Kommentar sollte nicht die Erklärung des Befehls stehen. Sondern zusatzliche Informationen, die nicht direkt aus dem lesen des Quelltextes ersichtlich sind. z.B. so: ///////////////////////////////////////////////////////// // Timer 2 konfigurieren, wird für das multiplexen der LEDS benötigt // alle 0,1 ms wird ein CompareMatch-Interrupt ausgeloest TCCR2 = (1<<CS01); // Prescaler CPU/8 TCCR2 |= (1<<WGM01); // CTC-Modus einstellen OCR2 = 149; // OCR2-Register laden für 0,1 ms TIMSK |= (1<<OCIE2); // CompareMatch-Interrupt aktivieren ist zwar "C" aber fürs Prinzip: Programm in einezelne kleinere Blöcke aufteilen. Am Anfang eines Blockes schreiben was er bewirken soll. Die Zeile selber ist eigentlich selbst erklärend. Da ich mir aber die Register und deren Bezeichnungen nicht alle Merken kann, habe ich mir hier ebenfalls dahinter geschrieben was diese Zeile bewirken soll. Das ersparte mir schon so manchmal einen Blick ins Datenblatt. just my 2 cent Dietmar
Hi >in einer Schleife und bekomme es einfach nicht hin weder in >Bascom noch Assembler... >abfrage: ldi r17, PORTD Damit lädst du r17 mit der Adresse ($12) von PORTD. Den Zustand der Pins bekommst du mit 'in r17,PIND'. MfG Spess
Dietmar schrieb: > Das ist im Prinzip ja auch nicht falsch. Nur in dem Kommentar sollte > > nicht die Erklärung des Befehls stehen. Sondern zusatzliche > > Informationen, die nicht direkt aus dem lesen des Quelltextes > > ersichtlich sind. Deswegen tippte ich: Vivil schrieb: > Nicht beschreiben was der Befehl macht sondern warum Du ihn machst.
Wenn er aber hätte, könnte man auch die Diskrepanz zwischen Befehl und Kommentar erkennen. --> Hilfe wäre einfacher
Meine Rede und eventuell würde er die Wiedersprüche auch selber erkennen.
Hallo Freunde, Habt vielen Dank für alle Erläuterungen und Hinweise, ich habe mich auch vielleicht falsch noch ausgedrückt , weiss immer noch nicht so recht wie ich es beschreiben soll, eben noch Anfänger der lernt. Ich mache zur Zeit die Schaltung fertig und stelle sie dann auf meinen Webspace, da kann man vieleicht besser erkennen was ich da meine.. Vorerst allen recht herzlichen Dank, Ihr seid wie immer, mir eine grosse Hilfe !! Gruss Gerhard
Vivil schrieb: > ldi r16, 0xFF ; lade Arbeitsregister r16 mit der Konstanten 0xFF > out DDRB, r16 ; Inhalt von r16 ins IO-Register DDRB ausgeben > > ldi r16, 0b11111111 ; 0b11111111 in r16 laden > out PORTB, r16 ; r16 ins IO-Register PORTB ausgeben > > Nicht beschreiben was der Befehl macht sondern warum Du ihn machst. DU selbst hast in Deinem Beispiel unübertreffbar genau das exakte Gegenteil von dem gemacht, was Du (völlig korrekterweise!) als falsch beschreibst: Du dokumentierst dort lediglich, WAS Du programmierst (oder treffender: was die CPU ausführt), OHNE auch nur anzudeuten, WARUM. Sonst hättest Du bspw. in den Kommentaren darauf hingewiesen, daß Du Einser-Bit nicht "nur einfach nur so" in das DDRB Register schreibst, sondern weil die CPU den jeweils dazugehörenden Port-Pin als Ausgang verwenden soll. Oder noch besser - um Dich noch näher dem praktischen Betrieb des Systems anzunäheren - mußt Du im Kommentar erklären, warum das eine oder andere Port überhaupt gegenüber dem Post-Reset-Status des Controllers als Ausgang eingerichtet werden muß. Also erklären, welche Systemanforderung jeder einzelne Programmschritt wie erfüllt. Erst Beschreibungen dieser Qualität sind kompatibel mit Deiner eigenen Forderung. Das was Du im Beispiel oben rechts hinter die Semikoli "gedichtet" hast, ist dagegen nichts weiter als eine sinngemäße 1:1-Wiedergabe aus der Befehlssatzbeschreibung des Controllers - und entsprechend redundant. MfG
Wenn Du schon Erbsen zählst so zähle richtig. Das war ein Auszug aus seinem Code wie du oben nachlesen kannst. Also auch Du erst Denken, richtig lesen und dann motzen. Also hau mich hier nicht so an, schon klar das in diesem Forum dieses gerne gemacht wird. Aber Obacht wenn schon dan richtig grins
Hallo Leute, bitte streitet Euch doch nicht, ich denke jeder kann mal was falsch machen oder ein Anderer sieht es anders als man selbst. So ich habe mal die Schaltung ,noch mehr Entwurf und nicht komplett vollständig, ins Web geladen : http://werkstatt.oderlachs.de/avr/pictures/signal_controll.gif Diese Schaltung ist noch mit dem AM8535, drum nicht wundern warum ich oben vom 8515 schrieb, den habe ich zum experimentieren, vor allem zum Lernen auf den STK 500... Also wird eine der Tasten in der Schaltung betätigt soll der entsprechende Ausgang vom µC den dazugehörigen Optokoppler schalten und das ziemlich schnell, ein Durchlauf der Portabfrage(Eingang) sollte max 1 Sec. dauern und dann ausgegeben werden. Vielleicht ist es jetzt besser zu verstehen, was ich machen möchte, will Euch ja auch nicht übermässig mit meinen Anfängerproblemen belasten. Später soll dann die Eingabe/Ausgabe etwas präzisiert werden, also Länge der Ausgabezeit usw. Mir geht es aber jetzt nur darum zu wissen, wie ich das vom Eingang auf den Ausgang bekomme. Die Tasten gegen Masse und Optokoppler gegen +5V habe ich darum gewählt, um es auf dem STk nachvollziehen zu können. Ich dank Euch schon mal im Voraus, für Hilfe und Ratschläge Gerhard Edit 1: Morgen oder übermorgen werde ich mal schreiben wie ich mit dem Programm überhaupt was weiter gekommen bin, habe nicht immer so Zeit dafür.
Also zumindestens habe ich den Schritt geschafft mit den Eingangspegeln die Ausgangspegel zu schalten, allerdings mit anderen Port. ich habe bei RN-Wissen.de dazu folgenes in einem Assembler-Tutorial gefunden Hier das Zitat: Beispiel An PORTC haben wir (mit Vorwiderständen) ein paar LEDs angeschlossen. Und die sollen einfach nur zeigen, welche 0-er und 1-er am PORTB anliegen. ; Eigene Initialisierungen LDI R24, 0 ; der wert "0" ins allgemeine Register R24 OUT DDRB, R24 ; das kommt ins Controll-register f. PortB ; dadurch sind diese PINs als INPUT festgelegt LDI R24, 255 ; der wert "255" = FF ins allgemeine Register R24 OUT DDRC, R24 ; das kommt ins Controll-register f. PortC ; dadurch ist das Port auf OUTPUT gestellt ; Eigene Befehle (in der Hauptschleife) IN R24, PINB ; die Bits vom PortB ins allgemeine Register R24 OUT PORTC, r24 ; schreiben wir nach PortC ; wo ein 1-er ist, leuchtet nun die LED Wenn wir diese Befehle in das Programm-Schema oben einfügen, haben wir also das erste Assemblerprogramm schon geschrieben. ......... Zitatende Nur eines begreife ich dabei nicht wie es zu der "Hauptschleife" kommt, ich habe nur folgenden Code daraus gemacht, d.h. die erste Zeile hinzugefügt : .include "m8515def.inc" LDI R24, 0 ; der wert "0" ins allgemeine Register R24 OUT DDRB, R24 ; das kommt ins Controll-register f. PortB ; dadurch sind diese PINs als INPUT festgelegt LDI R24, 255 ; der wert "255" = FF ins allgemeine Register R24 OUT DDRC, R24 ; das kommt ins Controll-register f. PortC ; dadurch ist das Port auf OUTPUT gestellt ; Eigene Befehle (in der Hauptschleife) IN R24, PINB ; die Bits vom PortB ins allgemeine Register R24 OUT PORTC, r24 ; schreiben wir nach PortC und schon geht es...
Hi >Nur eines begreife ich dabei nicht wie es zu der "Hauptschleife" kommt, >ich habe nur folgenden Code daraus gemacht, d.h. die erste Zeile >hinzugefügt : Meinst du die: .include "m8515def.inc" ? Wenn ja: Dadurch weiss der Assembler erst, welche Adresse Portx, ... haben. Die sind bei unterschiedlichen AVRs durchaus verschieden. > LDI R24, 255 benutze bitte LDI R24,0b11111111 oder LDI R24,$FF (0xFF). Dezimalzahlen sind an der Stell irreführend bzw. total unverständlich. MfG Spess
Hallo Spess ! Ja ich verstehe das schon mit der Dezimalzahlangabe, das mit binärem Wert sieht mann auch gleich das Bitmuster, ist mir auch klar. Ich habe auch das nur so org. aus dem Tuto übernommen, das mit der m8515def.inc ist mir auch verständlich , dort werden dem Compiler die Adressen für die Worte wie PortA,DDRB usw.. übergeben. Man müsste wohl sonst den Code in kopfzermarternden Adressangaben schreiben, aus C64er Zeit mir noch gut bekannt... Was ich nicht verstehe ist hier : IN R24, PINB ; die Bits vom PortB ins allgemeine Register R24 OUT PORTC, r24 ; schreiben wir nach PortC Wie kommt der Progcounter nach der Abarbeitung der out ... Anweisung wieder zurück in die In... Anweisung, um PortB neu abzufragen, ob sich da was geändert hat ?? Aber je mehr Probleme ich habe um so mehr muss ich lernen und das ist gut !! Euch Allen, auch natürlich besten Dank für alle Hilfe !!! Gerhard
Hi >Was ich nicht verstehe ist hier : >IN R24, PINB ; die Bits vom PortB ins allgemeine Register R24 >OUT PORTC, r24 ; schreiben wir nach PortC >Wie kommt der Progcounter nach der Abarbeitung der out ... Anweisung >wieder zurück in die In... Anweisung, um PortB neu abzufragen, ob sich >da was geändert hat ?? Eigentlich gar nicht. Wenn allerdings der Rest des Programmspeichers durch Löschen mit $FF gefüllt ist, wird er wohl bis zum Speicherende durchlaufen und dann von vorn wieder anfangen. Um eine Programmschleife zu erhalten, musst du folgendes machen: label: IN R24, PINB ; die Bits vom PortB ins allgemeine Register R24 OUT PORTC, r24 ; schreiben wir nach PortC rjmp label ; Sprung nach label Wobei 'label' ein Bezeichner deiner Wahl ist. MfG Spess
Wenn Du mit PIN statt PORT drangehst, müßte es funktionieren: config PortD = input config PortB = output dim P as bit do P = PIND.0 'Hier ist die Stelle PortB.0 =P .... .... P= PIND.7 PortB.7 = P loop end Print "MfG Paul"
Danke Spess, habe selbiges eben gemacht "rjmp schleife"...geht Danke Paul, ja das mit dem PinD o.ä. ja das weiss ich noch nicht alles so genau aus dem Kopf, meine ersten IO-Schritte dieser Art, die ich mache... Danke für den Hinweis. Ich freue mich ja so ,daß ich hier nachfragen darf, wenn ich mich auch manchmal böd anstelle, aber so im "Selbststudium" erkennt man seine eigenen Fehler schlecht selber.. ;) Ich habe vor 15 Jahre mal Assembler 8085 gemacht, davor noch mit dem C64er. da ist ein wenig hängen geblieben, aber sind die Mnemonik und die Bezeichner doch oft anders, gerade in ASSR bei verschiedenen Chips... Gruss Gerhard
Hi >Ich habe vor 15 Jahre mal Assembler 8085 gemacht, davor noch mit dem >C64er. da ist ein wenig hängen geblieben, aber sind die Mnemonik und die >Bezeichner doch oft anders, gerade in ASSR bei verschiedenen Chips... Ich habe in den 80-ern mit dem U880(Z80) angefangen. Mit dem Hintergrundwissen fand ich den Einstieg bei den AVRs nicht sehr kompliziert. Sie dir mal in Ruhe das Instruction Set an: http://www.atmel.com/dyn/resources/prod_documents/doc0856.pdf MfG Spess
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.