6
6
#include "i2c_api.h"
7
7
#include "pinmap.h"
8
8
#include "PeripheralPins.h"
9
+ #include "objects.h"
10
+ #include "stdio.h"
11
+
12
+ /******************************************************************************
13
+ * DEFINE
14
+ ******************************************************************************/
15
+
16
+ #if 1
17
+ #define DEBUG_PRINTF (...) printf(__VA_ARGS__)
18
+ #else
19
+ #define DEBUG_PRINTF (...)
20
+ #endif
21
+
22
+ #define NoData 0 // the slave has not been addressed
23
+ #define ReadAddressed 1 // the master has requested a read from this slave (slave = transmitter)
24
+ #define WriteGeneral 2 // the master is writing to all slave
25
+ #define WriteAddressed 3 // the master is writing to this slave (slave = receiver)
9
26
10
27
/******************************************************************************
11
28
* CONST
@@ -24,12 +41,23 @@ void i2c_init(i2c_t *obj, PinName sda, PinName scl)
24
41
I2CName const i2c_scl = (I2CName )pinmap_peripheral (scl , PinMap_I2C_SCL );
25
42
MBED_ASSERT (i2c_sda == i2c_scl );
26
43
44
+ #if DEVICE_I2CSLAVE
45
+ /** was_slave is used to decide which driver call we need
46
+ * to use when uninitializing a given instance
47
+ */
48
+ obj -> was_slave = false;
49
+ obj -> is_slave = false;
50
+ obj -> slave_addr = 0 ;
51
+ #endif
52
+
27
53
/* Obtain the pointer to the I2C hardware instance. */
28
54
obj -> dev = (i2c_inst_t * )pinmap_function (sda , PinMap_I2C_SDA );
29
- obj -> baudrate = DEFAULT_I2C_BAUDRATE ;
55
+ //obj->baudrate = DEFAULT_I2C_BAUDRATE;
56
+ //Call this function because if we are configuring a slave, we don't have to set the frequency
57
+ //i2c_frequency(obj->dev, DEFAULT_I2C_BAUDRATE);
30
58
31
59
/* Initialize the I2C module. */
32
- _i2c_init (obj -> dev , obj -> baudrate );
60
+ _i2c_init (obj -> dev , DEFAULT_I2C_BAUDRATE );
33
61
34
62
/* Configure GPIO for I2C as alternate function. */
35
63
gpio_set_function (sda , GPIO_FUNC_I2C );
@@ -42,6 +70,14 @@ void i2c_init(i2c_t *obj, PinName sda, PinName scl)
42
70
43
71
void i2c_frequency (i2c_t * obj , int hz )
44
72
{
73
+ DEBUG_PRINTF ("obj->is_slave: %d\r\n" , obj -> is_slave );
74
+
75
+ #if DEVICE_I2CSLAVE
76
+ /* Slaves automatically get frequency from master */
77
+ if (obj -> is_slave ) {
78
+ return ;
79
+ }
80
+ #endif
45
81
obj -> baudrate = i2c_set_baudrate (obj -> dev , hz );
46
82
}
47
83
@@ -95,3 +131,108 @@ const PinMap *i2c_master_scl_pinmap()
95
131
{
96
132
return PinMap_I2C_SCL ;
97
133
}
134
+
135
+ const PinMap * i2c_slave_sda_pinmap ()
136
+ {
137
+ return PinMap_I2C_SDA ;
138
+ }
139
+
140
+ const PinMap * i2c_slave_scl_pinmap ()
141
+ {
142
+ return PinMap_I2C_SCL ;
143
+ }
144
+
145
+ int i2c_stop (i2c_t * obj )
146
+ {
147
+
148
+ }
149
+
150
+ #if DEVICE_I2CSLAVE
151
+
152
+ /** Configure I2C as slave or master.
153
+ * @param obj The I2C object
154
+ * @param enable_slave Enable i2c hardware so you can receive events with ::i2c_slave_receive
155
+ * @return non-zero if a value is available
156
+ */
157
+ void i2c_slave_mode (i2c_t * obj , int enable_slave )
158
+ {
159
+ DEBUG_PRINTF ("i2c_slave_mode: %p, %d\r\n" , obj , enable_slave );
160
+
161
+ obj -> is_slave = enable_slave ;
162
+ }
163
+
164
+ /** Check to see if the I2C slave has been addressed.
165
+ * @param obj The I2C object
166
+ * @return The status - 1 - read addressed, 2 - write to all slaves,
167
+ * 3 write addressed, 0 - the slave has not been addressed
168
+ */
169
+ int i2c_slave_receive (i2c_t * obj )
170
+ {
171
+ int retValue = NoData ;
172
+
173
+ int rd_req = (obj -> dev -> hw -> raw_intr_stat & I2C_IC_RAW_INTR_STAT_RD_REQ_BITS ) >> 5 ;
174
+
175
+ if (rd_req == I2C_IC_RAW_INTR_STAT_RD_REQ_VALUE_ACTIVE ) {
176
+ DEBUG_PRINTF ("Read addressed\r\n" );
177
+ return ReadAddressed ;
178
+ }
179
+
180
+ int wr_req = (obj -> dev -> hw -> status & I2C_IC_STATUS_RFNE_BITS ) >> 3 ;
181
+
182
+ if (wr_req == I2C_IC_STATUS_RFNE_VALUE_NOT_EMPTY ) {
183
+ DEBUG_PRINTF ("Write addressed\r\n" );
184
+ return WriteAddressed ;
185
+ }
186
+
187
+ return (retValue );
188
+ }
189
+
190
+ /** Configure I2C as slave or master.
191
+ * @param obj The I2C objecti2c_get_read_availableread
192
+ * @return non-zero if a value is available
193
+ */
194
+ int i2c_slave_read (i2c_t * obj , char * data , int length )
195
+ {
196
+ size_t read_len = i2c_read_raw_blocking (obj -> dev , (uint8_t * )data , length );
197
+
198
+ DEBUG_PRINTF ("i2c_slave read %d bytes\r\n" , read_len );
199
+
200
+ return read_len ;
201
+ }
202
+
203
+ /** Configure I2C as slave or master.
204
+ * @param obj The I2C object
205
+ * @param data The buffer for sending
206
+ * @param length Number of bytes to write
207
+ * @return non-zero if a value is available
208
+ */
209
+ int i2c_slave_write (i2c_t * obj , const char * data , int length )
210
+ {
211
+ DEBUG_PRINTF ("i2c_slave_write\r\n" );
212
+
213
+ i2c_write_raw_blocking (obj -> dev , (const uint8_t * )data , (size_t )length );
214
+
215
+ //Clear interrupt
216
+ int clear_read_req = i2c_get_hw (obj -> dev )-> clr_rd_req ;
217
+ DEBUG_PRINTF ("clear_read_req: %d\n" , clear_read_req );
218
+
219
+ return length ;
220
+ }
221
+
222
+ /** Configure I2C address.
223
+ * @param obj The I2C object
224
+ * @param idx Currently not used
225
+ * @param address The address to be set
226
+ * @param mask Currently not used
227
+ */
228
+ void i2c_slave_address (i2c_t * obj , int idx , uint32_t address , uint32_t mask )
229
+ {
230
+ if (obj -> is_slave ) {
231
+ DEBUG_PRINTF ("i2c_slave_address: %p, %d, %d, %d\r\n" , obj , idx , address , mask );
232
+
233
+ obj -> slave_addr = (uint8_t )(address >> 1 );
234
+ i2c_set_slave_mode (obj -> dev , true, obj -> slave_addr );
235
+ }
236
+ }
237
+
238
+ #endif // DEVICE_I2CSLAVE
0 commit comments