Compare commits

..

37 Commits

Author SHA1 Message Date
1bd6cf048b
libos: Remove some shared pointers and change them to owned/live on the stack
All checks were successful
continuous-integration/drone/pr Build is passing
2023-08-08 12:51:06 +02:00
2c42b088e0
wind: Spawn a new client process after startup
Also, create the socket after dropping privileges.
2023-08-08 12:51:06 +02:00
d0b5eb11ef
apps: Add gclient 2023-08-08 12:51:05 +02:00
5f7b055c36
libos: Add os::LocalClient 2023-08-08 12:51:05 +02:00
9306b98d17
libui: Change 'into' to 'onto' 2023-08-08 12:51:05 +02:00
fe65be8a89
libui: Document ui::Font 2023-08-08 12:51:05 +02:00
41b54610b0
libui+wind: Move some static variables inside functions 2023-08-08 12:51:05 +02:00
a77d698544
wind: Generate random windows on keypresses 2023-08-08 12:51:05 +02:00
2ad53db448
wind: Make sure windows have a minimum size to fit the titlebar 2023-08-08 12:51:05 +02:00
871b5c6a35
libui: Properly cut off the last drawn character if necessary 2023-08-08 12:51:04 +02:00
a38dbce9bd
libui: Add Rect::contains(Rect) 2023-08-08 12:51:04 +02:00
93d74a29b5
libui: Render font characters properly with no spacing, matching the width calculations 2023-08-08 12:51:04 +02:00
3d3d1aeed5
wind: Render an actual TGA mouse cursor 2023-08-08 12:51:04 +02:00
60385c4614
wind: Add a close button to windows using a TGA icon 2023-08-08 12:51:04 +02:00
38c00a8384
libui: Add support for TGA image loading 2023-08-08 12:51:04 +02:00
ae5dd3f340
libui: Add an interface to fill a Canvas with an array of pixels 2023-08-08 12:51:03 +02:00
a843ef943e
wind: Add window titlebars using ui::Font 2023-08-08 12:51:03 +02:00
4cb2c5ea83
libui: Add PSF font loading and rendering 2023-08-08 12:51:03 +02:00
0bc7af62df
libui: Add Color::GRAY 2023-08-08 12:51:03 +02:00
98a0049e54
libui: Rename Rect::absolute to normalized and add a new absolute function 2023-08-08 12:51:03 +02:00
9c78ec605c
libluna: Add assignment operators to Buffer 2023-08-08 12:51:03 +02:00
d8ba20b23d
wind: Reorder drag sequence 2023-08-08 12:51:02 +02:00
0927dd71cc
libui: Add Rect::relative 2023-08-08 12:51:02 +02:00
3d559cb8c8
libui: Remove redundant statement 2023-08-08 12:51:02 +02:00
42dca14d09
libui: Add getters for separate color values 2023-08-08 12:51:02 +02:00
69b36b0b09
libui: Remove unnecessary stuff 2023-08-08 12:51:02 +02:00
ee0bdd59d3
base: Remove startup items not necessary for GUI startup 2023-08-08 12:51:01 +02:00
d8150113c5
libui+wind: (Draggable) windows 2023-08-08 12:51:01 +02:00
b48daad58a
wind: Create a local server object 2023-08-08 12:51:01 +02:00
a1f47cacd4
libos: Add a new LocalServer class for local domain sockets 2023-08-08 12:51:01 +02:00
78a4c4f111
kernel: Support listening sockets in poll() 2023-08-08 12:51:01 +02:00
cab45a414c
base: Start wind on startup instead of the shell 2023-08-08 12:51:01 +02:00
646ccb2854
wind: Add a simple display server skeleton using libui
No client functionality yet, but it's a start.
2023-08-08 12:51:01 +02:00
1984a4de08
libui: Add a GUI and graphics library 2023-08-08 12:51:00 +02:00
5c09fdfbc6
kernel: Fix negative movement in the PS/2 mouse driver 2023-08-08 12:50:56 +02:00
159c05c064
libluna: Add max() and min()
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-08 12:39:03 +02:00
b63a8ff245
libluna: Move get_blocks_from_size to a new header and call it ceil_div instead
All checks were successful
continuous-integration/drone/push Build is passing
2023-08-08 11:58:33 +02:00
10 changed files with 101 additions and 49 deletions

View File

@ -7,6 +7,7 @@
#include <luna/Alignment.h>
#include <luna/Alloc.h>
#include <luna/CString.h>
#include <luna/Common.h>
#include <luna/ScopeGuard.h>
static bool can_execute_segment(u32 flags)
@ -113,14 +114,14 @@ Result<u64> ELFLoader::load(AddressSpace* space)
if (can_write_segment(program_header.p_flags)) prot |= PROT_WRITE;
if (can_execute_segment(program_header.p_flags)) prot |= PROT_EXEC;
if (!TRY(space->test_and_alloc_region(
base_vaddr, get_blocks_from_size(program_header.p_memsz + vaddr_diff, ARCH_PAGE_SIZE), prot,
MAP_ANONYMOUS | MAP_PRIVATE, 0, true)))
if (!TRY(space->test_and_alloc_region(base_vaddr,
ceil_div(program_header.p_memsz + vaddr_diff, ARCH_PAGE_SIZE), prot,
MAP_ANONYMOUS | MAP_PRIVATE, 0, true)))
return err(ENOMEM);
// Allocate physical memory for the segment
TRY(MemoryManager::alloc_at(
base_vaddr, get_blocks_from_size(program_header.p_memsz + vaddr_diff, ARCH_PAGE_SIZE), flags));
TRY(MemoryManager::alloc_at(base_vaddr, ceil_div(program_header.p_memsz + vaddr_diff, ARCH_PAGE_SIZE),
flags));
// Zero out unused memory (before the start of the segment)
memset((void*)base_vaddr, 0, vaddr_diff);

View File

@ -6,7 +6,7 @@
#include "memory/MemoryManager.h"
#include "thread/Thread.h"
#include <bits/modes.h>
#include <luna/Alignment.h>
#include <luna/Common.h>
TarStream g_initrd;
extern const BOOTBOOT bootboot;
@ -47,7 +47,7 @@ Result<void> InitRD::populate_vfs()
}
// Now we don't need the original initrd anymore
MemoryManager::free_frames(bootboot.initrd_ptr, get_blocks_from_size(bootboot.initrd_size, ARCH_PAGE_SIZE));
MemoryManager::free_frames(bootboot.initrd_ptr, ceil_div(bootboot.initrd_size, ARCH_PAGE_SIZE));
return {};
}

View File

@ -1,6 +1,6 @@
#include "fs/ext2/FileSystem.h"
#include "fs/ext2/Inode.h"
#include <luna/Alignment.h>
#include <luna/Common.h>
static VFS::InodeType vfs_type_from_ext2_type(mode_t mode)
{
@ -114,7 +114,7 @@ namespace Ext2
fs->m_host_device = host_device;
fs->m_block_size = 1024 << fs->m_superblock.log_block_size;
fs->m_block_groups = get_blocks_from_size(fs->m_superblock.nr_blocks, fs->m_superblock.blocks_per_block_group);
fs->m_block_groups = ceil_div(fs->m_superblock.nr_blocks, fs->m_superblock.blocks_per_block_group);
#ifdef EXT2_DEBUG
kdbgln("ext2: Mounting new Ext2 file system, block size=%lu, blocks=%u, inodes=%u, block group=(%u blocks, %u "

View File

@ -5,6 +5,7 @@
#include "memory/MemoryMap.h"
#include <luna/Alignment.h>
#include <luna/Bitmap.h>
#include <luna/Common.h>
#include <luna/ScopeGuard.h>
#include <luna/Spinlock.h>
#include <luna/SystemError.h>
@ -40,11 +41,11 @@ namespace MemoryManager
Result<void> protect_kernel_sections()
{
const usize rodata_size = (usize)(end_of_kernel_rodata - start_of_kernel_rodata);
const usize rodata_pages = get_blocks_from_size(rodata_size, ARCH_PAGE_SIZE);
const usize rodata_pages = ceil_div(rodata_size, ARCH_PAGE_SIZE);
TRY(remap((u64)start_of_kernel_rodata, rodata_pages, MMU::NoExecute));
const usize data_size = (usize)(end_of_kernel_data - start_of_kernel_data);
const usize data_pages = get_blocks_from_size(data_size, ARCH_PAGE_SIZE);
const usize data_pages = ceil_div(data_size, ARCH_PAGE_SIZE);
TRY(remap((u64)start_of_kernel_data, data_pages, MMU::NoExecute | MMU::ReadWrite));
return {};
@ -67,7 +68,7 @@ namespace MemoryManager
// We store our frame bitmap at the beginning of the largest free memory block.
char* const frame_bitmap_addr = (char*)largest_free_entry.ptr();
const usize frame_bitmap_size = get_blocks_from_size(physical_address_space_size / ARCH_PAGE_SIZE, 8UL);
const usize frame_bitmap_size = ceil_div(physical_address_space_size / ARCH_PAGE_SIZE, 8UL);
// This should never happen, unless memory is very fragmented. Usually there is always a very big block of
// usable memory and then some tiny blocks around it.
@ -96,7 +97,7 @@ namespace MemoryManager
}
// Make sure that the physical frames used by the bitmap aren't handed out to anyone else.
lock_frames(largest_free_entry.address(), get_blocks_from_size(frame_bitmap_size, ARCH_PAGE_SIZE));
lock_frames(largest_free_entry.address(), ceil_div(frame_bitmap_size, ARCH_PAGE_SIZE));
}
void init()
@ -526,7 +527,7 @@ namespace MemoryManager
uintptr_t diff = address - page;
usize pages = get_blocks_from_size(size + diff, ARCH_PAGE_SIZE);
usize pages = ceil_div(size + diff, ARCH_PAGE_SIZE);
while (pages--)
{

View File

@ -8,6 +8,7 @@
#include <bits/mmap.h>
#include <bits/open-flags.h>
#include <luna/Alignment.h>
#include <luna/Common.h>
constexpr uintptr_t USERSPACE_HEAP_BASE = 0x3000000;
@ -32,7 +33,7 @@ Result<u64> sys_mmap(Registers*, SyscallArgs args)
if (!is_aligned<ARCH_PAGE_SIZE>(params.offset)) return err(EINVAL);
params.len = align_up<ARCH_PAGE_SIZE>(params.len);
const usize pages = ceil_div(params.len, ARCH_PAGE_SIZE);
SharedMemory* shmem = nullptr;
u64 shmid = 0;
@ -41,12 +42,12 @@ Result<u64> sys_mmap(Registers*, SyscallArgs args)
if (!description)
{
params.offset = 0;
shmid = TRY(SharedMemory::create(nullptr, 0, params.len / ARCH_PAGE_SIZE));
shmid = TRY(SharedMemory::create(nullptr, 0, pages));
}
else
{
if ((params.prot & PROT_WRITE) && !(description->flags & O_WRONLY)) return err(EACCES);
shmid = TRY(description->inode->query_shared_memory(params.offset, params.len / ARCH_PAGE_SIZE));
shmid = TRY(description->inode->query_shared_memory(params.offset, pages));
}
shmem = g_shared_memory_map.try_get_ref(shmid);
shmem->refs++;
@ -55,15 +56,13 @@ Result<u64> sys_mmap(Registers*, SyscallArgs args)
u64 address;
if (!params.addr)
address = TRY(current->address_space->alloc_region(get_blocks_from_size(params.len, ARCH_PAGE_SIZE),
params.prot, params.flags, params.offset, shmid));
address = TRY(current->address_space->alloc_region(pages, params.prot, params.flags, params.offset, shmid));
else
{
// FIXME: We should be more flexible if MAP_FIXED was not specified.
address = align_down<ARCH_PAGE_SIZE>((u64)params.addr);
if (!TRY(current->address_space->test_and_alloc_region(address,
get_blocks_from_size(params.len, ARCH_PAGE_SIZE),
params.prot, params.flags, params.offset, shmid)))
if (!TRY(current->address_space->test_and_alloc_region(address, pages, params.prot, params.flags, params.offset,
shmid)))
return err(ENOMEM);
}
@ -76,10 +75,10 @@ Result<u64> sys_mmap(Registers*, SyscallArgs args)
kdbgln("mmap: mapping memory at %#lx, size=%zu", address, params.len);
#endif
if (shmem) { TRY(shmem->map(address, mmu_flags, params.offset, params.len / ARCH_PAGE_SIZE)); }
if (shmem) { TRY(shmem->map(address, mmu_flags, params.offset, pages)); }
else
{
TRY(MemoryManager::alloc_at_zeroed(address, get_blocks_from_size(params.len, ARCH_PAGE_SIZE), mmu_flags));
TRY(MemoryManager::alloc_at_zeroed(address, pages, mmu_flags));
if (description) { TRY(description->inode->read((u8*)address, params.offset, params.len)); }
}
@ -92,11 +91,11 @@ Result<u64> sys_munmap(Registers*, SyscallArgs args)
usize size = (usize)args[1];
if (size == 0) return err(EINVAL);
if (!is_aligned<ARCH_PAGE_SIZE>(size)) return err(EINVAL);
if (!is_aligned<ARCH_PAGE_SIZE>(address)) return err(EINVAL);
Thread* current = Scheduler::current();
bool ok = TRY(current->address_space->free_region(address, get_blocks_from_size(size, ARCH_PAGE_SIZE)));
bool ok = TRY(current->address_space->free_region(address, ceil_div(size, ARCH_PAGE_SIZE)));
// POSIX says munmap should silently do nothing if the memory was not already mapped.
if (!ok) return 0;
@ -105,7 +104,7 @@ Result<u64> sys_munmap(Registers*, SyscallArgs args)
kdbgln("munmap: unmapping memory at %#lx, size=%zu", address, size);
#endif
TRY(MemoryManager::unmap_owned_if_possible(address, get_blocks_from_size(size, ARCH_PAGE_SIZE)));
TRY(MemoryManager::unmap_owned_if_possible(address, ceil_div(size, ARCH_PAGE_SIZE)));
return { 0 };
}
@ -120,7 +119,7 @@ Result<u64> sys_msync(Registers*, SyscallArgs args)
Thread* current = Scheduler::current();
TRY(current->address_space->sync_regions(address, get_blocks_from_size(size, ARCH_PAGE_SIZE)));
TRY(current->address_space->sync_regions(address, ceil_div(size, ARCH_PAGE_SIZE)));
return { 0 };
}

View File

@ -1,5 +1,6 @@
#include <bits/errno-return.h>
#include <fcntl.h>
#include <luna/Common.h>
#include <luna/Format.h>
#include <stdio.h>
#include <stdlib.h>
@ -107,7 +108,7 @@ static ssize_t write_into_buffer(FILE* stream, const u8* data, ssize_t size)
}
ssize_t size_remaining = stream->_buf.capacity - stream->_buf.size;
nwritten = size > size_remaining ? size_remaining : size;
nwritten = min(size_remaining, size);
memcpy(stream->_buf.buffer + stream->_buf.size, data, nwritten);
stream->_buf.status |= FileStatusFlags::LastWrite;
@ -120,7 +121,7 @@ static ssize_t write_into_buffer(FILE* stream, const u8* data, ssize_t size)
}
}
else
nwritten = write(stream->_fd, data, size > BUFSIZ ? BUFSIZ : size);
nwritten = write(stream->_fd, data, min(size, BUFSIZ));
if (nwritten < 0) return nwritten;
size -= nwritten;
data += nwritten;
@ -160,13 +161,13 @@ static ssize_t read_from_buffer(FILE* stream, u8* data, ssize_t size)
}
ssize_t size_remaining = stream->_buf.size - stream->_buf.index;
nread = size > size_remaining ? size_remaining : size;
nread = min(size_remaining, size);
memcpy(data, stream->_buf.buffer + stream->_buf.index, nread);
stream->_buf.index += nread;
}
else
nread = read(stream->_fd, data, size > BUFSIZ ? BUFSIZ : size);
nread = read(stream->_fd, data, min(size, BUFSIZ));
if (nread < 0) return nread;
if (nread == 0) return total_read;
size -= nread;

View File

@ -30,16 +30,6 @@ static_assert(align_up<512>(598ul) == 1024ul);
static_assert(align_up<64>(194ul) == 256ul);
static_assert(align_up<32>(64ul) == 64ul);
template <typename T> constexpr T get_blocks_from_size(T value, T block_size)
{
return (value + (block_size - 1)) / block_size;
}
static_assert(get_blocks_from_size(40960, 4096) == 10);
static_assert(get_blocks_from_size(194, 64) == 4);
static_assert(get_blocks_from_size(2, 32) == 1);
static_assert(get_blocks_from_size(0, 256) == 0);
// Offset a pointer by exactly <offset> bytes, no matter the type. Useful to avoid the quirks that come from C pointer
// arithmetic.
template <typename T, typename Offset> constexpr inline T* offset_ptr(T* ptr, Offset offset)

View File

@ -0,0 +1,59 @@
/**
* @file Common.h
* @author apio (cloudapio.eu)
* @brief Common utility functions.
*
* @copyright Copyright (c) 2023, the Luna authors.
*
*/
#pragma once
/**
* @brief Divide a by b, rounding the quotient up to the next multiple of b.
*
* @tparam T The type of a and b.
* @param a The dividend.
* @param b The divisor.
* @return constexpr T The result of the operation.
*/
template <typename T> inline constexpr T ceil_div(T a, T b)
{
return (a + (b - 1)) / b;
}
/**
* @brief Return the minimum value out of a set of arguments.
*
* @tparam T The type of the arguments.
* @param a The first value of the set of arguments.
* @param args The rest of the set of arguments.
* @return constexpr T The minimum value.
*/
template <typename T, class... Args> inline constexpr T min(T a, Args... args)
{
if constexpr (sizeof...(args) == 0) return a;
else
{
T b = min(args...);
return a > b ? b : a;
}
}
/**
* @brief Return the maximum value out of a set of arguments.
*
* @tparam T The type of the arguments.
* @param a The first value of the set of arguments.
* @param args The rest of the set of arguments.
* @return constexpr T The maximum value.
*/
template <typename T, class... Args> inline constexpr T max(T a, Args... args)
{
if constexpr (sizeof...(args) == 0) return a;
else
{
T b = max(args...);
return a > b ? a : b;
}
}

View File

@ -1,5 +1,6 @@
#pragma once
#include <luna/CString.h>
#include <luna/Common.h>
#include <luna/StringView.h>
#include <luna/Types.h>
@ -37,8 +38,7 @@ template <usize Size> class StaticString
void adopt(StringView string)
{
usize length = strlcpy(m_buffer, string.chars(),
string.length() > sizeof(m_buffer) ? sizeof(m_buffer) : string.length() + 1);
usize length = strlcpy(m_buffer, string.chars(), min(sizeof(m_buffer), string.length() + 1));
if (length > Size) { m_length = Size; }
else
m_length = length;

View File

@ -1,6 +1,7 @@
#include <luna/Alignment.h>
#include <luna/Alloc.h>
#include <luna/CString.h>
#include <luna/Common.h>
#include <luna/DebugLog.h>
#include <luna/Heap.h>
#include <luna/LinkedList.h>
@ -52,7 +53,7 @@ static Spinlock g_heap_lock;
// of pages.
static usize get_pages_for_allocation(usize bytes)
{
usize pages = get_blocks_from_size(bytes, PAGE_SIZE);
usize pages = ceil_div(bytes, PAGE_SIZE);
if (pages < MINIMUM_PAGES_PER_ALLOCATION) pages = MINIMUM_PAGES_PER_ALLOCATION;
return pages;
}
@ -154,7 +155,7 @@ static Result<void> combine_forward(HeapBlock* block)
{
if (next->status & BLOCK_START_MEM)
{
const usize pages = get_blocks_from_size(next->full_size + sizeof(HeapBlock), PAGE_SIZE);
const usize pages = ceil_div(next->full_size + sizeof(HeapBlock), PAGE_SIZE);
TRY(release_pages_impl(next, pages));
return {};
}
@ -183,7 +184,7 @@ static Result<HeapBlock*> combine_backward(HeapBlock* block)
{
if (block->status & BLOCK_START_MEM)
{
const usize pages = get_blocks_from_size(block->full_size + sizeof(HeapBlock), PAGE_SIZE);
const usize pages = ceil_div(block->full_size + sizeof(HeapBlock), PAGE_SIZE);
TRY(release_pages_impl(block, pages));
return last;
}
@ -303,7 +304,7 @@ Result<void> free_impl(void* ptr)
if ((block->status & BLOCK_START_MEM) && (block->status & BLOCK_END_MEM))
{
heap.remove(block);
const usize pages = get_blocks_from_size(block->full_size + sizeof(HeapBlock), PAGE_SIZE);
const usize pages = ceil_div(block->full_size + sizeof(HeapBlock), PAGE_SIZE);
TRY(release_pages_impl(block, pages));
}
@ -366,7 +367,7 @@ Result<void*> realloc_impl(void* ptr, usize size, bool may_realloc_again)
lock.take_over().unlock();
void* const new_ptr = TRY(malloc_impl(size, may_realloc_again, false));
memcpy(new_ptr, ptr, old_size > size ? size : old_size);
memcpy(new_ptr, ptr, min(size, old_size));
TRY(free_impl(ptr));
if (old_size < size) { memset(offset_ptr(new_ptr, old_size), MALLOC_SCRUB_BYTE, size - old_size); }