5 votos

SPI.h para ATTiny

¿Existe una implementación diferente de la biblioteca SPI de Arduino que se pueda utilizar para la serie ATTinyX5? Lo supongo, en parte porque creo que el SPI de ATTiny se proporciona a través de USI... Tengo la configuración del entorno utilizando las instrucciones aquí pero cuando trato de compilar cualquier cosa con SPI.h incluido sólo arroja todo tipo de errores:

C:\Program Files (x86)\arduino\libraries\SPI/SPI.h: In static member function 'static byte SPIClass::transfer(byte)':
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:56: error: 'SPDR' was not declared in this scope
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:57: error: 'SPSR' was not declared in this scope
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:57: error: 'SPIF' was not declared in this scope
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h: In static member function 'static void SPIClass::attachInterrupt()':
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:63: error: 'SPCR' was not declared in this scope
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:63: error: 'SPIE' was not declared in this scope
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h: In static member function 'static void SPIClass::detachInterrupt()':
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:67: error: 'SPCR' was not declared in this scope
C:\Program Files (x86)\arduino\libraries\SPI/SPI.h:67: error: 'SPIE' was not declared in this scope

En la misma línea, ¿hay algo que deba hacerse al código que utiliza el hardware SPI para que funcione en el ATTiny? Pude conseguir que funcionara con una implementación de bits, pero SPI por hardware estaría bien.

2voto

azhar Puntos 21

No has dicho si estás usando el tinyx5 como maestro o esclavo... si es esclavo, entonces sugiero conectar la línea de selección de esclavo a una interrupción de hardware para disparar la operación de lectura y escritura basada en la entrada de reloj. Si el tinyx5 se utiliza como maestro, es muy fácil utilizar una solución de software. Yo no uso Arduino en absoluto, pero estoy muy familiarizado con los dispositivos AVR.

Cuando la USI está involucrada, la cosa se puede complicar un poco. Siendo realistas, puede ser más efectivo usar una solución de bit-bang que usar la USI como SPI para la mayoría de las necesidades. Los errores que ves surgen porque los registros SPI descritos en el archivo de cabecera no se llaman igual en todos los dispositivos (si es que existen). En el caso del dispositivo ATtiny, no existen ya que utiliza el módulo USI para actuar como SPI. Podrías intentar que el USI funcionara como SPI, pero te recomendaría probar primero esta sencilla solución de software para ver si se adapta a tus necesidades. Las variables de capital necesitan ser definidas en tu proyecto como los pines de datos y de reloj SPI apropiados. Por ejemplo:

#define _USI_SPI_PORT PORTB
#define _U_DO         (1<<PB0)  // Or _BV(PB0)

Haga esto para DO (MOSI), DI (MISO) y SCK. A continuación, utilice esta función para transferir un byte:

unsigned char SPI_transferByte(unsigned char data)
{
  unsigned char bit = 0;

  _U_SPI_PORT &= ~_U_SS                 // Need to manually Lower the SS line first

  for(bit = 0; bit < 8; bit++)          // Loop through 8 bits
  {  
    if(data & 0x80) _U_SPI_PORT |= _U_DO;   // If bit(7) of "data" is high
    else _U_SPI_PORT &= ~_U_DO;          // if bit(7) of "data" is low
    _U_SPI_PORT |= _U_SCK;                  // Serial Clock Rising Edge 
    data <<= 1;                             // Shift "data" to the left by one bit
    if(_U_SPI_PIN & _U_DI) data |= 0x01;    // If bit of slave data is high
    else data &= ~0x01;                  // if bit of slave data is low
    _U_SPI_PORT &= ~_U_SCK;              // Serial Clock Falling Edge
  }
  _U_SPI_PORT |= _U_SS                 // Need to manually Raise the SS line Last

  return data;                      // Returns shifted data in value
}

Se podría crear otra función para llamar repetidamente a esta función para transferir paquetes de datos más grandes. Sólo en el caso de una gran transferencia de datos es útil utilizar el módulo de hardware, ya que podría ser controlado por interrupciones, dejando al programa principal libre para hacer otras cosas mientras los datos se transfieren. Pero si sólo se transfieren unos pocos bytes a la vez, este método de software es muy eficaz.

0voto

JW. Puntos 145

Por favor, eche un vistazo a la Atmel App Note AVR319 y al software que la acompaña.

Deberías poder usar esos materiales para hacer los cambios necesarios en la biblioteca de Arduino.

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X