From f875f0f0120ed158d7138fdf3a8eb8d6e5593516 Mon Sep 17 00:00:00 2001 From: eelke Date: Mon, 4 Nov 2019 18:02:48 +0100 Subject: [PATCH] Implementation, tests and first use of rangechecked_cast --- .gitignore | 2 ++ common.pri | 1 + core/BackupFormatModel.cpp | 8 ++--- core/ExplainTreeModelItem.cpp | 3 +- core/core.pro | 1 + core/rangechecked_cast.h | 15 ++++++++++ tests/pglabtests/pglabtests.pro | 1 + tests/pglabtests/tst_rangechecked_cast.cpp | 35 ++++++++++++++++++++++ 8 files changed, 61 insertions(+), 5 deletions(-) create mode 100644 core/rangechecked_cast.h create mode 100644 tests/pglabtests/tst_rangechecked_cast.cpp diff --git a/.gitignore b/.gitignore index 7f98342..bf62961 100644 --- a/.gitignore +++ b/.gitignore @@ -4,6 +4,8 @@ build/* .kdev4/* local.pri DIST/ +DIST32/ +DIST64/ *.autosave srcdoc/ pglabAll.pro.user.4.8-pre1 diff --git a/common.pri b/common.pri index 3232773..9513af1 100644 --- a/common.pri +++ b/common.pri @@ -12,4 +12,5 @@ QMAKE_CXXFLAGS += /std:c++17 # depend on your compiler). Please consult the documentation of the # deprecated API in order to know how to port your code away from it. DEFINES += QT_DEPRECATED_WARNINGS +DEFINES += BOOST_ENABLE_ASSERT_HANDLER DEFINES += WIN32_LEAN_AND_MEAN NOMINMAX _WIN32_WINNT=0x0501 diff --git a/core/BackupFormatModel.cpp b/core/BackupFormatModel.cpp index 639b337..4ea073c 100644 --- a/core/BackupFormatModel.cpp +++ b/core/BackupFormatModel.cpp @@ -1,5 +1,5 @@ #include "BackupFormatModel.h" - +#include "rangechecked_cast.h" #include namespace { @@ -61,7 +61,7 @@ BackupFormatModel::BackupFormatModel(QObject *parent) int BackupFormatModel::rowCount(const QModelIndex &) const { - int size = g_BackupFormats.size(); + int size = rangechecked_cast(g_BackupFormats.size()); return size; } @@ -79,7 +79,7 @@ QVariant BackupFormatModel::data(const QModelIndex &index, int role) const const int col = index.column(); if (role == Qt::DisplayRole) { - const auto &item = g_BackupFormats.at(row); + const auto &item = g_BackupFormats.at(rangechecked_cast(row)); switch (col) { case ColumnShort: result = item.shortFlag; @@ -93,7 +93,7 @@ QVariant BackupFormatModel::data(const QModelIndex &index, int role) const } } else if (role == Qt::ToolTipRole) { - const auto &item = g_BackupFormats.at(row); + const auto &item = g_BackupFormats.at(rangechecked_cast(row)); result = item.description; } } diff --git a/core/ExplainTreeModelItem.cpp b/core/ExplainTreeModelItem.cpp index 035c671..ef5344b 100644 --- a/core/ExplainTreeModelItem.cpp +++ b/core/ExplainTreeModelItem.cpp @@ -1,5 +1,6 @@ #include "ExplainTreeModelItem.h" #include "json/json.h" +#include "rangechecked_cast.h" #include namespace { @@ -110,7 +111,7 @@ ExplainTreeModelItemPtr ExplainTreeModelItem::child(int row) int ExplainTreeModelItem::childCount() const { - return m_childItems.size(); + return rangechecked_cast(m_childItems.size()); } //int ExplainTreeModelItem::columnCount() const diff --git a/core/core.pro b/core/core.pro index ab3d990..fa842c8 100644 --- a/core/core.pro +++ b/core/core.pro @@ -56,6 +56,7 @@ HEADERS += PasswordManager.h \ SqlAstSelectListEntry.h \ SqlAstSelect.h \ SqlAstExpression.h \ + rangechecked_cast.h \ std_utils.h \ IntegerRange.h diff --git a/core/rangechecked_cast.h b/core/rangechecked_cast.h new file mode 100644 index 0000000..1188d57 --- /dev/null +++ b/core/rangechecked_cast.h @@ -0,0 +1,15 @@ +#ifndef RANGECHECKED_CAST_H +#define RANGECHECKED_CAST_H + +#include +#include + +template +To rangechecked_cast(From f) +{ + BOOST_ASSERT(f > std::numeric_limits::lowest()); + BOOST_ASSERT(f < std::numeric_limits::max()); + return static_cast(f); +} + +#endif // RANGECHECKED_CAST_H diff --git a/tests/pglabtests/pglabtests.pro b/tests/pglabtests/pglabtests.pro index 73c4847..d58e4b8 100644 --- a/tests/pglabtests/pglabtests.pro +++ b/tests/pglabtests/pglabtests.pro @@ -20,6 +20,7 @@ SOURCES += main.cpp \ tst_escapeConnectionStringValue.cpp \ tst_expected.cpp \ tst_SqlLexer.cpp \ + tst_rangechecked_cast.cpp \ tst_scopeguard.cpp \ tst_CsvWriter.cpp \ tst_PasswordManager.cpp \ diff --git a/tests/pglabtests/tst_rangechecked_cast.cpp b/tests/pglabtests/tst_rangechecked_cast.cpp new file mode 100644 index 0000000..7ea2460 --- /dev/null +++ b/tests/pglabtests/tst_rangechecked_cast.cpp @@ -0,0 +1,35 @@ +#include +#include +#include "rangechecked_cast.h" +#include "PrintTo_Qt.h" + +using namespace testing; + + +TEST(rangechecked_cast, in_range) +{ + ASSERT_NO_THROW({ + int8_t in = 42; + int expected = 42; + auto output = rangechecked_cast(in); + ASSERT_EQ(output, expected); + }); +} + +TEST(rangechecked_cast, above_max) +{ + int64_t in = std::numeric_limits::max() + static_cast(1); + ASSERT_THROW({ + rangechecked_cast(in); + }, + std::runtime_error); +} + +TEST(rangechecked_cast, below_lowest) +{ + int64_t in = std::numeric_limits::lowest() - static_cast(1); + ASSERT_THROW({ + rangechecked_cast(in); + }, + std::runtime_error); +}