Microchip MCP342x ADC library

Committer:
antoniogonzalez
Date:
Wed Jun 15 10:37:24 2016 +0000
Revision:
0:7dbf7356da6b
Child:
1:c4da9889ff85
First commit

Who changed what in which revision?

UserRevisionLine numberNew contents of line
antoniogonzalez 0:7dbf7356da6b 1 /**
antoniogonzalez 0:7dbf7356da6b 2 * Author: Antonio Gonzalez <antgon@cantab.net>
antoniogonzalez 0:7dbf7356da6b 3 * Copyright (c) 2016 The Francis Crick Institute.
antoniogonzalez 0:7dbf7356da6b 4 *
antoniogonzalez 0:7dbf7356da6b 5 * This program is free software: you can redistribute it and/or modify
antoniogonzalez 0:7dbf7356da6b 6 * it under the terms of the GNU General Public License as published by
antoniogonzalez 0:7dbf7356da6b 7 * the Free Software Foundation, either version 3 of the License, or
antoniogonzalez 0:7dbf7356da6b 8 * (at your option) any later version.
antoniogonzalez 0:7dbf7356da6b 9 *
antoniogonzalez 0:7dbf7356da6b 10 * This program is distributed in the hope that it will be useful,
antoniogonzalez 0:7dbf7356da6b 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
antoniogonzalez 0:7dbf7356da6b 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
antoniogonzalez 0:7dbf7356da6b 13 * GNU General Public License for more details.
antoniogonzalez 0:7dbf7356da6b 14 *
antoniogonzalez 0:7dbf7356da6b 15 * You should have received a copy of the GNU General Public License
antoniogonzalez 0:7dbf7356da6b 16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
antoniogonzalez 0:7dbf7356da6b 17 */
antoniogonzalez 0:7dbf7356da6b 18
antoniogonzalez 0:7dbf7356da6b 19 #ifndef MCP342x_h
antoniogonzalez 0:7dbf7356da6b 20 #define MCP342x_h
antoniogonzalez 0:7dbf7356da6b 21
antoniogonzalez 0:7dbf7356da6b 22 #include "mbed.h"
antoniogonzalez 0:7dbf7356da6b 23
antoniogonzalez 0:7dbf7356da6b 24 /**
antoniogonzalez 0:7dbf7356da6b 25 * @brief Microchip analog-to-digital converter MCP3422/3/4
antoniogonzalez 0:7dbf7356da6b 26 *
antoniogonzalez 0:7dbf7356da6b 27 * Library for using Microchip's family of analog-to-digital converters
antoniogonzalez 0:7dbf7356da6b 28 * MCP3422/3/4. Some features of these include:
antoniogonzalez 0:7dbf7356da6b 29 * - 12-, 14-, 16-, or 18-bit ADC.
antoniogonzalez 0:7dbf7356da6b 30 * - Two-wire I2C interface.
antoniogonzalez 0:7dbf7356da6b 31 * - Sampling rate, 3.75 (18-bit), 15 (16-bit), 60 (14-bit), or 240
antoniogonzalez 0:7dbf7356da6b 32 * (12-bit) SPS.
antoniogonzalez 0:7dbf7356da6b 33 * - Two (MCP3422/3) or four (MCP3424) channels, differential input.
antoniogonzalez 0:7dbf7356da6b 34 * - Internal voltage reference, 2.048 V.
antoniogonzalez 0:7dbf7356da6b 35 * - Selectable PGA, x1, x2, x4, or x8.
antoniogonzalez 0:7dbf7356da6b 36 * - Conversion modes: one-shot or continuous.
antoniogonzalez 0:7dbf7356da6b 37 *
antoniogonzalez 0:7dbf7356da6b 38 * TODO:
antoniogonzalez 0:7dbf7356da6b 39 * - Implement 'conversion mode one-shot'
antoniogonzalez 0:7dbf7356da6b 40 *
antoniogonzalez 0:7dbf7356da6b 41 * Example:
antoniogonzalez 0:7dbf7356da6b 42 * @code
antoniogonzalez 0:7dbf7356da6b 43 * #include "mbed.h"
antoniogonzalez 0:7dbf7356da6b 44 * #include "mcp342x.h"
antoniogonzalez 0:7dbf7356da6b 45 *
antoniogonzalez 0:7dbf7356da6b 46 * I2C i2c(p9, p10);
antoniogonzalez 0:7dbf7356da6b 47 * MCP342x mcp_adc(&i2c);
antoniogonzalez 0:7dbf7356da6b 48 *
antoniogonzalez 0:7dbf7356da6b 49 * int main(){
antoniogonzalez 0:7dbf7356da6b 50 * mcp_adc.set_channel(MCP342x::CHANNEL_2);
antoniogonzalez 0:7dbf7356da6b 51 * mcp_adc.set_pga(MCP342x::PGA_4);
antoniogonzalez 0:7dbf7356da6b 52 * mcp_adc.set_resolution(MCP342x::RESOLUTION_12);
antoniogonzalez 0:7dbf7356da6b 53 *
antoniogonzalez 0:7dbf7356da6b 54 * while(1){
antoniogonzalez 0:7dbf7356da6b 55 * // Channel 2 was selected above. Read data from this channel.
antoniogonzalez 0:7dbf7356da6b 56 * long chan2_val = mcp_adc.read();
antoniogonzalez 0:7dbf7356da6b 57 *
antoniogonzalez 0:7dbf7356da6b 58 * // Select now channel 1 and read it.
antoniogonzalez 0:7dbf7356da6b 59 * mcp_adc.set_channel(MCP342x::CHANNEL_1);
antoniogonzalez 0:7dbf7356da6b 60 * long chan1_val = mcp_adc.read();
antoniogonzalez 0:7dbf7356da6b 61 *
antoniogonzalez 0:7dbf7356da6b 62 * printf("CH1 %i CH2 %i\r\n", chan1_val, chan2_val);
antoniogonzalez 0:7dbf7356da6b 63 * wait(5);
antoniogonzalez 0:7dbf7356da6b 64 * }
antoniogonzalez 0:7dbf7356da6b 65 * }
antoniogonzalez 0:7dbf7356da6b 66 * @endcode
antoniogonzalez 0:7dbf7356da6b 67 */
antoniogonzalez 0:7dbf7356da6b 68 class MCP342x
antoniogonzalez 0:7dbf7356da6b 69 {
antoniogonzalez 0:7dbf7356da6b 70 public:
antoniogonzalez 0:7dbf7356da6b 71 // Registers.
antoniogonzalez 0:7dbf7356da6b 72 // The device has only one register, which is the configuration
antoniogonzalez 0:7dbf7356da6b 73 // byte. It consists of these bits:
antoniogonzalez 0:7dbf7356da6b 74 // 7 ~ready
antoniogonzalez 0:7dbf7356da6b 75 // 6-5 channel selection
antoniogonzalez 0:7dbf7356da6b 76 // 4 conversion mode (one-shot, continuous)
antoniogonzalez 0:7dbf7356da6b 77 // 3-2 sample rate selection (12, 14, 16, or 18)
antoniogonzalez 0:7dbf7356da6b 78 // 1-0 PGA gain selection (1x, 2x, 4x, or 8x)
antoniogonzalez 0:7dbf7356da6b 79 typedef enum {
antoniogonzalez 0:7dbf7356da6b 80 REG_PGA_Pos = 0,
antoniogonzalez 0:7dbf7356da6b 81 REG_RESOLUTION_Pos = 2,
antoniogonzalez 0:7dbf7356da6b 82 REG_MODE_Pos = 4,
antoniogonzalez 0:7dbf7356da6b 83 REG_CHANNEL_Pos = 5,
antoniogonzalez 0:7dbf7356da6b 84 REG_RDY_Pos = 7,
antoniogonzalez 0:7dbf7356da6b 85
antoniogonzalez 0:7dbf7356da6b 86 REG_PGA_Clear = ~(0x3 << REG_PGA_Pos),
antoniogonzalez 0:7dbf7356da6b 87 REG_RESOLUTION_Clear = ~(0x3 << REG_RESOLUTION_Pos),
antoniogonzalez 0:7dbf7356da6b 88 REG_MODE_Clear = ~(0x1 << REG_MODE_Pos),
antoniogonzalez 0:7dbf7356da6b 89 REG_CHANNEL_Clear = ~(0x3 << REG_CHANNEL_Pos),
antoniogonzalez 0:7dbf7356da6b 90 REG_RDY_Clear = ~(0x1 << REG_RDY_Pos)
antoniogonzalez 0:7dbf7356da6b 91 } mcp342x_reg_t;
antoniogonzalez 0:7dbf7356da6b 92
antoniogonzalez 0:7dbf7356da6b 93 // Programmable gain.
antoniogonzalez 0:7dbf7356da6b 94 typedef enum {
antoniogonzalez 0:7dbf7356da6b 95 PGA_1 = 0,
antoniogonzalez 0:7dbf7356da6b 96 PGA_2 = 1,
antoniogonzalez 0:7dbf7356da6b 97 PGA_4 = 2,
antoniogonzalez 0:7dbf7356da6b 98 PGA_8 = 3
antoniogonzalez 0:7dbf7356da6b 99 } mcp342x_pga_t;
antoniogonzalez 0:7dbf7356da6b 100
antoniogonzalez 0:7dbf7356da6b 101 // Resolution.
antoniogonzalez 0:7dbf7356da6b 102 typedef enum {
antoniogonzalez 0:7dbf7356da6b 103 RESOLUTION_12 = 0,
antoniogonzalez 0:7dbf7356da6b 104 RESOLUTION_14 = 1,
antoniogonzalez 0:7dbf7356da6b 105 RESOLUTION_16 = 2,
antoniogonzalez 0:7dbf7356da6b 106 RESOLUTION_18 = 3
antoniogonzalez 0:7dbf7356da6b 107 } mcp342x_resolution_t;
antoniogonzalez 0:7dbf7356da6b 108
antoniogonzalez 0:7dbf7356da6b 109 // Conversion mode.
antoniogonzalez 0:7dbf7356da6b 110 typedef enum {
antoniogonzalez 0:7dbf7356da6b 111 CONVERSION_MODE_ONESHOT = 0,
antoniogonzalez 0:7dbf7356da6b 112 CONVERSION_MODE_CONTINUOUS = 1
antoniogonzalez 0:7dbf7356da6b 113 } mcp342x_conversion_mode_t;
antoniogonzalez 0:7dbf7356da6b 114
antoniogonzalez 0:7dbf7356da6b 115 // Channels.
antoniogonzalez 0:7dbf7356da6b 116 typedef enum {
antoniogonzalez 0:7dbf7356da6b 117 CHANNEL_1 = 0,
antoniogonzalez 0:7dbf7356da6b 118 CHANNEL_2 = 1,
antoniogonzalez 0:7dbf7356da6b 119 CHANNEL_3 = 2,
antoniogonzalez 0:7dbf7356da6b 120 CHANNEL_4 = 3
antoniogonzalez 0:7dbf7356da6b 121 } mcp342x_channel_t;
antoniogonzalez 0:7dbf7356da6b 122
antoniogonzalez 0:7dbf7356da6b 123 /**
antoniogonzalez 0:7dbf7356da6b 124 * MCP342x constructor
antoniogonzalez 0:7dbf7356da6b 125 *
antoniogonzalez 0:7dbf7356da6b 126 * @param i2c Pointer to I2C
antoniogonzalez 0:7dbf7356da6b 127 * @param device_address Address for this sensor
antoniogonzalez 0:7dbf7356da6b 128 */
antoniogonzalez 0:7dbf7356da6b 129 MCP342x(I2C *i2c, uint8_t device_address = 0b000);
antoniogonzalez 0:7dbf7356da6b 130
antoniogonzalez 0:7dbf7356da6b 131 /**
antoniogonzalez 0:7dbf7356da6b 132 * Set channel to read from.
antoniogonzalez 0:7dbf7356da6b 133 *
antoniogonzalez 0:7dbf7356da6b 134 * @param channel Channel number
antoniogonzalez 0:7dbf7356da6b 135 */
antoniogonzalez 0:7dbf7356da6b 136 void set_channel(mcp342x_channel_t channel);
antoniogonzalez 0:7dbf7356da6b 137
antoniogonzalez 0:7dbf7356da6b 138 /**
antoniogonzalez 0:7dbf7356da6b 139 * Set conversion mode.
antoniogonzalez 0:7dbf7356da6b 140 *
antoniogonzalez 0:7dbf7356da6b 141 * @param mode Conversion mode. Options are
antoniogonzalez 0:7dbf7356da6b 142 * MCP342x::CONVERSION_MODE_ONESHOT or
antoniogonzalez 0:7dbf7356da6b 143 * MCP342x::CONVERSION_MODE_CONTINUOUS.
antoniogonzalez 0:7dbf7356da6b 144 */
antoniogonzalez 0:7dbf7356da6b 145 void set_conversion_mode(mcp342x_conversion_mode_t mode);
antoniogonzalez 0:7dbf7356da6b 146
antoniogonzalez 0:7dbf7356da6b 147 /**
antoniogonzalez 0:7dbf7356da6b 148 * Set resolution.
antoniogonzalez 0:7dbf7356da6b 149 *
antoniogonzalez 0:7dbf7356da6b 150 * @param resolution Resolution, one of
antoniogonzalez 0:7dbf7356da6b 151 * MCP342x::RESOLUTION_12, MCP342x::RESOLUTION_14,
antoniogonzalez 0:7dbf7356da6b 152 * MCP342x::RESOLUTION_16 or MCP342x::RESOLUTION_18.
antoniogonzalez 0:7dbf7356da6b 153 */
antoniogonzalez 0:7dbf7356da6b 154 void set_resolution(mcp342x_resolution_t resolution);
antoniogonzalez 0:7dbf7356da6b 155
antoniogonzalez 0:7dbf7356da6b 156 /**
antoniogonzalez 0:7dbf7356da6b 157 * Set programable gain amplifier. Options are
antoniogonzalez 0:7dbf7356da6b 158 * MCP342x::PGA_1, MCP342x::PGA_2, MCP342x::PGA_4, or MCP342x::PGA_8.
antoniogonzalez 0:7dbf7356da6b 159 */
antoniogonzalez 0:7dbf7356da6b 160 void set_pga(mcp342x_pga_t pga);
antoniogonzalez 0:7dbf7356da6b 161
antoniogonzalez 0:7dbf7356da6b 162 /**
antoniogonzalez 0:7dbf7356da6b 163 * Read the ADC value. The value will be that read from the channel
antoniogonzalez 0:7dbf7356da6b 164 * set previously (`set_channel`)
antoniogonzalez 0:7dbf7356da6b 165 *
antoniogonzalez 0:7dbf7356da6b 166 * @return Analog measurement in raw data (integer)
antoniogonzalez 0:7dbf7356da6b 167 */
antoniogonzalez 0:7dbf7356da6b 168 long read();
antoniogonzalez 0:7dbf7356da6b 169
antoniogonzalez 0:7dbf7356da6b 170 /**
antoniogonzalez 0:7dbf7356da6b 171 * Read the ADC value in volts. The value will be that read from the
antoniogonzalez 0:7dbf7356da6b 172 * channel set previously (`set_channel`).
antoniogonzalez 0:7dbf7356da6b 173 *
antoniogonzalez 0:7dbf7356da6b 174 * The data are coded in two's complements format, and the final
antoniogonzalez 0:7dbf7356da6b 175 * voltage is also a function of the resolution and gain settings.
antoniogonzalez 0:7dbf7356da6b 176 * This function follows the equations presented in the device's
antoniogonzalez 0:7dbf7356da6b 177 * datasheet (Microchip DS22088C), Section 4.9.
antoniogonzalez 0:7dbf7356da6b 178 *
antoniogonzalez 0:7dbf7356da6b 179 * @return Analog measurement in volts (float)
antoniogonzalez 0:7dbf7356da6b 180 */
antoniogonzalez 0:7dbf7356da6b 181 float read_volts();
antoniogonzalez 0:7dbf7356da6b 182
antoniogonzalez 0:7dbf7356da6b 183 private:
antoniogonzalez 0:7dbf7356da6b 184 uint8_t _address;
antoniogonzalez 0:7dbf7356da6b 185 I2C *_i2c;
antoniogonzalez 0:7dbf7356da6b 186 uint8_t _resolution;
antoniogonzalez 0:7dbf7356da6b 187 uint8_t _pga;
antoniogonzalez 0:7dbf7356da6b 188 char _configuration[1];
antoniogonzalez 0:7dbf7356da6b 189 static const uint8_t _device_code = 0b1101; // Hardcoded in factory
antoniogonzalez 0:7dbf7356da6b 190 void _write_configuration();
antoniogonzalez 0:7dbf7356da6b 191 };
antoniogonzalez 0:7dbf7356da6b 192
antoniogonzalez 0:7dbf7356da6b 193 //void mcp342x_start_conversion(void); For one-shot mode.
antoniogonzalez 0:7dbf7356da6b 194
antoniogonzalez 0:7dbf7356da6b 195 #endif