Hallo zusammen Ich bin derzeit noch Anfänger in der AVR Programierung und möchte jetzt einen kleinen Versuch zum Verstehen von I²C/TWI starten. Ich habe da auch schon gegoogelt aber ich habe es entweder nicht verstanden oder es war für GCC was ich (noch nicht) behersche und möchte es mit mit dem Atmel AVR Assembler programieren. Geht das Überhaupt in Atmel AVR Assembler? Ich habe hier ein selbstgebautes Bord für Atmega32 und eins für den Atmega8 liegen Ich möchte hier jetzt einfach nur eine Zahl übertragen. Daher Atmega32 --> Master || Atmega8 --> Slave (oder andersherum) Ich stelle mir das so vor das ich an dem Master an porta (bzw pina) ein paar Taster anschließe und den Wert der an den Pins "gedrückt wird" einfach dann an den Slave übertrage und der mir den Dann anhand von 8 LED´s an portb ausgibt Das alles hat natürlich keine Funktion und dient erstmal nur zum Verstehen Es wäre nett wenn ihr mir mal erklären würdet wie ich I²C/TWI initialisiere und dann etwas übertrage. Das es einen Start und Stop bit gibt habe ich schon herausgefunden und das eine Übertragung auf 9 Bit`s erfolgt. aber wie mache ich dem einen µc klar das er ein Master is und dem anderen ein Slave. Wie gebe ich dem slave dann eine Adresse und sage dem Master das er den Slave ansprechen soll, und dann auchnoch eine Übertragung der eigendlichen Daten? Wäre echt nett wenn Ihr mir da ein bisschen helfen könntet. Danke im voraus MFG Chris ;)
Lies die Datenblätter und - sobald Du TWI im Datenblatt wirklich verstanden hast - die entsprechenden Application Notes. Im übrigen solltest Du erst einmal derartige Dinge im Single-Prozessor-Betrieb zum Laufen bringen. Bernhard
Okay danke Ich werde mir jetzt mal die Datenblätter durchlesen aber wie soll das mit einem Prozessor klappen ich dachte TWI ist zum Übertragen von daten auf verschiede Bausteine
Hi >Das es einen Start und Stop bit gibt habe ich schon herausgefunden und >das eine Übertragung auf 9 Bit`s erfolgt. Bist du sicher, das du TWI meinst? Bei I2C/TWI gibt es Start-/Stop-Conditions, aber keine entsprechenden Bits. >aber wie mache ich dem einen µc klar das er ein Master is und dem >anderen ein Slave. Wie gebe ich dem slave dann eine Adresse und sage dem >Master das er den Slave ansprechen soll, und dann auchnoch eine >Übertragung der eigendlichen Daten? Was ist eigentlich naheliegender, als die Datenblätter zu lesen? Dort findest du eine umfassende Beschreibung und Codebeispiele in Assembler und C. MfG Spess
Ja klar aber wenns erklärt wird is es 1. immer besser und in dem fall auf Deutsch :D MFG Chris
So ich habe jetzt ein bisschen Datenblatt Literatur intus aber es ist immernoch schwer verständlich für mich. also ich habe jetzt folgende fragen auf jeden fall offen: stimmt diese Reihenfolge : initialisieren des Masters -->start condition senden --> adresse des anzusprechenden Atmegas senden --> Daten senden --> stop condition senden Wofür ist das TWI Bit Rate Register – TWBR und woher weiß ich was ich da eintrgen soll. ich vermute das das irgendwas mit der Geschwindigkeit von SCL zu tuhen hat (mein Prozessor läuft mit 1hz Internen takt) wenn ihr mir sagt das ich den höher stellen soll, mache ich das :) wie sende ich den die Adresse des anzusprechenden Controllers Helft mir bitte, habt doch mitleid mit einem noob :) MFG Christian
Christian schrieb: > (mein Prozessor läuft mit 1hz Internen takt) Ich hoffe doch, du meinst 1 M Hz? TWBR ist im Datenblatt beschrieben - damit lässt sich der Teiler und damit die SCL-Frequenz festlegen. Gruß, Marcel EDIT: Beachte die Maximal-Frequenz der TWI-Verbindung sowohl beim Master als auch beim Slave. Zur Adresse: Im Forum sind genug Beispiele dazu zu finden - ich selbst habe bisher aber keines davon getestet. Die Resonanz ist aber eher positiv, kommentare sind auch genug vorhanden. ;)
Marcel Papst schrieb: > Ich hoffe doch, du meinst 1 M Hz? Ja meine ich, hab mich verschrieben aber wie errechne ich was ich da eintragen muss? Im Datenblatt steht ja man soll die formel ; CPU Clock frequency __________________ 16 + 2(TWBR) ⋅ 4^TWPS anwenden das würde in meinem Fall ja bedeuten 1 __________________ 16 + 2(TWBR) ⋅ 4^TWPS Um das auszurechnen muss ich ja für TWBR und TWPS etwas einsetzten aber was ?
Hi Nimm für TWPS Null. Aber mit 1MHz Taktfrequenz bekommst du auf maximal 62,5 kHz TWI-Takt. Und die Taktfrequenz des Slaves muss 16x höher wie der TWI-Takt sein. MfG Spess
Aber wenn ich für den TWPS1/TWPS0 "0" setze gibt das doch einen Prescaler von 1 also rennt SCL dann nicht mit 1MHZ ?
Hi >Aber wenn ich für den TWPS1/TWPS0 "0" setze gibt das doch einen >Prescaler von 1 also rennt SCL dann nicht mit 1MHZ ? Rate mal, was die 16 in der Formel bewirkt. MfG Spess
spess53 schrieb: > Rate mal, was die 16 in der Formel bewirkt. Danke für den Tipp ;) Okay dann setzte ich den mal auf 0 und was ist mit TWBR ?
Hi
>und was ist mit TWBR ?
Mit TWPS=0 wird 4^TWPS=1. Damit hat die Formel nur noch eine Unbekannte.
Den Rest solltest du selbst können.
MfG Spess
Langsam verzweifele ich.... ich habe jetzt ffolgende Programme geschrieben; ersmal der Master Transmiter:
1 | |
2 | .include "m32def.inc" |
3 | |
4 | iniatall: |
5 | |
6 | ldi r16, LOW(RAMEND) |
7 | out SPL, r16 |
8 | ldi r16, HIGH(RAMEND) |
9 | out SPH, r16 |
10 | |
11 | ldi r16,255 |
12 | out DDRA,r16 |
13 | ldi r16,0 |
14 | out DDRB,r16 |
15 | ldi r16,255 |
16 | out portb,r16 |
17 | |
18 | |
19 | ldi r16, 0<<TWPS1 | 0<<TWPS0 |
20 | out TWSR,r16 |
21 | |
22 | ldi r16,255 |
23 | out TWBR,r16 |
24 | |
25 | |
26 | |
27 | loop: |
28 | |
29 | ldi r16, (1<<TWINT) | (1<<TWSTA) | (1<<TWEN) ;1 START condition senden |
30 | out TWCR, r16 |
31 | |
32 | |
33 | wait1: ;Wait for TWINT Flag set. This indicates that the START condition has been transmitted |
34 | in r16,TWCR |
35 | sbrs r16,TWINT |
36 | rjmp wait1 |
37 | |
38 | |
39 | ldi r16,0b11001100 ;Load SLA_W into TWDR Register. Clear TWINT bit in TWCR to start transmission of address |
40 | out TWDR, r16 |
41 | ldi r16, (1<<TWINT) | (1<<TWEN) ;MARK 1 /// MARK 1 //// MARK 1 /// MARK 1 //// MARK 1 /// MARK 1 //// |
42 | out TWCR, r16 |
43 | |
44 | wait2: ;Wait for TWINT Flag set. This indicates that the SLA+W has been transmitted, and ACK/NACK has been received. |
45 | in r16,TWCR |
46 | sbrs r16,TWINT |
47 | rjmp wait2 |
48 | |
49 | |
50 | ldi r16, 0b11011101 ; daten reinladen |
51 | out TWDR, r16 |
52 | ldi r16, (1<<TWINT) | (1<<TWEN) |
53 | out TWCR, r16 |
54 | |
55 | wait3: |
56 | in r16,TWCR |
57 | sbrs r16,TWINT |
58 | rjmp wait3 |
59 | |
60 | |
61 | ldi r16, (1<<TWINT) |(1<<TWSTO) | (1<<TWEN) ; STOP condition senden |
62 | out TWCR, r16 |
63 | |
64 | rcall wait |
65 | rjmp loop |
66 | |
67 | wait: |
68 | ldi r17,255 |
69 | ws1: |
70 | ldi r18,255 |
71 | ws2: |
72 | dec r18 |
73 | brne ws2 |
74 | dec r17 |
75 | brne ws1 |
76 | ret |
und den slave Receiver
1 | .include "m8def.inc" |
2 | |
3 | iniatall: |
4 | |
5 | ldi r16, LOW(RAMEND) |
6 | out SPL, r16 |
7 | ldi r16, HIGH(RAMEND) |
8 | out SPH, r16 |
9 | |
10 | ldi r16,255 |
11 | out DDRd,r16 |
12 | |
13 | |
14 | ldi r16, 0<<TWPS1 | 0<<TWPS0 |
15 | out TWSR,r16 |
16 | |
17 | ldi r16,255 |
18 | out TWBR,r16 |
19 | |
20 | ldi r16,0b11001101 |
21 | out TWAR,r16 |
22 | |
23 | |
24 | |
25 | loop: |
26 | ldi r16, 1<<TWEA | 1<<TWEN |
27 | out TWCR,r16 |
28 | |
29 | wait1: ;Wait for TWINT Flag set. This indicates that the START condition has been transmitted |
30 | in r16,TWCR |
31 | sbrs r16,TWINT |
32 | rjmp wait1 |
33 | |
34 | rjmp match |
35 | |
36 | rjmp loop |
37 | |
38 | match: |
39 | ldi r16,255 |
40 | out portd,r16 |
41 | rjmp match |
In dem Transmitter code ist die stelle "MARK1" zu finden .... da muss die adresse des anzusprechenden µc´s rein oder ? ich wollte erstmal nur den portb des atmega8 auf high stellen sobald er merkt das er über twi angesprochen wird aber das funzt alles nicht :( kann mir einer veraten was ich falsch mache ?
Hi >Mag mit keiner helfen ? Nicht gleich weinen. Ich habe dir mal Routinen für einen Master von mir angehängt. Versuche dich mal rein zu finden. An deiner Stelle würde ich als Slave erst mal einen einfachen I2C-IC, wie PCF8574 nehmen. Erst wenn du den als Master korrekt ansprechen kannst, lohnt es sich mit dem Slave weiter zu machen. So wie du es angehst hast du zwei Baustellen. Und du weisst nicht auf welcher Seite es klemmt. MfG Spess
Das ist Gut denn ich habe in dem ganzen Datenblatt keine Infos zum Register TWSB gefunden... war wahrscheinlich wieder zu dämlich:D... ich habe zwar mitbekommen das sich da der zustand des buses befindet aber wusste nich welcher Wert was bedeutet???? naja mit dem informationen in deinem Routine Programm oben kann ich eine Menge anfangen und werde sie jetzt einmal in mein Programm einbauen, den mitlerweile bekomme ich nun nach 2 Tagen fummeln meinen wert vom atmega 32 auf den Atmega8 :)
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.