Autor Tema: Problemas con la comunicacion I2C entre pics  (Leído 3280 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado JJcorps

  • PIC12
  • **
  • Mensajes: 51
    • Proyectos de JJcorps
Problemas con la comunicacion I2C entre pics
« en: 04 de Mayo de 2006, 18:19:35 »
Hola tengo problemas con el i2c para comunicar un maestro con un esclavo,esta comunicacion hace lo siguiente el maestro pide informacion al esclavo el cual le responde con (0xA0)  el problema esta en que el maestro recibe siempre la señal (0xFF)  es decir todo a 1 es como si no pudiese poner niveles bajos en las lineas de comunicacion i2c.

Uso PIC16F877A tanto para el maestro como para el esclavo y la resistencia pull-up que uso para i2c es 2K2

CODIGO DEL MAESTRO
Código: [Seleccionar]
//////////////////////////////////////////////////
// I2C master                                   //
// PIC16F877A                                   //
//                                 PICmaster.C  //
// Crea una comunicacion entre varios PICS      //
// por i2c mandando lo leido al PC por el       //
// el puerto serie.                             //
//                                              //
// Realizado por Juan José Chica Barrera        //
//////////////////////////////////////////////////


#include <16f877A.h>
#fuses HS,NOWDT,NOPROTECT,PUT,BROWNOUT,NOLVP
#use delay(clock = 10000000)       // reloj 10MHz
/*
   Configuracion principal del I2C
   Modo Maestro
   Tasa de transferencia rapida, aunq puede tener problemas
   I2c se hace por harwdware pa eso lo tenemos en el
*/
#use i2c(MASTER,SDA=PIN_C4,SCL=PIN_C3,FAST,FORCE_HW)
/*
   Configuracion principal del puerto serie
   velocidad de 9600 baudios
   sin paridad
   con un bit de parada
*/
#use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7)



/*
   Rutina de ESCRITURA a un dispositivo conectado al i2c

   i2cdev --> Direccion del dispositvo
   i2cdat --> Dato que le quiero enviar
*/
void i2cw(int i2cdev, int i2cdat){

   i2c_start();                  // Inicializo comunicación I2C
   i2c_write(i2cdev);            // Envio Dirección de dispositivo I2C + R/W
   i2c_write(i2cdat);            // Envio byte a escribir
   i2c_stop();                   // Cierro comunicacion
}


/*
   Rutina de LECTURA a un dispositivo conectado al i2c

   i2cdev --> Direccion del dispositvo del que quiero leer
*/
int  i2cr(int i2cdev){           // Rutina de lectura I2C

   int r=0x00;

   i2c_start();
   i2c_write(i2cdev+1);
   r=i2c_read();
   i2c_stop();
   return(r);
}

unsigned int giro=80;
main()
{
     output_float(PIN_C3);         //I2C pin float
     output_float(PIN_C4);         //I2C pin float

     while(1)
     {
         //COMUNICACION CON EL ESCLAVO 1
         giro = i2cr(0x02);           //Leo del dispositivo esclavo y lo muestro por el puerto B
         printf("Prueba de i2c %U\n\r",giro);  //Lo muestro por el puerto serie
         delay_ms(1000);            //Retardo de 1 segundo
         giro = 0;                    //Reseteo la variable

     }


}

CODIGO DEL ESCLAVO
Código: [Seleccionar]
//////////////////////////////////////////////////
// I2C slave                                    //
// PIC16F877A                                   //
//                                 PICslave1.C  //
// Crea una comunicacion entre varios PICS      //
// siendo una comunicacion muy basica           //
//                                              //
// Realizado por Juan José Chica Barrera        //
//////////////////////////////////////////////////

#include <16f877A.h>
#fuses HS,NOWDT,NOPROTECT,PUT,BROWNOUT,NOLVP
#use delay(clock = 10000000)       // reloj 10MHz
#use fast_io(B)                    // cambio rapido de estados en los puertos
/*
   Configuracion principal del I2C
   Modo Esclavo
   Direccion 0b00000010  = 0x02  (Son 7 bits el bit que se desprecia es el de menor peso por tanto es 1)
   Tasa de transferencia rapida, aunq puede tener problemas
   I2c se hace por harwdware pa eso lo tenemos en el chip
*/

#use i2c(SLAVE,SDA=PIN_C4,SCL=PIN_C3,ADDRESS=0x02,FAST,FORCE_HW)

byte DATA = 69;  // antes era 0x0F

//Interrupcion provocada cuando algo ocurre en el i2c
#INT_SSP
void ssp_interupt (){
     output_b(0xFF);
     if(i2c_poll()){               //Si tenemos algo en el buffer de entrada
           output_b(i2c_read());   //lo mostramos por el puerto B
     }
     else{

           i2c_write(0xA0);    //Si no esq el master quiere q le mandemos la info
                                   //solamente la parte baja de un entero (1 byte)
           output_b(0x00);
     }
}

void main (){

     set_tris_b(0x00);             //RB 7-0:OUT

     output_float(PIN_C3);         //I2C pin float
     output_float(PIN_C4);         //I2C pin float

     output_b(0);        //en un principio esta apagado

     enable_interrupts(GLOBAL);      //Activamos las interrupciones
     enable_interrupts(INT_SSP);     //Activamos la interrupcion para el i2c

   while (1);  //bucle infinito
}


Envio los datos por el puerto serie para verlos en condiciones, uso el CSS PICC.

¿alguna idea de donde puede estar el error?
« Última modificación: 10 de Mayo de 2006, 16:27:50 por JJcorps »

Desconectado jfh900

  • Moderadores
  • DsPIC30
  • *****
  • Mensajes: 3595
Re: Problemas con la comunicacion I2C entre pics
« Respuesta #1 en: 05 de Mayo de 2006, 04:25:11 »
Visto tus programas por encima veo dos errores:

1º Cuando haces la lectura desde el maestro la dirección a enviar es i2cdev+1 para indicar al esclavo que vamos a proceder a leer.

2º La rutina de tratamiento de la interrupcion i2c es mas complicada ya que se pasan por varias fases, consulta el ejemplo de esclavo que trae el CCS creo que se llama ex_slave.c

Un saludo
* Cuando hables, procura que tus palabras sean mejores que el silencio.
* 'Todos somos ignorantes, lo que ocurre es que no todos ignoramos las mismas cosas.' Albert Einstein.
* No hay nada peor que un experto para evitar el progreso en un campo
* "La vida es como una novela. No importa que sea larga, sino que esté bien narrada" Seneca
* La vida no se vive por las veces que respiras, sino por los momentos que dejan sin aliento.
* Dios dijo: ∇·E=ρ/ε0 ; ∇·B=0 ; ∇xE=-dB/dt ; ∇xB= μ0ε0dE/dt..y la luz se hizo..!!..

Desde España Jesús

Desconectado JJcorps

  • PIC12
  • **
  • Mensajes: 51
    • Proyectos de JJcorps
Re: Problemas con la comunicacion I2C entre pics
« Respuesta #2 en: 06 de Mayo de 2006, 06:31:18 »
jfh900 gracias por lo de i2cdev+1 se me habia pasado, la funcion de la interrupcion que tra el codigo ex_slave.c es muy complicada mas que lo que he hecho yo.

Si alguien tiene la amabilidad de esplicarla seria de gran ayuda. pero de todas formas con mi funcion no funciona y queria saber porque.

Gracias

Desconectado JJcorps

  • PIC12
  • **
  • Mensajes: 51
    • Proyectos de JJcorps
Re: Problemas con la comunicacion I2C entre pics
« Respuesta #3 en: 10 de Mayo de 2006, 16:25:57 »
He estado haciendo pruebas al codigo y he sacao las siguientes conclusiones:

Funcionar funciona a veces, es decir q no siempre se muestra por el puerto serie 160 (lo que manda el esclavo) si no muestra este valor manda 255

Toqueteando un poco mas el 255 sale cuando el i2c_write(i2cdev+1) no consigue mandar la direccion del dispositivo correctamente.
No puede ser que aun este la interrupcion activa cuando se intenta comunicar otra vez con el dispositivo pq hay un delay de por medio de un segundo.

Si alguien tiene alguna idea que por favor que la comente.

GRACIAS