1 #ifndef EAGLE_EBOARD_HELPLIB_TWI 2 #define EAGLE_EBOARD_HELPLIB_TWI 5 #define TWI_FREQ 100000L 13 #define TWI_FREQ 100000L 16 #ifndef TWI_BUFFER_LENGTH 17 #define TWI_BUFFER_LENGTH 32 30 uint8_t
twi_readFrom(uint8_t, uint8_t*, uint8_t, uint8_t);
31 uint8_t
twi_writeTo(uint8_t, uint8_t*, uint8_t, uint8_t, uint8_t);
40 #ifndef TWI_BUFFER_LENGTH 41 #define TWI_BUFFER_LENGTH 32 52 #include <avr/interrupt.h> 53 #include <compat/twi.h> 56 #define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit)) 60 #define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit)) 63 #include "pins_arduino.h" 65 static volatile uint8_t twi_state;
66 static volatile uint8_t twi_slarw;
67 static volatile uint8_t twi_sendStop;
68 static volatile uint8_t twi_inRepStart;
70 static void (*twi_onSlaveTransmit)(void);
71 static void (*twi_onSlaveReceive)(uint8_t*, int);
74 static volatile uint8_t twi_masterBufferIndex;
75 static volatile uint8_t twi_masterBufferLength;
78 static volatile uint8_t twi_txBufferIndex;
79 static volatile uint8_t twi_txBufferLength;
82 static volatile uint8_t twi_rxBufferIndex;
84 static volatile uint8_t twi_error;
89 twi_inRepStart =
false;
96 TWBR = ((F_CPU /
TWI_FREQ) - 16) / 2;
98 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA);
105 uint8_t
twi_readFrom(uint8_t address, uint8_t* data, uint8_t length, uint8_t sendStop) {
113 twi_sendStop = sendStop;
117 twi_masterBufferIndex = 0;
118 twi_masterBufferLength = length-1;
120 twi_slarw |= address << 1;
122 if (
true == twi_inRepStart) {
123 twi_inRepStart =
false;
125 TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE);
128 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTA);
130 while(
TWI_MRX == twi_state)
continue;
132 if (twi_masterBufferIndex < length)
133 length = twi_masterBufferIndex;
135 for(i = 0; i < length; ++i) data[i] = twi_masterBuffer[i];
140 uint8_t
twi_writeTo(uint8_t address, uint8_t* data, uint8_t length, uint8_t wait, uint8_t sendStop) {
148 twi_sendStop = sendStop;
151 twi_masterBufferIndex = 0;
152 twi_masterBufferLength = length;
154 for(i = 0; i < length; ++i) twi_masterBuffer[i] = data[i];
156 twi_slarw = TW_WRITE;
157 twi_slarw |= address << 1;
159 if (
true == twi_inRepStart) {
160 twi_inRepStart =
false;
162 TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE);
165 TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE) | _BV(TWSTA);
167 while(wait && (
TWI_MTX == twi_state))
continue;
169 if (twi_error == 0xFF)
return 0;
170 else if (twi_error == TW_MT_SLA_NACK)
return 2;
171 else if (twi_error == TW_MT_DATA_NACK)
return 3;
175 uint8_t
twi_transmit(
const uint8_t* data, uint8_t length) {
180 if(
TWI_STX != twi_state)
return 2;
182 twi_txBufferLength = length;
183 for(i = 0; i < length; ++i) twi_txBuffer[i] = data[i];
189 twi_onSlaveReceive =
function;
193 twi_onSlaveTransmit =
function;
198 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT) | _BV(TWEA);
200 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT);
206 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTO);
208 while(TWCR & _BV(TWSTO))
continue;
214 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT);
228 if(twi_masterBufferIndex < twi_masterBufferLength){
229 TWDR = twi_masterBuffer[twi_masterBufferIndex++];
234 twi_inRepStart =
true;
235 TWCR = _BV(TWINT) | _BV(TWSTA)| _BV(TWEN) ;
241 twi_error = TW_MT_SLA_NACK;
244 case TW_MT_DATA_NACK:
245 twi_error = TW_MT_DATA_NACK;
249 twi_error = TW_MT_ARB_LOST;
253 twi_masterBuffer[twi_masterBufferIndex++] = TWDR;
255 if(twi_masterBufferIndex < twi_masterBufferLength)
twi_reply(1);
258 case TW_MR_DATA_NACK:
259 twi_masterBuffer[twi_masterBufferIndex++] = TWDR;
262 twi_inRepStart =
true;
263 TWCR = _BV(TWINT) | _BV(TWSTA)| _BV(TWEN) ;
271 case TW_SR_GCALL_ACK:
272 case TW_SR_ARB_LOST_SLA_ACK:
273 case TW_SR_ARB_LOST_GCALL_ACK:
275 twi_rxBufferIndex = 0;
279 case TW_SR_GCALL_DATA_ACK:
281 twi_rxBuffer[twi_rxBufferIndex++] = TWDR;
287 if(twi_rxBufferIndex <
TWI_BUFFER_LENGTH) twi_rxBuffer[twi_rxBufferIndex] =
'\0';
289 twi_onSlaveReceive(twi_rxBuffer, twi_rxBufferIndex);
290 twi_rxBufferIndex = 0;
293 case TW_SR_DATA_NACK:
294 case TW_SR_GCALL_DATA_NACK:
298 case TW_ST_ARB_LOST_SLA_ACK:
300 twi_txBufferIndex = 0;
301 twi_txBufferLength = 0;
302 twi_onSlaveTransmit();
303 if(0 == twi_txBufferLength){
304 twi_txBufferLength = 1;
305 twi_txBuffer[0] = 0x00;
308 TWDR = twi_txBuffer[twi_txBufferIndex++];
309 if(twi_txBufferIndex < twi_txBufferLength)
twi_reply(1);
312 case TW_ST_DATA_NACK:
313 case TW_ST_LAST_DATA:
321 twi_error = TW_BUS_ERROR;
void twi_releaseBus(void)
void twi_setAddress(uint8_t)
uint8_t twi_transmit(const uint8_t *, uint8_t)
uint8_t twi_readFrom(uint8_t, uint8_t *, uint8_t, uint8_t)
void twi_setFrequency(uint32_t)
uint8_t twi_writeTo(uint8_t, uint8_t *, uint8_t, uint8_t, uint8_t)
#define TWI_BUFFER_LENGTH
void twi_attachSlaveRxEvent(void(*)(uint8_t *, int))
void twi_attachSlaveTxEvent(void(*)(void))