fix: dedupe mounts by source device for storage
This commit is contained in:
parent
ecf6c84290
commit
7a12a85b98
1 changed files with 29 additions and 8 deletions
|
|
@ -207,6 +207,18 @@ void Storage::tick() {
|
||||||
const qreal prevPercentage = percentage();
|
const qreal prevPercentage = percentage();
|
||||||
QHash<QString, Accum> byDisk;
|
QHash<QString, Accum> byDisk;
|
||||||
|
|
||||||
|
// Multiple mounts can share a single backing filesystem (btrfs subvolumes,
|
||||||
|
// bind mounts, etc.) and each one reports identical bytesTotal/bytesAvailable.
|
||||||
|
// Dedupe by source device so the filesystem only contributes once per disk.
|
||||||
|
struct DeviceEntry {
|
||||||
|
quint64 totalBytes = 0;
|
||||||
|
quint64 usedBytes = 0;
|
||||||
|
bool hasRoot = false;
|
||||||
|
QByteArray device;
|
||||||
|
};
|
||||||
|
|
||||||
|
QHash<QByteArray, DeviceEntry> byDevice;
|
||||||
|
|
||||||
const auto mountedVols = QStorageInfo::mountedVolumes();
|
const auto mountedVols = QStorageInfo::mountedVolumes();
|
||||||
for (const QStorageInfo& v : mountedVols) {
|
for (const QStorageInfo& v : mountedVols) {
|
||||||
if (!v.isReady() || !v.isValid() || v.bytesTotal() <= 0) {
|
if (!v.isReady() || !v.isValid() || v.bytesTotal() <= 0) {
|
||||||
|
|
@ -216,24 +228,33 @@ void Storage::tick() {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
const QStringList disks = resolveToPhysicalDisks(QString::fromLocal8Bit(v.device()));
|
const QByteArray device = v.device();
|
||||||
if (disks.isEmpty()) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
const auto totalBytes = static_cast<quint64>(v.bytesTotal());
|
const auto totalBytes = static_cast<quint64>(v.bytesTotal());
|
||||||
const auto availBytes = static_cast<quint64>(v.bytesAvailable());
|
const auto availBytes = static_cast<quint64>(v.bytesAvailable());
|
||||||
const quint64 usedBytes = totalBytes > availBytes ? totalBytes - availBytes : 0;
|
const quint64 usedBytes = totalBytes > availBytes ? totalBytes - availBytes : 0;
|
||||||
const bool isRoot = v.rootPath() == QStringLiteral("/");
|
const bool isRoot = v.rootPath() == QStringLiteral("/");
|
||||||
|
|
||||||
|
DeviceEntry& e = byDevice[device];
|
||||||
|
e.device = device;
|
||||||
|
e.totalBytes = totalBytes;
|
||||||
|
e.usedBytes = usedBytes;
|
||||||
|
e.hasRoot = e.hasRoot || isRoot;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (auto it = byDevice.constBegin(); it != byDevice.constEnd(); ++it) {
|
||||||
|
const DeviceEntry& e = it.value();
|
||||||
|
const QStringList disks = resolveToPhysicalDisks(QString::fromLocal8Bit(e.device));
|
||||||
|
if (disks.isEmpty()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
for (const QString& d : disks) {
|
for (const QString& d : disks) {
|
||||||
if (d.startsWith(QStringLiteral("zram"))) {
|
if (d.startsWith(QStringLiteral("zram"))) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
Accum& a = byDisk[d];
|
Accum& a = byDisk[d];
|
||||||
a.usedBytes += usedBytes;
|
a.usedBytes += e.usedBytes;
|
||||||
a.totalBytes += totalBytes;
|
a.totalBytes += e.totalBytes;
|
||||||
a.hasRoot = a.hasRoot || isRoot;
|
a.hasRoot = a.hasRoot || e.hasRoot;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue