diff options
author | Dan Goodliffe <dan@randomdan.homeip.net> | 2021-08-10 18:14:30 +0100 |
---|---|---|
committer | Dan Goodliffe <dan@randomdan.homeip.net> | 2021-08-10 18:14:30 +0100 |
commit | ee2e68f44f7b9ee099f98b668257b5d57a86a695 (patch) | |
tree | d7593729cdb2dcad097c7a801f0c39c8d59381c0 | |
parent | Tests, fixes, improvements to WritePqCopyStream (diff) | |
download | mygrate-ee2e68f44f7b9ee099f98b668257b5d57a86a695.tar.bz2 mygrate-ee2e68f44f7b9ee099f98b668257b5d57a86a695.tar.xz mygrate-ee2e68f44f7b9ee099f98b668257b5d57a86a695.zip |
Enable numeric conversion warning and fix the fallout
-rw-r--r-- | Jamroot.jam | 1 | ||||
-rw-r--r-- | lib/compileTimeFormatter.h | 2 | ||||
-rw-r--r-- | lib/dbStmt.h | 2 | ||||
-rw-r--r-- | lib/dbTypes.h | 12 | ||||
-rw-r--r-- | lib/helpers.cpp | 11 | ||||
-rw-r--r-- | lib/helpers.h | 11 | ||||
-rw-r--r-- | lib/input/mysqlBindings.h | 8 | ||||
-rw-r--r-- | lib/mysql_types.cpp | 26 | ||||
-rw-r--r-- | lib/output/pq/pqRecordSet.cpp | 4 | ||||
-rw-r--r-- | lib/output/pq/pqStmt.cpp | 2 | ||||
-rw-r--r-- | lib/output/pq/writePqCopyStrm.cpp | 4 | ||||
-rw-r--r-- | lib/streamSupport.cpp | 2 | ||||
-rw-r--r-- | test/test-postgresql.cpp | 2 |
13 files changed, 59 insertions, 28 deletions
diff --git a/Jamroot.jam b/Jamroot.jam index c85ea56..bf471aa 100644 --- a/Jamroot.jam +++ b/Jamroot.jam @@ -21,6 +21,7 @@ project : requirements <variant>release:<lto>on <variant>debug:<warnings>extra <variant>debug:<warnings-as-errors>on + <variant>debug:<cflags>-Wconversion <variant>coverage:<coverage>on <toolset>tidy:<checkxx>boost-* <toolset>tidy:<checkxx>bugprone-* diff --git a/lib/compileTimeFormatter.h b/lib/compileTimeFormatter.h index e45a3d9..647fb30 100644 --- a/lib/compileTimeFormatter.h +++ b/lib/compileTimeFormatter.h @@ -133,7 +133,7 @@ namespace MyGrate { template<typename stream, typename char_type> static inline void - appendStream(stream & s, const char_type * p, size_t n) + appendStream(stream & s, const char_type * p, std::streamsize n) { s.write(p, n); } diff --git a/lib/dbStmt.h b/lib/dbStmt.h index 44ab62c..a6d4a65 100644 --- a/lib/dbStmt.h +++ b/lib/dbStmt.h @@ -26,7 +26,7 @@ namespace MyGrate { const auto pn = [](const char * c, const char * const e) { std::size_t n {0}; while (++c != e && *c >= '0' && *c <= '9') { - n = (n * 10) + (*c - '0'); + n = (n * 10) + unsigned(*c - '0'); } return n; }; diff --git a/lib/dbTypes.h b/lib/dbTypes.h index f49c929..e17315b 100644 --- a/lib/dbTypes.h +++ b/lib/dbTypes.h @@ -46,7 +46,11 @@ namespace MyGrate { struct Date { inline Date() { } inline Date(uint16_t y, uint8_t m, uint8_t d) : year {y}, month {m}, day {d} { } - explicit inline Date(const tm & tm) : Date(tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday) { } + explicit inline Date(const tm & tm) : + Date(boost::numeric_cast<uint16_t>(tm.tm_year + 1900), boost::numeric_cast<uint8_t>(tm.tm_mon + 1), + boost::numeric_cast<uint8_t>(tm.tm_mday)) + { + } uint16_t year; uint8_t month; uint8_t day; @@ -54,7 +58,11 @@ namespace MyGrate { struct Time { inline Time() { } inline Time(uint8_t h, uint8_t m, uint8_t s) : hour {h}, minute {m}, second {s} { } - explicit inline Time(const tm & tm) : Time(tm.tm_hour, tm.tm_min, tm.tm_sec) { } + explicit inline Time(const tm & tm) : + Time(boost::numeric_cast<uint8_t>(tm.tm_hour), boost::numeric_cast<uint8_t>(tm.tm_min), + boost::numeric_cast<uint8_t>(tm.tm_sec)) + { + } uint8_t hour; uint8_t minute; uint8_t second; diff --git a/lib/helpers.cpp b/lib/helpers.cpp new file mode 100644 index 0000000..23cec2a --- /dev/null +++ b/lib/helpers.cpp @@ -0,0 +1,11 @@ +#include "helpers.h" + +namespace MyGrate { + static_assert(std::is_same_v<SmallestUInt<1>, uint8_t>); + static_assert(std::is_same_v<SmallestUInt<8>, uint8_t>); + static_assert(std::is_same_v<SmallestUInt<9>, uint16_t>); + static_assert(std::is_same_v<SmallestUInt<16>, uint16_t>); + static_assert(std::is_same_v<SmallestUInt<17>, uint32_t>); + static_assert(std::is_same_v<SmallestUInt<32>, uint32_t>); + static_assert(std::is_same_v<SmallestUInt<33>, uint64_t>); +} diff --git a/lib/helpers.h b/lib/helpers.h index f09a206..2c7f4c2 100644 --- a/lib/helpers.h +++ b/lib/helpers.h @@ -1,6 +1,7 @@ #ifndef MYGRATE_HELPERS_H #define MYGRATE_HELPERS_H +#include <boost/numeric/conversion/cast.hpp> #include <concepts> #include <cstdint> #include <cstdlib> @@ -8,8 +9,13 @@ #include <utility> namespace MyGrate { + template<uint8_t size> + using SmallestUInt = std::conditional_t<size <= 8, uint8_t, + std::conditional_t<size <= 16, uint16_t, std::conditional_t<size <= 32, uint32_t, uint64_t>>>; + + template<uint8_t size> constexpr inline auto - bitslice(const std::integral auto i, uint8_t offset, uint8_t size) + bitslice(const std::integral auto i, uint8_t offset) -> SmallestUInt<size> { return (i >> offset) & ((1U << size) - 1U); } @@ -27,7 +33,8 @@ namespace MyGrate { constexpr inline auto mod100_extract(std::integral auto & i) { - const auto r {i % 100}; + using R = std::conditional_t<std::is_signed_v<decltype(i)>, int8_t, uint8_t>; + const auto r {boost::numeric_cast<R>(i % 100)}; i /= 100; return r; } diff --git a/lib/input/mysqlBindings.h b/lib/input/mysqlBindings.h index 3d1ad7f..36ef2bf 100644 --- a/lib/input/mysqlBindings.h +++ b/lib/input/mysqlBindings.h @@ -159,11 +159,15 @@ namespace MyGrate::Input { private: operator Date() const { - return Date(buf.year, buf.month, buf.day); + return Date(boost::numeric_cast<decltype(Date::year)>(buf.year), + boost::numeric_cast<decltype(Date::month)>(buf.month), + boost::numeric_cast<decltype(Date::day)>(buf.day)); } operator Time() const { - return Time(buf.hour, buf.minute, buf.second); + return Time(boost::numeric_cast<decltype(Time::hour)>(buf.hour), + boost::numeric_cast<decltype(Time::minute)>(buf.minute), + boost::numeric_cast<decltype(Time::second)>(buf.second)); } operator DateTime() const { diff --git a/lib/mysql_types.cpp b/lib/mysql_types.cpp index a4641ba..41dbb6e 100644 --- a/lib/mysql_types.cpp +++ b/lib/mysql_types.cpp @@ -16,11 +16,11 @@ namespace MyGrate::MySQL { #define INTEGER_TYPE(ET) \ typename Type<ET, false>::C Type<ET, false>::read(RawDataReader &, RawDataReader & data) \ { \ - return data.readValue<typename Type<ET>::C>(); \ + return data.readValue<typename Type<ET, false>::C>(); \ } \ typename Type<ET, true>::C Type<ET, true>::read(RawDataReader &, RawDataReader & data) \ { \ - return data.readValue<typename Type<ET>::C>(); \ + return data.readValue<typename Type<ET, true>::C>(); \ } INTEGER_TYPE(MYSQL_TYPE_TINY); INTEGER_TYPE(MYSQL_TYPE_SHORT); @@ -138,7 +138,7 @@ namespace MyGrate::MySQL { dt.hour = mod100_extract(dtint); dt.day = mod100_extract(dtint); dt.month = mod100_extract(dtint); - dt.year = dtint; + dt.year = boost::numeric_cast<decltype(dt.year)>(dtint); return dt; } @@ -149,7 +149,7 @@ namespace MyGrate::MySQL { Time t {}; t.second = mod100_extract(tint); t.minute = mod100_extract(tint); - t.hour = tint; + t.hour = boost::numeric_cast<decltype(t.hour)>(tint); return t; } @@ -164,9 +164,9 @@ namespace MyGrate::MySQL { { auto dint {data.readValue<uint32_t, 3>()}; Date d {}; - d.day = bitslice(dint, 0, 6); - d.month = bitslice(dint, 6, 4); - d.year = bitslice(dint, 10, 14); + d.day = bitslice<6>(dint, 0); + d.month = bitslice<4>(dint, 6); + d.year = bitslice<14>(dint, 10); return d; } @@ -201,12 +201,12 @@ namespace MyGrate::MySQL { std::reverse(r.b.begin(), r.b.end()); DateTime dt; - dt.year = (bitslice(r.i, 22, 17) / 13); - dt.month = (bitslice(r.i, 22, 17) % 13); - dt.day = bitslice(r.i, 17, 5); - dt.hour = bitslice(r.i, 12, 5); - dt.minute = bitslice(r.i, 6, 6); - dt.second = bitslice(r.i, 0, 6); + dt.year = boost::numeric_cast<decltype(dt.year)>(bitslice<17>(r.i, 22) / 13); + dt.month = boost::numeric_cast<decltype(dt.month)>(bitslice<17>(r.i, 22) % 13); + dt.day = bitslice<5>(r.i, 17); + dt.hour = bitslice<5>(r.i, 12); + dt.minute = bitslice<6>(r.i, 6); + dt.second = bitslice<6>(r.i, 0); return dt; } } diff --git a/lib/output/pq/pqRecordSet.cpp b/lib/output/pq/pqRecordSet.cpp index 71ddee4..e25c571 100644 --- a/lib/output/pq/pqRecordSet.cpp +++ b/lib/output/pq/pqRecordSet.cpp @@ -18,13 +18,13 @@ namespace MyGrate::Output::Pq { std::size_t PqRecordSet::rows() const { - return PQntuples(res.get()); + return boost::numeric_cast<std::size_t>(PQntuples(res.get())); } std::size_t PqRecordSet::columns() const { - return PQnfields(res.get()); + return boost::numeric_cast<std::size_t>(PQnfields(res.get())); } DbValue diff --git a/lib/output/pq/pqStmt.cpp b/lib/output/pq/pqStmt.cpp index eb3c32d..c6399e4 100644 --- a/lib/output/pq/pqStmt.cpp +++ b/lib/output/pq/pqStmt.cpp @@ -53,7 +53,7 @@ namespace MyGrate::Output::Pq { if (const auto i = c->stmts.find(q); i != c->stmts.end()) { return i->second; } - auto nam {scprintf<"pst%0x">(c->stmts.size())}; + auto nam {scprintf<"pst%0lx">(c->stmts.size())}; ResPtr res {PQprepare(c->conn.get(), nam.c_str(), q, (int)n, nullptr), PQclear}; verify<PqErr>(PQresultStatus(res.get()) == PGRES_COMMAND_OK, q, c->conn.get()); return c->stmts.emplace(q, std::move(nam)).first->second; diff --git a/lib/output/pq/writePqCopyStrm.cpp b/lib/output/pq/writePqCopyStrm.cpp index 4664e6b..984b4fd 100644 --- a/lib/output/pq/writePqCopyStrm.cpp +++ b/lib/output/pq/writePqCopyStrm.cpp @@ -56,7 +56,7 @@ namespace MyGrate::Output::Pq { return std::iscntrl(c); }); if (esc != pos) { - fwrite(pos, esc - pos, 1, out); + fwrite(pos, boost::numeric_cast<size_t>(esc - pos), 1, out); pos = esc; } while (pos != v.end() && std::iscntrl(*pos)) { @@ -77,7 +77,7 @@ namespace MyGrate::Output::Pq { static constexpr const auto hex {[] { std::array<std::array<char, 2>, 256> h {}; std::array<char, 16> hc {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'}; - for (int x {}; x < 256; x += 1) { + for (decltype(h)::size_type x {}; x < 256; x += 1) { h[x] = {hc[x >> 4], hc[x & 0xF]}; } return h; diff --git a/lib/streamSupport.cpp b/lib/streamSupport.cpp index f3c88cf..433fb83 100644 --- a/lib/streamSupport.cpp +++ b/lib/streamSupport.cpp @@ -31,7 +31,7 @@ namespace std { std::ostream & operator<<(std::ostream & s, const timespec & ts) { - return MyGrate::scprintf<"%d.%09d">(s, ts.tv_sec, ts.tv_nsec); + return MyGrate::scprintf<"%ld.%09ld">(s, ts.tv_sec, ts.tv_nsec); } std::ostream & diff --git a/test/test-postgresql.cpp b/test/test-postgresql.cpp index 727e08c..dda05ca 100644 --- a/test/test-postgresql.cpp +++ b/test/test-postgresql.cpp @@ -134,7 +134,7 @@ using FloatTypes = boost::mpl::list<float, double>; BOOST_AUTO_TEST_CASE_TEMPLATE(write_floats, T, FloatTypes) { MyGrate::Output::Pq::WritePqCopyStream c {s}; - c(T {1.1}); + c(T {1.1F}); flush(); BOOST_REQUIRE(out); |