gavin beardall
/
hsc
Revision 1:d01abb5e6f52, committed 2011-10-17
- Comitter:
- gbeardall
- Date:
- Mon Oct 17 10:41:37 2011 +0000
- Parent:
- 0:2fdc6095d7b4
- Commit message:
Changed in this revision
main.cpp | Show annotated file Show diff for this revision Revisions of this file |
diff -r 2fdc6095d7b4 -r d01abb5e6f52 main.cpp --- a/main.cpp Wed Sep 07 07:27:01 2011 +0000 +++ b/main.cpp Mon Oct 17 10:41:37 2011 +0000 @@ -1,3 +1,10 @@ +/* + * Honeywell Pressure Sensor + * + */ + +#include <math.h> + #include "mbed.h" DigitalOut myled(LED1); @@ -34,14 +41,19 @@ unsigned char data[4]; i2c.read((id<<1)|1, (char*)data, sizeof(data)); //printf("%02X %02X %02X %02X\n\r", data[0], data[1], data[2], data[3]); + int st = data[0]>>6; // status int bd = ((data[0] & 0x3f) << 8) | data[1]; // bridge data int td = ((data[2]<<8) | data[3]) >> 5; // temp data - float p = ((float)bd-1638)*(15-0)/(14745-1638)-0; // convert to psi - p = p * 68.9475729; // psi to hPa + // P: 14 bits + // Cmin=2^14-1*.1 Cmax=2^14-1*.9 + // Pmin=0 Pmax=15 + float p = (((float)bd-1638)*(15-0)/(14745-1638))+0; // convert raw data to psi + p = p * 68.9475729; // convert psi to hPa - float t = (((float)td*200)/2047)-50; // convert to deg C + // T: 11 bits (Cmax=2047=2^11-1) + float t = (((float)td*200)/2047)-50; // convert raw data to deg C printf("%d: %.2f hPa %.2f C\n\r", st, p, t); wait(1); @@ -55,3 +67,76 @@ } // while } // main + + +// http://en.wikipedia.org/wiki/Barometric_formula +const float layers[][4] = { +// Height[m], Pressure[Pa], Temp[K], Lapse[K/m], Subscript + 0, 101325.0, 288.15, -0.0065, // 0 + 11000, 22632.1, 216.65, 0.0, // 1 + 20000, 5474.89, 216.65, 0.001, // 2 + 32000, 868.019, 228.65, 0.0028, // 3 + 47000, 110.906, 270.65, 0.0, // 4 + 51000, 66.9389, 270.65, -0.0028, // 5 + 71000, 3.95642, 214.65, -0.002 // 6 +}; + +enum { L_HEIGHT=0, L_PRESS, L_TEMP, L_LAPSE }; + +const float g = 9.80665; +const float M = 0.0289644; +const float R = 8.31432; +const float Ta = -273.15; // Absolute zero [deg C] + +// Search for subscript which matches pressure range +// Choose appropriate formula and plug in values +// Lookup derived h in table and check subscript is still same, otherwise recalculate +// Add height correction + +// Pass in pressure and temperature from sensor +// Return height[m] +float pressureToHeight(float p, float t) { + float h = -999; // error + int b; + int tries; + + // Search backwards thru layers for our pressure + for(b = 6; b >= 0; --b) { + if(p <= layers[b][1]) break; + } + if(b < 0) b = 0; // adjust so can have -ve heights + int b1 = b; + + // Only retry limited times + for(tries = 10; tries; --tries) { + + float Hb = layers[b][0]; + float Pb = layers[b][1]; + float Tb = layers[b][2]; //??? Tb = t - Ta; + float Lb = layers[b][3]; + + if(Lb != 0.0) + //h = (log(g*M/R/Lb)/log(p/Pb)*Tb - Tb)/Lb + Hb; // Equation 1 (non-zero lapse rate) + h = (Tb/exp(R*Lb/g/M*log(p/Pb))-Tb)/Lb + Hb; + else + h = -log(p/Pb)*R*Tb/g/M + Hb; // Equation 2 (zero lapse rate) + + // Search again for derived height + for(b = 6; b >= 0; --b) { + if(h <= layers[b][0]) break; + } + + if(b == b1) break; // gave same subscript, so we can stop + b1 = b; + + } // for - tries + + if(tries <= 0) h = -999; // error + + + return h; + +} // pressureToHeight + +/*end*/ +