diff --git a/libraries/SPI/SPI.cpp b/libraries/SPI/SPI.cpp index 29ecbcb65f3b2b8469f058c9328f31c7d2473759..18a7c853d7710fe2b944e69aea5d5bf24fd9121f 100644 --- a/libraries/SPI/SPI.cpp +++ b/libraries/SPI/SPI.cpp @@ -1,7 +1,6 @@ /* * SPI Master library for arduino. * Copyright (c) 2014 Arduino. - * based on Copyright (c) 2011 Cristian Maglie <c.maglie@bug.st>. * * This file is free software; you can redistribute it and/or modify * it under the terms of either the GNU General Public License version 2 @@ -16,8 +15,8 @@ SPIClass::SPIClass(SERCOM *p_sercom, uint8_t uc_pinMISO, uint8_t uc_pinSCK, uint8_t uc_pinMOSI) { - assert(p_sercom != NULL ); - _p_sercom = p_sercom; + assert(p_sercom != NULL); + _p_sercom = p_sercom; _uc_pinMiso = uc_pinMISO; _uc_pinSCK = uc_pinSCK; @@ -31,68 +30,69 @@ void SPIClass::begin() pinPeripheral(_uc_pinSCK, g_APinDescription[_uc_pinSCK].ulPinType); pinPeripheral(_uc_pinMosi, g_APinDescription[_uc_pinMosi].ulPinType); - // Default speed set to 4Mhz, SPI mode set to MODE 0 and Bit order set to MSB first. - _p_sercom->initSPI(SPI_PAD_2_SCK_3, SERCOM_RX_PAD_0, SPI_CHAR_SIZE_8_BITS, MSB_FIRST); - _p_sercom->initSPIClock(SERCOM_SPI_MODE_0, 4000000); + // Default speed set to 4Mhz, SPI mode set to MODE 0 and Bit order set to MSB first. + _p_sercom->initSPI(SPI_PAD_2_SCK_3, SERCOM_RX_PAD_0, SPI_CHAR_SIZE_8_BITS, MSB_FIRST); + _p_sercom->initSPIClock(SERCOM_SPI_MODE_0, 4000000); - _p_sercom->enableSPI(); + _p_sercom->enableSPI(); } void SPIClass::end() { - _p_sercom->resetSPI(); + _p_sercom->resetSPI(); } void SPIClass::usingInterrupt(uint8_t interruptNumber) { - // XXX: TODO + // XXX: TODO } void SPIClass::beginTransaction(SPISettings settings) { - // XXX: TODO - setBitOrder(settings.bitOrder); - setClockDivider(settings.clockDiv); - setDataMode(settings.dataMode); + // XXX: TODO + setBitOrder(settings.bitOrder); + setClockDivider(settings.clockDiv); + setDataMode(settings.dataMode); } void SPIClass::endTransaction(void) { - // XXX: TODO + // XXX: TODO } void SPIClass::setBitOrder(BitOrder order) { - if(order == LSBFIRST) - _p_sercom->setDataOrderSPI(LSB_FIRST); - else - _p_sercom->setDataOrderSPI(MSB_FIRST); + if (order == LSBFIRST) { + _p_sercom->setDataOrderSPI(LSB_FIRST); + } else { + _p_sercom->setDataOrderSPI(MSB_FIRST); + } } void SPIClass::setDataMode(uint8_t mode) { - switch(mode) - { - case SPI_MODE0: - _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_0); - break; - - case SPI_MODE1: - _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_1); - break; - - case SPI_MODE2: - _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_2); - break; - - case SPI_MODE3: - _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_3); - break; - - default: - break; - } + switch (mode) + { + case SPI_MODE0: + _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_0); + break; + + case SPI_MODE1: + _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_1); + break; + + case SPI_MODE2: + _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_2); + break; + + case SPI_MODE3: + _p_sercom->setClockModeSPI(SERCOM_SPI_MODE_3); + break; + + default: + break; + } } void SPIClass::setClockDivider(uint8_t div) @@ -106,19 +106,19 @@ void SPIClass::setClockDivider(uint8_t div) byte SPIClass::transfer(uint8_t data) { - //Writing the data - _p_sercom->writeDataSPI(data); + // Writing the data + _p_sercom->writeDataSPI(data); - //Read data - return _p_sercom->readDataSPI(); + // Read data + return _p_sercom->readDataSPI(); } void SPIClass::attachInterrupt() { - // Should be enableInterrupt() + // Should be enableInterrupt() } void SPIClass::detachInterrupt() { - // Should be disableInterrupt() + // Should be disableInterrupt() } -SPIClass SPI( &sercom4, PIN_SPI_MISO, PIN_SPI_SCK, PIN_SPI_MOSI ) ; +SPIClass SPI( &sercom4, PIN_SPI_MISO, PIN_SPI_SCK, PIN_SPI_MOSI ); diff --git a/libraries/SPI/SPI.h b/libraries/SPI/SPI.h index 6473ab23c6b4c69a020204c8db2563f78ebcd76a..65a825adc2085b940174eba4feb61124de17e534 100644 --- a/libraries/SPI/SPI.h +++ b/libraries/SPI/SPI.h @@ -30,73 +30,77 @@ class SPISettings { public: - SPISettings(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) { - if (__builtin_constant_p(clock)) { - init_AlwaysInline(clock, bitOrder, dataMode); - } else { - init_MightInline(clock, bitOrder, dataMode); - } - } - SPISettings() { init_AlwaysInline(4000000, MSBFIRST, SPI_MODE0); } - private: - void init_MightInline(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) { - init_AlwaysInline(clock, bitOrder, dataMode); - } - void init_AlwaysInline(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) __attribute__((__always_inline__)) { - uint8_t div; - if (clock < (F_CPU / 255)) { - div = 255; - } else if (clock >= (F_CPU / SPI_MIN_CLOCK_DIVIDER)) { - div = SPI_MIN_CLOCK_DIVIDER; - } else { - div = (F_CPU / (clock + 1)) + 1; - } - this->clockDiv = div; - this->dataMode = dataMode; - this->bitOrder = bitOrder; - } - uint8_t clockDiv, dataMode; - BitOrder bitOrder; - friend class SPIClass; + SPISettings(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) { + if (__builtin_constant_p(clock)) { + init_AlwaysInline(clock, bitOrder, dataMode); + } else { + init_MightInline(clock, bitOrder, dataMode); + } + } + + SPISettings() { init_AlwaysInline(4000000, MSBFIRST, SPI_MODE0); } + private: + void init_MightInline(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) { + init_AlwaysInline(clock, bitOrder, dataMode); + } + + void init_AlwaysInline(uint32_t clock, BitOrder bitOrder, uint8_t dataMode) __attribute__((__always_inline__)) { + uint8_t div; + if (clock < (F_CPU / 255)) { + div = 255; + } else if (clock >= (F_CPU / SPI_MIN_CLOCK_DIVIDER)) { + div = SPI_MIN_CLOCK_DIVIDER; + } else { + div = (F_CPU / (clock + 1)) + 1; + } + this->clockDiv = div; + this->dataMode = dataMode; + this->bitOrder = bitOrder; + } + + uint8_t clockDiv, dataMode; + BitOrder bitOrder; + + friend class SPIClass; }; class SPIClass { public: - SPIClass(SERCOM *p_sercom, uint8_t uc_pinMISO, uint8_t uc_pinSCK, uint8_t uc_pinMOSI); + SPIClass(SERCOM *p_sercom, uint8_t uc_pinMISO, uint8_t uc_pinSCK, uint8_t uc_pinMOSI); + + byte transfer(uint8_t data); + inline void transfer(void *buf, size_t count); - byte transfer(uint8_t data); - inline void transfer(void *buf, size_t count); + // Transaction Functions + void usingInterrupt(uint8_t interruptNumber); + void beginTransaction(SPISettings settings); + void endTransaction(void); - // Transaction Functions - void usingInterrupt(uint8_t interruptNumber); - void beginTransaction(SPISettings settings); - void endTransaction(void); + // SPI Configuration methods + void attachInterrupt(); + void detachInterrupt(); - // SPI Configuration methods - void attachInterrupt(); - void detachInterrupt(); + void begin(); + void end(); - void begin(); - void end(); - - void setBitOrder(BitOrder order); - void setDataMode(uint8_t uc_mode); - void setClockDivider(uint8_t uc_div); + void setBitOrder(BitOrder order); + void setDataMode(uint8_t uc_mode); + void setClockDivider(uint8_t uc_div); private: - SERCOM *_p_sercom; - uint8_t _uc_pinMiso; - uint8_t _uc_pinMosi; - uint8_t _uc_pinSCK; + SERCOM *_p_sercom; + uint8_t _uc_pinMiso; + uint8_t _uc_pinMosi; + uint8_t _uc_pinSCK; }; void SPIClass::transfer(void *buf, size_t count) { - // TODO: Optimize for faster block-transfer - uint8_t *buffer = reinterpret_cast<uint8_t *>(buf); - for (size_t i=0; i<count; i++) - buffer[i] = transfer(buffer[i]); + // TODO: Optimize for faster block-transfer + uint8_t *buffer = reinterpret_cast<uint8_t *>(buf); + for (size_t i=0; i<count; i++) + buffer[i] = transfer(buffer[i]); } #if SPI_INTERFACES_COUNT > 0