File indexing completed on 2024-06-09 04:00:37

0001 /*
0002     SPDX-FileCopyrightText: 2010 Mario Bensi <mbensi@ipsquad.net>
0003 
0004     SPDX-License-Identifier: LGPL-2.1-only OR LGPL-3.0-only OR LicenseRef-KDE-Accepted-LGPL
0005 */
0006 
0007 #include "fstabmanager.h"
0008 #include "../shared/rootdevice.h"
0009 #include "fstab_debug.h"
0010 #include "fstabdevice.h"
0011 #include "fstabhandling.h"
0012 #include "fstabservice.h"
0013 #include "fstabwatcher.h"
0014 
0015 using namespace Solid::Backends::Fstab;
0016 using namespace Solid::Backends::Shared;
0017 
0018 FstabManager::FstabManager(QObject *parent)
0019     : Solid::Ifaces::DeviceManager(parent)
0020     , m_deviceList(FstabHandling::deviceList())
0021 {
0022     m_supportedInterfaces << Solid::DeviceInterface::StorageAccess;
0023     m_supportedInterfaces << Solid::DeviceInterface::NetworkShare;
0024 
0025     connect(FstabWatcher::instance(), &FstabWatcher::fstabChanged, this, &FstabManager::onFstabChanged);
0026     connect(FstabWatcher::instance(), &FstabWatcher::mtabChanged, this, &FstabManager::onMtabChanged);
0027 }
0028 
0029 QString FstabManager::udiPrefix() const
0030 {
0031     return QString::fromLatin1(FSTAB_UDI_PREFIX);
0032 }
0033 
0034 QSet<Solid::DeviceInterface::Type> FstabManager::supportedInterfaces() const
0035 {
0036     return m_supportedInterfaces;
0037 }
0038 
0039 QStringList FstabManager::allDevices()
0040 {
0041     QStringList result;
0042 
0043     result << udiPrefix();
0044     for (const QString &device : std::as_const(m_deviceList)) {
0045         result << udiPrefix() + "/" + device;
0046     }
0047 
0048     return result;
0049 }
0050 
0051 QStringList FstabManager::devicesFromQuery(const QString &parentUdi, Solid::DeviceInterface::Type type)
0052 {
0053     if ((parentUdi == udiPrefix()) || parentUdi.isEmpty()) {
0054         QStringList result;
0055         if (type == Solid::DeviceInterface::StorageAccess) {
0056             for (const QString &device : std::as_const(m_deviceList)) {
0057                 result << udiPrefix() + "/" + device;
0058             }
0059             return result;
0060         } else if (type == Solid::DeviceInterface::NetworkShare) {
0061             for (const QString &device : std::as_const(m_deviceList)) {
0062                 result << udiPrefix() + "/" + device;
0063             }
0064             return result;
0065         }
0066     } else {
0067         if (type == Solid::DeviceInterface::StorageAccess || type == Solid::DeviceInterface::NetworkShare) {
0068             return QStringList{parentUdi};
0069         }
0070     }
0071 
0072     return QStringList();
0073 }
0074 
0075 QObject *FstabManager::createDevice(const QString &udi)
0076 {
0077     if (udi == udiPrefix()) {
0078         RootDevice *root = new RootDevice(FSTAB_UDI_PREFIX);
0079 
0080         root->setProduct(tr("Filesystem Volumes"));
0081         root->setDescription(tr("Mountable filesystems declared in your system"));
0082         root->setIcon("folder");
0083 
0084         return root;
0085 
0086     } else {
0087         // global device manager makes sure udi starts with udi prefix + '/'
0088         QString internalName = udi.mid(udiPrefix().length() + 1, -1);
0089         if (!m_deviceList.contains(internalName)) {
0090             return nullptr;
0091         }
0092 
0093         FstabDevice *device = new FstabDevice(udi);
0094         connect(this, &FstabManager::mtabChanged, device, &FstabDevice::onMtabChanged);
0095         return device;
0096     }
0097 }
0098 
0099 void FstabManager::onFstabChanged()
0100 {
0101     FstabHandling::flushFstabCache();
0102     _k_updateDeviceList();
0103 }
0104 
0105 void FstabManager::_k_updateDeviceList()
0106 {
0107     const QStringList deviceList = FstabHandling::deviceList();
0108     const QSet<QString> newlist(deviceList.begin(), deviceList.end());
0109     const QSet<QString> oldlist(m_deviceList.begin(), m_deviceList.end());
0110 
0111     m_deviceList = deviceList;
0112 
0113     qCDebug(FSTAB_LOG) << oldlist << "->" << newlist;
0114 
0115     for (const QString &device : newlist) {
0116         if (!oldlist.contains(device)) {
0117             Q_EMIT deviceAdded(udiPrefix() + "/" + device);
0118         }
0119     }
0120 
0121     for (const QString &device : oldlist) {
0122         if (!newlist.contains(device)) {
0123             Q_EMIT deviceRemoved(udiPrefix() + "/" + device);
0124         }
0125     }
0126 }
0127 
0128 void FstabManager::onMtabChanged()
0129 {
0130     FstabHandling::flushMtabCache();
0131 
0132     _k_updateDeviceList(); // devicelist is union of mtab and fstab
0133 
0134     for (const QString &device : std::as_const(m_deviceList)) {
0135         // notify storageaccess objects via device ...
0136         Q_EMIT mtabChanged(device);
0137     }
0138 }
0139 
0140 FstabManager::~FstabManager()
0141 {
0142 }
0143 
0144 #include "moc_fstabmanager.cpp"