Zitat Zitat von robo_tom_24 Beitrag anzeigen
Hallo

Ich hab im Internet eine Software I²C Implementierung gefunden (-> MAIN: i.c HEADER:i2c_software_master.h)
Mein I²C Bus ist auf 3.3V ausgelegt und die Implementierung ist für den 5V Master. Hierfür hab ich externe Pull-Up Widerstände - somit muss ich die internen vom Master ja deaktivieren (auskommentieren):
Code:
/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
void sda_low()
{
	I2C_PORT 		&=  ~(1<<SDA);    			// internen Pull-Up aus
	I2C_DDR 		|=   (1<<I2C_DDR_REG_BIT);  // Pin von SDA als Ausgang

}
/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
void sda_high()
{
	I2C_DDR 		&= ~(1<<I2C_DDR_REG_BIT);  	// Pin von SDA als Eingang 
	//I2C_PORT 		|=  (1<<SDA);    			// internen Pull-Up an 
} 
/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
////////////////////////////////////////////////////////////////////////////////////////////

#define I2C_SCL_LOW		I2C_PORT &= ~(1 << SCL)	// Clock Low Output
#define I2C_SCL_HIGH	        I2C_PORT |=  (1 << SCL)	// Clock High Output
Ist das richtig so? Oder muss ich da im eigentlichen Programmcode noch ändern?
Ich kenne zwar den Prozessor nicht, im gezeigten Code kann ich aber nichts von Pullups erkennen. Ich sehe da nur Daten und Direction-Bits. Die Komentare scheinen mir falsch und machen auch keinen Sinn, die Pullups sind immer an, nur der Treiber wird an- und ausgeschaltet.

Was ich aber sehe, ist daß SCL und SDA unterschiedlich behandelt werden. SCL wird nicht über das Direction-Bit als "quasi Opencollector Ausgang" gesteuert, sondern direkt. Während man mit externen Pullups von wenigen k Ohm gegen 3,3V die internen Pullups von mehren 10k gegen 5V noch neutralisieren könnte, geht das so garnicht.

Was man aus diesen Macros aber sehen kann ist, das dieser Code in die Kategorie "works mostly" gehört. Sowohl SDA als auch SCL können und werden sowohl vom Master als auch vom Slave angesteuert. Bei SCL nennt man das Clock stretching. Wie das funktioniert, steht in der I2C Spec. Mit den gezeigten Macros für SCL läßt sich das nicht implementieren. Ich würde den Code daher nicht verwenden.

MfG Klebwax