BME280にアクセスするためのライブラリ

Committer:
j_rocket_boy
Date:
Tue Jul 10 07:38:08 2018 +0000
Revision:
0:95f2b96cdc7f
Child:
1:0dbf59c6e564
???????; ????????; ??????????

Who changed what in which revision?

UserRevisionLine numberNew contents of line
j_rocket_boy 0:95f2b96cdc7f 1 #include "mbed.h"
j_rocket_boy 0:95f2b96cdc7f 2 #include "BME280.h"
j_rocket_boy 0:95f2b96cdc7f 3 #include "i2c_general_io.h"
j_rocket_boy 0:95f2b96cdc7f 4
j_rocket_boy 0:95f2b96cdc7f 5 BME280::BME280(PinName sda, PinName scl)
j_rocket_boy 0:95f2b96cdc7f 6 :
j_rocket_boy 0:95f2b96cdc7f 7 i2c_p(new GEN_I2C(sda, scl)),
j_rocket_boy 0:95f2b96cdc7f 8 sensor(*i2c_p)
j_rocket_boy 0:95f2b96cdc7f 9 {
j_rocket_boy 0:95f2b96cdc7f 10 init();
j_rocket_boy 0:95f2b96cdc7f 11 }
j_rocket_boy 0:95f2b96cdc7f 12
j_rocket_boy 0:95f2b96cdc7f 13 BME280::BME280(GEN_I2C &i2c_obj)
j_rocket_boy 0:95f2b96cdc7f 14 :
j_rocket_boy 0:95f2b96cdc7f 15 i2c_p(NULL),
j_rocket_boy 0:95f2b96cdc7f 16 sensor(i2c_obj)
j_rocket_boy 0:95f2b96cdc7f 17 {
j_rocket_boy 0:95f2b96cdc7f 18 init();
j_rocket_boy 0:95f2b96cdc7f 19 }
j_rocket_boy 0:95f2b96cdc7f 20
j_rocket_boy 0:95f2b96cdc7f 21 BME280::~BME280()
j_rocket_boy 0:95f2b96cdc7f 22 {
j_rocket_boy 0:95f2b96cdc7f 23 if (NULL != i2c_p)
j_rocket_boy 0:95f2b96cdc7f 24 delete i2c_p;
j_rocket_boy 0:95f2b96cdc7f 25 }
j_rocket_boy 0:95f2b96cdc7f 26
j_rocket_boy 0:95f2b96cdc7f 27
j_rocket_boy 0:95f2b96cdc7f 28 void BME280::read_sensor(void){
j_rocket_boy 0:95f2b96cdc7f 29 char sensor_raw_data[8];
j_rocket_boy 0:95f2b96cdc7f 30 BME280_S32_t T,P,H; //ADC読み込み後温度,気圧,湿度の生データ
j_rocket_boy 0:95f2b96cdc7f 31 BME280_S32_t T_cor; //温度の補正データ
j_rocket_boy 0:95f2b96cdc7f 32 BME280_U32_t P_cor,H_cor; //気圧,湿度の補正データ
j_rocket_boy 0:95f2b96cdc7f 33
j_rocket_boy 0:95f2b96cdc7f 34 //読み込み
j_rocket_boy 0:95f2b96cdc7f 35 set_force_mode(); //測定開始
j_rocket_boy 0:95f2b96cdc7f 36 while(STATUS_IS_MEASURING); //測定待ち
j_rocket_boy 0:95f2b96cdc7f 37 sensor.read_reg(BME280_add, PRESS_MSB, sensor_raw_data, 8); //PRESS_MSBレジスタから8バイト読み込み
j_rocket_boy 0:95f2b96cdc7f 38 T = sensor_raw_data[3] << 12 | sensor_raw_data[4] << 4 | sensor_raw_data[5] >> 4 ;
j_rocket_boy 0:95f2b96cdc7f 39 P = sensor_raw_data[0] << 12 | sensor_raw_data[1] << 4 | sensor_raw_data[2] >> 4 ;
j_rocket_boy 0:95f2b96cdc7f 40 H = sensor_raw_data[6] << 8 | sensor_raw_data[7];
j_rocket_boy 0:95f2b96cdc7f 41
j_rocket_boy 0:95f2b96cdc7f 42 //補正
j_rocket_boy 0:95f2b96cdc7f 43 T_cor = BME280_compensate_T_int32(T);
j_rocket_boy 0:95f2b96cdc7f 44 P_cor = BME280_compensate_P_int64(P);
j_rocket_boy 0:95f2b96cdc7f 45 H_cor = BME280_compensate_H_int32(H);
j_rocket_boy 0:95f2b96cdc7f 46
j_rocket_boy 0:95f2b96cdc7f 47 temp = T_cor / 100.0;
j_rocket_boy 0:95f2b96cdc7f 48 press = P_cor / 256.0;
j_rocket_boy 0:95f2b96cdc7f 49 hum = H_cor / 1024.0;
j_rocket_boy 0:95f2b96cdc7f 50 }
j_rocket_boy 0:95f2b96cdc7f 51
j_rocket_boy 0:95f2b96cdc7f 52 bool BME280::data_is_ready(void){
j_rocket_boy 0:95f2b96cdc7f 53 return !STATUS_IS_MEASURING;
j_rocket_boy 0:95f2b96cdc7f 54 }
j_rocket_boy 0:95f2b96cdc7f 55
j_rocket_boy 0:95f2b96cdc7f 56 void BME280::set_sleep_mode(void){
j_rocket_boy 0:95f2b96cdc7f 57 sensor.write_reg(BME280_add, CTRL_MEAS, (meas_reg_value&0xFC) | SLEEP_MODE );
j_rocket_boy 0:95f2b96cdc7f 58 }
j_rocket_boy 0:95f2b96cdc7f 59
j_rocket_boy 0:95f2b96cdc7f 60 void BME280::set_force_mode(void){
j_rocket_boy 0:95f2b96cdc7f 61 sensor.write_reg(BME280_add, CTRL_MEAS, (meas_reg_value&0xFC) | FORCE_MODE );
j_rocket_boy 0:95f2b96cdc7f 62 }
j_rocket_boy 0:95f2b96cdc7f 63
j_rocket_boy 0:95f2b96cdc7f 64 void BME280::set_normal_mode(void){
j_rocket_boy 0:95f2b96cdc7f 65 sensor.write_reg(BME280_add, CTRL_MEAS, (meas_reg_value&0xFC) | NORMAL_MODE );
j_rocket_boy 0:95f2b96cdc7f 66 }
j_rocket_boy 0:95f2b96cdc7f 67
j_rocket_boy 0:95f2b96cdc7f 68
j_rocket_boy 0:95f2b96cdc7f 69 //データシートより,補正関数
j_rocket_boy 0:95f2b96cdc7f 70 // 温度を℃で返します。分解能は0.01℃です。「5123」の出力値は、51.23℃に相当します。
j_rocket_boy 0:95f2b96cdc7f 71 // t_fineは、グローバル値として細かい温度値を持ちます。
j_rocket_boy 0:95f2b96cdc7f 72 BME280_S32_t BME280::BME280_compensate_T_int32(BME280_S32_t adc_T){
j_rocket_boy 0:95f2b96cdc7f 73 BME280_S32_t var1, var2, T;
j_rocket_boy 0:95f2b96cdc7f 74 var1 = ((((adc_T>>3) - ((BME280_S32_t)dig_T1<<1))) * ((BME280_S32_t)dig_T2)) >> 11;
j_rocket_boy 0:95f2b96cdc7f 75 var2 = (((((adc_T>>4) - ((BME280_S32_t)dig_T1)) * ((adc_T>>4) - ((BME280_S32_t)dig_T1))) >> 12) *
j_rocket_boy 0:95f2b96cdc7f 76 ((BME280_S32_t)dig_T3)) >> 14;
j_rocket_boy 0:95f2b96cdc7f 77 t_fine = var1 + var2;
j_rocket_boy 0:95f2b96cdc7f 78 T = (t_fine * 5 + 128) >> 8;
j_rocket_boy 0:95f2b96cdc7f 79 return T;
j_rocket_boy 0:95f2b96cdc7f 80 }
j_rocket_boy 0:95f2b96cdc7f 81
j_rocket_boy 0:95f2b96cdc7f 82 // 圧力(Pa)を、Q24.8形式の符号なし32ビット整数として返します。(24個の整数ビットと8個の小数ビット)
j_rocket_boy 0:95f2b96cdc7f 83 // 「24674867」の出力値は、24674867/256 = 96386.2Pa = 963.862hPaに相当します。
j_rocket_boy 0:95f2b96cdc7f 84 BME280_U32_t BME280::BME280_compensate_P_int64(BME280_S32_t adc_P){
j_rocket_boy 0:95f2b96cdc7f 85 BME280_S64_t var1, var2, p;
j_rocket_boy 0:95f2b96cdc7f 86 var1 = ((BME280_S64_t)t_fine) - 128000;
j_rocket_boy 0:95f2b96cdc7f 87 var2 = var1 * var1 * (BME280_S64_t)dig_P6;
j_rocket_boy 0:95f2b96cdc7f 88 var2 = var2 + ((var1*(BME280_S64_t)dig_P5)<<17);
j_rocket_boy 0:95f2b96cdc7f 89 var2 = var2 + (((BME280_S64_t)dig_P4)<<35);
j_rocket_boy 0:95f2b96cdc7f 90 var1 = ((var1 * var1 * (BME280_S64_t)dig_P3)>>8) + ((var1 * (BME280_S64_t)dig_P2)<<12);
j_rocket_boy 0:95f2b96cdc7f 91 var1 = (((((BME280_S64_t)1)<<47)+var1))*((BME280_S64_t)dig_P1)>>33;
j_rocket_boy 0:95f2b96cdc7f 92 if (var1 == 0){
j_rocket_boy 0:95f2b96cdc7f 93 return 0; // ゼロ除算による例外を避ける。
j_rocket_boy 0:95f2b96cdc7f 94 }
j_rocket_boy 0:95f2b96cdc7f 95 p = 1048576-adc_P;
j_rocket_boy 0:95f2b96cdc7f 96 p = (((p<<31)-var2)*3125)/var1;
j_rocket_boy 0:95f2b96cdc7f 97 var1 = (((BME280_S64_t)dig_P9) * (p>>13) * (p>>13)) >> 25;
j_rocket_boy 0:95f2b96cdc7f 98 var2 = (((BME280_S64_t)dig_P8) * p) >> 19;
j_rocket_boy 0:95f2b96cdc7f 99 p = ((p + var1 + var2) >> 8) + (((BME280_S64_t)dig_P7)<<4);
j_rocket_boy 0:95f2b96cdc7f 100 return (BME280_U32_t)p;
j_rocket_boy 0:95f2b96cdc7f 101 }
j_rocket_boy 0:95f2b96cdc7f 102
j_rocket_boy 0:95f2b96cdc7f 103 // 湿度(%RH)を、Q22.10形式の符号なし32ビット整数として返します。(22個の整数と10個の小数ビット)
j_rocket_boy 0:95f2b96cdc7f 104 // 「47445」の出力値は、47445/1024 = 46.333%RHに相当します。
j_rocket_boy 0:95f2b96cdc7f 105 BME280_U32_t BME280::BME280_compensate_H_int32(BME280_S32_t adc_H){
j_rocket_boy 0:95f2b96cdc7f 106 BME280_S32_t v_x1_u32r;
j_rocket_boy 0:95f2b96cdc7f 107 v_x1_u32r = (t_fine - ((BME280_S32_t)76800));
j_rocket_boy 0:95f2b96cdc7f 108 v_x1_u32r = (((((adc_H << 14) - (((BME280_S32_t)dig_H4) << 20) - (((BME280_S32_t)dig_H5) * v_x1_u32r)) +
j_rocket_boy 0:95f2b96cdc7f 109 ((BME280_S32_t)16384)) >> 15) * (((((((v_x1_u32r * ((BME280_S32_t)dig_H6)) >> 10) * (((v_x1_u32r *
j_rocket_boy 0:95f2b96cdc7f 110 ((BME280_S32_t)dig_H3)) >> 11) + ((BME280_S32_t)32768))) >> 10) + ((BME280_S32_t)2097152)) *
j_rocket_boy 0:95f2b96cdc7f 111 ((BME280_S32_t)dig_H2) + 8192) >> 14));
j_rocket_boy 0:95f2b96cdc7f 112 v_x1_u32r = (v_x1_u32r - (((((v_x1_u32r >> 15) * (v_x1_u32r >> 15)) >> 7) * ((BME280_S32_t)dig_H1)) >> 4));
j_rocket_boy 0:95f2b96cdc7f 113 v_x1_u32r = (v_x1_u32r < 0 ? 0 : v_x1_u32r);
j_rocket_boy 0:95f2b96cdc7f 114 v_x1_u32r = (v_x1_u32r > 419430400 ? 419430400 : v_x1_u32r);
j_rocket_boy 0:95f2b96cdc7f 115 return (BME280_U32_t)(v_x1_u32r>>12);
j_rocket_boy 0:95f2b96cdc7f 116 }
j_rocket_boy 0:95f2b96cdc7f 117 //補正関数終わり
j_rocket_boy 0:95f2b96cdc7f 118
j_rocket_boy 0:95f2b96cdc7f 119 void BME280::init(void){
j_rocket_boy 0:95f2b96cdc7f 120 char calib[32] = {0};
j_rocket_boy 0:95f2b96cdc7f 121 char reg_data;
j_rocket_boy 0:95f2b96cdc7f 122 sensor.write_reg(BME280_add, RESET_REG, RESET_VALUE);
j_rocket_boy 0:95f2b96cdc7f 123
j_rocket_boy 0:95f2b96cdc7f 124 reg_data = sensor.read_reg(BME280_add,ID); //ID読み込み
j_rocket_boy 0:95f2b96cdc7f 125 if(reg_data != ID_VALUE){ //ID不一致エラー
j_rocket_boy 0:95f2b96cdc7f 126 printf("error\n");
j_rocket_boy 0:95f2b96cdc7f 127 while(1);
j_rocket_boy 0:95f2b96cdc7f 128 }
j_rocket_boy 0:95f2b96cdc7f 129 while(STATUS_IS_COPYING); //不揮発メモリのデータのレジスタコピー待ち
j_rocket_boy 0:95f2b96cdc7f 130
j_rocket_boy 0:95f2b96cdc7f 131 //ADC補償式用定数読み込み
j_rocket_boy 0:95f2b96cdc7f 132 sensor.read_reg(BME280_add, CALIB00, &(calib[0]), 24);
j_rocket_boy 0:95f2b96cdc7f 133 sensor.read_reg(BME280_add, CALIB25, &(calib[24]), 1);
j_rocket_boy 0:95f2b96cdc7f 134 sensor.read_reg(BME280_add, CALIB26, &(calib[25]), 7);
j_rocket_boy 0:95f2b96cdc7f 135
j_rocket_boy 0:95f2b96cdc7f 136 dig_T1 = calib[ 0] | (calib[ 1] << 8);
j_rocket_boy 0:95f2b96cdc7f 137 dig_T2 = calib[ 2] | (calib[ 3] << 8);
j_rocket_boy 0:95f2b96cdc7f 138 dig_T3 = calib[ 4] | (calib[ 5] << 8);
j_rocket_boy 0:95f2b96cdc7f 139
j_rocket_boy 0:95f2b96cdc7f 140 dig_P1 = calib[ 6] | (calib[ 7] << 8);
j_rocket_boy 0:95f2b96cdc7f 141 dig_P2 = calib[ 8] | (calib[ 9] << 8);
j_rocket_boy 0:95f2b96cdc7f 142 dig_P3 = calib[10] | (calib[11] << 8);
j_rocket_boy 0:95f2b96cdc7f 143 dig_P4 = calib[12] | (calib[13] << 8);
j_rocket_boy 0:95f2b96cdc7f 144 dig_P5 = calib[14] | (calib[15] << 8);
j_rocket_boy 0:95f2b96cdc7f 145 dig_P6 = calib[16] | (calib[17] << 8);
j_rocket_boy 0:95f2b96cdc7f 146 dig_P7 = calib[18] | (calib[19] << 8);
j_rocket_boy 0:95f2b96cdc7f 147 dig_P8 = calib[20] | (calib[21] << 8);
j_rocket_boy 0:95f2b96cdc7f 148 dig_P9 = calib[22] | (calib[23] << 8);
j_rocket_boy 0:95f2b96cdc7f 149
j_rocket_boy 0:95f2b96cdc7f 150 dig_H1 = calib[24];
j_rocket_boy 0:95f2b96cdc7f 151 dig_H2 = calib[25] | (calib[26] << 8);
j_rocket_boy 0:95f2b96cdc7f 152 dig_H3 = calib[27];
j_rocket_boy 0:95f2b96cdc7f 153 dig_H4 = (calib[28]<<4) | (calib[29] & 0x0F);
j_rocket_boy 0:95f2b96cdc7f 154 dig_H5 = ((calib[29]>>4) & 0x0F) | (calib[30] << 4);
j_rocket_boy 0:95f2b96cdc7f 155 dig_H6 = calib[31];
j_rocket_boy 0:95f2b96cdc7f 156 //ADC補償式用定数読み込みEND
j_rocket_boy 0:95f2b96cdc7f 157
j_rocket_boy 0:95f2b96cdc7f 158 //センサ設定
j_rocket_boy 0:95f2b96cdc7f 159 sensor.write_reg(BME280_add, CTRL_HUM , hum_reg_value);
j_rocket_boy 0:95f2b96cdc7f 160 sensor.write_reg(BME280_add, CTRL_MEAS, meas_reg_value);
j_rocket_boy 0:95f2b96cdc7f 161 sensor.write_reg(BME280_add, CONFIG , config_reg_value);
j_rocket_boy 0:95f2b96cdc7f 162
j_rocket_boy 0:95f2b96cdc7f 163 }
j_rocket_boy 0:95f2b96cdc7f 164
j_rocket_boy 0:95f2b96cdc7f 165