-
Notifications
You must be signed in to change notification settings - Fork 48
/
I2C.h
149 lines (133 loc) · 5.55 KB
/
I2C.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
/*
I2C.h - I2C library
Copyright (c) 2011-2012 Wayne Truchsess. All right reserved.
Rev 5.0 - January 24th, 2012
- Removed the use of interrupts completely from the library
so TWI state changes are now polled.
- Added calls to lockup() function in most functions
to combat arbitration problems
- Fixed scan() procedure which left timeouts enabled
and set to 80msec after exiting procedure
- Changed scan() address range back to 0 - 0x7F
- Removed all Wire legacy functions from library
- A big thanks to Richard Baldwin for all the testing
and feedback with debugging bus lockups!
Rev 4.0 - January 14th, 2012
- Updated to make compatible with 8MHz clock frequency
Rev 3.0 - January 9th, 2012
- Modified library to be compatible with Arduino 1.0
- Changed argument type from boolean to uint8_t in pullUp(),
setSpeed() and receiveByte() functions for 1.0 compatability
- Modified return values for timeout feature to report
back where in the transmission the timeout occured.
- added function scan() to perform a bus scan to find devices
attached to the I2C bus. Similar to work done by Todbot
and Nick Gammon
Rev 2.0 - September 19th, 2011
- Added support for timeout function to prevent
and recover from bus lockup (thanks to PaulS
and CrossRoads on the Arduino forum)
- Changed return type for stop() from void to
uint8_t to handle timeOut function
Rev 1.0 - August 8th, 2011
This is a modified version of the Arduino Wire/TWI
library. Functions were rewritten to provide more functionality
and also the use of Repeated Start. Some I2C devices will not
function correctly without the use of a Repeated Start. The
initial version of this library only supports the Master.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#if (ARDUINO >= 100)
#include <Arduino.h>
#else
#include <WProgram.h>
#endif
#include <inttypes.h>
#ifndef I2C_h
#define I2C_h
#define START 0x08
#define REPEATED_START 0x10
#define MT_SLA_ACK 0x18
#define MT_SLA_NACK 0x20
#define MT_DATA_ACK 0x28
#define MT_DATA_NACK 0x30
#define MR_SLA_ACK 0x40
#define MR_SLA_NACK 0x48
#define MR_DATA_ACK 0x50
#define MR_DATA_NACK 0x58
#define LOST_ARBTRTN 0x38
#define TWI_STATUS (TWSR & 0xF8)
#define SLA_W(address) (address << 1)
#define SLA_R(address) ((address << 1) + 0x01)
#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
#define MAX_BUFFER_SIZE 32
class I2C
{
public:
I2C();
void begin();
void end();
void timeOut(uint16_t);
void setSpeed(uint8_t);
void pullup(uint8_t);
void scan();
uint8_t available();
uint8_t receive();
uint8_t write(uint8_t, uint8_t);
uint8_t write(int, int);
uint8_t write(uint8_t, uint8_t, uint8_t);
uint8_t write(int, int, int);
uint8_t write(uint8_t, uint8_t, const char *);
uint8_t write(uint8_t, uint8_t, uint16_t); //Will write 2 bytes
uint8_t write(uint8_t, uint8_t, uint32_t); //Will write 4 bytes
uint8_t write(uint8_t, uint8_t, uint64_t); //Will write 8 bytes
uint8_t write(uint8_t, uint8_t, const uint8_t *, uint8_t);
uint8_t read(uint8_t, uint8_t);
uint8_t read(int, int);
uint8_t read(uint8_t, uint8_t, uint8_t);
uint8_t read(int, int, int);
uint8_t read(uint8_t, uint8_t, uint8_t *);
uint8_t readex(uint8_t, uint16_t, uint8_t *);//overload for more than 255 bytes
uint8_t read(uint8_t, uint8_t, uint8_t, uint8_t *);
uint8_t readex(uint8_t, uint8_t, uint16_t, uint8_t *);//overload for more than 255 bytes
//These functions will be used to write to Slaves that take 16-bit addresses
uint8_t write16(uint8_t, uint16_t);
uint8_t write16(uint8_t, uint16_t, uint8_t);
uint8_t write16(uint8_t, uint16_t, const char *);
uint8_t write16(uint8_t, uint16_t, uint16_t); //Will write 2 bytes
uint8_t write16(uint8_t, uint16_t, uint32_t); //Will write 4 bytes
uint8_t write16(uint8_t, uint16_t, uint64_t); //Will write 8 bytes
uint8_t write16(uint8_t, uint16_t, const uint8_t *, uint8_t);
//These functions will be used to read from Slaves that take 16-bit addresses
uint8_t read16(uint8_t, uint16_t, uint8_t);
uint8_t read16(uint8_t, uint16_t, uint8_t, uint8_t *);
//Low-level methods
uint8_t _start();
uint8_t _sendAddress(uint8_t);
uint8_t _sendByte(uint8_t);
uint8_t _receiveByte(uint8_t);
uint8_t _receiveByte(uint8_t, uint8_t *target);
uint8_t _stop();
private:
void lockUp();
uint8_t returnStatus;
uint8_t nack;
uint8_t data[MAX_BUFFER_SIZE];
static uint8_t bytesAvailable;
static uint8_t bufferIndex;
static uint8_t totalBytes;
static uint16_t timeOutDelay;
};
extern I2C I2c;
#endif