Initial commit
This commit is contained in:
commit
ecd4fe2bc1
20
Makefile
Normal file
20
Makefile
Normal file
@ -0,0 +1,20 @@
|
||||
.PHONY: all clean install
|
||||
|
||||
all: kernel
|
||||
|
||||
install: kernel
|
||||
mount bootdisk.img /mnt -o loop
|
||||
cp kernel /mnt/kernel
|
||||
umount /mnt
|
||||
|
||||
kernel: start.o link.ld main.o vga.o
|
||||
ld -m elf_i386 -T link.ld -o kernel start.o main.o vga.o
|
||||
|
||||
%.o: %.c
|
||||
gcc -Wall -m32 -O -fstrength-reduce -fomit-frame-pointer -finline-functions -nostdinc -fno-builtin -I./include -c -o $@ $<
|
||||
|
||||
start.o: start.asm
|
||||
nasm -f elf -o start.o start.asm
|
||||
|
||||
clean:
|
||||
rm -f *.o kernel
|
2
README.md
Normal file
2
README.md
Normal file
@ -0,0 +1,2 @@
|
||||
# klange's OS Development Repo #
|
||||
I'm writing an OS because I'm bored and want a massive project to suck up the little pieces of my time for the next few years.
|
BIN
bootdisk.img
Normal file
BIN
bootdisk.img
Normal file
Binary file not shown.
19
include/system.h
Normal file
19
include/system.h
Normal file
@ -0,0 +1,19 @@
|
||||
#ifndef __SYSTEM_H
|
||||
#define __SYSTEM_H
|
||||
|
||||
/* Kernel Main */
|
||||
extern unsigned char *memcpy(unsigned char *dest, const unsigned char *src, int count);
|
||||
extern unsigned char *memset(unsigned char *dest, unsigned char val, int count);
|
||||
extern unsigned short *memsetw(unsigned short *dest, unsigned short val, int count);
|
||||
extern int strlen(const char *str);
|
||||
extern unsigned char inportb (unsigned short _port);
|
||||
extern void outportb (unsigned short _port, unsigned char _data);
|
||||
|
||||
/* VGA driver */
|
||||
extern void cls();
|
||||
extern void putch(unsigned char c);
|
||||
extern void puts(unsigned char *str);
|
||||
extern void settextcolor(unsigned char forecolor, unsigned char backcolor);
|
||||
extern void init_video();
|
||||
|
||||
#endif
|
25
link.ld
Normal file
25
link.ld
Normal file
@ -0,0 +1,25 @@
|
||||
OUTPUT_FORMAT("binary")
|
||||
ENTRY(start)
|
||||
phys = 0x00100000;
|
||||
SECTIONS
|
||||
{
|
||||
.text phys : AT(phys) {
|
||||
code = .;
|
||||
*(.text)
|
||||
*(.rodata)
|
||||
. = ALIGN(4096);
|
||||
}
|
||||
.data : AT(phys + (data - code))
|
||||
{
|
||||
data = .;
|
||||
*(.data)
|
||||
. = ALIGN(4096);
|
||||
}
|
||||
.bss : AT(phys + (bss - code))
|
||||
{
|
||||
bss = .;
|
||||
*(.bss)
|
||||
. = ALIGN(4096);
|
||||
}
|
||||
end = .;
|
||||
}
|
108
main.c
Normal file
108
main.c
Normal file
@ -0,0 +1,108 @@
|
||||
#include <system.h>
|
||||
|
||||
/*
|
||||
* memcpy
|
||||
* Copy from source to destination. Assumes that
|
||||
* source and destination are not overlapping.
|
||||
*/
|
||||
unsigned char *
|
||||
memcpy(
|
||||
unsigned char *dest,
|
||||
const unsigned char *src,
|
||||
int count
|
||||
) {
|
||||
int i;
|
||||
i = 0;
|
||||
for ( ; i < count; ++i ) {
|
||||
dest[i] = src[i];
|
||||
|
||||
}
|
||||
return dest;
|
||||
}
|
||||
|
||||
/*
|
||||
* memset
|
||||
* Set `count` bytes to `val`.
|
||||
*/
|
||||
unsigned char *
|
||||
memset(
|
||||
unsigned char *dest,
|
||||
unsigned char val,
|
||||
int count
|
||||
) {
|
||||
int i;
|
||||
i = 0;
|
||||
for ( ; i < count; ++i ) {
|
||||
dest[i] = val;
|
||||
}
|
||||
return dest;
|
||||
}
|
||||
|
||||
/*
|
||||
* memsetw
|
||||
* Set `count` shorts to `val`.
|
||||
*/
|
||||
unsigned short *
|
||||
memsetw(
|
||||
unsigned short *dest,
|
||||
unsigned short val,
|
||||
int count
|
||||
) {
|
||||
int i;
|
||||
i = 0;
|
||||
for ( ; i < count; ++i ) {
|
||||
dest[i] = val;
|
||||
}
|
||||
return dest;
|
||||
}
|
||||
|
||||
/*
|
||||
* strlen
|
||||
* Returns the length of a given `str`.
|
||||
*/
|
||||
int
|
||||
strlen(
|
||||
const char *str
|
||||
) {
|
||||
int i = 0;
|
||||
while (str[i] != (char)0) {
|
||||
++i;
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
/*
|
||||
* inportb
|
||||
* Read from an I/O port.
|
||||
*/
|
||||
unsigned char
|
||||
inportb(
|
||||
unsigned short _port
|
||||
) {
|
||||
unsigned char rv;
|
||||
__asm__ __volatile__ ("inb %1, %0" : "=a" (rv) : "dN" (_port));
|
||||
return rv;
|
||||
}
|
||||
|
||||
/*
|
||||
* outportb
|
||||
* Write to an I/O port.
|
||||
*/
|
||||
void
|
||||
outportb(
|
||||
unsigned short _port,
|
||||
unsigned char _data
|
||||
) {
|
||||
__asm__ __volatile__ ("outb %1, %0" : : "dN" (_port), "a" (_data));
|
||||
}
|
||||
|
||||
/*
|
||||
* Kernel Entry Point
|
||||
*/
|
||||
int
|
||||
main() {
|
||||
init_video();
|
||||
puts("Hello world!\n");
|
||||
for (;;);
|
||||
return 0;
|
||||
}
|
44
start.asm
Normal file
44
start.asm
Normal file
@ -0,0 +1,44 @@
|
||||
[BITS 32]
|
||||
global start
|
||||
start:
|
||||
mov esp, _sys_stack
|
||||
jmp stublet
|
||||
|
||||
ALIGN 4
|
||||
mboot:
|
||||
MULTIBOOT_PAGE_ALIGN equ 1<<0
|
||||
MULTIBOOT_MEMORY_INFO equ 1<<1
|
||||
MULTIBOOT_AOUT_KLUDGE equ 1<<16
|
||||
MULTIBOOT_HEADER_MAGIC equ 0x1BADB002
|
||||
MULTIBOOT_HEADER_FLAGS equ MULTIBOOT_PAGE_ALIGN | MULTIBOOT_MEMORY_INFO | MULTIBOOT_AOUT_KLUDGE
|
||||
MULTIBOOT_CHECKSUM equ -(MULTIBOOT_HEADER_MAGIC + MULTIBOOT_HEADER_FLAGS)
|
||||
EXTERN code, bss, end
|
||||
; GRUB Multiboot header, boot signature
|
||||
dd MULTIBOOT_HEADER_MAGIC
|
||||
dd MULTIBOOT_HEADER_FLAGS
|
||||
dd MULTIBOOT_CHECKSUM
|
||||
; AOUT kludge (must be physical addresses)
|
||||
; Linker script fills these in
|
||||
dd mboot
|
||||
dd code
|
||||
dd bss
|
||||
dd end
|
||||
dd start
|
||||
|
||||
; Main entrypoint
|
||||
stublet:
|
||||
extern main
|
||||
call main
|
||||
jmp $
|
||||
|
||||
; GDT
|
||||
|
||||
; Interrupt Service Routines
|
||||
|
||||
; BSS Section
|
||||
SECTION .bss
|
||||
resb 8192 ; 8KB of memory reserved
|
||||
_sys_stack:
|
||||
; This line intentionally left blank
|
||||
|
||||
|
140
vga.c
Normal file
140
vga.c
Normal file
@ -0,0 +1,140 @@
|
||||
#include <system.h>
|
||||
|
||||
/*
|
||||
* Text pointer, background, foreground
|
||||
*/
|
||||
unsigned short * textmemptr;
|
||||
int attrib = 0x0F;
|
||||
int csr_x = 0, csr_y = 0;
|
||||
|
||||
/*
|
||||
* scroll
|
||||
* Scroll the screen
|
||||
*/
|
||||
void
|
||||
scroll() {
|
||||
unsigned blank, temp;
|
||||
blank = 0x20 | (attrib << 8);
|
||||
if (csr_y >= 25) {
|
||||
/*
|
||||
* Move the current text chunk that makes up the screen
|
||||
* back in the buffer by one line.
|
||||
*/
|
||||
temp = csr_y - 25 + 1;
|
||||
memcpy(textmemptr, textmemptr + temp * 80, (25 - temp) * 80 * 2);
|
||||
/*
|
||||
* Set the chunk of memory that occupies
|
||||
* the last line of text to the blank character
|
||||
*/
|
||||
memsetw(textmemptr + (25 - temp) * 80, blank, 80);
|
||||
csr_y = 25 - 1;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* move_csr
|
||||
* Update the hardware cursor
|
||||
*/
|
||||
void
|
||||
move_csr() {
|
||||
unsigned temp;
|
||||
temp = csr_y * 80 + csr_x;
|
||||
|
||||
/*
|
||||
* Write stuff out.
|
||||
*/
|
||||
outportb(0x3D4, 14);
|
||||
outportb(0x3D5, temp >> 8);
|
||||
outportb(0x3D4, 15);
|
||||
outportb(0x3D5, temp);
|
||||
}
|
||||
|
||||
/*
|
||||
* cls
|
||||
* Clear the screen
|
||||
*/
|
||||
void
|
||||
cls() {
|
||||
unsigned blank;
|
||||
int i;
|
||||
blank = 0x20 | (attrib << 8);
|
||||
for (i = 0; i < 25; ++i) {
|
||||
memsetw(textmemptr + i * 80, blank, 80);
|
||||
}
|
||||
csr_x = 0;
|
||||
csr_y = 0;
|
||||
move_csr();
|
||||
}
|
||||
|
||||
/*
|
||||
* putch
|
||||
* Puts a character to the screen
|
||||
*/
|
||||
void
|
||||
putch(
|
||||
unsigned char c
|
||||
) {
|
||||
unsigned short *where;
|
||||
unsigned att = attrib << 8;
|
||||
if (c == 0x08) {
|
||||
/* Backspace */
|
||||
if (csr_x != 0) csr_x--;
|
||||
} else if (c == 0x09) {
|
||||
/* Tab */
|
||||
csr_x = (csr_x + 8) & ~(8 - 1);
|
||||
} else if (c == '\r') {
|
||||
/* Carriage return */
|
||||
csr_x = 0;
|
||||
} else if (c == '\n') {
|
||||
/* New line */
|
||||
csr_x = 0;
|
||||
csr_y++;
|
||||
} else if (c >= ' ') {
|
||||
where = textmemptr + (csr_y * 80 + csr_x);
|
||||
*where = c | att;
|
||||
csr_x++;
|
||||
}
|
||||
|
||||
if (csr_x >= 80) {
|
||||
csr_x = 0;
|
||||
csr_y++;
|
||||
}
|
||||
scroll();
|
||||
move_csr();
|
||||
}
|
||||
|
||||
/*
|
||||
* puts
|
||||
* Put string to screen
|
||||
*/
|
||||
void
|
||||
puts(
|
||||
unsigned char * text
|
||||
){
|
||||
int i;
|
||||
int len = strlen(text);
|
||||
for (i = 0; i < len; ++i) {
|
||||
putch(text[i]);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* settextcolor
|
||||
* Sets the foreground and background color
|
||||
*/
|
||||
void
|
||||
settextcolor(
|
||||
unsigned char forecolor,
|
||||
unsigned char backcolor
|
||||
) {
|
||||
attrib = (backcolor << 4) | (forecolor & 0x0F);
|
||||
}
|
||||
|
||||
/*
|
||||
* init_video
|
||||
* Initialize the VGA driver.
|
||||
*/
|
||||
void init_video() {
|
||||
textmemptr = (unsigned short *)0xB8000;
|
||||
cls();
|
||||
}
|
Loading…
Reference in New Issue
Block a user