Line data Source code
1 : /*
2 : * SPDX-License-Identifier: GPL-3.0-only
3 : * MuseScore-CLA-applies
4 : *
5 : * MuseScore Studio
6 : * Music Composition & Notation
7 : *
8 : * Copyright (C) 2026 MuseScore Limited and others
9 : *
10 : * This program is free software: you can redistribute it and/or modify
11 : * it under the terms of the GNU General Public License version 3 as
12 : * published by the Free Software Foundation.
13 : *
14 : * This program is distributed in the hope that it will be useful,
15 : * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 : * GNU General Public License for more details.
18 : *
19 : * You should have received a copy of the GNU General Public License
20 : * along with this program. If not, see <https://www.gnu.org/licenses/>.
21 : */
22 : #include "filestream.h"
23 :
24 : #include "ioretcodes.h"
25 :
26 : #include "log.h"
27 :
28 : using namespace muse;
29 : using namespace muse::io;
30 :
31 40 : FileStream::FileStream(const path_t& filePath)
32 40 : : m_filePath(filePath)
33 : {
34 40 : }
35 :
36 40 : FileStream::~FileStream()
37 : {
38 40 : closeStream();
39 40 : }
40 :
41 15 : void FileStream::doClose()
42 : {
43 15 : Ret ret = closeStream();
44 15 : if (!ret) {
45 0 : setError(ret.code(), ret.text());
46 : }
47 15 : }
48 :
49 81 : Ret FileStream::closeStream()
50 : {
51 81 : if (m_streamId == INVALID_STREAM_ID) {
52 56 : return make_ok();
53 : }
54 :
55 25 : Ret ret = fileSystem()->closeStream(m_streamId);
56 25 : m_streamId = INVALID_STREAM_ID;
57 25 : return ret;
58 25 : }
59 :
60 0 : const path_t& FileStream::filePath() const
61 : {
62 0 : return m_filePath;
63 : }
64 :
65 26 : bool FileStream::doOpen(OpenMode m)
66 : {
67 26 : closeStream();
68 :
69 : io::OpenMode fsMode;
70 26 : switch (m) {
71 23 : case OpenMode::WriteOnly:
72 23 : fsMode = io::OpenMode::WriteOnly;
73 23 : m_size = 0;
74 23 : break;
75 3 : case OpenMode::Append: {
76 3 : fsMode = io::OpenMode::Append;
77 3 : RetVal<uint64_t> sz = fileSystem()->fileSize(m_filePath);
78 3 : m_size = sz.ret ? static_cast<size_t>(sz.val) : 0;
79 3 : break;
80 3 : }
81 0 : default:
82 0 : setError(int(Err::FSWriteError), "FileStream supports only WriteOnly and Append modes");
83 0 : return false;
84 : }
85 :
86 52 : RetVal<StreamId> rv = fileSystem()->openStream(m_filePath, fsMode);
87 26 : if (!rv.ret) {
88 1 : setError(rv.ret.code(), rv.ret.text());
89 1 : return false;
90 : }
91 :
92 25 : m_streamId = rv.val;
93 25 : m_expectedPos = m_size;
94 25 : return true;
95 : }
96 :
97 31 : size_t FileStream::dataSize() const
98 : {
99 31 : return m_size;
100 : }
101 :
102 0 : const uint8_t* FileStream::rawData() const
103 : {
104 0 : return nullptr;
105 : }
106 :
107 23 : bool FileStream::resizeData(size_t size)
108 : {
109 23 : m_size = size;
110 23 : return true;
111 : }
112 :
113 23 : size_t FileStream::writeData(const uint8_t* data, size_t len)
114 : {
115 23 : IF_ASSERT_FAILED(m_streamId != INVALID_STREAM_ID) {
116 0 : return 0;
117 : }
118 :
119 23 : uint64_t offset = (pos() == m_expectedPos) ? STREAM_POS_CURRENT : static_cast<uint64_t>(pos());
120 :
121 23 : Ret ret = fileSystem()->writeToStream(m_streamId, ByteArray::fromRawData(data, len), offset);
122 23 : if (!ret) {
123 0 : setError(ret.code(), ret.text());
124 0 : return 0;
125 : }
126 :
127 23 : m_expectedPos = pos() + len;
128 23 : return len;
129 23 : }
|