Hallo allerseits,
erstmal ein Lob an dieses geniale Forum!
bisher hab ich nur mit Arduinos gearbeitet, aber man will ja immer was
Neues lernen ... zu meiner eigentlichen Frage:
Bevor ich mich verrenne ...
ich möchte mir kleine Boards bauen, die 2 Gabellichtschranken (Home &
Endstop) abfragen und einen Schrittmotortreiber wie zB den A4988 mit
mindestens STEP und DIR (vielleicht noch MS1 bis MS3, wenn nicht per
jumper gelöst) an den Controller angechlossen, steuern. Also eine
Achsensteuerung.
Dieses kleinen Boards soll von einem "Haupt-Controller" (ein Arduino
Mega 2560, der per USB an einem WinPC hängt) gesteuert werden.
Die Kommunikation dieser Boards mit dem Haut-Board, sowie die zu
verwendenden µC breiten mir etwas Kopfzerbrechen ...
Ist I2C dafür überhaupt das richtige Protokoll und/oder sollte ich noch
andere Dinge bedenken?
MfG Neod
neod schrieb:> Ist I2C dafür überhaupt das richtige Protokoll und/oder sollte ich noch> andere Dinge bedenken?
I2C ist eine Schnittstelle. Das Protokoll, das darauf gefahren wird,
ist je nach angeschlossenen ICs anders. Oder vereinfacht:
Schnittstelle=Hardware, Protokoll=Software
Zur Verbindung zwischen 2 uC würde ich aber einfach eine RS232
Schnittstelle nehmen. Diese Schnittstelle ist Vollduplex, d.h. sie kann
in beide Richtungen gleichzeitig übertragen...
Falls du mit der seriellen Schnittstelle nur auf der Platine unterwegs
bist, reicht TTL-Pegel aus. Falls du ein paar Meter weiter fahren musst,
kannst du RS232 Pegel fahren. Und wenn du dann wirklich große Strecken
hast, kannst du sogar auf RS422 umschwenken. 3 verschiedene
Schnittstellen für 3 verschiedene Anwendungsbereiche, aber nur 1
Protokoll und damit keine Softwareänderung.
Ja, UART ist das Mittel der Wahl. Niemand zwingt einen, sich auf 115kBd
zu beschränken. Ich nehm gern 500kBd. Dazu hat fast jeder µC den Block
eh drin, so dass das einfach zu Handeln ist.
Das ist dann viel schneller als I2C, betreffs Latenz und Datenrate und
trotzdem robuster...
Aber Anfänger und einige Foristen hier scheinen einen Narren an I2C über
Kabel gefressen zu haben, dabei hat es gewaltige Nachteile:
- Nich Push-Pull --> EMV ist problematisch (Immunität)
- Taktsynchron --> Empfindlich auf Laufzeiteffekte
Die Leute sollten mal überlegen was I2C heißt: Inter Integrated Circuit.
Dafür ist es da, und dafür ist es gut. Jaja, ich weiß, HDMI, DVI, PS2.
Aber das ist IT - eine Welt für sich.
Einen Nachteil der UART sollte man nicht vergessen: Mit dem Takt ist
Vorsicht geboten. Der muss eie bestimmte Genauigkeit haben - welche
steht im Datenblatt. Bei den STM32 heißt das fast immer:
Keramikresonator oder Oszillator.
Ein Kollege hat mir nicht geglaubt - und musste eine Menge Platinen
wegwerfen lassen, weil bei 10% die UART nicht ging (Takt differiert zu
weit)...
WehOhWeh schrieb:> Ein Kollege hat mir nicht geglaubt - und musste eine Menge Platinen> wegwerfen lassen, weil bei 10% die UART nicht ging (Takt differiert zu> weit)...
Schön, damit hast Du eine Stärke des IIC indirekt betont. Eine weitere
wäre die einfache Adressierbarkeit.
Andererseits bevorzuge ich auch eine UART mit Multiprozessorprotokoll,
sobald die Signale die Platine verlassen.
Christian J. schrieb:> Ich nehme onboard immer die SPI... sicherm, einfach, megaschnell :-)
Aber eben nicht so richtig bidirektional. Und gerade beim AVR zudem
nicht richtig gut gepuffert. Und "megaschnell" ist bei dieser Anwendung
hier vermutlich gleichzusetzen mit "Overkill"...
Der absolute Vorteil der seriellen Schnitte ist natürlich, dass man
einfach mit einem PC "mithören" und mitprotokollieren kann. Das ist oft
Gold wert.
Hat CAN hier irgendwelche Vorteile? Also bei Kabel quer durchs
Zimmer/Haus?
Wenn nicht schon im mC vorhanden brauchts neben den transceiver halt
noch einen controller (für RS232 brauchts auch nen MAX232 o.ä?)
CAN ist doch afaik Takt- und Störunanfällig?
Und man könnte später noch weitere Teilnehmer hinzufügen, ohne am
"Master" (Mega2560/STM32) was anzupassen...
t_k schrieb:> CAN ist doch afaik Takt- und Störunanfällig?
Eine stabile und präzise Taktquelle ist Voraussetzung. Genauer als bei
UART. Ein interner RC-Osz ist meist nicht ausreichend.
t_k schrieb:> gibt es brauchbare alternativen
One-Wire, geht zuverlässig auch über größere Entfernungen, kann
gegebenenfalls auch auf Funk umgestellt werden, verwendbar ist z.B. das
ds1820 protokoll.
grundschüler schrieb:> One-Wire
gibts da controller/transceiver für, die Last vom Prozessor nehmen oder
andere native Implementierungen ausserhalb von Sensoren?
sicher noch kein perfekter code, funktioniert aber sehr zuverlässig.
Der Master leitet den Sendevorgang durch einen low-impuls ein. Es gibt
einen Header von 4 bytes, der sender, empfänger, modus und
Datensatzlänge festlegt:
1
...
2
case(fb_red)://Owx_Daten_senden
3
#ifdef owx_port
4
owx_len=10;
5
owx_tx_buffer[0]=88+owx_WRITE;//dest_adr
6
owx_tx_buffer[1]=owx_len-2;
7
owx_tx_buffer[2]=10;//source_adr
8
owx_tx_buffer[3]=0;//status
9
owx_tx_buffer[4]=0;//len_read
10
owx_tx_buffer[5]=hou;
11
owx_tx_buffer[6]=min;
12
owx_tx_buffer[7]=sec;
13
14
ret=owx_senden(owx_tx_buffer,owx_len,0);
15
16
lgi(1,13,ret);
17
#endif
18
break;
19
20
case(fb_yellow):////Owx_Daten_abfragen
21
#ifdef owx_port
22
owx_len=5;
23
owx_tx_buffer[0]=88+owx_READ;//dest_adr
24
owx_tx_buffer[1]=owx_len-2;
25
owx_tx_buffer[2]=10;//source_adr
26
owx_tx_buffer[3]=1;//status
27
owx_tx_buffer[4]=6;//len_read
28
ret=owx_senden(owx_tx_buffer,owx_len,1);
29
lgi(1,15,ret);
30
#endif
31
break;
32
...
Die Richtigkeit der Übertragung wird durch eine vereinfachte crc
geprüft. Ich babe das ganze mit 2x m328 ausprobiert. der Master sendet
dem Slave sehr zuverlässig die Uhrzeit oder liest sie zurück.
Es gibt aber sicher auch noch andere 1wire/master/slave-Projekte.
t_k schrieb:>> One-Wire>> gibts da controller/transceiver für, die Last vom Prozessor nehmen oder> andere native Implementierungen ausserhalb von Sensoren?
Tu Dir das doch nicht an. Für Eindraht-Verbindungen geht auch UART im
Halbduplex-Betrieb.
t_k schrieb:> ok. guter punkt.> gibt es brauchbare alternativen
LIN. LIN ist ein 1-Draht (+GND) UART-Protokoll mit einigen
Besonderheiten.
1. Master-Slave Betrieb. Der Master gibt das Timing vor und braucht
daher einen Quarz. Die Slaves brauchen keinen Quarz.
2. LIN arbeitet mit BREAKs, die UARTs müssen also BREAKs erzeugen und
erkennen können. Ein BREAK ist quasi ein Startbit, das mehr als 13
Bitzeiten lang ist, also in der normalen Datenübertragung niemals
vorkommen kann.
3. Nach einem BREAK kommt ein Synchronbyte 0x55. Die Slaves müssen das
ausmessen und ihre Bitrate darauf einstellen. Der RC-Oszillatoren der
Slaves müssen damit nur kurzzeitstabil sein. Gute UART-Implementationen
(zB PIC24/dsPIC/PIC32) können das Ausmessen in Hardware, hier muss man
nur ein Bit setzen, der PIC macht den Rest. LIN ist jedoch so gebaut,
dass man bei den Slaves auch eine Software-Only-Implementation verwenden
kann. Das ist dann allerdings ziemlicher Entwicklungsaufwand. Die
AVR-UARTs sind eher mäßig für LIN geeignet, PIC24 ist hier viel besser.
4. LIN arbeitet mit 12V-Pegel und braucht dafür einen Transceiver, der
die Schnittstelle ziemlich gut vor Störungen von außen schützt. Es gibt
auch Transceiver, die gleichzeitig Spannungsregler und Systemüberwachung
beinhalten.
5. LIN kommt aus der Automobilindustrie und ist millionenfach getestet.
Es ist quasi die Low-End Erweitung für CAN, d.h. dort wo CAN zu teuer
ist, kommt LIN zum Einsatz.
fchk
ich habe einen Atmega8 mit internem Quarz und ohne jede Beschaltung als
Relaisbaustein seit über einem Jahr bei meiner Heizungsanlage im
Einsatz. Grund war, dass ein 74hc595 zu störanfällig war. Das ganze
funktioniert gut, aber noch nicht perfekt. Die heizung schaltet manchmal
ungesteuert ab. Deswegen habe ich den code so weiterentwickelt, dass der
Master den Zustand des slaves abfragen kann. Master und Slave sollen
sich zukünftig gegenseitig überwachen und notfalls einen Reset des
anderen Bausteins auslösen. Im Prinzip ist es ja eine Umnutzung des
ds1820-codes, also durchaus auch ein vielfach bewährtes System. Vorteil
des ds1820 ist, dass er ohne nennenswerten Aufwand auch über größere
Entfernungen funktioniert.