/* * Copyright (c) 2010 by Cristian Maglie * Copyright (c) 2014 by Paul Stoffregen (Transaction API) * Copyright (c) 2014 by Matthijs Kooijman (SPISettings AVR) * Copyright (c) 2014 by Andrew J. Kroll (atomicity fixes) * SPI Master library for arduino. * * 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 * or the GNU Lesser General Public License version 2.1, both as * published by the Free Software Foundation. */ #ifndef _SPI_H_INCLUDED #define _SPI_H_INCLUDED #include #include "mik32_hal_spi.h" // SPI_HAS_TRANSACTION means SPI has beginTransaction(), endTransaction(), // usingInterrupt(), and SPISetting(clock, bitOrder, dataMode) #define SPI_HAS_TRANSACTION 1 // SPI_HAS_NOTUSINGINTERRUPT means that SPI has notUsingInterrupt() method #define SPI_HAS_NOTUSINGINTERRUPT 1 // SPI_ATOMIC_VERSION means that SPI has atomicity fixes and what version. // This way when there is a bug fix you can check this define to alert users // of your code if it uses better version of this library. // This also implies everything that SPI_HAS_TRANSACTION as documented above is // available too. #define SPI_ATOMIC_VERSION 1 #define SPI_DEFAULT_SPEED 4000000 #ifndef LSBFIRST #define LSBFIRST 0 #endif #ifndef MSBFIRST #define MSBFIRST 1 #endif // dividers for setClockDivider() #define SPI_CLOCK_DIV4 0x01 // 8 MHz #define SPI_CLOCK_DIV8 0x02 // 4 MHz #define SPI_CLOCK_DIV16 0x03 // 2 MHz #define SPI_CLOCK_DIV32 0x04 // 1 MHz #define SPI_CLOCK_DIV64 0x05 // 500 kHz #define SPI_CLOCK_DIV128 0x06 // 250 kHz #define SPI_CLOCK_DIV256 0x07 // 125 kHz // mode[1] - polarity, mode[0] - phase #define SPI_MODE0 0b00 #define SPI_MODE1 0b01 #define SPI_MODE2 0b10 #define SPI_MODE3 0b11 class SPISettings { public: SPISettings(uint32_t speedMaximum, uint8_t dataOrder, uint8_t dataMode) { spiUpdateSettings(speedMaximum, dataOrder, dataMode); } SPISettings() { spiUpdateSettings(SPI_DEFAULT_SPEED, MSBFIRST, SPI_MODE0); } private: void spiUpdateSettings(uint32_t speedMaximum, uint8_t dataOrder, uint8_t dataMode); friend class SPIClass; }; class SPIClass { private: static bool spiInUse; static uint8_t interruptMode; // 0=none, 1=mask static uint8_t interruptMask; // which interrupts to mask public: // Initialize the SPI library static void begin(); // If SPI is used from within an interrupt, this function registers // that interrupt with the SPI library, so beginTransaction() can // prevent conflicts. The input interruptNumber is the number used // with attachInterrupt. static void usingInterrupt(uint8_t interruptNumber); // And this does the opposite. static void notUsingInterrupt(uint8_t interruptNumber); // Note: the usingInterrupt and notUsingInterrupt functions should // not to be called from ISR context or inside a transaction. // For details see: // https://github.com/arduino/Arduino/pull/2381 // https://github.com/arduino/Arduino/pull/2449 // Before using SPI.transfer() or asserting chip select pins, // this function is used to gain exclusive access to the SPI bus // and configure the correct settings. void beginTransaction(SPISettings settings); // Write to the SPI bus (MOSI pin) and also receive (MISO pin) uint8_t transfer(uint8_t data); uint16_t transfer16(uint16_t data); void transfer(void *buf, size_t count); // After performing a group of transfers and releasing the chip select // signal, this function allows others to access the SPI bus void endTransaction(void); // Disable the SPI bus static void end(); // This function is deprecated. New applications should use // beginTransaction() to configure SPI settings. void setBitOrder(uint8_t bitOrder); // This function is deprecated. New applications should use // beginTransaction() to configure SPI settings. void setDataMode(uint8_t dataMode); // This function is deprecated. New applications should use // beginTransaction() to configure SPI settings. void setClockDivider(uint8_t clockDiv); // A temporary function until this error is fixed in the HAL library HAL_StatusTypeDef exchange(SPI_HandleTypeDef *hspi, uint8_t TransmitBytes[], uint8_t ReceiveBytes[], uint32_t DataSize, uint32_t Timeout); }; extern SPIClass SPI; #endif