![](/media/cache/img/default_profile.jpg.50x50_q85.jpg)
I2C not yet integrated
Tested working with single and differential voltages.
Connect SCL (pin 11) to D15 Connect SDA (pin 10) to D14 Connect pin 16 to +5v Connect pin 9 to gnd
LTC2991.cpp@2:c9e727dcd00e, 2016-12-06 (annotated)
- Committer:
- lrdawg99
- Date:
- Tue Dec 06 18:34:46 2016 +0000
- Revision:
- 2:c9e727dcd00e
- Parent:
- 1:4e4194db7cd6
- Child:
- 4:85017622b676
made object oriented
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
lrdawg99 | 0:1473318f27b6 | 1 | /*! |
lrdawg99 | 0:1473318f27b6 | 2 | LTC2991: 14-bit Octal I2C Voltage, Current, and Temperature Monitor |
lrdawg99 | 0:1473318f27b6 | 3 | |
lrdawg99 | 0:1473318f27b6 | 4 | @verbatim |
lrdawg99 | 0:1473318f27b6 | 5 | |
lrdawg99 | 0:1473318f27b6 | 6 | The LTC2991 is used to monitor system temperatures, voltages and currents. |
lrdawg99 | 0:1473318f27b6 | 7 | Through the I2C serial interface, the eight monitors can individually measure |
lrdawg99 | 0:1473318f27b6 | 8 | supply voltages and can be paired for differential measurements of current sense |
lrdawg99 | 0:1473318f27b6 | 9 | resistors or temperature sensing transistors. Additional measurements include |
lrdawg99 | 0:1473318f27b6 | 10 | internal temperature and internal VCC. The internal 10ppm reference minimizes |
lrdawg99 | 0:1473318f27b6 | 11 | the number of supporting components and area required. Selectable address and |
lrdawg99 | 0:1473318f27b6 | 12 | configurable functionality give the LTC2991 flexibility to be incorporated in |
lrdawg99 | 0:1473318f27b6 | 13 | various systems needing temperature, voltage or current data. The LTC2991 fits |
lrdawg99 | 0:1473318f27b6 | 14 | well in systems needing submillivolt voltage resolution, 1% current measurement |
lrdawg99 | 0:1473318f27b6 | 15 | and 1 degree Celsius temperature accuracy or any combination of the three. |
lrdawg99 | 0:1473318f27b6 | 16 | |
lrdawg99 | 0:1473318f27b6 | 17 | @endverbatim |
lrdawg99 | 0:1473318f27b6 | 18 | |
lrdawg99 | 0:1473318f27b6 | 19 | http://www.linear.com/product/LTC2991 |
lrdawg99 | 0:1473318f27b6 | 20 | |
lrdawg99 | 0:1473318f27b6 | 21 | http://www.linear.com/product/LTC2991#demoboards |
lrdawg99 | 0:1473318f27b6 | 22 | |
lrdawg99 | 0:1473318f27b6 | 23 | REVISION HISTORY |
lrdawg99 | 0:1473318f27b6 | 24 | $Revision: 3659 $ |
lrdawg99 | 0:1473318f27b6 | 25 | $Date: 2015-07-01 10:19:20 -0700 (Wed, 01 Jul 2015) $ |
lrdawg99 | 0:1473318f27b6 | 26 | |
lrdawg99 | 0:1473318f27b6 | 27 | Copyright (c) 2013, Linear Technology Corp.(LTC) |
lrdawg99 | 0:1473318f27b6 | 28 | All rights reserved. |
lrdawg99 | 0:1473318f27b6 | 29 | |
lrdawg99 | 0:1473318f27b6 | 30 | Redistribution and use in source and binary forms, with or without |
lrdawg99 | 0:1473318f27b6 | 31 | modification, are permitted provided that the following conditions are met: |
lrdawg99 | 0:1473318f27b6 | 32 | |
lrdawg99 | 0:1473318f27b6 | 33 | 1. Redistributions of source code must retain the above copyright notice, this |
lrdawg99 | 0:1473318f27b6 | 34 | list of conditions and the following disclaimer. |
lrdawg99 | 0:1473318f27b6 | 35 | 2. Redistributions in binary form must reproduce the above copyright notice, |
lrdawg99 | 0:1473318f27b6 | 36 | this list of conditions and the following disclaimer in the documentation |
lrdawg99 | 0:1473318f27b6 | 37 | and/or other materials provided with the distribution. |
lrdawg99 | 0:1473318f27b6 | 38 | |
lrdawg99 | 0:1473318f27b6 | 39 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND |
lrdawg99 | 0:1473318f27b6 | 40 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
lrdawg99 | 0:1473318f27b6 | 41 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
lrdawg99 | 0:1473318f27b6 | 42 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR |
lrdawg99 | 0:1473318f27b6 | 43 | ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
lrdawg99 | 0:1473318f27b6 | 44 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
lrdawg99 | 0:1473318f27b6 | 45 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
lrdawg99 | 0:1473318f27b6 | 46 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
lrdawg99 | 0:1473318f27b6 | 47 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
lrdawg99 | 0:1473318f27b6 | 48 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
lrdawg99 | 0:1473318f27b6 | 49 | |
lrdawg99 | 0:1473318f27b6 | 50 | The views and conclusions contained in the software and documentation are those |
lrdawg99 | 0:1473318f27b6 | 51 | of the authors and should not be interpreted as representing official policies, |
lrdawg99 | 0:1473318f27b6 | 52 | either expressed or implied, of Linear Technology Corp. |
lrdawg99 | 0:1473318f27b6 | 53 | |
lrdawg99 | 0:1473318f27b6 | 54 | The Linear Technology Linduino is not affiliated with the official Arduino team. |
lrdawg99 | 0:1473318f27b6 | 55 | However, the Linduino is only possible because of the Arduino team's commitment |
lrdawg99 | 0:1473318f27b6 | 56 | to the open-source community. Please, visit http://www.arduino.cc and |
lrdawg99 | 0:1473318f27b6 | 57 | http://store.arduino.cc , and consider a purchase that will help fund their |
lrdawg99 | 0:1473318f27b6 | 58 | ongoing work. |
lrdawg99 | 0:1473318f27b6 | 59 | */ |
lrdawg99 | 0:1473318f27b6 | 60 | |
lrdawg99 | 0:1473318f27b6 | 61 | //! @defgroup LTC2991 LTC2991: 14-bit Octal I2C Voltage, Current, and Temperature Monitor |
lrdawg99 | 0:1473318f27b6 | 62 | |
lrdawg99 | 0:1473318f27b6 | 63 | /*! @file |
lrdawg99 | 0:1473318f27b6 | 64 | @ingroup LTC2991 |
lrdawg99 | 0:1473318f27b6 | 65 | Library for LTC2991: 14-bit Octal I2C Voltage, Current, and Temperature Monitor |
lrdawg99 | 0:1473318f27b6 | 66 | */ |
lrdawg99 | 0:1473318f27b6 | 67 | |
lrdawg99 | 0:1473318f27b6 | 68 | #include <stdint.h> |
lrdawg99 | 0:1473318f27b6 | 69 | #include "Linduino.h" |
lrdawg99 | 0:1473318f27b6 | 70 | #include "LT_I2C.h" |
lrdawg99 | 0:1473318f27b6 | 71 | #include "LTC2991.h" |
lrdawg99 | 0:1473318f27b6 | 72 | #include "mbed.h" |
lrdawg99 | 0:1473318f27b6 | 73 | |
lrdawg99 | 1:4e4194db7cd6 | 74 | Serial pc2(USBTX, USBRX, 9600); |
lrdawg99 | 1:4e4194db7cd6 | 75 | |
lrdawg99 | 2:c9e727dcd00e | 76 | LTC2991::LTC2991() { |
lrdawg99 | 2:c9e727dcd00e | 77 | lti2c = new LT_I2C(); |
lrdawg99 | 2:c9e727dcd00e | 78 | } |
lrdawg99 | 2:c9e727dcd00e | 79 | |
lrdawg99 | 2:c9e727dcd00e | 80 | LTC2991::LTC2991(PinName i2c_scl_, PinName i2c_sda_) { |
lrdawg99 | 2:c9e727dcd00e | 81 | lti2c = new LT_I2C(i2c_scl_, i2c_sda_); |
lrdawg99 | 2:c9e727dcd00e | 82 | } |
lrdawg99 | 0:1473318f27b6 | 83 | |
lrdawg99 | 0:1473318f27b6 | 84 | // Reads a 14-bit adc_code from LTC2991. |
lrdawg99 | 2:c9e727dcd00e | 85 | int8_t LTC2991::LTC2991_adc_read(uint8_t i2c_address, uint8_t msb_register_address, int16_t *adc_code, int8_t *data_valid) |
lrdawg99 | 0:1473318f27b6 | 86 | { |
lrdawg99 | 0:1473318f27b6 | 87 | int8_t ack = 0; |
lrdawg99 | 0:1473318f27b6 | 88 | uint16_t code; |
lrdawg99 | 2:c9e727dcd00e | 89 | ack = lti2c->i2c_read_word_data(i2c_address, msb_register_address, &code); |
lrdawg99 | 1:4e4194db7cd6 | 90 | |
lrdawg99 | 0:1473318f27b6 | 91 | |
lrdawg99 | 0:1473318f27b6 | 92 | *data_valid = (code >> 15) & 0x01; // Place Data Valid Bit in *data_valid |
lrdawg99 | 0:1473318f27b6 | 93 | |
lrdawg99 | 0:1473318f27b6 | 94 | *adc_code = code & 0x7FFF; // Removes data valid bit to return proper adc_code value |
lrdawg99 | 1:4e4194db7cd6 | 95 | |
lrdawg99 | 1:4e4194db7cd6 | 96 | //pc2.printf("i2c_read_word_data result: raw code: %0x%X, ack %d\n", code, ack); |
lrdawg99 | 0:1473318f27b6 | 97 | |
lrdawg99 | 0:1473318f27b6 | 98 | return(ack); |
lrdawg99 | 0:1473318f27b6 | 99 | } |
lrdawg99 | 0:1473318f27b6 | 100 | |
lrdawg99 | 0:1473318f27b6 | 101 | // Reads a 14-bit adc_code from the LTC2991 but enforces a maximum timeout. |
lrdawg99 | 0:1473318f27b6 | 102 | // Similar to LTC2991_adc_read except it repeats until the data_valid bit is set, it fails to receive an I2C acknowledge, or the timeout (in milliseconds) |
lrdawg99 | 0:1473318f27b6 | 103 | // expires. It keeps trying to read from the LTC2991 every millisecond until the data_valid bit is set (indicating new data since the previous |
lrdawg99 | 0:1473318f27b6 | 104 | // time this register was read) or until it fails to receive an I2C acknowledge (indicating an error on the I2C bus). |
lrdawg99 | 2:c9e727dcd00e | 105 | int8_t LTC2991::LTC2991_adc_read_timeout(uint8_t i2c_address, uint8_t msb_register_address, int16_t *adc_code, int8_t *data_valid, uint16_t timeout, uint8_t status_bit) |
lrdawg99 | 0:1473318f27b6 | 106 | { |
lrdawg99 | 0:1473318f27b6 | 107 | int8_t ack = 0; |
lrdawg99 | 0:1473318f27b6 | 108 | uint8_t reg_data; |
lrdawg99 | 0:1473318f27b6 | 109 | uint16_t timer_count; // Timer count for data_valid |
lrdawg99 | 0:1473318f27b6 | 110 | |
lrdawg99 | 0:1473318f27b6 | 111 | for (timer_count = 0; timer_count < timeout; timer_count++) |
lrdawg99 | 0:1473318f27b6 | 112 | { |
lrdawg99 | 1:4e4194db7cd6 | 113 | //pc2.printf("status_bit: %d\n", status_bit); |
lrdawg99 | 1:4e4194db7cd6 | 114 | |
lrdawg99 | 0:1473318f27b6 | 115 | if (status_bit<8) |
lrdawg99 | 0:1473318f27b6 | 116 | { |
lrdawg99 | 0:1473318f27b6 | 117 | ack |= LTC2991_register_read(i2c_address, LTC2991_STATUS_LOW_REG, ®_data); //! 1)Read status register until correct data valid bit is set |
lrdawg99 | 0:1473318f27b6 | 118 | } |
lrdawg99 | 0:1473318f27b6 | 119 | else |
lrdawg99 | 0:1473318f27b6 | 120 | { |
lrdawg99 | 0:1473318f27b6 | 121 | ack |= LTC2991_register_read(i2c_address, LTC2991_STATUS_HIGH_REG, ®_data); //! 1)Read status register until correct data valid bit is set |
lrdawg99 | 0:1473318f27b6 | 122 | if (status_bit==8) |
lrdawg99 | 0:1473318f27b6 | 123 | { |
lrdawg99 | 0:1473318f27b6 | 124 | status_bit =1; |
lrdawg99 | 0:1473318f27b6 | 125 | } |
lrdawg99 | 0:1473318f27b6 | 126 | else |
lrdawg99 | 0:1473318f27b6 | 127 | { |
lrdawg99 | 0:1473318f27b6 | 128 | status_bit = 0; |
lrdawg99 | 0:1473318f27b6 | 129 | } |
lrdawg99 | 0:1473318f27b6 | 130 | } |
lrdawg99 | 1:4e4194db7cd6 | 131 | |
lrdawg99 | 0:1473318f27b6 | 132 | if ((ack) || (((reg_data>>status_bit)&0x1)==1)) |
lrdawg99 | 0:1473318f27b6 | 133 | { |
lrdawg99 | 0:1473318f27b6 | 134 | break; |
lrdawg99 | 0:1473318f27b6 | 135 | } |
lrdawg99 | 0:1473318f27b6 | 136 | |
lrdawg99 | 0:1473318f27b6 | 137 | wait_ms(1); |
lrdawg99 | 0:1473318f27b6 | 138 | } |
lrdawg99 | 0:1473318f27b6 | 139 | |
lrdawg99 | 0:1473318f27b6 | 140 | ack |= LTC2991_adc_read(i2c_address, msb_register_address, &(*adc_code), &(*data_valid)); //! 2) It's either valid or it's timed out, we read anyways |
lrdawg99 | 0:1473318f27b6 | 141 | if (*data_valid !=1) |
lrdawg99 | 0:1473318f27b6 | 142 | { |
lrdawg99 | 1:4e4194db7cd6 | 143 | pc2.printf("Data not valid: 0x%X\n", *data_valid); |
lrdawg99 | 0:1473318f27b6 | 144 | return (1); |
lrdawg99 | 0:1473318f27b6 | 145 | } |
lrdawg99 | 1:4e4194db7cd6 | 146 | |
lrdawg99 | 0:1473318f27b6 | 147 | return(ack); |
lrdawg99 | 0:1473318f27b6 | 148 | } |
lrdawg99 | 0:1473318f27b6 | 149 | |
lrdawg99 | 0:1473318f27b6 | 150 | // Reads new data (even after a mode change) by flushing old data and waiting for the data_valid bit to be set. |
lrdawg99 | 0:1473318f27b6 | 151 | // This function simplifies adc reads when modes are changing. For example, if V1-V2 changes from temperature mode |
lrdawg99 | 0:1473318f27b6 | 152 | // to differential voltage mode, the data in the register may still correspond to the temperature reading immediately |
lrdawg99 | 0:1473318f27b6 | 153 | // after the mode change. Flushing one reading and waiting for a new reading guarantees fresh data is received. |
lrdawg99 | 0:1473318f27b6 | 154 | // If the timeout is reached without valid data (*data_valid=1) the function exits. |
lrdawg99 | 2:c9e727dcd00e | 155 | int8_t LTC2991::LTC2991_adc_read_new_data(uint8_t i2c_address, uint8_t msb_register_address, int16_t *adc_code, int8_t *data_valid, uint16_t timeout) |
lrdawg99 | 0:1473318f27b6 | 156 | { |
lrdawg99 | 0:1473318f27b6 | 157 | int8_t ack = 0; |
lrdawg99 | 0:1473318f27b6 | 158 | |
lrdawg99 | 0:1473318f27b6 | 159 | ack |= LTC2991_adc_read_timeout(i2c_address, msb_register_address, &(*adc_code), &(*data_valid), timeout, ((msb_register_address/2) - 0x05)); //! 1) Throw away old data |
lrdawg99 | 0:1473318f27b6 | 160 | ack |= LTC2991_adc_read_timeout(i2c_address, msb_register_address, &(*adc_code), &(*data_valid), timeout, ((msb_register_address/2) - 0x05)); //! 2) Read new data |
lrdawg99 | 0:1473318f27b6 | 161 | |
lrdawg99 | 0:1473318f27b6 | 162 | return(ack); |
lrdawg99 | 0:1473318f27b6 | 163 | } |
lrdawg99 | 0:1473318f27b6 | 164 | |
lrdawg99 | 0:1473318f27b6 | 165 | // Reads an 8-bit register from the LTC2991 using the standard repeated start format. |
lrdawg99 | 2:c9e727dcd00e | 166 | int8_t LTC2991::LTC2991_register_read(uint8_t i2c_address, uint8_t register_address, uint8_t *register_data) |
lrdawg99 | 0:1473318f27b6 | 167 | { |
lrdawg99 | 0:1473318f27b6 | 168 | int8_t ack = 0; |
lrdawg99 | 2:c9e727dcd00e | 169 | ack = lti2c->i2c_read_byte_data(i2c_address, register_address, register_data); |
lrdawg99 | 0:1473318f27b6 | 170 | return(ack); |
lrdawg99 | 0:1473318f27b6 | 171 | } |
lrdawg99 | 0:1473318f27b6 | 172 | |
lrdawg99 | 0:1473318f27b6 | 173 | // Write one byte to an LTC2991 register. |
lrdawg99 | 0:1473318f27b6 | 174 | // Writes to an 8-bit register inside the LTC2991 using the standard I2C repeated start format. |
lrdawg99 | 2:c9e727dcd00e | 175 | int8_t LTC2991::LTC2991_register_write(uint8_t i2c_address, uint8_t register_address, uint8_t register_data) |
lrdawg99 | 0:1473318f27b6 | 176 | { |
lrdawg99 | 0:1473318f27b6 | 177 | int8_t ack = 0; |
lrdawg99 | 2:c9e727dcd00e | 178 | ack = lti2c->i2c_write_byte_data(i2c_address, register_address, register_data); |
lrdawg99 | 0:1473318f27b6 | 179 | return(ack); |
lrdawg99 | 0:1473318f27b6 | 180 | } |
lrdawg99 | 0:1473318f27b6 | 181 | |
lrdawg99 | 0:1473318f27b6 | 182 | // Used to set and clear bits in a control register. bits_to_set will be bitwise OR'd with the register. |
lrdawg99 | 0:1473318f27b6 | 183 | // bits_to_clear will be inverted and bitwise AND'd with the register so that every location with a 1 will result in a 0 in the register. |
lrdawg99 | 2:c9e727dcd00e | 184 | int8_t LTC2991::LTC2991_register_set_clear_bits(uint8_t i2c_address, uint8_t register_address, uint8_t bits_to_set, uint8_t bits_to_clear) |
lrdawg99 | 0:1473318f27b6 | 185 | { |
lrdawg99 | 0:1473318f27b6 | 186 | uint8_t register_data; |
lrdawg99 | 0:1473318f27b6 | 187 | int8_t ack = 0; |
lrdawg99 | 0:1473318f27b6 | 188 | |
lrdawg99 | 0:1473318f27b6 | 189 | ack |= LTC2991_register_read(i2c_address, register_address, ®ister_data); //! 1) Read register |
lrdawg99 | 0:1473318f27b6 | 190 | register_data = register_data & (~bits_to_clear); //! 2) Clear bits that were set to be cleared |
lrdawg99 | 0:1473318f27b6 | 191 | register_data = register_data | bits_to_set; |
lrdawg99 | 0:1473318f27b6 | 192 | ack |= LTC2991_register_write(i2c_address, register_address, register_data); //! 3) Write to register with the cleared bits |
lrdawg99 | 0:1473318f27b6 | 193 | return(ack); |
lrdawg99 | 0:1473318f27b6 | 194 | } |
lrdawg99 | 0:1473318f27b6 | 195 | |
lrdawg99 | 0:1473318f27b6 | 196 | // Calculates the LTC2991 single-ended input voltages |
lrdawg99 | 2:c9e727dcd00e | 197 | float LTC2991::LTC2991_code_to_single_ended_voltage(int16_t adc_code, float LTC2991_single_ended_lsb) |
lrdawg99 | 0:1473318f27b6 | 198 | { |
lrdawg99 | 0:1473318f27b6 | 199 | float voltage; |
lrdawg99 | 0:1473318f27b6 | 200 | int16_t sign = 1; |
lrdawg99 | 0:1473318f27b6 | 201 | if (adc_code >> 14) |
lrdawg99 | 0:1473318f27b6 | 202 | { |
lrdawg99 | 0:1473318f27b6 | 203 | adc_code = (adc_code ^ 0x7FFF) + 1; //! 1) Converts two's complement to binary |
lrdawg99 | 0:1473318f27b6 | 204 | sign = -1; |
lrdawg99 | 0:1473318f27b6 | 205 | } |
lrdawg99 | 0:1473318f27b6 | 206 | adc_code = (adc_code & 0x3FFF); |
lrdawg99 | 0:1473318f27b6 | 207 | voltage = ((float) adc_code) * LTC2991_single_ended_lsb * sign; //! 2) Convert code to voltage from lsb |
lrdawg99 | 0:1473318f27b6 | 208 | return (voltage); |
lrdawg99 | 0:1473318f27b6 | 209 | } |
lrdawg99 | 0:1473318f27b6 | 210 | |
lrdawg99 | 0:1473318f27b6 | 211 | // Calculates the LTC2991 Vcc voltage |
lrdawg99 | 2:c9e727dcd00e | 212 | float LTC2991::LTC2991_code_to_vcc_voltage(int16_t adc_code, float LTC2991_single_ended_lsb) |
lrdawg99 | 0:1473318f27b6 | 213 | { |
lrdawg99 | 0:1473318f27b6 | 214 | float voltage; |
lrdawg99 | 0:1473318f27b6 | 215 | int16_t sign = 1; |
lrdawg99 | 0:1473318f27b6 | 216 | if (adc_code >> 14) |
lrdawg99 | 0:1473318f27b6 | 217 | { |
lrdawg99 | 0:1473318f27b6 | 218 | adc_code = (adc_code ^ 0x7FFF) + 1; //! 1) Converts two's complement to binary |
lrdawg99 | 0:1473318f27b6 | 219 | sign = -1; |
lrdawg99 | 0:1473318f27b6 | 220 | } |
lrdawg99 | 0:1473318f27b6 | 221 | |
lrdawg99 | 0:1473318f27b6 | 222 | voltage = (((float) adc_code) * LTC2991_single_ended_lsb * sign) + 2.5; //! 2) Convert code to Vcc Voltage from single-ended lsb |
lrdawg99 | 0:1473318f27b6 | 223 | return (voltage); |
lrdawg99 | 0:1473318f27b6 | 224 | } |
lrdawg99 | 0:1473318f27b6 | 225 | |
lrdawg99 | 0:1473318f27b6 | 226 | // Calculates the LTC2991 differential input voltage. |
lrdawg99 | 2:c9e727dcd00e | 227 | float LTC2991::LTC2991_code_to_differential_voltage(int16_t adc_code, float LTC2991_differential_lsb) |
lrdawg99 | 0:1473318f27b6 | 228 | { |
lrdawg99 | 0:1473318f27b6 | 229 | float voltage; |
lrdawg99 | 0:1473318f27b6 | 230 | int16_t sign = 1; |
lrdawg99 | 0:1473318f27b6 | 231 | if (adc_code >> 14) |
lrdawg99 | 0:1473318f27b6 | 232 | { |
lrdawg99 | 0:1473318f27b6 | 233 | adc_code = (adc_code ^ 0x7FFF) + 1; //! 1)Converts two's complement to binary |
lrdawg99 | 0:1473318f27b6 | 234 | sign = -1; |
lrdawg99 | 0:1473318f27b6 | 235 | } |
lrdawg99 | 0:1473318f27b6 | 236 | voltage = ((float) adc_code) * LTC2991_differential_lsb * sign; //! 2) Convert code to voltage form differential lsb |
lrdawg99 | 0:1473318f27b6 | 237 | return (voltage); |
lrdawg99 | 0:1473318f27b6 | 238 | } |
lrdawg99 | 0:1473318f27b6 | 239 | |
lrdawg99 | 0:1473318f27b6 | 240 | // Calculates the LTC2991 temperature |
lrdawg99 | 2:c9e727dcd00e | 241 | float LTC2991::LTC2991_temperature(int16_t adc_code, float LTC2991_temperature_lsb, boolean unit) |
lrdawg99 | 0:1473318f27b6 | 242 | { |
lrdawg99 | 0:1473318f27b6 | 243 | float temperature; |
lrdawg99 | 0:1473318f27b6 | 244 | adc_code = (adc_code & 0x1FFF); //! 1) Removes first 3 bits |
lrdawg99 | 0:1473318f27b6 | 245 | if (!unit) //! 2)Checks to see if it's Kelvin |
lrdawg99 | 0:1473318f27b6 | 246 | { |
lrdawg99 | 0:1473318f27b6 | 247 | if (adc_code >>12) |
lrdawg99 | 0:1473318f27b6 | 248 | { |
lrdawg99 | 0:1473318f27b6 | 249 | adc_code = (adc_code | 0xE000); //! Sign extend if it's not Kelvin (Celsius) |
lrdawg99 | 0:1473318f27b6 | 250 | } |
lrdawg99 | 0:1473318f27b6 | 251 | } |
lrdawg99 | 0:1473318f27b6 | 252 | temperature = ((float) adc_code) * LTC2991_temperature_lsb; //! 3) Converts code to temperature from temperature lsb |
lrdawg99 | 0:1473318f27b6 | 253 | |
lrdawg99 | 0:1473318f27b6 | 254 | return (temperature); |
lrdawg99 | 0:1473318f27b6 | 255 | } |
lrdawg99 | 0:1473318f27b6 | 256 | |
lrdawg99 | 0:1473318f27b6 | 257 | // Calculates the LTC2991 diode voltage |
lrdawg99 | 2:c9e727dcd00e | 258 | float LTC2991::LTC2991_code_to_diode_voltage(int16_t adc_code, float LTC2991_diode_voltage_lsb) |
lrdawg99 | 0:1473318f27b6 | 259 | { |
lrdawg99 | 0:1473318f27b6 | 260 | float voltage; |
lrdawg99 | 0:1473318f27b6 | 261 | adc_code = (adc_code & 0x1FFF); //! 1) Removes first 3 bits |
lrdawg99 | 0:1473318f27b6 | 262 | voltage = ((float) adc_code) * LTC2991_diode_voltage_lsb; //! 2) Convert code to voltage from diode voltage lsb |
lrdawg99 | 0:1473318f27b6 | 263 | return (voltage); |
lrdawg99 | 0:1473318f27b6 | 264 | } |