diff options
Diffstat (limited to 'src/TimestampDecoder.cpp')
-rw-r--r-- | src/TimestampDecoder.cpp | 210 |
1 files changed, 210 insertions, 0 deletions
diff --git a/src/TimestampDecoder.cpp b/src/TimestampDecoder.cpp new file mode 100644 index 0000000..3dd64bf --- /dev/null +++ b/src/TimestampDecoder.cpp @@ -0,0 +1,210 @@ +/* + Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010 Her Majesty the + Queen in Right of Canada (Communications Research Center Canada) + + Includes modifications for which no copyright is claimed + 2012, Matthias P. Braendli, matthias.braendli@mpb.li + */ +/* + This file is part of CRC-DADMOD. + + CRC-DADMOD is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as + published by the Free Software Foundation, either version 3 of the + License, or (at your option) any later version. + + CRC-DADMOD is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with CRC-DADMOD. If not, see <http://www.gnu.org/licenses/>. + */ + +#include "TimestampDecoder.h" +#include "Eti.h" +#include <sys/types.h> +#include "PcDebug.h" +#include <iostream> +#include <fstream> +#include <string> +#include <boost/lexical_cast.hpp> + +//#define MDEBUG(fmt, args...) fprintf (LOG, fmt , ## args) +#define MDEBUG(fmt, args...) PDEBUG(fmt, ## args) + + +void TimestampDecoder::calculateTimestamp(struct frame_timestamp& ts) +{ + ts.timestamp_valid = full_timestamp_received_mnsc; + ts.timestamp_sec = time_secs; + ts.timestamp_pps_offset = time_pps; + + ts.timestamp_refresh = offset_changed; + offset_changed = false; + + ts += timestamp_offset; + //ts.print("calc2 "); +} + +void TimestampDecoder::pushMNSCData(int framephase, uint16_t mnsc) +{ + struct eti_MNSC_TIME_0 *mnsc0; + struct eti_MNSC_TIME_1 *mnsc1; + struct eti_MNSC_TIME_2 *mnsc2; + struct eti_MNSC_TIME_3 *mnsc3; + + switch (framephase) + { + case 0: + mnsc0 = (struct eti_MNSC_TIME_0*)&mnsc; + enableDecode = (mnsc0->type == 0) && + (mnsc0->identifier == 0); + gmtime_r(0, &temp_time); + break; + + case 1: + mnsc1 = (struct eti_MNSC_TIME_1*)&mnsc; + temp_time.tm_sec = mnsc1->second_tens * 10 + mnsc1->second_unit; + temp_time.tm_min = mnsc1->minute_tens * 10 + mnsc1->minute_unit; + + if (!mnsc1->sync_to_frame) + { + enableDecode = false; + PDEBUG("TimestampDecoder: MNSC time info is not synchronised to frame\n"); + } + + break; + + case 2: + mnsc2 = (struct eti_MNSC_TIME_2*)&mnsc; + temp_time.tm_hour = mnsc2->hour_tens * 10 + mnsc2->hour_unit; + temp_time.tm_mday = mnsc2->day_tens * 10 + mnsc2->day_unit; + break; + + case 3: + mnsc3 = (struct eti_MNSC_TIME_3*)&mnsc; + temp_time.tm_mon = (mnsc3->month_tens * 10 + mnsc3->month_unit) - 1; + temp_time.tm_year = (mnsc3->year_tens * 10 + mnsc3->year_unit) + 100; + + if (enableDecode) + { + full_timestamp_received_mnsc = true; + updateTimestampSeconds(mktime(&temp_time)); + } + break; + } + + MDEBUG("TimestampDecoder::pushMNSCData(%d, 0x%x)\n", framephase, mnsc); + MDEBUG(" -> %s\n", asctime(&temp_time)); + MDEBUG(" -> %zu\n", mktime(&temp_time)); +} + +void TimestampDecoder::updateTimestampSeconds(uint32_t secs) +{ + MDEBUG("TimestampDecoder::updateTimestampSeconds(%d)\n", secs); + if (inhibit_second_update > 0) + { + inhibit_second_update--; + } + else + { + time_secs = secs; + } +} + +void TimestampDecoder::updateTimestampPPS(double pps) +{ + MDEBUG("TimestampDecoder::updateTimestampPPS(%f)\n", pps); + + if (time_pps > pps) // Second boundary crossed + { + MDEBUG("TimestampDecoder::updateTimestampPPS crossed second\n", pps); + + // The second for the next eight frames will not + // be defined by the MNSC + inhibit_second_update = 2; + time_secs += 1; + } + + time_pps = pps; + +} + +void TimestampDecoder::updateTimestampEti(int framephase, uint16_t mnsc, double pps) +{ + updateTimestampPPS(pps); + pushMNSCData(framephase, mnsc); +} + + +bool TimestampDecoder::updateModulatorOffset() +{ + using namespace std; + using boost::lexical_cast; + using boost::bad_lexical_cast; + + if (modconfig.use_offset_fixed) + { + timestamp_offset = modconfig.offset_fixed; + PDEBUG("Setting timestamp offset to %f\n", timestamp_offset); + return true; + } + else if (modconfig.use_offset_file) + { + bool r = false; + double newoffset; + + std::string filedata; + ifstream filestream; + + try + { + filestream.open(modconfig.offset_filename); + if (!filestream.eof()) + { + getline(filestream, filedata); + try + { + newoffset = lexical_cast<double>(filedata); + r = true; + } + catch (bad_lexical_cast& e) + { + fprintf(stderr, "Error parsing timestamp offset from file\n"); + r = false; + } + } + else + { + fprintf(stderr, "Error reading from timestamp offset file: eof reached\n"); + r = false; + } + filestream.close(); + } + catch (exception& e) + { + fprintf(stderr, "Error opening timestamp offset file\n"); + r = false; + } + + + if (r) + { + if (timestamp_offset != newoffset) + { + timestamp_offset = newoffset; + fprintf(stderr, "TimestampDecoder::updateTimestampOffset:" \ + "new offset is %f\n", timestamp_offset); + offset_changed = true; + } + + } + + return r; + } + else { + return false; + } +} |