cancel
Showing results for 
Search instead for 
Did you mean: 

Could not read and write the ISM330DLC each 10ms period

NSemrHomeInit
Senior

Dear ST Hello,

I am trying to use the ISM330DLC 3D accelerometer and gyroscope with the stm32F329Discovery board and I am facing some problems when I want to read and write all the registers every 10 ms ISR period.

I want to try to change the registers every period without compiling in changing the code each time. I am doing this to have to calibrate the filters in real time.

To do so I am defining all the registers in a header file. here is an example of the status register.

#define ISM330DLC_STATUS_REG             0x1EU
typedef volatile union
{
	uint8_t All;
	struct
	{
		uint8_t XLDA :1;	//Accelerometer new data available
		uint8_t GDA :1;	//Gyroscope new data available
		uint8_t TDA :1;	//Temperature new data available
		uint8_t Reserved :5;
	} ISM330DLC_RegBits;
} Tun_Status_Reg;

I am doing the same thing to all the registers and I am defining a union (buffer & struct) for all the ISM330DLC registers.

typedef union
{
	struct
	{
		uint8_t Reserved1;                                                //RESERVED
		Tun_Runc_Cfg_Access FUNC_CFG_ACCESS;                              //FUNC_CFG_ACCESS
		uint8_t Reserved2;                                                //RESERVED
		uint8_t Reserved3;                                                //RESERVED	
...
	uint8_t Reserved9;                                                //RESERVED
	} ISM330DLC_Reg_Struct;
	uint8_t ISM330DLC_Reg_Tab[ISM330DLC_MAX_BUFFER_REG];
} ISM330DLC_iDriver_Description;

I stored in an array of structures the type (RW) and the address of each register

Reg_Type_Address IMS330DLC_Reg_Type_Adr [] =
{	//adr          //Type	           //R/W
	{.adr=0x00,    .type=0xFF},	       //-         //FF Reserved    RESERVED
	{.adr=0x01,    .type=0x03},	       //r/w       //0x02 Read      FUNC_CFG_ACCESS
	{.adr=0x02,    .type=0xFF},	       //-         //0x03 Write     RESERVED
	{.adr=0x03,    .type=0xFF},        //-                          RESERVED
	{.adr=0x04,    .type=0x03},        //r/w                        ENSOR_SYNC_TIME_FRAME
	{.adr=0x05,    .type=0x03},        //r/w                        SENSOR_SYNC_RES_RATIO
	{.adr=0x06,    .type=0x03},        //r/w                        FIFO_CTRL1
	{.adr=0x07,    .type=0x03},        //r/w                        FIFO_CTRL2
...
	{.adr=0x6F,    .type=0x03},        //r/w                        INT_OIS
	{.adr=0x70,    .type=0x03},        //r/w                        CTRL1_OIS
	{.adr=0x71,    .type=0x03},        //r/w                        CTRL2_OIS
	{.adr=0x72,    .type=0x03},        //r/w                        CTRL3_OIS
	{.adr=0x73,    .type=0x03},        //r/w                        X_OFS_USR
	{.adr=0x74,    .type=0x03},        //r/w                        Y_OFS_USR
	{.adr=0x75,    .type=0x03},        //r/w                        Z_OFS_USR
	{.adr=0x7F,    .type=0xFF},        //-                          RESERVED
};

I have two functions the first one is for init and the second is the task:

The init just fills up the structure with the values to be sent to the Gryro in the init phase.

the BSP_ISM330DLC_ReadWrite_Reg will be called each 10ms and read all the registers and write if any register is manually updated in the real-time watch expression.

uint16_t BSP_ISM330DLC_ReadWrite_Reg(ISM330DLC_iDriver_Description *GyroAccDriverReg, uint16_t Num)
 
{
 
	uint16_t index;
 
	uint16_t sizeofBuffer;
 
	sizeofBuffer = 40;//sizeof(GyroAccDriverReg->ISM330DLC_Reg_Tab)/sizeof(GyroAccDriverReg->ISM330DLC_Reg_Tab[0]);
 
 
 
	if(GyroAcc->ReadID() == GyroAccDriverReg->ISM330DLC_Reg_Struct.WHO_AM_I)
 
	{
 
		for (index = 0; index < sizeofBuffer ; index++)
 
		{
 
			Debugvariable.loop_counter++;
 
			if (0xFF != IMS330DLC_Reg_Type_Adr[index].type)
 
			{
 
				//check if any bit has been changed
 
				if (u8_ISM330DLC_Reg[index] != GyroAccDriverReg->ISM330DLC_Reg_Tab[index])
 
				{
 
					//bit has been changed in the driver register updated it
 
					ISM330DLC_Update_Regiter_Flag = 1;
 
				}
 
				//loop through the buffer and read write if necessary
 
				if (0x02 == IMS330DLC_Reg_Type_Adr[index].type)
 
				{
 
					//read
 
					Acc_Gyro_Ism330dlc_Read(&GyroAccDriverReg->ISM330DLC_Reg_Tab[index], IMS330DLC_Reg_Type_Adr[index].adr, Num);
 
 
 
					// Read data to a local buffer
 
					u8_TL3GD20_Reg[index] = GyroAccDriverReg->ISM330DLC_Reg_Tab[index];
 
 
 
					//reset the flag when write is done!
 
					ISM330DLC_Update_Regiter_Flag = 0;
 
				}
 
				else if (0x03 == IMS330DLC_Reg_Type_Adr[index].type)
 
				{
 
					if ((1u == ISM330DLC_Update_Regiter_Flag))
 
					{
 
						//write
 
						Acc_Gyro_Imc330dlc_Write(&GyroAccDriverReg->ISM330DLC_Reg_Tab[index], IMS330DLC_Reg_Type_Adr[index].adr, Num);
 
						//reset the flag when write is done!
 
						ISM330DLC_Update_Regiter_Flag = 0;
 
					}
 
					//read
 
					Acc_Gyro_Ism330dlc_Read(&GyroAccDriverReg->ISM330DLC_Reg_Tab[index], IMS330DLC_Reg_Type_Adr[index].adr, Num);
 
					//if write read is not good issue a problem.
 
 
 
					// Read data to a local buffer
 
					u8_ISM330DLC_Reg[index] = GyroAccDriverReg->ISM330DLC_Reg_Tab[index];
 
				}
 
				else
 
				{
 
 
 
				}
 
 
 
 
 
			}
 
		}
 
		return 1;
 
	}
 
	else
 
	{
 
		Debugvariable.id_failure++;
 
		return -1;
 
	}
 
}

My problem is when I read all the registers some of them are messy

and shifted in some cases. It looks like I read more than uint8_t somewhere and overwritten the structure. I read the datasheet all registers are 8 bits.

I pushed my code to git if you want to see the whole code.

https://github.com/semrade/Meme_project.git

0 REPLIES 0