Problema de detención del protocolo de comunicación i2C del software "MikroC for Pic"

-3

Trabajo con Pic16f688, y hago un i2C suave

MikroC for pic compiler no proporciona el código de funciones de sus bibliotecas

este es el código completo que uso para MCU

sbit   dataReady    at     PORTC.b1 ;
sbit   LEDup        at     PORTA.b0;
sbit   LEDdown      at     PORTA.b1;
sbit   LED          at     PORTC.b2;


// Software I2C connections
sbit Soft_I2C_Scl           at RA5_bit;
sbit Soft_I2C_Sda           at RA4_bit;
sbit Soft_I2C_Scl_Direction at TRISA5_bit;
sbit Soft_I2C_Sda_Direction at TRISA4_bit;

// End Software I2C connections

unsigned short int i=0;
unsigned short int Data[6]={0,0,0,0,0,0};
unsigned short int responce[5];
//########################################################################

void main()
{
  OSCTUNE.TUN4=1;
  OSCTUNE.TUN3=1;
  OSCTUNE.TUN2=1;
  OSCTUNE.TUN1=1;
  OSCTUNE.TUN0=1;
  OSCCON.SCS=1;
  OSCCON.IRCF0=0;
  OSCCON.IRCF1=0;
  OSCCON.IRCF2=1;
  UART1_Init(9600);
  Delay_ms(10);// Wait for UART module to stabilize

/*INTCON.INTE=0;
  INT0Enable=1;
  OPTION_REG.INTEDG=0;
  INTCON.GIE=1;
  INTCON.INTE=1;*/
  /*WDTCON.WDTPS3=0;
  WDTCON.WDTPS2=1;
  WDTCON.WDTPS1=1;
  WDTCON.WDTPS0=1;
  WDTCON.SWDTEN=1;*/
  ANSEL=0b00000000;
  CMCON0.CM0=1;
  CMCON0.CM1=1;
  CMCON0.CM2=1;
  ADCON0.VCFG=0;
  ADCON0.ADON=0;
  TRISC0_bit=0 ;
  TRISC1_bit=1 ;//dataReady
  TRISC2_bit=0 ;
  TRISC3_bit=0 ;
  TRISA0_bit=0 ;
  TRISA1_bit=0 ;
 //Timer0_Function();

 INTCON.GIE=0;
 Soft_I2C_Init();
 Delay_ms(500);
    /*Soft_I2C_Start();
     Soft_I2C_Write(0x9A);
         Soft_I2C_Write(0x55);  Soft_I2C_Write(0x01);Soft_I2C_Write(0x12);
     Soft_I2C_Stop();*/
    /* Soft_I2C_Start();
     for(i=0;i<5;i++)
     {
      if(i==4)responce[i]=Soft_I2C_Read(0);
      else responce[i]=Soft_I2C_Read(1);
     }
     Soft_I2C_Stop();*/
   LEDup=0;
   LEDdown=1;
   LED=1;
  while(1)
  {
     Delay_ms(2000);
  //higher_byte=0x1E;  UART1_Write(higher_byte) ;
/*if(dataReady==1)
   {
     //UART1_Write(0x11);
     Soft_I2C_Start();
     for(i=0;i<6;i++)
     {
       if(i<5)Data[i]=Soft_I2C_Read(0);
       else Data[i]=Soft_I2C_Read(1);
     }
     Soft_I2C_Stop();
   }
   else
   {
    for(i=0;i<6;i++)
    {
      while(UART1_Tx_Idle()==0) { }
      UART1_Write(Data[i]) ;
    }
   }*/

          UART1_Write(0x11) ;

           //asm{CLRWDT}
  }

 }

//##############################################################################

pero esto no funciona, por lo que cualquier ayuda o sugerencia por favor No funciona, ya que el flujo del programa se detiene. Después de esas líneas le digo a MCU lo siguiente

sbit   LED          at     PORTC.b2;
LED=1;

espero ver que el led está encendido pero nada funciona, revisé todas las conexiones, pero en vano. por eso digo que no funciona en primer lugar.

Más más Quería asegurarme de que no sea una conexión de hardware la razón, así que Usé el terminal USART para mostrar algunos bytes en el terminal, escribo esas líneas después de las líneas de código i2C anteriores:

UART1_Write(0x11) ;  

así que cuando comento el código i2C obtengo 0x11 en el terminal, cuando los descomento, ¡todo se detiene!

También, cuando comento, el led de las líneas i2C está arriba, de lo contrario está abajo.

eliminar todo el código de i2c suave y solo dejar Soft_I2C_Init(); es suficiente para detener el flujo del programa

ESTO ES AR1020 hoja de datos enlace

note

En el diseño de circuitos, los dos pines en MCU utilizados para soft_i2C no están conectados para levantar la resistencia como en los pines i2C de hardware

    

1 respuesta

1

@AhmedZainElDein,

  

En el diseño de circuitos, los dos pines en MCU utilizados para soft_i2C no son   conectado para levantar la resistencia como en los pines i2C de hardware

Algunas partes de su descripción no están claras (al menos para mí), pero al leer otras partes de su pregunta, hay un problema (y una respuesta) claro: agregue resistencias de recuperación a la SCL y pines SDA.

A pesar de que su PIC16F688 no tiene opciones de salida de drenaje abierto (OD), la forma estándar de emular pines OD es que el software cambie entre la activación activa del pin de salida bajo y que ese pin sea una entrada (permitiendo que Resistencia de pull-up externa para tirar del pasador alto). Además, los esclavos I2C todavía necesitan las resistencias pull-up, ya que no pueden elevar esas señales. *

[* Excepto los pocos dispositivos de especificación I2C más nuevos y rápidos, que utilizan controladores push-pull, esto no se aplica aquí.]

  

eliminando todo el código de i2c de software y simplemente dejando Soft_I2C_Init (); es suficiente   detener el flujo del programa

Sí, esto es lo esperado. La biblioteca de Soft I2C estará esperando a que el pin SCL alcance un nivel alto y esperará hasta que eso suceda. El enlace a continuación es un ejemplo de exactamente esta situación (no hay resistencias de activación y la llamada a Soft_I2C_Init () se cuelga) en el foro de MikroE [ 1 ]: observe que la solución es agregar resistencias de pull-up a los pines SCL y SDA:

enlace

También se explica la necesidad de resistencias de pull-up en los documentos de la biblioteca Soft I2C:

enlace

Donde dice:

  

Los pines utilizados para la comunicación del software I²C deben estar conectados   a las resistencias pull-up

y

  

Todas las funciones de la biblioteca I²C son funciones de llamada de bloqueo (son   esperando que la línea de reloj I²C se convierta en una lógica).

Por eso se cuelga tu código, sin resistencias pull-up.

Puede que haya otros problemas con su código [no tengo tiempo para analizarlo todo] y en cualquier trabajo con I2C, siempre he encontrado que un osciloscopio (y / o un analizador lógico) es útil o, a veces, vital. . Después de agregar las resistencias de pull-up (la elección del mejor valor se obtiene al ver las señales con un 'alcance', le sugiero que comience con 4k7 pull-ups, pero otras personas pueden sugerir valores de inicio diferentes) y luego su llamada a Soft_I2C_Init ( ) ya no debe colgar. Buena suerte.

    
respondido por el SamGibson

Lea otras preguntas en las etiquetas