TODOPIC

Microcontroladores PIC => Lenguaje C para microcontroladores PIC => Mensaje iniciado por: vasconinicolas en 03 de Diciembre de 2008, 20:20:20

Título: Sacar variable serialmente
Publicado por: vasconinicolas en 03 de Diciembre de 2008, 20:20:20
Perdon por lo basico del asunto pero hace tiempo lo hice en ASM y ahora en C no se como hacerlo aficientemente,
el tema es simple, tengo una variable "buffer" y quero sacar los valores de cada uno de sus bit por un pin del puerto_c mediante una instrucción while. A su vez cada bit que saco debería mandar un aviso por otro pin para que el receptor se entere que debe capturar un valor. Al final de la secuencia de 8 bits un tercer pin le avisa al receptor que está completo en envío.
Muchas gracias de antemano.
Nicolás
Título: Re: Sacar variable serialmente
Publicado por: migsantiago en 03 de Diciembre de 2008, 20:53:26
Hola

En ASM seguramente lo hiciste con RRF o RLF. En C lo podrías también hacer con rotaciones

Código: [Seleccionar]
int variable;
int i=0;
...

while(i<8)
{
variable=variable>>1;
if((int1)variable==1)  //trunca y deja el LSb
      instrucción para poner pin de c a 1;
else
      instrucción para poner pin de c a 0;
i++;
}

Hay otras formas más eficientes pero no se me ocurren por ahora  :D

Título: Re: Sacar variable serialmente
Publicado por: RedPic en 03 de Diciembre de 2008, 21:14:21
Eso es lo que se denomina una transmisión Síncrona o "Data & Clock"

Aquí tienes un par de funciones para transmitir de esa forma y lo que hace falta, como defines y constantes .. y un ejemplo.

Código: C#
  1. #define OUT_CLOCK    PIN_B3 // Pin para la señal de "hay lectura"
  2. #define OUT_DATA     PIN_B5 // Pin para el dato del bit a transmitir
  3. #define maxBufferLen  // Máxima longitud del buffer de transmisión
  4. #define ETU 250 // Delay Elapsed Time Unit
  5.  
  6. char Buffer[maxBufferLen]; // Buffer de transmisión
  7.  
  8. void Transmite_Bit(char c)
  9. {
  10.    // Data
  11.    if((c&0x01)==0){
  12.       output_high(OUT_DATA);
  13.    }
  14.    else{
  15.       output_low(OUT_DATA);
  16.    }
  17.    // Clock
  18.    delay_us(ETU );
  19.    output_low(OUT_CLOCK);
  20.    delay_us(ETU );
  21.    output_high(OUT_CLOCK);
  22. }
  23.  
  24. void Transmite_Byte(char c)
  25. {
  26.         int i;
  27.         char bt;
  28.  
  29.         for(i=0;i<8;i++){
  30.                 bt=(c>>i)&0x01;
  31.                 Transmite_Bit(bt);
  32.         }
  33. }
  34.  
  35. void output_Buffer(void){
  36.  
  37.    int i;
  38.  
  39.    // bytes de code
  40.    for(i=0;i<maxBufferLen;i++)  {
  41.       Transmite_Byte(Buffer[i]);
  42.    }
  43. }

Solo tienes que llamar a la función output_Buffer() para transmitir el Buffer.

Si solo quieres mandar un número dado de bytes hay que modificar un poco la función output_Buffer() para pasarle el número de bytes que quieres enviar:

Código: C#
  1. void output_Buffer(n){
  2.  
  3.    int i;
  4.  
  5.    // bytes de code
  6.    for(i=0;i<n,i<maxBufferLen;i++)      {
  7.       Transmite_Byte(Buffer[i]);
  8.    }
  9. }

En fin, de ahí hasta el infinito lo que quieras.  :mrgreen:
Título: Re: Sacar variable serialmente
Publicado por: vasconinicolas en 03 de Diciembre de 2008, 22:11:47
Gracias maestros, muy gentiles por su tiempo y contribuciones. Me ha servido perfectamente.
Estoy tratando de separar mi circuito en 2 porque necesito controlar 2 motores pap y como la electronica principal (pic, teclado y lcd) la tengo en un control de mano, me harían falta 4 + 4 + 1 (positovo o negativo) 9 cables  para llegar a los motores y eso es mucho clable.. Por eso la idea de serializar mediante un 4094 pero voy a pensar alguna otra solucion porque entre interrupiones y demás no marchan parejos los motores sino que se frenan algunas veces entre paso y paso. En fin, veré como solucionarlo y les cuento.
Saludos.
Muchas gracias por todo!!
Nico