diff options
| author | Carlos Maiolino <[email protected]> | 2025-07-25 08:20:12 +0200 |
|---|---|---|
| committer | Carlos Maiolino <[email protected]> | 2025-07-25 08:23:02 +0200 |
| commit | ed16669fb8629fde0593bd4b8dc266a697af6245 (patch) | |
| tree | 18d95215f2950c15c47f780850746fad44ab0d7e /src | |
| parent | 8a064d5fb6b426aba5efa32bdbc15a83a0d380af (diff) | |
Add VGA text mode driver
Add driver to deal with VGA text mode.
Also adds a simple vprintl function while I don't implement a print
library.
Signed-off-by: Carlos Maiolino <[email protected]>
Diffstat (limited to 'src')
| -rw-r--r-- | src/include/vga.h | 25 | ||||
| -rw-r--r-- | src/vga.c | 81 |
2 files changed, 106 insertions, 0 deletions
diff --git a/src/include/vga.h b/src/include/vga.h new file mode 100644 index 0000000..7aaa210 --- /dev/null +++ b/src/include/vga.h @@ -0,0 +1,25 @@ +#ifndef VGA_H +#define VGA_H +#include <stddef.h> + +#define VGA_ADDRESS 0xb8000 +#define VGA_WIDTH 80 +#define VGA_HEIGHT 20 + +struct vga_display { + uint16_t *buf; + uint16_t color; + size_t row; + size_t col; +}; + +extern struct vga_display display; + +void vga_put_char(size_t row, size_t col, char c, uint16_t color); +void vga_write_char(char c); +void vprintl(char *str); + +void init_display(uint16_t color); + + +#endif /* VGA_H */ diff --git a/src/vga.c b/src/vga.c new file mode 100644 index 0000000..52109c6 --- /dev/null +++ b/src/vga.c @@ -0,0 +1,81 @@ +#include <stdint.h> +#include <stddef.h> +#include <vga.h> +#include "lib/string.h" + +struct vga_display display; + +void +vga_set_color(uint16_t c) +{ + display.color = c; +} + +void +vga_set_pos(size_t r, size_t c) +{ + display.row = r; + display.col = c; +} + +static uint16_t +vga_build_char(char c, char color) +{ + return (uint16_t)((color << 8) | c); +} + +void +vga_put_char(size_t row, size_t col, char c, uint16_t color) +{ + size_t pos = (VGA_WIDTH * row) + col; + display.buf[pos] = vga_build_char(c, color); +} + +void +vga_write_char(char c) +{ + switch (c) { + case '\n': + vga_set_pos(++display.row, 0); + break; + default: + vga_put_char(display.row, display.col, c, display.color); + display.col++; + } + + + if (display.col == VGA_WIDTH) + vga_set_pos(++display.row, 0); +} + +void +vprintl(char *str) +{ + int i = 0; + size_t len = strlen(str); + + for (i = 0; i <= len; i++) { + vga_write_char(str[i]); + } +} + +static void +clean_display(void) +{ + int row, col; + + for (row = 0; row < VGA_HEIGHT; row++) + for (col = 0; col < VGA_WIDTH; col++) + vga_put_char(row, col, ' ', 0); +} + +void +init_display(uint16_t color) +{ + display.buf = (uint16_t *)VGA_ADDRESS; + vga_set_pos(0, 0); + clean_display(); + vga_set_color(color); + vga_set_pos(0, 0); +} + |
