Inside Bitcoin
Opening the selected file…
Inside Bitcoin
Opening the selected file…
The code behind the network, with room to understand it.
Release published 2026-10-28 · Snapshot fetched 2026-11-01. Latest stable release at fetch time; development branches and Git history are excluded. Only the selected code window and visible folders load here.
1// Copyright (c) 2011-present The Bitcoin Core developers2// Distributed under the MIT software license, see the accompanying3// file COPYING or http://www.opensource.org/licenses/mit-license.php.5#include <qt/bantablemodel.h>7#include <interfaces/node.h>8#include <net_types.h>10#include <utility>12#include <QDateTime>13#include <QList>14#include <QLocale>15#include <QModelIndex>16#include <QVariant>18bool BannedNodeLessThan::operator()(const CCombinedBan& left, const CCombinedBan& right) const19{20const CCombinedBan* pLeft = &left;21const CCombinedBan* pRight = &right;23if (order == Qt::DescendingOrder)24std::swap(pLeft, pRight);26switch (static_cast<BanTableModel::ColumnIndex>(column)) {27case BanTableModel::Address:28return pLeft->subnet.ToString().compare(pRight->subnet.ToString()) < 0;29case BanTableModel::Bantime:30return pLeft->banEntry.nBanUntil < pRight->banEntry.nBanUntil;31} // no default case, so the compiler can warn about missing cases32assert(false);33}35// private implementation36class BanTablePriv37{38public:39/** Local cache of peer information */40QList<CCombinedBan> cachedBanlist;41/** Column to sort nodes by (default to unsorted) */42int sortColumn{-1};43/** Order (ascending or descending) to sort nodes by */44Qt::SortOrder sortOrder;46/** Pull a full list of banned nodes from interfaces::Node into our cache */47void refreshBanlist(interfaces::Node& node)48{49banmap_t banMap;50node.getBanned(banMap);52cachedBanlist.clear();53cachedBanlist.reserve(banMap.size());54for (const auto& entry : banMap)55{56CCombinedBan banEntry;57banEntry.subnet = entry.first;58banEntry.banEntry = entry.second;59cachedBanlist.append(banEntry);60}62if (sortColumn >= 0)63// sort cachedBanlist (use stable sort to prevent rows jumping around unnecessarily)64std::stable_sort(cachedBanlist.begin(), cachedBanlist.end(), BannedNodeLessThan(sortColumn, sortOrder));65}67int size() const68{69return cachedBanlist.size();70}72CCombinedBan *index(int idx)73{74if (idx >= 0 && idx < cachedBanlist.size())75return &cachedBanlist[idx];77return nullptr;78}79};81BanTableModel::BanTableModel(interfaces::Node& node, QObject* parent) :82QAbstractTableModel(parent),83m_node(node)84{85columns << tr("IP/Netmask") << tr("Banned Until");86priv.reset(new BanTablePriv());88// load initial data89refresh();90}92BanTableModel::~BanTableModel() = default;94int BanTableModel::rowCount(const QModelIndex &parent) const95{96if (parent.isValid()) {97return 0;98}99return priv->size();100}102int BanTableModel::columnCount(const QModelIndex &parent) const103{104if (parent.isValid()) {105return 0;106}107return columns.length();108}110QVariant BanTableModel::data(const QModelIndex &index, int role) const111{112if(!index.isValid())113return QVariant();115CCombinedBan *rec = static_cast<CCombinedBan*>(index.internalPointer());117const auto column = static_cast<ColumnIndex>(index.column());118if (role == Qt::DisplayRole) {119switch (column) {120case Address:121return QString::fromStdString(rec->subnet.ToString());122case Bantime:123QDateTime date = QDateTime::fromMSecsSinceEpoch(0);124date = date.addSecs(rec->banEntry.nBanUntil);125return QLocale::system().toString(date, QLocale::LongFormat);126} // no default case, so the compiler can warn about missing cases127assert(false);128}130return QVariant();131}133QVariant BanTableModel::headerData(int section, Qt::Orientation orientation, int role) const134{135if(orientation == Qt::Horizontal)136{137if(role == Qt::DisplayRole && section < columns.size())138{139return columns[section];140}141}142return QVariant();143}145Qt::ItemFlags BanTableModel::flags(const QModelIndex &index) const146{147if (!index.isValid()) return Qt::NoItemFlags;149Qt::ItemFlags retval = Qt::ItemIsSelectable | Qt::ItemIsEnabled;150return retval;151}153QModelIndex BanTableModel::index(int row, int column, const QModelIndex &parent) const154{155Q_UNUSED(parent);156CCombinedBan *data = priv->index(row);158if (data)159return createIndex(row, column, data);160return QModelIndex();161}163void BanTableModel::refresh()164{165Q_EMIT layoutAboutToBeChanged();166priv->refreshBanlist(m_node);167Q_EMIT layoutChanged();168}170void BanTableModel::sort(int column, Qt::SortOrder order)171{172priv->sortColumn = column;173priv->sortOrder = order;174refresh();175}177bool BanTableModel::shouldShow()178{179return priv->size() > 0;180}182bool BanTableModel::unban(const QModelIndex& index)183{184CCombinedBan* ban{static_cast<CCombinedBan*>(index.internalPointer())};185return ban != nullptr && m_node.unban(ban->subnet);186}
Independent explanations by MyBitcoinExplorer. Not affiliated with or endorsed by Bitcoin Core. Guides are educational and do not replace the source or its tests.
Bitcoin Core source © its contributors, distributed under the MIT license. Original notices and bundled third-party licenses are retained in the source tree.