summaryrefslogtreecommitdiff
path: root/term/term.ha
diff options
context:
space:
mode:
authorAlejandro Sior <aho@sior.be>2022-05-13 20:50:39 +0200
committerAlejandro Sior <aho@sior.be>2022-05-13 20:50:39 +0200
commite50cbe8eb763cf63fb44b047d5164f6fbf07eb39 (patch)
tree8acb610a4f33462c843f54016861780ffadc010d /term/term.ha
boot: longmode to realmode stub
This is the initial commit to the repo. It adds all the code. The last proper thing that I got working before committing is calling real mode functions from long mode using a stub. Next up, I would like to implement a disk reader abstraction over the BIOS in order to read form partitions (most notably FAT32).
Diffstat (limited to 'term/term.ha')
-rw-r--r--term/term.ha116
1 files changed, 116 insertions, 0 deletions
diff --git a/term/term.ha b/term/term.ha
new file mode 100644
index 0000000..3104e71
--- /dev/null
+++ b/term/term.ha
@@ -0,0 +1,116 @@
+// Defines the colors that a terminal is expected to implement.
+// These are the classical VGA colors.
+export type color = enum {
+ BLACK,
+ BLUE,
+ GREEN,
+ CYAN,
+ RED,
+ MAGENTA,
+ BROWN,
+ LGRAY,
+ DGRAY,
+ LBLUE,
+ LGREEN,
+ LCYAN,
+ LRED,
+ YELLOW,
+ LMAGENTA,
+ WHITE
+};
+
+export type vtable = struct {
+ setpos: *fn(_: *term, _: (size, size)) void,
+ getpos: *fn(_: *term) (size, size),
+ setcolors: *fn(_: *term, _: (color, color)) void,
+ getcolors: *fn(_: *term) (color, color),
+ putchar: *fn(_: *term, _: u8) void,
+ getdim: *fn(_: *term) (size, size),
+};
+
+export type term = *vtable;
+
+export fn setpos(ctrl: *term, pos: (size, size)) void = {
+ ctrl.setpos(ctrl, pos);
+};
+export fn getpos(ctrl: *term) (size, size) = {
+ return ctrl.getpos(ctrl);
+};
+export fn setcolors(ctrl: *term, colors: (color, color)) void = {
+ ctrl.setcolors(ctrl, colors);
+};
+export fn getcolors(ctrl: *term) (color, color) = {
+ return ctrl.getcolors(ctrl);
+};
+export fn putchar(ctrl: *term, c: u8) void = {
+ ctrl.putchar(ctrl, c);
+};
+export fn getdim(ctrl: *term) (size, size) = {
+ return ctrl.getdim(ctrl);
+};
+
+
+fn advancex(ctrl: *term) void = {
+ let dim = getdim(ctrl);
+ let pos = getpos(ctrl);
+
+ pos.0 += 1;
+ if (pos.0 >= dim.0) {
+ newline(ctrl);
+ } else {
+ setpos(ctrl, pos);
+ };
+};
+
+fn newline(ctrl: *term) void = {
+ let dim = getdim(ctrl);
+ let pos = getpos(ctrl);
+
+ pos.0 = 0;
+ pos.1 += 1;
+
+ if (pos.1 >= dim.1) {
+ clear(ctrl);
+ setpos(ctrl, (0, 0));
+ } else {
+ setpos(ctrl, pos);
+ };
+};
+
+fn carriage(ctrl: *term) void = {
+ let pos = getpos(ctrl);
+
+ pos.0 = 0;
+ setpos(ctrl, pos);
+};
+
+export fn print(ctrl: *term, msg: str) void = {
+ let msg = *(&msg: *[]u8);
+
+ for (let i = 0z; i < len(msg); i += 1) {
+ switch (msg[i]) {
+ case '\n' => newline(ctrl);
+ case '\r' => carriage(ctrl);
+ case =>
+ putchar(ctrl, msg[i]);
+ advancex(ctrl);
+ };
+ };
+};
+
+export fn clear(ctrl: *term) void = {
+ let colors = getcolors(ctrl);
+ setcolors(ctrl, (colors.1, colors.1));
+ let dim = getdim(ctrl);
+ let pos = getpos(ctrl);
+
+ for (let j = 0z; j < dim.1; j += 1) {
+ for (let i = 0z; i < dim.0; i += 1) {
+ setpos(ctrl, (i, j));
+ putchar(ctrl, ' ');
+ };
+ };
+
+ setpos(ctrl, pos);
+ setcolors(ctrl, colors);
+};