mbed library sources
Dependents: frdm_kl05z_gpio_test
Fork of mbed-src by
targets/hal/TARGET_STM/TARGET_STM32F4XX/i2c_api.c@285:31249416b6f9, 2014-08-15 (annotated)
- Committer:
- mbed_official
- Date:
- Fri Aug 15 16:30:08 2014 +0100
- Revision:
- 285:31249416b6f9
- Parent:
- 251:de9a1e4ffd79
Synchronized with git revision 601712595f49bbd2a2771c52cf3e84c9c7a591af
Full URL: https://github.com/mbedmicro/mbed/commit/601712595f49bbd2a2771c52cf3e84c9c7a591af/
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
bogdanm | 20:4263a77256ae | 1 | /* mbed Microcontroller Library |
bogdanm | 20:4263a77256ae | 2 | * Copyright (c) 2006-2013 ARM Limited |
bogdanm | 20:4263a77256ae | 3 | * |
bogdanm | 20:4263a77256ae | 4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
bogdanm | 20:4263a77256ae | 5 | * you may not use this file except in compliance with the License. |
bogdanm | 20:4263a77256ae | 6 | * You may obtain a copy of the License at |
bogdanm | 20:4263a77256ae | 7 | * |
bogdanm | 20:4263a77256ae | 8 | * http://www.apache.org/licenses/LICENSE-2.0 |
bogdanm | 20:4263a77256ae | 9 | * |
bogdanm | 20:4263a77256ae | 10 | * Unless required by applicable law or agreed to in writing, software |
bogdanm | 20:4263a77256ae | 11 | * distributed under the License is distributed on an "AS IS" BASIS, |
bogdanm | 20:4263a77256ae | 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
bogdanm | 20:4263a77256ae | 13 | * See the License for the specific language governing permissions and |
bogdanm | 20:4263a77256ae | 14 | * limitations under the License. |
bogdanm | 20:4263a77256ae | 15 | */ |
mbed_official | 227:7bd0639b8911 | 16 | #include "mbed_assert.h" |
bogdanm | 20:4263a77256ae | 17 | #include "i2c_api.h" |
bogdanm | 20:4263a77256ae | 18 | |
bogdanm | 20:4263a77256ae | 19 | #if DEVICE_I2C |
bogdanm | 20:4263a77256ae | 20 | |
bogdanm | 20:4263a77256ae | 21 | #include "cmsis.h" |
bogdanm | 20:4263a77256ae | 22 | #include "pinmap.h" |
mbed_official | 285:31249416b6f9 | 23 | #include "mbed_error.h" |
bogdanm | 20:4263a77256ae | 24 | |
bogdanm | 20:4263a77256ae | 25 | static const PinMap PinMap_I2C_SDA[] = { |
bogdanm | 20:4263a77256ae | 26 | {PB_7, I2C_1, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 27 | {PB_9, I2C_1, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 28 | {PB_11, I2C_2, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 29 | {PC_9, I2C_3, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 30 | {PF_0, I2C_2, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 31 | {PH_5, I2C_2, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 32 | {PH_8, I2C_3, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 33 | {NC, NC, 0} |
bogdanm | 20:4263a77256ae | 34 | }; |
bogdanm | 20:4263a77256ae | 35 | |
bogdanm | 20:4263a77256ae | 36 | static const PinMap PinMap_I2C_SCL[] = { |
bogdanm | 20:4263a77256ae | 37 | {PA_8, I2C_3, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 38 | {PB_6, I2C_1, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 39 | {PB_8, I2C_1, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 40 | {PB_10, I2C_2, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 41 | {PF_1, I2C_2, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 42 | {PH_4, I2C_2, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 43 | {PH_7, I2C_3, STM_PIN_DATA(2, 4)}, |
bogdanm | 20:4263a77256ae | 44 | {NC, NC, 0} |
bogdanm | 20:4263a77256ae | 45 | }; |
bogdanm | 20:4263a77256ae | 46 | |
bogdanm | 20:4263a77256ae | 47 | static const uint32_t I2C_addr_offset[2][4] = { |
bogdanm | 20:4263a77256ae | 48 | {0x0C, 0x20, 0x24, 0x28}, |
bogdanm | 20:4263a77256ae | 49 | {0x30, 0x34, 0x38, 0x3C} |
bogdanm | 20:4263a77256ae | 50 | }; |
bogdanm | 20:4263a77256ae | 51 | |
bogdanm | 20:4263a77256ae | 52 | |
bogdanm | 20:4263a77256ae | 53 | static inline void i2c_interface_enable(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 54 | obj->i2c->CR1 |= I2C_CR1_PE; |
bogdanm | 20:4263a77256ae | 55 | } |
bogdanm | 20:4263a77256ae | 56 | |
bogdanm | 20:4263a77256ae | 57 | static inline void i2c_interface_disable(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 58 | obj->i2c->CR1 &= ~I2C_CR1_PE; |
bogdanm | 20:4263a77256ae | 59 | } |
bogdanm | 20:4263a77256ae | 60 | |
bogdanm | 20:4263a77256ae | 61 | |
bogdanm | 20:4263a77256ae | 62 | static inline void i2c_power_enable(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 63 | switch ((int)obj->i2c) { |
bogdanm | 20:4263a77256ae | 64 | case I2C_1: |
bogdanm | 20:4263a77256ae | 65 | RCC->AHB1ENR |= RCC_AHB1ENR_GPIOBEN; |
bogdanm | 20:4263a77256ae | 66 | RCC->APB1ENR |= RCC_APB1ENR_I2C1EN; |
bogdanm | 20:4263a77256ae | 67 | break; |
bogdanm | 20:4263a77256ae | 68 | case I2C_2: |
bogdanm | 20:4263a77256ae | 69 | RCC->AHB1ENR |= RCC_AHB1ENR_GPIOBEN | RCC_AHB1ENR_GPIOFEN | |
bogdanm | 20:4263a77256ae | 70 | RCC_AHB1ENR_GPIOHEN; |
bogdanm | 20:4263a77256ae | 71 | RCC->APB1ENR |= RCC_APB1ENR_I2C2EN; |
bogdanm | 20:4263a77256ae | 72 | break; |
bogdanm | 20:4263a77256ae | 73 | case I2C_3: |
bogdanm | 20:4263a77256ae | 74 | RCC->AHB1ENR |= RCC_AHB1ENR_GPIOAEN | RCC_AHB1ENR_GPIOCEN | |
bogdanm | 20:4263a77256ae | 75 | RCC_AHB1ENR_GPIOHEN; |
bogdanm | 20:4263a77256ae | 76 | RCC->APB1ENR |= RCC_APB1ENR_I2C3EN; |
bogdanm | 20:4263a77256ae | 77 | break; |
bogdanm | 20:4263a77256ae | 78 | } |
bogdanm | 20:4263a77256ae | 79 | } |
bogdanm | 20:4263a77256ae | 80 | |
bogdanm | 20:4263a77256ae | 81 | static inline void i2c_wait_status(i2c_t *obj, uint32_t sr1_mask, |
bogdanm | 20:4263a77256ae | 82 | uint32_t sr2_mask) { |
bogdanm | 20:4263a77256ae | 83 | while (!(((obj->i2c->SR1 & sr1_mask) >= sr1_mask) && |
bogdanm | 20:4263a77256ae | 84 | ((obj->i2c->SR2 & sr2_mask) == sr2_mask))); |
bogdanm | 20:4263a77256ae | 85 | } |
bogdanm | 20:4263a77256ae | 86 | |
bogdanm | 20:4263a77256ae | 87 | // Wait until the slave address has been acknowledged |
bogdanm | 20:4263a77256ae | 88 | static inline void i2c_wait_addr_tx(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 89 | uint32_t sr1_mask = I2C_SR1_ADDR | I2C_SR1_TXE; |
bogdanm | 20:4263a77256ae | 90 | uint32_t sr2_mask = I2C_SR2_MSL | I2C_SR2_BUSY | I2C_SR2_TRA; |
bogdanm | 20:4263a77256ae | 91 | i2c_wait_status(obj, sr1_mask, sr2_mask); |
bogdanm | 20:4263a77256ae | 92 | } |
bogdanm | 20:4263a77256ae | 93 | |
bogdanm | 20:4263a77256ae | 94 | // Wait until the slave address has been acknowledged |
bogdanm | 20:4263a77256ae | 95 | static inline void i2c_wait_addr_rx(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 96 | uint32_t sr1_mask = I2C_SR1_ADDR; |
bogdanm | 20:4263a77256ae | 97 | uint32_t sr2_mask = I2C_SR2_MSL | I2C_SR2_BUSY; |
bogdanm | 20:4263a77256ae | 98 | i2c_wait_status(obj, sr1_mask, sr2_mask); |
bogdanm | 20:4263a77256ae | 99 | } |
bogdanm | 20:4263a77256ae | 100 | |
bogdanm | 20:4263a77256ae | 101 | |
bogdanm | 20:4263a77256ae | 102 | // Wait until a byte has been sent |
bogdanm | 20:4263a77256ae | 103 | static inline void i2c_wait_send(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 104 | uint32_t sr1_mask = I2C_SR1_BTF | I2C_SR1_TXE; |
bogdanm | 20:4263a77256ae | 105 | uint32_t sr2_mask = I2C_SR2_MSL | I2C_SR2_BUSY | I2C_SR2_TRA; |
bogdanm | 20:4263a77256ae | 106 | i2c_wait_status(obj, sr1_mask, sr2_mask); |
bogdanm | 20:4263a77256ae | 107 | } |
bogdanm | 20:4263a77256ae | 108 | |
bogdanm | 20:4263a77256ae | 109 | // Wait until a byte has been received |
bogdanm | 20:4263a77256ae | 110 | static inline void i2c_wait_receive(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 111 | uint32_t sr1_mask = I2C_SR1_RXNE; |
bogdanm | 20:4263a77256ae | 112 | uint32_t sr2_mask = I2C_SR2_MSL | I2C_SR2_BUSY; |
bogdanm | 20:4263a77256ae | 113 | i2c_wait_status(obj, sr1_mask, sr2_mask); |
bogdanm | 20:4263a77256ae | 114 | } |
bogdanm | 20:4263a77256ae | 115 | |
bogdanm | 20:4263a77256ae | 116 | // Wait until the start condition has been accepted |
bogdanm | 20:4263a77256ae | 117 | static inline void i2c_wait_start(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 118 | uint32_t sr1_mask = I2C_SR1_SB; |
bogdanm | 20:4263a77256ae | 119 | uint32_t sr2_mask = I2C_SR2_MSL | I2C_SR2_BUSY; |
bogdanm | 20:4263a77256ae | 120 | i2c_wait_status(obj, sr1_mask, sr2_mask); |
bogdanm | 20:4263a77256ae | 121 | } |
bogdanm | 20:4263a77256ae | 122 | |
bogdanm | 20:4263a77256ae | 123 | void i2c_init(i2c_t *obj, PinName sda, PinName scl) { |
bogdanm | 20:4263a77256ae | 124 | // determine the SPI to use |
bogdanm | 20:4263a77256ae | 125 | I2CName i2c_sda = (I2CName)pinmap_peripheral(sda, PinMap_I2C_SDA); |
bogdanm | 20:4263a77256ae | 126 | I2CName i2c_scl = (I2CName)pinmap_peripheral(scl, PinMap_I2C_SCL); |
bogdanm | 20:4263a77256ae | 127 | obj->i2c = (I2C_TypeDef *)pinmap_merge(i2c_sda, i2c_scl); |
mbed_official | 227:7bd0639b8911 | 128 | MBED_ASSERT((int)obj->i2c != NC); |
bogdanm | 20:4263a77256ae | 129 | |
bogdanm | 20:4263a77256ae | 130 | // enable power |
bogdanm | 20:4263a77256ae | 131 | i2c_power_enable(obj); |
bogdanm | 20:4263a77256ae | 132 | |
bogdanm | 20:4263a77256ae | 133 | pinmap_pinout(sda, PinMap_I2C_SDA); |
bogdanm | 20:4263a77256ae | 134 | pinmap_pinout(scl, PinMap_I2C_SCL); |
bogdanm | 20:4263a77256ae | 135 | |
bogdanm | 20:4263a77256ae | 136 | pin_mode(sda, OpenDrain); |
bogdanm | 20:4263a77256ae | 137 | pin_mode(scl, OpenDrain); |
bogdanm | 20:4263a77256ae | 138 | |
bogdanm | 20:4263a77256ae | 139 | // Force reset if the bus is stuck in the BUSY state |
bogdanm | 20:4263a77256ae | 140 | if (obj->i2c->SR2 & I2C_SR2_BUSY) { |
bogdanm | 20:4263a77256ae | 141 | obj->i2c->CR1 |= I2C_CR1_SWRST; |
bogdanm | 20:4263a77256ae | 142 | obj->i2c->CR1 &= ~I2C_CR1_SWRST; |
bogdanm | 20:4263a77256ae | 143 | } |
bogdanm | 20:4263a77256ae | 144 | |
bogdanm | 20:4263a77256ae | 145 | // Set the peripheral clock frequency |
bogdanm | 20:4263a77256ae | 146 | obj->i2c->CR2 |= 42; |
bogdanm | 20:4263a77256ae | 147 | |
bogdanm | 20:4263a77256ae | 148 | // set default frequency at 100k |
bogdanm | 20:4263a77256ae | 149 | i2c_frequency(obj, 100000); |
bogdanm | 20:4263a77256ae | 150 | i2c_interface_enable(obj); |
bogdanm | 20:4263a77256ae | 151 | } |
bogdanm | 20:4263a77256ae | 152 | |
bogdanm | 20:4263a77256ae | 153 | inline int i2c_start(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 154 | // Wait until we are not busy any more |
bogdanm | 20:4263a77256ae | 155 | while (obj->i2c->SR2 & I2C_SR2_BUSY); |
bogdanm | 20:4263a77256ae | 156 | |
bogdanm | 20:4263a77256ae | 157 | // Generate the start condition |
bogdanm | 20:4263a77256ae | 158 | obj->i2c->CR1 |= I2C_CR1_START; |
bogdanm | 20:4263a77256ae | 159 | i2c_wait_start(obj); |
bogdanm | 20:4263a77256ae | 160 | |
bogdanm | 20:4263a77256ae | 161 | return 0; |
bogdanm | 20:4263a77256ae | 162 | } |
bogdanm | 20:4263a77256ae | 163 | |
bogdanm | 20:4263a77256ae | 164 | inline int i2c_stop(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 165 | // Generate the stop condition |
bogdanm | 20:4263a77256ae | 166 | obj->i2c->CR1 |= I2C_CR1_STOP; |
bogdanm | 20:4263a77256ae | 167 | return 0; |
bogdanm | 20:4263a77256ae | 168 | } |
bogdanm | 20:4263a77256ae | 169 | |
bogdanm | 20:4263a77256ae | 170 | |
bogdanm | 20:4263a77256ae | 171 | static inline int i2c_do_write(i2c_t *obj, int value, uint8_t addr) { |
bogdanm | 20:4263a77256ae | 172 | obj->i2c->DR = value; |
bogdanm | 20:4263a77256ae | 173 | return 0; |
bogdanm | 20:4263a77256ae | 174 | } |
bogdanm | 20:4263a77256ae | 175 | |
bogdanm | 20:4263a77256ae | 176 | static inline int i2c_do_read(i2c_t *obj, int last) { |
bogdanm | 20:4263a77256ae | 177 | if(last) { |
bogdanm | 20:4263a77256ae | 178 | // Don't acknowledge the byte |
bogdanm | 20:4263a77256ae | 179 | obj->i2c->CR1 &= ~(I2C_CR1_ACK); |
bogdanm | 20:4263a77256ae | 180 | } else { |
bogdanm | 20:4263a77256ae | 181 | // Acknowledge the byte |
bogdanm | 20:4263a77256ae | 182 | obj->i2c->CR1 |= I2C_CR1_ACK; |
bogdanm | 20:4263a77256ae | 183 | } |
bogdanm | 20:4263a77256ae | 184 | |
bogdanm | 20:4263a77256ae | 185 | // Wait until we receive the byte |
bogdanm | 20:4263a77256ae | 186 | i2c_wait_receive(obj); |
bogdanm | 20:4263a77256ae | 187 | |
bogdanm | 20:4263a77256ae | 188 | int data = obj->i2c->DR; |
bogdanm | 20:4263a77256ae | 189 | return data; |
bogdanm | 20:4263a77256ae | 190 | } |
bogdanm | 20:4263a77256ae | 191 | |
bogdanm | 20:4263a77256ae | 192 | void i2c_frequency(i2c_t *obj, int hz) { |
bogdanm | 20:4263a77256ae | 193 | i2c_interface_disable(obj); |
bogdanm | 20:4263a77256ae | 194 | obj->i2c->CCR &= ~(I2C_CCR_CCR | I2C_CCR_FS); |
bogdanm | 20:4263a77256ae | 195 | if (hz > 100000) { |
bogdanm | 20:4263a77256ae | 196 | // Fast Mode |
bogdanm | 20:4263a77256ae | 197 | obj->i2c->CCR |= I2C_CCR_FS; |
bogdanm | 20:4263a77256ae | 198 | int result = 42000000 / (hz * 3); |
bogdanm | 20:4263a77256ae | 199 | obj->i2c->CCR |= result & I2C_CCR_CCR; |
bogdanm | 20:4263a77256ae | 200 | obj->i2c->TRISE = ((42 * 300) / 1000) + 1; |
bogdanm | 20:4263a77256ae | 201 | } |
bogdanm | 20:4263a77256ae | 202 | else { |
bogdanm | 20:4263a77256ae | 203 | // Standard mode |
bogdanm | 20:4263a77256ae | 204 | obj->i2c->CCR &= ~I2C_CCR_FS; |
bogdanm | 20:4263a77256ae | 205 | int result = 42000000 / (hz << 1); |
bogdanm | 20:4263a77256ae | 206 | result = result < 0x4 ? 0x4 : result; |
bogdanm | 20:4263a77256ae | 207 | obj->i2c->CCR |= result & I2C_CCR_CCR; |
bogdanm | 20:4263a77256ae | 208 | obj->i2c->TRISE = 42 + 1; |
bogdanm | 20:4263a77256ae | 209 | } |
bogdanm | 20:4263a77256ae | 210 | i2c_interface_enable(obj); |
bogdanm | 20:4263a77256ae | 211 | } |
bogdanm | 20:4263a77256ae | 212 | |
bogdanm | 20:4263a77256ae | 213 | // The I2C does a read or a write as a whole operation |
bogdanm | 20:4263a77256ae | 214 | // There are two types of error conditions it can encounter |
bogdanm | 20:4263a77256ae | 215 | // 1) it can not obtain the bus |
bogdanm | 20:4263a77256ae | 216 | // 2) it gets error responses at part of the transmission |
bogdanm | 20:4263a77256ae | 217 | // |
bogdanm | 20:4263a77256ae | 218 | // We tackle them as follows: |
bogdanm | 20:4263a77256ae | 219 | // 1) we retry until we get the bus. we could have a "timeout" if we can not get it |
bogdanm | 20:4263a77256ae | 220 | // which basically turns it in to a 2) |
bogdanm | 20:4263a77256ae | 221 | // 2) on error, we use the standard error mechanisms to report/debug |
bogdanm | 20:4263a77256ae | 222 | // |
bogdanm | 20:4263a77256ae | 223 | // Therefore an I2C transaction should always complete. If it doesn't it is usually |
bogdanm | 20:4263a77256ae | 224 | // because something is setup wrong (e.g. wiring), and we don't need to programatically |
bogdanm | 20:4263a77256ae | 225 | // check for that |
bogdanm | 20:4263a77256ae | 226 | |
bogdanm | 20:4263a77256ae | 227 | int i2c_read(i2c_t *obj, int address, char *data, int length, int stop) { |
bogdanm | 20:4263a77256ae | 228 | int count; |
bogdanm | 20:4263a77256ae | 229 | |
bogdanm | 20:4263a77256ae | 230 | i2c_start(obj); |
bogdanm | 20:4263a77256ae | 231 | |
bogdanm | 20:4263a77256ae | 232 | // Send the slave address |
bogdanm | 20:4263a77256ae | 233 | i2c_do_write(obj, (address | 0x01), 1); |
bogdanm | 20:4263a77256ae | 234 | |
bogdanm | 20:4263a77256ae | 235 | // Wait until we have transmitted and the ADDR byte is set |
bogdanm | 20:4263a77256ae | 236 | i2c_wait_addr_rx(obj); |
bogdanm | 20:4263a77256ae | 237 | |
bogdanm | 20:4263a77256ae | 238 | // Read in all except last byte |
bogdanm | 20:4263a77256ae | 239 | for (count = 0; count < (length - 1); count++) { |
bogdanm | 20:4263a77256ae | 240 | int value = i2c_do_read(obj, 0); |
bogdanm | 20:4263a77256ae | 241 | data[count] = (char) value; |
bogdanm | 20:4263a77256ae | 242 | } |
bogdanm | 20:4263a77256ae | 243 | |
bogdanm | 20:4263a77256ae | 244 | // read in last byte |
bogdanm | 20:4263a77256ae | 245 | int value = i2c_do_read(obj, 1); |
bogdanm | 20:4263a77256ae | 246 | data[count] = (char) value; |
bogdanm | 20:4263a77256ae | 247 | |
bogdanm | 20:4263a77256ae | 248 | // If not repeated start, send stop. |
bogdanm | 20:4263a77256ae | 249 | if (stop) { |
bogdanm | 20:4263a77256ae | 250 | i2c_stop(obj); |
bogdanm | 20:4263a77256ae | 251 | } |
bogdanm | 20:4263a77256ae | 252 | |
bogdanm | 20:4263a77256ae | 253 | return length; |
bogdanm | 20:4263a77256ae | 254 | } |
bogdanm | 20:4263a77256ae | 255 | |
bogdanm | 20:4263a77256ae | 256 | int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop) { |
bogdanm | 20:4263a77256ae | 257 | int i; |
bogdanm | 20:4263a77256ae | 258 | |
bogdanm | 20:4263a77256ae | 259 | i2c_start(obj); |
bogdanm | 20:4263a77256ae | 260 | |
bogdanm | 20:4263a77256ae | 261 | // Send the slave address |
bogdanm | 20:4263a77256ae | 262 | i2c_do_write(obj, (address & 0xFE), 1); |
bogdanm | 20:4263a77256ae | 263 | i2c_wait_addr_tx(obj); |
bogdanm | 20:4263a77256ae | 264 | |
bogdanm | 20:4263a77256ae | 265 | for (i=0; i<length; i++) { |
bogdanm | 20:4263a77256ae | 266 | i2c_do_write(obj, data[i], 0); |
bogdanm | 20:4263a77256ae | 267 | i2c_wait_send(obj); |
bogdanm | 20:4263a77256ae | 268 | } |
bogdanm | 20:4263a77256ae | 269 | |
bogdanm | 20:4263a77256ae | 270 | // If not repeated start, send stop. |
bogdanm | 20:4263a77256ae | 271 | if (stop) { |
bogdanm | 20:4263a77256ae | 272 | i2c_stop(obj); |
bogdanm | 20:4263a77256ae | 273 | } |
bogdanm | 20:4263a77256ae | 274 | |
bogdanm | 20:4263a77256ae | 275 | return length; |
bogdanm | 20:4263a77256ae | 276 | } |
bogdanm | 20:4263a77256ae | 277 | |
bogdanm | 20:4263a77256ae | 278 | void i2c_reset(i2c_t *obj) { |
bogdanm | 20:4263a77256ae | 279 | i2c_stop(obj); |
bogdanm | 20:4263a77256ae | 280 | } |
bogdanm | 20:4263a77256ae | 281 | |
bogdanm | 20:4263a77256ae | 282 | int i2c_byte_read(i2c_t *obj, int last) { |
bogdanm | 20:4263a77256ae | 283 | return (i2c_do_read(obj, last) & 0xFF); |
bogdanm | 20:4263a77256ae | 284 | } |
bogdanm | 20:4263a77256ae | 285 | |
bogdanm | 20:4263a77256ae | 286 | int i2c_byte_write(i2c_t *obj, int data) { |
bogdanm | 20:4263a77256ae | 287 | i2c_do_write(obj, (data & 0xFF), 0); |
bogdanm | 20:4263a77256ae | 288 | i2c_wait_send(obj); |
bogdanm | 20:4263a77256ae | 289 | |
bogdanm | 20:4263a77256ae | 290 | // TODO: Should return whether write has been acknowledged |
bogdanm | 20:4263a77256ae | 291 | return 1; |
bogdanm | 20:4263a77256ae | 292 | } |
bogdanm | 20:4263a77256ae | 293 | |
bogdanm | 20:4263a77256ae | 294 | #endif |