Bosch Sensortec Community

    cancel
    Showing results for 
    Search instead for 
    Did you mean: 

    BMX160_SPI

    BMX160_SPI

    amar
    Established Member

    Hi everyone,

    I am trying to read BMX160's ACC and GYRO data, as part of doing this  i am able read its device id as 0xD8 and then i configured its ACC and GYRO into

    NORMAL MODEs and trying to read its raw raw data from 12 registers(0x0C-0x17). 

    Till now i am able to read GYRO data(I saw gyro data on MISO), but for ACC i am not getting any data(x,y,z) on MISO even by moving the sensor also.

    Note:- Can we read ACC raw data directly by config its reg or is it depends GYRO or MAG data also?

    Please help mje to come out this issue.

    Thanks in advance.

    Regards,

    amarr

     

    12 REPLIES 12

    Minhwan
    Community Moderator
    Community Moderator

    Hello Amar, 

     

    Here is the my answer. 

    1) If i use bmi160 with spi interface then which  interface can i use for bmm150, is it SPI or I2C? 

    -> I2C only. You can only get BMM150 mag thru BMI160 using i2c.  

    2) Can i config bmi160 and bmm150 with same SPI interface which i used for communicating with host to bmi160.

    -> Same question as Q1. Technically, yes. You can communicate SPI with BMI160, then BMI160 is going to communicate with BMM150 using I2C. 

    3) If i config bmi160 with SPI and bmm150 with I2C, then how can i read MAG data from bmm150 because two are different protocols.

    -> System hierarchy is lie this Host MCU- BMI160 - BMM150. It's okay SPI or I2C to communicate with BMI160.  BMI160 give you BMM150 mag data with your interface. But, BMI160 and BMM150 should be communicated thru I2C. 

    amar
    Established Member

    Hi Minhwan,

    Thank you very much your replay,

    Now i got an idea of it.  Actually i am using SPI for BMI160, Now i want to read MAG data from BMM150 by using I2C, i added your suggested code into my source code for BMM150. I am confusing for using BMI160 and BMM150 APIs. Can you please help to how integrate SPI and I2C APIs for reading MAG data. I am attaching code which is merged by your suggested BMM150 code.

    Thank you,

    AMARR

    Minhwan
    Community Moderator
    Community Moderator

    Hello Amar, 

     

    My example is exactly the code what you want. 

    Please check my code one more time, and I attached zip file regarding my i2c and spi function for my example code. 

    You can check my interface functions' structure. 

    coines_write_i2c

    coines_read_i2c

    coines_write_spi

    coines_read_spi

    Of course, you also can download and see coines function in detail.

    https://www.bosch-sensortec.com/software-tools/tools/coines/

    Thank you. 

    amar
    Established Member

    Hi minhwan, 

    Thank you for your replay,

    Now i am able to read PITCH, ROLL, YAW  readings. As per sensor rotation around X and Y axis respectively pitch and roll values are varying but when i rotate sensor around Z-axis the YAW readings are not varying as per rotation.

    Actually when i start rotate the sensor around Z-axis, quickly yaw value going to High or low based on direction of sensor rotation and then yaw value comming to the initial stage even sensor rotating.

    Is YAW readings are depends on MAGNETOMETER readings?

    Thank you,

    amarr

    amar
    Established Member

    Hi minhwan,

    Present  i am configured my bmx160 like below

    bmi160 primary interface ----------------------------------------------->SPI Interfce

    bmi160 aux_interface for bmm150 --------------------------------> I2C Interface

    Till now i am able to read ACC and GYRO data from bmi160. For reading MAG data from BMM150, I used your suggested code but i am unable to read

    MAG data.

    1) For reading MAG data or even BMM150 Chip_id also, Finally we get data from  SPI only because it is the bmi160 primary interface. right?

    2) Eventhough if you call  " bmm_init();"  API,  still it will use spi_read/spi_write of bmi160 driver via  aux_interface of bmi160 like below

        bmm150_init(&bmm); ---> bmm150_get_regs ----->dev->intf_rslt = dev->read(reg_addr, reg_data, len, dev->intf_ptr);  ---->bmm150_aux_read() ----                        -------->bmi160_aux_read.  right?

    3) How do we know bmi160 aux_interface working fine or not?

    4) Can i change bmi160 aux_interface to SPI from I2C?

    5) Can i read MAG data directly form bmm150(without using bmm150 driver), if yes can you please suggest me how to implement it.

    i am adding my main code snippet below. if i am approaching in wrong way so please help me to come out from it.

     

    #include "bmi160.h"
    #include "bmi160_defs.h"
    #include "bmm150_defs.h"
    #include "bmm150.h"
    #define ACC_FRAMES	10 /* 10 Frames are available every 100ms @ 100Hz */
    #define GYR_FRAMES	10
    #define MAG_FRAMES	10
    #define FIFO_SIZE	250 
    #define BUFFER_SIZE (2)
    
    struct bmi160_dev bmi; 
    struct bmm150_dev bmm;
    static uint8_t i2c_bus;
    struct bmm150_settings bmm150dev_settings;
    
    uint8_t fifo_buff[FIFO_SIZE];
    struct bmi160_fifo_frame fifo_frame;
    struct bmi160_aux_data aux_data[MAG_FRAMES];
    struct bmm150_mag_data mag_data[MAG_FRAMES];
    struct bmi160_sensor_data gyro_data[GYR_FRAMES], accel_data[ACC_FRAMES];
    
    
    int8_t spi_reg_read(uint8_t cs, uint8_t reg_addr, uint8_t *reg_data, uint16_t length);
    int8_t spi_reg_write(uint8_t cs, uint8_t reg_addr, uint8_t *reg_data, uint16_t length);
    void delay_ms_user(uint32_t period);
    
    int8_t bmm150_aux_write(uint8_t reg_addr, uint8_t *reg_data, uint32_t length, void *intf_ptr);
    int8_t bmm150_aux_read(uint8_t reg_addr, uint8_t *reg_data, uint32_t length, void *intf_ptr) ;
    void bmm150_delay_usec(uint32_t period);
    
    int main(void)
    {
       	bmi.chip_id = BMI160_CHIP_ID;
        bmi.interface = BMI160_SPI_INTF;
        bmi.read = spi_reg_read;
        bmi.write = spi_reg_write;
        bmi.delay_ms = delay_ms_user;
    			
        /* I2C setup */
        /* link read/write/delay function of host system to appropriate
         * bmi160 function call prototypes */
        i2c_bus = BMM150_DEFAULT_I2C_ADDRESS; 
    	bmm.intf_ptr = &i2c_bus;
        bmm.intf = BMM150_I2C_INTF;
        bmm.read = bmm150_aux_read;
        bmm.write = bmm150_aux_write;
        bmm.delay_us = bmm150_delay_usec;
            
    		
    		bmi160_init(&bmi);
    		
    		
    	/* Configure device structure for auxiliary sensor parameter */
    	bmi.aux_cfg.aux_i2c_addr  = BMM150_DEFAULT_I2C_ADDRESS;
    	bmi.aux_cfg.aux_sensor_enable = BMI160_ENABLE; // auxiliary sensor enable
    	bmi.aux_cfg.aux_i2c_addr = BMI160_AUX_BMM150_I2C_ADDR; // auxiliary sensor address
    	bmi.aux_cfg.manual_enable = BMI160_ENABLE; /* Manual mode */ 
    	bmi.aux_cfg.aux_rd_burst_len = BMI160_AUX_READ_LEN_3;// burst read of 8 byte
     
        bmi160_aux_init(&bmi);
    			
    	bmm150_init(&bmm);
    			
        /* Configure the accelerometer */
        bmi.accel_cfg.odr = BMI160_ACCEL_ODR_1600HZ;
        bmi.accel_cfg.range = BMI160_ACCEL_RANGE_2G;
        bmi.accel_cfg.bw = BMI160_ACCEL_BW_NORMAL_AVG4;
        bmi.accel_cfg.power = BMI160_ACCEL_NORMAL_MODE;
    
        /* Configure the gyroscope */
        bmi.gyro_cfg.odr = BMI160_GYRO_ODR_1600HZ;
        bmi.gyro_cfg.range = BMI160_GYRO_RANGE_250_DPS;
        bmi.gyro_cfg.bw = BMI160_GYRO_BW_NORMAL_MODE;
        bmi.gyro_cfg.power = BMI160_GYRO_NORMAL_MODE;
    
        rslt = bmi160_set_sens_conf(&bmi);
        /* Check rslt for any error codes */
    		
    		
        /* Configure the magnetometer. The regular preset supports up to 100Hz in Forced mode */
        bmm150dev_settings.preset_mode = BMM150_PRESETMODE_REGULAR;
        rslt = bmm150_set_presetmode(&bmm150dev_settings, &bmm);
    		
        /* Check rslt for any error codes */
        bmm150dev_settings.pwr_mode = BMM150_POWERMODE_FORCED;
        bmm150_set_op_mode(&bmm150dev_settings, &bmm);
    
        uint8_t bmm150_data_start = BMM150_REG_DATA_X_LSB;
    	
        bmi.aux_cfg.aux_odr = BMI160_AUX_ODR_100HZ;
    	
        rslt = bmi160_set_aux_auto_mode(&bmm150_data_start, &bmi);
    		
        if (rslt < 0)
        {
    			return BMI160_E_COM_FAIL;
        }
    
        fifo_frame.data = fifo_buff;
        fifo_frame.length = FIFO_SIZE;
        bmi.fifo = &fifo_frame;
    
        /* Clear all existing FIFO configurations */
        rslt = bmi160_set_fifo_config(BMI160_FIFO_CONFIG_1_MASK , BMI160_DISABLE, &bmi);
        /* Check rslt for any error codes */
    
        uint8_t fifo_config = BMI160_FIFO_HEADER | BMI160_FIFO_AUX |  BMI160_FIFO_ACCEL | BMI160_FIFO_GYRO;
        rslt = bmi160_set_fifo_config(fifo_config, BMI160_ENABLE, &bmi);		
    	
        while (times_to_read < 1000)
        {
    			
             uint8_t i; 
            bmi.fifo->length = FIFO_SIZE;
            rslt = bmi160_get_fifo_data(&bmi);
    
            uint8_t aux_inst = MAG_FRAMES, gyr_inst = GYR_FRAMES, acc_inst = ACC_FRAMES;
            rslt = bmi160_extract_aux(aux_data, &aux_inst, &bmi);
           
            for ( i = 0; i < acc_inst; i++) 
    		   {
            	rslt = bmm150_aux_mag_data(&aux_data[i].data[0], &mag_data[i], &bmm);
                printf("Mag data gx:%d gy:%d gz:%d \r\n", mag_data[i].x, mag_data[i].y, mag_data[i].z);
            }
    
    		
    		 fflush(stdout);	
            delay_ms_user(100);
            times_to_read = times_to_read + 1;
    				
    	}
    		
    }
    
    
    int8_t spi_reg_write(uint8_t cs, uint8_t reg_addr, uint8_t *reg_data, uint16_t length)
    {
    
    }
    
    
    int8_t spi_reg_read(uint8_t cs, uint8_t reg_addr, uint8_t *reg_data, uint16_t length)
    {	  
    
    }
    
    void delay_ms_user(uint32_t period)
    {
    
    
    }	
    
    /* Auxiliary function definitions */
    int8_t bmm150_aux_read(uint8_t reg_addr, uint8_t *reg_data, uint32_t length, void *intf_ptr)  
    {
        rslt = bmi160_aux_read(reg_addr, reg_data, length, &bmi);
    		
    	return rslt;
    }
    
    int8_t bmm150_aux_write(uint8_t reg_addr, uint8_t *reg_data, uint32_t length, void *intf_ptr)  
    {
        rslt =  bmi160_aux_write(reg_addr, reg_data, length, &bmi);
    
    	return rslt;
    	
    }
    
    void bmm150_delay_usec(uint32_t period)  
    {
    
    }

     

    Please give me replay.

    Thank you in advance.

    Thank you,

    amarr

     

     

     

    Icon--AD-black-48x48Icon--address-consumer-data-black-48x48Icon--appointment-black-48x48Icon--back-left-black-48x48Icon--calendar-black-48x48Icon--center-alignedIcon--Checkbox-checkIcon--clock-black-48x48Icon--close-black-48x48Icon--compare-black-48x48Icon--confirmation-black-48x48Icon--dealer-details-black-48x48Icon--delete-black-48x48Icon--delivery-black-48x48Icon--down-black-48x48Icon--download-black-48x48Ic-OverlayAlertIcon--externallink-black-48x48Icon-Filledforward-right_adjustedIcon--grid-view-black-48x48IC_gd_Check-Circle170821_Icons_Community170823_Bosch_Icons170823_Bosch_Icons170821_Icons_CommunityIC-logout170821_Icons_Community170825_Bosch_Icons170821_Icons_CommunityIC-shopping-cart2170821_Icons_CommunityIC-upIC_UserIcon--imageIcon--info-i-black-48x48Icon--left-alignedIcon--Less-minimize-black-48x48Icon-FilledIcon--List-Check-grennIcon--List-Check-blackIcon--List-Cross-blackIcon--list-view-mobile-black-48x48Icon--list-view-black-48x48Icon--More-Maximize-black-48x48Icon--my-product-black-48x48Icon--newsletter-black-48x48Icon--payment-black-48x48Icon--print-black-48x48Icon--promotion-black-48x48Icon--registration-black-48x48Icon--Reset-black-48x48Icon--right-alignedshare-circle1Icon--share-black-48x48Icon--shopping-bag-black-48x48Icon-shopping-cartIcon--start-play-black-48x48Icon--store-locator-black-48x48Ic-OverlayAlertIcon--summary-black-48x48tumblrIcon-FilledvineIc-OverlayAlertwhishlist