cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F407 I2C ADDR bit clearing itself and interrupt problems

Defensive
Associate

Hi, Im new to STM32 and writing a bare metal interrupt based i2c library. For some reason addr bit clears itself automatically even though im not reading sr1 and sr2. I also have problems with debug mode, if i decide to step over the function that sets up the interrupt for I2C1_EV_IRQ it sometimes causes debugger to skip the interrupt, it happens randomly. I had some problems with the built in debugger.

 

void I2C_ReceiveData(I2C_Com* i2c, uint8_t address, uint8_t deviceRegister, uint8_t* data, uint8_t length)
{
	if(!i2c->isBusy)
	{
		i2c->i2cReg->I2C_CR1 |= (1 << 10);

		i2c->deviceAddress = address;
		i2c->deviceAddress <<= 1;

		i2c->deviceRegister = deviceRegister;
		i2c->registerNotSent = 1;

		i2c->txLength = 0;

		i2c->rxBuffer = data;
		i2c->rxLength = length;

		i2c->isBusy = 1;
		i2c->repeatedStart = 1;

		i2c->i2cReg->I2C_CR2 |= (1 << 9);
		i2c->i2cReg->I2C_CR2 |= (1 << 10);

		SetNVIC(I2C1_EV_IRQ_NUM, 1);

		//Start condition
		i2c->i2cReg->I2C_CR1 |= (1 << 8);
	}
}

void I2C_EventInterruptHandler(I2C_Com* i2c)
{
	uint8_t temp;

	//Check if event interrupt bit is set
	if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_CR2, 9))
	{
		//Start condition
		if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_SR1, 0))
		{
			temp = i2c->i2cReg->I2C_SR1;

			i2c->i2cReg->I2C_DR = i2c->deviceAddress;
		}

		//Check for address sent
                //ADDR BIT CLEARS ITSELF CANT GET INTO THIS IF STATEMENT
		if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_SR1, 1))
		{
			//Check if its in read mode and if rxLegth is 1
			if(i2c->deviceAddress & 1 && i2c->rxLength == 1)
			{
				//Disable ack
				i2c->i2cReg->I2C_CR1 &= ~(1 << 10);
				i2c->i2cReg->I2C_CR1 |= (1 << 9);
			}

			temp = i2c->i2cReg->I2C_SR1;
			temp = i2c->i2cReg->I2C_SR2;
		}

		//Check for tx/rx interrupt bit
		else if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_CR2, 10))
		{
			//tx interrupt
			if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_SR1, 7))
			{
				I2C_TxInterruptHandler(i2c);
			}

			//rx interrupt
			if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_SR1, 6))
			{
				I2C_RxInterruptHandler(i2c);
			}
		}

		//Check for BFT bit
		else if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_SR1, 2))
		{
			I2C_BFTInterruptHandler(i2c);
		}


		//Check for Stop bit
		else if(I2C_CheckBitStatus(&i2c->i2cReg->I2C_SR1, 4))
		{

		}
	}

}

void I2C1_EV_IRQHandler()
{
	I2C_EventInterruptHandler(&i2c1Com);
}

 

0 REPLIES 0