File indexing completed on 2024-04-06 12:23:13
0001 #include <ctime>
0002 #include <iostream>
0003 #include <string>
0004 #include <stdexcept>
0005 #include <cmath>
0006 #include <cstdio>
0007
0008 #include "OnlineDB/EcalCondDB/interface/Tm.h"
0009
0010 using namespace std;
0011
0012
0013
0014
0015
0016
0017
0018 std::ostream &operator<<(std::ostream &out, const Tm &t) {
0019 out << t.str();
0020 return out;
0021 }
0022
0023
0024 Tm::Tm() { this->setNull(); }
0025
0026
0027 Tm::Tm(struct tm *initTm) { m_tm = *initTm; }
0028
0029 Tm::Tm(uint64_t micros) {
0030 this->setNull();
0031 if (micros > PLUS_INF_MICROS) {
0032
0033 this->setToCmsNanoTime(micros);
0034 } else {
0035 this->setToMicrosTime(micros);
0036 }
0037 }
0038
0039
0040 Tm::~Tm() {}
0041
0042 struct tm Tm::c_tm() const { return m_tm; }
0043
0044 int Tm::isNull() const {
0045 if (m_tm.tm_year == 0 && m_tm.tm_mon == 0 && m_tm.tm_mday == 0) {
0046 return 1;
0047 } else {
0048 return 0;
0049 }
0050 }
0051
0052 void Tm::setNull() {
0053 m_tm.tm_hour = 0;
0054 m_tm.tm_isdst = 0;
0055 m_tm.tm_mday = 0;
0056 m_tm.tm_min = 0;
0057 m_tm.tm_mon = 0;
0058 m_tm.tm_sec = 0;
0059 m_tm.tm_wday = 0;
0060 m_tm.tm_yday = 0;
0061 m_tm.tm_year = 0;
0062 }
0063
0064 string Tm::str() const {
0065 if (this->isNull()) {
0066 return "";
0067 }
0068
0069
0070
0071
0072
0073
0074
0075
0076
0077
0078 char timebuf[20] = "";
0079 if (this->microsTime() >= PLUS_INF_MICROS) {
0080 sprintf(timebuf, "9999-12-12 23:59:59");
0081 } else {
0082 Tm dummy_Tm;
0083 dummy_Tm.setToGMTime(this->microsTime() / 1000000);
0084 struct tm dummy_tm = dummy_Tm.c_tm();
0085 strftime(timebuf, 20, "%Y-%m-%d %H:%M:%S", &dummy_tm);
0086 }
0087 return string(timebuf);
0088 }
0089
0090 uint64_t Tm::cmsNanoSeconds() const { return microsTime() / 1000000 << 32; }
0091
0092 uint64_t Tm::unixTime() const { return microsTime() / 1000000; }
0093
0094 uint64_t Tm::microsTime() const {
0095 uint64_t result = 0;
0096
0097
0098
0099
0100
0101
0102
0103
0104
0105 struct tm time_struct;
0106 time_struct.tm_year = 1970 - 1900;
0107 time_struct.tm_mon = 0;
0108 time_struct.tm_mday = 1;
0109 time_struct.tm_sec = 0;
0110 time_struct.tm_min = 0;
0111 time_struct.tm_hour = 0;
0112 time_struct.tm_isdst = 0;
0113
0114 time_t t1970 = mktime(&time_struct);
0115 tm s = m_tm;
0116 time_t t_this = mktime(&s);
0117
0118 double x = difftime(t_this, t1970);
0119 result = (uint64_t)x * 1000000;
0120
0121 return result;
0122 }
0123
0124 void Tm::setToCmsNanoTime(uint64_t nanos) { setToMicrosTime((nanos >> 32) * 1000000); }
0125
0126 void Tm::setToMicrosTime(uint64_t micros) {
0127 time_t t = micros / 1000000;
0128 if (t >= INT_MAX) {
0129 t = INT_MAX;
0130 }
0131 m_tm = *gmtime(&t);
0132 }
0133
0134 void Tm::setToCurrentLocalTime() {
0135 time_t t = time(nullptr);
0136 m_tm = *localtime(&t);
0137 }
0138
0139 void Tm::setToCurrentGMTime() {
0140 time_t t = time(nullptr);
0141 m_tm = *gmtime(&t);
0142 }
0143
0144 void Tm::setToLocalTime(time_t t) { m_tm = *localtime(&t); }
0145
0146 void Tm::setToGMTime(time_t t) { m_tm = *gmtime(&t); }
0147
0148 void Tm::setToString(const string s) noexcept(false) {
0149 sscanf(s.c_str(),
0150 "%04d-%02d-%02d %02d:%02d:%02d",
0151 &m_tm.tm_year,
0152 &m_tm.tm_mon,
0153 &m_tm.tm_mday,
0154 &m_tm.tm_hour,
0155 &m_tm.tm_min,
0156 &m_tm.tm_sec);
0157
0158 try {
0159 if (m_tm.tm_year > 9999 || m_tm.tm_year < 1900) {
0160 throw(std::runtime_error("Year out of bounds"));
0161 } else if (m_tm.tm_mon > 12 || m_tm.tm_mon < 1) {
0162 throw(std::runtime_error("Month out of bounds"));
0163 } else if (m_tm.tm_mday > 31 || m_tm.tm_mday < 1) {
0164 throw(std::runtime_error("Day out of bounds"));
0165 } else if (m_tm.tm_hour > 23 || m_tm.tm_mday < 0) {
0166 throw(std::runtime_error("Hour out of bounds"));
0167 } else if (m_tm.tm_min > 59 || m_tm.tm_min < 0) {
0168 throw(std::runtime_error("Minute out of bounds"));
0169 } else if (m_tm.tm_sec > 59 || m_tm.tm_sec < 0) {
0170 throw(std::runtime_error("Day out of bounds"));
0171 }
0172
0173 if (m_tm.tm_year >= 2038) {
0174
0175 m_tm.tm_year = 2038;
0176 if (m_tm.tm_mon > 1) {
0177 m_tm.tm_mon = 1;
0178 }
0179 if (m_tm.tm_mday > 19) {
0180 m_tm.tm_mday = 19;
0181 }
0182 if (m_tm.tm_hour > 3) {
0183 m_tm.tm_hour = 3;
0184 }
0185 if (m_tm.tm_min > 14) {
0186 m_tm.tm_min = 14;
0187 }
0188 if (m_tm.tm_sec > 7) {
0189 m_tm.tm_sec = 7;
0190 }
0191 }
0192 m_tm.tm_year -= 1900;
0193 m_tm.tm_mon -= 1;
0194 } catch (std::runtime_error &e) {
0195 this->setNull();
0196 string msg("Tm::setToString(): ");
0197 msg.append(e.what());
0198 throw(std::runtime_error(msg));
0199 }
0200 }
0201
0202 void Tm::dumpTm() {
0203 cout << "=== dumpTm() ===" << endl;
0204 cout << "tm_year " << m_tm.tm_year << endl;
0205 cout << "tm_mon " << m_tm.tm_mon << endl;
0206 cout << "tm_mday " << m_tm.tm_mday << endl;
0207 cout << "tm_hour " << m_tm.tm_hour << endl;
0208 cout << "tm_min " << m_tm.tm_min << endl;
0209 cout << "tm_sec " << m_tm.tm_sec << endl;
0210 cout << "tm_yday " << m_tm.tm_yday << endl;
0211 cout << "tm_wday " << m_tm.tm_wday << endl;
0212 cout << "tm_isdst " << m_tm.tm_isdst << endl;
0213 cout << "================" << endl;
0214 }