Hallo, ich habe zwei PIC16F873. Einer davon soll als Master arbeiten und einer als Slave. Master: ======= void i2c_test() { SEN = 1; // Bus übernehmen while (SSPIF == 0); // warten bis der Bus übernommen wurde SSPIF = 0; // Bit zurücksetzen SSPBUF = 0b.0100.1110 & 0xFE; // an Adresse 0b.0100.1110 schreiben while (SSPIF == 0); // warten bis ein ACK kommt SSPIF = 0; // Bit zurücksetzen SSPBUF = 'a'; // ein 'a' schreiben while (SSPIF == 0); // warten bis ein ACK kommt SSPIF = 0; // Bit zurücksetzen PEN = 1; // Bus wieder freigeben while (SSPIF == 0); // warten bis der Bus freigegeben wurde SSPIF = 0; // Bit zurücksetzen } void main(void) { ... // alle analogen Eingänge auf digital umstellen ADCON1 = 7; // Die analogen Eingänge werden als digitale Eingänge // genutzt. // RA0 bis RA3 sind externe Eingänge der originalen Platine zur // Motoransteuerung // RA4 und RA5 sind UNBELEGTE Pins TRISA = 0b.1111.1111; // Alle Pins des Ports A sind als Eingänge geschaltet. // RB1 und RB2 sind die Ausgänge um die Richtung der beiden Motoren zu steuern // RB0, RB3 bis RB7 sind UNGENUTZTE Pins TRISB = 0b.0000.0000; // Alle Pins des Ports B sind als Ausgänge geschaltet. PORTB = 0b.0000.0000; // Alle Pins des Port B auf low schalten // RC0 und RC5 sind ungenutzte Pins // RC1 und RC2 sind PWM-Ausgänge zur Geschwindigkeitsregelung der Motoren // RC3 und RC4 sind I2C-Leitungen // RC6 ist der serielle Ausgang // RC7 ist der serielle Eingang TRISC = 0b.1001.1000; // Alle Pins bis auf RC3, RC4 und RC7 als Ausgänge definiert // RC3 = I2C, RC4 = I2C PORTC = 0b.0000.0000; // Alle Pins des Port C auf low schalten delay100(40); // I2C einstellen und aktivieren SSPADD = 0b.0000.1100; // Teiler von 12 -> i1c-takt von 385kHz SSPCON = 0b.0000.1000; // I2C master mode SSPEN = 1; PEIE = 1; // Peripheral Interrupt Enable bit RCIE = 1; // USART Receive Interrupt Enable bit GIE = 1; // global interrupt enable erasebuffer(); while(1) { i2c_test(); } } Slave: ====== #pragma origin 4 // Der folgende Code steht ab Adresse 4 interrupt int_handler(void) { int_save_registers // W, STATUS (und PCLATH) retten char sv_FSR = FSR; // save FSR if required //Interrupt from MSSP (I2C)-module if(SSPIF) { SSPIF=0; //Reset interrupt from MSSP-module. char x = SSPBUF; PORTB.0 = 1; PORTB.1 = 1; PORTB.3 = 1; } FSR = sv_FSR; // restore FSR if saved int_restore_registers // W, STATUS (und PCLATH) Wiederherstellen } void main(void) { // alle analogen Eingänge auf digital umstellen ADCON1 = 7; // Die analogen Eingänge werden als digitale Eingänge // genutzt. // RA0, RA3 und RA4 werden als Eingänge genutzt TRISA = 0b.1111.1111; // Alle Pins des Ports A sind als Eingänge geschaltet. // RB0, RB1 und RB3 sind Ausgänge, die auf low geschaltet werden // RB2, RB5, RB6 und RB7 sind Eingänge TRISB = 0b.1110.0100; PORTB = 0b.0000.0000; // RC2 ist ein Eingang // RC3 und RC4 sind für I2C // RC5 und RC6 ist ein Ausgang TRISC = 0b.0001.1100; PORTC = 0b.0000.0000; // Alle Pins des Port C auf low schalten // I2C einstellen und aktivieren SSPADD = 0x40; // Teiler von 12 -> i1c-takt von 385kHz SSPCON = 0b.0011.0110; // I2C slave mode SSPEN = 1; PEIE = 1; // Peripheral Interrupt Enable bit SSPIE = 1; // Synchronous Serial Port Interrupt Enable bit GIE = 1; //global interrupt enable SSPIF = 0; // clear SSPIF interrupt flag while(1) { } } Wenn alles funktionieren würde, dann würde zumindest erstmal die Interrupt-Routine des Slave aufgerufen. Dort sollten dann die Ausgänge RB0, RB1 und RB2 auf high gezogen werden. Das passiert aber leider nicht. Hat evtl. jemand eine Idee was ich falsch mache? Ich bin schon wieder ein bißchen verzweifelt. mfg Sebastian
Am Slave hast Du in SSPADD etwas abgelegt. Du meinst, es sei die Geschwindigkeit, der PIC meint, es sei seine I2C-Adresse. Das paßt nicht. Nur der Master setzt die Geschwindigkeit, der Slave setzt seine Adresse (0b.0100.1110).
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.