Ich hab mir schon einiges überlegt, aber finde irgendwie nicht so recht
eine Lösung, wie ich ein Byte das im SRAM des Attiny steht (Inhalt
entweder 0 oder 1)an ein bestimmte Stelle im Register schreiben kann.
Hat da wer eine Idee
Viele Grüße
Michael
Btw. Ich verwende Assembler
Solche Problemstellungen gehören zu den häufig Auftretenden.
Ihr Lösung besteht in der Anwendung von sogenannten "Bitmanipulationen".
Grob gesagt, ist der Ablauf etwa wie folgt:
1. Isolierung des Wertes eines einzelnen Bits. Dabei ist der Transport
von zunächst allen Bits in ein Register, auf das man Befehle zur
Bitmanipulation anwenden kann, wiederum eine triviale Aufgabe.
Wesentlich ist die Anwendung einer "Bitmaske" in der Verknüpfung des
veränderlichen Bits und mit einer "Und"-Operation um den Wert des Bytes
nur noch von dem fraglichen einzelnen Bit abhängen zu lassen.
2. Das Verschieben des veränderlichen Bits von einer Position im Byte zu
einer anderen. Dazu werden Bit-Schiebeoperationen verwendet. Ihre
Anwendung, - das ist aber hier nicht wesentlich -, verändert auch den
Wert des Bytes, wenn es etwa als Integer-Zahl interpretiert wird.
Einzelheiten findest Du in dem Artikel:
https://www.mikrocontroller.net/articles/Bitmanipulation hier im Forum.
Da es sich um ein Basisthema handelt, finden sich im Internet dazu
reichlich alternative Darstellungen.
Ich möchte möglichst wenig aufwand haben dehalb wollte ich versuchen mit
einem Zähler in einem Register (r16) die einzelenen Bits durchzuegehn?
Kann den Code oben jetzt grade nicht ausprobieren
Viele Grüße
Michael
Warum probierst du es nicht einfach aus und liest die Fehlermeldung?
Alternativ lies die Beschreibung des AVR Befehlssatzes.
> Ich möchte möglichst wenig aufwand haben dehalb wollte ich versuchen mit> einem Zähler in einem Register (r16) die einzelenen Bits durchzuegehn?
Warum willst du jetzt alle Bits durchgehen? Erst hieß es noch, du
wolltest nur ein einzelnes Bit eines Bytes aus dem RAM testen. Wenn du
beim Schreiben des Programms schon weißt, welches Bit du testen mußt,
dann kannst du die Bitmaske als Konstante direkt in das Programm
schreiben.
Wenn du hingegen alle Bits testen willst, dann kannst du entweder mit
einer Maske auf Bit 0 anfangen (auch wieder eine Konstante) und dann die
Maske mit Schiebebefehlen durch dein Register schieben. Eleganter ist es
jedoch, das zu testende Byte selber durch das Carry-Flag zu schieben.
Dann kriegst du die Bits der Reihe nach in das Flag und kannst mit
Branch- oder Skip-Befehlen die gewünschten Aktionen abhängig vom Wert
des Bits ausführen.
Michael schrieb:
> ldi r17, (1 << r16)
Nein. Das geht nicht so.
Der Text eines Assemblerprogrammes unterliegt, wie der eines
C-Programmes einer bestimmten "Deutung"; er hat eine Bedeutung, eine
genau fest gelegte Interpretation. Diese ist in dem Assembler-Manual des
Assemblers beschrieben. Im AVR-Studio (ich vermute mal einen AVR), unter
"Hilfe" beschrieben.
Dein Fehler hier, besteht darin, dass Du einen konstanten Ausdruck
hinschreiben willst, aber darin ein Register verwendest. Konstante
Ausdrücke sind aber das, was der Assembler laut seiner Beschreibung und
das wiederum, laut der Beschreibung des Befehles "LDI" (Load Immediate)
als rechten Operanden erwartet. "Immediate" ist in diesem Kontext ein
anderes Wort für "Konstante".
Nun ist es aber so, dass konstante Ausdrücke zu dem Zeitpunkt berechnet
werden, in dem der Assembler (das Programm, dass "Assembler" heisst und
ein in der Assembler-Sprache geschriebenes Programm interpretiert) aus
diesem Programm eine von dem Prozessor verstandene Darstellung macht;
das nennt man assemblieren. Daraus folgt, dass Du in konstanten
Ausdrücken nichts verwenden darfst, was nicht schon zu diesem Zeitpunkt
bekannt ist. Insbesondere nicht den Inhalt von Registern, denn deren
Inhalt, wird erst zu der Zeit bestimmt, zu der das Programm vom
Prozessor ausgeführt wird.
(Das ist in gewisser Weise eine vereinfachte, formal nicht korrekte
Darstellung, aber sie stimmt im wesentlichen).
Daraus folgt, dass Du als "Immediate", als "Konstante" zwar etwa
(1 << 7)
genau wie:
(5 * 4) + 8
oder ähnliches schreiben kannst, aber nicht das von Dir gezeigte.
Faustregel kann etwa folgendes sein: Alles was Du selbst (auf dem Papier
oder im Kopf) ausrechnen kannst, so das eine bestimmte Zahl herauskommt,
ohne das Du den tatsächlichen Inhalt eines Registers oder einer
Speicherstelle kennen musst, darfst Du dort hinschreiben.
Also damit das auch jeder versteht wie ich es meine.
Ich hab im SRAM 8 Byte gespeichert die entweder den Wert 0 oder 1 haben.
Über den Z-Pointer greif ich auf das erste Byte im Ram zu.
Jetzt will ich das ganze in ein Register zusammen schreiben. (Geht ja
weil die Bytes immer nur den Wert 0 oder 1 haben)
0 Byte aus dem Ram an die 7te Stelle im Register
1 Byte aus dem Ram an die 6te Stelle im Register
.
.
.
7 Byte aus dem Ram an die 0te Stelle im Register
Ich hoffe ich bin verständlich genug
Wenn also irgendwer n Plan hat wäre ich demjenigen sehr verbunden mir
das mitzuteilen.
Michael
Dann schau Dir mal die Rotierbefehle über Carry an, die sind genau dafür
gemacht.
Am einfachsten wäre es aber, die Bits gleich beim Schreiben in den SRAM
zu packen.
Michael schrieb:> Ich hab im SRAM 8 Byte gespeichert die entweder den Wert 0 oder 1 haben.
Woher kommen diese 8 Bytes?
Ist das jeweils eine binäre 1 und eine binäre 0?
Oder eine ASCII-'1' und eine ASCII '0'.
Lothar M. schrieb:> Michael schrieb:>> Ich hab im SRAM 8 Byte gespeichert die entweder den Wert 0 oder 1 haben.> Woher kommen diese 8 Bytes?> Ist das jeweils eine binäre 1 und eine binäre 0?> Oder eine ASCII-'1' und eine ASCII '0'.
Ich glaube eher, Michael kennt nicht den Unterschied zwischen "Bit" und
"Byte". Seine ganze Umschreibung deutet darauf hin, daß er "Bit" meint".
Michael schrieb:> Jetzt will ich das ganze in ein Register zusammen schreiben. (Geht ja> weil die Bytes immer nur den Wert 0 oder 1 haben)>> 0 Byte aus dem Ram an die 7te Stelle im Register> 1 Byte aus dem Ram an die 6te Stelle im Register> .> Wenn also irgendwer n Plan hat wäre ich demjenigen sehr verbunden mir> das mitzuteilen.
Ja.
Axel S. schrieb:> Helfersyndrom mal wieder.
Das ist doch der tiefere Sinn eines Forums, oder ?
> Dem TE wäre langfristig besser gedient, wenn> er das selber gelernt hätte.
Wie schon die alten Griechen behaupteten:
Ein Codeschnipsel sagt mehr als Tausend Worte