Compare commits

..

60 Commits

Author SHA1 Message Date
b95d495815
base: Actually add the start icon to source control
Some checks failed
continuous-integration/drone/pr Build is failing
2023-08-16 14:54:59 +02:00
43061a099f
libui: Add Buttons 2023-08-16 14:54:59 +02:00
a529c091f0
libui: Handle other mouse events 2023-08-16 14:54:59 +02:00
efd21c9a1c
libui: Add aligned items using Containers, ImageWidget 2023-08-16 14:54:59 +02:00
88a2e60ea2
libui: Add VerticalLayout 2023-08-16 14:54:59 +02:00
7b55d594d1
wind+libui+taskbar: Add GetScreenRect IPC, non-decorated windows, taskbar 2023-08-16 14:54:58 +02:00
2c3c5b8aea
libui: Actually fill window backgrounds with the correct color 2023-08-16 14:54:58 +02:00
e3f31fb463
libui: Add basic widget and layout system =D 2023-08-16 14:54:58 +02:00
7159de0752
ui+wind: Send mouse move events through IPC 2023-08-16 14:54:58 +02:00
c430146c8b
wind+libui: Add protocol for window close requests 2023-08-16 14:54:58 +02:00
b7086dabf3
libos+libui+wind: Use uppercase for static struct IDs to avoid confusion with fields 2023-08-16 14:54:58 +02:00
6d3fdec98a
libui+gclient: Add basic OOP wrappers around the IPC protocol 2023-08-16 14:54:58 +02:00
c3c1ce150e
wind+gclient: Add SetWindowTitle and support shm buffers 2023-08-16 14:54:57 +02:00
b3dbbbf257
gclient: Create two example windows 2023-08-16 14:54:57 +02:00
537923a5bc
wind: Handle CreateWindow IPC messages 2023-08-16 14:54:57 +02:00
944aa3f3e5
libui: Add CreateWindow IPC message definitions 2023-08-16 14:54:57 +02:00
399edbcf0e
libos: Add basic IPC message framework 2023-08-16 14:54:57 +02:00
bd4c123fdd
kernel: Fix poll syscall 2023-08-16 14:54:57 +02:00
0a3df694c1
wind: Monitor data on client connections 2023-08-16 14:54:57 +02:00
887cc65461
kernel: Add POLLHUP and store it when a polled socket's peer disconnects 2023-08-16 14:54:56 +02:00
2b7bb40d14
libui: Add copyright/author text 2023-08-16 14:54:56 +02:00
b25a9bda6e
libos: Add copyright/author comments to LocalServer and LocalClient 2023-08-16 14:54:56 +02:00
a4fde43d4f
wind: Use init --user and pledge() 2023-08-16 14:54:56 +02:00
84060f2739
Update .gitignore 2023-08-16 14:54:56 +02:00
6bb7707e8d
libos: Remove some shared pointers and change them to owned/live on the stack 2023-08-16 14:54:56 +02:00
9f4a6639fc
wind: Spawn a new client process after startup
Also, create the socket after dropping privileges.
2023-08-16 14:54:55 +02:00
c7d7b9e1ac
apps: Add gclient 2023-08-16 14:54:55 +02:00
c9e172f1c3
libos: Add os::LocalClient 2023-08-16 14:54:55 +02:00
4e1dee5e73
libui: Change 'into' to 'onto' 2023-08-16 14:54:55 +02:00
ad492b42fc
libui: Document ui::Font 2023-08-16 14:54:55 +02:00
88c09edf53
libui+wind: Move some static variables inside functions 2023-08-16 14:54:55 +02:00
2d6300dd65
wind: Generate random windows on keypresses 2023-08-16 14:54:55 +02:00
8cd8896a87
wind: Make sure windows have a minimum size to fit the titlebar 2023-08-16 14:54:55 +02:00
4910f55603
libui: Properly cut off the last drawn character if necessary 2023-08-16 14:54:54 +02:00
23f3e8822b
libui: Add Rect::contains(Rect) 2023-08-16 14:54:54 +02:00
fbeafc7ec2
libui: Render font characters properly with no spacing, matching the width calculations 2023-08-16 14:54:54 +02:00
bdfa05a398
wind: Render an actual TGA mouse cursor 2023-08-16 14:54:54 +02:00
42c398615a
wind: Add a close button to windows using a TGA icon 2023-08-16 14:54:54 +02:00
6599d1a9bd
libui: Add support for TGA image loading 2023-08-16 14:54:54 +02:00
b83e68f6e1
libui: Add an interface to fill a Canvas with an array of pixels 2023-08-16 14:54:54 +02:00
d7ffc5f5a0
wind: Add window titlebars using ui::Font 2023-08-16 14:54:53 +02:00
8a33aa9c86
libui: Add PSF font loading and rendering 2023-08-16 14:54:53 +02:00
9765a03321
libui: Add Color::GRAY 2023-08-16 14:54:53 +02:00
ebbe755f51
libui: Rename Rect::absolute to normalized and add a new absolute function 2023-08-16 14:54:53 +02:00
0f9c5348dd
libluna: Add assignment operators to Buffer 2023-08-16 14:54:53 +02:00
0b3aac37c8
wind: Reorder drag sequence 2023-08-16 14:54:53 +02:00
2b1ce2a8c0
libui: Add Rect::relative 2023-08-16 14:54:53 +02:00
de7f487039
libui: Remove redundant statement 2023-08-16 14:54:52 +02:00
5d6cfc882e
libui: Add getters for separate color values 2023-08-16 14:54:52 +02:00
d6c7092e4b
libui: Remove unnecessary stuff 2023-08-16 14:54:52 +02:00
7c86993896
base: Remove startup items not necessary for GUI startup 2023-08-16 14:54:52 +02:00
e57a3ae23c
libui+wind: (Draggable) windows 2023-08-16 14:54:52 +02:00
2f37877644
wind: Create a local server object 2023-08-16 14:54:52 +02:00
4436ea2332
libos: Add a new LocalServer class for local domain sockets 2023-08-16 14:54:52 +02:00
a0b94ecc6c
kernel: Support listening sockets in poll() 2023-08-16 14:54:51 +02:00
4fe5d15ec1
base: Start wind on startup instead of the shell 2023-08-16 14:54:51 +02:00
3ac925a2d3
wind: Add a simple display server skeleton using libui
No client functionality yet, but it's a start.
2023-08-16 14:54:51 +02:00
6783e9253e
libui: Add a GUI and graphics library 2023-08-16 14:54:51 +02:00
6c40cbd09f
kernel: Fix negative movement in the PS/2 mouse driver 2023-08-16 14:54:51 +02:00
d43590e68c
kernel: Improve Your Disk IO performance by 500% with this One Trick!
Some checks failed
continuous-integration/drone/push Build is failing
The trick being caching lol.
2023-08-16 14:54:13 +02:00
11 changed files with 203 additions and 74 deletions

View File

@ -52,12 +52,14 @@ set(SOURCES
src/fs/Mount.cpp src/fs/Mount.cpp
src/fs/MBR.cpp src/fs/MBR.cpp
src/fs/GPT.cpp src/fs/GPT.cpp
src/fs/StorageCache.cpp
src/net/UnixSocket.cpp src/net/UnixSocket.cpp
src/fs/tmpfs/FileSystem.cpp src/fs/tmpfs/FileSystem.cpp
src/fs/tmpfs/Inode.cpp src/fs/tmpfs/Inode.cpp
src/fs/ext2/FileSystem.cpp src/fs/ext2/FileSystem.cpp
src/fs/ext2/Inode.cpp src/fs/ext2/Inode.cpp
src/fs/devices/DeviceRegistry.cpp src/fs/devices/DeviceRegistry.cpp
src/fs/devices/BlockDevice.cpp
src/fs/devices/NullDevice.cpp src/fs/devices/NullDevice.cpp
src/fs/devices/ZeroDevice.cpp src/fs/devices/ZeroDevice.cpp
src/fs/devices/FullDevice.cpp src/fs/devices/FullDevice.cpp

View File

@ -11,4 +11,5 @@ target_compile_definitions(moon PRIVATE EXT2_DEBUG)
target_compile_definitions(moon PRIVATE DEVICE_REGISTRY_DEBUG) target_compile_definitions(moon PRIVATE DEVICE_REGISTRY_DEBUG)
target_compile_definitions(moon PRIVATE FORK_DEBUG) target_compile_definitions(moon PRIVATE FORK_DEBUG)
target_compile_definitions(moon PRIVATE MOUNT_DEBUG) target_compile_definitions(moon PRIVATE MOUNT_DEBUG)
target_compile_definitions(moon PRIVATE CACHE_DEBUG)
target_compile_options(moon PRIVATE -fsanitize=undefined) target_compile_options(moon PRIVATE -fsanitize=undefined)

View File

@ -739,66 +739,26 @@ Result<String> ATA::Drive::create_drive_name(ATA::Drive* drive)
Result<SharedPtr<Device>> ATADevice::create(ATA::Drive* drive) Result<SharedPtr<Device>> ATADevice::create(ATA::Drive* drive)
{ {
auto device = TRY(adopt_shared_if_nonnull(new (std::nothrow) ATADevice())); auto device = TRY(adopt_shared_if_nonnull(new (std::nothrow) ATADevice(drive)));
device->m_drive = drive;
device->m_device_path = TRY(ATA::Drive::create_drive_name(drive)); device->m_device_path = TRY(ATA::Drive::create_drive_name(drive));
TRY(DeviceRegistry::register_special_device(DeviceRegistry::Disk, next_minor++, device, 0400)); TRY(DeviceRegistry::register_special_device(DeviceRegistry::Disk, next_minor++, device, 0400));
return (SharedPtr<Device>)device; return (SharedPtr<Device>)device;
} }
Result<u64> ATADevice::read(u8* buf, usize offset, usize size) const ATADevice::ATADevice(ATA::Drive* drive) : BlockDevice(drive->block_size(), drive->block_count()), m_drive(drive)
{ {
if (size == 0) return 0; }
if (offset > m_drive->capacity()) return 0;
if (offset + size > m_drive->capacity()) size = m_drive->capacity() - offset;
usize length = size;
auto block_size = m_drive->block_size();
Result<void> ATADevice::read_block(Buffer& buf, u64 block) const
{
ScopedKMutexLock<100> lock(m_drive->channel()->lock()); ScopedKMutexLock<100> lock(m_drive->channel()->lock());
Buffer temp; if (buf.size() != m_drive->block_size())
if (offset % block_size)
{ {
// The size we need to read to round up to a block. kwarnln("ata: error while reading block %lu: cache entry size mismatch (%lu), data=%p", block, buf.size(),
usize extra_size = block_size - (offset % block_size); buf.data());
// Maybe we don't even want enough to get to the next block? fail("Cache entry size mismatch");
if (extra_size > size) extra_size = size;
TRY(temp.try_resize(block_size));
TRY(m_drive->read_lba(offset / block_size, temp.data(), 1));
memcpy(buf, temp.data() + (offset % block_size), extra_size);
offset += extra_size;
size -= extra_size;
buf += extra_size;
} }
while (size >= ARCH_PAGE_SIZE) return m_drive->read_lba(block, buf.data(), 1);
{
TRY(m_drive->read_lba(offset / block_size, buf, ARCH_PAGE_SIZE / block_size));
offset += ARCH_PAGE_SIZE;
size -= ARCH_PAGE_SIZE;
buf += ARCH_PAGE_SIZE;
}
while (size >= block_size)
{
TRY(m_drive->read_lba(offset / block_size, buf, 1));
offset += block_size;
size -= block_size;
buf += block_size;
}
if (size)
{
TRY(temp.try_resize(block_size));
TRY(m_drive->read_lba(offset / block_size, temp.data(), 1));
memcpy(buf, temp.data(), size);
}
return length;
} }

View File

@ -1,5 +1,6 @@
#pragma once #pragma once
#include "arch/PCI.h" #include "arch/PCI.h"
#include "fs/devices/BlockDevice.h"
#include "fs/devices/DeviceRegistry.h" #include "fs/devices/DeviceRegistry.h"
#include "lib/KMutex.h" #include "lib/KMutex.h"
#include <luna/Atomic.h> #include <luna/Atomic.h>
@ -256,7 +257,6 @@ namespace ATA
Controller* m_controller; Controller* m_controller;
u8 m_channel_index; u8 m_channel_index;
bool m_is_pci_native_mode; bool m_is_pci_native_mode;
u8 m_interrupt_line; u8 m_interrupt_line;
KMutex<100> m_lock {}; KMutex<100> m_lock {};
@ -297,44 +297,25 @@ namespace ATA
} }
class ATADevice : public Device class ATADevice : public BlockDevice
{ {
public: public:
// Initializer for DeviceRegistry. // Initializer for DeviceRegistry.
static Result<SharedPtr<Device>> create(ATA::Drive* drive); static Result<SharedPtr<Device>> create(ATA::Drive* drive);
Result<usize> read(u8*, usize, usize) const override; Result<void> read_block(Buffer& buf, u64 block) const override;
Result<usize> write(const u8*, usize, usize) override
{
return err(ENOTSUP);
}
bool will_block_if_read() const override bool will_block_if_read() const override
{ {
return false; return false;
} }
bool is_block_device() const override
{
return true;
}
usize size() const override
{
return m_drive->capacity();
}
Result<usize> block_size() const override
{
return m_drive->block_size();
}
StringView device_path() const override StringView device_path() const override
{ {
return m_device_path.view(); return m_device_path.view();
} }
ATADevice(ATA::Drive* drive);
virtual ~ATADevice() = default; virtual ~ATADevice() = default;
private: private:

View File

@ -0,0 +1,44 @@
#include "fs/StorageCache.h"
#include "Log.h"
#include <luna/ScopeGuard.h>
static LinkedList<StorageCache> g_storage_caches;
Result<StorageCache::CacheEntry*> StorageCache::fetch_entry(u64 block)
{
{
CacheEntry* entry = m_cache_entries.try_get_ref(block);
if (entry && !entry->buffer.is_empty()) return entry;
}
CacheEntry entry {};
TRY(m_cache_entries.try_set(block, move(entry)));
#ifdef CACHE_DEBUG
kdbgln("cache: Created new cache entry for block %lu", block);
#endif
return m_cache_entries.try_get_ref(block);
}
void StorageCache::clear()
{
ScopedKMutexLock<100> lock(m_mutex);
m_cache_entries.clear();
}
StorageCache::StorageCache()
{
g_storage_caches.append(this);
}
StorageCache::~StorageCache()
{
g_storage_caches.remove(this);
}
void StorageCache::clear_caches()
{
for (auto* cache : g_storage_caches) { cache->clear(); }
}

View File

@ -0,0 +1,37 @@
#pragma once
#include "lib/KMutex.h"
#include <luna/Buffer.h>
#include <luna/HashMap.h>
#include <luna/LinkedList.h>
class StorageCache : public LinkedListNode<StorageCache>
{
public:
struct CacheEntry
{
Buffer buffer {};
};
void lock()
{
return m_mutex.lock();
}
void unlock()
{
return m_mutex.unlock();
}
Result<CacheEntry*> fetch_entry(u64 block);
void clear();
static void clear_caches();
StorageCache();
~StorageCache();
private:
HashMap<u64, CacheEntry> m_cache_entries;
KMutex<100> m_mutex;
};

View File

@ -0,0 +1,51 @@
#include "fs/devices/BlockDevice.h"
#include "arch/MMU.h"
#include <luna/Common.h>
BlockDevice::BlockDevice(u64 block_size, u64 num_blocks) : m_cache(), m_block_size(block_size), m_num_blocks(num_blocks)
{
}
Result<usize> BlockDevice::read(u8* buf, usize offset, usize length) const
{
if (length == 0) return 0;
if (offset > size()) return 0;
if (offset + length > size()) length = size() - offset;
const usize saved = length;
auto read_data = [&](u64 off, u64 len) -> Result<void> {
const u64 block = offset / m_block_size;
m_cache.lock();
auto guard = make_scope_guard([&] { m_cache.unlock(); });
auto* entry = TRY(m_cache.fetch_entry(block));
if (entry->buffer.is_empty())
{
// TODO: What if the cache needs clearing in the middle of try_resize()? That could lead to some weird
// state...
TRY(entry->buffer.try_resize(m_block_size));
TRY(read_block(entry->buffer, block));
}
memcpy(buf, entry->buffer.data() + off, len);
offset += len;
length -= len;
buf += len;
return {};
};
if (offset % m_block_size)
{
const u64 off = offset % m_block_size;
const u64 len = min(m_block_size - off, length);
TRY(read_data(off, len));
}
while (length >= m_block_size) { TRY(read_data(0, m_block_size)); }
if (length) { TRY(read_data(0, length)); }
return saved;
}

View File

@ -0,0 +1,40 @@
#pragma once
#include "fs/StorageCache.h"
#include "fs/devices/Device.h"
class BlockDevice : public Device
{
public:
BlockDevice(u64 block_size, u64 num_blocks);
Result<usize> read(u8* buf, usize offset, usize length) const override;
virtual Result<void> read_block(Buffer& buf, u64 block) const = 0;
Result<usize> write(const u8*, usize, usize) override
{
return err(ENOTSUP);
}
usize size() const override
{
return m_block_size * m_num_blocks;
}
bool is_block_device() const override
{
return true;
}
Result<usize> block_size() const override
{
return m_block_size;
}
virtual ~BlockDevice() = default;
protected:
mutable StorageCache m_cache;
u64 m_block_size;
u64 m_num_blocks;
};

View File

@ -2,6 +2,8 @@
#include "Log.h" #include "Log.h"
#include <luna/Result.h> #include <luna/Result.h>
#include <luna/SharedPtr.h> #include <luna/SharedPtr.h>
#include <luna/StringView.h>
#include <sys/types.h>
class Device : public Shareable class Device : public Shareable
{ {

View File

@ -1,6 +1,7 @@
#include "memory/MemoryManager.h" #include "memory/MemoryManager.h"
#include "Log.h" #include "Log.h"
#include "arch/MMU.h" #include "arch/MMU.h"
#include "fs/StorageCache.h"
#include "memory/KernelVM.h" #include "memory/KernelVM.h"
#include "memory/MemoryMap.h" #include "memory/MemoryMap.h"
#include <luna/Alignment.h> #include <luna/Alignment.h>
@ -143,7 +144,12 @@ namespace MemoryManager
usize index; usize index;
bool ok = frame_bitmap->find_and_toggle(false, start_index).try_set_value(index); bool ok = frame_bitmap->find_and_toggle(false, start_index).try_set_value(index);
if (!ok) return err(ENOMEM); if (!ok)
{
kwarnln("OOM alert! Trying to free caches...");
StorageCache::clear_caches();
if (!frame_bitmap->find_and_toggle(false, start_index).try_set_value(index)) return err(ENOMEM);
}
start_index = index + 1; start_index = index + 1;

View File

@ -49,6 +49,11 @@ template <typename K, typename V> struct HashMap
return m_table.try_remove(HashPair<K, V> { key, {} }); return m_table.try_remove(HashPair<K, V> { key, {} });
} }
void clear()
{
m_table.clear();
}
private: private:
HashTable<HashPair<K, V>> m_table; HashTable<HashPair<K, V>> m_table;
}; };