Interfacing ADXL375 problem

Discussion in 'Embedded Systems and Microcontrollers' started by Vindhyachal Takniki, Dec 27, 2014.

  1. Vindhyachal Takniki

    Thread Starter Member

    Nov 3, 2014
    348
    6
    I have interfaced ADXL375 & I have some below. I have attached the code.

    1. The offset I am getting is huge.
    It is 1g approx on both x & y axis & 1.5g on z-axis.
    I don't know what could be problem. I read offset registers , they are all zero in ADXL375.
    I had read thread on Analog forum, someone gad same problem with offset +4G on z axis.
    He had removed the IC & resoldered new one & problem gone.
    But I wan't to know what could be exact reason?

    2. For ODR <= 800Hz, we multiply register value with 49 to get g value i.e:
    g = (register_value * 49)

    But when OCR = 1600 or 3200Hz, what is the factor.
    I had red in datasheet that in this case LSB is always zero. So what will be coversion factor or it will remain same = 49.


    3. I had calibrated the adxl375 by placing it in z = +1g & other axis = 0.
    But I have seen example in which calibrate in all six axis is done:
    https://learn.adafruit.com/adxl345-digital-accelerometer/programming

    But how to calculate final offset from these six offset values?
    Or should I take there average.

    4. Edit: I have been able to read DEV id properly & SPi speed is 3.75Mhz.

    Code (Text):
    1.  
    2. #define ADXL_REG_DEV_ID          (0x00)
    3. #define ADXL_VAL_DEV_ID          (0xe5)
    4. #define ADXL_REG_PW_CTRL         (0x2d)
    5. #define ADXL_REG_INT_EN          (0x2e)
    6. #define ADXL_REG_INT_MAP          (0x2f)
    7. #define ADXL_REG_DATA_FM         (0x31)
    8. #define ADXL_REG_DATA_RATE       (0x2c)
    9. #define ADXL_REG_DATAX0          (0x32)
    10.  
    11.  
    12. void main(void)
    13. {
    14.     configure_adxl375();
    15.  
    16.     while(1)
    17.     {
    18.         //take 100 samples & average
    19.         adxl_read_offset_values(&x_val , &y_val ,&z_val);
    20.         x_val *= 49;
    21.         y_val *= 49;
    22.         z_val *= 49;
    23.    
    24.         //offset for x:1274 , y: 1225 , z:1597
    25.     }
    26.  
    27. }
    28.  
    29.  
    30.  
    31. void adxl_read_g_values(int16_t *x_val , int16_t *y_val , int16_t *z_val)
    32. {
    33.     uint8_t values[6];
    34.     uint32_t error
    35.  
    36.     adxl_read_reister(ADXL_REG_DATAX0 , 6U , &values[0]);
    37.  
    38.     *x_val = (s16_t)( ((u16_t)values[1] << 8U) | ((u16_t)values[0]) ) ;
    39.     *y_val = (s16_t)( ((u16_t)values[3] << 8U) | ((u16_t)values[2]) ) ;
    40.     *z_val = (s16_t)( ((u16_t)values[5] << 8U) | ((u16_t)values[4]) ) ;    
    41. }
    42.  
    43.  
    44.  
    45. void configure_adxl375(void)
    46. {
    47.     uint8_t data;
    48.  
    49.     SPI_MODE(3);
    50.  
    51.     data = adxl_read(ADXL_REG_DEV_ID);
    52.     if(0xe5 != data)
    53.     {
    54.         error_trap();
    55.     }
    56.  
    57. /* power ctrl */
    58.     adxl_write(ADXL_REG_PW_CTRL , 0x00);
    59.     adxl_write_register(ADXL_REG_DATA_FM , 0x0bU);
    60.     adxl_write_register(ADXL_REG_DATA_RATE , 0x0dU);
    61.     adxl_write_register(ADXL_REG_PW_CTRL , 0x08U);
    62.  
    63. }
    64.  
    65.  
    66.  
    67. void adxl_write_register(uint8_t address , uint8_t value)
    68. {
    69.     ADXL_CS_ENABLE();
    70.  
    71.     adxl_spi_byte(address);
    72.     adxl_spi_byte(value);
    73.     ADXL_CS_DISABLE();
    74.  
    75. }
    76.  
    77.  
    78.  
    79.  
    80. void adxl_read_reister(uint8_t address , uint32_t no_bytes , uint8_t *values)
    81. {
    82.     uint32_t cnt;
    83.     uint8_t reg_add = 0x80U | address;      /* msb is high fro reading */
    84.    
    85.     if(no_bytes > 1U)   /* for multi read bit 6 is also set */
    86.     {
    87.         reg_add = reg_add | 0x40U;
    88.     }
    89.  
    90.     ADXL_CS_ENABLE();
    91.  
    92. /* send address */
    93.     adxl_spi_byte(reg_add);
    94.  
    95.  
    96. /* sent bytes */    
    97.     for(cnt = 0U ; (cnt< no_bytes) ; cnt++ )
    98.     {
    99.         values[cnt] = adxl_spi_byte(0xffU);
    100.     }
    101.  
    102.     ADXL_CS_DISABLE();
    103.  
    104. }
    105.  
     
    Last edited: Dec 27, 2014
  2. Vindhyachal Takniki

    Thread Starter Member

    Nov 3, 2014
    348
    6
    1. Way I have done calibration now:
    I have take gain & offset errros into account.
    Took two readings in +x axis & -ve axis.
    Value at +x axis (1000mg) comes out to 1500mg.
    Value at -x axis(-1000mg) comes out to 789mg.

    From here I have calculated gain & offset error for x axis, by two point calibration.
    Similarly for other two axis.

    Is it correct method?

    2. Why so much error? Only thermal stress can produce so much error?

    3.
    For ODR <= 800Hz, we multiply register value with 49 to get g value i.e:
    g = (register_value * 49)
    But when OCR = 1600 or 3200Hz, what is the factor.
     
  3. Vindhyachal Takniki

    Thread Starter Member

    Nov 3, 2014
    348
    6
    1. If, ODR = 3200 then number of sampes I can take per sec is 1600 without aliasing right?

    2. What is the final g value from three axis. Is it:
    g = ( (x*x + y*y + z*z) ^ 0.5 ) / 3

    3.If I configure ODR = 3200 & not able to take sample at Data ready interrupt. Then does that mean new data will overwrite older data & 3 axis data read can be corrupted or whenever I read 3 axis data it is always reliable & current data?

    I read 3 axis data at once.
     
Loading...