I2C not yet integrated

Dependencies:   mbed

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

Committer:
lrdawg99
Date:
Tue Nov 29 03:20:35 2016 +0000
Revision:
1:4e4194db7cd6
Parent:
0:1473318f27b6
Child:
2:c9e727dcd00e
Tested working, reads single ended and differential voltages.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
lrdawg99 0:1473318f27b6 1
lrdawg99 0:1473318f27b6 2 /*!
lrdawg99 0:1473318f27b6 3 LT_I2C: Routines to communicate with ATmega328P's hardware I2C port.
lrdawg99 0:1473318f27b6 4
lrdawg99 0:1473318f27b6 5 @verbatim
lrdawg99 0:1473318f27b6 6
lrdawg99 0:1473318f27b6 7 LT_I2C contains the low level routines to communicate with devices using the
lrdawg99 0:1473318f27b6 8 ATMega328's onboard hardware I2C port. Each routine checks the Two Wire Status
lrdawg99 0:1473318f27b6 9 Register (TWSR) at the end of the transaction and returns 0 if successful and 1
lrdawg99 0:1473318f27b6 10 if not successful.
lrdawg99 0:1473318f27b6 11
lrdawg99 0:1473318f27b6 12 I2C Frequency = (CPU Clock frequency)/(16+2(TWBR)*Prescaler)
lrdawg99 0:1473318f27b6 13
lrdawg99 0:1473318f27b6 14 TWBR-Two Wire Bit Rate Register
lrdawg99 0:1473318f27b6 15 TWCR=Two Wire Control Register (TWINT TWEA TWSTA TWSTO TWWC TWEN - TWIE)
lrdawg99 0:1473318f27b6 16 TWSR=Two Wire Status Register
lrdawg99 0:1473318f27b6 17
lrdawg99 0:1473318f27b6 18 Prescaler Values:
lrdawg99 0:1473318f27b6 19 TWSR1 TWSR0 Prescaler
lrdawg99 0:1473318f27b6 20 0 0 1
lrdawg99 0:1473318f27b6 21 0 1 4
lrdawg99 0:1473318f27b6 22 1 0 16
lrdawg99 0:1473318f27b6 23 1 1 64
lrdawg99 0:1473318f27b6 24
lrdawg99 0:1473318f27b6 25 Examples:
lrdawg99 0:1473318f27b6 26 CPU Frequency = 16Mhz on Arduino Uno
lrdawg99 0:1473318f27b6 27 I2C Frequency Prescaler TWSR1 TWSR0 TWBR
lrdawg99 0:1473318f27b6 28 1khz 64 1 1 125
lrdawg99 0:1473318f27b6 29 10khz 64 1 1 12
lrdawg99 0:1473318f27b6 30 50khz 16 1 0 10
lrdawg99 0:1473318f27b6 31 100khz 4 0 1 18
lrdawg99 0:1473318f27b6 32 400khz 1 0 0 12
lrdawg99 0:1473318f27b6 33
lrdawg99 0:1473318f27b6 34 @endverbatim
lrdawg99 0:1473318f27b6 35
lrdawg99 0:1473318f27b6 36 REVISION HISTORY
lrdawg99 0:1473318f27b6 37 $Revision: 5469 $
lrdawg99 0:1473318f27b6 38 $Date: 2016-07-22 17:01:32 -0700 (Fri, 22 Jul 2016) $
lrdawg99 0:1473318f27b6 39
lrdawg99 0:1473318f27b6 40 Copyright (c) 2013, Linear Technology Corp.(LTC)
lrdawg99 0:1473318f27b6 41 All rights reserved.
lrdawg99 0:1473318f27b6 42
lrdawg99 0:1473318f27b6 43 Redistribution and use in source and binary forms, with or without
lrdawg99 0:1473318f27b6 44 modification, are permitted provided that the following conditions are met:
lrdawg99 0:1473318f27b6 45
lrdawg99 0:1473318f27b6 46 1. Redistributions of source code must retain the above copyright notice, this
lrdawg99 0:1473318f27b6 47 list of conditions and the following disclaimer.
lrdawg99 0:1473318f27b6 48 2. Redistributions in binary form must reproduce the above copyright notice,
lrdawg99 0:1473318f27b6 49 this list of conditions and the following disclaimer in the documentation
lrdawg99 0:1473318f27b6 50 and/or other materials provided with the distribution.
lrdawg99 0:1473318f27b6 51
lrdawg99 0:1473318f27b6 52 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
lrdawg99 0:1473318f27b6 53 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
lrdawg99 0:1473318f27b6 54 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
lrdawg99 0:1473318f27b6 55 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
lrdawg99 0:1473318f27b6 56 ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
lrdawg99 0:1473318f27b6 57 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
lrdawg99 0:1473318f27b6 58 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
lrdawg99 0:1473318f27b6 59 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
lrdawg99 0:1473318f27b6 60 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
lrdawg99 0:1473318f27b6 61 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
lrdawg99 0:1473318f27b6 62
lrdawg99 0:1473318f27b6 63 The views and conclusions contained in the software and documentation are those
lrdawg99 0:1473318f27b6 64 of the authors and should not be interpreted as representing official policies,
lrdawg99 0:1473318f27b6 65 either expressed or implied, of Linear Technology Corp.
lrdawg99 0:1473318f27b6 66
lrdawg99 0:1473318f27b6 67 The Linear Technology Linduino is not affiliated with the official Arduino team.
lrdawg99 0:1473318f27b6 68 However, the Linduino is only possible because of the Arduino team's commitment
lrdawg99 0:1473318f27b6 69 to the open-source community. Please, visit http://www.arduino.cc and
lrdawg99 0:1473318f27b6 70 http://store.arduino.cc , and consider a purchase that will help fund their
lrdawg99 0:1473318f27b6 71 ongoing work.
lrdawg99 0:1473318f27b6 72 */
lrdawg99 0:1473318f27b6 73
lrdawg99 0:1473318f27b6 74 //! @defgroup LT_I2C LT_I2C: Routines to Communicate With ATmega328P's hardware I2C port.
lrdawg99 0:1473318f27b6 75
lrdawg99 0:1473318f27b6 76 /*! @file
lrdawg99 0:1473318f27b6 77 @ingroup LT_I2C
lrdawg99 0:1473318f27b6 78 Library for LT_I2C: Routines to Communicate With ATmega328P's hardware I2C port.
lrdawg99 0:1473318f27b6 79 */
lrdawg99 0:1473318f27b6 80
lrdawg99 0:1473318f27b6 81 //#include <Arduino.h>
lrdawg99 0:1473318f27b6 82 #include <stdint.h>
lrdawg99 0:1473318f27b6 83 //#include <util/delay.h>
lrdawg99 0:1473318f27b6 84 #include "Linduino.h"
lrdawg99 0:1473318f27b6 85 #include "LT_I2C.h"
lrdawg99 1:4e4194db7cd6 86 #include "mbed.h"
lrdawg99 0:1473318f27b6 87
lrdawg99 0:1473318f27b6 88 //! CPU master clock frequency
lrdawg99 0:1473318f27b6 89 #ifndef F_CPU
lrdawg99 0:1473318f27b6 90 #define F_CPU 16000000UL
lrdawg99 0:1473318f27b6 91 #endif
lrdawg99 1:4e4194db7cd6 92 Serial pc1(USBTX, USBRX, 9600);
lrdawg99 0:1473318f27b6 93
lrdawg99 0:1473318f27b6 94
lrdawg99 1:4e4194db7cd6 95 I2C i2c(I2C_SDA , I2C_SCL);
lrdawg99 0:1473318f27b6 96
lrdawg99 0:1473318f27b6 97 // Read a byte of data at register specified by "command", store in "value"
lrdawg99 0:1473318f27b6 98 int8_t i2c_read_byte_data(uint8_t address, uint8_t command, uint8_t *value)
lrdawg99 0:1473318f27b6 99 {
lrdawg99 1:4e4194db7cd6 100 int8_t ret = 0;
lrdawg99 1:4e4194db7cd6 101
lrdawg99 1:4e4194db7cd6 102 char cmd1[1];
lrdawg99 1:4e4194db7cd6 103 cmd1[0] = command;
lrdawg99 1:4e4194db7cd6 104 char v[1];
lrdawg99 1:4e4194db7cd6 105 v[0] = 0;
lrdawg99 1:4e4194db7cd6 106
lrdawg99 1:4e4194db7cd6 107 ret |= i2c.write((address<<1) | I2C_WRITE_BIT, cmd1, 1, true);
lrdawg99 1:4e4194db7cd6 108 ret |= i2c.read((address<<1) | I2C_READ_BIT, v, 1, false);
lrdawg99 1:4e4194db7cd6 109
lrdawg99 1:4e4194db7cd6 110 *value = v[0];
lrdawg99 1:4e4194db7cd6 111
lrdawg99 1:4e4194db7cd6 112 if (ret == 0) {
lrdawg99 1:4e4194db7cd6 113 return 0; //success
lrdawg99 1:4e4194db7cd6 114 }
lrdawg99 1:4e4194db7cd6 115 return(1);
lrdawg99 0:1473318f27b6 116 }
lrdawg99 0:1473318f27b6 117
lrdawg99 0:1473318f27b6 118 // Write a byte of data to register specified by "command"
lrdawg99 0:1473318f27b6 119 int8_t i2c_write_byte_data(uint8_t address, uint8_t command, uint8_t value)
lrdawg99 0:1473318f27b6 120 {
lrdawg99 1:4e4194db7cd6 121 int8_t ret = 0;
lrdawg99 1:4e4194db7cd6 122 char cmd[2];
lrdawg99 1:4e4194db7cd6 123 cmd[0] = command;
lrdawg99 1:4e4194db7cd6 124 cmd[1] = value;
lrdawg99 1:4e4194db7cd6 125 ret |= i2c.write((address<<1) | I2C_WRITE_BIT, cmd, 2, false);
lrdawg99 1:4e4194db7cd6 126
lrdawg99 1:4e4194db7cd6 127 if (ret == 0) {
lrdawg99 1:4e4194db7cd6 128 return 0; //success
lrdawg99 1:4e4194db7cd6 129 }
lrdawg99 1:4e4194db7cd6 130 return(1);
lrdawg99 0:1473318f27b6 131 }
lrdawg99 0:1473318f27b6 132
lrdawg99 1:4e4194db7cd6 133 //// Read a byte of data at register specified by "command", store in "value"
lrdawg99 1:4e4194db7cd6 134 //int8_t i2c_read_byte_data(uint8_t address, uint8_t command, uint8_t *value)
lrdawg99 1:4e4194db7cd6 135 //{
lrdawg99 1:4e4194db7cd6 136 // checkDevice();
lrdawg99 1:4e4194db7cd6 137 // int8_t ret = 1;
lrdawg99 1:4e4194db7cd6 138 //
lrdawg99 1:4e4194db7cd6 139 // i2c.start(); // I2C START
lrdawg99 1:4e4194db7cd6 140 // ret &= i2c.write((address<<1) | I2C_WRITE_BIT); // Write 7 bit address with W bit
lrdawg99 1:4e4194db7cd6 141 // pc1.printf("[read] ret 0: %d\n", ret);
lrdawg99 1:4e4194db7cd6 142 // ret &= i2c.write(command); // Set register to be read to command
lrdawg99 1:4e4194db7cd6 143 // pc1.printf("[read] ret 1: %d\n", ret);
lrdawg99 1:4e4194db7cd6 144 // i2c.start(); //2nd start condition
lrdawg99 1:4e4194db7cd6 145 // ret &= i2c.write((address<<1) | I2C_READ_BIT); // Write 7 bit address with R bit
lrdawg99 1:4e4194db7cd6 146 // pc1.printf("[read] ret 2: %d\n", ret);
lrdawg99 1:4e4194db7cd6 147 // *value = i2c.read(WITH_NACK); // Read byte from buffer with *NAK*
lrdawg99 1:4e4194db7cd6 148 // i2c.stop(); // I2C STOP
lrdawg99 1:4e4194db7cd6 149 // if (ret == 1) {
lrdawg99 1:4e4194db7cd6 150 // return 0; //success
lrdawg99 1:4e4194db7cd6 151 // }
lrdawg99 1:4e4194db7cd6 152 // return(1);
lrdawg99 1:4e4194db7cd6 153 //}
lrdawg99 1:4e4194db7cd6 154 //
lrdawg99 1:4e4194db7cd6 155 //// Write a byte of data to register specified by "command"
lrdawg99 1:4e4194db7cd6 156 //int8_t i2c_write_byte_data(uint8_t address, uint8_t command, uint8_t value)
lrdawg99 1:4e4194db7cd6 157 //{
lrdawg99 1:4e4194db7cd6 158 // checkDevice();
lrdawg99 1:4e4194db7cd6 159 // int8_t ret = 1;
lrdawg99 1:4e4194db7cd6 160 //
lrdawg99 1:4e4194db7cd6 161 // i2c.start(); // I2C START
lrdawg99 1:4e4194db7cd6 162 // ret &= i2c.write((address<<1) | I2C_WRITE_BIT); // Write 7 bit address with W bit
lrdawg99 1:4e4194db7cd6 163 // pc1.printf("[write] ret 0: %d\n", ret);
lrdawg99 1:4e4194db7cd6 164 // ret &= i2c.write(command); // Set register to be read to command
lrdawg99 1:4e4194db7cd6 165 // pc1.printf("[write] ret 1: %d\n", ret);
lrdawg99 1:4e4194db7cd6 166 // ret &= i2c.write(value);
lrdawg99 1:4e4194db7cd6 167 // pc1.printf("[write] ret 2: %d\n", ret);
lrdawg99 1:4e4194db7cd6 168 // i2c.stop();
lrdawg99 1:4e4194db7cd6 169 // if (ret == 1) {
lrdawg99 1:4e4194db7cd6 170 // return 0; //success
lrdawg99 1:4e4194db7cd6 171 // }
lrdawg99 1:4e4194db7cd6 172 // return(1);
lrdawg99 1:4e4194db7cd6 173 //}
lrdawg99 1:4e4194db7cd6 174
lrdawg99 0:1473318f27b6 175 // Read a 16-bit word of data from register specified by "command"
lrdawg99 1:4e4194db7cd6 176 //int8_t i2c_read_word_data(uint8_t address, uint8_t command, uint16_t *value)
lrdawg99 1:4e4194db7cd6 177 //{
lrdawg99 1:4e4194db7cd6 178 // int8_t ret = 1;
lrdawg99 1:4e4194db7cd6 179 //
lrdawg99 1:4e4194db7cd6 180 // union {
lrdawg99 1:4e4194db7cd6 181 // uint8_t b[2];
lrdawg99 1:4e4194db7cd6 182 // uint16_t w;
lrdawg99 1:4e4194db7cd6 183 // } data;
lrdawg99 1:4e4194db7cd6 184 //
lrdawg99 1:4e4194db7cd6 185 // i2c.start();
lrdawg99 1:4e4194db7cd6 186 // ret &= i2c.write((address << 1) | I2C_WRITE_BIT); // Write 7 bit address with W bit
lrdawg99 1:4e4194db7cd6 187 // ret &= i2c.write(command); // Set register to be read to command
lrdawg99 1:4e4194db7cd6 188 // i2c.start(); //2nd start condition
lrdawg99 1:4e4194db7cd6 189 // ret &= i2c.write((address<<1) | I2C_READ_BIT); // Write 7 bit address with R bit
lrdawg99 1:4e4194db7cd6 190 //
lrdawg99 1:4e4194db7cd6 191 // data.b[1] = i2c.read(WITH_ACK); // Read MSB from buffer
lrdawg99 1:4e4194db7cd6 192 // data.b[0] = i2c.read(WITH_NACK); // Read LSB from buffer
lrdawg99 1:4e4194db7cd6 193 // i2c.stop();
lrdawg99 1:4e4194db7cd6 194 //
lrdawg99 1:4e4194db7cd6 195 // *value = data.w;
lrdawg99 1:4e4194db7cd6 196 // if (ret == 1) {
lrdawg99 1:4e4194db7cd6 197 // return 0;
lrdawg99 1:4e4194db7cd6 198 // }
lrdawg99 1:4e4194db7cd6 199 // return(1);
lrdawg99 1:4e4194db7cd6 200 //}
lrdawg99 1:4e4194db7cd6 201 //
lrdawg99 1:4e4194db7cd6 202 //// Write a 16-bit word of data to register specified by "command"
lrdawg99 1:4e4194db7cd6 203 //int8_t i2c_write_word_data(uint8_t address, uint8_t command, uint16_t value)
lrdawg99 1:4e4194db7cd6 204 //{
lrdawg99 1:4e4194db7cd6 205 // int8_t ret = 1;
lrdawg99 1:4e4194db7cd6 206 //
lrdawg99 1:4e4194db7cd6 207 // union {
lrdawg99 1:4e4194db7cd6 208 // uint8_t b[2];
lrdawg99 1:4e4194db7cd6 209 // uint16_t w;
lrdawg99 1:4e4194db7cd6 210 // } data;
lrdawg99 1:4e4194db7cd6 211 // data.w = value;
lrdawg99 1:4e4194db7cd6 212 //
lrdawg99 1:4e4194db7cd6 213 // i2c.start();
lrdawg99 1:4e4194db7cd6 214 // ret &= i2c.write((address<<1) | I2C_WRITE_BIT); // Write 7 bit address with W bit
lrdawg99 1:4e4194db7cd6 215 // ret &= i2c.write(command); // Set register to be read to command
lrdawg99 1:4e4194db7cd6 216 // ret &= i2c.write(data.b[1]); // Write MSB
lrdawg99 1:4e4194db7cd6 217 // ret &= i2c.write(data.b[0]); // Write LSB;
lrdawg99 1:4e4194db7cd6 218 //
lrdawg99 1:4e4194db7cd6 219 // i2c.stop(); // I2C STOP
lrdawg99 1:4e4194db7cd6 220 // if (ret == 1) {
lrdawg99 1:4e4194db7cd6 221 // return 0;
lrdawg99 1:4e4194db7cd6 222 // }
lrdawg99 1:4e4194db7cd6 223 // return(1);
lrdawg99 1:4e4194db7cd6 224 //}
lrdawg99 1:4e4194db7cd6 225
lrdawg99 0:1473318f27b6 226 int8_t i2c_read_word_data(uint8_t address, uint8_t command, uint16_t *value)
lrdawg99 0:1473318f27b6 227 {
lrdawg99 1:4e4194db7cd6 228 int8_t ret = 0;
lrdawg99 1:4e4194db7cd6 229
lrdawg99 1:4e4194db7cd6 230
lrdawg99 1:4e4194db7cd6 231 union {
lrdawg99 1:4e4194db7cd6 232 char b[2];
lrdawg99 1:4e4194db7cd6 233 uint16_t w;
lrdawg99 1:4e4194db7cd6 234 } data;
lrdawg99 1:4e4194db7cd6 235
lrdawg99 1:4e4194db7cd6 236 char writedata[2];
lrdawg99 1:4e4194db7cd6 237 writedata[0] = command; //msb
lrdawg99 1:4e4194db7cd6 238 writedata[1] = command+1; //lsb
lrdawg99 1:4e4194db7cd6 239
lrdawg99 1:4e4194db7cd6 240 ret |= i2c.write((address << 1) | I2C_WRITE_BIT, &writedata[0], 1, true);
lrdawg99 1:4e4194db7cd6 241 ret |= i2c.read((address << 1) | I2C_READ_BIT, &data.b[1], 1, false);
lrdawg99 1:4e4194db7cd6 242 ret |= i2c.write((address << 1) | I2C_WRITE_BIT, &writedata[1], 1, true);
lrdawg99 1:4e4194db7cd6 243 ret |= i2c.read((address << 1) | I2C_READ_BIT, &data.b[0], 1, false);
lrdawg99 1:4e4194db7cd6 244
lrdawg99 1:4e4194db7cd6 245
lrdawg99 1:4e4194db7cd6 246 *value = data.w;
lrdawg99 1:4e4194db7cd6 247
lrdawg99 1:4e4194db7cd6 248 if (ret == 0) {
lrdawg99 1:4e4194db7cd6 249 return 0;
lrdawg99 1:4e4194db7cd6 250 }
lrdawg99 1:4e4194db7cd6 251 return(1);
lrdawg99 0:1473318f27b6 252 }
lrdawg99 0:1473318f27b6 253
lrdawg99 0:1473318f27b6 254 // Write a 16-bit word of data to register specified by "command"
lrdawg99 0:1473318f27b6 255 int8_t i2c_write_word_data(uint8_t address, uint8_t command, uint16_t value)
lrdawg99 0:1473318f27b6 256 {
lrdawg99 1:4e4194db7cd6 257 int8_t ret = 0;
lrdawg99 1:4e4194db7cd6 258
lrdawg99 1:4e4194db7cd6 259 union
lrdawg99 1:4e4194db7cd6 260 {
lrdawg99 1:4e4194db7cd6 261 uint8_t b[2];
lrdawg99 1:4e4194db7cd6 262 uint16_t w;
lrdawg99 1:4e4194db7cd6 263 } data;
lrdawg99 1:4e4194db7cd6 264 data.w = value;
lrdawg99 1:4e4194db7cd6 265
lrdawg99 1:4e4194db7cd6 266 char cmd[3];
lrdawg99 1:4e4194db7cd6 267 cmd[0] = command;
lrdawg99 1:4e4194db7cd6 268 cmd[1] = data.b[1];
lrdawg99 1:4e4194db7cd6 269 cmd[2] = data.b[0];
lrdawg99 0:1473318f27b6 270
lrdawg99 1:4e4194db7cd6 271 ret |= i2c.write((address<<1) | I2C_WRITE_BIT, cmd, 3, false);
lrdawg99 0:1473318f27b6 272
lrdawg99 1:4e4194db7cd6 273 if (ret == 0) {
lrdawg99 1:4e4194db7cd6 274 return 0;
lrdawg99 1:4e4194db7cd6 275 }
lrdawg99 1:4e4194db7cd6 276 return(1);
lrdawg99 1:4e4194db7cd6 277 }