LT_SPI
Embed:
(wiki syntax)
Show/hide line numbers
LT_SPI.cpp
Go to the documentation of this file.
00001 //! @todo Review this document. 00002 /*! 00003 LT_SPI: Routines to communicate with ATmega328P's hardware SPI port. 00004 00005 @verbatim 00006 00007 LT_SPI implements the low level master SPI bus routines using 00008 the hardware SPI port. 00009 00010 SPI Frequency = (CPU Clock frequency)/(16+2(TWBR)*Prescaler) 00011 SPCR = SPI Control Register (SPIE SPE DORD MSTR CPOL CPHA SPR1 SPR0) 00012 SPSR = SPI Status Register (SPIF WCOL - - - - - SPI2X) 00013 00014 Data Modes: 00015 CPOL CPHA Leading Edge Trailing Edge 00016 0 0 sample rising setup falling 00017 0 1 setup rising sample falling 00018 1 0 sample falling setup rising 00019 1 1 sample rising setup rising 00020 00021 CPU Frequency = 16MHz on Arduino Uno 00022 SCK Frequency 00023 SPI2X SPR1 SPR0 Frequency Uno_Frequency 00024 0 0 0 fosc/4 4 MHz 00025 0 0 1 fosc/16 1 MHz 00026 0 1 0 fosc/64 250 kHz 00027 0 1 1 fosc/128 125 kHz 00028 0 0 0 fosc/2 8 MHz 00029 0 0 1 fosc/8 2 MHz 00030 0 1 0 fosc/32 500 kHz 00031 00032 @endverbatim 00033 00034 REVISION HISTORY 00035 $Revision: 6237 $ 00036 $Date: 2016-12-20 15:09:16 -0800 (Tue, 20 Dec 2016) $ 00037 00038 Copyright (c) 2013, Linear Technology Corp.(LTC) 00039 All rights reserved. 00040 00041 Redistribution and use in source and binary forms, with or without 00042 modification, are permitted provided that the following conditions are met: 00043 00044 1. Redistributions of source code must retain the above copyright notice, this 00045 list of conditions and the following disclaimer. 00046 2. Redistributions in binary form must reproduce the above copyright notice, 00047 this list of conditions and the following disclaimer in the documentation 00048 and/or other materials provided with the distribution. 00049 00050 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 00051 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 00052 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 00053 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 00054 ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 00055 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 00056 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 00057 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00058 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00059 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00060 00061 The views and conclusions contained in the software and documentation are those 00062 of the authors and should not be interpreted as representing official policies, 00063 either expressed or implied, of Linear Technology Corp. 00064 00065 The Linear Technology Linduino is not affiliated with the official Arduino team. 00066 However, the Linduino is only possible because of the Arduino team's commitment 00067 to the open-source community. Please, visit http://www.arduino.cc and 00068 http://store.arduino.cc , and consider a purchase that will help fund their 00069 ongoing work. 00070 */ 00071 00072 //! @ingroup Linduino 00073 //! @{ 00074 //! @defgroup LT_SPI LT_SPI: Routines to communicate with ATmega328P's hardware SPI port. 00075 //! @} 00076 00077 /*! @file 00078 @ingroup LT_SPI 00079 Library for LT_SPI: Routines to communicate with ATmega328P's hardware SPI port. 00080 */ 00081 #include <stdint.h> 00082 #include "LT_SPI.h " 00083 00084 //DigitalOut QUIKEVAL_GPIO D9; //!< Linduino QuikEval GPIO pin (QuikEval connector pin 14) connects to Arduino pin 9 00085 //DigitalOut QUIKEVAL_CS A3; //!< QuikEval CS pin (SPI chip select on QuikEval connector pin 6) connects to Arduino SS pin. 00086 //DigitalInOut QUIKEVAL_MUX_MODE_PIN(8,output); /*!< QUIKEVAL_MUX_MODE_PIN defines the control pin for the QuikEval MUX. 00087 //The I2C port's SCL and the SPI port's SCK signals share the same pin on the Linduino's QuikEval connector. 00088 //Additionally, the I2C port's SDA and the SPI port's MOSI signals share the same pin on the Linduino's QuikEval connector. 00089 //The pair of pins connected to the QuikEval connector is switched using a MUX on the Linduino board. 00090 //The control pin to switch the MUX is defined as QUIKEVAL_MUX_MODE_PIN (Arduino pin 8). */ 00091 00092 void output_low(uint8_t pin) 00093 { 00094 pin = 0; 00095 } 00096 void output_high(uint8_t pin) 00097 { 00098 pin = 1; 00099 } 00100 00101 00102 // Reads and sends a byte 00103 // Return 0 if successful, 1 if failed 00104 void spi_transfer_byte(uint8_t cs_pin, uint8_t tx, uint8_t *rx) 00105 { 00106 output_low(cs_pin); //! 1) Pull CS low 00107 00108 *rx = spi.write(tx); //! 2) Read byte and send byte 00109 00110 output_high(cs_pin); //! 3) Pull CS high 00111 } 00112 00113 // Reads and sends a word 00114 // Return 0 if successful, 1 if failed 00115 void spi_transfer_word(uint8_t cs_pin, uint16_t tx, uint16_t *rx) 00116 { 00117 union 00118 { 00119 uint8_t b[2]; 00120 uint16_t w; 00121 } data_tx; 00122 00123 union 00124 { 00125 uint8_t b[2]; 00126 uint16_t w; 00127 } data_rx; 00128 00129 data_tx.w = tx; 00130 00131 output_low(cs_pin); //! 1) Pull CS low 00132 00133 data_rx.b[1] = spi.write(data_tx.b[1]); //! 2) Read MSB and send MSB 00134 data_rx.b[0] = spi.write(data_tx.b[0]); //! 3) Read LSB and send LSB 00135 00136 *rx = data_rx.w; 00137 00138 output_high(cs_pin); //! 4) Pull CS high 00139 } 00140 00141 // Reads and sends a byte array 00142 void spi_transfer_block(uint8_t cs_pin, uint8_t *tx, uint8_t *rx, uint8_t length) 00143 { 00144 int8_t i; 00145 00146 output_low(cs_pin); //! 1) Pull CS low 00147 00148 for (i=(length-1); i >= 0; i--) 00149 rx[i] = spi.write(tx[i]); //! 2) Read and send byte array 00150 00151 output_high(cs_pin); //! 3) Pull CS high 00152 } 00153 00154 // Connect SPI pins to QuikEval connector through the Linduino MUX. This will disconnect I2C. 00155 //void quikeval_SPI_connect() 00156 //{ 00157 // output_high(QUIKEVAL_CS); //! 1) Pull Chip Select High 00158 // 00159 // //! 2) Enable Main SPI 00160 // pinMode(QUIKEVAL_MUX_MODE_PIN, OUTPUT); 00161 // QUIKEVAL_MUX_MODE_PIN = 0; 00162 //} 00163 00164 // Configure the SPI port for 4MHz SCK. 00165 // This function or spi_enable() must be called 00166 // before using the other SPI routines. 00167 //void quikeval_SPI_init(void) // Initializes SPI 00168 //{ 00169 // spi_enable(SPI_CLOCK_DIV16); //! 1) Configure the spi port for 4MHz SCK 00170 //} 00171 00172 // Setup the processor for hardware SPI communication. 00173 // Must be called before using the other SPI routines. 00174 // Alternatively, call quikeval_SPI_connect(), which automatically 00175 // calls this function. 00176 void spi_enable(void) // Configures SCK frequency. Use constant defined in header file. 00177 { 00178 //pinMode(SCK, OUTPUT); //! 1) Setup SCK as output 00179 //pinMode(MOSI, OUTPUT); //! 2) Setup MOSI as output 00180 //pinMode(QUIKEVAL_CS, OUTPUT); //! 3) Setup CS as output 00181 spi.format(16,3); 00182 spi.frequency(1000000); 00183 } 00184 00185 // Disable the SPI hardware port 00186 //void spi_disable() 00187 //{ 00188 // spi.end(); 00189 //} 00190 00191 // Write a data byte using the SPI hardware 00192 //void spi_write(int8_t data) // Byte to be written to SPI port 00193 //{ 00194 // SPDR = data; //! 1) Start the SPI transfer 00195 // while (!(SPSR & _BV(SPIF))); //! 2) Wait until transfer complete 00196 //} 00197 00198 // Read and write a data byte using the SPI hardware 00199 // Returns the data byte read 00200 //int8_t spi_read(int8_t data) //!The data byte to be written 00201 //{ 00202 // SPDR = data; //! 1) Start the SPI transfer 00203 // while (!(SPSR & _BV(SPIF))); //! 2) Wait until transfer complete 00204 // return SPDR; //! 3) Return the data read 00205 //} 00206 00207 // Below are implementations of spi_read, etc. that do not use the 00208 // Arduino SPI library. To use these functions, uncomment them and comment out 00209 // the correcsponding function above. 00210 // 00211 // // Reads and sends a byte 00212 // // Return 0 if successful, 1 if failed 00213 // uint8_t spi_transfer_byte(uint8_t cs_pin, uint8_t tx, uint8_t *rx) 00214 // { 00215 // output_low(cs_pin); //! 1) Pull CS low 00216 // 00217 // *rx = spi_read(tx); //! 2) Read byte and send byte 00218 // 00219 // output_high(cs_pin); //! 3) Pull CS high 00220 // 00221 // return(0); 00222 // } 00223 // 00224 // // Reads and sends a word 00225 // // Return 0 if successful, 1 if failed 00226 // uint8_t spi_transfer_word(uint8_t cs_pin, uint16_t tx, uint16_t *rx) 00227 // { 00228 // union 00229 // { 00230 // uint8_t b[2]; 00231 // uint16_t w; 00232 // } data_tx; 00233 // 00234 // union 00235 // { 00236 // uint8_t b[2]; 00237 // uint16_t w; 00238 // } data_rx; 00239 // 00240 // data_tx.w = tx; 00241 // 00242 // output_low(cs_pin); //! 1) Pull CS low 00243 // 00244 // data_rx.b[1] = spi_read(data_tx.b[1]); //! 2) Read MSB and send MSB 00245 // data_rx.b[0] = spi_read(data_tx.b[0]); //! 3) Read LSB and send LSB 00246 // *rx = data_rx.w; 00247 // 00248 // output_high(cs_pin); //! 4) Pull CS high 00249 // 00250 // return(0); 00251 // } 00252 // 00253 // // Reads and sends a byte array 00254 // // Return 0 if successful, 1 if failed 00255 // uint8_t spi_transfer_block(uint8_t cs_pin, uint8_t *tx, uint8_t *rx, uint8_t length) 00256 // { 00257 // int8_t i; 00258 // 00259 // output_low(cs_pin); //! 1) Pull CS low 00260 // 00261 // for(i=0; i < length; i++) 00262 // rx[i] = spi_read(tx[i]); //! 2) Read and send byte array 00263 // 00264 // output_high(cs_pin); //! 3) Pull CS high 00265 // 00266 // return(0); 00267 // } 00268 // 00269 // // Connect SPI pins to QuikEval connector through the Linduino MUX. This will disconnect I2C. 00270 // void quikeval_SPI_connect() 00271 // { 00272 // output_high(QUIKEVAL_CS); //! 1) Pull Chip Select High 00273 // 00274 // //! 2) Enable Main SPI 00275 // pinMode(QUIKEVAL_MUX_MODE_PIN, OUTPUT); 00276 // digitalWrite(QUIKEVAL_MUX_MODE_PIN, LOW); 00277 // } 00278 // 00279 // // Configure the SPI port for 4MHz SCK. 00280 // // This function or spi_enable() must be called 00281 // // before using the other SPI routines. 00282 // void quikeval_SPI_init(void) // Initializes SPI 00283 // { 00284 // spi_enable(SPI_CLOCK_DIV32); //! 2) Configure the spi port for 4MHz SCK 00285 // } 00286 // 00287 // // Setup the processor for hardware SPI communication. 00288 // // Must be called before using the other SPI routines. 00289 // // Alternatively, call quikeval_SPI_connect(), which automatically 00290 // // calls this function. 00291 // void spi_enable(uint8_t spi_clock_divider) // Configures SCK frequency. Use constant defined in header file. 00292 // { 00293 // pinMode(SCK, OUTPUT); //! 1) Setup SCK as output 00294 // pinMode(MOSI, OUTPUT); //! 2) Setup MOSI as output 00295 // pinMode(QUIKEVAL_CS, OUTPUT); //! 3) Setup CS as output 00296 // output_low(SCK); 00297 // output_low(MOSI); 00298 // output_high(QUIKEVAL_CS); 00299 // SPCR |= _BV(MSTR); //! 4) Set the SPI port to master mode 00300 // //! 5) Set the SPI hardware rate 00301 // SPCR = (SPCR & ~SPI_CLOCK_MASK) | (spi_clock_divider & SPI_CLOCK_MASK); 00302 // SPSR = (SPSR & ~SPI_2XCLOCK_MASK) | ((spi_clock_divider >> 2) & SPI_2XCLOCK_MASK); 00303 // SPCR |= _BV(SPE); //! 5) Enable the SPI port 00304 // } 00305 // 00306 // // Disable the SPI hardware port 00307 // void spi_disable() 00308 // { 00309 // SPCR &= ~_BV(SPE); 00310 // }
Generated on Sun Jul 17 2022 07:21:55 by 1.7.2