diff options
author | Matthias P. Braendli <matthias.braendli@mpb.li> | 2017-06-23 11:24:34 +0200 |
---|---|---|
committer | Matthias P. Braendli <matthias.braendli@mpb.li> | 2017-06-23 11:24:34 +0200 |
commit | 2629f182e8ae26c155fc895a3b6dd751485ef2a7 (patch) | |
tree | 1a0d0640fec3f24d89b33d2f6ed391bf4a6b78a6 | |
parent | 27e489a4b40a139ace3c679215e44f109f006127 (diff) | |
download | dabmux-2629f182e8ae26c155fc895a3b6dd751485ef2a7.tar.gz dabmux-2629f182e8ae26c155fc895a3b6dd751485ef2a7.tar.bz2 dabmux-2629f182e8ae26c155fc895a3b6dd751485ef2a7.zip |
Add a few sanity checks for the configuration parser
-rw-r--r-- | doc/advanced.mux | 2 | ||||
-rw-r--r-- | src/ConfigParser.cpp | 27 | ||||
-rw-r--r-- | src/DabMux.cpp | 4 | ||||
-rw-r--r-- | src/utils.cpp | 25 |
4 files changed, 46 insertions, 12 deletions
diff --git a/doc/advanced.mux b/doc/advanced.mux index 74c1dd4..801857b 100644 --- a/doc/advanced.mux +++ b/doc/advanced.mux @@ -220,7 +220,7 @@ subchannels { ; input. ; by default, it is disabled, set encryption to 1 to enable - encryption 1 + encryption true ; the multiplexer key pair. Keep these secret. secret-key "keys/mux.sec" diff --git a/src/ConfigParser.cpp b/src/ConfigParser.cpp index 8eed560..dc71857 100644 --- a/src/ConfigParser.cpp +++ b/src/ConfigParser.cpp @@ -131,7 +131,7 @@ static void parse_linkage(boost::property_tree::ptree& pt, const ptree pt_set = it.second; uint16_t lsn = hexparse(pt_set.get("lsn", "0")); - if (lsn == 0) { + if (lsn == 0 or lsn > 0xFFF) { etiLog.level(error) << "LSN for linking set " << setuid << " invalid or missing"; throw runtime_error("Invalid service linking definition"); @@ -367,9 +367,15 @@ void parse_ptree( /* Ensemble ID */ ensemble->id = hexparse(pt_ensemble.get("id", "0")); + if (ensemble->id == 0) { + etiLog.level(warn) << "Ensemble ID is 0!"; + } /* Extended Country Code */ ensemble->ecc = hexparse(pt_ensemble.get("ecc", "0")); + if (ensemble->ecc == 0) { + etiLog.level(warn) << "ECC is 0!"; + } ensemble->international_table = pt_ensemble.get("international-table", 0); @@ -438,6 +444,10 @@ void parse_ptree( auto cl = make_shared<AnnouncementCluster>(name); cl->cluster_id = hexparse(pt_announcement.get<string>("cluster")); + if (cl->cluster_id == 0 or cl->cluster_id == 0xFF) { + throw runtime_error("Announcement cluster id " + + to_string(cl->cluster_id) + " is not allowed"); + } cl->flags = get_announcement_flag_from_ptree( pt_announcement.get_child("flags")); cl->subchanneluid = pt_announcement.get<string>("subchannel"); @@ -808,7 +818,7 @@ static Inputs::dab_input_zmq_config_t setup_zmq_input( zmqconfig.curve_secret_keyfile = pt.get<string>("secret-key",""); zmqconfig.curve_public_keyfile = pt.get<string>("public-key",""); - zmqconfig.enable_encryption = pt.get<int>("encryption", 0); + zmqconfig.enable_encryption = pt.get<bool>("encryption", false); return zmqconfig; } @@ -981,14 +991,15 @@ static void setup_subchannel_from_ptree(DabSubchannel* subchan, } } catch (ptree_error &e) { - stringstream ss; - ss << "Error, no bitrate defined for subchannel " << subchanuid; - throw runtime_error(ss.str()); + throw runtime_error("Error, no bitrate defined for subchannel " + subchanuid); } /* Get id */ try { subchan->id = hexparse(pt.get<std::string>("id")); + if (subchan->id >= 64) { + throw runtime_error("Invalid subchannel id " + to_string(subchan->id)); + } } catch (ptree_error &e) { for (int i = 0; i < 64; ++i) { // Find first free subchannel @@ -1015,6 +1026,12 @@ static void setup_subchannel_from_ptree(DabSubchannel* subchan, else if (profile == "UEP") { protection->form = UEP; } + else if (profile == "") { + /* take defaults */ + } + else { + throw runtime_error("Invalid protection-profile: " + profile); + } /* Get protection level */ try { diff --git a/src/DabMux.cpp b/src/DabMux.cpp index 3870df5..5d109fa 100644 --- a/src/DabMux.cpp +++ b/src/DabMux.cpp @@ -481,6 +481,10 @@ int main(int argc, char *argv[]) etiLog.level(error) << "Caught invalid argument : " << except.what(); returnCode = 1; } + catch (const std::out_of_range& except) { + etiLog.level(error) << "Caught out of range exception : " << except.what(); + returnCode = 1; + } catch (const std::runtime_error& except) { etiLog.level(error) << "Caught runtime error : " << except.what(); returnCode = 2; diff --git a/src/utils.cpp b/src/utils.cpp index 8b4de67..885e49a 100644 --- a/src/utils.cpp +++ b/src/utils.cpp @@ -538,14 +538,19 @@ long hexparse(const std::string& input) long value = 0; errno = 0; + char* endptr = nullptr; + + const bool is_hex = (input.find("0x") == 0); + // Do not use strtol's base=0 because // we do not want to accept octal. - if (input.find("0x") == 0) { - value = strtol(input.c_str() + 2, nullptr, 16); - } - else { - value = strtol(input.c_str(), nullptr, 10); - } + const int base = is_hex ? 16 : 10; + + const char* const startptr = is_hex ? + input.c_str() + 2 : + input.c_str(); + + value = strtol(input.c_str(), &endptr, base); if ((value == LONG_MIN or value == LONG_MAX) and errno == ERANGE) { throw out_of_range("hexparse: value out of range"); @@ -556,6 +561,14 @@ long hexparse(const std::string& input) throw invalid_argument(ss.str()); } + if (startptr == endptr) { + throw out_of_range("hexparse: no value found"); + } + + if (*endptr != '\0') { + throw out_of_range("hexparse: superfluous characters after value found: '" + input + "'"); + } + return value; } |