diff options
Diffstat (limited to 'include/mercury')
-rw-r--r-- | include/mercury/kernel/framebuffer.hpp | 27 | ||||
-rw-r--r-- | include/mercury/kernel/paging.hpp | 34 | ||||
-rw-r--r-- | include/mercury/kernel/terminal.hpp | 30 | ||||
-rw-r--r-- | include/mercury/kernel/utility.hpp | 124 |
4 files changed, 215 insertions, 0 deletions
diff --git a/include/mercury/kernel/framebuffer.hpp b/include/mercury/kernel/framebuffer.hpp new file mode 100644 index 0000000..5c6ca23 --- /dev/null +++ b/include/mercury/kernel/framebuffer.hpp @@ -0,0 +1,27 @@ +#ifndef MERCURY_KERNEL_FRAMEBUFFER_HPP +#define MERCURY_KERNEL_FRAMEBUFFER_HPP + +#include <cstdint> + +namespace mercury::kernel::framebuffer { + + extern int width; + extern int height; + + void init_framebuffer(uint64_t vaddr, uint64_t width, uint64_t height, uint64_t pitch); + + typedef uint32_t color; + color encode_color(uint8_t r, uint8_t g, uint8_t b); + + void set_pixel(int x, int y, color c); + + //[from_start_x, from_end_x) x [from_start_y, from_end_y) -> [to_start_x, ...) x [to_start_y, ...) + //we assume from_start_x < from_end_x and from_start_y < from_end_y + void move_region(int from_start_x, int from_start_y, int from_end_x, int from_end_y, int to_start_x, int to_start_y); + + //[start_x, end_x) x [start_y, end_y) + void fill_region(int start_x, int start_y, int end_x, int end_y, color c); + +} + +#endif diff --git a/include/mercury/kernel/paging.hpp b/include/mercury/kernel/paging.hpp new file mode 100644 index 0000000..9627162 --- /dev/null +++ b/include/mercury/kernel/paging.hpp @@ -0,0 +1,34 @@ +#ifndef MERCURY_KERNEL_PAGING_HPP +#define MERCURY_KERNEL_PAGING_HPP + +#include <cstdint> + +//in paging.asm +extern "C" [[noreturn]] void switch_to_kernel_p4(void (*and_then_jump_to)()); + +namespace mercury::kernel::paging { + + void mark_all_pram_used(); + void mark_all_vram_free(); + + //assumes page-alignment + void mark_pram_region_free(uint64_t start_addr, uint64_t end_addr); + //assumes page-alignment + void mark_vram_region_used(uint64_t start_addr, uint64_t end_addr); + + uint64_t find_unmapped_vram_region(uint64_t page_count); + + void init_kernel_page_tables(uint64_t kernel_offset); + + void map_kernel_stack(); + + //assumes page-alignment + void map_kernel_page( + uint64_t paddr, uint64_t vaddr, bool write, bool execute); + + uint64_t get_used_vram_page_count(); + uint64_t get_free_pram_page_count(); + +} + +#endif diff --git a/include/mercury/kernel/terminal.hpp b/include/mercury/kernel/terminal.hpp new file mode 100644 index 0000000..b9d9976 --- /dev/null +++ b/include/mercury/kernel/terminal.hpp @@ -0,0 +1,30 @@ +#ifndef MERCURY_KERNEL_TERMINAL_HPP +#define MERCURY_KERNEL_TERMINAL_HPP + +#include <cstdint> + +namespace mercury::kernel::terminal { + + extern uint8_t *termfont; + extern uint64_t termfont_len; + + void init_terminal(); + + extern int width; + extern int height; + + extern int cursor_x; + extern int cursor_y; + + extern framebuffer::color bg_color; + extern framebuffer::color fg_color; + + void put_char(char ch); + + void put_string_sz(const char *str); + + void put_int_decimal(uint64_t n, bool with_commas = true); + +} + +#endif diff --git a/include/mercury/kernel/utility.hpp b/include/mercury/kernel/utility.hpp new file mode 100644 index 0000000..dbf0cf9 --- /dev/null +++ b/include/mercury/kernel/utility.hpp @@ -0,0 +1,124 @@ +#ifndef MERCURY_KERNEL_UTILITY_HPP +#define MERCURY_KERNEL_UTILITY_HPP + +#include <optional> +#include <cstdint> + +namespace mercury::kernel::utility { + + template <class t> + static inline t min(t a, t b) { + return a < b ? a : b; + } + + //includes start_i, does not include end_i + void mark_bitmap_region_zero(uint64_t *bitmap, uint64_t start_i, uint64_t end_i); + //includes start_i, does not include end_i + void mark_bitmap_region_one(uint64_t *bitmap, uint64_t start_i, uint64_t end_i); + + struct uuid { + uint8_t bytes[16]; + }; + + template <class value_t> + struct string_tree { + + std::optional<value_t> value_here = {}; + string_tree<value_t> *parent = 0; + string_tree<value_t> *subtrees[256] = {}; + + //if there is a node whose key has a prefix in common with str, then this + //returns the deepest such node, and sets leftover_out to point to the + //character of str after the common prefix with that returned node. if + //there is no such node, this returns the current node and sets + //leftover_out to a null pointer. + string_tree &max_common_prefix( + const char *str, size_t str_len, const char *&leftover_out) { + + string_tree<value_t> *last_with_value = 0; + const char *leftover_at_last_with_value = 0; + string_tree<value_t> *on = this; + size_t len_so_far = 0; + + while (true) { + + if (on->value_here) { + last_with_value = on; + leftover_at_last_with_value = str + len_so_far; + } + + if (len_so_far == str_len) + break; + + on = on->subtrees[(uint8_t)str[len_so_far]]; + if (!on) + break; + + ++len_so_far; + + } + + if (last_with_value) { + leftover_out = leftover_at_last_with_value; + return *last_with_value; + } + + leftover_out = 0; + return *this; + + } + + bool try_insert(const char *str, size_t str_len, value_t value) { + + string_tree<value_t> *on = this; + for (size_t i = 0; i < str_len; ++i) { + string_tree<value_t> *&subtree = on->subtrees[(uint8_t)str[i]]; + if (!subtree) { + subtree = new string_tree<value_t>(); + subtree->parent = on; + } + on = subtree; + } + + if (on->value_here) + return false; + on->value_here = value; + return true; + + } + + }; + + //if c appears in str, this returns the index of the first time it appears. + //otherwise, this returns len. + static inline size_t find(const char *str, size_t len, char c) { + for (size_t i = 0; i < len; ++i) + if (str[i] == c) + return i; + return len; + } + + template <class value_t> + struct flist { + + struct node { + value_t value; + node *next; + }; + + node *first; + + flist() : first(0) {} + + void insert(value_t value) { + first = new node { + .value = value, + .next = first + }; + } + + }; + +} + +#endif |