cancel
Showing results for 
Search instead for 
Did you mean: 

Inemo-M1 'LSM303DLHC_AccDataReady.c' problem

bouvett
Associate
Posted on June 18, 2014 at 11:54

Hi guys,

I have jsut started using the Inemo_m1 discovery board.

After Installing the software and doing some hello world projects (using KEIL IDE;debugged via ST-Link debugger), I decided to setup communication with the on board accelerometer.

In the installation directory: STEVAL-MKI121V1\Discovery-M1_Fw_Package\iNemo_M1_Applications\Source\examples

There is a source file named: LSM303DLHC_AccDataReady.c

I created a project, set the code in this .c file as the main function and compiled the project. After including some source and header files, the project compiled succesfully.

I loaded the project onto the inemo and started debugging with the ST-Link debugger.. The debugger jams atinstruction ' while(!xAccDataReady);' waiting for the accelerometer data ready interrupt to happen. 

I have gone through all the code and it seems that all has been well set, I really can't figure out what is wrong... anybody had any try to this code? Any help is much appreciated..

regards

#lsm303dlhc_accdataready-inemo-m1
3 REPLIES 3
valeriagh
Associate II
Posted on July 03, 2014 at 18:10

Hello,

I'm currently trying the same code. I can show you my code, because I decided to modify it, and it seems to work. I have also included an additional part about USART communication; you can ignore it. I hope it could be helpful.... Bye! 😉

/* Includes ------------------------------------------------------------------*/

#include ''stm32f10x.h''

#include ''stm32f10x_usart.h''

#include ''stm32_eval.h''

#include ''LSM303DLHC.h''

#include ''misc.h''

void GPIO_Configuration(void);

void RCC_Configuration(void);

/**

 * @brief Accelerometer sensor init structure

 */

LSMAccInit LSMAccInitStructure;

/**

* @brief Accelerometer high pass filter init structure

*/

LSMAccFilterInit LSMAccFilterInitStructure;

/**

 * @brief Acceletometer DataReady flag

 */

FlagStatus xAccDataReady = RESET;

/**

 * @brief Acceleration and Magnetic field values

 */

float fAccXYZ[3];

/**

 * @brief Accelerometer status

 */

LSMADataStatus xAccStatus;

int main(void)

{

uint16_t data = 0x00;

/* At this stage the microcontroller clock setting is already configured,

 this is done through SystemInit() function which is called from startup

 file (startup_stm32f10x_xx.s) before to branch to application main.

 To reconfigure the default setting of SystemInit() function, refer to

 system_stm32f10x.c file

 */

 GPIO_InitTypeDef GPIO_InitStructure;

 USART_InitTypeDef USART_InitStructure;

 RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);

 /* Initialize the MCU digital interface to communicate with the sensor */

 Lsm303dlhcI2CInit();

 /* Fill the accelerometer structure */

 LSMAccInitStructure.xPowerMode = LSM_NORMAL_MODE;

 LSMAccInitStructure.xOutputDataRate = LSM_ODR_50_HZ;

 LSMAccInitStructure.xEnabledAxes= LSM_ALL_AXES_EN;

 LSMAccInitStructure.xFullScale = LSM_FS_2G;

 LSMAccInitStructure.xDataUpdate = LSM_CONTINUOS_UPDATE;

 LSMAccInitStructure.xEndianness=LSM_BIG_ENDIAN;

 LSMAccInitStructure.xHighResolution=LSM_ENABLE;

 /* Fill the accelerometer LPF structure */

 LSMAccFilterInitStructure.xHPF=LSM_DISABLE;

 LSMAccFilterInitStructure.xHPF_Mode=LSM_HPFM_NORMAL;

 LSMAccFilterInitStructure.cHPFReference=0x00;

 LSMAccFilterInitStructure.xHPFCutOff=LSM_HPCF_16;

 LSMAccFilterInitStructure.xHPFClick=LSM_DISABLE;

 LSMAccFilterInitStructure.xHPFAOI2=LSM_DISABLE;

 LSMAccFilterInitStructure.xHPFAOI1=LSM_DISABLE;

 /* Configure the sensor IRQ */

 Lsm303dlhcAccIrq1Config(LSM_I1_DRDY1,LSM_ENABLE);

 /* Configure the accelerometer main parameters */

 Lsm303dlhcAccConfig(&LSMAccInitStructure);

 /* Configure the accelerometer LPF main parameters */

 Lsm303dlhcAccFilterConfig(&LSMAccFilterInitStructure);

 /* System Clocks Configuration */

  RCC_Configuration();

 /* Configure the GPIO ports */

 GPIO_Configuration();

 /*USART1 Initialization*/

 USART_InitStructure.USART_BaudRate = 9600;

 USART_InitStructure.USART_WordLength = USART_WordLength_8b;

 USART_InitStructure.USART_StopBits = USART_StopBits_1;

 USART_InitStructure.USART_Parity = USART_Parity_No;

 USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;

 USART_InitStructure.USART_Mode = USART_Mode_Tx| USART_Mode_Rx;

 /* Configure the USART1 */

 USART_Init(USART1, &USART_InitStructure);

 /* Enable USART1 to receive interrupt */

 USART_ITConfig(USART1,USART_IT_RXNE, ENABLE);

 /* Enable the USART1 */

 USART_Cmd(USART1, ENABLE);

 while(1)

{

     /* Wait for data ready (set by the proper ISR) */

     while(!xAccDataReady);

     xAccDataReady=RESET;

     /* Read the data status */

     xAccStatus =Lsm303dlhcAccGetDataStatus();

     /* Read data */

     Lsm303dlhcAccReadAcc(fAccXYZ);

     // wait until data register is empty

     while( !(USART1->SR & 0x00000040) );

     USART_SendData(USART1, 0x46);

 }

}

void RCC_Configuration(void)

{

  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA , ENABLE);

  RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1 , ENABLE);

}

void GPIO_Configuration(void)

{

  GPIO_InitTypeDef GPIO_InitStructure1,GPIO_InitStructure2;

  /* Configure USARTy Rx as input floating */

  GPIO_InitStructure1.GPIO_Pin =GPIO_Pin_10;

  GPIO_InitStructure1.GPIO_Speed = GPIO_Speed_50MHz;

  GPIO_InitStructure1.GPIO_Mode = GPIO_Mode_IN_FLOATING;

  GPIO_Init(GPIOA, &GPIO_InitStructure1);

  /* Configure USARTy Tx as alternate function push-pull */

  GPIO_InitStructure2.GPIO_Pin =GPIO_Pin_9;

  GPIO_InitStructure2.GPIO_Speed = GPIO_Speed_50MHz;

  GPIO_InitStructure2.GPIO_Mode = GPIO_Mode_AF_PP;

  GPIO_Init(GPIOA, &GPIO_InitStructure2);

  /* Configure USARTz Tx as alternate function push-pull */

}

valeriagh
Associate II
Posted on July 05, 2014 at 09:13

Hello,

I'm sorry for the reply posted a few days ago,  but it didn't work. I fixed some problems and found a new solution to receive data from accelerometer. You can also choose another type of communication with iNEMO (CAN , SPI, etc..) ; I decided to use USART because it's easier to set configuration. I have tested this code and it works fine! Here's the code: 

/* Includes ------------------------------------------------------------------*/

#include ''stm32f10x.h''

#include ''stm32f10x_usart.h''

#include ''stm32_eval.h''

#include ''LSM303DLHC.h''

#include ''misc.h''

void GPIO_Configuration(void);

void RCC_Configuration(void);

/**

 * @brief Accelerometer sensor init structure

 */

LSMAccInit LSMAccInitStructure;

/**

* @brief Accelerometer high pass filter init structure

*/

LSMAccFilterInit LSMAccFilterInitStructure;

LSMADataStatus AccStatus;

/**

 * @brief Acceleration and Magnetic field values

 */

float fAccXYZ[3];

/**

 * @brief Accelerometer status

 */

LSMADataStatus xAccStatus;

int main(void)

{

LSMADataStatus AccDataStatus;

uint8_t data_sample = 0;

uint16_t data_reg = 0;

     int i = 0;

for (i = 0; i<3; i++)

{

fAccXYZ[i] = 0.0;

}

/* At this stage the microcontroller clock setting is already configured,

 this is done through SystemInit() function which is called from startup

 file (startup_stm32f10x_xx.s) before to branch to application main.

 To reconfigure the default setting of SystemInit() function, refer to

 system_stm32f10x.c file

 */

/*I2C communication  configuration*/

      iNemoI2CInit(LSM_I2C, LSM_I2C_Speed);

 GPIO_InitTypeDef GPIO_InitStructure;

 USART_InitTypeDef USART_InitStructure;

 RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);

 /* Initialize the MCU digital interface to communicate with the sensor */

 Lsm303dlhcI2CInit();

 /* Fill the accelerometer structure */

 LSMAccInitStructure.xPowerMode = LSM_NORMAL_MODE;

 LSMAccInitStructure.xOutputDataRate = LSM_ODR_50_HZ;

 LSMAccInitStructure.xEnabledAxes= LSM_ALL_AXES_EN;  //all axes enabled

 LSMAccInitStructure.xFullScale = LSM_FS_2G;

 LSMAccInitStructure.xDataUpdate = LSM_BLOCK_UPDATE;

 LSMAccInitStructure.xEndianness = LSM_BIG_ENDIAN;

 LSMAccInitStructure.xHighResolution = LSM_ENABLE;

 /* Fill the accelerometer LPF structure */

 LSMAccFilterInitStructure.xHPF = LSM_DISABLE;

 LSMAccFilterInitStructure.xHPF_Mode = LSM_HPFM_NORMAL;

 LSMAccFilterInitStructure.cHPFReference = 0x00;

 LSMAccFilterInitStructure.xHPFCutOff = LSM_HPCF_16;

 LSMAccFilterInitStructure.xHPFClick = LSM_DISABLE;

 LSMAccFilterInitStructure.xHPFAOI2 = LSM_DISABLE;

 LSMAccFilterInitStructure.xHPFAOI1 = LSM_DISABLE;

 /* Configure the sensor IRQ */

 Lsm303dlhcAccIrq1Config(LSM_I1_DRDY1, LSM_ENABLE);

 /* Configure the accelerometer main parameters */

 Lsm303dlhcAccConfig(&LSMAccInitStructure);

 /* Configure the accelerometer LPF main parameters */

 Lsm303dlhcAccFilterConfig(&LSMAccFilterInitStructure);

 /* System Clocks Configuration */

  RCC_Configuration();

 /* Configure the GPIO ports */

 GPIO_Configuration();

 /*USART1 Initialization*/

 USART_InitStructure.USART_BaudRate = 9600;

 USART_InitStructure.USART_WordLength = USART_WordLength_8b;

 USART_InitStructure.USART_StopBits = USART_StopBits_1;

 USART_InitStructure.USART_Parity = USART_Parity_No;

 USART_InitStructure.USART_HardwareFlowControl =           USART_HardwareFlowControl_None;

 USART_InitStructure.USART_Mode = USART_Mode_Tx| USART_Mode_Rx;

 /* Configure the USART1 */

 USART_Init(USART1, &USART_InitStructure);

 /* Enable USART1 to receive interrupt */

 USART_ITConfig(USART1,USART_IT_RXNE, ENABLE);

 /* Enable the USART1 */

 USART_Cmd(USART1, ENABLE);

 /*Configure I2C*/

 iNemoI2CInit(I2C2, 100);

 AccDataStatus.X_Da  = RESET;

 while(1)

{

AccDataStatus = Lsm303dlhcAccGetDataStatus();

if(AccDataStatus.X_Da == SET)

{

             //Lsm303dlhcAccReadAcc(fAccXYZ);

             iNemoI2CBufferReadPolling(I2C2, LSM_A_I2C_ADDRESS, &data_sample, LSM_A_OUT_X_H_REG_ADDR, 1);

             data_reg |= data_sample;

             data_reg = data_reg << 8;

             iNemoI2CBufferReadPolling(I2C2, LSM_A_I2C_ADDRESS, &data_sample, LSM_A_OUT_X_L_REG_ADDR,1);

             data_reg |= data_sample;

             AccDataStatus.X_Da = RESET;

 }

     // wait until data register is empty

     while( !(USART1->SR & 0x00000040) );

     USART_SendData(USART1, data_reg );

     data_reg = 0;

 }

}

void RCC_Configuration(void)

{

  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA , ENABLE);

  RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1 , ENABLE);

}

void GPIO_Configuration(void)

{

  GPIO_InitTypeDef GPIO_InitStructure1,GPIO_InitStructure2;

  /* Configure USART Rx as input floating */

  GPIO_InitStructure1.GPIO_Pin =GPIO_Pin_10;

  GPIO_InitStructure1.GPIO_Speed = GPIO_Speed_50MHz;

  GPIO_InitStructure1.GPIO_Mode = GPIO_Mode_IN_FLOATING;

  GPIO_Init(GPIOA, &GPIO_InitStructure1);

  /* Configure USART Tx as alternate function push-pull */

  GPIO_InitStructure2.GPIO_Pin =GPIO_Pin_9;

  GPIO_InitStructure2.GPIO_Speed = GPIO_Speed_50MHz;

  GPIO_InitStructure2.GPIO_Mode = GPIO_Mode_AF_PP;

  GPIO_Init(GPIOA, &GPIO_InitStructure2);

}

I suppose that sample code in iNEMO folder is wrong, because it doesn't work. As you can see, I have used i2c iNEMO functions to take values from accelerometer registers. Hope this could be helpful! 

Bye

valeriagh
Associate II
Posted on July 13, 2014 at 17:32

Hello,

I don't know if you have already fixed this problem, but I've understood why interrupt handler is not being called. This is why software interrupts are disabled! So you have to modify the code, including 

/* Generate software interrupt: simulate a rising edge applied on  EXTI line interrupt*/

  EXTI_GenerateSWInterrupt(/*EXTI_Line_Interrupt*/);

in function ExtiConfiguration()  in main.c  🙂