Forum: Mikrocontroller und Digitale Elektronik Problem mit serieller Datenübertragung und ATtiny13


von F. J. (Gast)


Lesenswert?

Hallo zusammen,
ich habe ein Programm geschrieben, dass Bytes über die serielle 
Schnittstelle an den ATtiny13 sendet, und empfangene Bytes anzeigt. Wenn 
ich jetzt mit Bascom programmiere, dass der Tiny13 mir einen Text 
ausgeben soll, kommt der richtig an, die Baudrate habe ich sowohl im 
Bascom als auch in meinem Programm auf 1000 gestellt. Wenn ich jetzt 
z.B. das Byte 126 an den Tiny13 sende, verarbeitet es dies irgendwie 
nicht.
Weiß jemand warum?
Das Byte kommt richtig an, das sehe ich, wenn ich den Ausgang vom 
Computer an den Eingang vom Computer schließe.
Code ist folgender:

$regfile = "attiny13.dat"
$crystal = 1200000
Open "comb.0:1000, 8,n,1,Inverted" For Output As #2
Open "comb.1:1000, 8,n,1,Inverted" For Input As #1
Dim B As Byte
Do
B = Inkey(#1)
Loop Until B = 126
Print #2 , "126"
End

Vielen Dank!

von Karl H. (kbuchegg)


Lesenswert?

F. J. schrieb:

> z.B. das Byte 126 an den Tiny13 sende, verarbeitet es dies irgendwie
> nicht.

Wie wäre es, wenn du dir einfach mal den Wert von B ausgeben lässt?
Dann brauchst du nicht raten, sondern siehst direkt welche Bytes der 
Tiny empfängt.

> die Baudrate habe ich sowohl im
> Bascom als auch in meinem Programm auf 1000 gestellt.

1000 ist aber eine sehr unübliche Baudrate.
Kannst du die wirklich an deinem PC einstellen?

von F. J. (Gast)


Lesenswert?

Ich hab mal das gemacht:
Do
Input #1, B
Print #2, B
Loop

Da kommt nichts.

von Karl H. (kbuchegg)


Lesenswert?

Gah als allererstes mal auf eine vernünftige Baudrate.
300, 600, 2400, 4800, 9600

9600 ist am Anfang ein guter Kompromiss

von F. J. (Gast)


Lesenswert?

Bei 9600 gab es Übertragungsfehler, bei der Ausgabe von Text, deswegen 
1000.

von F. J. (Gast)


Lesenswert?

Funktionier immer noch nicht mit der Baudrate.

von Karl H. (kbuchegg)


Lesenswert?

F. J. schrieb:
> Bei 9600 gab es Übertragungsfehler, bei der Ausgabe von Text, deswegen
> 1000.

Aha. Lass mich raten.
Kein Quarz, interner Oszillator?


(Geh deinen Übertragungsfehlern auf den Grund. Bei 9600 darf es keine 
Fehler geben.)

: Wiederhergestellt durch User
von Hannes L. (hannes)


Lesenswert?

Der interne RC-Oszillator des Tiny13 geht nach der Blankenheimer 
Sonne...

Für'n Quarz wird es mit den Pins eng.

...

von F. J. (Gast)


Lesenswert?

Karl heinz Buchegger schrieb:
> Aha. Lass mich raten.
> Kein Quarz, interner Oszillator?

Ja.
Wieso geht es aber bei der Ausgabe, und wieso funktioniert der Eingang 
nicht?

von Karl H. (kbuchegg)


Lesenswert?

Weil die Empfangseinheit vom PC unter Umständen ein bischen 
fehlertoleranter ist. Gerade gut genug, dass der Empfang noch klappt.

von F. J. (Gast)


Lesenswert?

Mist. Das ist schlecht. Ein Quarz einbauen geht überhaupt nicht. Kann 
ich Softwaremäßig was machen? Ich müsste 60 Bytes übertragen. Wieso 
funktioniert der serielle ISP-Programmer dann eigentlich?

von Hannes L. (hannes)


Lesenswert?

F. J. schrieb:
> Mist. Das ist schlecht. Ein Quarz einbauen geht überhaupt nicht.

Dann hast Du auch keinen Anspruch auf wirklich zuverlässig 
funktionierendes RS232.

> Kann
> ich Softwaremäßig was machen?

Es kann am Schreibtisch funktionieren, es muss aber nicht.

> Ich müsste 60 Bytes übertragen.

RS232 geht nunmal nur zuverlässig, wenn die Baudrate stimmt. Es wird 
schließlich bei jedem Byte nur einmal synchronisiert (Startbit).

> Wieso
> funktioniert der serielle ISP-Programmer dann eigentlich?

Der arbeitet nach einem anderen Protokoll (SPI, synchron, wie bei 
Schieberegistern) und nutzt eine separate Taktleitung zur 
Synchronisation.

...

von Karl H. (kbuchegg)


Lesenswert?

Das das mit dem RC nicht zuverlässig wird, wurde ja schon erwähnt. Und 
du solltest das ernst nehmen.

Nichts desto trotz. Wenn deine Schaltung in etwa immer in derselben 
Umgebungstemperatur arbeitet, wird auch der RC sich nicht allzuviel 
verstellen.


Daher sollte man jetzt als allererstes

$crystal = 1200000

abklären, wie genau diese Angabe wirklich ist.
Sprich: du musst die Taktfrequenz deines µC herausfinden.

von Hannes L. (hannes)


Lesenswert?

Karl heinz Buchegger schrieb:
> Das das mit dem RC nicht zuverlässig wird, wurde ja schon erwähnt. Und
> du solltest das ernst nehmen.
>
> Nichts desto trotz. Wenn deine Schaltung in etwa immer in derselben
> Umgebungstemperatur arbeitet, wird auch der RC sich nicht allzuviel
> verstellen.

Dann lohnt es sich, mit Baudratenangaben zu experimentieren, die dicht 
neben der gewünschten Baudrate liegen. Bei Änderung von 
Versorgungsspannung und/oder Temperatur muss das aber nicht mehr 
funktionieren, ebenso bei einem anderen Exemplar.

Bei einem Mega8 funktionierte RS232 ohne Quarz z.B. überhaupt nicht. Da 
ein GLCD im 8-Bit-Mode angeschlossen war, konnte ich auch keinen Quarz 
anschließen, denn ich wollte den Datenport nicht teilen. Beim Tiny2313 
meines Pollin-IR8-Bausatzes funktioniert RS232 (Hardware-USRT) mit 19200 
Baud auch ohne Quarz. Mir ist aber bewusst, dass es nicht funktionieren 
muss.

>
>
> Daher sollte man jetzt als allererstes
>
> $crystal = 1200000
>
> abklären, wie genau diese Angabe wirklich ist.
> Sprich: du musst die Taktfrequenz deines µC herausfinden.

Naja, für einen neuen Tiny13 vom Markenhändler stimmt das schon, solange 
die Fuses nicht angerührt wurden. Sollte das Ding aber anderer Herkunft 
sein (Pollin, Lernprogramm, Bausatz), dann muss man die 
Fusebiteinstellungen eben nochmal überprüfen.

...

von F. J. (Gast)


Lesenswert?

Karl heinz Buchegger schrieb:
> Sprich: du musst die Taktfrequenz deines µC herausfinden.

Gut. Aber wie kann ich das machen?

von Hannes L. (hannes)


Lesenswert?

F. J. schrieb:
> Karl heinz Buchegger schrieb:
>> Sprich: du musst die Taktfrequenz deines µC herausfinden.
>
> Gut. Aber wie kann ich das machen?

Z.B. durch Auslesen der Fusebits und Vergleich mit den Angaben im 
Datenblatt des Tiny13.

...

von Karl H. (kbuchegg)


Lesenswert?

Hannes Lux schrieb:

>> abklären, wie genau diese Angabe wirklich ist.
>> Sprich: du musst die Taktfrequenz deines µC herausfinden.
>
> Naja, für einen neuen Tiny13 vom Markenhändler stimmt das schon, solange
> die Fuses nicht angerührt wurden.

Echt?
Einen Tiny13 hatte ich noch nie in den Fingern. Einen Tiny11. Gut das 
ist zwar eine andere Baustelle, aber ohne den OSCAL war der sowas von 
daneben.

von F. J. (Gast)


Lesenswert?

Ich werd mal gucken, ob ich damit weiterkomme.
Ansonsten würd ich es kompliziert machen, und sowas programmieren:
Senden "a"
Warten 2 MS
Auslesen Zustand an Pin, entscheiden ob 1 oder 0

das 5 mal
und dann zu Byte konvertieren.
Wäre das vom verfügbarem Speicher möglich?
Vielen Dank für eure Hilfe!

von Hannes L. (hannes)


Lesenswert?

Karl heinz Buchegger schrieb u.A.:
> Hannes Lux schrieb u.A.:
>> Naja, für einen neuen Tiny13 vom Markenhändler stimmt das schon, solange
>> die Fuses nicht angerührt wurden.
>
> Echt?
> Einen Tiny13 hatte ich noch nie in den Fingern. Einen Tiny11. Gut das
> ist zwar eine andere Baustelle, aber ohne den OSCAL war der sowas von
> daneben.

Ja, der läuft ab Werk mit internem RC mit 9,6 MHz und aktivem Vorteiler 
1 zu 8 und ist damit halbwegs kompatibel zum Vorgänger Tiny12. Ich nutze 
der Tiny13 ganz gern, allerdings nicht mit UART. Da bevorzuge ich 
bitsynchronisierende serielle Übertragung.

...

von F. J. (Gast)


Lesenswert?

Hallo zusammen,
ich hab mal weiter rumexperimentiert, und bei kleinerer Baudrate 
funktioniert das ganze auch.
Es kommen wieder die Bytes zurück, die ich gesendet habe.
Allerdings ganz richtig ist es immer noch nicht, ich sende ca. 10 Bytes, 
nach dreien oder vieren mache ich 1 sec. Pause, aber es kommen immer nur 
die ersten drei Bytes zurück.
Woran kann das liegen?
Vielen Dank!

von Grrrr (Gast)


Lesenswert?

F. J. schrieb:
> Woran kann das liegen?

Der Takt wird mit der Zeit weglaufen.

Es gibt noch die Möglichkeit mit dem OSCCAL-Register den Takt anhand der 
empfangenen Zeichen zu korrigieren. Gibt es hier auch Threads dazu. 
Allerdings muss dazu der Empfangsinterrupt selbst geschrieben werden. 
Weiss nicht ob das in BASCOM geht.

von Hannes L. (hannes)


Lesenswert?

Grrrr schrieb:
> F. J. schrieb:
>> Woran kann das liegen?
>
> Der Takt wird mit der Zeit weglaufen.
>
> Es gibt noch die Möglichkeit mit dem OSCCAL-Register den Takt anhand der
> empfangenen Zeichen zu korrigieren. Gibt es hier auch Threads dazu.
> Allerdings muss dazu der Empfangsinterrupt selbst geschrieben werden.
> Weiss nicht ob das in BASCOM geht.

Z.B. so:
1
$baud = 19200                           'Baudrate UART
2
...
3
On Urxc Onrxd                           'UART-Empfangs-Interrupt
4
Enable Interrupts                       'Interrupts global freigeben
5
...
6
7
Onrxd:                                  'ISR, UART-Byte eingetroffen
8
  Incr Rix                              'Schreibposition im Array erhöhen
9
  Rx_buf(rix) = Udr                     'Empfangsbyte in Buffer legen
10
Return                                  'fertig, zurück...
Wobei Rx_buf() ein Array zum Einsammeln der empfangenen Bytes ist und 
Rix der Index zu diesem Array. Erreicht Rix den vereinbarten Wert 
(entspricht len(string)), dann kopiert sich die Mainloop den Inhalt 
woandershin und löscht Rix.

Dies diente zum Empfang von Bytekolonnen fester Länge, man kann es aber 
auch als Ringbuffer organisieren.

...

von F. J. (Gast)


Lesenswert?

Erstmal vielen Dank für eure Antworten!

Grrrr schrieb:
> Der Takt wird mit der Zeit weglaufen.

Also umso langsamer ich den Tiny13 Takte, umso länger funktioniert es?

von Hannes L. (hannes)


Lesenswert?

F. J. schrieb:
> Erstmal vielen Dank für eure Antworten!
>
> Grrrr schrieb:
>> Der Takt wird mit der Zeit weglaufen.

RS232 synchronisiert sich bei jedem Startbit (1 mal pro Byte) neu. Wenn 
die ersten drei Bytes durchkommen, so sollten die anderen auch 
durchkommen. Oder Du liegst dermaßen grenzwertig daneben, dass es Zufall 
ist, ob es klappt oder nicht.

Vielleicht liegt der Fehler aber auch auf der PC-Seite. Ich hatte auch 
mal ähnliche Probleme (mit Terminal und auch VB6), da spuckte der 
RS232-FIFO im PC die Daten nicht zur rechten Zeit aus, sondern erst, 
wenn weitere Daten eintrafen. Das muss hier aber nicht unbedingt der 
Fall sein.

>
> Also umso langsamer ich den Tiny13 Takte, umso länger funktioniert es?

Nööö, wenn es Baudratenfehler aufgrund von Frequenzabweichungen sind, 
dann sind die bei jeder Baudrate und jeder Sollfrequenz (Takt) gleich. 
Das einzige Argument, warum kleinere Baudraten weniger Fehler 
verursachen, ist das, dass der Teilerfaktor größer und damit 
ganzzahliger wird, also dass der Nachkommawert, der ja unterschlagen 
wird, sich geringer auswirkt.

Wenn Du wirklich ohne Baudratenquarz eine RS232-Verbindung vom und zum 
PC realisieren willst, dann lass den Tiny13 mit hoher Taktfrequenz 
laufen (9M6) und experimentiere mit Baud-Angaben dicht um den Sollwert 
herum. Also bei 9600 Baud mit Werten im Bereich von 9200 bis 10000. 
Allerdings halte ich es für möglich, dass Bascom die Baudangaben auf 
genormte Werte rundet, dass diese Maßnahme also nichts bringt.
Dann bleibt nur noch die Manipulation von OSCCAL. Hierbei sollte 
beachtet werden, dass jedes Exemplar einen anderen Calibrationswert 
haben kann. Die "magische Zahl", die Du ermitteln kannst, gilt also nur 
für dieses eine Exemplar. Für eine Serie ist das also auch Murks.

Unterm Strich halte ich es deshalb für sinnvoller, einen AVR mit mehr 
Pins und Hardware-UART zu benutzen, dem einen Baudratenquarz zu 
spendieren und damit eine zuverlässige serielle Kommunikation zu 
erreichen.

...

von F. J. (Gast)


Lesenswert?

Danke für deine ausführlichen Beitrag.
Ich werd den Tiny jetzt mal schneller Takten und sehen was rauskommt.

von F. J. (Gast)


Lesenswert?

Danke!
Bei 9,6MHZ funktioniert das sehr gut, vorrausgesetzt, ich sende die 
Bytes einzeln mit 10ms Pause.

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.