Forum: Mikrocontroller und Digitale Elektronik Unidirektionale Datenübertragung, 1 Leitung, kein Quarz


von Egberto Gismonti (Gast)


Lesenswert?

Hallo Forum,

ich möchte Daten in einer Richtung von uC zu uC übertragen und möglichst 
nur eine Leitung dafür verwenden. Der empfangende ATTiny hat keinen 
Quarz!

Die Leitung sollte ein paar (<10) Meter lang sein können und mehrere 
Attinys sollten dran hängen können (Adressierung kriegen wir später ;-).

Was kann man da leicht implementieren (in C)?

Grüße,

Egberto

von Bensch (Gast)


Lesenswert?

nein

1 Leitung mit Quarz ja, 2 Leitungen ohne Quarz ja.

von Michael U. (amiga)


Lesenswert?

Hallo,

mehrere 01 am Anfang schicken zum Syncronisieren, dann eine Präambel um 
den Anfang zu erkennen, dann die Daten mit Prüfsumme.

Wenn es nicht verloren gehen soll, mehrmals schicken.

Die Kurzzeitstabilität sollte da ausreichen, wenn die Datenpakete nicht 
zu groß werden, sonst eben neu syncronisieren.

Sollte eigentlich gehen...

Gruß aus Berlin
Michael

von Peter D. (peda)


Lesenswert?

Egberto Gismonti wrote:
> ich möchte Daten in einer Richtung von uC zu uC übertragen und möglichst
> nur eine Leitung dafür verwenden. Der empfangende ATTiny hat keinen
> Quarz!

Ja, ist kein Problem.

Man kann die Baudrate automatisch ermitteln.
Hier ein Beispiel (Anhang 12. Beitrag):

Beitrag "LCD über nur einen IO-Pin ansteuern"


Peter

von 6640 (Gast)


Lesenswert?

Mit einer genugend tiefen Baudrate is das schon moeglich. Denkbar ist 
eine positive flanke zu detekieren, und eine Zeit danach (zB 100us)das 
Bit zu sampeln.

von Benedikt K. (benedikt)


Lesenswert?

OneWire Bus.

von Luther B. (luther-blissett)


Lesenswert?

Du könntest drei verschiedene Zustände auf der Leitung verwenden. Wenn 
du dann S0,S1,S2 hast, dann zeigt jeder Zustandswechsel clock an und die 
Richtung des Wechsels data.

Also
 S1->S0:0 S1->S2:1
 S0->S2:0 S0->S1:1
 S2->S1:0 S2->S1:1

Jetzt suchst du dir Zustände aus, die du gut implementieren kannst, z.B. 
-5V,0V,5V oder 0V,5V,hochohmig

von Egberto Gismonti (Gast)


Lesenswert?

@Peter Danneger

Hallo Peter,

sieht so aus, als wäre es das, was ich brauche (vielen Dank!).
Ich habe noch ein Verständnisproblem: lt deiner Doku setzt man mit 0x13 
+ Zahl die Baudrate - ich dachte, das ist autobaud??

Grüße,

Egberto

von Egberto Gismonti (Gast)


Lesenswert?

ok, habs verstanden.. ich muß aber Binärdaten übertragen??

von Alexander S. (esko) Benutzerseite


Lesenswert?

Luther Blissett wrote:
> Jetzt suchst du dir Zustände aus, die du gut implementieren kannst, z.B.
> -5V,0V,5V oder 0V,5V,hochohmig

Und wie soll hochohmig erkannt werden bei? Zumal bei mehreren 
Empfängern.

von Knut B. (Firma: TravelRec.) (travelrec) Benutzerseite


Lesenswert?

Manchester-Code funktioniert auch über eine Leitung ohne Quarz, da sich 
der Empfänger auf die Flanken synchronisieren kann. Die Fenster können 
mit einer Toleranz von bis zu 20% sicher ausgewertet werden.

von Luther B. (luther-blissett)


Lesenswert?

Alexander Schmidt wrote:
> Luther Blissett wrote:
>> Jetzt suchst du dir Zustände aus, die du gut implementieren kannst, z.B.
>> -5V,0V,5V oder 0V,5V,hochohmig
>
> Und wie soll hochohmig erkannt werden bei? Zumal bei mehreren
> Empfängern.

Ein Spannungsteiler für den ganzen Bus bringt die hochohmige Leitung auf 
2.5V könnte ich mir vorstellen. Wenn man es richtig dimensioniert, dann 
müssten die slaves eventuell sogar den dritten Zustand detektieren 
können indem sie ihre internen pullups aktivieren/deaktivieren.

von Egberto Gismonti (Gast)


Lesenswert?

Hat denn jemand einen einfachen Codeschnipsel zur unidirektionalen 
Übertragung mit Machester-Code (in C)?

Schon mal vielen Dank

von Egberto Gismonti (Gast)


Lesenswert?

**nach oben bring**

Keiner je sowas programmiert?

von Michael U. (amiga)


Lesenswert?

Hallo,

ich bisher nicht, aber z.B. wohl alle Leute, die einfache Funkmodule 
benutzen. Da werden üblicherweise die Daten Manchester-codiert in den 
Sender geschoben und aus dem Empfänger wieder rausgeholt...

Man kann durchaus sagen, daß jede Funkstrecke Sender-Empfänger eine 
1-Draht Verbindung ist, noch dazu mit dem Nachteil vorkommender 
Wackelkontakte ;-)

Gruß aus Berlin
Michael

von nixwisser (Gast)


Lesenswert?

Wie zeitkritisch ist eigentlich oneWire? Also wieviel % darf das Timing 
abweichen, damit man noch sicher übertragen kann?

von Egberto Gismonti (Gast)


Lesenswert?

Das Problem bei 1-Wire ist

1. Auf der Empfängersoftware liegt ein Copyright (oder Patent was auch 
immer)
2. sehr "strammes" Timing

Scheint für meinen Zweck ungeeignet.

Grüße,

Egberto

von Esko (Gast)


Lesenswert?

> Das Problem bei 1-Wire ist
> 1. Auf der Empfängersoftware liegt ein Copyright (oder Patent

Ist davon auszugehen, dass du deine Schaltung komerziell verwerten 
willst?
Falls nein braucht dich das Patent nicht zu kümmern.

von chris (Gast)


Lesenswert?

Es gibt Verfahren zur Datenübertragung über eine Leitung, die nicht so 
taktempfindlich sind.
z.B. das Morse-Verfahren: Kurz, Lang, Lang, Kurz, Lang ...
Dann kann man sehr gut eine Datenübertragung mit nur 2 Pegeln 
realisieren.

http://www.roboterclub-freiburg.de/AtmelAVR/Software/chEinAnschlussKom_V1.0.c.zip

von Luther B. (luther-blissett)


Lesenswert?

Egberto Gismonti wrote:
> Hat denn jemand einen einfachen Codeschnipsel zur unidirektionalen
> Übertragung mit Machester-Code (in C)?
>
> Schon mal vielen Dank

Naja, wenn das Verfahren verstanden hat, sollte es kein Problem sein das 
zu kodieren.

Senden - Du schickst einfach (clock xor data) auf den Draht. Damit sich 
der Empfänger leichter synchronisieren kann, schickst du am besten am 
Anfang einer Nachricht noch eine 0 als startbit vorraus.

void sendbit(bool b) { put(!b); delay(); put(b); delay(); }

Empfänger - Der Empfänger misst einfach die Zeit von Flankenwechsel zu 
Flankenwechsel. Da der Sender eine Start-0 mitgeschickt hat, bekommt er 
gleich eine ansteigende Flanke der Länge t (die dem delay() entspricht). 
Wenn du dir jetzt z.B. das Manchester Code Beispiel auf Wikipedia 
anschaust, dann siehst du, daß ein Puls der Länge 2*t nur dann vorkommt, 
wenn sich das Datenbit ändert. Ansonsten bekommst du zwei Pulse der 
Länge t. Ohne Gewähr hingehackt:
1
// wartet auf die nächste Flanke (egal welcher Richtung)
2
// gibt zurück wie lange das gedauert hat. 
3
unsigned wtf(); 
4
5
// Aufzurufen, wenn das Startbit sichtbar wird, am Eingang liegt 1 an.
6
void receive()
7
{
8
 bool bit=0; 
9
 unsigned t = wtf();  // länge des 1-er Puls
10
 while (1)  
11
 {
12
  unsigned tx=wtf();
13
  if (eps(tx,t)) 
14
   { 
15
     tx=wtf(); 
16
     if (eps(t,tx)) 
17
        {
18
        output(bit);
19
        t=(t+tx)/2; // der Drift folgen
20
        } 
21
     else 
22
        error();  
23
   }
24
  else if (eps(tx,2*t)) 
25
    {  
26
      bit=!bit; 
27
      output(bit);
28
      t=(2*t+tx)/4; // der Drift folgen
29
    }
30
  else error();
31
 }
32
}
eps(x,y) ist Vergleich mit akzeptabler Fehlermarge.

von Benedikt K. (benedikt)


Lesenswert?

Egberto Gismonti wrote:
> Das Problem bei 1-Wire ist
> 2. sehr "strammes" Timing

Das würd ich nicht so sehen: Nach dem kurze Low Impuls sampled der 
Empfänger in einem recht breiten Zeitfenster. Laut Datenblatt liegt 
dieses Fenster 15-45µs nach dem vom Master erzeugten Impuls. Selbst mit 
50% Taktabweichung sollte Onewire also noch funkionieren.

von Jan E. (Firma: Austriamicrosystems AG) (jankey)


Lesenswert?

versuchs doch mal damit, wenn 2 Systeme nicht Absolut genau zueinander 
sind, is es vl. in einem gewissen Maße Relativ genau.

versuchs mal mit:

1/3 LOW + 2/3 HIGH = 1
2/3 LOW + 1/3 HIGH = 0

also du hast einen zähler und zählst einfach wieviele clock pulse high 
sind und wieviele low sind. dann schaust du welche der beiden größer ist 
ob hightime oder lowtime. Wenn die Hightime länger war ist eine 1 
übertragen worden. und bei Lowtime > Hightime --> 0 Übertragen worden, 
also mit zb 15~20 Clock zyklen pro Bit funktioniert das schon wirklich 
sehr gut. Meiner ansicht nach der beste weg um Asnychronität 
auszugleichen.

lg

von Luther B. (luther-blissett)


Lesenswert?

Gehtdich Nixanduspammbot wrote:

> also du hast einen zähler und zählst einfach wieviele clock pulse high
> sind und wieviele low sind. dann schaust du welche der beiden größer ist
> ob hightime oder lowtime. Wenn die Hightime länger war ist eine 1
> übertragen worden. und bei Lowtime > Hightime --> 0 Übertragen worden,
> also mit zb 15~20 Clock zyklen pro Bit funktioniert das schon wirklich
> sehr gut. Meiner ansicht nach der beste weg um Asnychronität
> auszugleichen.
>
> lg

Das ist auch eine schöne Idee. Wenn man unterschiedliche Pegellängen 
benutzt, dann kann man auch auf beiden Flanken Daten übertragen. Man 
sendet zunächst ein Synchronisationszeichen. Wenn der darauffolgende 
Pegel die gleiche Länge t hat, dann wird 0 kodiert. Hat er eine andere 
Länge, dann 1. Die andere Länge könnte z.B abwechselnd t*3/2 und t*1/2 
sein, so daß die mittlere bitrate erhalten bleibt.

von STK500-Besitzer (Gast)


Lesenswert?

Die Synchonisation-Aktion kann man sich doch sparen, wenn man die Bits 
über ein bestimmte Periodenlänge verteilt, und die Information ob 1 oder 
0 über die Pulslänge realsiert.
Dann bräuchte man nur die Puls- und die Periodendauer (per ICP) messen 
und könnte aus dem Tastgrad den Bitwert feststellen.
So ähnlich arbeiten Modellbaufernsteuerungen ja auch.

von Marco S (Gast)


Lesenswert?

Hallo.

Von den ganzen Einleitungsbussen gibts von TI einen, der sich HDQ nennt. 
Diesen habe ich mal im wesentlichen kopiert. Der Bus überträgt die Daten 
bitseriell, mit einem 10us-Low als "1" und 30us-Low als "0", bei einer 
minimalen Zykluslänge von 80us. Für die Rahmensynchronisation wird dem 
Ganzen ein 60us-Low vorangestellt, und der Frame mit ACK/NACK bestätigt. 
Dazu habe ich einen ext. Interrupt auf fallende Flanke getriggert. Im 
Interrupt wird 80us lang ein Schleifenwert erhöht, solange der PIN low 
ist. Die Auswertung des Zählerstandes führt zu High/Low/Break.
Gemacht habe ich das, weil es auf die Datenrate nicht ankam. Zudem ist 
der Bus unempfindlich gegenüber Glitches, die nach der fallenden Flanke 
kommen (war bei mir durch einf. opt. Isolation mit Optokoppler der 
Fall).

von Peter D. (peda)


Lesenswert?

Der Manchester ist ziemlich aufwendig in Software und braucht ne 
Synchronisation (bekanntes 1.Bit).

Wenn man dessen Vorteil der Gleichspannungsfreiheit nicht braucht, 
sollte man ihn daher nicht benutzen.

Wennn man keine Lust hat, ne Software-UART mit automatischer 
Baudratenerkennung zu verwenden, bietet sich die Impulslängenmodulation 
an, z.B.:

4*T = Startbit
2*T = 1-Bit
1*T = 0-Bit

Vorzugsweise wählt man T so, daß ein 8Bit-Timer im Empfänger nach 3*T 
überläuft und der Comparator auf 1,5*T vergleicht.
Im Flankeninterrupt setzt man ihn zurück auf 0 und wertet diese beiden 
Flags aus.


Peter

von Winfried (Gast)


Lesenswert?


von Peter D. (peda)


Lesenswert?

chris schrieb:
> http://www.roboterclub-freiburg.de/AtmelAVR/Softwa...

Hallo Chris,

in meinem Thread:
Beitrag "Re: mehrere MC seriell über Datenbus verbinden (1Draht)"
hast Du geschrieben, daß Du 360KBit/s erreichst.

Ich habs mir daraufhin mal angesehen.
Also ich komme nur auf 1/(2*18,75µs) = 26,7kBit für 0-Bits bzw. 17,8kBit 
für 1-Bits.

Ich verstehe auch nicht, wie sich der Slave auf den Empfang 
synchronisieren kann, bzw. überhaupt mitkriegt, daß der Master sendet.

Es kann doch nicht sein, daß der Slave keine Main-Task machen kann, 
sondern immer nur auf den Empfang wartet.
Und was passiert, wenn der Master schon ein Bit gesendet hat, ehe der 
Slave auf Empfang geht?
Wie erfolgt eine Störerkennung bzw. Resynchronisation?


Die Prämisse bei meinem Code liegt nicht auf Geschwindigkeit.
Sondern der Slave soll nicht bei seiner Task behindert werden und auch 
eigene Interrupts ausführen können.
Er macht also seine eigenen Aufgabe völlig unabhängig vom Master.
Und erst, wenn der Master was will, adressiert er den Slave.
Die Kommunikation darf die eigentliche Aufgabe nicht stören oder 
verzögern.
Auch muß die Kommunikation nach einer Störung wieder alleine aufsetzen 
können.


Peter

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.