@@ -82,6 +82,8 @@ functional with Silicon date=0x16042000
82
82
*/
83
83
static i2c_err_t i2cAddQueue (i2c_t * i2c ,uint8_t mode , uint16_t i2cDeviceAddr , uint8_t * dataPtr , uint16_t dataLen ,bool sendStop , EventGroupHandle_t event ){
84
84
85
+ if (i2c == NULL ) return I2C_ERROR_DEV ;
86
+
85
87
I2C_DATA_QUEUE_t dqx ;
86
88
dqx .data = dataPtr ;
87
89
dqx .length = dataLen ;
@@ -100,6 +102,7 @@ if(event){// an eventGroup exist, so, initialize it
100
102
}
101
103
102
104
if (i2c -> dq != NULL ){ // expand
105
+ //log_i("expand");
103
106
I2C_DATA_QUEUE_t * tq = (I2C_DATA_QUEUE_t * )realloc (i2c -> dq ,sizeof (I2C_DATA_QUEUE_t )* (i2c -> queueCount + 1 ));
104
107
if (tq != NULL ){// ok
105
108
i2c -> dq = tq ;
@@ -111,6 +114,7 @@ if(i2c->dq!=NULL){ // expand
111
114
}
112
115
}
113
116
else { // first Time
117
+ //log_i("new");
114
118
i2c -> queueCount = 0 ;
115
119
i2c -> dq = (I2C_DATA_QUEUE_t * )malloc (sizeof (I2C_DATA_QUEUE_t ));
116
120
if (i2c -> dq != NULL ){
@@ -125,10 +129,12 @@ return I2C_ERROR_OK;
125
129
}
126
130
127
131
i2c_err_t i2cFreeQueue (i2c_t * i2c ){
132
+ if (i2c == NULL ) return I2C_ERROR_DEV ;
128
133
// need to grab a MUTEX for exclusive Queue,
129
134
// what out if ISR is running?
130
135
i2c_err_t rc = I2C_ERROR_OK ;
131
136
if (i2c -> dq != NULL ){
137
+ // log_i("free");
132
138
// what about EventHandle?
133
139
free (i2c -> dq );
134
140
i2c -> dq = NULL ;
@@ -319,6 +325,9 @@ i2c_t * i2cInit(uint8_t i2c_num) //before this is called, pins should be detache
319
325
}
320
326
#endif
321
327
I2C_MUTEX_LOCK ();
328
+
329
+ i2cReleaseISR (i2c ); // ISR exists, release it before disabling hardware
330
+
322
331
uint32_t old_clock = i2cGetFrequency (i2c );
323
332
324
333
if (i2c_num == 0 ) {
@@ -348,7 +357,7 @@ i2c_t * i2cInit(uint8_t i2c_num) //before this is called, pins should be detache
348
357
349
358
return i2c ;
350
359
}
351
-
360
+ /* unused 03/15/2018
352
361
void i2cInitFix(i2c_t * i2c){
353
362
if(i2c == NULL){
354
363
return;
@@ -370,7 +379,8 @@ void i2cInitFix(i2c_t * i2c){
370
379
while ((!i2c->dev->command[2].done) && (--count > 0));
371
380
I2C_MUTEX_UNLOCK();
372
381
}
373
-
382
+ /*
383
+ unused 03/15/2018
374
384
void i2cReset(i2c_t* i2c){
375
385
if(i2c == NULL){
376
386
return;
@@ -382,6 +392,7 @@ void i2cReset(i2c_t* i2c){
382
392
periph_module_enable( moduleId );
383
393
I2C_MUTEX_UNLOCK();
384
394
}
395
+ */
385
396
386
397
/* Stickbreaker ISR mode debug support
387
398
*/
@@ -615,7 +626,6 @@ log_n("Enable Core Debug Level \"Error\"");
615
626
#endif
616
627
}
617
628
618
-
619
629
void i2cDumpI2c (i2c_t * i2c ){
620
630
log_e ("i2c=%p" ,i2c );
621
631
log_e ("dev=%p date=%p" ,i2c -> dev ,i2c -> dev -> date );
@@ -960,19 +970,31 @@ i2c_err_t i2cProcQueue(i2c_t * i2c, uint32_t *readCount, uint16_t timeOutMillis)
960
970
install ISR if necessary
961
971
setup EventGroup
962
972
handle bus busy?
963
- do I load command[] or just pass that off to the ISR
964
973
*/
965
974
//log_e("procQueue i2c=%p",&i2c);
966
975
* readCount = 0 ; //total reads accomplished in all queue elements
967
976
if (i2c == NULL ){
968
977
return I2C_ERROR_DEV ;
969
978
}
970
979
if (i2c -> dev -> status_reg .bus_busy ){ // return error, let TwoWire() handle resetting the hardware.
980
+ /* if multi master then this if should be changed to this 03/12/2018
981
+ if(multiMaster){// try to let the bus clear by its self
982
+ uint32_t timeOutTick = millis();
983
+ while((i2c->dev->status_reg.bus_busy)&&(millis()-timeOutTick<timeOutMillis())){
984
+ delay(2); // allow task switch
985
+ }
986
+ }
987
+ if(i2c->dev->status_reg.bus_busy){ // still busy, so die
988
+ log_i("Bus busy, reinit");
989
+ return I2C_ERROR_BUSY;
990
+ }
991
+ */
971
992
log_i ("Bus busy, reinit" );
972
993
return I2C_ERROR_BUSY ;
973
994
}
995
+
974
996
I2C_MUTEX_LOCK ();
975
- /* what about co-existance with SLAVE mode?
997
+ /* what about co-existence with SLAVE mode?
976
998
Should I check if a slaveMode xfer is in progress and hang
977
999
until it completes?
978
1000
if i2c->stage == I2C_RUNNING or I2C_SLAVE_ACTIVE
@@ -987,16 +1009,14 @@ for(uint16_t i=0;i<INTBUFFMAX;i++){
987
1009
}
988
1010
intPos [i2c -> num ] = 0 ;
989
1011
#endif
990
- // EventGroup is used to signal transmisison completion from ISR
1012
+ // EventGroup is used to signal transmission completion from ISR
991
1013
// not always reliable. Sometimes, the FreeRTOS scheduler is maxed out and refuses request
992
1014
// if that happens, this call hangs until the timeout period expires, then it continues.
993
1015
if (!i2c -> i2c_event ){
994
1016
i2c -> i2c_event = xEventGroupCreate ();
995
1017
}
996
1018
if (i2c -> i2c_event ) {
997
1019
uint32_t ret = xEventGroupClearBits (i2c -> i2c_event , 0xFF );
998
-
999
- // log_e("after clearBits(%p)=%p",i2c->i2c_event,ret);
1000
1020
}
1001
1021
else {// failed to create EventGroup
1002
1022
log_e ("eventCreate failed=%p" ,i2c -> i2c_event );
@@ -1032,7 +1052,7 @@ i2c->queuePos=0;
1032
1052
i2c -> byteCnt = 0 ;
1033
1053
uint32_t totalBytes = 0 ; // total number of bytes to be Moved!
1034
1054
// convert address field to required I2C format
1035
- while (i2c -> queuePos < i2c -> queueCount ){
1055
+ while (i2c -> queuePos < i2c -> queueCount ){ // need to push these address modes upstream, to AddQueue
1036
1056
I2C_DATA_QUEUE_t * tdq = & i2c -> dq [i2c -> queuePos ++ ];
1037
1057
uint16_t taddr = 0 ;
1038
1058
if (tdq -> ctrl .addrReq == 2 ){ // 10bit address
@@ -1073,7 +1093,7 @@ i2c->dev->int_ena.val =
1073
1093
I2C_RXFIFO_FULL_INT_ENA ; // (BIT(0)) trigger emptyRxFifo()
1074
1094
1075
1095
if (!i2c -> intr_handle ){ // create ISR for either peripheral
1076
- log_i ("create ISR" );
1096
+ // log_i("create ISR %d",i2c->num );
1077
1097
uint32_t ret ;
1078
1098
switch (i2c -> num ){
1079
1099
case 0 :
@@ -1218,19 +1238,40 @@ I2C_MUTEX_UNLOCK();
1218
1238
return reason ;
1219
1239
}
1220
1240
1221
- i2c_err_t i2cReleaseISR (i2c_t * i2c ){
1241
+ void i2cReleaseISR (i2c_t * i2c ){
1222
1242
if (i2c -> intr_handle ){
1243
+ // log_i("Release ISR %d",i2c->num);
1223
1244
esp_err_t error = esp_intr_free (i2c -> intr_handle );
1224
1245
// log_e("released ISR=%d",error);
1225
1246
i2c -> intr_handle = NULL ;
1226
1247
}
1248
+ }
1249
+
1250
+ void i2cReleaseAll (i2c_t * i2c ){ // release all resources, power down peripheral
1251
+ // gpio pins must be released BEFORE this function or a Glitch will appear
1252
+
1253
+ I2C_MUTEX_LOCK ();
1254
+
1255
+ i2cReleaseISR (i2c );
1256
+
1227
1257
if (i2c -> i2c_event ){
1228
1258
vEventGroupDelete (i2c -> i2c_event );
1229
1259
i2c -> i2c_event = NULL ;
1230
1260
}
1231
- return i2cFreeQueue (i2c );
1232
- }
1233
1261
1262
+ i2cFreeQueue (i2c );
1263
+
1264
+ // reset the I2C hardware and shut off the clock, power it down.
1265
+ if (i2c -> num == 0 ) {
1266
+ DPORT_SET_PERI_REG_MASK (DPORT_PERIP_RST_EN_REG ,DPORT_I2C_EXT0_RST ); //reset hardware
1267
+ DPORT_CLEAR_PERI_REG_MASK (DPORT_PERIP_CLK_EN_REG ,DPORT_I2C_EXT0_CLK_EN ); // shutdown hardware
1268
+ } else {
1269
+ DPORT_SET_PERI_REG_MASK (DPORT_PERIP_RST_EN_REG ,DPORT_I2C_EXT1_RST ); //reset Hardware
1270
+ DPORT_CLEAR_PERI_REG_MASK (DPORT_PERIP_CLK_EN_REG ,DPORT_I2C_EXT1_CLK_EN ); // shutdown Hardware
1271
+ }
1272
+
1273
+ I2C_MUTEX_UNLOCK ();
1274
+ }
1234
1275
/* todo
1235
1276
24Nov17
1236
1277
Need to think about not usings I2C_MASTER_TRAN_COMP_INT_ST to adjust queuePos. This
0 commit comments