cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F4 Discovery and accelerometer

simoneformichella
Associate
Posted on September 10, 2016 at 20:32

Hi everybody,

I'm writing this post to ask if someone, please, can help me resolving a problem with the datas-reading from the accelerometer integrated in the STM32F4 Evaluation Board.

What I want to do it's simply to read the accelerations datas from the sensor, using the SPI interface. I've had a look at a lot of examples but I still don't know why my code doesn't work.

Here the main functions:

void WriteAccelerometer(SPI_HandleTypeDef SPI, uint8_t address, uint8_t data)

{

       HAL_GPIO_WritePin(GPIOE, GPIO_PIN_3, GPIO_PIN_RESET); //CS --> Low

           HAL_SPI_Transmit(&SPI,&address,1,50);

           HAL_SPI_Transmit(&SPI,&data,1,50);

           HAL_GPIO_WritePin(GPIOE, GPIO_PIN_3, GPIO_PIN_SET); //CS --> High

uint8_t ReadAccelerometer(SPI_HandleTypeDef SPI, uint8_t address, uint8_t data)

{

 address = address | 0x80;

 HAL_GPIO_WritePin(GPIOE, GPIO_PIN_3, GPIO_PIN_RESET); //CS --> Low

          HAL_SPI_Transmit(&SPI,&address,1,50);

 HAL_SPI_Receive(&SPI,&data,1,50);

          HAL_GPIO_WritePin(GPIOE, GPIO_PIN_3, GPIO_PIN_SET); //CS --> High

 return data;

}

Here the SPI configuration function:

static void MX_SPI1_Init(void)

{

  

hspi1.Instance = SPI1;

  hspi1.Init.Mode = SPI_MODE_MASTER;

  hspi1.Init.Direction = SPI_DIRECTION_2LINES;

  hspi1.Init.DataSize = SPI_DATASIZE_8BIT;

  hspi1.Init.CLKPolarity = SPI_POLARITY_LOW;

  hspi1.Init.CLKPhase = SPI_PHASE_1EDGE;

  hspi1.Init.NSS = SPI_NSS_SOFT;

  hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_16;

  hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB;

  hspi1.Init.TIMode = SPI_TIMODE_DISABLE;

  hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;

  hspi1.Init.CRCPolynomial = 10;

  if (HAL_SPI_Init(&hspi1) != HAL_OK)

  {

    Error_Handler();

  }

//WriteAccelerometer(hspi1,0x23,0xC9); //reset

//WriteAccelerometer(hspi1,0x21,0x00);

}

I use the two functions reported in this post to configurate and read the accelerometer with this commands:

uint8_t config_address = 0x20;

uint8_t config_data = 0x27; 

uint8_t Address_ACCX = 0x29;

uint8_t Address_ACCY = 0x2B;

uint8_t Address_ACCZ = 0x2D;

WriteAccelerometer(hspi1,config_address,config_data); //config

// read data:

AccX = ReadAccelerometer(hspi1,Address_ACCX,AccX);

AccY = ReadAccelerometer(hspi1,Address_ACCY,AccY);

AccZ = ReadAccelerometer(hspi1,Address_ACCZ,AccZ);

Thank you in advance for the help..

Simone

28 REPLIES 28
Posted on October 31, 2017 at 11:42

Yep, set ADDR 0x20 to 0x67 to initialise the MEMS and it responds to WHO_AM_I. Sometimes the temperature doesn't respond, but I found that on startup I reboot the MEMS by setting the BOOT bit high in 0x24 register.

My next problem is that my axes accelerations are static. I get a reading but it doesnt change at all. Any ideas?

EDIT: i have posted my (simplified) code in another comment

Posted on October 31, 2017 at 11:46

My function definitions are:

void

MEMS_write(

uint8_t

addr,

uint8_t

data){

   

uint8_t

send[2] = {addr, data};

   

HAL_GPIO_WritePin(

CS_I2C_SPI_GPIO_Port

, CS_I2C_SPI_Pin, LOW);

   HAL_SPI_Transmit(&hspi1, send, 2, 5000);

   

HAL_GPIO_WritePin(CS_I2C_SPI_GPIO_Port, CS_I2C_SPI_Pin, HIGH);

   

return

;

}

uint8_t

MEMS_read(

uint8_t

addr){

   

uint8_t

send[1] = {0x80 | addr};

   

uint8_t

out[1] = {0x00};

   

HAL_GPIO_WritePin(CS_I2C_SPI_GPIO_Port, CS_I2C_SPI_Pin, LOW);

   

HAL_SPI_TransmitReceive(&hspi1, send, out, 2, 0xFF);

   

HAL_GPIO_WritePin(CS_I2C_SPI_GPIO_Port, CS_I2C_SPI_Pin, HIGH);

   

return

out[1];

}

My simplified main is: (omitting non-spi code for readability)

int main(void){ 

  MEMS_write(0x24, 0b1000000);

//rebooting the

mems

seems to unlock it?

 

HAL_Delay(100);

 

MEMS_write(0x20, 0x67); //enable x, y, z axes and ODR

 

MEMS_write(0x24, 0x01);

//3 wire

spi

 

while

(1)

 

{

 

MEMS_read(0x0F); //request WHO_AM_I

 

HAL_Delay(10);

 

}

}

Zek_De
Senior
Posted on October 31, 2017 at 13:39

Actually I tried to use the 

LIS3DSH but no getting value.Maybe interested cpol and cpha now I have come home,I will look it and try.

Zek_De
Senior
Posted on October 31, 2017 at 13:57

Again no value ,Ok I am sending some code maybe you can understand my mistake.

if(HAL_SPI_GetState(hspi) == HAL_SPI_STATE_READY )

{

a = BW_RATE;

b = 0x0D;

HAL_GPIO_WritePin(ADXL345_CS_GPIO_Port,ADXL345_CS_Pin, GPIO_PIN_RESET);

HAL_SPI_Transmit(hspi,&a,1,100);//800Hz ODR , Normal mode

HAL_SPI_Transmit(hspi,&b,1,100);

HAL_GPIO_WritePin(ADXL345_CS_GPIO_Port,ADXL345_CS_Pin, GPIO_PIN_SET);

a = POWER_CTL;

b = 0x08;

HAL_GPIO_WritePin(ADXL345_CS_GPIO_Port,ADXL345_CS_Pin, GPIO_PIN_RESET);

HAL_SPI_Transmit(hspi,&a,1,100);////Measurement mode

HAL_SPI_Transmit(hspi,&b,1,100);

HAL_GPIO_WritePin(ADXL345_CS_GPIO_Port,ADXL345_CS_Pin, GPIO_PIN_SET);

}

else

above codes are to set.

below codes are to get values

do

{

adress = INT_SOURCE | 0x80;

HAL_GPIO_WritePin(ADXL345_CS_GPIO_Port,ADXL345_CS_Pin, GPIO_PIN_RESET);

HAL_SPI_Transmit(hspi,&adress,1,100);

HAL_SPI_Receive(hspi,&temp,1,100);

HAL_GPIO_WritePin(ADXL345_CS_GPIO_Port,ADXL345_CS_Pin, GPIO_PIN_SET);

}while((temp & 0x80) == 0);

moving is stucking in loop.Am I wrong in this step ' 

adress = INT_SOURCE | 0x80; '

As much as I know this is a way to get value with SPI related 0x80.

Posted on October 31, 2017 at 13:12

Ahh you're not using the same MEMS as me. I'm using the LIS3DSH. Google SPI modes, and have a look what mode matches your ADXL datasheet and set your CPOL and CPHA accordingly.

Also as you are using a different ic, you will probably have different register addresses.

Zek_De
Senior
Posted on October 31, 2017 at 22:13

#define DATA_FORMAT (uint8_t)0x31 

#define BW_RATE (uint8_t)0x2C

#define POWER_CTL (uint8_t)0x2D

#define FIFO_CTL (uint8_t)0x38

#define DATAXL (uint8_t)0x32

#define DATAXH (uint8_t)0x33

#define DATAYL (uint8_t)0x34

#define DATAYH (uint8_t)0x35

#define DATAZL (uint8_t)0x36

#define DATAZH (uint8_t)0x37

#define OFSX (uint8_t)0x1E

#define OFSY (uint8_t)0x1F

#define OFSZ (uint8_t)0x20

#define INT_ENABLE (uint8_t)0x2E 

#define INT_SOURCE (uint8_t)0x30
Zek_De
Senior
Posted on October 31, 2017 at 22:15

0690X00000604BCQAY.jpg
Zek_De
Senior
Posted on October 31, 2017 at 22:18

I am using STM32f4 discovery board,actually .SPI is working I controlled with Osciloscope also NRF24L01 is working and I2C is working same ADXL345 I mean device is strong.Also my new codes are here.

void ADXL345_Setup(SPI_HandleTypeDef *hspi)

{

if(HAL_SPI_GetState(hspi) == HAL_SPI_STATE_READY )

{

ADXL345_Write_Single(hspi,BW_RATE,0x0D);

ADXL345_Write_Single(hspi,POWER_CTL,0x08);

//ADXL345_Write_Single(hspi,DATA_FORMAT,0x04);

}

else

{

while(1)

{

}

}

}

//##################################################################################

void ADXL345_Raw_Values(SPI_HandleTypeDef *hspi,int16_t *AccRaw)

{

uint8_t out[6]={0},temp=0;

do

{

temp = ADXL345_Read_Single(hspi,INT_SOURCE);

}while((temp & 0x80) == 0);

ADXL345_Read_Multi(hspi,DATAXL,out,6);

AccRaw[x_eksen] = (int16_t)(((uint16_t)out[1]<<8) | out[0]);

AccRaw[y_eksen] = (int16_t)(((uint16_t)out[3]<<8) | out[2]);

AccRaw[z_eksen] = (int16_t)(((uint16_t)out[5]<<8) | out[4]);

}

//##################################################################################

void ADXL345_Write_Single(SPI_HandleTypeDef *hspi, uint8_t reg, uint8_t data)

{

CS_LOW;

HAL_SPI_Transmit(hspi,&reg,1,100);

HAL_SPI_Transmit(hspi,&data,1,100);

CS_HIGH;

}

//##################################################################################

//##################################################################################

uint8_t ADXL345_Read_Single(SPI_HandleTypeDef *hspi, uint8_t reg)

{

reg |= 0x80; // Okuma biti etkin //

uint8_t out;

CS_LOW;

HAL_SPI_Transmit(hspi,&reg,1,100);

HAL_SPI_Receive(hspi,&out,1,100);

//HAL_SPI_TransmitReceive(hspi, &adr, &out, 1, 200);

CS_HIGH;

return out;

}

//##################################################################################

//##################################################################################

void ADXL345_Read_Multi(SPI_HandleTypeDef *hspi, uint8_t reg,uint8_t *out, uint8_t NumberOfByte)

{

reg |= 0xC0; // Okuma ve çoklu okuma bitleri etkin.0b1100-0000 //

CS_LOW;

HAL_SPI_TransmitReceive(hspi,&reg,out,NumberOfByte,100);

CS_HIGH;

}

//##################################################################################

//##################################################################################
Zek_De
Senior
Posted on October 31, 2017 at 22:19

I am trying 2 days this.

Zek_De
Senior
Posted on October 31, 2017 at 22:44

I didnt manage to understand rhat you mean,sorry my late reply