#include "spi.h" #include void spi_begin() { #if defined(SPCR) #error to write ... // Set SS to high so a connected chip will be "deselected" by default digitalWrite(SS, HIGH); // When the SS pin is set as OUTPUT, it can be used as // a general purpose output port (it doesn't influence // SPI operations). pinMode(SS, OUTPUT); // Warning: if the SS pin ever becomes a LOW INPUT then SPI // automatically switches to Slave, so the data direction of // the SS pin MUST be kept as OUTPUT. SPCR |= _BV(MSTR); SPCR |= _BV(SPE); // Set direction register for SCK and MOSI pin. // MISO pin automatically overrides to INPUT. // By doing this AFTER enabling SPI, we avoid accidentally // clocking in a single bit since the lines go directly // from "input" to SPI control. // http://code.google.com/p/arduino/issues/detail?id=888 pinMode(SCK, OUTPUT); pinMode(MOSI, OUTPUT); #else PRR &= ~(_BV(PRUSI)); USICR = _BV(USIWM0); USCK_DDR |= _BV(USCK_BIT); //set the USCK pin as output DO_DDR |= _BV(DO_BIT); //set the DO pin as output DI_DDR &= ~_BV(DI_BIT); //set the DI pin as input #endif } uint8_t spi_transfer(uint8_t b) { #if defined(SPCR) SPDR = b; while (!(SPSR & _BV(SPIF))); return SPDR; #else USIDR = b; USISR = _BV(USIOIF); do { USICR = _BV(USIWM0) | _BV(USICS1) | _BV(USICLK) | _BV(USITC); // _delay_ms(1); }while ((USISR & _BV(USIOIF)) == 0); return USIDR; #endif } void spi_end() { #if defined(SPCR) SPCR &= ~_BV(SPE); #else USICR &= ~(_BV(USIWM1) | _BV(USIWM0)); #endif } void spi_setBitOrder(uint8_t bitOrder) { #if defined(SPCR) if(bitOrder == LSBFIRST) { SPCR |= _BV(DORD); } else { SPCR &= ~(_BV(DORD)); } #endif } void spi_setDataMode(uint8_t mode) { #if defined(SPCR) SPCR = (SPCR & ~SPI_MODE_MASK) | mode; #else #endif }