Atmega48 - Bascom -> SPI gibt daten anders formatiert aus als UART

OP #2893636
Lesenswert?

Hallo Forum, ich bin langsam am verzweifeln.

Vorneweg, ich arbeite mit Bascom und möchte eine 16Bit Variable so über 
SPI ausgeben wie ich Sie schreibe. Also z.B. var = &b1000000000011111

Wenn ich mit Print bin(var) ausgebe, dann bekomme ich auch 
&b1000000000011111 am UART zu sehen. passt.

Wenn ich allerdings mit SPIOUT var ,2 ausgebe dann bekomme ich über SPI 
folgendes raus &b0001111110000000. Also ist das zeite mit dem ersten 
byte vertauscht. Warum wird das so ausgegeben ???

-> Mein Ziel ist es eine Variable, wie oben Binär von links nach rechts 
geschrieben auch so auf meinem SPI zu sehen.


LG Tim

Hier ist mein Code:
1
$crystal = 8000000
2
$regfile = "m48def.dat"
3

4
$hwstack = 40
5
$swstack = 20
6
$framesize = 20
7

8
Config Portd = Output
9

10
Dim Test As Word
11

12
Test = &B1000000000011111
13

14

15
Config Com1 = 19200 , Synchrone = 0 , Parity = None , Stopbits = 1 , Databits = 8 , Clockpol = 0
16
Config Spi = Soft , Din = Pinb.7 , Dout = Portb.1 , Ss = Portb.6 , Clock = Portb.2
17

18
Spiinit
19

20

21
Do
22

23
Waitms 10
24

25
Spiout Testvar , 2
26
Print Bin(Testvar)
27

28
Loop
29
End
#2893668
Lesenswert?

Tim E. schrieb:

> Wenn ich allerdings mit SPIOUT var ,2 ausgebe dann bekomme ich über SPI
> folgendes raus &b0001111110000000. Also ist das zeite mit dem ersten
> byte vertauscht. Warum wird das so ausgegeben ???

Schuss ins Blaue?

Weil BIN deine 16-Bit Variable auch als 16 Bit Variable erkennt und die 
Bitreihenfolge 'richtig' rum macht.

Wohingegen die SPI Ausgabe ganz einfach 2 Bytes, beginnen bei der 
angegebenen Startadresse im SPeicher ausgibt - sprich deine 16 Bit 
einfach nur als 2 hintereinanderliegende Bytes ansieht. Erkennt man auch 
schon daran, dass du bei BIN keine weitere Angabe brauchtest, während du 
der SPI Ausgabe explizit angeben musstest, dass da 2 Bytes liegen. Und 
die beiden Bytes eines 16 Bit Wertes liegen nun mal in dieser 
Reihenfolge im Speicher.
Persönliche Seite #2893670
Lesenswert?

Tim E. schrieb:
> Wenn ich allerdings mit SPIOUT var ,2 ausgebe dann bekomme ich über SPI
> folgendes raus &b0001111110000000. Also ist das zeite mit dem ersten
> byte vertauscht. Warum wird das so ausgegeben ???

Ich vermute, dass die Daten genau in der Reihenfolge übermittelt werden, 
wie sie im Speicher liegen. Der AVR ist eine little endian Maschine. Ein 
16 bit Wert ("word", "int16" o.ä.) liegt also als Highbyte:Lowbyte im 
Speicher (high an niedriger Adresse, low an höherer).
#2893672
Lesenswert?

Tim E. schrieb:
> Warum wird das so ausgegeben ???
Weil das so richtig ist.
Deine Speicherreihenfolge ist Little Endian. D.h. bei Mehrbytegrössen, 
daß das niederwertige Byte auf der niedrigeren Adresse steht und somit 
auch zuerst ausgegeben wird. Da wird einfach der Speicher Byte für Byte 
ins SPI-Register geschrieben.
Also ein 16-Bit-Wert steht bei
Adr x Low-Byte
Adr x+1 High-Byte
im Speicher.
Ich kann zwar kein Bascom, aber ich denke das
> Spiout Testvar , 2
gibt ab der Adresse "Testvar" zwei Byte aus: Lowbyte-Highbyte. So wie es 
im Speicher steht.

In die Print-Funktion dagegen ist eine Formatierung eingebaut. Damit 
gibt sie die Daten (menschen-)lesbar für den Bildschirm aus. Dafür ist 
sie ja urprünglich gedacht.


mfg.

PS:
uffzmuffz schrieb:
> mein Beileid
Von mir auch.
OP #2893762
Lesenswert?

uffzmuffz schrieb:
> Tim E. schrieb:
>> Vorneweg, ich arbeite mit Bascom
>
> mein Beileid

Danke dir, muss aber nicht sein. Ich programmiere auch in C, doch wenn 
es mal etwas kleines ist, dann in Bascom weil ich mir viel 
programiererei spare. Da investiere ich lieber in Hardware Entwicklung.


@den Rest der Antworter:

Vielen Dank euch. Nun ist es mir auch wunderbar verständlich ;D

LG Tim
#2893835
Lesenswert?

mue-c schrieb:
> Dreht er dann die Bits oder die Bytes?
Na überleg mal selber.
Das ist ein 8-Bit-Controller. Der weiss gar nicht was word oder int ist. 
Und woher soll er wissen, daß nach dem aktuellen Byte noch eines kommen 
soll. Vor allen Dingen: Wo soll er das erste solange lassen, wenn er das 
zweite vorher abschicken soll?
Die Ausrichtung im Speicher ist auch nur softwaremässig. In Assembler 
kannst du das auch anders einlagern. Nur bei 16-, 32-, etc.- 
Bit-Rechnern ist das von der Hardware vorgegeben.
Wobei beim AVR natürlich die 16-Bit Register, TCNT1 bspw., welche aus 2 
8-Bit-Registern bestehen, in Little Endian abgelegt sind. Deshalb wäre 
es Unsinn, wenn der Compiler oder der Assemblerprogrammierer das anders 
machen würden. Aber möglich wäre das.
Macht auch deswegen schon keinen Sinn, da die Peripherie-Hardware das 
auch in der Reihenfolge haben will. Ist eben das weiter verbreitete 
System. Allein schon deswegen, weil Intel das so macht.

mfg.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren