#ifndef ADS7818_h #define ADS7871_h //------------------------------------------------------------------------------ /** nop to tune soft SPI timing */ #define nop asm volatile ("nop\n\t") //------------------------------------------------------------------------------ /** doxygen can't handle __attribute__ very well */ #define STATIC_ALWAYS_INLINE static inline __attribute__((always_inline)) //------------------------------------------------------------------------------ template class ADS7818 { public: void begin() { fastPinMode(ClkPin, 1); fastDigitalWrite(ClkPin, 0); fastPinMode(ConvPin, 1); fastDigitalWrite(ConvPin, 1); fastPinMode(DataPin, 0); } //---------------------------------------------------------------------------- inline __attribute__((always_inline)) uint16_t read() { uint16_t v = 0; fastDigitalWrite(ConvPin, 0); fastDigitalWrite(ClkPin, 1); fastDigitalWrite(ClkPin, 0); fastDigitalWrite(ConvPin, 1); fastDigitalWrite(ClkPin, 1); fastDigitalWrite(ClkPin, 0); readBitFast16(v, 11); readBitFast16(v, 10); readBitFast16(v, 9); readBitFast16(v, 8); readBitFast16(v, 7); readBitFast16(v, 6); readBitFast16(v, 5); readBitFast16(v, 4); readBitFast16(v, 3); readBitFast16(v, 2); readBitFast16(v, 1); readBitFast16(v, 0); return v; } private: //---------------------------------------------------------------------------- inline __attribute__((always_inline)) void readBitFast16(uint16_t &v, uint8_t b) { fastDigitalWrite(ClkPin, 1); if (fastDigitalRead(DataPin)) v |= (1 << b); fastDigitalWrite(ClkPin, 0); } }; #if 0 /** initialize I/O ports */ STATIC_ALWAYS_INLINE void adcBegin() { fastPinMode(ADC_CLK_PIN, 1); fastDigitalWrite(ADC_CLK_PIN, 0); fastPinMode(ADC_CONV_PIN, 1); fastDigitalWrite(ADC_CONV_PIN, 1); fastPinMode(ADC_DATA_PIN, 0); } //------------------------------------------------------------------------------ /** clock for don't care bits *\param[in] delayBefore if true, delay before raising clock*/ STATIC_ALWAYS_INLINE void fastDummy(bool first) { if (!first) nop; fastDigitalWrite(ADC_CLK_PIN, 1); nop; fastDigitalWrite(ADC_CLK_PIN, 0); } //------------------------------------------------------------------------------ /** read next bit fast as possible * \param[in] v word to receive bit * \param[in] b bit number to be set. v |= (1 << b) if next bit is high. */ STATIC_ALWAYS_INLINE void readBitFast16(uint16_t &v, uint8_t b) { fastDigitalWrite(ADC_CLK_PIN, 1); if (fastDigitalRead(ADC_DATA_PIN)) v |= (1 << b); fastDigitalWrite(ADC_CLK_PIN, 0); } //------------------------------------------------------------------------------ /** Read AD7680 16-bit ADC in less than 8 microseconds * cs is chip select pin */ STATIC_ALWAYS_INLINE uint16_t adcRead(bool centered = false) { uint16_t v = 0; fastDigitalWrite(ADC_CONV_PIN, 0); fastDigitalWrite(ADC_CLK_PIN, 1); fastDigitalWrite(ADC_CLK_PIN, 0); fastDigitalWrite(ADC_CONV_PIN, 1); fastDigitalWrite(ADC_CLK_PIN, 1); fastDigitalWrite(ADC_CLK_PIN, 0); // uint16_t v = 0; // fastDummy(1); // fastDummy(0); // fastDummy(0); // fastDummy(0); // readBitFast16(v, 15); // readBitFast16(v, 14); // readBitFast16(v, 13); // readBitFast16(v, 12); readBitFast16(v, 11); readBitFast16(v, 10); readBitFast16(v, 9); readBitFast16(v, 8); readBitFast16(v, 7); readBitFast16(v, 6); readBitFast16(v, 5); readBitFast16(v, 4); readBitFast16(v, 3); readBitFast16(v, 2); readBitFast16(v, 1); readBitFast16(v, 0); return centered ? v ^ 0X8000 : v; } #endif // 0 #endif // ADS7818_h