Kernel/LibC: Implement basic epoll

This implementation is on top of inodes instead of fds as linux does it.
If I start finding ports/software that relies on epoll allowing
duplicate inodes, I will do what linux does.

I'm probably missing multiple epoll_notify's which may cause hangs but
the system seems to work fine :dd:
This commit is contained in:
2025-05-13 10:10:35 +03:00
parent 143a00626b
commit 1bcd1edbf5
43 changed files with 627 additions and 119 deletions

View File

@@ -51,6 +51,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return true; }
virtual bool can_write_impl() const override { return true; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
// Returns maximum number of data blocks in use

View File

@@ -49,6 +49,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return true; }
virtual bool can_write_impl() const override { return true; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
FATInode(FATFS& fs, const FAT::DirectoryEntry& entry, ino_t ino, uint32_t block_count)

View File

@@ -1,6 +1,7 @@
#pragma once
#include <BAN/ByteSpan.h>
#include <BAN/LinkedList.h>
#include <BAN/RefPtr.h>
#include <BAN/String.h>
#include <BAN/StringView.h>
@@ -19,9 +20,8 @@
namespace Kernel
{
class FileSystem;
class FileBackedRegion;
class FileSystem;
class SharedFileData;
class Inode : public BAN::RefCounted<Inode>
@@ -85,6 +85,7 @@ namespace Kernel
virtual dev_t rdev() const = 0;
virtual bool is_device() const { return false; }
virtual bool is_epoll() const { return false; }
virtual bool is_pipe() const { return false; }
virtual bool is_tty() const { return false; }
@@ -123,9 +124,14 @@ namespace Kernel
bool can_read() const;
bool can_write() const;
bool has_error() const;
bool has_hangup() const;
BAN::ErrorOr<long> ioctl(int request, void* arg);
BAN::ErrorOr<void> add_epoll(class Epoll*);
void del_epoll(class Epoll*);
void epoll_notify(uint32_t event);
protected:
// Directory API
virtual BAN::ErrorOr<BAN::RefPtr<Inode>> find_inode_impl(BAN::StringView) { return BAN::Error::from_errno(ENOTSUP); }
@@ -160,6 +166,7 @@ namespace Kernel
virtual bool can_read_impl() const = 0;
virtual bool can_write_impl() const = 0;
virtual bool has_error_impl() const = 0;
virtual bool has_hangup_impl() const = 0;
virtual BAN::ErrorOr<long> ioctl_impl(int, void*) { return BAN::Error::from_errno(ENOTSUP); }
@@ -168,6 +175,7 @@ namespace Kernel
private:
BAN::WeakPtr<SharedFileData> m_shared_region;
BAN::LinkedList<class Epoll*> m_epolls;
friend class FileBackedRegion;
friend class OpenFileDescriptorSet;
friend class SharedFileData;

View File

@@ -40,6 +40,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return m_buffer_size > 0; }
virtual bool can_write_impl() const override { return true; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return m_writing_count == 0; }
private:
Pipe(const Credentials&);

View File

@@ -47,6 +47,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return true; }
virtual bool can_write_impl() const override { return false; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
ProcROProcessInode(Process&, size_t (Process::*)(off_t, BAN::ByteSpan) const, TmpFileSystem&, const TmpInodeInfo&);
@@ -72,6 +73,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return true; }
virtual bool can_write_impl() const override { return false; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
ProcROInode(size_t (*callback)(off_t, BAN::ByteSpan), TmpFileSystem&, const TmpInodeInfo&);

View File

@@ -80,6 +80,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return true; }
virtual bool can_write_impl() const override { return true; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
TmpFileInode(TmpFileSystem&, ino_t, const TmpInodeInfo&);
@@ -102,6 +103,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return false; }
virtual bool can_write_impl() const override { return false; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
TmpSocketInode(TmpFileSystem&, ino_t, const TmpInodeInfo&);
@@ -123,6 +125,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return false; }
virtual bool can_write_impl() const override { return false; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
TmpSymlinkInode(TmpFileSystem&, ino_t, const TmpInodeInfo&);
@@ -153,6 +156,7 @@ namespace Kernel
virtual bool can_read_impl() const override { return false; }
virtual bool can_write_impl() const override { return false; }
virtual bool has_error_impl() const override { return false; }
virtual bool has_hangup_impl() const override { return false; }
private:
template<TmpFuncs::for_each_valid_entry_callback F>