SGmetar: catch bad temp/pressure data and throw
Also replace raw pointer with managed storage for the raw data, to avoid manual clean-up on exception-throw paths.
This commit is contained in:
parent
119f3d9814
commit
6fe7c307b2
@ -96,14 +96,14 @@ SGMetar::SGMetar(const string& m) :
|
|||||||
_snow(false),
|
_snow(false),
|
||||||
_cavok(false)
|
_cavok(false)
|
||||||
{
|
{
|
||||||
_data = new char[m.length() + 2]; // make room for " \0"
|
_data.resize(m.length() + 2); // make room for " \0"
|
||||||
strcpy(_data, m.c_str());
|
strcpy(_data.data(), m.c_str());
|
||||||
_url = _data;
|
_url = m;
|
||||||
|
|
||||||
normalizeData();
|
|
||||||
|
|
||||||
_m = _data;
|
normalizeData();
|
||||||
_icao[0] = '\0';
|
|
||||||
|
_m = _data.data();
|
||||||
|
_icao[0] = '\0';
|
||||||
|
|
||||||
// NOAA preample
|
// NOAA preample
|
||||||
if (!scanPreambleDate())
|
if (!scanPreambleDate())
|
||||||
@ -113,7 +113,6 @@ SGMetar::SGMetar(const string& m) :
|
|||||||
// METAR header
|
// METAR header
|
||||||
scanType();
|
scanType();
|
||||||
if (!scanId() || !scanDate()) {
|
if (!scanId() || !scanDate()) {
|
||||||
delete[] _data;
|
|
||||||
throw sg_io_exception("metar data bogus ", sg_location(_url));
|
throw sg_io_exception("metar data bogus ", sg_location(_url));
|
||||||
}
|
}
|
||||||
scanModifier();
|
scanModifier();
|
||||||
@ -125,7 +124,15 @@ SGMetar::SGMetar(const string& m) :
|
|||||||
while (scanRwyVisRange()) ;
|
while (scanRwyVisRange()) ;
|
||||||
while (scanWeather()) ;
|
while (scanWeather()) ;
|
||||||
while (scanSkyCondition()) ;
|
while (scanSkyCondition()) ;
|
||||||
scanTemperature();
|
|
||||||
|
if (!scanTemperature()) {
|
||||||
|
throw sg_io_exception("metar temperature data malformed or missing ", sg_location(_url));
|
||||||
|
}
|
||||||
|
if (!scanPressure()) {
|
||||||
|
throw sg_io_exception("metar pressure data malformed or missing ", sg_location(_url));
|
||||||
|
}
|
||||||
|
|
||||||
|
scanTemperature();
|
||||||
scanPressure();
|
scanPressure();
|
||||||
while (scanSkyCondition()) ;
|
while (scanSkyCondition()) ;
|
||||||
while (scanRunwayReport()) ;
|
while (scanRunwayReport()) ;
|
||||||
@ -139,11 +146,10 @@ SGMetar::SGMetar(const string& m) :
|
|||||||
scanRemark();
|
scanRemark();
|
||||||
|
|
||||||
if (_grpcount < 4) {
|
if (_grpcount < 4) {
|
||||||
delete[] _data;
|
|
||||||
throw sg_io_exception("metar data incomplete ", sg_location(_url));
|
throw sg_io_exception("metar data incomplete ", sg_location(_url));
|
||||||
}
|
}
|
||||||
|
|
||||||
_url = "";
|
_url.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -155,7 +161,6 @@ SGMetar::~SGMetar()
|
|||||||
_clouds.clear();
|
_clouds.clear();
|
||||||
_runways.clear();
|
_runways.clear();
|
||||||
_weather.clear();
|
_weather.clear();
|
||||||
delete[] _data;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -486,17 +491,24 @@ void SGMetar::useCurrentDate()
|
|||||||
_month = now.tm_mon + 1;
|
_month = now.tm_mon + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const char* SGMetar::getRawDataPtr()
|
||||||
|
{
|
||||||
|
return _data.data();
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
* Replace any number of subsequent spaces by just one space, and add
|
* Replace any number of subsequent spaces by just one space, and add
|
||||||
* a trailing space. This makes scanning for things like "ALL RWY" easier.
|
* a trailing space. This makes scanning for things like "ALL RWY" easier.
|
||||||
*/
|
*/
|
||||||
void SGMetar::normalizeData()
|
void SGMetar::normalizeData()
|
||||||
{
|
{
|
||||||
char *src, *dest;
|
// TODO : use strutils::simplify here
|
||||||
for (src = dest = _data; (*dest++ = *src++); )
|
char* src = _data.data();
|
||||||
while (*src == ' ' && src[1] == ' ')
|
char* dest = src;
|
||||||
|
for (; (*dest++ = *src++);) {
|
||||||
|
while (*src == ' ' && src[1] == ' ')
|
||||||
src++;
|
src++;
|
||||||
for (dest--; isspace(*--dest); ) ;
|
}
|
||||||
|
for (dest--; isspace(*--dest); ) ;
|
||||||
*++dest = ' ';
|
*++dest = ' ';
|
||||||
*++dest = '\0';
|
*++dest = '\0';
|
||||||
}
|
}
|
||||||
|
@ -186,9 +186,9 @@ public:
|
|||||||
std::vector<std::string> phenomena;
|
std::vector<std::string> phenomena;
|
||||||
};
|
};
|
||||||
|
|
||||||
inline const char *getData() const { return _data; }
|
const char* getRawDataPtr();
|
||||||
inline const char *getUnusedData() const { return _m; }
|
|
||||||
inline bool getProxy() const { return _x_proxy; }
|
inline bool getProxy() const { return _x_proxy; }
|
||||||
inline const char *getId() const { return _icao; }
|
inline const char *getId() const { return _icao; }
|
||||||
inline int getYear() const { return _year; }
|
inline int getYear() const { return _year; }
|
||||||
inline int getMonth() const { return _month; }
|
inline int getMonth() const { return _month; }
|
||||||
@ -244,9 +244,9 @@ protected:
|
|||||||
std::string _url;
|
std::string _url;
|
||||||
int _grpcount;
|
int _grpcount;
|
||||||
bool _x_proxy;
|
bool _x_proxy;
|
||||||
char *_data;
|
std::vector<char> _data;
|
||||||
char *_m;
|
char* _m;
|
||||||
char _icao[5];
|
char _icao[5];
|
||||||
int _year;
|
int _year;
|
||||||
int _month;
|
int _month;
|
||||||
int _day;
|
int _day;
|
||||||
|
Loading…
Reference in New Issue
Block a user