From a50c2a1233dc1f247a812ccafb2f3e11fa18c9bf Mon Sep 17 00:00:00 2001 From: Josh Holtrop Date: Mon, 2 Aug 2004 22:00:00 -0400 Subject: [PATCH] Import backup from 2004-08-02 --- .bochsrc | 2 +- Makefile | 2 +- kernel/Makefile | 9 +- kernel/char/console.c | 44 +++++++ kernel/char/console.h | 24 ++++ kernel/char/keyboard.c | 247 +++++++++++++++++++++++++++++++++++ kernel/char/keyboard.h | 49 +++++++ kernel/char/mouse.c | 52 ++++++++ kernel/char/mouse.h | 15 +++ kernel/char/parallel.c | 15 +++ kernel/char/parallel.h | 13 ++ kernel/fs/devices.c | 4 + kernel/fs/devices.h | 3 + kernel/hos_defines.h | 1 + kernel/kernel.c | 59 ++++++--- kernel/kout.c | 122 +++++++++++++++++ kernel/kout.h | 19 +++ kernel/{ => lang}/asmfuncs.h | 0 kernel/lang/conv.c | 83 ++++++++++++ kernel/lang/conv.h | 16 +++ kernel/mm/vmm.c | 24 ++-- 21 files changed, 766 insertions(+), 37 deletions(-) create mode 100644 kernel/char/console.c create mode 100644 kernel/char/console.h create mode 100644 kernel/char/keyboard.c create mode 100644 kernel/char/keyboard.h create mode 100644 kernel/char/mouse.c create mode 100644 kernel/char/mouse.h create mode 100644 kernel/char/parallel.c create mode 100644 kernel/char/parallel.h create mode 100644 kernel/kout.c create mode 100644 kernel/kout.h rename kernel/{ => lang}/asmfuncs.h (100%) create mode 100644 kernel/lang/conv.c create mode 100644 kernel/lang/conv.h diff --git a/.bochsrc b/.bochsrc index 8a4ad77..d7b38b4 100644 --- a/.bochsrc +++ b/.bochsrc @@ -11,7 +11,7 @@ ata0: enabled=1, ioaddr1=0x1f0, ioaddr2=0x3f0, irq=14 ata1: enabled=0 ata2: enabled=0 ata3: enabled=0 -parport1: enabled=1, file="" +parport1: enabled=1, file="parallel.out" com1: enabled=1, dev="" usb1: enabled=1, ioaddr=0xff80, irq=10 # no sb16 diff --git a/Makefile b/Makefile index 2fa1480..9c536de 100644 --- a/Makefile +++ b/Makefile @@ -14,7 +14,7 @@ all: clean: - make -C kernel clean - make -C rmmod clean - - rm *~ hos.flp + - rm *~ *.out hos.flp \#* grub: diff --git a/kernel/Makefile b/kernel/Makefile index aebbee9..6cabcab 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -16,7 +16,9 @@ LD=ld LD_FLAGS=-nodefaultlibs -nostdlib --no-demangle -T link.ld all: Asm_Kernel C_Kernel - $(LD) $(LD_FLAGS) -Map kernel.map boot.o kernel.o asmfuncs.o mm.o vmm.o -o kernel.bin + $(LD) $(LD_FLAGS) -Map kernel.map boot.o \ + kernel.o asmfuncs.o mm.o vmm.o parallel.o \ + conv.o kout.o -o kernel.bin Asm_Kernel: $(NASM) $(NASM_FLAGS) -l boot.lst boot.asm -o boot.o @@ -26,11 +28,14 @@ C_Kernel: $(CC) $(CC_FLAGS) -c kernel.c -o kernel.o $(CC) $(CC_FLAGS) -c mm/mm.c -o mm.o $(CC) $(CC_FLAGS) -c mm/vmm.c -o vmm.o + $(CC) $(CC_FLAGS) -c char/parallel.c -o parallel.o + $(CC) $(CC_FLAGS) -c lang/conv.c -o conv.o + $(CC) $(CC_FLAGS) -c kout.c -o kout.o ################################################# # Clean up the source directory of any binaries # ################################################# clean: - - rm *.o *.bin *.map *.lst *~ + - rm *.o *.bin *.map *.lst *.out *~ diff --git a/kernel/char/console.c b/kernel/char/console.c new file mode 100644 index 0000000..21ccff6 --- /dev/null +++ b/kernel/char/console.c @@ -0,0 +1,44 @@ +// console.c +// Author: Josh Holtrop +// Date: 08/02/04 + +#include "char/console.h" +#include "hos_defines.h" +#include "fs/devices.h" + +console_t *consoles[256]; + +int console_new(minor_t minor) +{ + if (consoles[minor]) + return -1; // minor already taken + if ( consoles[minor] = kmalloc(sizeof(console_t)) ) + { + consoles[minor]->cursorPosition = 0; + consoles[minor]->width = 80; + consoles[minor]->height = 25; + consoles[minor]->attribute = 0x07; + if (consoles[minor]->buffer = kmalloc(4000)) + { + memsetw(consoles[minor]->buffer, 0, 2000); + } + else + { + kfree (consoles[minor]); + consoles[minor] = 0; + return -3; // couldn't allocate memory + } + + return 0; + } + else + return -2; // couldn't allocate memory +} + +void console_outb(minor_t id, int c) +{ + if (!consoles[minor]) + return; + +} + diff --git a/kernel/char/console.h b/kernel/char/console.h new file mode 100644 index 0000000..dc6512e --- /dev/null +++ b/kernel/char/console.h @@ -0,0 +1,24 @@ +// console.h +// Author: Josh Holtrop +// Date: 08/02/04 + +#ifndef __HOS_CONSOLE__ +#define __HOS_CONSOLE__ __HOS_CONSOLE__ + +#include "hos_defines.h" +#include "fs/devices.h" + +typedef struct +{ + u32_t cursorPosition; + u16_t width; + u16_t height; + u8_t attribute; + u16_t *buffer; +} console_t; + +int console_new(minor_t minor); +void console_outb(minor_t id, int c); + +#endif + diff --git a/kernel/char/keyboard.c b/kernel/char/keyboard.c new file mode 100644 index 0000000..74b2fa9 --- /dev/null +++ b/kernel/char/keyboard.c @@ -0,0 +1,247 @@ +// keyboard.c +// Author: Josh Holtrop +// Created: 04/17/03 +// Modified: 08/02/04 + +#include "hos_defines.h" +#include "char/keyboard.h" +#include "sys/io.h" +#include "sys/pic.h" +#include "functions.h" +#include "kio.h" + +#define KBD_BUFFER_LENGTH 64 + +byte kbdFlags = 0; //holds current keyboard flags - caps/num/scroll/shift/ctrl/alt +byte kbdAscii = 0; //holds ASCII value of a key pressed +byte kbdScan = 0; //holds the keyboard scan code of a key pressed + +dword kbdBuffer[KBD_BUFFER_LENGTH]; //a buffer for all keypresses +int kbdBufferStart = 0; //position of next key in buffer +int kbdBufferLen = 0; //number of keys left in the buffer +byte kbdExt = 0; //# of extended key codes left to input +byte kbdExt2 = 0; //# of 2nd-set-extended key codes left to input +byte ackReason = 0; //used to record the reason why we would get an acknowledge byte (0xFA) + + +//these arrays convert a keyboard scan code to an ASCII character value + //nul esc bksp tab lctl lsft rsft lalt caps F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 numScrlNumPad------- unknown---- F11 F12 unknown.... +const byte SCAN2ASCII[129] = "\000\0331234567890-=\010\011qwertyuiop[]\n\001asdfghjkl;'`\001\\zxcvbnm,./\001*\001 \001\001\001\001\001\001\001\001\001\001\001\001\001\001\001\001-\001\001\001+\001\001\001\001\001\002\002\002\001\001\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002"; +const byte SCAN2ASCIISHIFT[129] = "\000\033!@#$%^&*()_+\010\011QWERTYUIOP{}\n\001ASDFGHJKL:\"~\001|ZXCVBNM<>?\001*\001 \001\001\001\001\001\001\001\001\001\001\001\001\001789-456+1230.\002\002\002\001\001\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002\002"; + +//====FUNCTIONS: +// The Keyboard Interrupt Service Routine +void isr_keyboard() +{ + kbdScan = inportb(0x60); + //printf("\nKEYBOARD INTERRUPT: 0x%x", kbdScan); + byte inState = inportb(0x61); + outportb(0x61, inState|0x80); + outportb(0x61, inState); + + //printf("IRQ 1: %x\n", kbdScan); + + if (kbdScan == 0xFA) //250 //ACKnowledge + { + //printf("KBD_ACK 0x%x!\n", ackReason); + if (ackReason == 0xED) //reset LEDs + { + outportb(0x60, (kbdFlags & 0x07)); + } + ackReason = 0; + } + if (kbdScan == 224) //extended key + { + kbdExt = 1; + pic_eoi(); + return; + } + if (kbdScan == 225) //2nd-set-extended key + { + kbdExt2 = 2; + pic_eoi(); + return; + } + +//====handle control keys:: + kbdAscii = 2; + switch (kbdScan) //control keys + { + case KBD_SCAN_LSHIFT: + kbdFlags |= KBD_SHIFT; + kbdAscii = 1; + break; + case KBD_SCAN_RSHIFT: + kbdFlags |= KBD_SHIFT; + kbdAscii = 1; + break; + case KBD_SCAN_LCTRL: + kbdFlags |= KBD_CTRL; + kbdAscii = 1; + break; + case KBD_SCAN_LALT: + kbdFlags |= KBD_ALT; + kbdAscii = 1; + break; + + case KBD_SCAN_LSHIFT + KBD_SCAN_RELEASED: + kbdFlags &= (KBD_SHIFT ^ 0xFF); + kbdAscii = 1; + break; + case KBD_SCAN_RSHIFT + KBD_SCAN_RELEASED: + kbdFlags &= (KBD_SHIFT ^ 0xFF); + kbdAscii = 1; + break; + case KBD_SCAN_LCTRL + KBD_SCAN_RELEASED: + kbdFlags &= (KBD_CTRL ^ 0xFF); + kbdAscii = 1; + break; + case KBD_SCAN_LALT + KBD_SCAN_RELEASED: + kbdFlags &= (KBD_ALT ^ 0xFF); + kbdAscii = 1; + break; + + case KBD_SCAN_CAPS+KBD_SCAN_RELEASED: + kbdFlags ^= KBD_CAPS; + kbdAscii = 1; + kbd_resetLEDs(); //update LEDs + break; + case KBD_SCAN_SCROLL+KBD_SCAN_RELEASED: + kbdFlags ^= KBD_SCROLL; + kbdAscii = 1; + kbd_resetLEDs(); //update LEDs + break; + case KBD_SCAN_NUM+KBD_SCAN_RELEASED: + kbdFlags ^= KBD_NUM; + kbdAscii = 1; + kbd_resetLEDs(); //update LEDs + break; + } + if (kbdAscii == 1) + { + if (kbdExt > 0) + kbdExt--; + pic_eoi(); + return; + } +//====determine ASCII value of key:: + if (kbdExt > 0) //extended key, kbdScan holds extended key + { + kbdExt--; + kbdAscii = 1; + switch (kbdScan) + { + case KBD_SCANE_ENTER: + kbdAscii = '\n'; break; + case 53: // '/' character (divide on numpad) + kbdAscii = '/'; break; + } + } + else if (kbdExt2 > 0) //extended key 2 + { + kbdExt2--; +// if (kbdScan == 69) // (pause|break) +// kbdAscii = 2; //flag ascii value of 1 means control character (pausebreak) +// else + kbdAscii = 2; //flag ascii value of 2 means ignore key (or unknown value) + } + else //not an extended key + { + // if letter key + if (((kbdScan >= 16) && (kbdScan <= 25)) || ((kbdScan >= 30) && (kbdScan <= 38)) || ((kbdScan >= 44) && (kbdScan <= 50))) + { + // if caps and shift are different (either one pressed, not both) + if (((kbdFlags & KBD_SHIFT) != 0) & ((kbdFlags & KBD_CAPS) != 0)) + kbdAscii = SCAN2ASCII[kbdScan & 0x7F]; + else if (((kbdFlags & KBD_SHIFT) == 0) & ((kbdFlags & KBD_CAPS) == 0)) + kbdAscii = SCAN2ASCII[kbdScan & 0x7F]; + else + kbdAscii = SCAN2ASCIISHIFT[kbdScan & 0x7F]; + } + // if numpad key + else if ((kbdScan >= 71) && (kbdScan <= 83)) + { + // if numlock on + if (kbdFlags & KBD_NUM) + kbdAscii = SCAN2ASCIISHIFT[kbdScan & 0x7F]; + else + kbdAscii = SCAN2ASCII[kbdScan & 0x7F]; + } + // other key + else + { + if ((kbdFlags & KBD_SHIFT) != 0) + kbdAscii = SCAN2ASCIISHIFT[kbdScan & 0x7F]; + else + kbdAscii = SCAN2ASCII[kbdScan & 0x7F]; + } + } + +//====do something with key:: +// printf("kbdScan == %d\nkbdAscii == %d\nkbdFlags == %d\n", kbdScan, kbdAscii, kbdFlags); + if ((kbdScan == 83) && (kbdFlags & KBD_CTRL) && (kbdFlags & KBD_ALT)) + { + printf("Initiating reboot."); + restart(); + } + if (kbdAscii == 2) //unknown key / ignore key + { + pic_eoi(); + return; + } + if (kbdScan < KBD_SCAN_RELEASED) //a key was pressed, save it + { + if (kbdBufferLen >= KBD_BUFFER_LENGTH) //no key slots available + { + pic_eoi(); + return; + } + else + { + kbdBuffer[(kbdBufferStart+kbdBufferLen++)%KBD_BUFFER_LENGTH] = (dword) ((kbdFlags << 16) | (kbdScan << 8) | kbdAscii); +// printf("S:%d\tL:%d\tR:%x\n", kbdBufferStart, kbdBufferLen, kbdBuffer[kbdBufferStart]); + } + } + + pic_eoi(); + +} + +//Gets a key from the buffer, returns 0 if no keys available, returns immediately +dword kbdGetKey() +{ + if (kbdBufferLen == 0) //buffer empty + return 0; + dword retVal = kbdBuffer[kbdBufferStart]; + kbdBufferStart++; + kbdBufferLen--; + if (kbdBufferStart >= KBD_BUFFER_LENGTH) + kbdBufferStart = 0; + return retVal; +} + +//Gets a key from the buffer, if no keys available, waits for one to be entered +dword kbdWaitKey() +{ + for (;;) + { + if (kbdBufferLen != 0) //buffer empty + break; + } + dword retVal = kbdBuffer[kbdBufferStart]; + kbdBufferStart++; + kbdBufferLen--; + if (kbdBufferStart >= KBD_BUFFER_LENGTH) + kbdBufferStart = 0; + return retVal; +} + +//Resets the keyboard LEDs to reflect the current state of the num lock, caps lock, and scroll lock bits +void kbd_resetLEDs() +{ + outportb(0x60, 0xED); + ackReason = 0xED; +} + + + diff --git a/kernel/char/keyboard.h b/kernel/char/keyboard.h new file mode 100644 index 0000000..130c0ce --- /dev/null +++ b/kernel/char/keyboard.h @@ -0,0 +1,49 @@ +// keyboard.h +// Author: Josh Holtrop +// Created: 04/17/03 +// Modified: 08/02/04 + +#include "hos_defines.h" + +#ifndef __HOS_KEYBOARD__ +#define __HOS_KEYBOARD__ __HOS_KEYBOARD__ + +#define KBD_SCROLL 0x01 +#define KBD_NUM 0x02 +#define KBD_CAPS 0x04 +#define KBD_SHIFT 0x10 +#define KBD_CTRL 0x20 +#define KBD_ALT 0x40 + +#define KBD_SCAN_RELEASED 128 + +#define KBD_SCAN_LCTRL 29 +#define KBD_SCAN_LSHIFT 42 +#define KBD_SCAN_RSHIFT 54 +#define KBD_SCAN_LALT 56 +#define KBD_SCAN_SCROLL 70 +#define KBD_SCAN_CAPS 58 +#define KBD_SCAN_NUM 69 + +#define KBD_SCANE_PRINTSCREEN 55 +#define KBD_SCANE_INS 82 +#define KBD_SCANE_HOME 71 +#define KBD_SCANE_PGUP 73 +#define KBD_SCANE_DEL 83 +#define KBD_SCANE_END 79 +#define KBD_SCANE_PGDN 81 +#define KBD_SCANE_ENTER 28 + +#define KBD_SCANE_NULL 42 + + + +//====PROTOTYPES: + +void isr_keyboard(); +void kbd_resetLEDs(); +u32_t kbdGetKey(); +u32_t kbdWaitKey(); + +#endif + diff --git a/kernel/char/mouse.c b/kernel/char/mouse.c new file mode 100644 index 0000000..7519781 --- /dev/null +++ b/kernel/char/mouse.c @@ -0,0 +1,52 @@ +// mouse.c +// Author: Josh Holtrop +// Date: 10/03/03 +// Modified: 08/02/04 + +#include "hos_defines.h" +#include "char/mouse.h" +#include "video/video.h" +#include "sys/io.h" + +int mouse_bytesRead; +byte mouse_inbuffer[MOUSE_BUFFER_LENGTH]; + +//This method initializes the ps/2 mouse +void mouse_init() +{ + outportb(0x64, 0x20); //tell keyboard controller we are going to read keyboard controller command byte + byte temp = inportb(0x60); //read keyboard controller command byte + outportb(0x64, 0x60); //tell keyboard controller we are going to write keyboard controller command byte + outportb(0x60, 0x03 | (temp & 0x40)); //write keyboard controller command byte: enable mouse/keyboard ints, include original XLATE bit from temp (bit6) + + outportb(0x64, 0xA8); //enable mouse port + + outportb(0x64, 0xD4); //send command to mouse, not kbd + outportb(0x60, 0xF4); //enable data reporting + + mouse_bytesRead = 0; + + //outportb(0x64, 0xD4); + //outportb(0x60, 0xE7); //scaling 2:1 +} + + +//This method is called when a mouse interrupt occurs +void isr_mouse() +{ + byte inb = inportb(0x60); //read mouse byte + if ((inb == 0xFA) && (mouse_bytesRead < 1)) //ACK + return; + mouse_inbuffer[mouse_bytesRead] = inb; + mouse_bytesRead++; + if (mouse_bytesRead == 3) //complete packet received + { + mouse_bytesRead = 0; + int adjx = (char) mouse_inbuffer[1]; + int adjy = (char) mouse_inbuffer[2]; + // TODO: do something with adjx, adjy... + } +} + + + diff --git a/kernel/char/mouse.h b/kernel/char/mouse.h new file mode 100644 index 0000000..6331369 --- /dev/null +++ b/kernel/char/mouse.h @@ -0,0 +1,15 @@ +// mouse.h +// Author: Josh Holtrop +// Date: 10/03/03 +// Modified: 08/02/04 + +#ifndef __HOS_MOUSE__ +#define __HOS_MOUSE__ __HOS_MOUSE__ + +#define MOUSE_BUFFER_LENGTH 16 + +void mouse_init(); +void isr_mouse(); + +#endif + diff --git a/kernel/char/parallel.c b/kernel/char/parallel.c new file mode 100644 index 0000000..8427065 --- /dev/null +++ b/kernel/char/parallel.c @@ -0,0 +1,15 @@ +// parallel.c +// Author: Josh Holtrop +// Date: 08/02/04 + +#include "hos_defines.h" +#include "functions.h" +#include "parallel.h" + +void outparb(int c) +{ + outportb(0x37a, 0xc); + outportb(0x378, c); + outportb(0x37a, 0x1); +} + diff --git a/kernel/char/parallel.h b/kernel/char/parallel.h new file mode 100644 index 0000000..929ba60 --- /dev/null +++ b/kernel/char/parallel.h @@ -0,0 +1,13 @@ +// parallel.h +// Author: Josh Holtrop +// Date: 08/02/04 + +#ifndef __HOS_PARALLEL__ +#define __HOS_PARALLEL__ __HOS_PARALLEL__ + +#include "hos_defines.h" + +void outparb(int c); + +#endif + diff --git a/kernel/fs/devices.c b/kernel/fs/devices.c index edb219d..d2d4ace 100644 --- a/kernel/fs/devices.c +++ b/kernel/fs/devices.c @@ -1,3 +1,7 @@ +// devices.c +// Author: Josh Holtrop +// Date: 08/02/04 + #include "fs/devices.h" #include "kernel.h" diff --git a/kernel/fs/devices.h b/kernel/fs/devices.h index 8819068..392cdb3 100644 --- a/kernel/fs/devices.h +++ b/kernel/fs/devices.h @@ -1,3 +1,6 @@ +// devices.h +// Author: Josh Holtrop +// Date: 08/02/04 #ifndef __HOS_DEVICES_H__ diff --git a/kernel/hos_defines.h b/kernel/hos_defines.h index 5d0dd27..dd16e7a 100644 --- a/kernel/hos_defines.h +++ b/kernel/hos_defines.h @@ -2,6 +2,7 @@ #ifndef __HOS_DEFINES_H__ #define __HOS_DEFINES_H__ __HOS_DEFINES_H__ +#define PARALLEL_DEBUG #define VIRT_OFFSET 0xC0000000 #define PHYS_LOAD 0x00108000 diff --git a/kernel/kernel.c b/kernel/kernel.c index 8090cff..1421404 100644 --- a/kernel/kernel.c +++ b/kernel/kernel.c @@ -2,10 +2,13 @@ #include "kernel.h" #include "multiboot.h" #include "module.h" -#include "asmfuncs.h" +#include "lang/asmfuncs.h" #include "functions.h" #include "mm/mm.h" #include "mm/vmm.h" +#include "char/parallel.h" +#include "kout.h" +#include "lang/conv.h" mb_info_t mb_info_block; mb_mmap_t mb_mmap[MAX_MMAP]; @@ -16,6 +19,8 @@ byte real_mode_module; char mb_cmdline[256]; int criticalCounter; +extern u32_t mm_freepages; + /* This function runs in segmented memory - 0xC000_0000 is mapped to 0x0 but 0x0 itself is an invalid linear address. Therefore, the multiboot information addresses must be manually adjusted by VIRT_OFFSET to become valid linear addresses. */ @@ -56,14 +61,14 @@ int k_mbsave(mb_info_t *mbinfo, unsigned int mb_magic) } if (mb_info_block.flags & MB_BOOTLOADER_MMAP) { - mb_info_block.mmap_addr += VIRT_OFFSET - 4; //-4 to get to size field, not base_addr_low field + mb_info_block.mmap_addr += (VIRT_OFFSET - 4); //-4 to get to size field, not base_addr_low field mb_mmap_t *mmap = (mb_mmap_t *)mb_info_block.mmap_addr; int i, sz = 0; for (i = 0; sz < mb_info_block.mmap_length && i < MAX_MMAP; i++) { - sz += mmap->size; + sz += mmap->size + 4; mb_mmap[i] = *mmap; - mmap = (mb_mmap_t *)(((u32_t) mmap) + mmap->size); + mmap = (mb_mmap_t *)(((u32_t) mmap) + mmap->size + 4); mmap_entries++; } } @@ -78,27 +83,50 @@ int k_mbsave(mb_info_t *mbinfo, unsigned int mb_magic) /* Main kernel initialization routine */ void k_init() { + kprintf("k_init()\n"); k_enter_critical(); mm_init(); vmm_init(); if (real_mode_module) { - (*(char*)(CONSOLE_MEMORY+40))++; + kprintf("Real mode module present\n"); } - u32_t *ptr = kmalloc(sizeof(u32_t)); - BOCHS_DEBUG(50, (u32_t)ptr); - *ptr = 42; - while (*ptr == 42); - kfree(ptr); + u32_t alloc_size = 1; + void *addresses[32]; + memsetd(addresses, 0, 32); + void *address; + int i; + for (i = -5; i < 5; i++) + { + kprintf("Counting down... %d\t0x%x\t%u\n", i, i, i); + } + for (i = 0; i < 32; i++) + { + kprintf("\e[31mAllocating %u (0x%x) bytes\e[0m,\tmm_freepages = %u...\n", alloc_size, alloc_size, mm_freepages); + address = kmalloc(alloc_size); + if (!address) + break; + addresses[i] = address; + alloc_size <<= 1; + } + for (i = 0; i < 32; i++) + { + if (!addresses[i]) + break; + kprintf("\e[32mFreeing 0x%x\e[0m,\tmm_freepages = %u...\n", addresses[i], mm_freepages); + kfree(addresses[i]); + } + // dev_init(); - BOCHS_DEBUG(0, 0xdeadbeef); + kprintf("End of k_init()\n"); criticalCounter--; } void isr(u32_t num) { criticalCounter++; - BOCHS_DEBUG(158, 0xbeef1234); + kprintf("Interrupt #%d!\n", num); + halt(); switch (num) { @@ -120,10 +148,3 @@ void k_leave_critical() enable_ints(); } -void BOCHS_DEBUG(u32_t pos, u32_t param) -{ - for (;;) - { - (*(char*)(0xC00B8000+pos))++; - } -} diff --git a/kernel/kout.c b/kernel/kout.c new file mode 100644 index 0000000..bab7e37 --- /dev/null +++ b/kernel/kout.c @@ -0,0 +1,122 @@ +// kout.c +// Author: Josh Holtrop +// Date: 08/02/04 + +#include "hos_defines.h" +#include "char/parallel.h" +#include "kout.h" +#include "lang/conv.h" + +char buffer[64]; + +// print a character +void putc(int c) +{ + #ifdef PARALLEL_DEBUG + outparb(c); + #endif +} + + +// print a formatted string +void kprintf(char *fmt, ...) +{ + u32_t *params = ((u32_t *)(&fmt)) + 1; //points to the first paramater + int i; + int special = 0; + for (i = 0; ; i++) + { + if (special) + { + special = 0; + switch (fmt[i]) + { + case 0: + return; + case '%': + putc('%'); + break; + case 's': case 'S': + puts((char *)*params); + params++; + break; + case 'c': case 'C': + putc(*params); + params++; + break; + case 'd': case 'D': case 'i': case 'I': + putDec(*params); + params++; + break; + case 'u': case 'U': + putDecu(*params); + params++; + break; + case 'x': case 'X': + putHex(*params); + params++; + break; + case 'b': case 'B': + kio_putBCD(*params); + params++; + break; + } + } + else + { + switch (fmt[i]) + { + case '%': + special = 1; + break; + case 0: + return; + default: + putc(fmt[i]); + } + } + } +} + + +// This function prints a raw string +void puts(char *str) +{ + while (*str) + { + putc(*str++); + } +} + + +// This function prints a signed, decimal integer +void putDec(int num) +{ + itoa(num, buffer); + puts(buffer); +} + + +// This function prints an unsigned, decimal integer +void putDecu(u32_t num) +{ + utoa(num, buffer); + puts(buffer); +} + + +// This function displays a number in hexadecimal +void putHex(u32_t num) +{ + itox(num, buffer); + puts(buffer); +} + + +// This function prints a two-digit binary-coded-decimal value +void kio_putBCD(u32_t bcd) +{ + bcdtoa(bcd, buffer); + +} + diff --git a/kernel/kout.h b/kernel/kout.h new file mode 100644 index 0000000..7897c45 --- /dev/null +++ b/kernel/kout.h @@ -0,0 +1,19 @@ +// kout.h +// Author: Josh Holtrop +// Date: 08/02/04 + +#ifndef __HOS_KOUT__ +#define __HOS_KOUT__ __HOS_KOUT__ + +#include "hos_defines.h" + +void printf(char *fmt, ...); +void putHex(u32_t number); +void kio_putBCD(u32_t bcd); +void putc(int c); +void puts(char *str); +void putDec(int num); +void putDecu(u32_t num); + +#endif + diff --git a/kernel/asmfuncs.h b/kernel/lang/asmfuncs.h similarity index 100% rename from kernel/asmfuncs.h rename to kernel/lang/asmfuncs.h diff --git a/kernel/lang/conv.c b/kernel/lang/conv.c new file mode 100644 index 0000000..00cf8af --- /dev/null +++ b/kernel/lang/conv.c @@ -0,0 +1,83 @@ +// conv.h +// Author: Josh Holtrop +// Date: 08/02/04 + +#include "conv.h" +#include "hos_defines.h" + +// BCD to string +// returns number of characters generated before null terminator +int bcdtoa(u32_t bcd, char *buf) +{ + *buf++ = ((bcd & 0xF0) >> 4) + '0'; + *buf++ = (bcd & 0xF) + '0'; + *buf = 0; + return 2; +} + + +// convert integer to hexadecimal string +int itox(u32_t num, char *buf) +{ + int s, i = 0; + for (s = 28; s >= 0; s -= 4) + { + u32_t val = (num >> s) & 0xF; + if (i || val || (!s)) + { + val = (val > 9) ? (val + 'A' - 10) : (val + '0'); + buf[i++] = val; + } + } + buf[i] = 0; + return i - 1; +} + + +// convert signed integer to decimal string +int itoa(int num, char *buf) +{ + // 4,294,967,296 + int hitNum = 0, i = 0, mod, val; + if (num < 0) + { + buf[i++] = '-'; + num = -num; + } + for (mod = 1000000000; mod >= 1; mod /= 10) + { + val = num / mod; + num %= mod; + if (val || (mod == 1)) + hitNum = 1; + if (hitNum) + { + buf[i++] = val + '0'; + } + } + buf[i] = 0; + return i - 1; +} + + +// convert an unsigned integer to decimal string +int utoa(u32_t num, char *buf) +{ + // 4,294,967,296 + int hitNum = 0, i = 0, mod, val; + for (mod = 1000000000; mod >= 1; mod /= 10) + { + val = num / mod; + num %= mod; + if (val || (mod == 1)) + hitNum = 1; + if (hitNum) + { + buf[i++] = val + '0'; + } + } + buf[i] = 0; + return i - 1; +} + + diff --git a/kernel/lang/conv.h b/kernel/lang/conv.h new file mode 100644 index 0000000..05e2bd8 --- /dev/null +++ b/kernel/lang/conv.h @@ -0,0 +1,16 @@ +// conv.h +// Author: Josh Holtrop +// Date: 08/02/04 + +#ifndef __HOS_CONV__ +#define __HOS_CONV__ __HOS_CONV__ + +#include "hos_defines.h" + +int bcdtoa(u32_t bcd, char *buf); +int itox(u32_t num, char *buf); +int itoa(int num, char *buf); +int utoa(u32_t num, char *buf); + +#endif + diff --git a/kernel/mm/vmm.c b/kernel/mm/vmm.c index 919afec..3d3d7c6 100644 --- a/kernel/mm/vmm.c +++ b/kernel/mm/vmm.c @@ -7,7 +7,7 @@ #include "hos_defines.h" #include "kernel.h" #include "mm/vmm.h" -#include "asmfuncs.h" +#include "lang/asmfuncs.h" #include "mm/mm.h" int vmm_map(void *virt); @@ -31,7 +31,7 @@ extern mb_info_t mb_info_block; extern mb_module_t mb_modules[MAX_MODULES]; extern u32_t mm_freepages; -HeapEntryQueue_t heapEntryQueues[VMM_HE_TYPES]; // linked queue of HeapEntry objects +HeapEntryQueue_t heapEntryQueues[VMM_HE_TYPES]; // linked queues of HeapEntry objects HeapEntry_t heapEntryHeadNodes[VMM_HE_TYPES]; // head nodes for linked queues HeapEntry_t heapEntryTailNodes[VMM_HE_TYPES]; // tail nodes for linked queues HeapEntryBlock_t initialHEB; // block for initial 256 HeapEntry objects @@ -62,10 +62,9 @@ void vmm_init() /* Allocate a physical page and map the virtual address to it, return physical address allocated or NULL */ int vmm_map(void *virt) { - if (mm_freepages < 10); + if (mm_freepages < 10) return -1; - vmm_map1((u32_t)virt, mm_palloc()); - return 0; + return vmm_map1((u32_t)virt, mm_palloc()); } @@ -79,7 +78,7 @@ int vmm_map1(u32_t virt, u32_t physical) { u32_t newpagetable; if (!(newpagetable = mm_palloc())) - return 1; //out of physical memory + return -1; //out of physical memory pageTables[pde] = newpagetable | 0x03; invlpg_(virt); //in case it was cached, so we can fill page table safely memsetd((void*)(0xFFC00000 | (pde << 12)), 0, 1024); //zero out new page table @@ -194,7 +193,7 @@ void *vmm_palloc() k_enter_critical(); HeapEntry_t *he = heapEntryQueues[VMM_HE_HOLE].head->next; HeapEntry_t *wilderness = he; - while (he) + while (he->next) { if (he->length == 4096) { @@ -229,15 +228,11 @@ int vmm_pfree(void *addr) { k_enter_critical(); HeapEntry_t *he = heapEntryQueues[VMM_HE_USED].head->next; - while (he) + while (he->next) { if (he->base == addr) //found the page to free { - ((HeapEntry_t *)he->prev)->next = he->next; - ((HeapEntry_t *)he->next)->prev = he->prev; - heapEntryQueues[VMM_HE_USED].count--; - he->next = NULL; - he->prev = NULL; + vmm_removeHeapEntry(VMM_HE_USED, he); vmm_unmap1((u32_t)he->base); vmm_addToQueue(VMM_HE_HOLE, &heapEntryHeadNodes[VMM_HE_HOLE], he); k_leave_critical(); @@ -377,7 +372,8 @@ int vmm_coalesceEntry(u32_t queue, HeapEntry_t *newHE) } else if ((newHE->base + newHE->length) == existing->base) { - existing->base -= newHE->length; + existing->base = newHE->base; + existing->length += newHE->length; return 0; } existing = (HeapEntry_t *)existing->next;