/****** I2C Driver implementation *******/ static bool StartTransfer(I2C_MODULE i2c_id, bool restart) { I2C_STATUS status; // Send the Start (or Restart) signal if (restart) { I2CRepeatStart(i2c_id); } else { // Wait for the bus to be idle, then start the transfer while (!I2CBusIsIdle(i2c_id)); if (I2CStart(i2c_id) != I2C_SUCCESS) { //DBPRINTF("Error: Bus collision during transfer Start\n"); return FALSE; } } // Wait for the signal to complete do { status = I2CGetStatus(i2c_id); } while (!(status & I2C_START)); return TRUE; }
BOOL StartTransfer( BOOL restart ) { I2C_STATUS status; // Send the Start (or Restart) signal if(restart) { I2CRepeatStart(EEPROM_I2C_BUS); } else { // Wait for the bus to be idle, then start the transfer while( !I2CBusIsIdle(EEPROM_I2C_BUS) ); if(I2CStart(EEPROM_I2C_BUS) != I2C_SUCCESS) { DBPRINTF("Error: Bus collision during transfer Start\n"); return FALSE; } } // Wait for the signal to complete do { status = I2CGetStatus(EEPROM_I2C_BUS); } while ( !(status & I2C_START) ); return TRUE; }
BOOL I2C_startTransfer(I2C_MODULE I2C_ID, BOOL restart){ I2C_STATUS status; // Send the Start (or Restart) signal if(restart){ if(I2CRepeatStart(I2C_ID) != I2C_SUCCESS){ #ifdef DEBUG printf("Error: Bus collision during transfer Start at Read\n"); #endif return FALSE; } } else{ // Wait for the bus to be idle, then start the transfer while( !I2CBusIsIdle(I2C_ID) ); if(I2CStart(I2C_ID) != I2C_SUCCESS){ #ifdef DEBUG printf("Error: Bus collision during transfer Start at Write\n"); #endif return FALSE; } } // Wait for the signal to complete do{ status = I2CGetStatus(I2C_ID); } while (!(status & I2C_START) ); return TRUE; }
/** * Invokes an I2C start condition * * @param restart invoke a restart condition if true */ void I2C_StartTransfer(bool restart) { // Send the Start (or Restart) signal if (restart) { I2CRepeatStart(I2C1); } else { // Wait for the bus to be idle, then start the transfer while (!I2CBusIsIdle(I2C1)); if (I2CStart(I2C1) != I2C_SUCCESS) { //serialPrint("Error: Bus collision during transfer Start\r\n"); while (1); } } // Wait for the signal to complete while (!(I2CGetStatus(I2C1) & I2C_START)); }
bool i2c_start(bool restart) { if (restart) { state = I2C_STATE_REPEATED_START; if (I2CRepeatStart(I2C1) != I2C_SUCCESS) return FALSE; } else { state = I2C_STATE_START; if (I2CStart(I2C1) != I2C_SUCCESS) return FALSE; } if (!semaphore_take(bus_lock, PORT_MAX_DELAY)) return FALSE; return TRUE; }
/************************************************************************************************** Function: static BOOL I2CShared_StartTransfer(const I2C_MODULE i2c, const BOOL restart) Author(s): mkobit Summary: Starts or restarts a transaction Description: Blocks until transaction has been started, restarts the transaction if (restart) is TRUE Static function, used by internal library Preconditions: I2C module configured *Transaction started - *only if (restart) is TRUE Parameters: const I2C_MODULE i2c - I2C module to be used for this transaction const BOOL restart - restart transaction when TRUE, just start when FALSE Returns: TRUE - If successful FALSE - If unsuccessful Example: <code> I2CShared_StartTransfer(i2c, FALSE) </code> Conditions at Exit: Bus transaction started I2C waiting for next action **************************************************************************************************/ static BOOL I2CShared_StartTransfer(const I2C_MODULE i2c, const BOOL restart) { I2C_STATUS status; int fault_count = 0; // Send the start/restart signal if(restart) { I2CRepeatStart(i2c); } else { // Wait for the bus to be idle, then start the transfer while(!I2CBusIsIdle(i2c)){ if (fault_count++ == TIMEOUT) { //printf("I2CShared_StartTransfer: Timeout waiting for bus to be idle\n"); return FALSE; } } if(I2CStart(i2c) == I2C_ARBITRATION_LOSS) { //printf("I2CShared_StartTransfer: I2CStart experienced I2C_ARBITRATION_LOSS\n"); //I2CShared_DebugStatus(i2c); return FALSE; } } fault_count = 0; // Wait for the signal to complete do { status = I2CGetStatus(i2c); if (status & I2C_ARBITRATION_LOSS) { //printf("I2CShared_StartTransfer: lost arbitration on i2c bus\n"); return FALSE; } if (fault_count++ == TIMEOUT) { //printf("I2CShared_StartTransfer: Timeout waiting for bus to start\n"); return FALSE; } } while (!(status & I2C_START)); return TRUE; }
BOOL StartTransfer( BOOL restart ) { I2C_STATUS status; // Send the Start (or Restart) signal if(restart) { I2CRepeatStart(PIC24_I2C_BUS); } else { // Wait for the bus to be idle, then start the transfer while( !I2CBusIsIdle(PIC24_I2C_BUS) ); if(I2CStart(PIC24_I2C_BUS) != I2C_SUCCESS) { DBPRINTF("Error: Bus collision during transfer Start\n"); printf("bus coll\n"); //Succ = FALSE; //goto RECOVER; } } // Wait for the signal to complete do { status = I2CGetStatus(PIC24_I2C_BUS); //printf("waiting for signal\n"); } while ( !(status & I2C_START) ); RECOVER: //if(!Succ) return FALSE; //else return TRUE; return TRUE; }
/* Sends a start inside i2c transaction (with no strings attached) */ void repeatStart(I2C_MODULE I2C){ I2CRepeatStart(I2C); while( ! (I2CGetStatus(I2C) & I2C_START) ); I2CClearStatus(I2C, I2C_START); }
void i2c_isr(uint8_t p) { I2CModule_t * mod; // Get a reference to the module structure switch (p) { case I2C2: mod = &I2C_2; break; default: return; } switch (mod->state) { case IDLE: break; case START: I2CStart(mod->moduleName); mod->state = ADDRESS; I2C_2.dataDirection = WRITING; break; case ADDRESS: switch (mod->dataDirection) { case READING: I2CSendByte(mod->moduleName, mod->frame->address + 1); mod->state = CHECK_ACK; break; case WRITING: I2CSendByte(mod->moduleName, mod->frame->address); mod->state = CHECK_ACK; break; } break; case CHECK_ACK: if (I2CByteWasAcknowledged(mod->moduleName) == True) { switch (mod->dataDirection) { case READING: mod->state = READ; break; case WRITING: mod->state = WRITE; break; } } else { mod->frame->success = False; mod->state = STOP; } i2c_isr(mod->moduleName); break; case RESTART: I2CRepeatStart(mod->moduleName); mod->dataDirection = READING; mod->state = ADDRESS; break; case READ_START: I2CReceiverEnable(mod->moduleName, TRUE); mod->state = READ; break; case READ: mod->frame->rx_buf[mod->frame->rx_buf_index++] = I2CGetByte(mod->moduleName); // If we need to read more bytes send an ACK if (mod->frame->rx_buf_index <= mod->frame->bytesToRead) { I2CAcknowledgeByte(mod->moduleName, True); // Send an ACK mod->state = READ_START; // Prepare for the next byte } else { I2CAcknowledgeByte(mod->moduleName, False); // Send a NACK mod->frame->success = True; mod->state = STOP; // Prepare for a stop condition } break; case WRITE: // If there are still bytes to send if (mod->frame->tx_buf_index < mod->frame->tx_buf_size) { I2CSendByte(mod->moduleName, mod->frame->tx_buf[mod->frame->tx_buf_index++]); } else { // If we need to read some bytes if (mod->frame->bytesToRead > 0) { mod->state = RESTART; // Send a restart condition } else { mod->frame->success = True; mod->state = STOP; // Send a stop condition } i2c_isr(mod->moduleName); // Re-run this function to call stop/restart // TODO: Perhaps there is a better way to do this..! } break; case STOP: I2CStop(mod->moduleName); mod->frameToSend = False; mod->state = IDLE; // Tell the owner of the frame that it has complete or failed if (mod->frame->success == True) { mod->frame->callback(); } else { mod->frame->error(); } break; case BUSERROR: led12 = 1; // TODO: Something..! while(1); // Don't know what to do here yet..! break; } }
void i2cRepeatedStart(I2C_MODULE id){ I2CRepeatStart(id); while ( !(I2CGetStatus(id) & I2C_START) ); }
BOOL MPU6050::StartTransfer( BOOL restart ) { I2C_STATUS status = I2C_START; //UINT16 count = 0; //sprintf(filename, "Starting StartTransfer(), status = %d.\n", status); //putsUART1( filename ); // Send the Start (or Restart) signal if(restart) { I2C_RESULT res = I2C_SUCCESS; if((res = I2CRepeatStart( this->i2cBusId )) != I2C_SUCCESS) { sprintf(filename, "Repeat start, status = %d.\n",res); putsUART1( filename ); // Do not return, try to connect anyway and fail } } else { // Wait for the bus to be idle, then start the transfer //while( !I2CBusIsIdle(MPU6050_I2C_BUS) ); // Checks if the bus is idle, and starts the transfer if so if( I2CBusIsIdle( this->i2cBusId ) ) { if(I2CStart( this->i2cBusId ) != I2C_SUCCESS) { //DBPRINTF("Error: Bus collision during transfer Start\n"); sprintf( filename, "Error in I2CStart(). Bus collision on bus %u during transfer Start.\n", (unsigned)this->i2cBusId ); putsUART1( filename ); return FALSE; } } else { sprintf( filename, "Error in I2CBusIsIdle(). Bus %u is not idle.\n", (unsigned)this->i2cBusId ); putsUART1( filename ); return FALSE; } } //sprintf( filename, "StartTransfer(). Checking for Start response...\n" ); //putsUART1( filename ); UINT16 max_tries = 64000, count = 0; // Wait for the signal to complete or until tries are out do { status = I2CGetStatus( this->i2cBusId ); //sprintf( filename, "StartTransfer(). Status is %u \n", status & I2C_START ); //putsUART1( filename ); } while (!(status & I2C_START) && ++count < max_tries); if( count >= max_tries ) { sprintf( filename, "Error in StartTransfer(). Timeout!\n" ); putsUART1( filename ); return FALSE; } //sprintf( filename, "StartTransfer(). Function successfully completed!\n" ); //putsUART1( filename ); return TRUE; }