File indexing completed on 2024-04-21 04:57:27

0001 /*
0002  * SPDX-FileCopyrightText: 2022 Kai Uwe Broulik <kde@broulik.de>
0003  * SPDX-License-Identifier: GPL-2.0-or-later
0004  */
0005 
0006 #include "afcfile.h"
0007 
0008 #include "afc_debug.h"
0009 
0010 #include "afcutils.h"
0011 
0012 using namespace KIO;
0013 
0014 AfcFile::AfcFile(const AfcClient::Ptr &client, const QString &path)
0015     : m_client(client)
0016     , m_path(path)
0017 {
0018 }
0019 
0020 AfcFile::AfcFile(AfcFile &&other) Q_DECL_NOEXCEPT : m_client(std::move(other.m_client)), m_path(other.m_path), m_handle(other.m_handle)
0021 {
0022     other.m_handle.reset();
0023 }
0024 
0025 AfcFile::~AfcFile()
0026 {
0027     if (m_handle) {
0028         close();
0029     }
0030 }
0031 
0032 AfcClient::Ptr AfcFile::client() const
0033 {
0034     return m_client;
0035 }
0036 
0037 QString AfcFile::path() const
0038 {
0039     return m_path;
0040 }
0041 
0042 WorkerResult AfcFile::open(QIODevice::OpenMode mode)
0043 {
0044     Q_ASSERT(!m_handle);
0045 
0046     afc_file_mode_t fileMode = static_cast<afc_file_mode_t>(0);
0047 
0048     if (mode == QIODevice::ReadOnly) {
0049         fileMode = AFC_FOPEN_RDONLY;
0050     } else if (mode == QIODevice::WriteOnly) {
0051         fileMode = AFC_FOPEN_WRONLY;
0052     } else if (mode == QIODevice::ReadWrite) {
0053         fileMode = AFC_FOPEN_RW;
0054     } else if (mode == (QIODevice::ReadWrite | QIODevice::Truncate)) {
0055         fileMode = AFC_FOPEN_WR;
0056     } else if (mode == QIODevice::Append || mode == (QIODevice::Append | QIODevice::WriteOnly)) {
0057         fileMode = AFC_FOPEN_APPEND;
0058     } else if (mode == (QIODevice::Append | QIODevice::ReadWrite)) {
0059         fileMode = AFC_FOPEN_RDAPPEND;
0060     }
0061 
0062     if (!fileMode) {
0063         return WorkerResult::fail(ERR_UNSUPPORTED_ACTION, QString::number(mode));
0064     }
0065 
0066     uint64_t handle = 0;
0067     const auto ret = afc_file_open(m_client->internalClient(), m_path.toLocal8Bit().constData(), fileMode, &handle);
0068 
0069     const WorkerResult result = AfcUtils::Result::from(ret);
0070     if (result.success()) {
0071         m_handle = handle;
0072     }
0073     return result;
0074 }
0075 
0076 WorkerResult AfcFile::seek(filesize_t offset)
0077 {
0078     Q_ASSERT(m_handle);
0079     const auto ret = afc_file_seek(m_client->internalClient(), m_handle.value(), offset, SEEK_SET);
0080     return AfcUtils::Result::from(ret);
0081 }
0082 
0083 WorkerResult AfcFile::truncate(filesize_t length)
0084 {
0085     Q_ASSERT(m_handle);
0086     const auto ret = afc_file_truncate(m_client->internalClient(), m_handle.value(), length);
0087     return AfcUtils::Result::from(ret);
0088 }
0089 
0090 WorkerResult AfcFile::write(const QByteArray &data, uint32_t &bytesWritten)
0091 {
0092     Q_ASSERT(m_handle);
0093     const auto ret = afc_file_write(m_client->internalClient(), m_handle.value(), data.constData(), data.size(), &bytesWritten);
0094     return AfcUtils::Result::from(ret);
0095 }
0096 
0097 WorkerResult AfcFile::close()
0098 {
0099     Q_ASSERT(m_handle);
0100 
0101     const auto ret = afc_file_close(m_client->internalClient(), m_handle.value());
0102 
0103     const WorkerResult result = AfcUtils::Result::from(ret);
0104     if (result.success()) {
0105         m_handle.reset();
0106     }
0107     return result;
0108 }
0109 
0110 AfcFileReader AfcFile::reader() const
0111 {
0112     Q_ASSERT(m_handle);
0113 
0114     AfcFileReader reader(m_client, m_handle.value());
0115     return reader;
0116 }