Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: mbed
ACCELEROMETER.cpp
- Committer:
 - subinmbed
 - Date:
 - 2017-09-02
 - Revision:
 - 2:c4fb968de7d3
 
File content as of revision 2:c4fb968de7d3:
#include "mbed.h"
#include "ACCELEROMETER.h"
#include "OBD.h"
#include "main.h"
#define     acc_address             0x32      
int i=0,j=0,Steady_cnt=0;
char src_data[1],FIRST=1,SECOND,MOVING_FLAG=0,TIMER_RUNNING;
unsigned int int1_src_data,cnt=0;
char acc_reg[1] = {0x29};
char acc_data[6];
//char int1_dur[2] = {0x33, 0x70};
long speed,FIRST_SPEED=0,CURRENT_SPEED=0;
Timer t;
void configure_accelerometer()
{
/*   
    char ctrl_reg_0[2]      = {0x1E, 0x10};             // SA0 Internal pullup Enabled
    char ctrl_reg_1[2]      = {0x20, 0x2F};             // ODR -> 10Hz, X,Y,Z axis Enabled
    char ctrl_reg_2[2]      = {0x21, 0x8E};             // High pass filter enabled for CLICK function, cutoff : 0.2Hz, High pass filter AOI function is routed to INT2 pin
    char ctrl_reg_3[2]      = {0x22, 0x40};             // (Default value of this register is 0x00, so eliminate this statement later)...Disable CLICK, IA, ZYXDA, WTM, OVERRUN interrupts on INT1 pin..... 
    char ctrl_reg_4[2]      = {0x23, 0x80};             // BDU enabled, 2g full scale selection, Self test diabled
    char ctrl_reg_5[2]      = {0x24, 0x40};             // Reboot memory content disabled, FIFO enabled, Interrupt request not latched on INT1 & INT2, 4D detection disbaled
    char ctrl_reg_6[2]      = {0x25, 0xA0};             // CLICK Interrupt on INT2 pin, INT1 function on INT2 pin disabled, INT2 function on INt2 pin enabled, BOOT on INT2 pi disabled, Activity on INT2 pin disabled, INT1 & INT2 pin polarity is set to active HIGH
    char fifo_ctrl_reg[2]   = {0x2E, 0x80};             // STREAM Mode selected, Trigger event allows triggerring signal on INT1, WATER MARK LEVEL set to 0 (default value)                  
    char int1_cfg[2]        = {0x30, 0x1F};             // OR combination of interrupts, Interrupts enabled for all X/Y/Z high and low except Z-high event
    char int1_ths[2]        = {0x32, 7};                // For 2g Full scale, 1LSB = 16mg, Aim : Threshold : 100mg, 100/16 = 6.25, rounded to '7'
    char int1_dur[2]        = {0x33, (50 & 127)};       // Configured for 5sec : Duration time = N / ODR ; N = time * ODR = 5 * 10 = '50'   (Value should not exceed 127)        
    
    i2c.write(acc_address, ctrl_reg_0, 2);
    i2c.write(acc_address, ctrl_reg_1, 2);
    i2c.write(acc_address, ctrl_reg_2, 2);
    i2c.write(acc_address, ctrl_reg_3, 2);
    i2c.write(acc_address, ctrl_reg_4, 2);
    i2c.write(acc_address, ctrl_reg_5, 2);
    i2c.write(acc_address, ctrl_reg_6, 2);
    i2c.write(acc_address, fifo_ctrl_reg, 2);
    i2c.write(acc_address, int1_cfg, 2);
    i2c.write(acc_address, int1_ths, 2);
    i2c.write(acc_address, int1_dur, 2);  
    
    char ver_data[1];
    i2c.write(acc_address, ctrl_reg_1, 1);
    i2c.read(acc_address, ver_data, 1);
    pc.printf("\r\n\r\n Verification data : ");
    print_data_bits(ver_data[0]);
*/
    char ctrl_reg_0[2]      = {0x1E, 0x10};         //added additionally this line
    char ctrl_reg_1[2]      = {0x20, 0x21};         //[ODR3 ODR2 ODR1 ODR0 nop Zen Yen Xen]////data rate=10hz(T=100MS)and x enabled
    char ctrl_reg_2[2]      = {0x21, 0x03};         //HIGH PASS FILTER  Autoreset on interrupt event BUT NOT ENABLED FOR ANY FUNCTION
    char ctrl_reg_3[2]      = {0x22, 0x40};         //INT1 on INT1, CLK_INT DISABLED 
    char ctrl_reg_4[2]      = {0x23, 0x80};         //block update ENABLED #NOT NEED FOR OUR APPLICATION
    char ctrl_reg_5[2]      = {0x24, 0x04};         //4D ENABLED AND IT ACTS WITH 6D ENABLING IN OTHER REGISTER 
    char ctrl_reg_6[2]      = {0x25, 0x20};         // INT2 Interrupt on INT2 pin /clk INT2 & activity INT DISABLED..FOR CLICK=0XA0 
        
    char int1_cfg[2]        = {0x30, 0x43};         // 6D direction motion detection enabled ,XH & XL enabled
    char int1_ths[2]        = {0x32, 0x01};         //INT1 threshold value  
    char int1_dur[2]        = {0x33, 0x03};         //INT1 DURATION(GIVEN VALUE *100MS) value 
    
    char int2_cfg[2]        = {0x34, 0xFF};         //6D direction position detection enabled for XYZ high OR low
    char int2_ths[2]        = {0x36, 0x01};         //INT2 threshold value 
    char int2_dur[2]        = {0x37, 0x02};         //INT2 DURATION(GIVEN VALUE *100MS) value 
    
    char act_ths[2]         = {0x3E, 0x00};         //#not used .sleep_to_wake up threshold
    char act_dur[2]         = {0x3F, 0x00};         //#not used.sleep_to_wake up duration
    
//  char clk_cfg[2]         = {0x38, 0x15};          //enable XYZ single clicks
//  char clk_src[2]         = {0x39, 0x5F};          //Enable single click
//  char clk_ths[2]         = {0x3A, 0x01};          //click threshold
//  char clk_Tlimit[2]      = {0x3B, 0x03};          //max time for a tap to abv ths
//  char clk_Tlatncy[2]     = {0x3C, 0x0};           //time delay to start timr for waiting  scnd  tap
//  char clk_Twindow[2]     = {0x3D, 0x0};           //max time for timer to wait for scnd
    
    //32 33 30
    //36 37 34
    i2c.write(acc_address, ctrl_reg_0, 2); 
    i2c.write(acc_address, ctrl_reg_1, 2);
    i2c.write(acc_address, ctrl_reg_2, 2);
    i2c.write(acc_address, ctrl_reg_3, 2);
    i2c.write(acc_address, ctrl_reg_4, 2);
    i2c.write(acc_address, ctrl_reg_5, 2);
    i2c.write(acc_address, ctrl_reg_6, 2);
 
    i2c.write(acc_address, int1_cfg, 2);   
    i2c.write(acc_address, int1_ths, 2);
    i2c.write(acc_address, int1_dur, 2);
    i2c.write(acc_address, int2_ths, 2);
    i2c.write(acc_address, int2_dur, 2);
    i2c.write(acc_address, int2_cfg, 2);
    i2c.write(acc_address, act_ths, 2);
    i2c.write(acc_address, act_dur, 2);
    i2c.write(acc_address, int1_dur, 2);
    
//   i2c.write(acc_address, clk_cfg, 2);
//   i2c.write(acc_address, clk_src, 2);
//   i2c.write(acc_address, clk_ths, 2);
//   i2c.write(acc_address, clk_Tlimit, 2);
//   i2c.write(acc_address, clk_Tlatncy, 2);
//   i2c.write(acc_address, clk_Twindow, 2);
}
//////////////////////////////////////////////////////////////////
char initialize_accelerometer()
{   
    i2c.frequency(100000);
    char dev_id_address[2] = {0x0F};
    char dev_id[1];
    //SA0 = 0;            // I2C LSB Address
    i2c.write(acc_address, dev_id_address, 1);
    wait(0.1);
    i2c.read(acc_address, dev_id, 1);
    wait(2);
    pc.printf("\r\n\r\nDEVICE ID : ");
    print_data_bits(dev_id[0]);
    if(dev_id[0] == 0x33)//00110011(who am i)
    {
        pc.printf("\r\nAccelerometer Initialized Successfully");
        return 1;
    }
    else
    {
        pc.printf("\r\nAccelerometer Initialization Failed..... Can't communicate with the device");
        return 0; 
    }      
}
////////////////////////////////////////////////////////////////////////////////
void initialise_configure_accelerometer()//CALLED BY PARENT FUNCTION
{
    char retry_attempt = 0;
    retry:  
    if(initialize_accelerometer())
    {
        configure_accelerometer();
    }
    else
    {
        if(retry_attempt < 100)          //it will try 100 times to initialise accelerometer in case prev attempts are failed
        {
            retry_attempt++;
            goto retry;
        }
    }
    
}
////////////////////////////////////////////////////////////////////
void print_data_bits(char data_fetched) //# now not using
{
    unsigned int shifter;
    
        for(shifter = 0; shifter < 8; shifter++)
        {
            pc.printf("%d",((data_fetched&0x80)>>7));
            data_fetched = data_fetched << 1;
        }
        pc.printf("\r\n");       
}
/////////////////////////////////////////////////////////////////////////////
void process_accelerometer()
{
//  if(MOVEMENT_FLAG)
//    {   
//        MOVEMENT_FLAG=0;
//        TIMING=t.read();
//    }
    
// if(MOTION)
    {
///////////////////////////////////////////////////////////if in motion no interrupt comes
//       if(FIRST)
//       {         
//           t.reset();
//           t.start();
//           FIRST=0;
//           FIRST_TIME=t.read();
//           FIRST_SPEED=fetch_vehicle_speed();
//       }
/////////////////////////////////////////////////////////
        {
            CURRENT_TIME=t.read();
            
            CURRENT_SPEED=fetch_vehicle_speed();
            pc.printf("\nspeed=%ld",CURRENT_SPEED);
            if((CURRENT_SPEED)>1)
                {
                    pc.printf("START_TO_MOVING....");
                    ACC_LED=1;
                    MOVING_FLAG=1;
                    START_TO_MOVING=1;
                    MOVING_TO_STOP=0;
                    PRE_MOVING=1;
                    TIMER_RUNNING=1;               //# not needed incase of if in motion no interrupt comes,it will enable reading current time in main
                    jerk_disable();                // jerk is disabled by disabling stm32 interrupt
                }
              if((CURRENT_SPEED<2)&&(MOVING_FLAG==1))//when speed reach from higher value to 1/0 #can edit according to real speed behavior
                {
                    pc.printf("MOVING_TO_STOP....");
                    MOVING_FLAG=0;
                    MOVING_TO_STOP=1;
                    START_TO_MOVING=0;
                    ACC_LED=0;
                    jerk_enable();                 // jerk is enabled by enabling stm32 interrupt again
                    TIMER_RUNNING=0;
                    t.stop();                      //# not needed incase of if in motion no interrupt comes, it will stop timer when stop detected during time interval
                } 
               else                    //speed is one at first itself it will not do anythimg consider as fault jerk,this we can eliminate if we set moving speed>1 and stopping at speed=0
                {   MOVING_TO_STOP=0;
                    START_TO_MOVING=0;
                    ACC_LED=0;
                    TIMER_RUNNING=0;
                    t.stop();
                }
        }
    }
}
/////////////////////////////////////////////////////////////////
void stopped()
{
    START_TO_MOVING=0;
    MOVING_TO_STOP=1;
    ACC_LED=0;
    PRE_MOVING=0;
    pc.printf("STOPPED");
    jerk_enable();
    TIMER_RUNNING=0;
}
////////////////////////////////////////////////////////////////
void jerk_threshold(char jt)   //#editing via this function is not working,inorder to edit threshold we have to change in configuration function
{
    char int2_cfg[2]        = {0x34, 0xFF};         //INT2 is disabled for XYZ HIE/LIE
    char int2_ths[2]        = {0x36, 0x09};         //changed from 2 more threshold
    char int2_dur[2]        = {0x37, 0x02};
    i2c.write(acc_address, int2_ths, 2);
    i2c.write(acc_address, int2_dur, 2);
    i2c.write(acc_address, int2_cfg, 2);
   
}
void jerk_duration(char jd)//#editing via this function is not working,inorder to edit threshold we have to change in configuration function
{
   char int2_dur[1] = {jd};
    i2c.write(acc_address, int2_dur, 2);
}
void movement_threshold(char mt)//#editing via this function is not working,inorder to edit threshold we have to change in configuration function
{
     char int1_ths[1] =  {mt}; 
    i2c.write(acc_address, int1_ths, 2); 
}
void movement_duration(char md)//#editing via this function is not working,inorder to edit threshold we have to change in configuration function
{
     char int1_dur[1] = {md}; 
    i2c.write(acc_address, int1_dur,2); 
}
void jerk_enable()           //enable stm32 interrupt
{
    jerk.rise(&sudden_jerk); 
     
}
void jerk_disable()          //enable stm32 interrupt
{
     jerk.rise(NULL);
     JERK_FLAG=0;   
}
void movement_enable()       //enable stm32 interrupt
{
    change.rise(&movement_inertia);
}
void movement_disable()       //enable stm32 interrupt
{
    change.rise(NULL);
}