BME280 library

Dependents:   mbed_BME280

Committer:
yasuyuki
Date:
Mon Nov 23 07:50:28 2015 +0000
Revision:
0:b32d0acc420d
Child:
1:0054d4a28927
release

Who changed what in which revision?

UserRevisionLine numberNew contents of line
yasuyuki 0:b32d0acc420d 1 //**********************
yasuyuki 0:b32d0acc420d 2 // BME280.cpp for mbed
yasuyuki 0:b32d0acc420d 3 //
yasuyuki 0:b32d0acc420d 4 // BME280 bme280(P0_5,P0_4);
yasuyuki 0:b32d0acc420d 5 // or
yasuyuki 0:b32d0acc420d 6 // I2C i2c(P0_5,P0_4);
yasuyuki 0:b32d0acc420d 7 // BME280 bme280(i2c);
yasuyuki 0:b32d0acc420d 8 //
yasuyuki 0:b32d0acc420d 9 // (C)Copyright 2015 All rights reserved by Y.Onodera
yasuyuki 0:b32d0acc420d 10 // http://einstlab.web.fc2.com
yasuyuki 0:b32d0acc420d 11 //**********************
yasuyuki 0:b32d0acc420d 12
yasuyuki 0:b32d0acc420d 13 #include "mbed.h"
yasuyuki 0:b32d0acc420d 14 #include "BME280.h"
yasuyuki 0:b32d0acc420d 15
yasuyuki 0:b32d0acc420d 16 BME280::BME280 (PinName sda, PinName scl) : _i2c(sda, scl) {
yasuyuki 0:b32d0acc420d 17 init();
yasuyuki 0:b32d0acc420d 18 }
yasuyuki 0:b32d0acc420d 19 BME280::BME280 (I2C& p_i2c) : _i2c(p_i2c) {
yasuyuki 0:b32d0acc420d 20 init();
yasuyuki 0:b32d0acc420d 21 }
yasuyuki 0:b32d0acc420d 22
yasuyuki 0:b32d0acc420d 23
yasuyuki 0:b32d0acc420d 24 unsigned char BME280::get(unsigned char a)
yasuyuki 0:b32d0acc420d 25 {
yasuyuki 0:b32d0acc420d 26
yasuyuki 0:b32d0acc420d 27 buf[0] = a; // register
yasuyuki 0:b32d0acc420d 28 _i2c.write(BME280_ADDR, buf, 1); // with stop
yasuyuki 0:b32d0acc420d 29 // get data
yasuyuki 0:b32d0acc420d 30 _i2c.read( BME280_ADDR, buf, 1);
yasuyuki 0:b32d0acc420d 31 return buf[0];
yasuyuki 0:b32d0acc420d 32
yasuyuki 0:b32d0acc420d 33 }
yasuyuki 0:b32d0acc420d 34
yasuyuki 0:b32d0acc420d 35 void BME280::set(unsigned char a, unsigned char b)
yasuyuki 0:b32d0acc420d 36 {
yasuyuki 0:b32d0acc420d 37
yasuyuki 0:b32d0acc420d 38 buf[0] = a; // register
yasuyuki 0:b32d0acc420d 39 buf[1] = b;
yasuyuki 0:b32d0acc420d 40 _i2c.write(BME280_ADDR, buf, 2); // with stop
yasuyuki 0:b32d0acc420d 41
yasuyuki 0:b32d0acc420d 42 }
yasuyuki 0:b32d0acc420d 43
yasuyuki 0:b32d0acc420d 44
yasuyuki 0:b32d0acc420d 45 void BME280::getALL()
yasuyuki 0:b32d0acc420d 46 {
yasuyuki 0:b32d0acc420d 47 // set ctrl_meas : forced mode
yasuyuki 0:b32d0acc420d 48 set(ctrl_meas, 0x25);
yasuyuki 0:b32d0acc420d 49
yasuyuki 0:b32d0acc420d 50 // wait status
yasuyuki 0:b32d0acc420d 51 if(get(status) != 0)wait_ms(1);
yasuyuki 0:b32d0acc420d 52
yasuyuki 0:b32d0acc420d 53 // get temp
yasuyuki 0:b32d0acc420d 54 temp.XLSB = get(temp_xlsb);
yasuyuki 0:b32d0acc420d 55 temp.LSB = get(temp_lsb);
yasuyuki 0:b32d0acc420d 56 temp.MSB = get(temp_msb);
yasuyuki 0:b32d0acc420d 57 temp.dummy = 0;
yasuyuki 0:b32d0acc420d 58
yasuyuki 0:b32d0acc420d 59 // get press
yasuyuki 0:b32d0acc420d 60 press.XLSB = get(press_xlsb);
yasuyuki 0:b32d0acc420d 61 press.LSB = get(press_lsb);
yasuyuki 0:b32d0acc420d 62 press.MSB = get(press_msb);
yasuyuki 0:b32d0acc420d 63 press.dummy = 0;
yasuyuki 0:b32d0acc420d 64
yasuyuki 0:b32d0acc420d 65 // get hum
yasuyuki 0:b32d0acc420d 66 hum.LSB = get(hum_lsb);
yasuyuki 0:b32d0acc420d 67 hum.MSB = get(hum_msb);
yasuyuki 0:b32d0acc420d 68
yasuyuki 0:b32d0acc420d 69
yasuyuki 0:b32d0acc420d 70 // compensation
yasuyuki 0:b32d0acc420d 71 t = BME280_compensate_T_int32(temp.s32>>12);
yasuyuki 0:b32d0acc420d 72 p = BME280_compensate_P_int64(press.s32>>12);
yasuyuki 0:b32d0acc420d 73 h = BME280_compensate_H_int32((signed int)hum.u16);
yasuyuki 0:b32d0acc420d 74 }
yasuyuki 0:b32d0acc420d 75
yasuyuki 0:b32d0acc420d 76 unsigned int BME280::humidity()
yasuyuki 0:b32d0acc420d 77 {
yasuyuki 0:b32d0acc420d 78
yasuyuki 0:b32d0acc420d 79 // get hum
yasuyuki 0:b32d0acc420d 80 getALL();
yasuyuki 0:b32d0acc420d 81 return h;
yasuyuki 0:b32d0acc420d 82
yasuyuki 0:b32d0acc420d 83 }
yasuyuki 0:b32d0acc420d 84
yasuyuki 0:b32d0acc420d 85 signed int BME280::temperature()
yasuyuki 0:b32d0acc420d 86 {
yasuyuki 0:b32d0acc420d 87
yasuyuki 0:b32d0acc420d 88 // get temp
yasuyuki 0:b32d0acc420d 89 getALL();
yasuyuki 0:b32d0acc420d 90 return t;
yasuyuki 0:b32d0acc420d 91
yasuyuki 0:b32d0acc420d 92 }
yasuyuki 0:b32d0acc420d 93
yasuyuki 0:b32d0acc420d 94 unsigned int BME280::pressure()
yasuyuki 0:b32d0acc420d 95 {
yasuyuki 0:b32d0acc420d 96
yasuyuki 0:b32d0acc420d 97 // get hum
yasuyuki 0:b32d0acc420d 98 getALL();
yasuyuki 0:b32d0acc420d 99 return p;
yasuyuki 0:b32d0acc420d 100
yasuyuki 0:b32d0acc420d 101 }
yasuyuki 0:b32d0acc420d 102
yasuyuki 0:b32d0acc420d 103 void BME280::init()
yasuyuki 0:b32d0acc420d 104 {
yasuyuki 0:b32d0acc420d 105
yasuyuki 0:b32d0acc420d 106 // get calibrations
yasuyuki 0:b32d0acc420d 107 calib.LSB = get(calib00);
yasuyuki 0:b32d0acc420d 108 calib.MSB = get(calib01);
yasuyuki 0:b32d0acc420d 109 dig_T1 = calib.u16;
yasuyuki 0:b32d0acc420d 110 calib.LSB = get(calib02);
yasuyuki 0:b32d0acc420d 111 calib.MSB = get(calib03);
yasuyuki 0:b32d0acc420d 112 dig_T2 = calib.s16;
yasuyuki 0:b32d0acc420d 113 calib.LSB = get(calib04);
yasuyuki 0:b32d0acc420d 114 calib.MSB = get(calib05);
yasuyuki 0:b32d0acc420d 115 dig_T3 = calib.s16;
yasuyuki 0:b32d0acc420d 116 calib.LSB = get(calib06);
yasuyuki 0:b32d0acc420d 117 calib.MSB = get(calib07);
yasuyuki 0:b32d0acc420d 118 dig_P1 = calib.u16;
yasuyuki 0:b32d0acc420d 119 calib.LSB = get(calib08);
yasuyuki 0:b32d0acc420d 120 calib.MSB = get(calib09);
yasuyuki 0:b32d0acc420d 121 dig_P2 = calib.s16;
yasuyuki 0:b32d0acc420d 122 calib.LSB = get(calib10);
yasuyuki 0:b32d0acc420d 123 calib.MSB = get(calib11);
yasuyuki 0:b32d0acc420d 124 dig_P3 = calib.s16;
yasuyuki 0:b32d0acc420d 125 calib.LSB = get(calib12);
yasuyuki 0:b32d0acc420d 126 calib.MSB = get(calib13);
yasuyuki 0:b32d0acc420d 127 dig_P4 = calib.s16;
yasuyuki 0:b32d0acc420d 128 calib.LSB = get(calib14);
yasuyuki 0:b32d0acc420d 129 calib.MSB = get(calib15);
yasuyuki 0:b32d0acc420d 130 dig_P5 = calib.s16;
yasuyuki 0:b32d0acc420d 131 calib.LSB = get(calib16);
yasuyuki 0:b32d0acc420d 132 calib.MSB = get(calib17);
yasuyuki 0:b32d0acc420d 133 dig_P6 = calib.s16;
yasuyuki 0:b32d0acc420d 134 calib.LSB = get(calib18);
yasuyuki 0:b32d0acc420d 135 calib.MSB = get(calib19);
yasuyuki 0:b32d0acc420d 136 dig_P7 = calib.s16;
yasuyuki 0:b32d0acc420d 137 calib.LSB = get(calib20);
yasuyuki 0:b32d0acc420d 138 calib.MSB = get(calib21);
yasuyuki 0:b32d0acc420d 139 dig_P8 = calib.s16;
yasuyuki 0:b32d0acc420d 140 calib.LSB = get(calib22);
yasuyuki 0:b32d0acc420d 141 calib.MSB = get(calib23);
yasuyuki 0:b32d0acc420d 142 dig_P9 = calib.s16;
yasuyuki 0:b32d0acc420d 143 dig_H1 = get(calib25);
yasuyuki 0:b32d0acc420d 144 calib.LSB = get(calib26);
yasuyuki 0:b32d0acc420d 145 calib.MSB = get(calib27);
yasuyuki 0:b32d0acc420d 146 dig_H2 = calib.s16;
yasuyuki 0:b32d0acc420d 147 dig_H3 = get(calib28);
yasuyuki 0:b32d0acc420d 148 calib.MSB = get(calib29);
yasuyuki 0:b32d0acc420d 149 calib.LSB = get(calib30) << 4;
yasuyuki 0:b32d0acc420d 150 dig_H4 = calib.s16>>4;
yasuyuki 0:b32d0acc420d 151 calib.LSB = get(calib30);
yasuyuki 0:b32d0acc420d 152 calib.MSB = get(calib31);
yasuyuki 0:b32d0acc420d 153 dig_H5 = calib.s16>>4;
yasuyuki 0:b32d0acc420d 154 dig_H6 = get(calib32);
yasuyuki 0:b32d0acc420d 155
yasuyuki 0:b32d0acc420d 156 // Set configuration
yasuyuki 0:b32d0acc420d 157 set(config, 0x00);
yasuyuki 0:b32d0acc420d 158 set(ctrl_hum, 0x01);
yasuyuki 0:b32d0acc420d 159
yasuyuki 0:b32d0acc420d 160 }
yasuyuki 0:b32d0acc420d 161
yasuyuki 0:b32d0acc420d 162 // Returns temperature in DegC, resolution is 0.01 DegC. Output value of "5123" equals 51.23 DegC.
yasuyuki 0:b32d0acc420d 163 // t_fine carries fine temperature as global value
yasuyuki 0:b32d0acc420d 164 BME280_S32_t BME280::BME280_compensate_T_int32(BME280_S32_t adc_T)
yasuyuki 0:b32d0acc420d 165 {
yasuyuki 0:b32d0acc420d 166 BME280_S32_t var1, var2, T;
yasuyuki 0:b32d0acc420d 167 var1 = ((((adc_T>>3) - ((BME280_S32_t)dig_T1<<1))) * ((BME280_S32_t)dig_T2)) >> 11;
yasuyuki 0:b32d0acc420d 168 var2 = (((((adc_T>>4) - ((BME280_S32_t)dig_T1)) * ((adc_T>>4) - ((BME280_S32_t)dig_T1))) >> 12) *
yasuyuki 0:b32d0acc420d 169 ((BME280_S32_t)dig_T3)) >> 14;
yasuyuki 0:b32d0acc420d 170 t_fine = var1 + var2;
yasuyuki 0:b32d0acc420d 171 T = (t_fine * 5 + 128) >> 8;
yasuyuki 0:b32d0acc420d 172 return T;
yasuyuki 0:b32d0acc420d 173 }
yasuyuki 0:b32d0acc420d 174
yasuyuki 0:b32d0acc420d 175 // Returns pressure in Pa as unsigned 32 bit integer in Q24.8 format (24 integer bits and 8 fractional bits).
yasuyuki 0:b32d0acc420d 176 // Output value of "24674867" represents 24674867/256 = 96386.2 Pa = 963.862 hPa
yasuyuki 0:b32d0acc420d 177 BME280_U32_t BME280::BME280_compensate_P_int64(BME280_S32_t adc_P)
yasuyuki 0:b32d0acc420d 178 {
yasuyuki 0:b32d0acc420d 179 BME280_S64_t var1, var2, p;
yasuyuki 0:b32d0acc420d 180 var1 = ((BME280_S64_t)t_fine) - 128000;
yasuyuki 0:b32d0acc420d 181 var2 = var1 * var1 * (BME280_S64_t)dig_P6;
yasuyuki 0:b32d0acc420d 182 var2 = var2 + ((var1*(BME280_S64_t)dig_P5)<<17);
yasuyuki 0:b32d0acc420d 183 var2 = var2 + (((BME280_S64_t)dig_P4)<<35);
yasuyuki 0:b32d0acc420d 184 var1 = ((var1 * var1 * (BME280_S64_t)dig_P3)>>8) + ((var1 * (BME280_S64_t)dig_P2)<<12);
yasuyuki 0:b32d0acc420d 185 var1 = (((((BME280_S64_t)1)<<47)+var1))*((BME280_S64_t)dig_P1)>>33;
yasuyuki 0:b32d0acc420d 186 if (var1 == 0)
yasuyuki 0:b32d0acc420d 187 {
yasuyuki 0:b32d0acc420d 188 return 0; // avoid exception caused by division by zero
yasuyuki 0:b32d0acc420d 189 }
yasuyuki 0:b32d0acc420d 190 p = 1048576-adc_P;
yasuyuki 0:b32d0acc420d 191 p = (((p<<31)-var2)*3125)/var1;
yasuyuki 0:b32d0acc420d 192 var1 = (((BME280_S64_t)dig_P9) * (p>>13) * (p>>13)) >> 25;
yasuyuki 0:b32d0acc420d 193 var2 = (((BME280_S64_t)dig_P8) * p) >> 19;
yasuyuki 0:b32d0acc420d 194 p = ((p + var1 + var2) >> 8) + (((BME280_S64_t)dig_P7)<<4);
yasuyuki 0:b32d0acc420d 195 return (BME280_U32_t)p;
yasuyuki 0:b32d0acc420d 196 }
yasuyuki 0:b32d0acc420d 197
yasuyuki 0:b32d0acc420d 198 // Returns humidity in %RH as unsigned 32 bit integer in Q22.10 format (22 integer and 10 fractional bits).
yasuyuki 0:b32d0acc420d 199 // Output value of "47445" represents 47445/1024 = 46.333 %RH
yasuyuki 0:b32d0acc420d 200 BME280_U32_t BME280::BME280_compensate_H_int32(BME280_S32_t adc_H)
yasuyuki 0:b32d0acc420d 201 {
yasuyuki 0:b32d0acc420d 202 BME280_S32_t v_x1_u32r;
yasuyuki 0:b32d0acc420d 203 v_x1_u32r = (t_fine - ((BME280_S32_t)76800));
yasuyuki 0:b32d0acc420d 204 v_x1_u32r = (((((adc_H << 14) - (((BME280_S32_t)dig_H4) << 20) - (((BME280_S32_t)dig_H5) * v_x1_u32r)) +
yasuyuki 0:b32d0acc420d 205 ((BME280_S32_t)16384)) >> 15) * (((((((v_x1_u32r * ((BME280_S32_t)dig_H6)) >> 10) * (((v_x1_u32r *
yasuyuki 0:b32d0acc420d 206 ((BME280_S32_t)dig_H3)) >> 11) + ((BME280_S32_t)32768))) >> 10) + ((BME280_S32_t)2097152)) *
yasuyuki 0:b32d0acc420d 207 ((BME280_S32_t)dig_H2) + 8192) >> 14));
yasuyuki 0:b32d0acc420d 208 v_x1_u32r = (v_x1_u32r - (((((v_x1_u32r >> 15) * (v_x1_u32r >> 15)) >> 7) * ((BME280_S32_t)dig_H1)) >> 4));
yasuyuki 0:b32d0acc420d 209 v_x1_u32r = (v_x1_u32r < 0 ? 0 : v_x1_u32r);
yasuyuki 0:b32d0acc420d 210 v_x1_u32r = (v_x1_u32r > 419430400 ? 419430400 : v_x1_u32r);
yasuyuki 0:b32d0acc420d 211 return (BME280_U32_t)(v_x1_u32r>>12);
yasuyuki 0:b32d0acc420d 212 }
yasuyuki 0:b32d0acc420d 213