aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid <dbphillipsnz@gmail.com>2013-11-11 19:02:19 +1300
committerDavid <dbphillipsnz@gmail.com>2014-03-27 20:32:47 +1300
commitb707eed2ccab33aa5c008a84d4a74788b4b2e52d (patch)
tree7f6402a0025e084559e5fe4646a94c11d9e670ef
parent9d9de30b314f763069ed18fe8da8b6187d6faf38 (diff)
downloadtoast-b707eed2ccab33aa5c008a84d4a74788b4b2e52d.tar.xz
Added %o %b %c in printf(), started memory detection
-rw-r--r--Makefile4
-rw-r--r--boot/boot.asm49
-rw-r--r--kernel.c37
-rw-r--r--lowlevel.h2
-rw-r--r--screen/console.c132
-rw-r--r--screen/console.h16
-rw-r--r--string/common.c60
-rw-r--r--string/common.h8
-rw-r--r--toast.h17
9 files changed, 247 insertions, 78 deletions
diff --git a/Makefile b/Makefile
index 534b71c..4226d9d 100644
--- a/Makefile
+++ b/Makefile
@@ -11,7 +11,8 @@ SOURCES = boot/boot.o \
screen/console.o \
string/common.o \
kernel.o \
- lowlevel.o
+ lowlevel.o\
+ panic.o
all: $(SOURCES) link
@@ -28,5 +29,6 @@ install:
# sudo umount $(TOAST_TARGET)
sudo mount /dev/loop0p1 $(TOAST_TARGET)
sudo cp kernel $(TOAST_TARGET)
+ ls $(TOAST_TARGET)
sudo umount $(TOAST_TARGET)
bochs -qf bochsrc
diff --git a/boot/boot.asm b/boot/boot.asm
index 645061c..d79c9a1 100644
--- a/boot/boot.asm
+++ b/boot/boot.asm
@@ -2,54 +2,53 @@
; get a prototype off the ground quickly without pissing around
; Declare constants used for creating a multiboot header.
-MBALIGN equ 1<<0 ; align loaded modules on page boundaries
-MEMINFO equ 1<<1 ; provide memory map
-FLAGS equ MBALIGN | MEMINFO ; this is the Multiboot 'flag' field
-MAGIC equ 0x1BADB002 ; 'magic number' lets bootloader find the header
-CHECKSUM equ -(MAGIC + FLAGS) ; checksum of above, to prove we are multiboot
-
-; Declare a header as in the Multiboot Standard. We put this into a special
-; section so we can force the header to be in the start of the final program.
-; You don't need to understand all these details as it is just magic values that
-; is documented in the multiboot standard. The bootloader will search for this
-; magic sequence and recognize us as a multiboot kernel.
+MBALIGN equ 1<<0 ; align loaded modules on page boundaries
+MEMINFO equ 1<<1 ; Ask for memory map
+FLAGS equ MBALIGN | MEMINFO
+MAGIC equ 0x1BADB002
+CHECKSUM equ -(MAGIC + FLAGS)
+
+; Standard mutliboot header so GRUB and other bootloaders can boot the kernel
section .multiboot
align 4
dd MAGIC
dd FLAGS
dd CHECKSUM
-; Currently the stack pointer register (esp) points at anything and using it may
-; cause massive harm. Instead, we'll provide our own stack. We will allocate
-; room for a small temporary stack by creating a symbol at the bottom of it,
-; then allocating 16384 bytes for it, and finally creating a symbol at the top.
+; Init our very own 16K stack
section .bootstrap_stack
align 4
stack_bottom:
times 16384 db 0
stack_top:
-; The linker script specifies _start as the entry point to the kernel and the
-; bootloader will jump to this position once the kernel has been loaded. It
-; doesn't make sense to return from this function as the bootloader is gone.
section .text
global _start
+global _kernel_exit
+
_start:
+ ; Functions in external objects
extern kernel_main
- extern console_print
- extern console_set_colors
+ extern console_print_string
+ extern console_set_color
+ ; Set stack up ready for C
mov esp, stack_top
+ push eax
+ push ebx
call kernel_main
; Let the user know that kernel_main() exited
- push word 0x0007
- call console_set_colors
- push mainexit
- call console_print
+ push 0x0A
+ call console_set_color ; Reset text colour
+ push exitmain
+ call console_print_string
+
+ ; Wake us not from our slumber
cli
+_kernel_exit:
.hang:
hlt
jmp .hang
-mainexit db 10,"asm: kernel_main() exited",0
+exitmain db 10,"boot: kernel_main() exited",0 \ No newline at end of file
diff --git a/kernel.c b/kernel.c
index 293045e..bb54c18 100644
--- a/kernel.c
+++ b/kernel.c
@@ -16,7 +16,6 @@
*
*/
-
// Complain if some pleb's not using a cross-compiler
#if defined(__linux__)
#error "You're not using a cross-compiler. Good luck with that."
@@ -24,16 +23,40 @@
#include <toast.h>
-void kernel_main()
+void kernel_main(multiboot_info_t *mbd, unsigned int magic)
{
- char b[10];
console_init();
console_set_colors(COLOR_BRIGHT_GRAY,COLOR_BLACK);
console_clear();
- console_print("Welcome to Toast "KERNEL_VERSION" (nickname '"KERNEL_NICKNAME"')\n");
+ console_print("Welcome to Toast v%d.%d (nickname '%s')\n",KERNEL_VERSION_MAJ,KERNEL_VERSION_MIN,KERNEL_NICKNAME);
console_set_color(COLOR_RED);
+
+ // Print some stuff about the bootload
console_print("Here is kernel_main()\n");
- char test[] = "1234";
- int a = atoi(test);
- itoa(a,b);
+ console_print("Bootloader: %s\n",mbd->boot_loader_name);
+ console_print("BIOS Memory: %d Bytes\n",mbd->mem_upper - mbd->mem_lower);// find out 100% what this is
+ console_print("Kernel: %s\n",mbd->cmdline);
+ console_print("Flags: %b\n",mbd->flags);
+ console_print("Boot Device: %x\n",mbd->boot_device);
+
+ console_print("--------------------------------\nShowing console_print() off...\n%dd in binary is %b\n%oo = %xh = %dd\n%d is the ASCII code for %c\n--------------------------------\n",100,100,1234,1234,1234,112,112);
+
+
+ // Show all memory stuff
+ uint32_t mmaps = mbd->mmap_length;
+
+ multiboot_memory_map_t* mmap = mbd->mmap_addr;
+ while(mmap < mbd->mmap_addr + mbd->mmap_length)
+ {
+ mmap = (multiboot_memory_map_t*) ( (unsigned int)mmap + mmap->size + sizeof(unsigned int) );
+ console_print("%s: 0x%x to 0x%x = %d bytes\n",
+ mmap->type == 1? "AVAILABLE" : "RESERVED ",
+ mmap->addr,
+ mmap->addr+mmap->len-1,
+ mmap->len
+ );
+ }
+
+
+ //panic(0x4655434B); // (TEST) testing panic
} \ No newline at end of file
diff --git a/lowlevel.h b/lowlevel.h
index d4dcb55..0671599 100644
--- a/lowlevel.h
+++ b/lowlevel.h
@@ -20,5 +20,7 @@
#define LOWLEVEL_H
void outb(uint16_t p,uint8_t val);
+void disable_ints();
+void enable_ints();
#endif \ No newline at end of file
diff --git a/screen/console.c b/screen/console.c
index 57f9d6b..00e9ebb 100644
--- a/screen/console.c
+++ b/screen/console.c
@@ -30,6 +30,15 @@ void console_init()
console_pointer = 0;
}
+
+/*********************************************************
+ * Update cursor position to x,y co-ord for next char
+ ********************************************************/
+void console_set_cursor_xy(uint8_t x,uint8_t y)
+{
+ console_pointer = (160*y) + (2*x);
+}
+
/*********************************************************
* Update flashing cursor to match console_position
* Note: Does _NOT_ dictate the pos for next printed byte
@@ -47,18 +56,18 @@ void console_update_cursor()
********************************************************/
void console_clear()
{
- int console_pointer;
- for (console_pointer = 0; console_pointer < 4000; console_pointer++)
+ for (console_pointer = 0; console_pointer < 4000; console_pointer+=2)
{
- console_buffer[console_pointer] = console_color;
- console_buffer[console_pointer++] = 0;
+ console_buffer[console_pointer] = 0;
+ console_buffer[console_pointer+1] = console_color;
}
- //console_update_cursor();
+ console_pointer = 0;
+ console_update_cursor();
}
/*********************************************************
- * Set the console foreground and background colours
+ * Set the console foreground AND background colours
********************************************************/
void console_set_colors(uint8_t fg, uint8_t bg)
{
@@ -67,7 +76,7 @@ void console_set_colors(uint8_t fg, uint8_t bg)
/*********************************************************
- * Set the console foreground colour
+ * Set ONLY the console foreground colour
********************************************************/
void console_set_color(uint8_t fg)
{
@@ -75,26 +84,113 @@ void console_set_color(uint8_t fg)
console_color |= fg; // Apply foreground color
}
+
+/*********************************************************
+ * Print a single character
+ ********************************************************/
+void console_print_char(const char c)
+{
+ // Scroll the screen up a line if the pointer is out of bounds
+ if (console_pointer >= 4000)
+ console_scroll();
+ switch (c)
+ {
+ case 8:
+ console_buffer[console_pointer-=2] = 0;
+ break;
+
+ case 10:
+ console_pointer += 160-(console_pointer%160);
+ break;
+
+ default:
+ console_buffer[console_pointer++] = c;
+ console_buffer[console_pointer++] = console_color;
+ }
+}
+
+
+/*********************************************************
+ * Print an integer of a certain base
+ ********************************************************/
+void console_print_num(const uint32_t num, const uint8_t base)
+{
+ char buffer[32];
+ uint32_t i = 0;
+ if (num == 0)
+ {
+ console_print_char('0');
+ } else {
+ itoa(num,buffer,base);
+ // Find the first digit which isn't a trailing digit
+ while(buffer[i++] == '0');
+ console_print_string(buffer+i-1);
+ }
+}
+
/*********************************************************
- * Print a null-terminated string to the text screen
+ * Print a single null-terminated string
********************************************************/
-void console_print(char *string, ...)
+void console_print_string(const char *string)
{
+ uint16_t i = 0;
+ while(string[i] != 0)
+ console_print_char(string[i++]);
+ console_update_cursor();
+}
+
+/*********************************************************
+ * Print a single null-terminated string
+ ********************************************************/
+void console_scroll(/*uint8_t lines*/)
+{
+ //memcpy(console_buffer, console_buffer+160, 3840);
+ memcpy(console_buffer, console_buffer+160, 3840);
+ memset(console_buffer+3840, 0, 160);
+ console_pointer = 3840;
+}
+
+
+/*********************************************************
+ * Print a formatted string
+ ********************************************************/
+void console_print(const char* format, ...)
+{
+ va_list strings;
+ va_start(strings,format);
uint16_t i;
- for (i = 0; i < strlen(string); i++)
+ uint64_t length = strlen(format);
+
+ for (i = 0; i < length; i++)
{
- // If special char, handle appropriately
- if (string[i] < 32)
+ if (format[i] == '%')
{
- switch (string[i])
- case 10:
- console_pointer = 160 + (console_pointer / 160) * 160;
+ switch (format[++i])
+ {
+ case 's':
+ console_print_string(va_arg(strings, char*));
+ break;
+ case 'c':
+ console_print_char(va_arg(strings, uint64_t));
+ break;
+ case 'd':
+ console_print_num(va_arg(strings, uint64_t),10);
+ break;
+ case 'x':
+ console_print_num(va_arg(strings, uint64_t),16);
+ break;
+ case 'o':
+ console_print_num(va_arg(strings, uint64_t),8);
+ break;
+ case 'b':
+ console_print_num(va_arg(strings, uint64_t),2);
+ break;
+ }
} else {
- console_buffer[console_pointer++] = string[i];
- console_buffer[console_pointer++] = console_color;
+ console_print_char(format[i]);
}
}
- console_update_cursor();
+ va_end(strings);
}
#endif \ No newline at end of file
diff --git a/screen/console.h b/screen/console.h
index 66a867a..f037592 100644
--- a/screen/console.h
+++ b/screen/console.h
@@ -19,6 +19,8 @@
#ifndef __CONSOLE_H
#define __CONSOLE_H
+#include <stdarg.h>
+
#define console_width 80
#define console_height 25
#define console_x_pos (console_pointer%(2*console_width))
@@ -32,28 +34,32 @@
#define COLOR_PURPLE 0x5
#define COLOR_GOLD 0x6
#define COLOR_BRIGHT_GREY 0x7
-#define COLOR_BRIGHT_GRAY 0x7 // Alias for grey vs gray
#define COLOR_GRAY 0x8
-#define COLOR_GREY 0x8 // Alias for grey vs gray
#define COLOR_BRIGHT_BLUE 0x9
#define COLOR_BRIGHT_GREEN 0xA
-#define COLOR_LIME 0xA // Alias for lime vs bright green
#define COLOR_AQUA 0xB
#define COLOR_RED 0xC
#define COLOR_PINK 0xD
#define COLOR_YELLOW 0xE
#define COLOR_WHITE 0xF
+#define COLOR_BRIGHT_GRAY COLOR_BRIGHT_GREY // Alias for grey vs gray
+#define COLOR_GREY COLOR_GRAY // Alias for grey vs gray
+#define COLOR_LIME COLOR_BRIGHT_GREEN // Alias for lime vs bright green
char* console_buffer;
uint16_t console_pointer;
uint8_t console_color;
void console_init();
+void console_set_cursor_xy(uint8_t x,uint8_t y);
void console_update_cursor();
void console_clear();
void console_set_colors(uint8_t fg, uint8_t bg);
void console_set_color(uint8_t fg);
-void console_print(char *string, ...);
-
+void console_print_char(const char c);
+void console_print_string(const char *string);
+void console_print(const char* format,...);
+void console_print_num(uint32_t num, uint8_t base);
+void console_scroll();
#endif \ No newline at end of file
diff --git a/string/common.c b/string/common.c
index d61bdff..6edce1a 100644
--- a/string/common.c
+++ b/string/common.c
@@ -21,31 +21,31 @@
#include <toast.h>
-uint64_t strlen(char *string)
+uint64_t strlen(const char *string)
{
uint64_t l = 0;
- while (string[l] != 0)
- l++;
+ while (string[++l] != 0);
return l;
}
-void itoa(uint32_t num,char *buffer)
+bool itoa(uint32_t num, char *buffer, uint8_t base)
{
+ // Lookup table is valid up to heptadecimal (it's an inside joke)
+ char lookup[] = "0123456789ABCDEFG";
+ if (base > 17)
+ return FALSE;
uint8_t i;
- uint8_t remainder;
-
- for(i = 10; i > 0; i--)
+ /// (Buffer size is 32 bytes)
+ for(i = 31; i > 0; i--)
{
- remainder = num % 10;
- num = (uint32_t)(num /10);
- buffer[i-1] = remainder+48;
- console_print(buffer);
+ buffer[i-1] = lookup[(num % base)];
+ num = (uint32_t)(num/base);
}
- buffer[10] = 0;
-
+ buffer[31] = 0;
+ return TRUE;
}
-uint32_t atoi(char *string)
+uint32_t atoi(const char *string)
{
uint32_t i;
uint32_t multiplier = 1;
@@ -58,4 +58,36 @@ uint32_t atoi(char *string)
return total;
}
+//strcmp()
+// UNFINISHED
+/*bool string_contains(char *haystack, char *needle)
+{
+ return FALSE;
+ uint32_t i;
+ for (i = strlen(haystack)-(strlen(needle)+1); i >= 0; i--)
+ {
+ // if ()
+ }
+}*/
+
+void memcpy(void *to, const void *from, uint32_t size)
+{
+ // TO DO: copy more than one byte at a time
+ char *t = to;
+ const char *f = from;
+ uint32_t i;
+ for (i = 0; i < size; i++)
+ t[i] = f[i];
+}
+
+
+void memset(void *to, uint8_t value, uint32_t size)
+{
+ // TO DO: copy more than one byte at a time
+ char *t = to;
+ uint32_t i;
+ for (i = 0; i < size; i++)
+ t[i] = value;
+
+}
#endif
diff --git a/string/common.h b/string/common.h
index f332f1c..82ad4b1 100644
--- a/string/common.h
+++ b/string/common.h
@@ -19,8 +19,10 @@
#ifndef STRING_COMMON_H
#define STRING_COMMON_H
-uint64_t strlen(char *string);
-void itoa(uint32_t num,char *buffer);
-uint32_t atoi(char *string);
+uint64_t strlen(const char *string);
+bool itoa(uint32_t num, char *buffer, uint8_t base);
+uint32_t atoi(const char *string);
+void memcpy(void *to, const void *from, uint32_t size);
+void memset(void *to, uint8_t value, uint32_t size);
#endif \ No newline at end of file
diff --git a/toast.h b/toast.h
index 479bd41..7aa1c3d 100644
--- a/toast.h
+++ b/toast.h
@@ -19,17 +19,24 @@
#ifndef TOAST_H
#define TOAST_H
-#define KERNEL_VERSION "0.1"
+#define KERNEL_VERSION_MAJ 0
+#define KERNEL_VERSION_MIN 1
#define KERNEL_NICKNAME "Hydrogen"
+#define NULL 0
+#define SUCCESS 1
-#include <stdbool.h> // Get our booleans defined
#include <stdint.h> // uint_8 etc
+#include <stdbool.h> // Get our boolean types defined
-#include <screen/console.h> // Console output functions
-//#include <console.h> // Console output functions
+#define TRUE true
+#define FALSE false
+
+#include <screen/console.h> // Console output functions
#include <lowlevel.h> // Low level assembly, eg outb(port,val)
#include <string/common.h> // Common string functions
-//#include <string.h> // Common string functions
+#include <panic.h> // Kernel panic and emergency procedures
+#include <multiboot.h>
+
// KERNEL.C
void kernel_main();