mirror of
https://github.com/RGBCube/serenity
synced 2025-07-25 22:57:44 +00:00
Kernel: Make File::write() and File::read() return KResultOr<size_t>
Instead of returning a ssize_t where negative values mean error, we now return KResultOr<size_t> and use the error state to report errors exclusively.
This commit is contained in:
parent
58feebeed2
commit
7a3ab6c517
58 changed files with 223 additions and 229 deletions
|
@ -132,9 +132,9 @@ bool BlockBasedFS::write_block(unsigned index, const u8* data, size_t count, siz
|
|||
u32 base_offset = static_cast<u32>(index) * static_cast<u32>(block_size()) + offset;
|
||||
file_description().seek(base_offset, SEEK_SET);
|
||||
auto nwritten = file_description().write(data, count);
|
||||
if (nwritten < 0)
|
||||
if (nwritten.is_error())
|
||||
return false;
|
||||
ASSERT(static_cast<size_t>(nwritten) == count);
|
||||
ASSERT(nwritten.value() == count);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -156,7 +156,8 @@ bool BlockBasedFS::raw_read(unsigned index, u8* buffer)
|
|||
u32 base_offset = static_cast<u32>(index) * static_cast<u32>(m_logical_block_size);
|
||||
file_description().seek(base_offset, SEEK_SET);
|
||||
auto nread = file_description().read(buffer, m_logical_block_size);
|
||||
ASSERT((size_t)nread == m_logical_block_size);
|
||||
ASSERT(!nread.is_error());
|
||||
ASSERT(nread.value() == m_logical_block_size);
|
||||
return true;
|
||||
}
|
||||
bool BlockBasedFS::raw_write(unsigned index, const u8* buffer)
|
||||
|
@ -164,7 +165,8 @@ bool BlockBasedFS::raw_write(unsigned index, const u8* buffer)
|
|||
u32 base_offset = static_cast<u32>(index) * static_cast<u32>(m_logical_block_size);
|
||||
file_description().seek(base_offset, SEEK_SET);
|
||||
auto nwritten = file_description().write(buffer, m_logical_block_size);
|
||||
ASSERT((size_t)nwritten == m_logical_block_size);
|
||||
ASSERT(!nwritten.is_error());
|
||||
ASSERT(nwritten.value() == m_logical_block_size);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -211,9 +213,9 @@ bool BlockBasedFS::read_block(unsigned index, u8* buffer, size_t count, size_t o
|
|||
u32 base_offset = static_cast<u32>(index) * static_cast<u32>(block_size()) + static_cast<u32>(offset);
|
||||
file_description().seek(base_offset, SEEK_SET);
|
||||
auto nread = file_description().read(buffer, count);
|
||||
if (nread < 0)
|
||||
if (nread.is_error())
|
||||
return false;
|
||||
ASSERT(static_cast<size_t>(nread) == count);
|
||||
ASSERT(nread.value() == count);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -222,9 +224,9 @@ bool BlockBasedFS::read_block(unsigned index, u8* buffer, size_t count, size_t o
|
|||
u32 base_offset = static_cast<u32>(index) * static_cast<u32>(block_size());
|
||||
file_description().seek(base_offset, SEEK_SET);
|
||||
auto nread = file_description().read(entry.data, block_size());
|
||||
if (nread < 0)
|
||||
if (nread.is_error())
|
||||
return false;
|
||||
ASSERT(static_cast<size_t>(nread) == block_size());
|
||||
ASSERT(nread.value() == block_size());
|
||||
entry.has_data = true;
|
||||
}
|
||||
if (buffer)
|
||||
|
|
|
@ -145,29 +145,19 @@ bool FIFO::can_write(const FileDescription&, size_t) const
|
|||
return m_buffer.space_for_writing() || !m_readers;
|
||||
}
|
||||
|
||||
ssize_t FIFO::read(FileDescription&, size_t, u8* buffer, ssize_t size)
|
||||
KResultOr<size_t> FIFO::read(FileDescription&, size_t, u8* buffer, size_t size)
|
||||
{
|
||||
if (!m_writers && m_buffer.is_empty())
|
||||
return 0;
|
||||
#ifdef FIFO_DEBUG
|
||||
dbg() << "fifo: read(" << size << ")\n";
|
||||
#endif
|
||||
ssize_t nread = m_buffer.read(buffer, size);
|
||||
#ifdef FIFO_DEBUG
|
||||
dbg() << " -> read (" << String::format("%c", buffer[0]) << ") " << nread;
|
||||
#endif
|
||||
return nread;
|
||||
return m_buffer.read(buffer, size);
|
||||
}
|
||||
|
||||
ssize_t FIFO::write(FileDescription&, size_t, const u8* buffer, ssize_t size)
|
||||
KResultOr<size_t> FIFO::write(FileDescription&, size_t, const u8* buffer, size_t size)
|
||||
{
|
||||
if (!m_readers) {
|
||||
Thread::current()->send_signal(SIGPIPE, Process::current());
|
||||
return -EPIPE;
|
||||
}
|
||||
#ifdef FIFO_DEBUG
|
||||
dbg() << "fifo: write(" << (const void*)buffer << ", " << size << ")";
|
||||
#endif
|
||||
return m_buffer.write(buffer, size);
|
||||
}
|
||||
|
||||
|
|
|
@ -57,8 +57,8 @@ public:
|
|||
|
||||
private:
|
||||
// ^File
|
||||
virtual ssize_t write(FileDescription&, size_t, const u8*, ssize_t) override;
|
||||
virtual ssize_t read(FileDescription&, size_t, u8*, ssize_t) override;
|
||||
virtual KResultOr<size_t> write(FileDescription&, size_t, const u8*, size_t) override;
|
||||
virtual KResultOr<size_t> read(FileDescription&, size_t, u8*, size_t) override;
|
||||
virtual bool can_read(const FileDescription&, size_t) const override;
|
||||
virtual bool can_write(const FileDescription&, size_t) const override;
|
||||
virtual String absolute_path(const FileDescription&) const override;
|
||||
|
|
|
@ -74,8 +74,8 @@ public:
|
|||
virtual bool can_read(const FileDescription&, size_t) const = 0;
|
||||
virtual bool can_write(const FileDescription&, size_t) const = 0;
|
||||
|
||||
virtual ssize_t read(FileDescription&, size_t, u8*, ssize_t) = 0;
|
||||
virtual ssize_t write(FileDescription&, size_t, const u8*, ssize_t) = 0;
|
||||
virtual KResultOr<size_t> read(FileDescription&, size_t, u8*, size_t) = 0;
|
||||
virtual KResultOr<size_t> write(FileDescription&, size_t, const u8*, size_t) = 0;
|
||||
virtual int ioctl(FileDescription&, unsigned request, FlatPtr arg);
|
||||
virtual KResultOr<Region*> mmap(Process&, FileDescription&, VirtualAddress preferred_vaddr, size_t offset, size_t size, int prot, bool shared);
|
||||
|
||||
|
|
|
@ -124,28 +124,32 @@ off_t FileDescription::seek(off_t offset, int whence)
|
|||
return m_current_offset;
|
||||
}
|
||||
|
||||
ssize_t FileDescription::read(u8* buffer, ssize_t count)
|
||||
KResultOr<size_t> FileDescription::read(u8* buffer, size_t count)
|
||||
{
|
||||
LOCKER(m_lock);
|
||||
if ((m_current_offset + count) < 0)
|
||||
Checked<size_t> new_offset = m_current_offset;
|
||||
new_offset += count;
|
||||
if (new_offset.has_overflow())
|
||||
return -EOVERFLOW;
|
||||
SmapDisabler disabler;
|
||||
int nread = m_file->read(*this, offset(), buffer, count);
|
||||
if (nread > 0 && m_file->is_seekable())
|
||||
m_current_offset += nread;
|
||||
return nread;
|
||||
auto nread_or_error = m_file->read(*this, offset(), buffer, count);
|
||||
if (!nread_or_error.is_error() && m_file->is_seekable())
|
||||
m_current_offset += nread_or_error.value();
|
||||
return nread_or_error;
|
||||
}
|
||||
|
||||
ssize_t FileDescription::write(const u8* data, ssize_t size)
|
||||
KResultOr<size_t> FileDescription::write(const u8* data, size_t size)
|
||||
{
|
||||
LOCKER(m_lock);
|
||||
if ((m_current_offset + size) < 0)
|
||||
Checked<size_t> new_offset = m_current_offset;
|
||||
new_offset += size;
|
||||
if (new_offset.has_overflow())
|
||||
return -EOVERFLOW;
|
||||
SmapDisabler disabler;
|
||||
int nwritten = m_file->write(*this, offset(), data, size);
|
||||
if (nwritten > 0 && m_file->is_seekable())
|
||||
m_current_offset += nwritten;
|
||||
return nwritten;
|
||||
auto nwritten_or_error = m_file->write(*this, offset(), data, size);
|
||||
if (!nwritten_or_error.is_error() && m_file->is_seekable())
|
||||
m_current_offset += nwritten_or_error.value();
|
||||
return nwritten_or_error;
|
||||
}
|
||||
|
||||
bool FileDescription::can_write() const
|
||||
|
|
|
@ -60,8 +60,8 @@ public:
|
|||
KResult close();
|
||||
|
||||
off_t seek(off_t, int whence);
|
||||
ssize_t read(u8*, ssize_t);
|
||||
ssize_t write(const u8* data, ssize_t);
|
||||
KResultOr<size_t> read(u8*, size_t);
|
||||
KResultOr<size_t> write(const u8* data, size_t);
|
||||
KResult fstat(stat&);
|
||||
|
||||
KResult chmod(mode_t);
|
||||
|
|
|
@ -44,21 +44,25 @@ InodeFile::~InodeFile()
|
|||
{
|
||||
}
|
||||
|
||||
ssize_t InodeFile::read(FileDescription& description, size_t offset, u8* buffer, ssize_t count)
|
||||
KResultOr<size_t> InodeFile::read(FileDescription& description, size_t offset, u8* buffer, size_t count)
|
||||
{
|
||||
ssize_t nread = m_inode->read_bytes(offset, count, buffer, &description);
|
||||
if (nread > 0)
|
||||
Thread::current()->did_file_read(nread);
|
||||
if (nread < 0)
|
||||
return KResult(nread);
|
||||
return nread;
|
||||
}
|
||||
|
||||
ssize_t InodeFile::write(FileDescription& description, size_t offset, const u8* data, ssize_t count)
|
||||
KResultOr<size_t> InodeFile::write(FileDescription& description, size_t offset, const u8* data, size_t count)
|
||||
{
|
||||
ssize_t nwritten = m_inode->write_bytes(offset, count, data, &description);
|
||||
if (nwritten > 0) {
|
||||
m_inode->set_mtime(kgettimeofday().tv_sec);
|
||||
Thread::current()->did_file_write(nwritten);
|
||||
}
|
||||
if (nwritten < 0)
|
||||
return KResult(nwritten);
|
||||
return nwritten;
|
||||
}
|
||||
|
||||
|
|
|
@ -47,8 +47,8 @@ public:
|
|||
virtual bool can_read(const FileDescription&, size_t) const override { return true; }
|
||||
virtual bool can_write(const FileDescription&, size_t) const override { return true; }
|
||||
|
||||
virtual ssize_t read(FileDescription&, size_t, u8*, ssize_t) override;
|
||||
virtual ssize_t write(FileDescription&, size_t, const u8*, ssize_t) override;
|
||||
virtual KResultOr<size_t> read(FileDescription&, size_t, u8*, size_t) override;
|
||||
virtual KResultOr<size_t> write(FileDescription&, size_t, const u8*, size_t) override;
|
||||
virtual KResultOr<Region*> mmap(Process&, FileDescription&, VirtualAddress preferred_vaddr, size_t offset, size_t size, int prot, bool shared) override;
|
||||
|
||||
virtual String absolute_path(const FileDescription&) const override;
|
||||
|
|
|
@ -57,7 +57,7 @@ bool InodeWatcher::can_write(const FileDescription&, size_t) const
|
|||
return true;
|
||||
}
|
||||
|
||||
ssize_t InodeWatcher::read(FileDescription&, size_t, u8* buffer, ssize_t buffer_size)
|
||||
KResultOr<size_t> InodeWatcher::read(FileDescription&, size_t, u8* buffer, size_t buffer_size)
|
||||
{
|
||||
LOCKER(m_lock);
|
||||
ASSERT(!m_queue.is_empty() || !m_inode);
|
||||
|
@ -72,9 +72,9 @@ ssize_t InodeWatcher::read(FileDescription&, size_t, u8* buffer, ssize_t buffer_
|
|||
return sizeof(event);
|
||||
}
|
||||
|
||||
ssize_t InodeWatcher::write(FileDescription&, size_t, const u8*, ssize_t)
|
||||
KResultOr<size_t> InodeWatcher::write(FileDescription&, size_t, const u8*, size_t)
|
||||
{
|
||||
return -EIO;
|
||||
return KResult(-EIO);
|
||||
}
|
||||
|
||||
String InodeWatcher::absolute_path(const FileDescription&) const
|
||||
|
|
|
@ -55,8 +55,8 @@ public:
|
|||
|
||||
virtual bool can_read(const FileDescription&, size_t) const override;
|
||||
virtual bool can_write(const FileDescription&, size_t) const override;
|
||||
virtual ssize_t read(FileDescription&, size_t, u8*, ssize_t) override;
|
||||
virtual ssize_t write(FileDescription&, size_t, const u8*, ssize_t) override;
|
||||
virtual KResultOr<size_t> read(FileDescription&, size_t, u8*, size_t) override;
|
||||
virtual KResultOr<size_t> write(FileDescription&, size_t, const u8*, size_t) override;
|
||||
virtual String absolute_path(const FileDescription&) const override;
|
||||
virtual const char* class_name() const override { return "InodeWatcher"; };
|
||||
|
||||
|
|
|
@ -426,9 +426,10 @@ KResult Plan9FS::post_message(Message& message)
|
|||
if (Thread::current()->block<Thread::WriteBlocker>(nullptr, description).was_interrupted())
|
||||
return KResult(-EINTR);
|
||||
}
|
||||
ssize_t nwritten = description.write(data, size);
|
||||
if (nwritten < 0)
|
||||
return KResult(nwritten);
|
||||
auto nwritten_or_error = description.write(data, size);
|
||||
if (nwritten_or_error.is_error())
|
||||
return nwritten_or_error.error();
|
||||
auto nwritten = nwritten_or_error.value();
|
||||
data += nwritten;
|
||||
size -= nwritten;
|
||||
}
|
||||
|
@ -444,9 +445,10 @@ KResult Plan9FS::do_read(u8* data, size_t size)
|
|||
if (Thread::current()->block<Thread::ReadBlocker>(nullptr, description).was_interrupted())
|
||||
return KResult(-EINTR);
|
||||
}
|
||||
ssize_t nread = description.read(data, size);
|
||||
if (nread < 0)
|
||||
return KResult(nread);
|
||||
auto nread_or_error = description.read(data, size);
|
||||
if (nread_or_error.is_error())
|
||||
return nread_or_error.error();
|
||||
auto nread = nread_or_error.value();
|
||||
if (nread == 0)
|
||||
return KResult(-EIO);
|
||||
data += nread;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue