Unterschiede
Hier werden die Unterschiede zwischen zwei Versionen angezeigt.
Beide Seiten der vorigen Revision Vorhergehende Überarbeitung Nächste Überarbeitung | Vorhergehende Überarbeitung | ||
microcontrollertechnik:11_i2c_schnittstelle [2021/06/23 12:51] tfischer |
microcontrollertechnik:11_i2c_schnittstelle [2024/08/29 19:37] (aktuell) mexleadmin |
||
---|---|---|---|
Zeile 1: | Zeile 1: | ||
- | ====== | + | ====== |
<WRAP group> | <WRAP group> | ||
<WRAP column 30%> | <WRAP column 30%> | ||
Zeile 9: | Zeile 9: | ||
- wissen wie die Kommunikation zwischen I2C Master und Slave funktioniert | - wissen wie die Kommunikation zwischen I2C Master und Slave funktioniert | ||
+ | Im Video wird eine Library für die Kommunikation verwendet. Wir werden in untenstehenden Beispiel die Register selbst schreiben. | ||
</ | </ | ||
==== Video ==== | ==== Video ==== | ||
+ | {{youtube> | ||
+ | |||
+ | <WRAP hide> | ||
{{youtube> | {{youtube> | ||
+ | </ | ||
</ | </ | ||
+ | ==== Statemachine für Datenpaket ==== | ||
- | ==== Dokumentation von Atmel ==== | + | ++++ Statemachine der I2C Kommunikation | === Statemachine der I2C Kommunikation |
- | * [[https:// | ||
- | * [[https:// | ||
- | * alternative Implementierung von [[https:// | ||
- | |||
- | \\ | ||
- | |||
- | ==== Übersicht über die am häufigsten verwendeten, | ||
- | |||
- | <WRAP group>< | ||
- | === USART === | ||
< | < | ||
- | < | + | < |
</ | </ | ||
- | {{drawio> | + | {{drawio> |
</ | </ | ||
- | * Keine gibt Takt vor. \\ Es sind gleichberechtigte Kommunikationspartner (siehe <imgref BildNr0> | ||
- | * Jeder darf zu jederzeit senden. | ||
- | * Senden und Empfangen geschieht über zwei separate Leitungen. | ||
- | * Kommunikation ist nur zwischen zwei Geräten möglich. \\ Ein weiterer Slave würde eine weiteren U(S)ART-Bus benötigen. | ||
- | </ | + | ++++ |
- | === I2C === | + | |
- | < | + | |
- | < | + | |
- | </ | + | |
- | {{drawio> | + | |
- | </ | + | |
- | * Master gibt Takt vor (siehe <imgref BildNr1> | + | |
- | * Slave darf nur zu bestimmten Zeiten senden und nur, wenn der Master dies anfordert. | + | |
- | * Senden und Empfangen geschieht über die gleiche Leitung. | + | |
- | * Alle Slaves hören am gleichen Bus mit und schreiben auf die gleiche Leitung. | + | |
- | * Jeder Slave muss anhand der Signale überprüfen, | + | |
- | + | ||
- | </ | + | |
- | === SPI === | + | |
- | < | + | |
- | < | + | |
- | </ | + | |
- | {{drawio> | + | |
- | </ | + | |
- | * Master gibt Takt vor (siehe <imgref BildNr2> | + | |
- | * Slave darf nur zu bestimmten Zeiten senden und nur, wenn der Master dies anfordert. | + | |
- | * Senden und Empfangen geschieht über zwei separate Leitungen. | + | |
- | * Alle Slaves hören auf der gleichen Leitung mit und schreiben auf die gleiche Leitung. | + | |
- | * Der gewünschte Slave wird über die __S__lave __S__elect Leitung ausgewählt. | + | |
- | + | ||
- | </ | + | |
+ | ==== I2C in Kürze und Zeitverlaufsdiagramm ==== | ||
< | < | ||
< | < | ||
</ | </ | ||
- | {{drawio> | + | {{drawio> |
</ | </ | ||
- | + | === Übertragung | |
- | ==== Statemachine für Datenpaket | + | |
- | + | ||
- | ++++ Statemachine der I2C Kommunikation | === Statemachine der I2C Kommunikation === | + | |
- | + | ||
- | < | + | |
- | < | + | |
- | </ | + | |
- | {{drawio> | + | |
- | </ | + | |
- | + | ||
- | ++++ | + | |
- | + | ||
- | ==== I2C in Kürze und Zeitverlaufsdiagramm ==== | + | |
- | + | ||
- | **Übertragung**\\ | + | |
Für die I2C Übertragung " | Für die I2C Übertragung " | ||
D.h. während der Datenübertragung bleibt die Datenleitung bei SCL=High konstant. \\ | D.h. während der Datenübertragung bleibt die Datenleitung bei SCL=High konstant. \\ | ||
Zeile 100: | Zeile 52: | ||
< | < | ||
</ | </ | ||
- | {{drawio> | + | {{drawio> |
</ | </ | ||
Zeile 112: | Zeile 64: | ||
< | < | ||
</ | </ | ||
- | {{drawio> | + | {{drawio> |
</ | </ | ||
Zeile 125: | Zeile 77: | ||
TWCR = (1<< | TWCR = (1<< | ||
// to set the following state: | // to set the following state: | ||
- | | (1<< | + | | (1<< |
| (1<< | | (1<< | ||
Zeile 142: | Zeile 94: | ||
< | < | ||
</ | </ | ||
- | {{drawio> | + | {{drawio> |
</ | </ | ||
Zeile 169: | Zeile 121: | ||
</ | </ | ||
</ | </ | ||
- | |||
- | |||
</ | </ | ||
Zeile 181: | Zeile 131: | ||
< | < | ||
</ | </ | ||
- | {{drawio> | + | {{drawio> |
</ | </ | ||
Zeile 194: | Zeile 144: | ||
TWCR = (1<< | TWCR = (1<< | ||
// to set the following state: | // to set the following state: | ||
- | | (1<< | + | | (1<< |
| (0<< | | (0<< | ||
</ | </ | ||
Zeile 204: | Zeile 154: | ||
===== Software ===== | ===== Software ===== | ||
+ | ==== einfache Anwendung - nur Polling ==== | ||
- | Files: | + | Im ersten Schritt ist im folgenden eine einfache Anwendung dargestellt. \\ |
- | * {{microcontrollertechnik: | + | Bei dieser werden Schalterstellungen vom Master an den Slave übertragen. |
- | * {{microcontrollertechnik: | + | |
- | * {{microcontrollertechnik: | + | |
- | * {{microcontrollertechnik: | + | |
- | * {{microcontrollertechnik: | + | |
- | ==== TWI Master ==== | + | --> I. Vorarbeiten |
- | <WRAP> | + | Laden Sie die Datei {{microcontrollertechnik: |
- | <sxh c; first-line: 1> | + | In ihr finden Sie die Simulation als '' |
+ | |||
+ | <-- | ||
+ | |||
+ | --> II. Analyse des fertigen Programms # | ||
+ | - Initialisieren des Programms | ||
+ | - Öffnen Sie SimulIDE und öffnen Sie dort mittels {{microcontrollertechnik: | ||
+ | - In der Simulation finden Sie unten links 8 Dip-Schalter, | ||
+ | - Die hex Files sollten bereits in der simulation verlinkt sein, sodass diese nach dem Start auch lauffähig sei soll. \\ Falls nicht finden Sie die hex Files unter '' | ||
+ | - Wenn Sie die Simulation starten, sehen Sie oben rechts im Logic Analyzer den Verlauf der Signale auf SDA (Daten) und SCL (Clock, also Takt). | ||
+ | - Sobald die Stopp-Bedingung erfüllt ist (positive Flanke auf SDA, wenn SCL bereits High ist), wird die Simulation automatisch gestoppt. \\ Dies geschieht, da im Logic Analyzer als Trigger '' | ||
+ | - Sie können hier einige Dinge analysieren: | ||
+ | - Was passiert in den I2C Registern ('' | ||
+ | - Was wird übertragen? | ||
+ | - Das Programm zu diesem Hexfile soll nun erstellt werden | ||
+ | |||
+ | <-- | ||
+ | |||
+ | --> III. Code in Microchip Studio # | ||
+ | |||
+ | <fs x-large> | ||
+ | |||
+ | <WRAP group>< | ||
/* ---------------------------------------------------------------------------- | /* ---------------------------------------------------------------------------- | ||
- | + | | |
| | ||
| | ||
- | |||
- | | ||
| | ||
- | | + | Dateiname : |
- | | + | |
- | | + | Autoren : Tim Fischer |
+ | |||
+ | | ||
+ | |||
+ | | ||
+ | |||
+ | | ||
| | ||
- | Version | + | Software : Entwicklungsumgebung: |
+ | C-Compiler: AVR/GNU C Compiler 5.4.0 | ||
| | ||
- | Hardware: | + | |
- | + | ||
- | | + | |
- | C-Compiler: AVR/GNU C Compiler 5.4.0 | + | |
- | + | ||
- | Funktion : TBD | + | |
- | + | ||
- | | + | |
- | + | ||
- | | + | |
- | + | ||
- | | + | |
- | + | ||
- | Fuses im uC: | + | |
- | + | ||
- | | + | |
- | + | ||
| | ||
+ | | ||
+ | | ||
+ | | ||
+ | Dabei zählt ein gedrückter Schalter (= hellgrün) als logisches High Signal | ||
+ | | ||
+ | | ||
+ | | ||
+ | Fuses im uC : keine | ||
+ | |||
// ----------------------------------------------------------------------------*/ | // ----------------------------------------------------------------------------*/ | ||
- | + | | |
// Deklarationen ============================================================== | // Deklarationen ============================================================== | ||
+ | | ||
+ | // Festlegung der Quarzfrequenz | ||
+ | #define F_CPU 8000000UL // | ||
+ | #define F_SCL | ||
- | // Festlegung der Quarzfrequenz | ||
- | #define F_CPU 8000000UL // | ||
- | #define F_SCL 40000L // Baudrate von 100 kHz | ||
- | |||
// Include von Header-Dateien | // Include von Header-Dateien | ||
- | #include < | ||
#include < | #include < | ||
- | #include < | ||
#include < | #include < | ||
+ | |||
// Konstanten | // Konstanten | ||
- | #define SET_BIT(PORT, BIT) ((PORT) |= (1 << (BIT))) // Port-Bit Zustand setzen | + | #define SET_BIT(BYTE, BIT) ((BYTE) |= (1 << (BIT))) // Bit Zustand |
- | #define CLR_BIT(PORT, BIT) ((PORT) &= ~(1 << (BIT))) // Port-Bit Zustand loeschen | + | #define CLR_BIT(BYTE, BIT) ((BYTE) &= ~(1 << (BIT))) // Bit Zustand |
- | #define TGL_BIT(PORT, BIT) ((PORT) ^= (1 << (BIT))) // Port-Bit Zustand wechseln (toggle) | + | #define TGL_BIT(BYTE, BIT) ((BYTE) ^= (1 << (BIT))) // Bit Zustand |
+ | |||
+ | #define SET_ALL_PULLUPS (0xFF) // | ||
+ | #define INVERING_MASK (0xFF) // | ||
+ | #define TWI_ADRESS (0b0001010) // | ||
// | // | ||
Zeile 271: | Zeile 240: | ||
void I2C_transmitDataOrAddress(char Data); | void I2C_transmitDataOrAddress(char Data); | ||
void I2C_transmitStop(); | void I2C_transmitStop(); | ||
- | void I2C_Data(); | + | |
- | + | uint8_t TWI_Address = | |
- | uint8_t TWI_Address = 0b0001010; | + | uint8_t TWI_Data |
- | uint8_t TWI_Data = | + | |
- | + | ||
int main(void) | int main(void) | ||
{ | { | ||
- | cli (); // Interrupt | + | PORTB = SET_ALL_PULLUPS; // Pull-up Widerstände an Port B aktivieren |
- | SET_BIT(DDRD, | + | while (1) |
- | TGL_BIT(PORTD, | + | { |
- | I2C_Init(); | + | I2C_Init(); |
- | + | I2C_transmitStart(); | |
- | + | I2C_transmitDataOrAddress((TWI_Address<< | |
- | while (1) | + | TWI_Data = PINB^INVERING_MASK; // Lese Tasterstellungen ein. Invertiere jedes Bit |
- | { | + | I2C_transmitDataOrAddress(TWI_Data); |
- | TGL_BIT(PORTD, | + | I2C_transmitStop(); |
- | I2C_Init(); | + | _delay_us(1); // erst durch den Delay ist ein Triggern im Simulide möglich |
- | TGL_BIT(PORTD, | + | } |
- | I2C_transmitStart(); | + | |
- | TGL_BIT(PORTD, | + | |
- | I2C_transmitDataOrAddress((TWI_Address<< | + | |
- | TGL_BIT(PORTD, | + | |
- | I2C_transmitDataOrAddress(TWI_Data);// | + | |
- | TGL_BIT(PORTD, | + | |
- | I2C_transmitStop(); | + | |
- | TGL_BIT(PORTD, PORTD1); // Debug Ausgang ansprechen -> Wechsel auf Low | + | |
- | _delay_us(1); | + | |
- | + | ||
- | } | + | |
} | } | ||
+ | |||
///////////////////////////////////////// | ///////////////////////////////////////// | ||
// I2C Initialisierung | // I2C Initialisierung | ||
Zeile 308: | Zeile 265: | ||
void I2C_Init() | void I2C_Init() | ||
{ | { | ||
- | TWSR = CLR_BIT(TWSR, | + | |
- | TWSR = CLR_BIT(TWSR, | + | CLR_BIT(TWSR, |
- | TWCR = 0; // | + | TWCR = 0; // Control Register zurücksetzen |
- | TWBR = ((F_CPU/ | + | TWBR = ((F_CPU/ |
} | } | ||
+ | |||
///////////////////////////////////////// | ///////////////////////////////////////// | ||
// I2C Startbit senden | // I2C Startbit senden | ||
Zeile 319: | Zeile 276: | ||
void I2C_transmitStart() | void I2C_transmitStart() | ||
{ | { | ||
- | TWCR = (1<<TWSTA)|(1<< | + | |
- | while (!(TWCR & (1<< | + | while (!(TWCR & (1<< |
} | } | ||
- | + | ||
+ | |||
///////////////////////////////////////// | ///////////////////////////////////////// | ||
// I2C Adressbyte/ | // I2C Adressbyte/ | ||
///////////////////////////////////////// | ///////////////////////////////////////// | ||
- | void I2C_transmitDataOrAddress(char Data) | + | void I2C_transmitDataOrAddress(char Data) |
{ | { | ||
- | TWDR = Data; | + | |
- | TWCR = (1<< | + | TWCR = (1<< |
- | while (!(TWCR & (1<< | + | while (!(TWCR & (1<< |
} | } | ||
+ | |||
///////////////////////////////////////// | ///////////////////////////////////////// | ||
// I2C Stoppbit senden | // I2C Stoppbit senden | ||
Zeile 339: | Zeile 296: | ||
void I2C_transmitStop() | void I2C_transmitStop() | ||
{ | { | ||
- | TWCR=(1<< | + | |
- | while (!(TWCR & (1<< | + | |
- | // | + | |
} | } | ||
- | |||
</ | </ | ||
- | </ | + | </ |
+ | \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ | ||
+ | '' | ||
+ | \\ \\ | ||
+ | - Hier wird die Frequenz des Quarz direkt eingestellt. | ||
+ | - Weiterhin wird eine Konstante für die I2C Frequenz definiert \\ \\ | ||
+ | - Die Header-Dateien und die Bit-ändernden Makros entsprechen denen der letzten Programme. \\ \\ \\ \\ \\ \\ | ||
+ | - Die weiteren Konstanten sind: | ||
+ | - Konstante für die Pullups | ||
+ | - Konstante für die Invertierung der Schalterstellungen | ||
+ | - Konstante für die I2C Adresse | ||
+ | - Zwei globale Variablen beinhalten die I2C Adresse und die Daten \\ \\ | ||
- | ==== TWI Slave ==== | + | '' |
+ | - es werden zunächst die Pull-up Widerstände aller Pins an Port B aktiviert, um die Schalter einlesen zu können | ||
+ | - in der Haupschleife läuft: | ||
+ | - Zu Beginn eine Iitialisierung der I2C Schnittstelle. Die wiederholte Initialisierung vermeidet Probleme der I2C Zustandsmaschine. | ||
+ | - Als nächstes wird die startende Flanke gesendet. | ||
+ | - Das erste Byte auf dem I2C Bus ist die Adressebyte. Dieses setzt sich aus der Adresse und einem Bit zusammen, welches angibt, ob der Slave nur zuhören ('' | ||
+ | - Nun wird der Zustand das Port B als I2C Daten eingelesen. | ||
+ | - Diese werden per I2C übertragen. | ||
+ | - Und zum Schluss wird das Stopp Bit gesendet \\ \\ | ||
- | < | + | '' |
- | <sxh c; first-line: 1> | + | - Durch das Zurücksetzen der Bits '' |
- | /* ---------------------------------------------------------------------------- | + | - Auch das Kontrollregister wird zurückgesetzt |
+ | | ||
+ | '' | ||
+ | | ||
+ | | ||
+ | '' | ||
+ | | ||
+ | | ||
+ | | ||
+ | '' | ||
+ | | ||
+ | | ||
+ | </ | ||
+ | |||
+ | <fs x-large> | ||
+ | |||
+ | <WRAP group>< | ||
+ | /* ---------------------------------------------------------------------------- | ||
+ | | ||
| | ||
| | ||
+ | | ||
+ | | ||
+ | | ||
+ | | ||
+ | | ||
+ | | ||
+ | | ||
+ | | ||
+ | |||
+ | | ||
+ | | ||
+ | | ||
+ | | ||
+ | |||
+ | | ||
- | Dateiname : I2C_SimpleMaster.c | + | Displayanzeige : keine |
- | Autoren | + | Tastenfunktion : Die Tastenstellung der Dip-Schalter an Port B werden als Wert über I2C weitergegeben. |
+ | Dabei zählt ein gedrückter Schalter | ||
- | Datum | + | Jumperstellung : |
- | + | ||
- | | + | |
- | + | ||
- | | + | |
- | + | ||
- | | + | |
- | C-Compiler: AVR/GNU C Compiler 5.4.0 | + | |
- | + | ||
- | | + | |
+ | Fuses im uC : keine | ||
| | ||
+ | |||
// ----------------------------------------------------------------------------*/ | // ----------------------------------------------------------------------------*/ | ||
- | + | | |
// Deklarationen ============================================================== | // Deklarationen ============================================================== | ||
- | + | | |
// Festlegung der Quarzfrequenz | // Festlegung der Quarzfrequenz | ||
- | #define F_CPU 16000000UL | + | #define F_CPU 8000000UL // |
- | #define F_SCL 10000L | + | #define F_SCL 100000L // Baudrate von 100 kHz |
+ | |||
// Include von Header-Dateien | // Include von Header-Dateien | ||
#include < | #include < | ||
+ | |||
// Konstanten | // Konstanten | ||
- | #define SET_BIT(PORT, BIT) ((PORT) |= (1 << (BIT))) // Port-Bit Zustand setzen | + | #define SET_BIT(BYTE, BIT) ((BYTE) |= (1 << (BIT))) // Bit Zustand |
- | #define CLR_BIT(PORT, BIT) ((PORT) &= ~(1 << (BIT))) // Port-Bit Zustand loeschen | + | #define CLR_BIT(BYTE, BIT) ((BYTE) &= ~(1 << (BIT))) // Bit Zustand |
- | #define TGL_BIT(PORT, BIT) ((PORT) ^= (1 << (BIT))) // Port-Bit Zustand wechseln (toggle) | + | #define TGL_BIT(BYTE, BIT) ((BYTE) ^= (1 << (BIT))) // Bit Zustand |
+ | #define SET_ALL_TO_OUT (0xFF) // | ||
+ | #define TWI_ADRESS (0b0001010) // | ||
+ | #define TWI_ADRESS_MASK (0b0001010) // | ||
+ | |||
// | // | ||
void I2C_Init(); | void I2C_Init(); | ||
void I2C_setAddress(char Address); | void I2C_setAddress(char Address); | ||
char I2C_readData(); | char I2C_readData(); | ||
- | + | ||
- | uint8_t TWI_Address = | + | uint8_t TWI_Address |
- | uint8_t TWI_AddressMask = 0b11111110; | + | uint8_t TWI_AddressMask |
+ | |||
int main(void) | int main(void) | ||
{ | { | ||
- | DDRC= 0xFF; // Auf DDRC die Daten ausgeben | + | DDRB= SET_ALL_TO_OUT; // Auf DDRC die Daten ausgeben |
- | I2C_setAddress(TWI_Address); | + | I2C_setAddress(TWI_Address); |
- | + | | |
while (1) | while (1) | ||
{ | { | ||
- | PORTC | + | PORTB = I2C_readData(); |
} | } | ||
} | } | ||
+ | |||
////////////////////////////////////////////////// | ////////////////////////////////////////////////// | ||
// Setzen der I2C Adresse auf die der Slave hört | // Setzen der I2C Adresse auf die der Slave hört | ||
////////////////////////////////////////////////// | ////////////////////////////////////////////////// | ||
- | void I2C_setAddress(char Address) | + | void I2C_setAddress(char Address) |
{ | { | ||
- | TWAR = (Address<< | + | |
- | TWAMR= TWI_AddressMask; | + | TWAMR= TWI_AddressMask; |
- | TWCR = (1<< | + | TWCR = (1<< |
} | } | ||
+ | |||
////////////////////////////////////////////////// | ////////////////////////////////////////////////// | ||
// Auslesen der übermittelten Daten | // Auslesen der übermittelten Daten | ||
////////////////////////////////////////////////// | ////////////////////////////////////////////////// | ||
- | char I2C_readData() | + | char I2C_readData() |
{ | { | ||
- | while (!(TWCR & (1<< | + | |
- | TWCR = (1<< | + | return TWDR; // übermittle Daten |
- | return TWDR; // übermittle Daten | + | |
} | } | ||
- | |||
</ | </ | ||
- | </ | + | </ |
+ | \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ \\ | ||
+ | '' | ||
+ | \\ \\ | ||
+ | - Hier wird die Frequenz des Quarz direkt eingestellt. | ||
+ | - Weiterhin wird eine Konstante für die I2C Frequenz definiert \\ \\ | ||
+ | - Die Header-Dateien und die Bit-ändernden Makros entsprechen denen der letzten Programme. \\ \\ \\ \\ | ||
+ | - Die weiteren Konstanten sind: | ||
+ | - Konstante für die das Setzen der Pins als Ausgang | ||
+ | - Konstante für die I2C Adresse | ||
+ | - Konstante für die Maskierung der Adresse \\ \\ \\ \\ \\ | ||
+ | - Zwei globale Variablen beinhalten die I2C Adresse und die Maske für die eingelesene Adresse \\ \\ | ||
+ | |||
+ | '' | ||
+ | |||
+ | - Es werden alle Pins an Port B als Ausgang geschalten | ||
+ | - Die I2C Adresse, auf welche der Slave hört, wird gesetzt \\ \\ | ||
+ | - In der Haupschleife läuft nur das Setzen des Port B anhand der eingelesenen I2C Daten \\ \\ \\ \\ \\ | ||
+ | |||
+ | '' | ||
+ | - Die Adresse wird in das Adressbyte geschrieben. | ||
+ | - Die Adressmaske wird in das Maskenbyte geschrieben. Durch die Maske lässt sich ein Slave auch mit verschiedenen Adressen ansprechen, da die Maske angibt, welche Bits nicht berücksichtigt werden sollen (mit '' | ||
+ | - Im Kontrollregister wird die " | ||
+ | '' | ||
+ | - Hier wird solange gewartet, bis I2C Daten vorliegen | ||
+ | - Nach dem Ändern des Konrollregisters muss die Abarbeitung abgewartet werden. Dies ist daran zu erkennen, das '' | ||
+ | |||
+ | </ | ||
+ | |||
+ | <-- | ||
+ | |||
+ | |||
+ | ==== komplexere Anwendung - mit Interrupt ==== | ||
+ | |||
+ | Als Beispiel wurde hier die Temperaturmessung aus Lektion 8 gewählt. \\ | ||
+ | Das Projekt und die Simulation ist hier zu finden {{microcontrollertechnik: | ||
+ | |||
+ | Bitte nutzen Sie diese als Vorlage, wen Sie eine I2C Schnittstelle implementieren wollen. Da in diesem Programmstand alles über Interrupts läuft, können auch weitere Funktionen abgearbeitet werden. | ||
+ | |||
+ | ===== weiterführende Unterlagen ===== | ||
+ | |||
+ | Die detaillierte Beschreibung zu I2C findet sich in des {{microcontrollertechnik: | ||
+ | |||
+ | ==== Bibliotheken ==== | ||
+ | * TWI Module as I2C Master (AVR315): | ||
+ | * Application Note: {{microcontrollertechnik: | ||
+ | * Library und Beispielcode: | ||
+ | * TWI Module as I2C Slave (AVR311): | ||
+ | * Application Note: {{microcontrollertechnik: | ||
+ | * Library und Beispielcode: | ||
+ | * alternative und schlanke Implementierung des Slaves von [[https:// | ||
+ | ==== Beispiele ==== | ||
- | ===== Beispiele ===== | + | * In Simulide ist eine Umsetzung von Software I2C zu finden: '' |
+ | * Eine vollständige Implementierung des Codes für den I2C Master ist in der Library von Peter Fleury zu finden: [[http:// | ||
+ | * Eine Implementierung eines [[Software I2C Slave]], also eines I2C an einem beliebigen Pin durch Bitmaipulation, | ||
- | * Simulide: '' | + | ==== Beschreibung ==== |
- | * Software I2C: | + | |
- | * Library von Peter Fleury: [[http:// | + | |
- | * [[Software I2C Slave]] | + | |
+ | Die " |