diff --git a/Functions.c b/Functions.c deleted file mode 100644 index 8359550..0000000 --- a/Functions.c +++ /dev/null @@ -1,340 +0,0 @@ -//Functions.c -//05/07/03 Josh Holtrop -//for HOS -//Modified: 10/30/03 - -//Writes a byte out to a port -inline void outportb(unsigned int port, unsigned char value) // Output a byte to a port -{ - asm volatile ("outb %%al,%%dx"::"d" (port), "a" (value)); -}; - -//Writes a word out to a port -inline void outportw(unsigned int port, unsigned int value) // Output a word to a port -{ - asm volatile ("outw %%ax,%%dx"::"d" (port), "a" (value)); -}; - -//Reads a byte from a port -inline byte inportb(unsigned short port) -{ - unsigned char ret_val; - - asm volatile("inb %w1,%b0" - : "=a"(ret_val) - : "d"(port)); - return ret_val; -}; - -//Enables (SeTs) Interrupt Flag on the processor -inline void enable_ints() -{ - asm("sti"); -}; - -//Disables (CLears) Interrupt Flag on the processor -inline void disable_ints() -{ - asm("cli"); -}; - - -char *strcat(char *dest, char *src) -{ - strcpy(dest+strlen(dest), src); -} - - -//Splits a string into multiple strings by turning all characters -// equal to delim into null values (string termination character) -//Returns the number of strings after the split, 1 if no delim chars -int string_split(char *str, char delim) -{ - if (strlen(str) < 1) - return 0; //empty string - int count = 1; - for (; *str; str++) - { - if (*str == delim) - { - count++; - *str = 0; - } - } - return count; -} - - -//Advances a char pointer to the byte after the current string's -// null-terminating character -//Useful after calling string_split() -//Returns a pointer to the following string -char *string_advance(char *str) -{ - for (; *str; str++); - return str+1; -} - - -//converts a binary-coded-decimal byte to its decimal equivalent -inline byte bcd2byte(byte bcd) -{ - return (10* ((bcd & 0xF0) >> 4)) + (bcd & 0x0F); -} - -//converts a binary-coded-decimal byte to its decimal equivalent -inline byte byte2bcd(byte bite) -{ - return ((bite / 10) << 4) | (bite % 10); -} - -void rtrim(char *str) -{ - str += strlen(str); //now points to the null character at the end of the string - str--; - for (;;) - { - if ((*str == ' ') || (*str == '\t') || (*str == '\n')) - *str-- = 0; - else - break; - } -} - - -char *ucase(char *str) -{ - char *ret = str; - for (;;) - { - if (*str == 0) - break; - if ((*str >= 'a') && (*str <= 'z')) - *str = (*str) - 32; - str++; - } - return ret; -} - - -char *lcase(char *str) -{ - char *ret = str; - for (;;) - { - if (*str == 0) - break; - if ((*str >= 'A') && (*str <= 'Z')) - *str = (*str) + 32; - str++; - } - return ret; -} - - -//Re-maps the Programmable Interrupr Controllers so IRQ0->pic1 base address, IRG8->pic2 base address -void remap_pics(int pic1, int pic2) -{ - byte a1, a2; - - a1 = inportb(PIC1_DATA); //0x21 - a2 = inportb(PIC2_DATA); //0xA1 - - outportb(PIC1_COMMAND, ICW1_INIT+ICW1_ICW4); //0x20, 0x10+0x01 00010001b - outportb(PIC2_COMMAND, ICW1_INIT+ICW1_ICW4); //0xA0, 0x10+0x01 00010001b - outportb(PIC1_DATA, pic1); //0x21, pic1 - outportb(PIC2_DATA, pic2); //0xA1, pic2 - outportb(PIC1_DATA, 4); //0x21, 0x04 00000100b - outportb(PIC2_DATA, 2); //0xA1, 0x02 00000010b - outportb(PIC1_DATA, ICW4_8086); //0x21, 0x01 00000001b - outportb(PIC2_DATA, ICW4_8086); //0xA1, 0x01 00000001b - - outportb(PIC1_DATA, a1); //0x21 - outportb(PIC2_DATA, a2); //0xA1 -} - -//Masks interrupts on first Programmable Interrupt Controller -inline void pic1_mask(byte mask) -{ - outportb(PIC1_DATA, mask); //0x21, maskfield *OCW1* -} - -//Masks interrupts on second Programmable Interrupt Controller -inline void pic2_mask(byte mask) -{ - outportb(PIC2_DATA, mask); //0xA1, maskfield *OCW1* -} - -//Restarts the computer -inline void restart() -{ - enable_ints(); - byte temp; - do - { - temp = inportb(0x64); - if (temp & 1) - inportb(0x60); - } while(temp & 2); - - - outportb (0x64, 0xfe); - for (;;) - { - } -} - -//Halts (freezes) the computer -inline void halt() -{ - asm("cli"); - asm("hlt"); - while (1) - ; -} - -//Initializes 8253 Programmable Interrupt Timer -inline void init_timer() -{ - //set timer : 2e9c = 100hz - outportb(0x43, 0x34); - outportb(0x40, 0x9c); //lsb - outportb(0x40, 0x2e); //msb -} - -//Signals an End Of Interrupt signal to the first PIC -inline void eoi() -{ - outportb(0x20, 0x20); -} - -//Signals an End Of Interrupt signal to both the second and first PIC unit -inline void eoi2() -{ - outportb(0xA0, 0x20); - outportb(0x20, 0x20); -} - -//Returns the size of the kernel (code & data) -// - this does not include the bss section -// - this should be 4kb aligned per the linker script -// - this should be the size of kernel.bin -inline dword kernel_size() -{ - return (dword)(&_bss)-(dword)(&_code); -} - - -//These functions are for reading and writing various values stored on the CMOS Real Time Clock -byte rtc_readDay() -{ - outportb(0x70, 7); - return bcd2byte(inportb(0x71)); -} - -byte rtc_readMonth() -{ - outportb(0x70, 8); - return bcd2byte(inportb(0x71)); -} - -byte rtc_readYear() -{ - outportb(0x70, 9); - return bcd2byte(inportb(0x71)); -} - -byte rtc_readSecond() -{ - outportb(0x70, 0); - return bcd2byte(inportb(0x71)); -} - -byte rtc_readMinute() -{ - outportb(0x70, 2); - return bcd2byte(inportb(0x71)); -} - -byte rtc_readHour() -{ - outportb(0x70, 4); - return bcd2byte(inportb(0x71)); -} - -void rtc_setDay(byte day) -{ - outportb(0x70, 7); - outportb(0x71, byte2bcd(day)); -} - -void rtc_setMonth(byte month) -{ - outportb(0x70, 8); - outportb(0x71, byte2bcd(month)); -} - -void rtc_setYear(byte year) -{ - outportb(0x70, 9); - outportb(0x71, byte2bcd(year)); -} - -void rtc_setSecond(byte second) -{ - outportb(0x70, 0); - outportb(0x71, byte2bcd(second)); -} - -void rtc_setMinute(byte minute) -{ - outportb(0x70, 2); - outportb(0x71, byte2bcd(minute)); -} - -void rtc_setHour(byte hour) -{ - outportb(0x70, 4); - outportb(0x71, byte2bcd(hour)); -} - - -//Returns the cmos type of floppy disk drive 0 (0 = not present) -byte cmos_getfd0() -{ - outportb(0x70, 0x10); - return (inportb(0x71) >> 4); -} - - -//Returns the cmos type of floppy disk drive 1 (0 = not present) -byte cmos_getfd1() -{ - outportb(0x70, 0x10); - return (inportb(0x71) & 0x0F); -} - - -//Returns the cmos type of hard disk drive 0 (0 = not present) -byte cmos_gethd0() -{ - outportb(0x70, 0x12); - return (inportb(0x71) >> 4); -} - - -//Returns the cmos type of hard disk drive 1 (0 = not present) -byte cmos_gethd1() -{ - outportb(0x70, 0x12); - return (inportb(0x71) & 0x0F); -} - - - - - - - - - diff --git a/backup.bat b/backup.bat deleted file mode 100755 index 6a114e5..0000000 --- a/backup.bat +++ /dev/null @@ -1,12 +0,0 @@ -@echo off -echo Backing up to .\Backup\%1 - -mkdir .\Backup\%1 - -copy *.h .\Backup\%1 -copy *.c .\Backup\%1 -copy *.inc .\Backup\%1 -copy *.asm .\Backup\%1 -copy *.ld .\Backup\%1 -copy *.bat .\Backup\%1 - diff --git a/c1.bat b/c1.bat deleted file mode 100755 index b726cb8..0000000 --- a/c1.bat +++ /dev/null @@ -1,2 +0,0 @@ -nasmw -f aout -o ks.o -l .\lst\kernel.lst kernel.asm - diff --git a/c2.bat b/c2.bat deleted file mode 100755 index 62a1f81..0000000 --- a/c2.bat +++ /dev/null @@ -1 +0,0 @@ -gcc -ffreestanding -fno-builtin -nostdlib -nodefaultlibs -c kernel.c -o kernel.o diff --git a/c3.bat b/c3.bat deleted file mode 100755 index cef03e3..0000000 --- a/c3.bat +++ /dev/null @@ -1 +0,0 @@ -nasmw -f aout -o asmfuncs.o -l .\lst\asmfuncs.lst asmfuncs.asm \ No newline at end of file diff --git a/cop.bat b/cop.bat deleted file mode 100755 index 7255e66..0000000 --- a/cop.bat +++ /dev/null @@ -1 +0,0 @@ -copy kernel.bin a: diff --git a/cops1.bat b/cops1.bat deleted file mode 100755 index f8b4245..0000000 --- a/cops1.bat +++ /dev/null @@ -1,2 +0,0 @@ -rem rawrite -f stage1.bin -d a -n -partcopy stage1.bin 0 200 -f0 diff --git a/cops2.bat b/cops2.bat deleted file mode 100755 index 3479300..0000000 --- a/cops2.bat +++ /dev/null @@ -1 +0,0 @@ -copy stage2.bin a: \ No newline at end of file diff --git a/cs1.bat b/cs1.bat deleted file mode 100755 index ed90279..0000000 --- a/cs1.bat +++ /dev/null @@ -1 +0,0 @@ -nasmw -f bin -o stage1.bin -l .\lst\stage1.lst stage1.asm diff --git a/cs2.bat b/cs2.bat deleted file mode 100755 index 01b3545..0000000 --- a/cs2.bat +++ /dev/null @@ -1 +0,0 @@ -nasmw -f bin -o stage2.bin -l .\lst\stage2.lst stage2.asm diff --git a/fat12.c b/fat12.c deleted file mode 100644 index 099cd5f..0000000 --- a/fat12.c +++ /dev/null @@ -1,345 +0,0 @@ -// fat12.c -// Author: Josh Holtrop -// Created: 01/04/04 -// Modified: 01/14/04 - - -byte *fat12_readFile(char *fileName, DiskDevice *dd) -{ - char *fileNameUCase = malloc(strlen(fileName) + 1); - strcpy(fileNameUCase, fileName); - ucase(fileNameUCase); - dword iMadeClusterChain = getClusterChain(dd); - Fat12Entry fe; - if (fat12_getFileHandle(fileNameUCase, dd, &fe)) - { - free(fileNameUCase); - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return 0; - } - byte *fp = (byte *)fat12_readClusterChain(dd, &fe); - free(fileNameUCase); - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return fp; -} - - -dword fat12_getFileHandle(char *fileName, DiskDevice *dd, Fat12Entry *destination) -{ - if (strlen(fileName) < 1) - return 1; - if (fileName[strlen(fileName)-1] == '/') - return 2; - dword iMadeClusterChain = getClusterChain(dd); - int fileName_length = strlen(fileName); - int a; - int entries = 1; - for (a = 0; a < fileName_length; a++) - { - if (fileName[a] == '/') - { - fileName[a] = 0; - entries++; - } - } - char *pointer = fileName; - Fat12Entry *workingDirectory = 0; - Fat12Entry workingDir; - for (a = 0; a < (entries - 1); a++) - { - if (fat12_getDirectoryHandle(pointer, dd, workingDirectory, &workingDir)) //an error occurred if this returns nonzero - { - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return 3; - } - workingDirectory = &workingDir; - for (;;) //advance to the next dir name - { - pointer++; - if (*pointer == 0) - { - pointer++; - break; - } - } - } - if (fat12_getFileHandleInDirectory(pointer, dd, workingDirectory, destination)) //an error occurred if this returns nonzero - { - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return 4; - } - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return 0; -} - - -dword fat12_getFileHandleInDirectory(char *fileName, DiskDevice *dd, Fat12Entry *currDir, Fat12Entry *destination) -{ - if (!currDir) // we are working in the root directory - { - Fat12Entry *rootDir = malloc(14*512); //root directory is 14 sectors long - vfs_readSector(dd, 19, (byte *)rootDir, 14); - int a; - for (a = 0; a < 224; a++) //224 max root directory entries in 14 sectors - { - if (rootDir[a].fileName[0] == 0) - break; - if ((byte)rootDir[a].fileName[0] != 0xE5) - { - if ((rootDir[a].attributes & 0x18) == 0) //this entry is a directory - { - char dirName[9]; - char dirExt[4]; - memcpy(dirName, rootDir[a].fileName, 8); - dirName[8] = 0; - memcpy(dirExt, rootDir[a].ext, 3); - dirExt[3] = 0; - rtrim(dirName); - rtrim(dirExt); - char dirWhole[14]; - strcpy(dirWhole, dirName); - if (strlen(dirExt) > 0) //the directory has an extension - { - strcat(dirWhole, "."); - strcat(dirWhole, dirExt); - } - if (strcmp(dirWhole, fileName)) //the entry found is a match - { - free(rootDir); - *destination = rootDir[a]; - return 0; - } - } - } - } - free(rootDir); - return 1; //no match found - } - dword retVal = 2; - dword iMadeClusterChain = getClusterChain(dd); - Fat12Entry *subDirectory = fat12_readClusterChain(dd, currDir); - if (!subDirectory) - return 5; - dword numberOfClusters = fat12_readClusterChainCount(dd, currDir); - int a; - for (a = 0; a < (numberOfClusters * 16); a++) - { - if (subDirectory[a].fileName[0] == 0) - break; - if ((byte)subDirectory[a].fileName[0] != 0xE5) - { - if ((subDirectory[a].attributes & 0x18) == 0) //this entry is a directory - { - char dirName[9]; - char dirExt[4]; - memcpy(dirName, subDirectory[a].fileName, 8); - dirName[8] = 0; - memcpy(dirExt, subDirectory[a].ext, 3); - dirExt[3] = 0; - rtrim(dirName); - rtrim(dirExt); - char dirWhole[14]; - strcpy(dirWhole, dirName); - if (strlen(dirExt) > 0) //the directory has an extension - { - strcat(dirWhole, "."); - strcat(dirWhole, dirExt); - } - if (strcmp(dirWhole, fileName)) //the entry found is a match - { - *destination = subDirectory[a]; - retVal = 0; - break; - } - } - } - } - free(subDirectory); - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return retVal; -} - - -dword fat12_getDirectoryHandle(char *directory, DiskDevice *dd, Fat12Entry *currDir, Fat12Entry *destination) -{ - if (!currDir) // we are working in the root directory - { - Fat12Entry *rootDir = malloc(14*512); //root directory is 14 sectors long - vfs_readSector(dd, 19, (byte *)rootDir, 14); - int a; - for (a = 0; a < 224; a++) //224 max root directory entries in 14 sectors - { - if (rootDir[a].fileName[0] == 0) - break; - if ((byte)rootDir[a].fileName[0] != 0xE5) - { - if ((rootDir[a].attributes & 0x18) == 0x10) //this entry is a directory - { - char dirName[9]; - char dirExt[4]; - memcpy(dirName, rootDir[a].fileName, 8); - dirName[8] = 0; - memcpy(dirExt, rootDir[a].ext, 3); - dirExt[3] = 0; - rtrim(dirName); - rtrim(dirExt); - char dirWhole[14]; - strcpy(dirWhole, dirName); - if (strlen(dirExt) > 0) //the directory has an extension - { - strcat(dirWhole, "."); - strcat(dirWhole, dirExt); - } - if (strcmp(dirWhole, directory)) //the entry found is a match - { - free(rootDir); - *destination = rootDir[a]; - return 0; - } - } - } - } - free(rootDir); - return 1; //no match found - } - dword retVal = 2; - dword iMadeClusterChain = getClusterChain(dd); - Fat12Entry *subDirectory = fat12_readClusterChain(dd, currDir); - if (!subDirectory) - return 5; - dword numberOfClusters = fat12_readClusterChainCount(dd, currDir); - int a; - for (a = 0; a < (numberOfClusters * 16); a++) - { - if (subDirectory[a].fileName[0] == 0) - break; - if ((byte)subDirectory[a].fileName[0] != 0xE5) - { - if ((subDirectory[a].attributes & 0x18) == 0x10) //this entry is a directory - { - char dirName[9]; - char dirExt[4]; - memcpy(dirName, subDirectory[a].fileName, 8); - dirName[8] = 0; - memcpy(dirExt, subDirectory[a].ext, 3); - dirExt[3] = 0; - rtrim(dirName); - rtrim(dirExt); - char dirWhole[14]; - strcpy(dirWhole, dirName); - if (strlen(dirExt) > 0) //the directory has an extension - { - strcat(dirWhole, "."); - strcat(dirWhole, dirExt); - } - if (strcmp(dirWhole, directory)) //the entry found is a match - { - *destination = subDirectory[a]; - retVal = 0; - break; - } - } - } - } - free(subDirectory); - if (iMadeClusterChain) - { - free(clusterChain); - clusterChain = 0; - } - return retVal; -} - - -Fat12Entry *fat12_readClusterChain(DiskDevice *dd, Fat12Entry *directory) -{ - dword numberOfClusters = fat12_readClusterChainCount(dd, directory); - if (numberOfClusters == 0) - return 0; - byte *bp = malloc(numberOfClusters * 512); - Fat12Entry *retVal = (Fat12Entry *)bp; - dword cluster = directory->firstCluster; - while (cluster < 0xFF0) - { - vfs_readSector(dd, cluster + 31, bp, 1); - cluster = fat12_getNextCluster(cluster); - bp += 512; - } - return retVal; -} - - -dword fat12_readClusterChainCount(DiskDevice *dd, Fat12Entry *directory) -{ - dword numberOfClusters = 0; - dword cluster = directory->firstCluster; - if (cluster == 0) - return 0; - while (cluster < 0xFF0) - { - cluster = fat12_getNextCluster(cluster); - numberOfClusters++; - } - return numberOfClusters; -} - - -dword fat12_getNextCluster(dword thisCluster) -{ - dword nextCluster = *(word *)((dword)clusterChain + ((thisCluster * 3) >> 1)); - if (thisCluster & 0x01) //this is an odd cluster - return nextCluster >> 4; - else //this is an even cluster - return nextCluster & 0x0FFF; -} - - -dword fat12_getFileSize(char *fileName, DiskDevice *dd) -{ - Fat12Entry fe; - if (fat12_getFileHandle(fileName, dd, &fe)) - return 0xFFFFFFFF; - return fe.fileSize; -} - - -dword getClusterChain(DiskDevice *dd) -{ - if (!clusterChain) - { - clusterChain = malloc(9*512); //9 sectors for File Allocation Table (cluster chain) - vfs_readSector(dd, 1, clusterChain, 9); //sectors 1 through 9 contain the first FAT - return 1; //this call created the cluster chain - } - else - return 0; //this call did not create the cluster chain -} - - - - - diff --git a/fat12.h b/fat12.h deleted file mode 100644 index ce42a52..0000000 --- a/fat12.h +++ /dev/null @@ -1,58 +0,0 @@ -// fat12.h -// Author: Josh Holtrop -// Created: 01/04/04 - - -typedef struct { - char fileName[8]; - char ext[3]; - byte attributes; - dword createTime; - word createDate; - word accessDate; - word unused0; - word modifiedDate; - word modifiedTime; - word firstCluster; - dword fileSize; -} __attribute__((packed)) Fat12Entry; - -typedef struct { - byte jump[3]; - byte sysName[8]; - word bytesPerSector; - byte sectorsPerCluster; - word reservedSectors; - byte FATcount; - word maxRootEntries; - word totalSectors1; - byte mediaDescriptor; - word sectorsPerFAT; - word sectorsPerTrack; - word headCount; - dword hiddenSectors; - dword totalSectors2; - byte driveNumber; - byte reserved1; - byte extBootSignature; - dword volumeSerial; - char volumeLabel[11]; - char fileSystemID[8]; -} __attribute__((packed)) Fat12BootSector; - - -byte *fat12_readFile(char *fileName, DiskDevice *dd); -dword fat12_getFileHandle(char *fileName, DiskDevice *dd, Fat12Entry *destination); -dword fat12_getDirectoryHandle(char *directory, DiskDevice *dd, Fat12Entry *currDir, Fat12Entry *destination); -Fat12Entry *fat12_readClusterChain(DiskDevice *dd, Fat12Entry *directory); -dword fat12_getFileHandleInDirectory(char *fileName, DiskDevice *dd, Fat12Entry *currDir, Fat12Entry *destination); -dword fat12_readClusterChainCount(DiskDevice *dd, Fat12Entry *directory); -dword fat12_getFileSize(char *fileName, DiskDevice *dd); -dword getClusterChain(DiskDevice *dd); -dword fat12_getNextCluster(dword thisCluster); - -byte *clusterChain = 0; - - - - diff --git a/fdc.c b/fdc.c deleted file mode 100644 index 64afa5b..0000000 --- a/fdc.c +++ /dev/null @@ -1,9 +0,0 @@ -//fdc.c -//Author: Josh Holtrop -//Date: 10/30/03 - - -inline void fdc_sendDOR(byte dor) -{ - outportb(FDC_DOR, dor); -} diff --git a/fdc.h b/fdc.h deleted file mode 100644 index a25fcf4..0000000 --- a/fdc.h +++ /dev/null @@ -1,12 +0,0 @@ -//fdc.h -//Author: Josh Holtrop -//Date: 10/30/03 - - -#define FDC_DOR 0x3f2 -#define FDC_MSR 0x3f4 - - -inline void fdc_sendDOR(byte dor); - - diff --git a/functions.h b/functions.h deleted file mode 100644 index f979a58..0000000 --- a/functions.h +++ /dev/null @@ -1,52 +0,0 @@ -//functions.h -//05/07/03 Josh Holtrop -//for HOS -//Modified: 10/30/03 - -extern dword _code; -extern dword _bss; -extern dword _end; - -inline void outportb(unsigned int port, unsigned char value); -inline void outportw(unsigned int port, unsigned int value); -inline byte inportb(unsigned short port); -inline void enable_ints(); -inline void disable_ints(); -inline void restart(); -inline void halt(); -void remap_pics(int pic1, int pic2); -inline void pic1_mask(byte mask); -inline void pic2_mask(byte mask); -inline void eoi(); -inline void eoi2(); -inline dword kernel_size(); -inline void init_timer(); -char *strcat(char *dest, char *src); -int string_split(char *str, char delim); -char *string_advance(char *str); -void rtrim(char *str); -char *ucase(char *str); -char *lcase(char *str); -inline byte bcd2byte(byte bcd); -inline byte byte2bcd(byte bite); -byte rtc_readDay(); -byte rtc_readMonth(); -byte rtc_readYear(); -byte rtc_readSecond(); -byte rtc_readMinute(); -byte rtc_readHour(); -void rtc_setDay(byte dat); -void rtc_setMonth(byte month); -void rtc_setYear(byte year); -void rtc_setSecond(byte second); -void rtc_setMinute(byte minute); -void rtc_setHour(byte hour); -byte cmos_getfd0(); -byte cmos_getfd1(); -byte cmos_gethd0(); -byte cmos_gethd1(); - - - - - diff --git a/gccasm.bat b/gccasm.bat deleted file mode 100755 index 1a2b65b..0000000 --- a/gccasm.bat +++ /dev/null @@ -1 +0,0 @@ -gcc -S kernel.c -masm=intel -fno-builtin diff --git a/getflop.bat b/getflop.bat deleted file mode 100755 index a74e197..0000000 --- a/getflop.bat +++ /dev/null @@ -1 +0,0 @@ -partcopy -f0 0 168000 flop.img \ No newline at end of file diff --git a/k_defines.h b/k_defines.h deleted file mode 100644 index 4781b59..0000000 --- a/k_defines.h +++ /dev/null @@ -1,55 +0,0 @@ -//k_defines.h -//03/17/03 Josh Holtrop -//Modified: 10/30/03 - -#define PIC1 0x20 -#define PIC2 0xA0 -#define PIC1_COMMAND PIC1 -#define PIC1_DATA (PIC1+1) -#define PIC2_COMMAND PIC2 -#define PIC2_DATA (PIC2+1) -#define PIC_EOI 0x20 - -#define ICW1_ICW4 0x01 /* ICW4 (not) needed */ -#define ICW1_SINGLE 0x02 /* Single (cascade) mode */ -#define ICW1_INTERVAL4 0x04 /* Call address interval 4 (8) */ -#define ICW1_LEVEL 0x08 /* Level triggered (edge) mode */ -#define ICW1_INIT 0x10 /* Initialization - required! */ - -#define ICW4_8086 0x01 /* 8086/88 (MCS-80/85) mode */ -#define ICW4_AUTO 0x02 /* Auto (normal) EOI */ -#define ICW4_BUF_SLAVE 0x08 /* Buffered mode/slave */ -#define ICW4_BUF_MASTER 0x0C /* Buffered mode/master */ -#define ICW4_SFNM 0x10 /* Special fully nested (not) */ - -#define BLUE_TXT 0x01 -#define RED_TXT 0x04 -#define WHITE_TXT 0x07 -#define CYAN_TXT 0x0B -#define YELLOW_TXT 0x0E -#define BRWHITE_TXT 0x0F - -#define FREERAM_START 0x368000 // 0x368000 is first available byte (this is right after the initrd @ 2mb, 1440kb. -#define MAX_RAM 0x40000000 //1gb maximum RAM supported - -#define PID_KERNEL 0x02 //kernel's PID -#define PID_VMM 0x03 -#define PID_USER 0x10000 //user processes' start PID - -typedef unsigned char byte; -typedef unsigned short word; -typedef unsigned int dword; - -typedef struct { - dword lowdword; - dword highdword; -} __attribute__((packed)) qword; - - -//these defines are the memory locations of values saved by the stage 2 bootloader -#define BOOT_MEMMAP_ENTRIES 0xC009040A -#define BOOT_FIRST_MEMMAP 0xC0092000 -#define BOOT_VIDEO_MODE 0xC0090002 -#define BOOT_VIDEO_MODE_INFO_BLOCK 0xC0090306 - - diff --git a/link.bat b/link.bat deleted file mode 100755 index 6f26b53..0000000 --- a/link.bat +++ /dev/null @@ -1 +0,0 @@ -ld -nodefaultlibs -nostdlib -T link.ld -o kernel.bin -Map .\lst\LDout.doc ks.o kernel.o asmfuncs.o \ No newline at end of file diff --git a/mouse.h b/mouse.h deleted file mode 100644 index 529b184..0000000 --- a/mouse.h +++ /dev/null @@ -1,17 +0,0 @@ -// mouse.h -// 10/03/03 -// Author: Josh Holtrop - - -int mouse_x; -int mouse_y; -int mouse_bytesRead = 0; -byte mouse_inbuffer[16]; - -void mouse_init(); -void isr_mouse(); - - - - - diff --git a/rd.c b/rd.c deleted file mode 100644 index 04e8a0b..0000000 --- a/rd.c +++ /dev/null @@ -1,14 +0,0 @@ -// rd.c -// Author: Josh Holtrop -// Created: 12/31/03 -// Modified: 01/04/04 - - -byte *rd_readSector(DiskDevice *rd, dword sector, byte *dest) -{ - memcpy(dest, (void *)(rd->location + (sector * 512)), 512); - return dest; -} - - - diff --git a/rd.h b/rd.h deleted file mode 100644 index ebba744..0000000 --- a/rd.h +++ /dev/null @@ -1,9 +0,0 @@ -// rd.h -// Author: Josh Holtrop -// Created: 12/31/03 -// Modified: 01/04/04 - - -byte *rd_readSector(DiskDevice *rd, dword sector, byte *dest); - - diff --git a/src/Makefile b/src/Makefile new file mode 100644 index 0000000..d668369 --- /dev/null +++ b/src/Makefile @@ -0,0 +1,192 @@ +##################################################################### +# Author: Benjamen R. Meyer # +# Date: 2004-2-15 # +# Purpose: To build Josh Holtrop's OS (HOS) using GNU make # +# Note: This makefile is for use on Linux & other Unix-like systems # +##################################################################### + +############## +# Variables: # +############## + +# Format of kernel binary: +# Do not change unless you know what you are doing +# Original: +KERNEL_FORMAT=aout +# CygWin: ?? +#KERNEL_FORMAT= + +# Assembler information: +NASM_BIN=nasm +NASM_FLAGS_IPL=-f bin +NASM_FLAGS_KERNEL=-f $(KERNEL_FORMAT) + +# C Compile Information: +CC=gcc +CC_FLAGS=-ffreestanding -fno-builtin -nostdlib -nodefaultlibs -I. + +# Linker Information: +LD=ld +LD_FLAGS=-nodefaultlibs -nostdlib -T link.ld + +# Information for creating a floppy image +# Note: FLOPPY_FS and FLOPPY_FAT_SIZE are related fields. +# FLOPPY_FAT_SIZE should be either 12 or 16, +# depending on if FLOPPY_FS is FAT12 or FAT16, respectively. +MKDOSFS_PROG=/sbin/mkdosfs +FLOPPY_IMAGE=floppy.img +FLOPPY_BLOCK_COUNT=1440 +FLOPPY_FS=FAT12 +FLOPPY_FAT_SIZE=12 +FLOPPY_MOUNT=./floppy_image + +# Floppy images are good for programs like VMware and Bochs Pentium Emulator. ;-) + +# Program for copying +COPY_BIN=cp + +########################################## +# Build the IPL (Boot Loader) and Kernel # +########################################## +all: Boot Link_Kernel + # A word of warning to users :-> And a little helpful information ;-) + @echo "Installation must be done as root." + @echo "Type 'make install' to install to a floppy in drive '/dev/fd0'" + @echo "Type 'make install_img' to create a floppy image and install to it." + +################################################# +# Clean up the source directory of any binaries # +################################################# +clean: + - rm *.o ./lst/*.lst *.bin $(FLOPPY_IMAGE) + +################# +# Build the IPL # +################# +Boot: + boot/make + +############################### +# Linking the kernel together # +############################### +Link_Kernel: Asm_Kernel Asm_Functions FAT_12 FDC Functions Keyboard KIO MM Mouse RD STDFONT VFS Video VMM C_Kernel + $(LD) $(LD_FLAGS) -o kernel.bin -Map ./lst/LDout.doc ks.o fat12.o fdc.o functions.o kernel.o keyboard.o kio.o mm.o mouse.o rd.o stdfont.o vfs.o video.o vmm.o asmfuncs.o + +########################## +# Assembly Kernel Loader # +########################## +Asm_Kernel: kernel.asm + $(NASM_BIN) $(NASM_FLAGS_KERNEL) -o ks.o -l ./lst/kernel.lst kernel.asm + +################################# +# Assembly Functions for Kernel # +################################# +Asm_Functions: asmfuncs.asm + $(NASM_BIN) $(NASM_FLAGS_KERNEL) -o asmfuncs.o -l ./lst/asmfuncs.lst asmfuncs.asm + +############ +# C Kernel # +############ +FAT_12: fat12.c fat12.h k_defines.h vfs.h + $(CC) $(CC_FLAGS) -c fat12.c -o fat12.o + +FDC: fdc.c fdc.h k_defines.h + $(CC) $(CC_FLAGS) -c fdc.c -o fdc.o + +Functions: functions.c functions.h k_defines.h + $(CC) $(CC_FLAGS) -c functions.c -o functions.o + +Keyboard: keyboard.c keyboard.h k_defines.h + $(CC) $(CC_FLAGS) -c keyboard.c -o keyboard.o + +KIO: kio.c kio.h k_defines.h video.h + $(CC) $(CC_FLAGS) -c kio.c -o kio.o + +MM: mm.c mm.h k_defines.h + $(CC) $(CC_FLAGS) -c mm.c -o mm.o + +Mouse: mouse.c mouse.h k_defines.h video.h + $(CC) $(CC_FLAGS) -c mouse.c -o mouse.o + +RD: rd.c rd.h k_defines.h vfs.h + $(CC) $(CC_FLAGS) -c rd.c -o rd.o + +STDFONT: stdfont.h stdfont.c + $(CC) $(CC_FLAGS) -c stdfont.c -o stdfont.o + +VFS: vfs.c vfs.h k_defines.h + $(CC) $(CC_FLAGS) -c vfs.c -o vfs.o + +Video: video.c video.h k_defines.h stdfont.h + $(CC) $(CC_FLAGS) -c video.c -o video.o + +# Why does this rely on video.h??? +VMM: vmm.c vmm.h k_defines.h video.h + $(CC) $(CC_FLAGS) -c vmm.c -o vmm.o + +C_Kernel: kernel.c k_defines.h fat12.h fdc.h functions.h keyboard.h kio.h mm.h mouse.h rd.h vfs.h video.h vmm.h + $(CC) $(CC_FLAGS) -c kernel.c -o kernel.o + +########################################### +# The following is for the floppy drive # +# Note: This must be done on *nix as root # +########################################### + +########################## +# Make install to floppy # +########################## +install: Install_IPL File_Copy + + +############################################ +# Write the Stage 1 IPL to the boot sector # +############################################ +Install_IPL: + boot/make install + +################################# +# Copy the files onto the drive # +################################# +File_Copy: kernel.bin + @echo -n "Copying kernel to the floppy: " + cp kernel.bin /dev/fd0 + +############################################ +# The following is for the floppy image. # +# Note: This must be done on *nix as root. # +############################################ + +######################## +# Make a floppy image: # +######################## +floppy_image: image_IPL image_file_copy + +###################################### +# Create and Format the floppy image # +###################################### +install_img: $(FLOPPY_IMAGE) + $(MKDOSFS_PROG) -C -F $(FLOPPY_FAT_SIZE) -r 112 $(FLOPPY_IMAGE) $(FLOPPY_BLOCK_COUNT) + +########################################## +# Mount the floppy on a loop back device # +########################################## +floppy_mount: + @echo "Mounting a file as a drive..." + mount $(FLOPPY_IMAGE) $(FLOPPY_MOUNT) -o loop + +############################################ +# Write the Stage 1 IPL to the boot sector # +############################################ +image_IPL: stage1.bin floppy_format + @echo "Writing boot sector to image..." + dd if=stage1.bin of=$(FLOPPY_MOUNT) seek=0 + +################################# +# Copy the files onto the image # +################################# +image_file_copy: stage2.bin kernel.bin + @echo -n "Copying files onto it: " + @echo -n "IPL Stage 2 " + $(COPY_BIN) stage2.bin $(FLOPPY_MOUNT) + @echo ", HOS Kernel" + $(COPY_BIN) kernel.bin $(FLOPPY_MOUNT) diff --git a/src/boot/Makefile b/src/boot/Makefile new file mode 100644 index 0000000..6502f9c --- /dev/null +++ b/src/boot/Makefile @@ -0,0 +1,30 @@ +######################## +# Author: Josh Holtrop # +# Date: 2004-2-15 # +######################## + +# Assembler information: +NASM_BIN=nasm + +################# +# Build the IPL # +################# +all: stage1 stage2 + +################ +# IPL: Stage 1 # +################ +stage1: stage1.asm + $(NASM_BIN) stage1.asm -o stage1.bin + +################ +# IPL: Stage 2 # +################ +stage2: stage2.asm + $(NASM_BIN) stage2.asm -o stage2.bin + +######### +# Clean # +######### +clean: + rm *.bin diff --git a/bootdef.inc b/src/boot/bootdef.inc similarity index 100% rename from bootdef.inc rename to src/boot/bootdef.inc diff --git a/stage1.asm b/src/boot/stage1.asm similarity index 100% rename from stage1.asm rename to src/boot/stage1.asm diff --git a/stage2.asm b/src/boot/stage2.asm similarity index 100% rename from stage2.asm rename to src/boot/stage2.asm diff --git a/asmfuncs.asm b/src/kernel/asmfuncs.asm similarity index 88% rename from asmfuncs.asm rename to src/kernel/asmfuncs.asm index 9a5f5e8..e220598 100644 --- a/asmfuncs.asm +++ b/src/kernel/asmfuncs.asm @@ -1,7 +1,7 @@ ; asmfuncs.asm ; Josh Holtrop ; Created: 10/23/03 -; Modified: 12/25/03 +; Modified: 02/26/04 [extern _putc] [extern _console_memory] @@ -137,27 +137,6 @@ _memcpy: pop ebp ret -;copies memory of n dwords (n*4 bytes) from src to destination -;extern void memcpyd(dword dest, dword src, dword n); -[global _memcpyd] -_memcpyd: - push ebp - mov ebp, esp - push esi - push edi - push ecx - mov edi, [ebp+8] - mov esi, [ebp+12] - mov ecx, [ebp+16] - - rep movsd - - pop ecx - pop edi - pop esi - pop ebp - ret - ;returns the number of characters in a string ;extern dword strlen(char *str); [global _strlen] diff --git a/src/kernel/asmfuncs.h b/src/kernel/asmfuncs.h new file mode 100644 index 0000000..975ddd0 --- /dev/null +++ b/src/kernel/asmfuncs.h @@ -0,0 +1,26 @@ +// asmfuncs.h +// Author: Josh Holtrop +// Created: 02/26/04 + +#ifndef __HOS_ASMFUNCS__ +#define __HOS_ASMFUNCS__ __HOS_ASMFUNCS__ + +dword write_cr0(dword cr0); +dword read_cr0(); +dword write_cr3(dword cr3); +dword read_cr2(); +dword read_cr3(); +void writeCursorPosition(dword pos); +dword getCursorPosition(); +void console_scroll(); +void console_cls(); +int puts(char *str); +int putDec(int number); +int putDecu(dword number); +void strcpy(char *dest, char *src); +void memcpy(void *dest, void *src, dword n); +dword strlen(char *str); + +#endif + + diff --git a/src/kernel/block/fdc.c b/src/kernel/block/fdc.c new file mode 100644 index 0000000..6fd6c8d --- /dev/null +++ b/src/kernel/block/fdc.c @@ -0,0 +1,9 @@ +//fdc.c +//Author: Josh Holtrop +//Created: 10/30/03 +//Modified: 02/26/04 + +#include "fdc.h" + + + diff --git a/src/kernel/block/fdc.h b/src/kernel/block/fdc.h new file mode 100644 index 0000000..e0028f4 --- /dev/null +++ b/src/kernel/block/fdc.h @@ -0,0 +1,21 @@ +//fdc.h +//Author: Josh Holtrop +//Date: 10/30/03 +//Modified: 02/26/04 + +#ifndef __HOS_FDC__ +#define __HOS_FDC__ __HOS_FDC__ + +#define FDC_DOR 0x3f2 +#define FDC_MSR 0x3f4 + +inline void fdc_sendDOR(byte dor); + +inline void fdc_sendDOR(byte dor) +{ + outportb(FDC_DOR, dor); +} + +#endif + + diff --git a/keyboard.c b/src/kernel/char/keyboard.c similarity index 91% rename from keyboard.c rename to src/kernel/char/keyboard.c index 5412870..bf8c26d 100644 --- a/keyboard.c +++ b/src/kernel/char/keyboard.c @@ -1,254 +1,246 @@ -//Keyboard.c -// Created: 04/17/03 Josh Holtrop -// Modified: 10/30/03 -//for HOS - -#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[128] = "\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[128] = "\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; - eoi(); - return; - } - if (kbdScan == 225) //2nd-set-extended key - { - kbdExt2 = 2; - 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--; - 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 - { - eoi(); - return; - } - if (kbdScan < KBD_SCAN_RELEASED) //a key was pressed, save it - { - if (kbdBufferLen >= KBD_BUFFER_LENGTH) //no key slots available - { - 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]); - } - } - - eoi(); - -} - -//Switches the case of an ASCII character -/*inline byte (byte asciiCode) -{ - if ((asciiCode >= 'A') & (asciiCode <= 'Z')) - return (asciiCode + ('a' - 'A')); - if ((asciiCode >= 'a') & (asciiCode <= 'z')) - return (asciiCode - ('a' - 'A')); - return asciiCode; -}*/ - -//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 -inline void kbd_resetLEDs() -{ - outportb(0x60, 0xED); - //outportb(0x60, (kbdFlags & 0x07)); - ackReason = 0xED; -} - - - - - - +// keyboard.c +// Author: Josh Holtrop +// Created: 04/17/03 +// Modified: 03/02/04 + +#include "hos_defines.h" +#include "keyboard.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[128] = "\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[128] = "\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; + eoi(); + return; + } + if (kbdScan == 225) //2nd-set-extended key + { + kbdExt2 = 2; + 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--; + 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 + { + eoi(); + return; + } + if (kbdScan < KBD_SCAN_RELEASED) //a key was pressed, save it + { + if (kbdBufferLen >= KBD_BUFFER_LENGTH) //no key slots available + { + 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]); + } + } + + 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/keyboard.h b/src/kernel/char/keyboard.h similarity index 62% rename from keyboard.h rename to src/kernel/char/keyboard.h index 3011fb3..a8e033e 100644 --- a/keyboard.h +++ b/src/kernel/char/keyboard.h @@ -1,47 +1,50 @@ -//Keyboard.h -// Created: 04/17/03 Josh Holtrop -// Modified: 05/07/03 -//for HOS - -#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(); -inline void kbd_resetLEDs(); -inline byte kbd_ascii(dword keycode); -inline byte kbd_scancode(dword keycode); -inline byte kbd_flags(dword keycode); -inline byte switchCase(byte asciiCode); -dword kbdGetKey(); -dword kbdWaitKey(); - - +// keyboard.h +// Author: Josh Holtrop +// Created: 04/17/03 +// Modified: 03/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(); +dword kbdGetKey(); +dword kbdWaitKey(); + + +#endif + diff --git a/mouse.c b/src/kernel/char/mouse.c similarity index 91% rename from mouse.c rename to src/kernel/char/mouse.c index d8542c9..d2e63ba 100644 --- a/mouse.c +++ b/src/kernel/char/mouse.c @@ -1,60 +1,69 @@ -// mouse.c -// 10/03/03 -// Author: Josh Holtrop - - -//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_x = video_mode.XResolution >> 1; - mouse_y = video_mode.YResolution >> 1; - - //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]; - mouse_x += adjx; - mouse_y -= adjy; //-= because screen y coordinates are opposite mouse y coordinates - if (mouse_x < 0) - mouse_x = 0; - if (mouse_x >= video_mode.XResolution) - mouse_x = video_mode.XResolution - 1; - if (mouse_y < 0) - mouse_y = 0; - if (mouse_y >= video_mode.YResolution) - mouse_y = video_mode.YResolution - 1; - if (mouse_inbuffer[0] & 0x01) //left button - video_pset(mouse_x, mouse_y, 0x00FF8800); - else - video_pset(mouse_x, mouse_y, 0x00FFFFFF); - } -} - - - - - +// mouse.c +// 10/03/03 +// Author: Josh Holtrop + +#include "mouse.h" +#include "hos_defines.h" + +#define MOUSE_BUFFER_LENGTH 16 + +int mouse_x; +int mouse_y; +int mouse_bytesRead = 0; +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_x = video_mode.XResolution >> 1; + mouse_y = video_mode.YResolution >> 1; + + //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]; + mouse_x += adjx; + mouse_y -= adjy; //-= because screen y coordinates are opposite mouse y coordinates + if (mouse_x < 0) + mouse_x = 0; + if (mouse_x >= video_mode.XResolution) + mouse_x = video_mode.XResolution - 1; + if (mouse_y < 0) + mouse_y = 0; + if (mouse_y >= video_mode.YResolution) + mouse_y = video_mode.YResolution - 1; + if (mouse_inbuffer[0] & 0x01) //left button + video_pset(mouse_x, mouse_y, 0x00FF8800); + else + video_pset(mouse_x, mouse_y, 0x00FFFFFF); + } +} + + + + + diff --git a/src/kernel/char/mouse.h b/src/kernel/char/mouse.h new file mode 100644 index 0000000..9deaa20 --- /dev/null +++ b/src/kernel/char/mouse.h @@ -0,0 +1,15 @@ +// mouse.h +// Author: Josh Holtrop +// Date: 10/03/03 +// Modified: 03/02/04 + +#ifndef __HOS_MOUSE__ +#define __HOS_MOUSE__ __HOS_MOUSE__ + + +void mouse_init(); +void isr_mouse(); + + +#endif + diff --git a/src/kernel/functions.c b/src/kernel/functions.c new file mode 100644 index 0000000..ee8d4b5 --- /dev/null +++ b/src/kernel/functions.c @@ -0,0 +1,8 @@ +//Functions.c +//05/07/03 Josh Holtrop +//for HOS +//Modified: 02/26/04 + +#include "functions.h" + + diff --git a/src/kernel/functions.h b/src/kernel/functions.h new file mode 100644 index 0000000..c0c1db9 --- /dev/null +++ b/src/kernel/functions.h @@ -0,0 +1,96 @@ +//functions.h +//05/07/03 Josh Holtrop +//for HOS +//Modified: 02/26/04 + +#include "hos_defines.h" + +#ifndef __HOS_FUNCTIONS__ +#define __HOS_FUNCTIONS__ __HOS_FUNCTIONS__ + +extern dword _code; +extern dword _bss; +extern dword _end; + +inline void enable_ints(); +inline void disable_ints(); +inline void restart(); +inline void halt(); +inline dword kernel_size(); +inline void timer_init(); +inline byte bcd2byte(byte bcd); +inline byte byte2bcd(byte bite); + +//Enables (SeTs) Interrupt Flag on the processor +inline void enable_ints() +{ + asm("sti"); +} + +//Disables (CLears) Interrupt Flag on the processor +inline void disable_ints() +{ + asm("cli"); +} + +//Restarts the computer +inline void restart() +{ + enable_ints(); + byte temp; + do + { + temp = inportb(0x64); + if (temp & 1) + inportb(0x60); + } while(temp & 2); + + + outportb (0x64, 0xfe); + for (;;) + { + } +} + +//Halts (freezes) the computer +inline void halt() +{ + asm("cli"); + asm("hlt"); + while (1) + ; +} + +//Initializes 8253 Programmable Interrupt Timer +inline void timer_init() +{ + //set timer : 2e9c = 100hz + outportb(0x43, 0x34); + outportb(0x40, 0x9c); //lsb + outportb(0x40, 0x2e); //msb +} + +//Returns the size of the kernel (code & data) +// - this does not include the bss section +// - this should be 4kb aligned per the linker script +// - this should be the size of kernel.bin +inline dword kernel_size() +{ + return (dword)(&_bss)-(dword)(&_code); +} + +//converts a binary-coded-decimal byte to its decimal equivalent +inline byte bcd2byte(byte bcd) +{ + return (10* ((bcd & 0xF0) >> 4)) + (bcd & 0x0F); +} + +//converts a binary-coded-decimal byte to its decimal equivalent +inline byte byte2bcd(byte bite) +{ + return ((bite / 10) << 4) | (bite % 10); +} + +#endif + + diff --git a/gdt.inc b/src/kernel/gdt.inc similarity index 93% rename from gdt.inc rename to src/kernel/gdt.inc index 63481f3..dcc5fec 100644 --- a/gdt.inc +++ b/src/kernel/gdt.inc @@ -1,71 +1,71 @@ -;gdt.inc -;Author: Josh Holtrop -;for HOS -;Modified: 10/30/03 - -gdtr: - dw gdt_end-gdt-1 - dd GDT_P -gdt: - dd 0 - dd 0 -KERNEL_CODE equ $-gdt - dw 0xffff ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x00 ;base 23:16 - db 0x9A ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -KERNEL_DATA equ $-gdt - dw 0xffff ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x00 ;base 23:16 - db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -VESA_CODE equ $-gdt - dw 0xffff ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x00 ;base 23:16 - db 0x9A ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -VESA_DATA equ $-gdt - dw 0xffff ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x00 ;base 23:16 - db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -VIDEO_TEXT equ $-gdt - dw 0x7FFF ;limit 15:0 - dw 0x8000 ;base 15:0 - db 0x0B ;base 23:16 - db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -VIDEO_GRAPHICS equ $-gdt - dw 0xFFFF ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x0A ;base 23:16 - db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -USER_CODE equ $-gdt - dw 0xffff ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x00 ;base 23:16 - db 0xFA ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -USER_DATA equ $-gdt - dw 0xffff ;limit 15:0 - dw 0x0000 ;base 15:0 - db 0x00 ;base 23:16 - db 0xF2 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) - db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 - db 0x00 ;base 31:24 -gdt_end: - - - +;gdt.inc +;Author: Josh Holtrop +;Date: 10/30/03 +;Modified: 03/02/04 + +gdtr: + dw gdt_end-gdt-1 + dd GDT_V +gdt: + dd 0 + dd 0 +KERNEL_CODE equ $-gdt + dw 0xffff ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x00 ;base 23:16 + db 0x9A ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +KERNEL_DATA equ $-gdt + dw 0xffff ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x00 ;base 23:16 + db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +USER_CODE equ $-gdt + dw 0xffff ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x00 ;base 23:16 + db 0xFA ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +USER_DATA equ $-gdt + dw 0xffff ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x00 ;base 23:16 + db 0xF2 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0xCF ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +gVESA_CODE equ $-gdt + dw 0xffff ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x00 ;base 23:16 + db 0x9A ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +VESA_DATA equ $-gdt + dw 0xffff ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x00 ;base 23:16 + db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +VIDEO_TEXT equ $-gdt + dw 0x7FFF ;limit 15:0 + dw 0x8000 ;base 15:0 + db 0x0B ;base 23:16 + db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +VIDEO_GRAPHICS equ $-gdt + dw 0xFFFF ;limit 15:0 + dw 0x0000 ;base 15:0 + db 0x0A ;base 23:16 + db 0x92 ;access ([P][DPL][1][Executable][Direction/Conforming][Writable/Readable][A]) + db 0x40 ;flags ([G][D/B][0][0]) / limit 19:16 + db 0x00 ;base 31:24 +dt_end: + + + diff --git a/src/kernel/hos_defines.h b/src/kernel/hos_defines.h new file mode 100644 index 0000000..817f3bf --- /dev/null +++ b/src/kernel/hos_defines.h @@ -0,0 +1,34 @@ +//hos_defines.h +//03/17/03 Josh Holtrop +//Modified: 03/02/04 + +#ifndef __HOS_HOS_DEFINES__ +#define __HOS_HOS_DEFINES__ __HOS_HOS_DEFINES__ + +#define FREERAM_START 0x368000 // 0x368000 is first available byte (this is right after the initrd @ 2mb, 1440kb. +#define MAX_RAM 0x40000000 //1gb maximum RAM supported + +#define PID_KERNEL 0x02 //kernel's PID +#define PID_VMM 0x03 +#define PID_USER 0x10000 //user processes' start PID + + +//these defines are the memory locations of values saved by the stage 2 bootloader +#define BOOT_MEMMAP_ENTRIES 0xC009040A +#define BOOT_FIRST_MEMMAP 0xC0092000 +#define BOOT_VIDEO_MODE 0xC0090002 +#define BOOT_VIDEO_MODE_INFO_BLOCK 0xC0090306 + + +typedef unsigned char byte; +typedef unsigned short word; +typedef unsigned int dword; + +typedef struct { + dword lowdword; + dword highdword; +} __attribute__((packed)) qword; + + +#endif + diff --git a/idt.inc b/src/kernel/idt.inc similarity index 88% rename from idt.inc rename to src/kernel/idt.inc index 03067d5..ddabf24 100644 --- a/idt.inc +++ b/src/kernel/idt.inc @@ -1,117 +1,117 @@ -;idt.inc -;Author: Josh Holtrop -;for HOS -;Modified: 10/30/03 - -idtr: - dw 50*8-1 ;size of idt - dd IDT_V ;address of idt - - -%macro isr_label 1 -isr_%1: - push eax - mov eax, %1 - jmp isr_main -%endmacro - -isr_label 0 -isr_label 1 -isr_label 2 -isr_label 3 -isr_label 4 -isr_label 5 -isr_label 6 -isr_label 7 -isr_label 8 -isr_label 9 -isr_label 10 -isr_label 11 -isr_label 12 -isr_label 13 -isr_label 14 -isr_label 15 -isr_label 16 -isr_label 17 -isr_label 18 -isr_label 19 -isr_label 20 -isr_label 21 -isr_label 22 -isr_label 23 -isr_label 24 -isr_label 25 -isr_label 26 -isr_label 27 -isr_label 28 -isr_label 29 -isr_label 30 -isr_label 31 -isr_label 32 -isr_label 33 -isr_label 34 -isr_label 35 -isr_label 36 -isr_label 37 -isr_label 38 -isr_label 39 -isr_label 40 -isr_label 41 -isr_label 42 -isr_label 43 -isr_label 44 -isr_label 45 -isr_label 46 -isr_label 47 -isr_label 48 -isr_label 49 - -isr_main: - cmp eax, 0x30 - jz isr_syscall - - pusha - push ds - push es - - push eax - - call _isr - - pop eax - - pop es - pop ds - popa - pop eax - - iret - - -isr_syscall: - pop eax ;syscall function number - pusha - push ds - push es - -sc1: - cmp eax, 1 ;syscall 1 - putc - jnz sc2 - push ebx - call _putc - add esp, 4 - jmp scdone -sc2: - -scdone: - pop es - pop ds - popa - iret - - - - - - - +;idt.inc +;Author: Josh Holtrop +;Date: 10/30/03 +;Modified: 03/02/04 + +idtr: + dw 50*8-1 ;size of idt + dd IDT_V ;address of idt + + +%macro isr_label 1 +isr_%1: + push eax + mov eax, %1 + jmp isr_main +%endmacro + +isr_label 0 +isr_label 1 +isr_label 2 +isr_label 3 +isr_label 4 +isr_label 5 +isr_label 6 +isr_label 7 +isr_label 8 +isr_label 9 +isr_label 10 +isr_label 11 +isr_label 12 +isr_label 13 +isr_label 14 +isr_label 15 +isr_label 16 +isr_label 17 +isr_label 18 +isr_label 19 +isr_label 20 +isr_label 21 +isr_label 22 +isr_label 23 +isr_label 24 +isr_label 25 +isr_label 26 +isr_label 27 +isr_label 28 +isr_label 29 +isr_label 30 +isr_label 31 +isr_label 32 +isr_label 33 +isr_label 34 +isr_label 35 +isr_label 36 +isr_label 37 +isr_label 38 +isr_label 39 +isr_label 40 +isr_label 41 +isr_label 42 +isr_label 43 +isr_label 44 +isr_label 45 +isr_label 46 +isr_label 47 +isr_label 48 +isr_label 49 + +isr_main: + cmp eax, 0x30 + jz isr_syscall + + pusha + push ds + push es + + push eax + + call _isr + + add esp, 4 + + pop es + pop ds + popa + pop eax + + iret + + +isr_syscall: + pop eax ;syscall function number + pusha + push ds + push es + +sc1: + cmp eax, 1 ;syscall 1 - putc + jnz sc2 + push ebx + call _putc + add esp, 4 + jmp scdone +sc2: + +scdone: + pop es + pop ds + popa + iret + + + + + + + diff --git a/kernel.asm b/src/kernel/kernel.asm similarity index 94% rename from kernel.asm rename to src/kernel/kernel.asm index c5d18f6..4ca707b 100644 --- a/kernel.asm +++ b/src/kernel/kernel.asm @@ -1,101 +1,102 @@ -;kernel.asm -;Author: Josh Holtrop -;Modified: 10/30/03 - -%define GDT_P 0x100000; ;1mb physical - Global Descriptor Table space -%define GDT_V GDT_P+0xC0000000 -%define IDT_P 0x102000 ;1mb+8kb - Interrupt Descriptor Table space -%define IDT_V IDT_P+0xC0000000 -%define PDBR_P 0x104000 ;1mb+16kb - Page Directory Base Register (first PD) -%define PDBR_V PDBR_P+0xC0000000 -%define LOPT_P 0x105000 ;1mb+20kb - LOw Page Table for mapping first 4mb -%define LOPT_V LOPT_P+0xC0000000 -%define KERNEL_P 0x106000 ;1mb+24kb - the kernel's physical address -%define KERNEL_V KERNEL_P+0xC0000000 ;3gb+1mb+24kb, the virtual address of the kernel - -[global start] -[extern _isr] -[extern _k_init] -[extern _putc] - -bits 32 - -;This is where the kernel begins execution -;At this point, the temporary gdt is set up to "map" 0xC000_0000 to 0x0. -;We must enable paging with the first 4mb mapped 1:1 virtual:physical -; and with the 4mb starting at 0xC000_0000 mapped to the first 4mb physical. -;Then we can start using our "real" gdt, then unmap the lower 4mb. -start: - cli ;if they weren't already off - - xor eax, eax - mov edi, PDBR_V - mov ecx, 1024 ;clear the PDBR - rep stosd - mov [PDBR_V], dword LOPT_P|0x03 ;store the physical address of the LOw Page Table (read/write, present) - mov [PDBR_V+0xC00], dword LOPT_P|0x03 ;store the physical address of the LOw Page Table (read/write, present) - - mov edi, LOPT_V - mov ecx, 1024 - mov eax, 0x03 ;starting physical address = 0x0 (read/write, present flags) -fill_lopt_loop: ;fill the page table - stosd - add eax, 4096 ;increment next phsyical address by 4kb - loop fill_lopt_loop - - mov eax, PDBR_P - mov cr3, eax ;store the Page Directory Base Address - mov eax, cr0 - or eax, 0x80000000 ;set page enable bit - mov cr0, eax ;now paging is active! - - - mov edi, GDT_V - mov esi, gdt - mov ecx, gdt_end-gdt -copy_gdt: - lodsb - stosb - loop copy_gdt - - mov edi, IDT_V ;destination - mov esi, isr_0 ;address of isr0 - mov edx, isr_1-isr_0 ;distance between isr labels - mov ecx, 50 ;number of isrlabels -fill_idt: - mov ebx, esi - mov ax, si - stosw ;0 offset 15:0 - mov ax, KERNEL_CODE - stosw ;2 selector 15:0 - mov ax, 0x8E00 - stosw ;4 [P][DPL][0][TYPE][0][0][0][0][0][0][0][0] - shr esi, 16 - mov ax, si - stosw ;6 offset 31:16 - mov esi, ebx - add esi, edx - loop fill_idt - mov word [IDT_V+0x30*8+4], 0xEE00 ;interrupt 0x30 has user priviledges - - lgdt [gdtr] ;load gdt - jmp KERNEL_CODE:newgdtcontinue -newgdtcontinue: - mov ax, KERNEL_DATA - mov es, ax - mov ds, ax - mov gs, ax - mov fs, ax - mov ss, ax - mov esp, 0xc01ffffc ;stack just under 3gb+2mb, moves downward - lidt [idtr] ;load idt - - call _k_init -haltit: - hlt ;halt processor when k_init is done - jmp haltit ;shouldn't get here... - -%include "gdt.inc" -%include "idt.inc" - - +;kernel.asm +;Author: Josh Holtrop +;Date: 10/30/03 +;Modified: 10/30/03 + +%define GDT_P 0x100000; ;1mb physical - Global Descriptor Table space +%define GDT_V GDT_P+0xC0000000 +%define IDT_P 0x102000 ;1mb+8kb - Interrupt Descriptor Table space +%define IDT_V IDT_P+0xC0000000 +%define PDBR_P 0x104000 ;1mb+16kb - Page Directory Base Register (first PD) +%define PDBR_V PDBR_P+0xC0000000 +%define LOPT_P 0x105000 ;1mb+20kb - LOw Page Table for mapping first 4mb +%define LOPT_V LOPT_P+0xC0000000 +%define KERNEL_P 0x106000 ;1mb+24kb - the kernel's physical address +%define KERNEL_V KERNEL_P+0xC0000000 ;3gb+1mb+24kb, the virtual address of the kernel + +[global start] +[extern _isr] +[extern _k_init] +[extern _putc] + +bits 32 + +;This is where the kernel begins execution +;At this point, the temporary gdt is set up to "map" 0xC000_0000 to 0x0. +;We must enable paging with the first 4mb mapped 1:1 virtual:physical +; and with the 4mb starting at 0xC000_0000 mapped to the first 4mb physical. +;Then we can start using our "real" gdt, then unmap the lower 4mb. +start: + cli ;if they weren't already off + + xor eax, eax + mov edi, PDBR_V + mov ecx, 1024 ;clear the PDBR + rep stosd + mov [PDBR_V], dword LOPT_P|0x03 ;store the physical address of the LOw Page Table (read/write, present) + mov [PDBR_V+0xC00], dword LOPT_P|0x03 ;store the physical address of the LOw Page Table (read/write, present) + + mov edi, LOPT_V + mov ecx, 1024 + mov eax, 0x03 ;starting physical address = 0x0 (read/write, present flags) +fill_lopt_loop: ;fill the page table + stosd + add eax, 4096 ;increment next phsyical address by 4kb + loop fill_lopt_loop + + mov eax, PDBR_P + mov cr3, eax ;store the Page Directory Base Address + mov eax, cr0 + or eax, 0x80000000 ;set page enable bit + mov cr0, eax ;now paging is active! + + + mov edi, GDT_V + mov esi, gdt + mov ecx, gdt_end-gdt +copy_gdt: + lodsb + stosb + loop copy_gdt + + mov edi, IDT_V ;destination + mov esi, isr_0 ;address of isr0 + mov edx, isr_1-isr_0 ;distance between isr labels + mov ecx, 50 ;number of isrlabels +fill_idt: + mov ebx, esi + mov ax, si + stosw ;0 offset 15:0 + mov ax, KERNEL_CODE + stosw ;2 selector 15:0 + mov ax, 0x8E00 + stosw ;4 [P][DPL][0][TYPE][0][0][0][0][0][0][0][0] + shr esi, 16 + mov ax, si + stosw ;6 offset 31:16 + mov esi, ebx + add esi, edx + loop fill_idt + mov word [IDT_V+0x30*8+4], 0xEE00 ;interrupt 0x30 has user priviledges + + lgdt [gdtr] ;load gdt + jmp KERNEL_CODE:newgdtcontinue +newgdtcontinue: + mov ax, KERNEL_DATA + mov es, ax + mov ds, ax + mov gs, ax + mov fs, ax + mov ss, ax + mov esp, 0xc0200000 ;stack just under 3gb+2mb, moves downward + lidt [idtr] ;load idt + + call _k_init +haltit: + hlt ;halt processor when k_init is done + jmp haltit ;shouldn't get here... + +%include "gdt.inc" +%include "idt.inc" + + diff --git a/kernel.c b/src/kernel/kernel.c similarity index 51% rename from kernel.c rename to src/kernel/kernel.c index e18ccb9..6735628 100644 --- a/kernel.c +++ b/src/kernel/kernel.c @@ -1,143 +1,101 @@ -//kernel.c -//08/13/03 Josh Holtrop -//Holtrop's Operating System -//Version: 0.12 -//Modified: 12/30/03 - -#include "k_defines.h" //#DEFINE's for kernel - - -#include "functions.h" //general functions -#include "video.h" //video functions -#include "mm.h" //physical memory management functions -#include "vmm.h" //virtual memory management & paging functions -#include "keyboard.h" //generic keyboard driver & functions -#include "mouse.h" //generic ps/2 mouse driver & functions -#include "fdc.h" //Floppy Disk Controller functions -#include "stdfont.h" //Standard font bitmask array -#include "kio.h" -#include "vfs.h" -#include "rd.h" -#include "fat12.h" - -void isr(dword num); -void k_init(); - -/* These functions are defined in asmfuncs.asm */ -extern dword write_cr0(dword cr0); -extern dword read_cr0(); -extern dword write_cr3(dword cr3); -extern dword read_cr2(); -extern dword read_cr3(); -extern void writeCursorPosition(dword pos); -extern dword getCursorPosition(); -extern void console_scroll(); -extern void console_cls(); -extern int puts(char *str); -extern int putDec(int number); -extern int putDecu(dword number); -extern void strcpy(char *dest, char *src); -extern void memcpy(void *dest, void *src, dword n); -extern dword strlen(char *str); - -#include "fat12.c" -#include "rd.c" -#include "vfs.c" -#include "kio.c" -#include "fdc.c" -#include "mouse.c" -#include "keyboard.c" -#include "mm.c" -#include "vmm.c" -#include "functions.c" -#include "video.c" - -dword timer = 0; - -//Main kernel initialization method -void k_init() -{ - // ===== Initialization - fdc_sendDOR(0x0C); //turn off floppy motor!! - console_cls(); - video_init(); - mm_init(); - vmm_init(); - remap_pics(0x20, 0x28); - init_timer(); - mouse_init(); - pic1_mask(0); //unmask IRQ's 0-7 - pic2_mask(0); //unmask IRQ's 8-15 - vfs_init(); - enable_ints(); - kbd_resetLEDs(); //after enabling interrupts!! - if (videoMode) - { - int p = video_mode.XResolution*video_mode.YResolution-1; - for (; p >= 0; p--) - video_psetp(p, 0x00000077); - video_drawConsole(); - } - - printf("HOS 0.13 - Kernel File Size: %u kb\tData Size: %u bytes\n", kernel_size()>>10, (dword)(&_end)-(dword)(&_code)); - printf("Memory available to OS: %u MB (%u bytes)\n", mm_megabytes, mm_totalmem); - printf("Free memory: %u bytes (%u pages)\n", mm_freemem(), mm_freemem()>>12); - printf("%d/%d/%d\t%d:%d:%d\n", rtc_readMonth(), rtc_readDay(), rtc_readYear(), rtc_readHour(), rtc_readMinute(), rtc_readSecond()); - printf("Root Directory: %s/\n", rootDevice->id); - -/* int a; - byte *addr = 0; - for (a = 0; a < 5; a++) - { - byte *app = mm_palloc(); - vmm_map1((dword)addr, (dword)app); - addr += 4096; - } - - addr = vfs_readFile("/bin/hash.hos"); - memcpy(0, addr, 4192); - asm("call 0"); - free(addr); -*/ - - dword key = 0; - for (;;) - { - key = kbdWaitKey(); - if ((key & 0xFF) > 2) //key is not a control key - putc(key); - } -} - -// main Interrupt Service Routine - handles all interrupts unless caught by kernel.asm -void isr(dword num) -{ - switch(num) - { - case 14: - printf("Page fault, CR2 = 0x%x\n", read_cr2()); - halt(); - break; - case 0x20: // IRQ0 - timer interrupt - timer++; - (*(byte *)(0xc00b8000))++; - eoi(); - break; - case 0x21: // IRQ1 - keyboard interrupt - isr_keyboard(); //isr_keybard() takes care of calling eoi() - break; - case 0x2C: // IRQ12 - PS/2 mouse - isr_mouse(); - eoi2(); - break; - default: - printf("Interrupt %d (0x%x) Unhandled!!\n", num, num); - halt(); - break; - } -} - - - - - +// kernel.c +// Author: Josh Holtrop +// Date: 08/13/03 +// Holtrop's Operating System - Version 0.13 +// Modified: 03/02/04 + +#include "hos_defines.h" //#DEFINE's for kernel + +#include "functions.h" //general functions +#include "asmfuncs.h" //assembly functions +#include "kio.h" //kernel input/output functions +#include "mm/mm.h" //physical memory management functions +#include "mm/vmm.h" //virtual memory management & paging functions +#include "char/keyboard.h" //generic keyboard driver & functions +#include "char/mouse.h" //generic ps/2 mouse driver & functions +#include "block/fdc.h" //Floppy Disk Controller functions +#include "string/string.h" //string functions +#include "sys/cmos.h" //CMOS interface functions +#include "sys/io.h" //port i/o functions +#include "sys/pic.h" //Programmable Interrupt Controller functions +#include "sys/rtc.h" //Real Time Clock functions +#include "video/stdfont.h" //Standard font bitmask array +#include "video/video.h" //video functions + +void isr(dword num); +void k_init(); + +dword timer = 0; + +//Main kernel initialization method +void k_init() +{ + // ===== Initialization + fdc_sendDOR(0x0C); //turn off floppy motor!! + console_cls(); + video_init(); + mm_init(); + vmm_init(); + remap_pics(0x20, 0x28); + init_timer(); + mouse_init(); + pic1_mask(0); //unmask IRQ's 0-7 + pic2_mask(0); //unmask IRQ's 8-15 + vfs_init(); + enable_ints(); + kbd_resetLEDs(); //after enabling interrupts!! + if (videoMode) + { + int p = video_mode.XResolution*video_mode.YResolution-1; + for (; p >= 0; p--) + video_psetp(p, 0x00000077); + video_drawConsole(); + } + + printf("HOS 0.13 - Kernel File Size: %u kb\tData Size: %u bytes\n", kernel_size()>>10, (dword)(&_end)-(dword)(&_code)); + printf("Memory available to OS: %u MB (%u bytes)\n", mm_megabytes, mm_totalmem); + printf("Free memory: %u bytes (%u pages)\n", mm_freemem(), mm_freemem()>>12); + printf("%d/%d/%d\t%d:%d:%d\n", rtc_readMonth(), rtc_readDay(), rtc_readYear(), rtc_readHour(), rtc_readMinute(), rtc_readSecond()); + printf("Root Directory: %s/\n", rootDevice->id); + + dword key = 0; + for (;;) + { + key = kbdWaitKey(); + if ((key & 0xFF) > 2) //key is not a control key + putc(key); + } +} + +// main Interrupt Service Routine - handles all interrupts unless caught by kernel.asm +void isr(dword num) +{ + switch(num) + { + case 14: + printf("Page fault, CR2 = 0x%x\n", read_cr2()); + halt(); + break; + case 0x20: // IRQ0 - timer interrupt + timer++; + (*(byte *)(0xc00b8000))++; + eoi(); + break; + case 0x21: // IRQ1 - keyboard interrupt + isr_keyboard(); //isr_keybard() takes care of calling eoi() + break; + case 0x2C: // IRQ12 - PS/2 mouse + isr_mouse(); + eoi2(); + break; + default: + printf("Interrupt %d (0x%x) Unhandled!!\n", num, num); + halt(); + break; + } +} + + + + + diff --git a/kio.c b/src/kernel/kio.c similarity index 92% rename from kio.c rename to src/kernel/kio.c index 0bb3514..7865c4a 100644 --- a/kio.c +++ b/src/kernel/kio.c @@ -1,133 +1,136 @@ - -//kio.c -// Author: Josh Holtrop -// Created: 12/25/03 -// Modified: 12/25/03 - - -// This is the main output routine, it uses a format string and a variable -// number of arguments to print formatted text -void printf(char *fmt, ...) -{ - dword *params = ((dword *)(&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': - putDec(*params); - params++; - break; - case 'u': case 'U': - putDecu(*params); - params++; - break; - case 'x': case 'X': - putHex(*params); - params++; - break; - } - } - else - { - switch (fmt[i]) - { - case '%': - special = 1; - break; - case 0: - return; - default: - putc(fmt[i]); - } - } - } -} - - -// This function draws a single character -void putc(dword chr) -{ - char charac = (char)chr; - word *vidmem = (word *)0xC00B8000; - if (charac == '\n') - { - if (cursorPosition % 80) - cursorPosition = cursorPosition + 80 - (cursorPosition % 80); - else - cursorPosition += 80; - } - else if (charac == '\t') - { - if (cursorPosition % 8) - cursorPosition = cursorPosition + 8 - (cursorPosition % 8); - else - cursorPosition += 8; - } - else - { - if (videoMode) - { - console_memory[cursorPosition] = charac | 0x0700; - video_drawConsoleChar(cursorPosition); - } - else - { - console_memory[cursorPosition] = charac | 0x0700; - vidmem[cursorPosition] = charac | 0x0700; - } - cursorPosition++; - } - if (cursorPosition >= 2000) - { - console_scroll(); - cursorPosition = 2000-80; - if (videoMode) - video_drawConsole(); - } - if (!videoMode) - writeCursorPosition(cursorPosition); -} - - -// This function displays a number in hexadecimal -int putHex(dword number) -{ - int hitNum = 0; - int i; - for (i = 7; i >= 0; i--) - { - dword val = (number >> (i*4)) & 0xF; - if ((val != 0) || (i == 0)) - hitNum = 1; - if (hitNum) - { - val = val + '0'; - if (val > '9') - val = val + ('A' - '9' - 1); - putc(val); - } - } -} - - - - +// kio.c +// Author: Josh Holtrop +// Created: 12/25/03 +// Modified: 03/02/04 + +#include "hos_defines.h" +#include "kio.h" + +dword cursorPosition = 0; //Caches the current cursor position + +// This is the main output routine, it uses a format string and a variable +// number of arguments to print formatted text +void printf(char *fmt, ...) +{ + dword *params = ((dword *)(&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': + putDec(*params); + params++; + break; + case 'u': case 'U': + putDecu(*params); + params++; + break; + case 'x': case 'X': + putHex(*params); + params++; + break; + } + } + else + { + switch (fmt[i]) + { + case '%': + special = 1; + break; + case 0: + return; + default: + putc(fmt[i]); + } + } + } +} + + +// This function draws a single character +void putc(dword chr) +{ + char charac = (char)chr; + word *vidmem = (word *)0xC00B8000; + if (charac == '\n') + { + if (cursorPosition % 80) + cursorPosition = cursorPosition + 80 - (cursorPosition % 80); + else + cursorPosition += 80; + } + else if (charac == '\t') + { + if (cursorPosition % 8) + cursorPosition = cursorPosition + 8 - (cursorPosition % 8); + else + cursorPosition += 8; + } + else + { + if (videoMode) + { + console_memory[cursorPosition] = charac | 0x0700; + video_drawConsoleChar(cursorPosition); + } + else + { + console_memory[cursorPosition] = charac | 0x0700; + vidmem[cursorPosition] = charac | 0x0700; + } + cursorPosition++; + } + if (cursorPosition >= 2000) + { + console_scroll(); + cursorPosition = 2000-80; + if (videoMode) + video_drawConsole(); + } + if (!videoMode) + writeCursorPosition(cursorPosition); +} + + +// This function displays a number in hexadecimal +int putHex(dword number) +{ + int hitNum = 0; + int i; + for (i = 7; i >= 0; i--) + { + dword val = (number >> (i*4)) & 0xF; + if ((val != 0) || (i == 0)) + hitNum = 1; + if (hitNum) + { + val = val + '0'; + if (val > '9') + val = val + ('A' - '9' - 1); + putc(val); + } + } +} + + + + diff --git a/kio.h b/src/kernel/kio.h similarity index 65% rename from kio.h rename to src/kernel/kio.h index 8ddb937..40137cc 100644 --- a/kio.h +++ b/src/kernel/kio.h @@ -1,15 +1,17 @@ -//kio.h -// Author: Josh Holtrop -// Created: 12/25/03 -// Modified: 12/25/03 - - - -void printf(char *fmt, ...); -void putc(dword chr); -int putHex(dword number); - - -dword cursorPosition = 0; //Caches the current cursor position - - +//kio.h +// Author: Josh Holtrop +// Created: 12/25/03 +// Modified: 12/25/03 + +#include "hos_defines.h" + +#ifndef __HOS_KIO__ +#define __HOS_KIO__ __HOS_KIO__ + +void printf(char *fmt, ...); +void putc(dword chr); +int putHex(dword number); + + +#endif + diff --git a/link.ld b/src/kernel/link.ld similarity index 100% rename from link.ld rename to src/kernel/link.ld diff --git a/mm.c b/src/kernel/mm/mm.c similarity index 95% rename from mm.c rename to src/kernel/mm/mm.c index 679a990..1e79bf8 100644 --- a/mm.c +++ b/src/kernel/mm/mm.c @@ -1,121 +1,124 @@ -// mm.c -// Author: Josh Holtrop -// Created: 09/01/03 -// Modified: 12/28/03 - -//The total amount of physical memory available (bytes, 1 bit per page) -#define BITMAP_SIZE 0x20000 -dword mm_totalmem = 0; -dword mm_megabytes; -byte page_bitmap[BITMAP_SIZE]; //used to store a bit for each page that is used, 0 if available - //0x20000*(8 bits/byte)=0x100000 pages in 4gb total - -//This function initializes the memory manager's linked list, filling it with the -// memory areas returned by bios interrupt 0x8E20 -void mm_init() -{ - dword memmap_entries = *(dword *)BOOT_MEMMAP_ENTRIES; - memmap_entry *maps = (memmap_entry *) BOOT_FIRST_MEMMAP; - dword a; - for (a = 0; a < BITMAP_SIZE; a++) - { - page_bitmap[a] = 0xFF; //all pages used - } - for (a = 0; a < memmap_entries; a++) - { - if (maps[a].attributes == 1) // (1) mem free to OS - { - mm_totalmem += maps[a].limit.lowdword; - if ((maps[a].base.lowdword + maps[a].limit.lowdword) >= (FREERAM_START+4096)) //goes past where we start freeram - { - if (maps[a].base.lowdword < FREERAM_START) - { - mm_pfreen(FREERAM_START, (maps[a].limit.lowdword - (FREERAM_START - maps[a].base.lowdword)) >> 12); - } - else - { - mm_pfreen(maps[a].base.lowdword, maps[a].limit.lowdword >> 12); //set the appropriate bits as "free" in the page bitmap - } - } - } - } - if (mm_totalmem % 0x100000) - mm_megabytes = (mm_totalmem >> 20) + 1; - else - mm_megabytes = mm_totalmem >> 20; -} - - -// This function frees a certain number of pages starting at the address -// specified in base for a length of pages pages -void mm_pfreen(dword base, dword pages) -{ - dword a; - dword max = base + (pages << 12); - for (a = base; a < max; a += 4096) - { - mm_pfree(a); - } -} - - -// This function frees a single page -void mm_pfree(dword base) -{ -// dword pageNumber = base >> 12; // >>12 == /4096 - dword byteNumber = base >> 15; //pageNumber >> 3; //pageNumber/8 - dword bitNumber = (base >> 12) % 8; //pageNumber % 8; - page_bitmap[byteNumber] = page_bitmap[byteNumber] & ((0x01 << bitNumber) ^ 0xFF); -} - - -// This function allocates a single page, returning its physical address -void *mm_palloc() -{ - dword bite; - for (bite = 0; bite < BITMAP_SIZE; bite++) - { - if (page_bitmap[bite] != 0xFF) //there is an available page within this 8-page region - { - int bit; - for (bit = 0; bit < 8; bit++) - { - if (!(page_bitmap[bite] & (1 << bit))) //this bite/bit combination is available - { - page_bitmap[bite] = page_bitmap[bite] | (1 << bit); //set page as used - return (void *)((bite << 15) | (bit << 12)); - } - } - } - } - return 0; //no free page -} - - -// This function reports the number of bytes of free physical memory -dword mm_freemem() -{ - dword a; - dword pages = 0; - for (a = 0; a < BITMAP_SIZE; a++) - { - int bit; - for (bit = 0; bit < 8; bit++) - { - if (!(page_bitmap[a] & (1 << bit))) - pages++; - } - } - return pages << 12; -} - - - - - - - - - - - +// mm.c +// Author: Josh Holtrop +// Created: 09/01/03 +// Modified: 03/02/04 + +#include "hos_defines.h" +#include "mm.h" + +//The total amount of physical memory available (bytes, 1 bit per page) +#define BITMAP_SIZE 0x20000 +dword mm_totalmem = 0; +dword mm_megabytes; +byte page_bitmap[BITMAP_SIZE]; //used to store a bit for each page that is used, 0 if available + //0x20000*(8 bits/byte)=0x100000 pages in 4gb total + +//This function initializes the memory manager's linked list, filling it with the +// memory areas returned by bios interrupt 0x8E20 +void mm_init() +{ + dword memmap_entries = *(dword *)BOOT_MEMMAP_ENTRIES; + memmap_entry *maps = (memmap_entry *) BOOT_FIRST_MEMMAP; + dword a; + for (a = 0; a < BITMAP_SIZE; a++) + { + page_bitmap[a] = 0xFF; //all pages used + } + for (a = 0; a < memmap_entries; a++) + { + if (maps[a].attributes == 1) // (1) mem free to OS + { + mm_totalmem += maps[a].limit.lowdword; + if ((maps[a].base.lowdword + maps[a].limit.lowdword) >= (FREERAM_START+4096)) //goes past where we start freeram + { + if (maps[a].base.lowdword < FREERAM_START) + { + mm_pfreen(FREERAM_START, (maps[a].limit.lowdword - (FREERAM_START - maps[a].base.lowdword)) >> 12); + } + else + { + mm_pfreen(maps[a].base.lowdword, maps[a].limit.lowdword >> 12); //set the appropriate bits as "free" in the page bitmap + } + } + } + } + if (mm_totalmem % 0x100000) + mm_megabytes = (mm_totalmem >> 20) + 1; + else + mm_megabytes = mm_totalmem >> 20; +} + + +// This function frees a certain number of pages starting at the address +// specified in base for a length of pages pages +void mm_pfreen(dword base, dword pages) +{ + dword a; + dword max = base + (pages << 12); + for (a = base; a < max; a += 4096) + { + mm_pfree(a); + } +} + + +// This function frees a single page +void mm_pfree(dword base) +{ +// dword pageNumber = base >> 12; // >>12 == /4096 + dword byteNumber = base >> 15; //pageNumber >> 3; //pageNumber/8 + dword bitNumber = (base >> 12) % 8; //pageNumber % 8; + page_bitmap[byteNumber] = page_bitmap[byteNumber] & ((0x01 << bitNumber) ^ 0xFF); +} + + +// This function allocates a single page, returning its physical address +void *mm_palloc() +{ + dword bite; + for (bite = 0; bite < BITMAP_SIZE; bite++) + { + if (page_bitmap[bite] != 0xFF) //there is an available page within this 8-page region + { + int bit; + for (bit = 0; bit < 8; bit++) + { + if (!(page_bitmap[bite] & (1 << bit))) //this bite/bit combination is available + { + page_bitmap[bite] = page_bitmap[bite] | (1 << bit); //set page as used + return (void *)((bite << 15) | (bit << 12)); + } + } + } + } + return 0; //no free page +} + + +// This function reports the number of bytes of free physical memory +dword mm_freemem() +{ + dword a; + dword pages = 0; + for (a = 0; a < BITMAP_SIZE; a++) + { + int bit; + for (bit = 0; bit < 8; bit++) + { + if (!(page_bitmap[a] & (1 << bit))) + pages++; + } + } + return pages << 12; +} + + + + + + + + + + + diff --git a/mm.h b/src/kernel/mm/mm.h similarity index 60% rename from mm.h rename to src/kernel/mm/mm.h index 3de6ab2..97404e8 100644 --- a/mm.h +++ b/src/kernel/mm/mm.h @@ -1,21 +1,27 @@ - - -typedef struct { - qword base; - qword limit; - dword attributes; -} __attribute__((packed)) memmap_entry; - - - -void mm_init(); -void mm_pfreen(dword base, dword pages); -void mm_pfree(dword base); -void *mm_palloc(); -dword mm_freemem(); - - - - - - +// mm.c +// Author: Josh Holtrop +// Created: 09/01/03 +// Modified: 03/02/04 + +#include "hos_defines.h" + +#ifndef __HOS_MM__ +#define __HOS_MM__ __HOS_MM__ + + +typedef struct { + qword base; + qword limit; + dword attributes; +} __attribute__((packed)) memmap_entry; + + +void mm_init(); +void mm_pfreen(dword base, dword pages); +void mm_pfree(dword base); +void *mm_palloc(); +dword mm_freemem(); + + +#endif + diff --git a/vmm.c b/src/kernel/mm/vmm.c similarity index 75% rename from vmm.c rename to src/kernel/mm/vmm.c index 664f983..179c69a 100644 --- a/vmm.c +++ b/src/kernel/mm/vmm.c @@ -1,354 +1,358 @@ -// vmm.c -// Author: Josh Holtrop -// Date: 09/30/03 -// Rewritten from scratch: 12/23/03 -// Modified: 12/30/03 - - -// This is the initialization procedure for the Virtual Memory Manager -// It sets up the final page directory/page table setup and maps video memory, if present -void vmm_init() -{ - dword *pageTables = (dword *)0xC0104000; //this is the location of the page directory - pageTables[0x3FF] = 0x104000|0x03; //the last page directory entry points to the page directory itself - pageTables[0] = 0; - invlpg(0); - if (videoMode) //we are in a graphical mode - { - dword vidPages = video_mode.XResolution * video_mode.YResolution * (video_mode.BitsPerPixel >> 3); - if (vidPages % 4096) - vidPages = (vidPages >> 12) + 1; - else - vidPages = (vidPages >> 12); - vmm_mapn(0xF0000000, video_mode.PhysBasePtr, vidPages); - } - dword firstHeapEntryBlock = (dword)mm_palloc(); - vmm_map1((dword)firstHeapEntry, firstHeapEntryBlock); - HeapEntryBlock *heb = (HeapEntryBlock *)firstHeapEntry; - vmm_heb_init(heb); - heb->entry[0].base = (dword)firstHeapEntry; //start of kernel's heap memory - heb->entry[0].size = 4096; //the first HeapEntryBlock is 1 page long - heb->entry[0].attributes = VMM_HE_HEB; //this is a HeapEntryBlock - heb->entry[1].base = (dword)firstHeapEntry+4096; //this is the start of the rest of the kernel's heap memory - heb->entry[1].size = 0x10000000-4096; //the rest of the kernel's heap memory: 256mb - 4kb - heb->entry[1].attributes = VMM_HE_HOLE; //this is a hold - an unmapped section of heap memory -} - - -// This function initialzes a Heap Entry Block to unused entries linked together -void vmm_heb_init(HeapEntryBlock *heb) -{ - int a; - for (a = 0; a < 256; a++) - { - heb->entry[a].base = 0; - heb->entry[a].size = 0; - heb->entry[a].attributes = VMM_HE_UNUSED; - heb->entry[a].link = (dword)&(heb->entry[a+1]); - } - heb->entry[255].link = 0; -} - - -// This function maps a virtual address to a physical address using the page directory / page table -void vmm_map1(dword virt, dword physical) -{ - dword pde = virt >> 22; - dword pte = (virt & 0x003FF000) >> 12; - dword *pageTables = (dword *)0xC0104000; //this is the location of the page directory - if (!(pageTables[pde] & 0x01)) //the page directory entry does not exist, we must allocate a page for it - { - dword *newpagetable = mm_palloc(); - pageTables[pde] = ((dword)newpagetable) | 0x03; - invlpg(virt); - dword *newpteptr = (dword *)(0xFFC00000 | (pde << 12)); //points to first dword of newly allocated page table - int a; - for (a = 0; a < 1024; a++) - { - newpteptr[a] = 0; - } - } - dword *pteptr = (dword *)(0xFFC00000 | (pde << 12) | (pte << 2)); - *pteptr = physical | 0x03; - invlpg(virt); -} - - -// This function maps a variable number of pages in a row -void vmm_mapn(dword virt, dword physical, dword n) -{ - for (; n > 0; n--) - { - vmm_map1(virt, physical); - virt += 4096; - physical += 4096; - } -} - - -// This function removes the virtual address's entry in the page directory / page table -void vmm_unmap1(dword virt) -{ - dword *pteptr = (dword *)(0xFFC00000 | ((virt & 0xFFC00000) >> 10) | ((virt & 0x003FF000) >> 10)); - *pteptr = 0; - invlpg(virt); -} - - -// This function removes multiple pages' entries -void vmm_unmapn(dword virt, dword n) -{ - for (; n > 0; n--) - { - vmm_unmap1(virt); - virt += 4096; - } -} - - -// Virtual Memory allocator function -void *malloc(dword bytes) -{ - if (bytes % VMM_MALLOC_GRANULARITY) - bytes = bytes + VMM_MALLOC_GRANULARITY - (bytes % VMM_MALLOC_GRANULARITY); - void *attempt = vmm_getFreeChunk(bytes); - if (attempt) - return attempt; - if(vmm_moreCore(bytes)) - return 0; //we could not get any more heap memory - return vmm_getFreeChunk(bytes); -} - - -// This function returns a pointer if a free chunk of memory exists -void *vmm_getFreeChunk(dword bytes) -{ - HeapEntry *he = firstHeapEntry; - for (;;) - { - if (he->attributes == VMM_HE_FREE) - { - if (he->size > bytes) - { - HeapEntry *nhe = vmm_nextHeapEntry(); - nhe->base = he->base; - nhe->size = bytes; - nhe->attributes = VMM_HE_USED; - he->base += bytes; - he->size -= bytes; - return (void *)(nhe->base); - } - if (he->size == bytes) - { - he->attributes = VMM_HE_USED; - return (void *)(he->base); - } - } - he = (HeapEntry *)he->link; - if (!he) - break; - } - return 0; -} - - -// This function coalesces any two adjacent heap entries into one entry -void vmm_coalesceHeapEntry(HeapEntry *he) -{ - if (!(he->attributes == VMM_HE_FREE || he->attributes == VMM_HE_HOLE)) - return; - if (he->size == 0) - { - he->attributes = VMM_HE_UNUSED; - return; - } - HeapEntry *hec = firstHeapEntry; - for (;;) - { - if (hec->attributes == he->attributes) - { - if ((hec->base + hec->size) == he->base) //hec ends where he begins - { - he->base = hec->base; - he->size += hec->size; - hec->attributes = VMM_HE_UNUSED; - } - if ((he->base + he->size) == hec->base) //he ends where hec begins - { - he->size += hec->size; - hec->attributes = VMM_HE_UNUSED; - } - } - hec = (HeapEntry *)hec->link; - if (!hec) - break; - } -} - - -// This function retrieves more physical memory for the heap -int vmm_moreCore(dword bytes) -{ - dword pages = (bytes >> 12) + 1; - bytes = pages << 12; - HeapEntry *he = vmm_getFirstHoleHeapEntry(bytes); - dword virt = he->base; - for (; pages > 0; pages--) - { - dword phys = (dword)mm_palloc(); - if (!phys) - return 1; - vmm_map1(virt, phys); - virt += 4096; - } - if (he->size == bytes) - { - he->attributes = VMM_HE_FREE; - vmm_coalesceHeapEntry(he); - } - else - { - HeapEntry *nhe = vmm_nextHeapEntry(); - nhe->base = he->base; - nhe->size = bytes; - nhe->attributes = VMM_HE_FREE; - he->base += bytes; - he->size -= bytes; - vmm_coalesceHeapEntry(nhe); - } - return 0; -} - - -// This function returns the next available heap entry, creates more entries if we are running low -HeapEntry *vmm_nextHeapEntry() -{ - if (vmm_heapEntriesLeft() < 10) - vmm_addHeapEntryBlock(); - return vmm_getFirstUnusedHeapEntry(); -} - - -// This function creates a new block (page) of heap entries (256) -void vmm_addHeapEntryBlock() -{ - HeapEntry *he = vmm_getFirstHoleHeapEntry(4096); - HeapEntry *newBlock = vmm_getFirstUnusedHeapEntry(); - dword heb = (dword)mm_palloc(); - vmm_map1(he->base, heb); - vmm_heb_init((HeapEntryBlock *)he->base); - HeapEntry *lhe = vmm_getLastHeapEntry(); - if (he->size == 4096) - { - he->attributes = VMM_HE_HEB; - lhe->link = (dword)he->base; - } - else - { - newBlock->base = he->base; - newBlock->size = 4096; - newBlock->attributes = VMM_HE_HEB; - he->base += 4096; - he->size -= 4096; - lhe->link = (dword)newBlock->base; - } - return; -} - - -// This function returns the last heap entry in the linked list, useful for setting -// its link field to point to the first entry of a newly allocated list -HeapEntry *vmm_getLastHeapEntry() -{ - HeapEntry *he = firstHeapEntry; - for (;;) - { - if (he->link == 0) - return he; - he = (HeapEntry *)he->link; - } -} - - -// This function returns the first heap entry corresponding to a memory "hole" -HeapEntry *vmm_getFirstHoleHeapEntry(dword minBytes) -{ - HeapEntry *he = firstHeapEntry; - for (;;) - { - if ((he->attributes == VMM_HE_HOLE) && (he->size >= minBytes)) - return he; - he = (HeapEntry *)he->link; - if (!he) - break; - } - return 0; -} - - -// This function returns the first heap entry that is not being used -HeapEntry *vmm_getFirstUnusedHeapEntry() -{ - HeapEntry *he = firstHeapEntry; - for (;;) - { - if (he->attributes == VMM_HE_UNUSED) - return he; - he = (HeapEntry *)he->link; - if (!he) - break; - } - return 0; -} - - -// This function returns the number of heap entries available for use -dword vmm_heapEntriesLeft() -{ - HeapEntry *he = firstHeapEntry; - dword entries = 0; - for (;;) - { - if (he->attributes == VMM_HE_UNUSED) - entries++; - he = (HeapEntry *)he->link; - if (!he) - break; - } - return entries; -} - - -// This function "frees" an area of memory previously allocated with malloc() -int free(void *ptr) -{ - HeapEntry *he = vmm_getHeapEntryByBase((dword)ptr); - if (!he) - return 1; //a heap entry starting at the given address was not found - he->attributes = VMM_HE_FREE; - vmm_coalesceHeapEntry(he); - return 0; -} - - -// This function scans the heap entry linked list for an entry that begins at the given address -HeapEntry *vmm_getHeapEntryByBase(dword base) -{ - HeapEntry *he = firstHeapEntry; - for (;;) - { - if (he->base == base) - return he; - he = (HeapEntry *)he->link; - if (!he) - break; - } - return 0; -} - - - - - - - +// vmm.c +// Author: Josh Holtrop +// Date: 09/30/03 +// Rewritten from scratch: 12/23/03 +// Modified: 03/02/04 + +#include "hos_defines.h" +#include "vmm.h" + +HeapEntry *firstHeapEntry = (HeapEntry *)0xD0000000; //this is where heap memory starts + +// This is the initialization procedure for the Virtual Memory Manager +// It sets up the final page directory/page table setup and maps video memory, if present +void vmm_init() +{ + unsigned int *pageTables = (unsigned int *)0xC0104000; //this is the location of the page directory + pageTables[0x3FF] = 0x104000|0x03; //the last page directory entry points to the page directory itself + pageTables[0] = 0; + invlpg(0); + if (videoMode) //we are in a graphical mode + { + unsigned int vidPages = video_mode.XResolution * video_mode.YResolution * (video_mode.BitsPerPixel >> 3); + if (vidPages % 4096) + vidPages = (vidPages >> 12) + 1; + else + vidPages = (vidPages >> 12); + vmm_mapn(0xF0000000, video_mode.PhysBasePtr, vidPages); + } + unsigned int firstHeapEntryBlock = (unsigned int)mm_palloc(); + vmm_map1((unsigned int)firstHeapEntry, firstHeapEntryBlock); + HeapEntryBlock *heb = (HeapEntryBlock *)firstHeapEntry; + vmm_heb_init(heb); + heb->entry[0].base = (unsigned int)firstHeapEntry; //start of kernel's heap memory + heb->entry[0].size = 4096; //the first HeapEntryBlock is 1 page long + heb->entry[0].attributes = VMM_HE_HEB; //this is a HeapEntryBlock + heb->entry[1].base = (unsigned int)firstHeapEntry+4096; //this is the start of the rest of the kernel's heap memory + heb->entry[1].size = 0x10000000-4096; //the rest of the kernel's heap memory: 256mb - 4kb + heb->entry[1].attributes = VMM_HE_HOLE; //this is a hold - an unmapped section of heap memory +} + + +// This function initialzes a Heap Entry Block to unused entries linked together +void vmm_heb_init(HeapEntryBlock *heb) +{ + int a; + for (a = 0; a < 256; a++) + { + heb->entry[a].base = 0; + heb->entry[a].size = 0; + heb->entry[a].attributes = VMM_HE_UNUSED; + heb->entry[a].link = (unsigned int)&(heb->entry[a+1]); + } + heb->entry[255].link = 0; +} + + +// This function maps a virtual address to a physical address using the page directory / page table +void vmm_map1(unsigned int virt, unsigned int physical) +{ + unsigned int pde = virt >> 22; + unsigned int pte = (virt & 0x003FF000) >> 12; + unsigned int *pageTables = (unsigned int *)0xC0104000; //this is the location of the page directory + if (!(pageTables[pde] & 0x01)) //the page directory entry does not exist, we must allocate a page for it + { + unsigned int *newpagetable = mm_palloc(); + pageTables[pde] = ((unsigned int)newpagetable) | 0x03; + invlpg(virt); + unsigned int *newpteptr = (unsigned int *)(0xFFC00000 | (pde << 12)); //points to first unsigned int of newly allocated page table + int a; + for (a = 0; a < 1024; a++) + { + newpteptr[a] = 0; + } + } + unsigned int *pteptr = (unsigned int *)(0xFFC00000 | (pde << 12) | (pte << 2)); + *pteptr = physical | 0x03; + invlpg(virt); +} + + +// This function maps a variable number of pages in a row +void vmm_mapn(unsigned int virt, unsigned int physical, unsigned int n) +{ + for (; n > 0; n--) + { + vmm_map1(virt, physical); + virt += 4096; + physical += 4096; + } +} + + +// This function removes the virtual address's entry in the page directory / page table +void vmm_unmap1(unsigned int virt) +{ + unsigned int *pteptr = (unsigned int *)(0xFFC00000 | ((virt & 0xFFC00000) >> 10) | ((virt & 0x003FF000) >> 10)); + *pteptr = 0; + invlpg(virt); +} + + +// This function removes multiple pages' entries +void vmm_unmapn(unsigned int virt, unsigned int n) +{ + for (; n > 0; n--) + { + vmm_unmap1(virt); + virt += 4096; + } +} + + +// Virtual Memory allocator function +void *malloc(unsigned int bytes) +{ + if (bytes % VMM_MALLOC_GRANULARITY) + bytes = bytes + VMM_MALLOC_GRANULARITY - (bytes % VMM_MALLOC_GRANULARITY); + void *attempt = vmm_getFreeChunk(bytes); + if (attempt) + return attempt; + if(vmm_moreCore(bytes)) + return 0; //we could not get any more heap memory + return vmm_getFreeChunk(bytes); +} + + +// This function returns a pointer if a free chunk of memory exists +void *vmm_getFreeChunk(unsigned int bytes) +{ + HeapEntry *he = firstHeapEntry; + for (;;) + { + if (he->attributes == VMM_HE_FREE) + { + if (he->size > bytes) + { + HeapEntry *nhe = vmm_nextHeapEntry(); + nhe->base = he->base; + nhe->size = bytes; + nhe->attributes = VMM_HE_USED; + he->base += bytes; + he->size -= bytes; + return (void *)(nhe->base); + } + if (he->size == bytes) + { + he->attributes = VMM_HE_USED; + return (void *)(he->base); + } + } + he = (HeapEntry *)he->link; + if (!he) + break; + } + return 0; +} + + +// This function coalesces any two adjacent heap entries into one entry +void vmm_coalesceHeapEntry(HeapEntry *he) +{ + if (!(he->attributes == VMM_HE_FREE || he->attributes == VMM_HE_HOLE)) + return; + if (he->size == 0) + { + he->attributes = VMM_HE_UNUSED; + return; + } + HeapEntry *hec = firstHeapEntry; + for (;;) + { + if (hec->attributes == he->attributes) + { + if ((hec->base + hec->size) == he->base) //hec ends where he begins + { + he->base = hec->base; + he->size += hec->size; + hec->attributes = VMM_HE_UNUSED; + } + if ((he->base + he->size) == hec->base) //he ends where hec begins + { + he->size += hec->size; + hec->attributes = VMM_HE_UNUSED; + } + } + hec = (HeapEntry *)hec->link; + if (!hec) + break; + } +} + + +// This function retrieves more physical memory for the heap +int vmm_moreCore(unsigned int bytes) +{ + unsigned int pages = (bytes >> 12) + 1; + bytes = pages << 12; + HeapEntry *he = vmm_getFirstHoleHeapEntry(bytes); + unsigned int virt = he->base; + for (; pages > 0; pages--) + { + unsigned int phys = (unsigned int)mm_palloc(); + if (!phys) + return 1; + vmm_map1(virt, phys); + virt += 4096; + } + if (he->size == bytes) + { + he->attributes = VMM_HE_FREE; + vmm_coalesceHeapEntry(he); + } + else + { + HeapEntry *nhe = vmm_nextHeapEntry(); + nhe->base = he->base; + nhe->size = bytes; + nhe->attributes = VMM_HE_FREE; + he->base += bytes; + he->size -= bytes; + vmm_coalesceHeapEntry(nhe); + } + return 0; +} + + +// This function returns the next available heap entry, creates more entries if we are running low +HeapEntry *vmm_nextHeapEntry() +{ + if (vmm_heapEntriesLeft() < 10) + vmm_addHeapEntryBlock(); + return vmm_getFirstUnusedHeapEntry(); +} + + +// This function creates a new block (page) of heap entries (256) +void vmm_addHeapEntryBlock() +{ + HeapEntry *he = vmm_getFirstHoleHeapEntry(4096); + HeapEntry *newBlock = vmm_getFirstUnusedHeapEntry(); + unsigned int heb = (unsigned int)mm_palloc(); + vmm_map1(he->base, heb); + vmm_heb_init((HeapEntryBlock *)he->base); + HeapEntry *lhe = vmm_getLastHeapEntry(); + if (he->size == 4096) + { + he->attributes = VMM_HE_HEB; + lhe->link = (unsigned int)he->base; + } + else + { + newBlock->base = he->base; + newBlock->size = 4096; + newBlock->attributes = VMM_HE_HEB; + he->base += 4096; + he->size -= 4096; + lhe->link = (unsigned int)newBlock->base; + } + return; +} + + +// This function returns the last heap entry in the linked list, useful for setting +// its link field to point to the first entry of a newly allocated list +HeapEntry *vmm_getLastHeapEntry() +{ + HeapEntry *he = firstHeapEntry; + for (;;) + { + if (he->link == 0) + return he; + he = (HeapEntry *)he->link; + } +} + + +// This function returns the first heap entry corresponding to a memory "hole" +HeapEntry *vmm_getFirstHoleHeapEntry(unsigned int minBytes) +{ + HeapEntry *he = firstHeapEntry; + for (;;) + { + if ((he->attributes == VMM_HE_HOLE) && (he->size >= minBytes)) + return he; + he = (HeapEntry *)he->link; + if (!he) + break; + } + return 0; +} + + +// This function returns the first heap entry that is not being used +HeapEntry *vmm_getFirstUnusedHeapEntry() +{ + HeapEntry *he = firstHeapEntry; + for (;;) + { + if (he->attributes == VMM_HE_UNUSED) + return he; + he = (HeapEntry *)he->link; + if (!he) + break; + } + return 0; +} + + +// This function returns the number of heap entries available for use +unsigned int vmm_heapEntriesLeft() +{ + HeapEntry *he = firstHeapEntry; + unsigned int entries = 0; + for (;;) + { + if (he->attributes == VMM_HE_UNUSED) + entries++; + he = (HeapEntry *)he->link; + if (!he) + break; + } + return entries; +} + + +// This function "frees" an area of memory previously allocated with malloc() +int free(void *ptr) +{ + HeapEntry *he = vmm_getHeapEntryByBase((unsigned int)ptr); + if (!he) + return 1; //a heap entry starting at the given address was not found + he->attributes = VMM_HE_FREE; + vmm_coalesceHeapEntry(he); + return 0; +} + + +// This function scans the heap entry linked list for an entry that begins at the given address +HeapEntry *vmm_getHeapEntryByBase(unsigned int base) +{ + HeapEntry *he = firstHeapEntry; + for (;;) + { + if (he->base == base) + return he; + he = (HeapEntry *)he->link; + if (!he) + break; + } + return 0; +} + + + + + + + diff --git a/vmm.h b/src/kernel/mm/vmm.h similarity index 52% rename from vmm.h rename to src/kernel/mm/vmm.h index 82d349f..59c0bab 100644 --- a/vmm.h +++ b/src/kernel/mm/vmm.h @@ -1,55 +1,54 @@ -// vmm.h -// Author: Josh Holtrop -// Date: 09/30/03 -// Rewritten from scratch: 12/23/03 -// Modified: 12/30/03 - - -#define VMM_HE_UNUSED 0 //available entry -#define VMM_HE_FREE 1 //free section of memory -#define VMM_HE_USED 2 //used section of memory -#define VMM_HE_HOLE 3 //a "hole" (unmapped) section of virtual memory -#define VMM_HE_HEB 4 //HeapEntryBlock - -#define VMM_MALLOC_GRANULARITY 4 //granularity for all memory requests - -typedef struct { - dword base; //virtual base address - dword size; //size in bytes - dword attributes; //free/used/hole - dword link; //link to next HeapEntry -} __attribute__((packed)) HeapEntry; - - -typedef struct { - HeapEntry entry[256]; //256 HeapEntry objects = 4kb (1 page) -} __attribute__((packed)) HeapEntryBlock; - - -void vmm_init(); -void *malloc(dword bytes); -int free(void *ptr); -void vmm_map1(dword virt, dword physical); -void vmm_mapn(dword virt, dword physical, dword n); -void vmm_unmap1(dword virt); -void vmm_unmapn(dword virt, dword n); -void vmm_heb_init(HeapEntryBlock *heb); -void *vmm_getFreeChunk(dword bytes); -HeapEntry *vmm_nextHeapEntry(); -dword vmm_heapEntriesLeft(); -HeapEntry *vmm_getLastHeapEntry(); -HeapEntry *vmm_getFirstUnusedHeapEntry(); -HeapEntry *vmm_getFirstHoleHeapEntry(dword minBytes); -void vmm_addHeapEntryBlock(); -int vmm_moreCore(dword bytes); -void vmm_coalesceHeapEntry(HeapEntry *he); -HeapEntry *vmm_getHeapEntryByBase(dword base); - - -HeapEntry *firstHeapEntry = (HeapEntry *)0xD0000000; //this is where heap memory starts - - - - - - +// vmm.h +// Author: Josh Holtrop +// Date: 09/30/03 +// Rewritten from scratch: 12/23/03 +// Modified: 03/02/04 + +#include "hos_defines.h" + +#ifndef __HOS_VMM__ +#define __HOS_VMM__ __HOS_VMM__ + +#define VMM_HE_UNUSED 0 //available entry +#define VMM_HE_FREE 1 //free section of memory +#define VMM_HE_USED 2 //used section of memory +#define VMM_HE_HOLE 3 //a "hole" (unmapped) section of virtual memory +#define VMM_HE_HEB 4 //HeapEntryBlock + +#define VMM_MALLOC_GRANULARITY 4 //granularity for all memory requests + +typedef struct { + unsigned int base; //virtual base address + unsigned int size; //size in bytes + unsigned int attributes; //free/used/hole + unsigned int link; //link to next HeapEntry +} __attribute__((packed)) HeapEntry; + + +typedef struct { + HeapEntry entry[256]; //256 HeapEntry objects = 4kb (1 page) +} __attribute__((packed)) HeapEntryBlock; + + +void vmm_init(); +void *malloc(unsigned int bytes); +int free(void *ptr); +void vmm_map1(unsigned int virt, unsigned int physical); +void vmm_mapn(unsigned int virt, unsigned int physical, unsigned int n); +void vmm_unmap1(unsigned int virt); +void vmm_unmapn(unsigned int virt, unsigned int n); +void vmm_heb_init(HeapEntryBlock *heb); +void *vmm_getFreeChunk(unsigned int bytes); +HeapEntry *vmm_nextHeapEntry(); +unsigned int vmm_heapEntriesLeft(); +HeapEntry *vmm_getLastHeapEntry(); +HeapEntry *vmm_getFirstUnusedHeapEntry(); +HeapEntry *vmm_getFirstHoleHeapEntry(unsigned int minBytes); +void vmm_addHeapEntryBlock(); +int vmm_moreCore(unsigned int bytes); +void vmm_coalesceHeapEntry(HeapEntry *he); +HeapEntry *vmm_getHeapEntryByBase(unsigned int base); + +#endif + + diff --git a/src/kernel/string/string.c b/src/kernel/string/string.c new file mode 100644 index 0000000..197e6c8 --- /dev/null +++ b/src/kernel/string/string.c @@ -0,0 +1,88 @@ +// string.c +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements string functions + +#include "string.h" + +char *strcat(char *dest, char *src) +{ + strcpy(dest+strlen(dest), src); +} + + +//Splits a string into multiple strings by turning all characters +// equal to delim into null values (string termination character) +//Returns the number of strings after the split, 1 if no delim chars +int string_split(char *str, char delim) +{ + if (strlen(str) < 1) + return 0; //empty string + int count = 1; + for (; *str; str++) + { + if (*str == delim) + { + count++; + *str = 0; + } + } + return count; +} + + +//Advances a char pointer to the byte after the current string's +// null-terminating character +//Useful after calling string_split() +//Returns a pointer to the following string +char *string_advance(char *str) +{ + for (; *str; str++); + return str+1; +} + + +void rtrim(char *str) +{ + str += strlen(str); //now points to the null character at the end of the string + str--; + for (;;) + { + if ((*str == ' ') || (*str == '\t') || (*str == '\n')) + *str-- = 0; + else + break; + } +} + + +char *ucase(char *str) +{ + char *ret = str; + for (;;) + { + if (*str == 0) + break; + if ((*str >= 'a') && (*str <= 'z')) + *str = (*str) - 32; + str++; + } + return ret; +} + + +char *lcase(char *str) +{ + char *ret = str; + for (;;) + { + if (*str == 0) + break; + if ((*str >= 'A') && (*str <= 'Z')) + *str = (*str) + 32; + str++; + } + return ret; +} + + diff --git a/src/kernel/string/string.h b/src/kernel/string/string.h new file mode 100644 index 0000000..16a53dd --- /dev/null +++ b/src/kernel/string/string.h @@ -0,0 +1,18 @@ +// strings.h +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements string functions + +#ifndef __HOS_STRING__ +#define __HOS_STRING__ __HOS_STRING__ + +char *strcat(char *dest, char *src); +int string_split(char *str, char delim); +char *string_advance(char *str); +void rtrim(char *str); +char *ucase(char *str); +char *lcase(char *str); + +#endif + + diff --git a/src/kernel/sys/cmos.c b/src/kernel/sys/cmos.c new file mode 100644 index 0000000..f27919d --- /dev/null +++ b/src/kernel/sys/cmos.c @@ -0,0 +1,41 @@ +// cmos.c +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements various CMOS function calls + +#include "hos_defines.h" +#include "cmos.h" + +//Returns the cmos type of floppy disk drive 0 (0 = not present) +unsigned char cmos_getfd0() +{ + outportb(0x70, 0x10); + return (inportb(0x71) >> 4); +} + + +//Returns the cmos type of floppy disk drive 1 (0 = not present) +unsigned char cmos_getfd1() +{ + outportb(0x70, 0x10); + return (inportb(0x71) & 0x0F); +} + + +//Returns the cmos type of hard disk drive 0 (0 = not present) +unsigned char cmos_gethd0() +{ + outportb(0x70, 0x12); + return (inportb(0x71) >> 4); +} + + +//Returns the cmos type of hard disk drive 1 (0 = not present) +unsigned char cmos_gethd1() +{ + outportb(0x70, 0x12); + return (inportb(0x71) & 0x0F); +} + + + diff --git a/src/kernel/sys/cmos.h b/src/kernel/sys/cmos.h new file mode 100644 index 0000000..cf5ce52 --- /dev/null +++ b/src/kernel/sys/cmos.h @@ -0,0 +1,18 @@ +// cmos.h +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements various CMOS function calls + +#include "hos_defines.h" + +#ifndef __HOS_CMOS__ +#define __HOS_CMOS__ __HOS_CMOS__ + +unsigned char cmos_getfd0(); +unsigned char cmos_getfd1(); +unsigned char cmos_gethd0(); +unsigned char cmos_gethd1(); + +#endif + + diff --git a/src/kernel/sys/io.c b/src/kernel/sys/io.c new file mode 100644 index 0000000..87a8b16 --- /dev/null +++ b/src/kernel/sys/io.c @@ -0,0 +1,8 @@ +// io.c +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements basic port input/output functions + +#include "io.h" + + diff --git a/src/kernel/sys/io.h b/src/kernel/sys/io.h new file mode 100644 index 0000000..807e22d --- /dev/null +++ b/src/kernel/sys/io.h @@ -0,0 +1,40 @@ +// io.h +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements basic port input/output functions + +#include "hos_defines.h" + +#ifndef __HOS_IO__ +#define __HOS_IO__ __HOS_IO__ + +inline void outportb(unsigned int port, unsigned char value); +inline void outportw(unsigned int port, unsigned int value); +inline unsigned char inportb(unsigned short port); + +//Writes a byte out to a port +inline void outportb(unsigned int port, unsigned char value) // Output a byte to a port +{ + asm volatile ("outb %%al,%%dx"::"d" (port), "a" (value)); +} + +//Writes a word out to a port +inline void outportw(unsigned int port, unsigned int value) // Output a word to a port +{ + asm volatile ("outw %%ax,%%dx"::"d" (port), "a" (value)); +} + +//Reads a byte from a port +inline unsigned char inportb(unsigned short port) +{ + unsigned char ret_val; + + asm volatile("inb %w1,%b0" + : "=a"(ret_val) + : "d"(port)); + return ret_val; +} + +#endif + + diff --git a/src/kernel/sys/pic.c b/src/kernel/sys/pic.c new file mode 100644 index 0000000..9380686 --- /dev/null +++ b/src/kernel/sys/pic.c @@ -0,0 +1,29 @@ +// pic.c +// Author: Josh Holtrop +// Created: 02/26/04 + +#include "hos_defines.h" +#include "pic.h" + +//Re-maps the Programmable Interrupr Controllers so IRQ0->pic1 base address, IRG8->pic2 base address +void pic_remap(int pic1, int pic2) +{ + byte a1, a2; + + a1 = inportb(PIC1_DATA); //0x21 + a2 = inportb(PIC2_DATA); //0xA1 + + outportb(PIC1_COMMAND, ICW1_INIT+ICW1_ICW4); //0x20, 0x10+0x01 00010001b + outportb(PIC2_COMMAND, ICW1_INIT+ICW1_ICW4); //0xA0, 0x10+0x01 00010001b + outportb(PIC1_DATA, pic1); //0x21, pic1 + outportb(PIC2_DATA, pic2); //0xA1, pic2 + outportb(PIC1_DATA, 4); //0x21, 0x04 00000100b + outportb(PIC2_DATA, 2); //0xA1, 0x02 00000010b + outportb(PIC1_DATA, ICW4_8086); //0x21, 0x01 00000001b + outportb(PIC2_DATA, ICW4_8086); //0xA1, 0x01 00000001b + + outportb(PIC1_DATA, a1); //0x21 + outportb(PIC2_DATA, a2); //0xA1 +} + + diff --git a/src/kernel/sys/pic.h b/src/kernel/sys/pic.h new file mode 100644 index 0000000..941451a --- /dev/null +++ b/src/kernel/sys/pic.h @@ -0,0 +1,64 @@ +// pic.h +// Author: Josh Holtrop +// Created: 02/26/04 + +#include "hos_defines.h" + +#ifndef __HOS_PIC__ +#define __HOS_PIC__ __HOS_PIC__ + +#define PIC1 0x20 +#define PIC2 0xA0 +#define PIC1_COMMAND PIC1 +#define PIC1_DATA (PIC1+1) +#define PIC2_COMMAND PIC2 +#define PIC2_DATA (PIC2+1) +#define PIC_EOI 0x20 + +#define ICW1_ICW4 0x01 /* ICW4 (not) needed */ +#define ICW1_SINGLE 0x02 /* Single (cascade) mode */ +#define ICW1_INTERVAL4 0x04 /* Call address interval 4 (8) */ +#define ICW1_LEVEL 0x08 /* Level triggered (edge) mode */ +#define ICW1_INIT 0x10 /* Initialization - required! */ + +#define ICW4_8086 0x01 /* 8086/88 (MCS-80/85) mode */ +#define ICW4_AUTO 0x02 /* Auto (normal) EOI */ +#define ICW4_BUF_SLAVE 0x08 /* Buffered mode/slave */ +#define ICW4_BUF_MASTER 0x0C /* Buffered mode/master */ +#define ICW4_SFNM 0x10 /* Special fully nested (not) */ + +void pic_remap(int pic1, int pic2); +inline void pic_mask1(byte mask); +inline void pic_mask2(byte mask); +inline void pic_eoi(); +inline void pic_eoi2(); + +//Masks interrupts on first Programmable Interrupt Controller +inline void pic_mask1(byte mask) +{ + outportb(PIC1_DATA, mask); //0x21, maskfield *OCW1* +} + +//Masks interrupts on second Programmable Interrupt Controller +inline void pic_mask2(byte mask) +{ + outportb(PIC2_DATA, mask); //0xA1, maskfield *OCW1* +} + + +//Signals an End Of Interrupt signal to the first PIC +inline void pic_eoi() +{ + outportb(0x20, 0x20); +} + +//Signals an End Of Interrupt signal to both the second and first PIC unit +inline void pic_eoi2() +{ + outportb(0xA0, 0x20); + outportb(0x20, 0x20); +} + +#endif + + diff --git a/src/kernel/sys/rtc.c b/src/kernel/sys/rtc.c new file mode 100644 index 0000000..c97c012 --- /dev/null +++ b/src/kernel/sys/rtc.c @@ -0,0 +1,82 @@ +// rtc.c +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements Real-Time Clock function calls +// These functions are for reading and writing various values stored on the CMOS Real Time Clock +// Parameters / return values are in BCD format + +#include "hos_defines.h" +#include "rtc.h" + +unsigned char rtc_readDay() +{ + outportb(0x70, 7); + return inportb(0x71); +} + +unsigned char rtc_readMonth() +{ + outportb(0x70, 8); + return inportb(0x71); +} + +unsigned char rtc_readYear() +{ + outportb(0x70, 9); + return inportb(0x71); +} + +unsigned char rtc_readSecond() +{ + outportb(0x70, 0); + return inportb(0x71); +} + +unsigned char rtc_readMinute() +{ + outportb(0x70, 2); + return inportb(0x71); +} + +unsigned char rtc_readHour() +{ + outportb(0x70, 4); + return inportb(0x71); +} + +void rtc_setDay(unsigned char day) +{ + outportb(0x70, 7); + outportb(0x71, day); +} + +void rtc_setMonth(unsigned char month) +{ + outportb(0x70, 8); + outportb(0x71, month); +} + +void rtc_setYear(unsigned char year) +{ + outportb(0x70, 9); + outportb(0x71, year); +} + +void rtc_setSecond(unsigned char second) +{ + outportb(0x70, 0); + outportb(0x71, second); +} + +void rtc_setMinute(unsigned char minute) +{ + outportb(0x70, 2); + outportb(0x71, minute); +} + +void rtc_setHour(unsigned char hour) +{ + outportb(0x70, 4); + outportb(0x71, hour); +} + diff --git a/src/kernel/sys/rtc.h b/src/kernel/sys/rtc.h new file mode 100644 index 0000000..cc21751 --- /dev/null +++ b/src/kernel/sys/rtc.h @@ -0,0 +1,28 @@ +// rtc.h +// Author: Josh Holtrop +// Created: 02/26/04 +// Implements Real-Time Clock function calls +// These functions are for reading and writing various values stored on the CMOS Real Time Clock +// Parameters / return values are in BCD format + +#include "hos_defines.h" + +#ifndef __HOS_RTC__ +#define __HOS_RTC__ __HOS_RTC__ + +unsigned char rtc_readDay(); +unsigned char rtc_readMonth(); +unsigned char rtc_readYear(); +unsigned char rtc_readSecond(); +unsigned char rtc_readMinute(); +unsigned char rtc_readHour(); +void rtc_setDay(unsigned char dat); +void rtc_setMonth(unsigned char month); +void rtc_setYear(unsigned char year); +void rtc_setSecond(unsigned char second); +void rtc_setMinute(unsigned char minute); +void rtc_setHour(unsigned char hour); + +#endif + + diff --git a/src/kernel/video/stdfont.c b/src/kernel/video/stdfont.c new file mode 100644 index 0000000..0c40a3b --- /dev/null +++ b/src/kernel/video/stdfont.c @@ -0,0 +1,545 @@ +// stdfont.c +// Author: Josh Holtrop +// Created: 02/26/04 + +#include "stdfont.h" + +const unsigned char stdfont8x5[] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x80, 0xC0, 0xE0, 0xF0, 0xE0, 0xC0, 0x80, + 0x00, 0x08, 0x18, 0x38, 0x78, 0x38, 0x18, 0x08, + 0x00, 0x20, 0x70, 0xA8, 0x20, 0xA8, 0x70, 0x20, + 0x00, 0xA0, 0xA0, 0xA0, 0xA0, 0x00, 0xA0, 0xA0, + 0x00, 0x78, 0xA8, 0xA8, 0x78, 0x28, 0x28, 0x68, + 0x00, 0x78, 0x80, 0x70, 0x88, 0x70, 0x08, 0xF0, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, 0xF8, + 0x00, 0x20, 0x70, 0xA8, 0x20, 0xA8, 0x70, 0xF8, + 0x00, 0x20, 0x70, 0xA8, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x20, 0x20, 0x20, 0x20, 0xA8, 0x70, 0x20, + 0x00, 0x00, 0x20, 0x10, 0xF8, 0x10, 0x20, 0x00, + 0x00, 0x00, 0x20, 0x40, 0xF8, 0x40, 0x20, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, + 0x00, 0x60, 0x90, 0x60, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x20, 0x70, 0xF8, 0xF8, 0x00, 0x00, + 0x00, 0x00, 0xF8, 0xF8, 0x70, 0x20, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x20, 0x20, 0x20, 0x20, 0x00, 0x20, 0x20, + 0x00, 0x50, 0x50, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x50, 0xF8, 0x50, 0x50, 0x50, 0xF8, 0x50, + 0x00, 0x20, 0x78, 0xA0, 0x70, 0x28, 0xF0, 0x20, + 0x00, 0x00, 0x08, 0x90, 0x20, 0x48, 0x80, 0x00, + 0x00, 0x20, 0x50, 0x50, 0x20, 0x58, 0x90, 0x68, + 0x00, 0x40, 0x40, 0x80, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x20, 0x40, 0x40, 0x40, 0x40, 0x40, 0x20, + 0x00, 0x40, 0x20, 0x20, 0x20, 0x20, 0x20, 0x40, + 0x00, 0x00, 0xA8, 0x70, 0xF8, 0x70, 0xA8, 0x00, + 0x00, 0x00, 0x20, 0x20, 0xF8, 0x20, 0x20, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x40, + 0x00, 0x00, 0x00, 0x00, 0xF0, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x60, + 0x00, 0x00, 0x08, 0x10, 0x20, 0x40, 0x80, 0x00, + 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, + 0x00, 0x20, 0x60, 0xA0, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x70, 0x88, 0x08, 0x10, 0x20, 0x40, 0xF8, + 0x00, 0x70, 0x88, 0x08, 0x10, 0x08, 0x88, 0x70, + 0x00, 0x30, 0x50, 0x90, 0x90, 0xF8, 0x10, 0x10, + 0x00, 0xF8, 0x80, 0x80, 0xF8, 0x08, 0x88, 0x70, + 0x00, 0x38, 0x40, 0x80, 0xF0, 0x88, 0x88, 0x70, + 0x00, 0xF8, 0x08, 0x10, 0x20, 0x40, 0x40, 0x40, + 0x00, 0x70, 0x88, 0x88, 0x70, 0x88, 0x88, 0x70, + 0x00, 0x70, 0x88, 0x88, 0x78, 0x08, 0x10, 0x60, + 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x60, 0x00, + 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x60, 0x40, + 0x00, 0x10, 0x20, 0x40, 0x80, 0x40, 0x20, 0x10, + 0x00, 0x00, 0x00, 0xF0, 0x00, 0xF0, 0x00, 0x00, + 0x00, 0x80, 0x40, 0x20, 0x10, 0x20, 0x40, 0x80, + 0x00, 0x70, 0x88, 0x08, 0x10, 0x20, 0x00, 0x20, + 0x00, 0x70, 0x88, 0x88, 0xB8, 0xB0, 0x80, 0x78, + 0x00, 0x70, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, + 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x88, 0x88, 0xF0, + 0x00, 0x70, 0x88, 0x80, 0x80, 0x80, 0x88, 0x70, + 0x00, 0xF0, 0x88, 0x88, 0x88, 0x88, 0x88, 0xF0, + 0x00, 0xF8, 0x80, 0x80, 0xF0, 0x80, 0x80, 0xF8, + 0x00, 0xF8, 0x80, 0x80, 0xF0, 0x80, 0x80, 0x80, + 0x00, 0x70, 0x88, 0x80, 0xB8, 0x88, 0x88, 0x70, + 0x00, 0x88, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, + 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x10, 0x10, 0x10, 0x10, 0x10, 0x90, 0x60, + 0x00, 0x88, 0x90, 0xA0, 0xC0, 0xA0, 0x90, 0x88, + 0x00, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0xF8, + 0x00, 0x88, 0xD8, 0xA8, 0x88, 0x88, 0x88, 0x88, + 0x00, 0x88, 0xC8, 0xE8, 0xB8, 0x98, 0x88, 0x88, + 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, + 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x80, 0x80, 0x80, + 0x00, 0x70, 0x88, 0x88, 0x88, 0xA8, 0x98, 0x70, + 0x00, 0xF0, 0x88, 0x88, 0xF0, 0xA0, 0x90, 0x88, + 0x00, 0x70, 0x88, 0x80, 0x70, 0x08, 0x88, 0x70, + 0x00, 0xF8, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, + 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0x50, 0x20, + 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0xA8, 0x50, + 0x00, 0x88, 0x50, 0x20, 0x20, 0x50, 0x88, 0x88, + 0x00, 0x88, 0x88, 0x50, 0x20, 0x20, 0x20, 0x20, + 0x00, 0xF8, 0x08, 0x10, 0x20, 0x40, 0x80, 0xF8, + 0x00, 0x70, 0x40, 0x40, 0x40, 0x40, 0x40, 0x70, + 0x00, 0x80, 0xC0, 0x60, 0x30, 0x18, 0x08, 0x00, + 0x00, 0xE0, 0x20, 0x20, 0x20, 0x20, 0x20, 0xE0, + 0x00, 0x20, 0x50, 0x88, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, + 0x00, 0x60, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x70, 0x08, 0x78, 0x88, 0x78, + 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0x88, 0xF0, + 0x00, 0x00, 0x00, 0x70, 0x88, 0x80, 0x88, 0x70, + 0x00, 0x08, 0x08, 0x78, 0x88, 0x88, 0x88, 0x78, + 0x00, 0x00, 0x00, 0x70, 0x88, 0xF8, 0x80, 0x78, + 0x00, 0x30, 0x40, 0x40, 0xE0, 0x40, 0x40, 0x40, + 0x00, 0x00, 0x00, 0x78, 0x88, 0x78, 0x08, 0x70, + 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0x88, 0x88, + 0x00, 0x20, 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x10, 0x00, 0x10, 0x10, 0x10, 0x90, 0x60, + 0x00, 0x80, 0x80, 0x90, 0xA0, 0xC0, 0xA0, 0x90, + 0x00, 0xC0, 0x40, 0x40, 0x40, 0x40, 0x40, 0xE0, + 0x00, 0x00, 0x00, 0xD0, 0xA8, 0xA8, 0xA8, 0xA8, + 0x00, 0x00, 0x00, 0xF0, 0x88, 0x88, 0x88, 0x88, + 0x00, 0x00, 0x00, 0x70, 0x88, 0x88, 0x88, 0x70, + 0x00, 0x00, 0x00, 0xF0, 0x88, 0xF0, 0x80, 0x80, + 0x00, 0x00, 0x00, 0x78, 0x88, 0x78, 0x08, 0x38, + 0x00, 0x00, 0x00, 0x70, 0x48, 0x40, 0x40, 0x40, + 0x00, 0x00, 0x00, 0x78, 0x80, 0x70, 0x08, 0xF0, + 0x00, 0x40, 0x40, 0xE0, 0x40, 0x40, 0x40, 0x20, + 0x00, 0x00, 0x00, 0x88, 0x88, 0x88, 0x88, 0x78, + 0x00, 0x00, 0x00, 0x88, 0x88, 0x88, 0x50, 0x20, + 0x00, 0x00, 0x00, 0x88, 0x88, 0x88, 0xA8, 0x50, + 0x00, 0x00, 0x00, 0x88, 0x50, 0x20, 0x50, 0x88, + 0x00, 0x00, 0x00, 0x88, 0x88, 0x78, 0x08, 0xF0, + 0x00, 0x00, 0x00, 0xF8, 0x10, 0x20, 0x40, 0xF8, + 0x00, 0x30, 0x40, 0x40, 0x80, 0x40, 0x40, 0x30, + 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0xC0, 0x20, 0x20, 0x10, 0x20, 0x20, 0xC0, + 0x00, 0x00, 0x68, 0x90, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x70, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, + 0x00, 0xF8, 0x88, 0x80, 0xF0, 0x88, 0x88, 0xF0, + 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x88, 0x88, 0xF0, + 0x00, 0xF8, 0x48, 0x40, 0x40, 0x40, 0x40, 0xE0, + 0x00, 0xF0, 0x50, 0x50, 0x50, 0x50, 0x78, 0x88, + 0x00, 0xF8, 0x80, 0x80, 0xF0, 0x80, 0x80, 0xF8, + 0x00, 0xA8, 0xA8, 0x70, 0x20, 0x70, 0xA8, 0xA8, + 0x00, 0x70, 0x88, 0x08, 0x30, 0x08, 0x88, 0x70, + 0x00, 0x88, 0x98, 0xA8, 0xA8, 0xA8, 0xC8, 0x88, + 0x00, 0xA8, 0xC8, 0x98, 0xA8, 0xA8, 0xC8, 0x88, + 0x00, 0x88, 0x90, 0xA0, 0xC0, 0xA0, 0x90, 0x88, + 0x00, 0xF8, 0x50, 0x50, 0x50, 0x50, 0x50, 0x90, + 0x00, 0x88, 0xD8, 0xA8, 0x88, 0x88, 0x88, 0x88, + 0x00, 0x88, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, + 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, + 0x00, 0xF8, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x80, 0x80, 0x80, + 0x00, 0x70, 0x88, 0x80, 0x80, 0x80, 0x88, 0x70, + 0x00, 0xF8, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x88, 0x88, 0x88, 0x50, 0x20, 0x40, 0x80, + 0x00, 0x70, 0x20, 0xF8, 0xA8, 0xF8, 0x20, 0x70, + 0x00, 0x88, 0x88, 0x50, 0x20, 0x50, 0x88, 0x88, + 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0xF8, 0x08, + 0x00, 0x88, 0x88, 0x88, 0xF8, 0x08, 0x08, 0x38, + 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, + 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, 0x08, + 0x00, 0xC0, 0x40, 0x40, 0x78, 0x48, 0x48, 0x78, + 0x00, 0x88, 0x88, 0xC8, 0xA8, 0xA8, 0xA8, 0xE8, + 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0x88, 0xF0, + 0x00, 0xF0, 0x88, 0x08, 0x78, 0x08, 0x88, 0xF0, + 0x00, 0x90, 0xA8, 0xA8, 0xE8, 0xA8, 0xA8, 0x90, + 0x00, 0x78, 0x88, 0x88, 0x78, 0x28, 0x48, 0x88, + 0x00, 0x00, 0x70, 0x08, 0x78, 0x88, 0x88, 0x78, + 0x00, 0x00, 0xF8, 0x80, 0xF0, 0x88, 0x88, 0xF0, + 0x00, 0x00, 0xF0, 0x88, 0xF0, 0x88, 0x88, 0xF0, + 0x00, 0x00, 0xF8, 0x48, 0x48, 0x40, 0x40, 0xE0, + 0x00, 0x00, 0x78, 0x50, 0x50, 0x50, 0x70, 0x88, + 0x00, 0x00, 0x70, 0x88, 0xF8, 0x80, 0x88, 0x70, + 0x00, 0x00, 0xA8, 0x70, 0x20, 0x70, 0xA8, 0xA8, + 0x00, 0x00, 0x00, 0xF0, 0x88, 0x30, 0x88, 0x70, + 0x00, 0x00, 0x88, 0x98, 0xA8, 0xC8, 0x88, 0x88, + 0x00, 0x50, 0x20, 0x88, 0x98, 0xA8, 0xC8, 0x88, + 0x00, 0x00, 0x88, 0x90, 0xA0, 0xE0, 0x90, 0x88, + 0x00, 0x00, 0xF8, 0x48, 0x48, 0x48, 0x48, 0xC8, + 0x00, 0x00, 0x88, 0xD8, 0xA8, 0x88, 0x88, 0x88, + 0x00, 0x00, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, + 0x00, 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x70, + 0x00, 0x00, 0xF8, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x70, 0x50, 0x70, 0x08, 0x78, 0x88, 0x78, + 0x00, 0x88, 0x00, 0x70, 0x08, 0x78, 0x88, 0x78, + 0x00, 0x88, 0x00, 0x70, 0x88, 0x88, 0x88, 0x70, + 0x00, 0x88, 0x00, 0x88, 0x88, 0x88, 0x88, 0x78, + 0x00, 0x90, 0x00, 0xF0, 0x80, 0xE0, 0x80, 0xF0, + 0x00, 0x00, 0x70, 0x48, 0x70, 0x48, 0x48, 0xF0, + 0x00, 0x88, 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x88, 0x00, 0x70, 0x88, 0xF8, 0x80, 0x78, + 0x00, 0x70, 0x50, 0x70, 0x88, 0xF8, 0x88, 0x88, + 0x00, 0x88, 0x70, 0x88, 0x88, 0xF8, 0x88, 0x88, + 0x00, 0x88, 0x70, 0x88, 0x88, 0x88, 0x88, 0x70, + 0x00, 0x88, 0x00, 0x88, 0x88, 0x88, 0x88, 0x78, + 0x00, 0x88, 0xF8, 0x80, 0xE0, 0x80, 0x80, 0xF8, + 0x00, 0x40, 0x20, 0x70, 0x88, 0xF8, 0x80, 0x78, + 0x00, 0x10, 0x20, 0x70, 0x88, 0xF8, 0x80, 0x78, + 0x00, 0x20, 0x50, 0x70, 0x88, 0xF8, 0x80, 0x78, + 0x00, 0x40, 0x20, 0x70, 0x08, 0x78, 0x88, 0x78, + 0x00, 0x20, 0x50, 0x00, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x20, 0x10, 0x88, 0x88, 0x88, 0x88, 0x78, + 0x00, 0x00, 0x00, 0x70, 0x80, 0x80, 0x70, 0x20, + 0x00, 0x70, 0x88, 0x40, 0xF0, 0x40, 0x40, 0xF8, + 0x00, 0x88, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x88, 0x88, 0x88, 0xF0, 0x80, 0x80, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x80, 0x80, + 0x00, 0x00, 0x70, 0x88, 0x80, 0x80, 0x88, 0x70, + 0x00, 0x00, 0xF8, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x00, 0x88, 0x88, 0x50, 0x20, 0x40, 0x80, + 0x00, 0x00, 0x70, 0x20, 0xF8, 0xF8, 0x20, 0x70, + 0x00, 0x00, 0x88, 0x50, 0x20, 0x50, 0x88, 0x88, + 0x00, 0x00, 0x88, 0x88, 0x88, 0x88, 0xF8, 0x08, + 0x00, 0x00, 0x88, 0x88, 0x88, 0xF8, 0x08, 0x38, + 0x00, 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, + 0x00, 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, 0x08, + 0x00, 0x00, 0xC0, 0x40, 0x70, 0x48, 0x48, 0x70, + 0x00, 0x00, 0x88, 0x88, 0xC8, 0xA8, 0xA8, 0xE8, + 0x00, 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0xF0, + 0x00, 0x00, 0x70, 0x88, 0x38, 0x08, 0x88, 0x70, + 0x00, 0x00, 0x90, 0xA8, 0xA8, 0xE8, 0xA8, 0x90, + 0x00, 0x00, 0x38, 0x48, 0x48, 0x38, 0x28, 0x48, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; + +const unsigned char stdfont10x7[] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x80, 0xE0, 0xF0, 0xFC, 0xF0, 0xE0, 0x80, 0x00, 0x00, + 0x00, 0x02, 0x0E, 0x1E, 0x7E, 0x1E, 0x0E, 0x02, 0x00, 0x00, + 0x00, 0x10, 0x7C, 0x92, 0x10, 0x92, 0x7C, 0x10, 0x00, 0x00, + 0x00, 0x90, 0x90, 0x90, 0x90, 0x00, 0x90, 0x90, 0x00, 0x00, + 0x00, 0x7E, 0x92, 0x92, 0x7E, 0x12, 0x12, 0x72, 0x00, 0x00, + 0x00, 0x7E, 0x80, 0x7C, 0x82, 0x7C, 0x02, 0xFC, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFE, 0x00, 0x00, + 0x00, 0x10, 0x7C, 0x92, 0x10, 0x92, 0x7C, 0xFE, 0x00, 0x00, + 0x00, 0x10, 0x7C, 0x92, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x10, 0x10, 0x10, 0x10, 0x92, 0x7C, 0x10, 0x00, 0x00, + 0x00, 0x00, 0x08, 0x04, 0xFE, 0x04, 0x08, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x20, 0x40, 0xFE, 0x40, 0x20, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x70, 0x88, 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x10, 0x7C, 0xFE, 0xFE, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0xFE, 0xFE, 0x7C, 0x10, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x10, 0x10, 0x10, 0x10, 0x00, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x6C, 0x6C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x44, 0xFE, 0x44, 0x44, 0x44, 0xFE, 0x44, 0x00, 0x00, + 0x00, 0x10, 0x7E, 0x90, 0x7C, 0x12, 0xFC, 0x10, 0x00, 0x00, + 0x00, 0x00, 0x04, 0x88, 0x10, 0x22, 0x40, 0x00, 0x00, 0x00, + 0x00, 0x38, 0x44, 0x44, 0x78, 0x86, 0x84, 0x7A, 0x00, 0x00, + 0x00, 0x40, 0x40, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x10, 0x20, 0x40, 0x40, 0x40, 0x20, 0x10, 0x00, 0x00, + 0x00, 0x40, 0x20, 0x10, 0x10, 0x10, 0x20, 0x40, 0x00, 0x00, + 0x00, 0x00, 0x10, 0x54, 0x38, 0x54, 0x10, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x10, 0x10, 0x7C, 0x10, 0x10, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x20, 0x00, + 0x00, 0x00, 0x00, 0x00, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x60, 0x00, 0x00, + 0x00, 0x00, 0x04, 0x08, 0x10, 0x20, 0x40, 0x00, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x10, 0x30, 0x50, 0x10, 0x10, 0x10, 0x38, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x02, 0x7C, 0x80, 0x80, 0xFE, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x02, 0x0C, 0x02, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x38, 0x48, 0x88, 0x88, 0xFE, 0x08, 0x08, 0x00, 0x00, + 0x00, 0xFE, 0x80, 0x80, 0xFE, 0x02, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x3E, 0x40, 0x80, 0xFC, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0xFE, 0x02, 0x04, 0x08, 0x10, 0x20, 0x20, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x7C, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x7E, 0x02, 0x02, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x70, 0x60, 0x00, 0x00, + 0x00, 0x08, 0x10, 0x20, 0x40, 0x20, 0x10, 0x08, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xFC, 0x00, 0xFC, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x40, 0x20, 0x10, 0x08, 0x10, 0x20, 0x40, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x02, 0x0C, 0x10, 0x00, 0x10, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x9A, 0x9C, 0x80, 0x7E, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0xFE, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x82, 0xFC, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x80, 0x80, 0x80, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x82, 0x82, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0xFE, 0x80, 0x80, 0xFC, 0x80, 0x80, 0xFE, 0x00, 0x00, + 0x00, 0xFE, 0x80, 0x80, 0xFC, 0x80, 0x80, 0x80, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x80, 0x9E, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0xFE, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x40, 0x40, 0x40, 0x40, 0x40, 0x40, 0x40, 0x00, 0x00, + 0x00, 0x02, 0x02, 0x02, 0x02, 0x02, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x84, 0x88, 0x90, 0xE0, 0x90, 0x88, 0x84, 0x00, 0x00, + 0x00, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0xFE, 0x00, 0x00, + 0x00, 0x82, 0xEE, 0x92, 0x82, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x82, 0xC2, 0xA2, 0x92, 0x8A, 0x86, 0x82, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x82, 0xFC, 0x80, 0x80, 0x80, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x82, 0x92, 0x8A, 0x7C, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x82, 0xFC, 0x88, 0x84, 0x82, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x80, 0x7C, 0x02, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0xFE, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0x82, 0x44, 0x28, 0x10, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0x82, 0x92, 0x92, 0x6C, 0x00, 0x00, + 0x00, 0x82, 0x44, 0x28, 0x10, 0x28, 0x44, 0x82, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x44, 0x28, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0xFE, 0x02, 0x0C, 0x10, 0x60, 0x80, 0xFE, 0x00, 0x00, + 0x00, 0x78, 0x40, 0x40, 0x40, 0x40, 0x40, 0x78, 0x00, 0x00, + 0x00, 0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x00, 0x00, 0x00, + 0x00, 0x78, 0x08, 0x08, 0x08, 0x08, 0x08, 0x78, 0x00, 0x00, + 0x00, 0x10, 0x28, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0x00, 0x00, + 0x00, 0x70, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7C, 0x02, 0x7E, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x80, 0x80, 0xFC, 0x82, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7C, 0x82, 0x80, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x02, 0x02, 0x7E, 0x82, 0x82, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7C, 0x82, 0xFE, 0x80, 0x7E, 0x00, 0x00, + 0x00, 0x30, 0x40, 0x40, 0xE0, 0x40, 0x40, 0x40, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7E, 0x82, 0x82, 0x82, 0x7E, 0x02, 0x7C, + 0x00, 0x80, 0x80, 0xF8, 0x84, 0x84, 0x84, 0x84, 0x00, 0x00, + 0x00, 0x40, 0x00, 0xC0, 0x40, 0x40, 0x40, 0xE0, 0x00, 0x00, + 0x00, 0x10, 0x00, 0x10, 0x10, 0x10, 0x10, 0x10, 0x90, 0x60, + 0x00, 0x80, 0x80, 0x88, 0xB0, 0xC0, 0xB0, 0x88, 0x00, 0x00, + 0x00, 0xC0, 0x40, 0x40, 0x40, 0x40, 0x40, 0xE0, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xEC, 0x92, 0x92, 0x92, 0x92, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xF8, 0x84, 0x84, 0x84, 0x84, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7C, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xFC, 0x82, 0x82, 0x82, 0xFC, 0x80, 0x80, + 0x00, 0x00, 0x00, 0x7C, 0x84, 0x84, 0x84, 0x7C, 0x04, 0x3C, + 0x00, 0x00, 0x00, 0xB8, 0x44, 0x40, 0x40, 0x40, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7C, 0x80, 0x78, 0x04, 0xF8, 0x00, 0x00, + 0x00, 0x40, 0x40, 0xE0, 0x40, 0x40, 0x40, 0x20, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x84, 0x84, 0x84, 0x84, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x82, 0x82, 0x44, 0x28, 0x10, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x82, 0x82, 0x82, 0x92, 0x6C, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x88, 0x50, 0x20, 0x50, 0x88, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x84, 0x84, 0x84, 0x84, 0x7C, 0x04, 0xF8, + 0x00, 0x00, 0x00, 0xF8, 0x10, 0x20, 0x40, 0xF8, 0x00, 0x00, + 0x00, 0x18, 0x20, 0x20, 0x40, 0x20, 0x20, 0x18, 0x00, 0x00, + 0x00, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x60, 0x10, 0x10, 0x08, 0x10, 0x10, 0x60, 0x00, 0x00, + 0x00, 0x00, 0x72, 0x8C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0xFE, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0xFE, 0x82, 0x80, 0xFC, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x82, 0xFC, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0xFE, 0x62, 0x60, 0x60, 0x60, 0x60, 0xF0, 0x00, 0x00, + 0x00, 0xFC, 0x6C, 0x6C, 0x6C, 0x6C, 0x7E, 0x82, 0x00, 0x00, + 0x00, 0xFE, 0x80, 0x80, 0xFC, 0x80, 0x80, 0xFE, 0x00, 0x00, + 0x00, 0x92, 0x92, 0x7C, 0x10, 0x7C, 0x92, 0x92, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x02, 0x1C, 0x02, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x82, 0x8E, 0x92, 0x92, 0x92, 0xE2, 0x82, 0x00, 0x00, + 0x00, 0x92, 0xE2, 0x8E, 0x92, 0x92, 0xE2, 0x82, 0x00, 0x00, + 0x00, 0x82, 0x8C, 0x90, 0xE0, 0x90, 0x8C, 0x82, 0x00, 0x00, + 0x00, 0xFE, 0x6C, 0x6C, 0x6C, 0x6C, 0x6C, 0x8C, 0x00, 0x00, + 0x00, 0x82, 0xEE, 0x92, 0x82, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0xFE, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x82, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0xFE, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x82, 0xFC, 0x80, 0x80, 0x80, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x80, 0x80, 0x80, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0xFE, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0x6C, 0x10, 0x60, 0x80, 0x00, 0x00, + 0x00, 0x7C, 0x10, 0xFE, 0x92, 0xFE, 0x10, 0x7C, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x6C, 0x10, 0x6C, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0x82, 0x82, 0xFE, 0x02, 0x00, 0x00, + 0x00, 0x82, 0x82, 0x82, 0xFE, 0x02, 0x02, 0x1E, 0x00, 0x00, + 0x00, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0xFE, 0x00, 0x00, + 0x00, 0x92, 0x92, 0x92, 0x92, 0x92, 0xFE, 0x02, 0x00, 0x00, + 0x00, 0xE0, 0x60, 0x60, 0x7E, 0x62, 0x62, 0x7E, 0x00, 0x00, + 0x00, 0x82, 0x82, 0xE2, 0x92, 0x92, 0x92, 0xF2, 0x00, 0x00, + 0x00, 0x80, 0x80, 0xFC, 0x82, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0xFC, 0x82, 0x02, 0x7E, 0x02, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0x8C, 0x92, 0x92, 0xF2, 0x92, 0x92, 0x8C, 0x00, 0x00, + 0x00, 0x7E, 0x82, 0x82, 0x7E, 0x12, 0x62, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x02, 0x7E, 0x82, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x00, 0xFE, 0x80, 0xFC, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0x00, 0xFC, 0x82, 0xFC, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0x00, 0xFE, 0x62, 0x62, 0x60, 0x60, 0xF0, 0x00, 0x00, + 0x00, 0x00, 0x7E, 0x6C, 0x6C, 0x6C, 0x7C, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x82, 0xFE, 0x80, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x92, 0x7C, 0x10, 0x7C, 0x92, 0x92, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xFC, 0x82, 0x1C, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x8E, 0x92, 0xE2, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x6C, 0x10, 0x82, 0x8E, 0x92, 0xE2, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x8C, 0x90, 0xF0, 0x8C, 0x82, 0x00, 0x00, + 0x00, 0x00, 0xFE, 0x62, 0x62, 0x62, 0x62, 0xE2, 0x00, 0x00, + 0x00, 0x00, 0x82, 0xEE, 0x92, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x82, 0xFE, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x82, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0xFE, 0x82, 0x82, 0x82, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x7C, 0x44, 0x7C, 0x02, 0x7E, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x44, 0x00, 0x7C, 0x02, 0x7E, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x44, 0x00, 0x7C, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x82, 0x00, 0x82, 0x82, 0x82, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x8C, 0x00, 0xFC, 0x80, 0xF0, 0x80, 0xFC, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x62, 0x7C, 0x62, 0x62, 0xFC, 0x00, 0x00, + 0x00, 0x82, 0x00, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x82, 0x00, 0x7C, 0x82, 0xFE, 0x80, 0x7E, 0x00, 0x00, + 0x00, 0x7C, 0x44, 0x7C, 0x82, 0xFE, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x82, 0x7C, 0x82, 0x82, 0xFE, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x82, 0x7C, 0x82, 0x82, 0x82, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x82, 0x00, 0x82, 0x82, 0x82, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x82, 0xFE, 0x80, 0xF0, 0x80, 0x80, 0xFE, 0x00, 0x00, + 0x00, 0x60, 0x10, 0x7C, 0x82, 0xFE, 0x80, 0x7E, 0x00, 0x00, + 0x00, 0x0C, 0x10, 0x7C, 0x82, 0xFE, 0x80, 0x7E, 0x00, 0x00, + 0x00, 0x10, 0x6C, 0x7C, 0x82, 0xFE, 0x80, 0x7E, 0x00, 0x00, + 0x00, 0x60, 0x10, 0x7C, 0x02, 0x7E, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x10, 0x6C, 0x00, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x10, 0x0C, 0x82, 0x82, 0x82, 0x82, 0x7E, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x7C, 0x80, 0x80, 0x7C, 0x10, 0x00, 0x00, + 0x00, 0x7C, 0x82, 0x60, 0xFC, 0x60, 0x60, 0xFE, 0x00, 0x00, + 0x00, 0x82, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x82, 0x82, 0xFC, 0x80, 0x80, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0xFC, 0x82, 0x82, 0xFC, 0x80, 0x80, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x82, 0x80, 0x80, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0xFE, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x82, 0x6C, 0x10, 0x60, 0x80, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x10, 0xFE, 0xFE, 0x10, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x6C, 0x10, 0x6C, 0x82, 0x82, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x82, 0x82, 0x82, 0xFE, 0x02, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x82, 0x82, 0xFE, 0x02, 0x1E, 0x00, 0x00, + 0x00, 0x00, 0x92, 0x92, 0x92, 0x92, 0x92, 0xFE, 0x00, 0x00, + 0x00, 0x00, 0x92, 0x92, 0x92, 0x92, 0xFE, 0x02, 0x00, 0x00, + 0x00, 0x00, 0xE0, 0x60, 0x7C, 0x62, 0x62, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x82, 0x82, 0xE2, 0x92, 0x92, 0xF2, 0x00, 0x00, + 0x00, 0x00, 0x80, 0x80, 0xFC, 0x82, 0x82, 0xFC, 0x00, 0x00, + 0x00, 0x00, 0x7C, 0x82, 0x1E, 0x02, 0x82, 0x7C, 0x00, 0x00, + 0x00, 0x00, 0x8C, 0x92, 0x92, 0xF2, 0x92, 0x8C, 0x00, 0x00, + 0x00, 0x00, 0x1E, 0x62, 0x62, 0x1E, 0x12, 0x62, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; + +StdFont fonts[] = { + {stdfont8x5, 8, 5}, + {stdfont10x7, 10, 7} +}; + +//Returns the standard font size, 0 = invalid font +// bits 0-7 = font width +// bits 8-15 = font height +unsigned int stdfont_getFontSize(unsigned int fontNumber) +{ + if (fontNumber >= STDFONTS) + return 0; + return (fonts[fontNumber].charHeight << 8) | fonts[fontNumber].charWidth; +} + +//Returns a pointer to the desired font's bitmap representation +unsigned char *stdfont_getBitmap(unsigned int fontNumber) +{ + if (fontNumber >= STDFONTS) + return 0; + return (unsigned char *)fonts[fontNumber].fontPtr; +} + diff --git a/src/kernel/video/stdfont.h b/src/kernel/video/stdfont.h new file mode 100644 index 0000000..c43bcd3 --- /dev/null +++ b/src/kernel/video/stdfont.h @@ -0,0 +1,26 @@ +// stdfont.c +// Author: Josh Holtrop +// Created: 02/26/04 +// Standard font server + +#ifndef __HOS_STDFONT__ +#define __HOS_STDFONT__ __HOS_STDFONT__ + +#define STDFONTS 2 + +typedef struct { + const unsigned char *fontPtr; + unsigned int charHeight; + unsigned int charWidth; +} StdFont; + +//Returns the standard font size, 0 = invalid font +// bits 0-7 = font width +// bits 8-15 = font height +unsigned int stdfont_getFontSize(unsigned int fontNumber); + +//Returns a pointer to the desired font's bitmap representation +unsigned char *stdfont_getBitmap(unsigned int fontNumber); + +#endif + diff --git a/video.c b/src/kernel/video/video.c similarity index 85% rename from video.c rename to src/kernel/video/video.c index dcd2c62..68add88 100644 --- a/video.c +++ b/src/kernel/video/video.c @@ -1,176 +1,188 @@ -//video.c -// 08/13/03 Josh Holtrop -// Modified: 11/12/03 - - -//Initialized the video mode information block video_mode and allocated double-buffer memory for graphics display -void video_init() -{ - videoMode = *(word *)BOOT_VIDEO_MODE; - - if (!videoMode) //we are in console mode - return; - - video_mode = *(ModeInfoBlock *) BOOT_VIDEO_MODE_INFO_BLOCK; - - switch(video_mode.BitsPerPixel) - { - case 16: - video_psetp = &video_psetp16; - break; - case 24: - video_psetp = &video_psetp24; - break; - case 32: - video_psetp = &video_psetp32; - } -} - -//Renders a character using stdfont[] as a bitmask -void video_renderChar(int x, int y, int character, dword color) -{ - int charpos = (character & 0xFF) * 8; - int row; - int col; - for (row = 0; row < 8; row++) - { - for (col = 0; col < 5; col++) - { - if ((stdfont[charpos+row] >> (col+3)) & 0x01) - video_pset(x+(5-col), y+row, color); - } - } -} - -//Draws a horizontal line -void video_horiz(int y, int x1, int x2, dword color) -{ - if (x1 > x2) - { - int tmp = x2; - x2 = x1; - x1 = tmp; //x2 >= x1 now - } - if (x2 < 0) - return; - if (x1 > video_mode.XResolution) - return; - if (x1 < 0) - x1 = 0; - if (x2 > video_mode.XResolution) - x2 = video_mode.XResolution; - int pixel = y*video_mode.XResolution+x1; - for (; x1 <= x2; x1++) - { - video_psetp(pixel++, color); - } -} - -//Draws a vertical line -void video_vert(int x, int y1, int y2, dword color) -{ - if (y1 > y2) - { - int tmp = y2; - y2 = y1; - y1 = tmp; //y2 >= y1 now - } - if (y2 < 0) - return; - if (y1 > video_mode.YResolution) - return; - if (y1 < 0) - y1 = 0; - if (y2 > video_mode.YResolution) - y2 = video_mode.YResolution; - int pixel = y1*video_mode.XResolution+x; - for (; y1 <= y2; y1++) - { - video_psetp(pixel, color); - pixel+=video_mode.XResolution; - } -} - -//Draws a rectangle -void video_rect(int x1, int y1, int x2, int y2, dword color) -{ - video_horiz(y1, x1, x2, color); - video_horiz(y2, x1, x2, color); - video_vert(x1, y1, y2, color); - video_vert(x2, y1, y2, color); -} - -//Draws a filled rectangle -void video_rectf(int x1, int y1, int x2, int y2, dword color) -{ - if (y2 < y1) - { - int tmp = y2; - y2 = y1; - y1 = tmp; - } - for (; y1 <= y2; y1++) - video_horiz(y1, x1, x2, color); -} - -//Draws a single pixel -inline void video_pset(int x, int y, dword color) -{ - if ((x < 0) || (x > video_mode.XResolution) || (y < 0) || (y > video_mode.YResolution)) - return; - video_psetp(y*video_mode.XResolution+x, color); -} - -//Draws a pixel at the specified pixel position -void video_psetp16(int pixel, dword color) -{ - vid_ptr16[pixel] = ((color&0xFF)>>3) | ((((color>>8)&0xFF)>>2)<<5) | ((((color>>16)&0xFF)>>3)<<11); -} - -//Draws a pixel at the specified pixel position -void video_psetp24(int pixel, dword color) -{ - vid_ptr24[pixel*3] = color & 0xFF; - vid_ptr24[pixel*3+1] = (color>>8) & 0xFF; - vid_ptr24[pixel*3+2] = (color>>16) & 0xFF; -} - -//Draws a pixel at the specified pixel position -void video_psetp32(int pixel, dword color) -{ - vid_ptr32[pixel] = color; -} - -//Dummy function to not draw anything if there is no graphical mode enabled -void video_psetpnull(int pixel, dword color) {} - - -// This function draws a simple "console" window in graphical mode to display text -void video_drawConsole() -{ - video_rectf(9, 9, 490, 260, 0); - video_rect(8, 8, 491, 261, 0x00777777); - int x, y; - for (x = 0; x < 80; x++) - { - for (y = 0; y < 25; y++) - { - video_renderChar(x*6+10, y*10+10, console_memory[y*80+x], 0x00FFFFFF); - } - } -} - - -// This function draws a "console" character to the graphical video screen -void video_drawConsoleChar(dword position) -{ - int x = position % 80; - int y = position / 80; - video_renderChar(x*6+10, y*10+10, console_memory[y*80+x], 0x00FFFFFF); -} - - - - - - +// video.c +// 08/13/03 Josh Holtrop +// Modified: 03/02/04 + +#include "hos_defines.h" +#include "video.h" + +ModeInfoBlock video_mode; +dword videoMode = 0; //what video mode # we are in, 0 for console mode +word *vid_ptr16 = (word *)0xF0000000; +byte *vid_ptr24 = (byte *)0xF0000000; +dword *vid_ptr32 = (dword *)0xF0000000; +word console_memory[2000]; //holds a copy of the console's memory +void (*video_psetp)(int, dword) = video_psetpnull; //function pointer to set a pixel + +//Initialized the video mode information block video_mode and allocated double-buffer memory for graphics display +void video_init() +{ + videoMode = *(word *)BOOT_VIDEO_MODE; + + if (!videoMode) //we are in console mode + return; + + video_mode = *(ModeInfoBlock *) BOOT_VIDEO_MODE_INFO_BLOCK; + + switch(video_mode.BitsPerPixel) + { + case 16: + video_psetp = &video_psetp16; + break; + case 24: + video_psetp = &video_psetp24; + break; + case 32: + video_psetp = &video_psetp32; + } +} + +//Renders a character using stdfont[] as a bitmask +void video_renderChar(int x, int y, int character, dword color) +{ + int charpos = (character & 0xFF) * 8; + int row; + int col; + for (row = 0; row < 8; row++) + { + for (col = 0; col < 5; col++) + { + if ((stdfont[charpos+row] >> (col+3)) & 0x01) + video_pset(x+(5-col), y+row, color); + } + } +} + +//Draws a horizontal line +void video_horiz(int y, int x1, int x2, dword color) +{ + if (x1 > x2) + { + int tmp = x2; + x2 = x1; + x1 = tmp; //x2 >= x1 now + } + if (x2 < 0) + return; + if (x1 > video_mode.XResolution) + return; + if (x1 < 0) + x1 = 0; + if (x2 > video_mode.XResolution) + x2 = video_mode.XResolution; + int pixel = y*video_mode.XResolution+x1; + for (; x1 <= x2; x1++) + { + video_psetp(pixel++, color); + } +} + +//Draws a single pixel +void video_pset(int x, int y, dword color) +{ + if ((x < 0) || (x > video_mode.XResolution) || (y < 0) || (y > video_mode.YResolution)) + return; + video_psetp(y*video_mode.XResolution+x, color); +} + +//Draws a pixel at the specified pixel position +void video_pseti(int pixel, dword color) +{ + video_psetp(pixel, color); +} + +//Draws a vertical line +void video_vert(int x, int y1, int y2, dword color) +{ + if (y1 > y2) + { + int tmp = y2; + y2 = y1; + y1 = tmp; //y2 >= y1 now + } + if (y2 < 0) + return; + if (y1 > video_mode.YResolution) + return; + if (y1 < 0) + y1 = 0; + if (y2 > video_mode.YResolution) + y2 = video_mode.YResolution; + int pixel = y1*video_mode.XResolution+x; + for (; y1 <= y2; y1++) + { + video_psetp(pixel, color); + pixel+=video_mode.XResolution; + } +} + +//Draws a rectangle +void video_rect(int x1, int y1, int x2, int y2, dword color) +{ + video_horiz(y1, x1, x2, color); + video_horiz(y2, x1, x2, color); + video_vert(x1, y1, y2, color); + video_vert(x2, y1, y2, color); +} + +//Draws a filled rectangle +void video_rectf(int x1, int y1, int x2, int y2, dword color) +{ + if (y2 < y1) + { + int tmp = y2; + y2 = y1; + y1 = tmp; + } + for (; y1 <= y2; y1++) + video_horiz(y1, x1, x2, color); +} + +//Draws a pixel at the specified pixel position +void video_psetp16(int pixel, dword color) +{ + vid_ptr16[pixel] = ((color&0xFF)>>3) | ((((color>>8)&0xFF)>>2)<<5) | ((((color>>16)&0xFF)>>3)<<11); +} + +//Draws a pixel at the specified pixel position +void video_psetp24(int pixel, dword color) +{ + vid_ptr24[pixel*3] = color & 0xFF; + vid_ptr24[pixel*3+1] = (color>>8) & 0xFF; + vid_ptr24[pixel*3+2] = (color>>16) & 0xFF; +} + +//Draws a pixel at the specified pixel position +void video_psetp32(int pixel, dword color) +{ + vid_ptr32[pixel] = color; +} + +//Dummy function to not draw anything if there is no graphical mode enabled +void video_psetpnull(int pixel, dword color) {} + + +// This function draws a simple "console" window in graphical mode to display text +void video_drawConsole() +{ + video_rectf(9, 9, 490, 260, 0); + video_rect(8, 8, 491, 261, 0x00777777); + int x, y; + for (x = 0; x < 80; x++) + { + for (y = 0; y < 25; y++) + { + video_renderChar(x*6+10, y*10+10, console_memory[y*80+x], 0x00FFFFFF); + } + } +} + + +// This function draws a "console" character to the graphical video screen +void video_drawConsoleChar(dword position) +{ + int x = position % 80; + int y = position / 80; + video_renderChar(x*6+10, y*10+10, console_memory[y*80+x], 0x00FFFFFF); +} + + diff --git a/video.h b/src/kernel/video/video.h similarity index 71% rename from video.h rename to src/kernel/video/video.h index 9109dbc..d2ab455 100644 --- a/video.h +++ b/src/kernel/video/video.h @@ -1,72 +1,68 @@ -//video.h -// 08/18/03 Josh Holtrop -// Modified: 12/28/03 - -void video_init(); -void video_horiz(int y, int x1, int x2, dword color); -void video_vert(int x, int y1, int y2, dword color); -void video_rect(int x1, int y1, int x2, int y2, dword color); -void video_rectf(int x1, int y1, int x2, int y2, dword color); -inline void video_pset(int x, int y, dword color); -void video_psetp16(int pixel, dword color); -void video_psetp24(int pixel, dword color); -void video_psetp32(int pixel, dword color); -void video_psetpnull(int pixel, dword color); -void video_renderChar(int x, int y, int character, dword color); -void video_drawConsole(); -void video_drawConsoleChar(dword position); - - -typedef struct{ - word ModeAttributes; - byte WinAAttributes; - byte WinBAttributes; - word WinGranularity; - word WinSize; - word WinASegment; - word WinBSegment; - dword WinFuncPtr; - word BytesPerScanLine; - - word XResolution; - word YResolution; - byte XCharSize; - byte YCharSize; - byte NumberOfPlanes; - byte BitsPerPixel; - byte NumberOfBanks; - byte MemoryModel; - byte BankSize; - byte NumberOfImagePages; - byte Reserved1; - - byte RedMaskSize; - byte RedFieldPosition; - byte GreenMaskSize; - byte GreenFieldPosition; - byte BlueMaskSize; - byte BlueFieldPosition; - byte RsvdMaskSize; - byte RsvdFieldPosition; - byte DirectColorModeInfo; - - dword PhysBasePtr; - dword OffScreenMemOffset; - word OffScreenMemSize; - byte Reserved[206]; -} ModeInfoBlock; - - -ModeInfoBlock video_mode; -dword videoMode = 0; //what video mode # we are in, 0 for console mode -word *vid_ptr16 = (word *)0xF0000000; -byte *vid_ptr24 = (byte *)0xF0000000; -dword *vid_ptr32 = (dword *)0xF0000000; -word console_memory[2000]; //holds a copy of the console's memory -void (*video_psetp)(int, dword) = video_psetpnull; //function pointer to set a pixel - - - - - - +// video.h +// 08/18/03 Josh Holtrop +// Modified: 03/02/04 + +#include "hos_defines.h" + +#ifndef __HOS_VIDEO__ +#define __HOS_VIDEO__ __HOS_VIDEO__ + +void video_init(); +void video_horiz(int y, int x1, int x2, dword color); +void video_vert(int x, int y1, int y2, dword color); +void video_rect(int x1, int y1, int x2, int y2, dword color); +void video_rectf(int x1, int y1, int x2, int y2, dword color); +void video_pset(int x, int y, dword color); +void video_pseti(int pixel, dword color); +void video_psetp16(int pixel, dword color); +void video_psetp24(int pixel, dword color); +void video_psetp32(int pixel, dword color); +void video_psetpnull(int pixel, dword color); +void video_renderChar(int x, int y, int character, dword color); +void video_drawConsole(); +void video_drawConsoleChar(dword position); + + +typedef struct{ + word ModeAttributes; + byte WinAAttributes; + byte WinBAttributes; + word WinGranularity; + word WinSize; + word WinASegment; + word WinBSegment; + dword WinFuncPtr; + word BytesPerScanLine; + + word XResolution; + word YResolution; + byte XCharSize; + byte YCharSize; + byte NumberOfPlanes; + byte BitsPerPixel; + byte NumberOfBanks; + byte MemoryModel; + byte BankSize; + byte NumberOfImagePages; + byte Reserved1; + + byte RedMaskSize; + byte RedFieldPosition; + byte GreenMaskSize; + byte GreenFieldPosition; + byte BlueMaskSize; + byte BlueFieldPosition; + byte RsvdMaskSize; + byte RsvdFieldPosition; + byte DirectColorModeInfo; + + dword PhysBasePtr; + dword OffScreenMemOffset; + word OffScreenMemSize; + byte Reserved[206]; +} ModeInfoBlock; + + +#endif + + diff --git a/src/readme.txt b/src/readme.txt new file mode 100644 index 0000000..8d50654 --- /dev/null +++ b/src/readme.txt @@ -0,0 +1,52 @@ +HOS - Holtrop's Operating System + + +HOS is a 32-bit, protected mode, graphical, multitasking operating system. +It was written by me, Josh Holtrop, with help from a few others along the way. + + + + +History +------------- + +0.14 +03/01/04 - Thanks to Ben Meyer for helping me get a Makefile working and building on linux to work! + +0.13 +01/26/04 - functions added to read/write CMOS clock date and time +01/19/04 - fixed bug GDTR/IDTR pointing to physical rather than linear table base address +01/07/04 - fixed bug not reading sectors correctly from floppy +12/28/03 - fixed bug not storing eax on interrupt +12/25/03 - fixed bug in mm_palloc() +12/25/03 - incorporated output functions as regular functions rather than as part of a linked library +12/23/03 - re-written physical memory manager using bitmap instead of stack +12/22/03 - kernel relocated to 3gb linear / 1mb+24kb physical to allow for app. address space + +0.12 +12/21/03 - sample bmp loader tested, works (tests loading a kernel of size ~ 932kb +12/20/03 - GDT/IDT now located at 1mb physical, before kernel +10/30/03 - turns floppy motor off +10/30/03 - keyboard LEDs working +10/29/03 - paging functions working +10/15/03 - physical memory management page allocators working + +0.11 +10/09/03 - PS/2 mouse driver + +0.10 +09/11/03 - Rewritten C and assembly kernel with VESA GUI mode support, keyboard driver + +0.05 +05/14/03 - HGUI24/HGUI32 commands finished for testing GUI on both 24bpp and 32bpp graphics cards +05/14/03 - first web release! + +0.04 +03/09/03 - added VM shortcut command +03/09/03 - press up to fill retrieve last inputted command for Nate Scholten +03/08/03 - press clear to clear console input +03/07/03 - added "shortcut" commands PC, IC, ? for Nate Scholten +03/06/03 - added PROMPTC, INPUTC commands + +0.03 +12/30/02 - Command Line Interface working, accepting basic commands \ No newline at end of file diff --git a/stdfont.h b/stdfont.h deleted file mode 100644 index d4a490e..0000000 --- a/stdfont.h +++ /dev/null @@ -1,258 +0,0 @@ -const byte stdfont[] = { - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x80, 0xC0, 0xE0, 0xF0, 0xE0, 0xC0, 0x80, - 0x00, 0x08, 0x18, 0x38, 0x78, 0x38, 0x18, 0x08, - 0x00, 0x20, 0x70, 0xA8, 0x20, 0xA8, 0x70, 0x20, - 0x00, 0xA0, 0xA0, 0xA0, 0xA0, 0x00, 0xA0, 0xA0, - 0x00, 0x78, 0xA8, 0xA8, 0x78, 0x28, 0x28, 0x68, - 0x00, 0x78, 0x80, 0x70, 0x88, 0x70, 0x08, 0xF0, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, 0xF8, - 0x00, 0x20, 0x70, 0xA8, 0x20, 0xA8, 0x70, 0xF8, - 0x00, 0x20, 0x70, 0xA8, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x20, 0x20, 0x20, 0x20, 0xA8, 0x70, 0x20, - 0x00, 0x00, 0x20, 0x10, 0xF8, 0x10, 0x20, 0x00, - 0x00, 0x00, 0x20, 0x40, 0xF8, 0x40, 0x20, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, - 0x00, 0x60, 0x90, 0x60, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x20, 0x70, 0xF8, 0xF8, 0x00, 0x00, - 0x00, 0x00, 0xF8, 0xF8, 0x70, 0x20, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x20, 0x20, 0x20, 0x20, 0x00, 0x20, 0x20, - 0x00, 0x50, 0x50, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x50, 0xF8, 0x50, 0x50, 0x50, 0xF8, 0x50, - 0x00, 0x20, 0x78, 0xA0, 0x70, 0x28, 0xF0, 0x20, - 0x00, 0x00, 0x08, 0x90, 0x20, 0x48, 0x80, 0x00, - 0x00, 0x20, 0x50, 0x50, 0x20, 0x58, 0x90, 0x68, - 0x00, 0x40, 0x40, 0x80, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x20, 0x40, 0x40, 0x40, 0x40, 0x40, 0x20, - 0x00, 0x40, 0x20, 0x20, 0x20, 0x20, 0x20, 0x40, - 0x00, 0x00, 0xA8, 0x70, 0xF8, 0x70, 0xA8, 0x00, - 0x00, 0x00, 0x20, 0x20, 0xF8, 0x20, 0x20, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x40, - 0x00, 0x00, 0x00, 0x00, 0xF0, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x60, - 0x00, 0x00, 0x08, 0x10, 0x20, 0x40, 0x80, 0x00, - 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, - 0x00, 0x20, 0x60, 0xA0, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x70, 0x88, 0x08, 0x10, 0x20, 0x40, 0xF8, - 0x00, 0x70, 0x88, 0x08, 0x10, 0x08, 0x88, 0x70, - 0x00, 0x30, 0x50, 0x90, 0x90, 0xF8, 0x10, 0x10, - 0x00, 0xF8, 0x80, 0x80, 0xF8, 0x08, 0x88, 0x70, - 0x00, 0x38, 0x40, 0x80, 0xF0, 0x88, 0x88, 0x70, - 0x00, 0xF8, 0x08, 0x10, 0x20, 0x40, 0x40, 0x40, - 0x00, 0x70, 0x88, 0x88, 0x70, 0x88, 0x88, 0x70, - 0x00, 0x70, 0x88, 0x88, 0x78, 0x08, 0x10, 0x60, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x60, 0x40, - 0x00, 0x10, 0x20, 0x40, 0x80, 0x40, 0x20, 0x10, - 0x00, 0x00, 0x00, 0xF0, 0x00, 0xF0, 0x00, 0x00, - 0x00, 0x80, 0x40, 0x20, 0x10, 0x20, 0x40, 0x80, - 0x00, 0x70, 0x88, 0x08, 0x10, 0x20, 0x00, 0x20, - 0x00, 0x70, 0x88, 0x88, 0xB8, 0xB0, 0x80, 0x78, - 0x00, 0x70, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, - 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x88, 0x88, 0xF0, - 0x00, 0x70, 0x88, 0x80, 0x80, 0x80, 0x88, 0x70, - 0x00, 0xF0, 0x88, 0x88, 0x88, 0x88, 0x88, 0xF0, - 0x00, 0xF8, 0x80, 0x80, 0xF0, 0x80, 0x80, 0xF8, - 0x00, 0xF8, 0x80, 0x80, 0xF0, 0x80, 0x80, 0x80, - 0x00, 0x70, 0x88, 0x80, 0xB8, 0x88, 0x88, 0x70, - 0x00, 0x88, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, - 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x10, 0x10, 0x10, 0x10, 0x10, 0x90, 0x60, - 0x00, 0x88, 0x90, 0xA0, 0xC0, 0xA0, 0x90, 0x88, - 0x00, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0xF8, - 0x00, 0x88, 0xD8, 0xA8, 0x88, 0x88, 0x88, 0x88, - 0x00, 0x88, 0xC8, 0xE8, 0xB8, 0x98, 0x88, 0x88, - 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, - 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x80, 0x80, 0x80, - 0x00, 0x70, 0x88, 0x88, 0x88, 0xA8, 0x98, 0x70, - 0x00, 0xF0, 0x88, 0x88, 0xF0, 0xA0, 0x90, 0x88, - 0x00, 0x70, 0x88, 0x80, 0x70, 0x08, 0x88, 0x70, - 0x00, 0xF8, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, - 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0x50, 0x20, - 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0xA8, 0x50, - 0x00, 0x88, 0x50, 0x20, 0x20, 0x50, 0x88, 0x88, - 0x00, 0x88, 0x88, 0x50, 0x20, 0x20, 0x20, 0x20, - 0x00, 0xF8, 0x08, 0x10, 0x20, 0x40, 0x80, 0xF8, - 0x00, 0x70, 0x40, 0x40, 0x40, 0x40, 0x40, 0x70, - 0x00, 0x80, 0xC0, 0x60, 0x30, 0x18, 0x08, 0x00, - 0x00, 0xE0, 0x20, 0x20, 0x20, 0x20, 0x20, 0xE0, - 0x00, 0x20, 0x50, 0x88, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, - 0x00, 0x60, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x70, 0x08, 0x78, 0x88, 0x78, - 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0x88, 0xF0, - 0x00, 0x00, 0x00, 0x70, 0x88, 0x80, 0x88, 0x70, - 0x00, 0x08, 0x08, 0x78, 0x88, 0x88, 0x88, 0x78, - 0x00, 0x00, 0x00, 0x70, 0x88, 0xF8, 0x80, 0x78, - 0x00, 0x30, 0x40, 0x40, 0xE0, 0x40, 0x40, 0x40, - 0x00, 0x00, 0x00, 0x78, 0x88, 0x78, 0x08, 0x70, - 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0x88, 0x88, - 0x00, 0x20, 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x10, 0x00, 0x10, 0x10, 0x10, 0x90, 0x60, - 0x00, 0x80, 0x80, 0x90, 0xA0, 0xC0, 0xA0, 0x90, - 0x00, 0xC0, 0x40, 0x40, 0x40, 0x40, 0x40, 0xE0, - 0x00, 0x00, 0x00, 0xD0, 0xA8, 0xA8, 0xA8, 0xA8, - 0x00, 0x00, 0x00, 0xF0, 0x88, 0x88, 0x88, 0x88, - 0x00, 0x00, 0x00, 0x70, 0x88, 0x88, 0x88, 0x70, - 0x00, 0x00, 0x00, 0xF0, 0x88, 0xF0, 0x80, 0x80, - 0x00, 0x00, 0x00, 0x78, 0x88, 0x78, 0x08, 0x38, - 0x00, 0x00, 0x00, 0x70, 0x48, 0x40, 0x40, 0x40, - 0x00, 0x00, 0x00, 0x78, 0x80, 0x70, 0x08, 0xF0, - 0x00, 0x40, 0x40, 0xE0, 0x40, 0x40, 0x40, 0x20, - 0x00, 0x00, 0x00, 0x88, 0x88, 0x88, 0x88, 0x78, - 0x00, 0x00, 0x00, 0x88, 0x88, 0x88, 0x50, 0x20, - 0x00, 0x00, 0x00, 0x88, 0x88, 0x88, 0xA8, 0x50, - 0x00, 0x00, 0x00, 0x88, 0x50, 0x20, 0x50, 0x88, - 0x00, 0x00, 0x00, 0x88, 0x88, 0x78, 0x08, 0xF0, - 0x00, 0x00, 0x00, 0xF8, 0x10, 0x20, 0x40, 0xF8, - 0x00, 0x30, 0x40, 0x40, 0x80, 0x40, 0x40, 0x30, - 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0xC0, 0x20, 0x20, 0x10, 0x20, 0x20, 0xC0, - 0x00, 0x00, 0x68, 0x90, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x70, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, - 0x00, 0xF8, 0x88, 0x80, 0xF0, 0x88, 0x88, 0xF0, - 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x88, 0x88, 0xF0, - 0x00, 0xF8, 0x48, 0x40, 0x40, 0x40, 0x40, 0xE0, - 0x00, 0xF0, 0x50, 0x50, 0x50, 0x50, 0x78, 0x88, - 0x00, 0xF8, 0x80, 0x80, 0xF0, 0x80, 0x80, 0xF8, - 0x00, 0xA8, 0xA8, 0x70, 0x20, 0x70, 0xA8, 0xA8, - 0x00, 0x70, 0x88, 0x08, 0x30, 0x08, 0x88, 0x70, - 0x00, 0x88, 0x98, 0xA8, 0xA8, 0xA8, 0xC8, 0x88, - 0x00, 0xA8, 0xC8, 0x98, 0xA8, 0xA8, 0xC8, 0x88, - 0x00, 0x88, 0x90, 0xA0, 0xC0, 0xA0, 0x90, 0x88, - 0x00, 0xF8, 0x50, 0x50, 0x50, 0x50, 0x50, 0x90, - 0x00, 0x88, 0xD8, 0xA8, 0x88, 0x88, 0x88, 0x88, - 0x00, 0x88, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, - 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x88, 0x70, - 0x00, 0xF8, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, - 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x80, 0x80, 0x80, - 0x00, 0x70, 0x88, 0x80, 0x80, 0x80, 0x88, 0x70, - 0x00, 0xF8, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x88, 0x88, 0x88, 0x50, 0x20, 0x40, 0x80, - 0x00, 0x70, 0x20, 0xF8, 0xA8, 0xF8, 0x20, 0x70, - 0x00, 0x88, 0x88, 0x50, 0x20, 0x50, 0x88, 0x88, - 0x00, 0x88, 0x88, 0x88, 0x88, 0x88, 0xF8, 0x08, - 0x00, 0x88, 0x88, 0x88, 0xF8, 0x08, 0x08, 0x38, - 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, - 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, 0x08, - 0x00, 0xC0, 0x40, 0x40, 0x78, 0x48, 0x48, 0x78, - 0x00, 0x88, 0x88, 0xC8, 0xA8, 0xA8, 0xA8, 0xE8, - 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0x88, 0xF0, - 0x00, 0xF0, 0x88, 0x08, 0x78, 0x08, 0x88, 0xF0, - 0x00, 0x90, 0xA8, 0xA8, 0xE8, 0xA8, 0xA8, 0x90, - 0x00, 0x78, 0x88, 0x88, 0x78, 0x28, 0x48, 0x88, - 0x00, 0x00, 0x70, 0x08, 0x78, 0x88, 0x88, 0x78, - 0x00, 0x00, 0xF8, 0x80, 0xF0, 0x88, 0x88, 0xF0, - 0x00, 0x00, 0xF0, 0x88, 0xF0, 0x88, 0x88, 0xF0, - 0x00, 0x00, 0xF8, 0x48, 0x48, 0x40, 0x40, 0xE0, - 0x00, 0x00, 0x78, 0x50, 0x50, 0x50, 0x70, 0x88, - 0x00, 0x00, 0x70, 0x88, 0xF8, 0x80, 0x88, 0x70, - 0x00, 0x00, 0xA8, 0x70, 0x20, 0x70, 0xA8, 0xA8, - 0x00, 0x00, 0x00, 0xF0, 0x88, 0x30, 0x88, 0x70, - 0x00, 0x00, 0x88, 0x98, 0xA8, 0xC8, 0x88, 0x88, - 0x00, 0x50, 0x20, 0x88, 0x98, 0xA8, 0xC8, 0x88, - 0x00, 0x00, 0x88, 0x90, 0xA0, 0xE0, 0x90, 0x88, - 0x00, 0x00, 0xF8, 0x48, 0x48, 0x48, 0x48, 0xC8, - 0x00, 0x00, 0x88, 0xD8, 0xA8, 0x88, 0x88, 0x88, - 0x00, 0x00, 0x88, 0x88, 0xF8, 0x88, 0x88, 0x88, - 0x00, 0x00, 0x70, 0x88, 0x88, 0x88, 0x88, 0x70, - 0x00, 0x00, 0xF8, 0x88, 0x88, 0x88, 0x88, 0x88, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x70, 0x50, 0x70, 0x08, 0x78, 0x88, 0x78, - 0x00, 0x88, 0x00, 0x70, 0x08, 0x78, 0x88, 0x78, - 0x00, 0x88, 0x00, 0x70, 0x88, 0x88, 0x88, 0x70, - 0x00, 0x88, 0x00, 0x88, 0x88, 0x88, 0x88, 0x78, - 0x00, 0x90, 0x00, 0xF0, 0x80, 0xE0, 0x80, 0xF0, - 0x00, 0x00, 0x70, 0x48, 0x70, 0x48, 0x48, 0xF0, - 0x00, 0x88, 0x00, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x88, 0x00, 0x70, 0x88, 0xF8, 0x80, 0x78, - 0x00, 0x70, 0x50, 0x70, 0x88, 0xF8, 0x88, 0x88, - 0x00, 0x88, 0x70, 0x88, 0x88, 0xF8, 0x88, 0x88, - 0x00, 0x88, 0x70, 0x88, 0x88, 0x88, 0x88, 0x70, - 0x00, 0x88, 0x00, 0x88, 0x88, 0x88, 0x88, 0x78, - 0x00, 0x88, 0xF8, 0x80, 0xE0, 0x80, 0x80, 0xF8, - 0x00, 0x40, 0x20, 0x70, 0x88, 0xF8, 0x80, 0x78, - 0x00, 0x10, 0x20, 0x70, 0x88, 0xF8, 0x80, 0x78, - 0x00, 0x20, 0x50, 0x70, 0x88, 0xF8, 0x80, 0x78, - 0x00, 0x40, 0x20, 0x70, 0x08, 0x78, 0x88, 0x78, - 0x00, 0x20, 0x50, 0x00, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x20, 0x10, 0x88, 0x88, 0x88, 0x88, 0x78, - 0x00, 0x00, 0x00, 0x70, 0x80, 0x80, 0x70, 0x20, - 0x00, 0x70, 0x88, 0x40, 0xF0, 0x40, 0x40, 0xF8, - 0x00, 0x88, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x88, 0x88, 0x88, 0xF0, 0x80, 0x80, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0xF0, 0x88, 0x88, 0xF0, 0x80, 0x80, - 0x00, 0x00, 0x70, 0x88, 0x80, 0x80, 0x88, 0x70, - 0x00, 0x00, 0xF8, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x00, 0x00, 0x88, 0x88, 0x50, 0x20, 0x40, 0x80, - 0x00, 0x00, 0x70, 0x20, 0xF8, 0xF8, 0x20, 0x70, - 0x00, 0x00, 0x88, 0x50, 0x20, 0x50, 0x88, 0x88, - 0x00, 0x00, 0x88, 0x88, 0x88, 0x88, 0xF8, 0x08, - 0x00, 0x00, 0x88, 0x88, 0x88, 0xF8, 0x08, 0x38, - 0x00, 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, - 0x00, 0x00, 0xA8, 0xA8, 0xA8, 0xA8, 0xF8, 0x08, - 0x00, 0x00, 0xC0, 0x40, 0x70, 0x48, 0x48, 0x70, - 0x00, 0x00, 0x88, 0x88, 0xC8, 0xA8, 0xA8, 0xE8, - 0x00, 0x00, 0x80, 0x80, 0xF0, 0x88, 0x88, 0xF0, - 0x00, 0x00, 0x70, 0x88, 0x38, 0x08, 0x88, 0x70, - 0x00, 0x00, 0x90, 0xA8, 0xA8, 0xE8, 0xA8, 0x90, - 0x00, 0x00, 0x38, 0x48, 0x48, 0x38, 0x28, 0x48, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; - diff --git a/vfs.c b/vfs.c deleted file mode 100644 index ee4f6c1..0000000 --- a/vfs.c +++ /dev/null @@ -1,91 +0,0 @@ -// vfs.c -// Author: Josh Holtrop -// Created: 12/31/03 -// Modified: 01/04/04 - - -void vfs_init() -{ - firstDiskDevice = malloc(sizeof(DiskDevice)); - firstDiskDevice->type = VFS_DISK_FD; - firstDiskDevice->fileSystem = VFS_FS_FAT12; - firstDiskDevice->location = VFS_LOC_FD0; - firstDiskDevice->link = 0; - strcpy(firstDiskDevice->id, "fd0"); - rootDevice = firstDiskDevice; - if (*(byte *)0xC0090000) // the user chose to load an initial ram disk from the floppy - { - DiskDevice *rd = malloc(sizeof(DiskDevice)); - firstDiskDevice->link = (dword)rd; - rd->type = VFS_DISK_RD; - rd->fileSystem = VFS_FS_FAT12; - rd->location = 0xC0200000; - rd->link = 0; - strcpy(rd->id, "rd0"); - rootDevice = rd; - } -} - - -byte *vfs_readFile(char *fileName) -{ - DiskDevice *dd; - dword fileStartPosition; - if (fileName[0] == '/') - { - dd = rootDevice; - fileStartPosition = 1; - } - else - { - if (strlen(fileName) < 5) //not a long enough file name - return 0; - if (!((fileName[3] == ':') && (fileName[4] == '/'))) //if we aren't using the root directory, then there must be a 3 character device explicitly specified - return 0; // followed by a colon and then a slash - char device[4]; - memcpy(device, fileName, 3); //copy the 3 digit device id to device - device[3] = 0; //null-terminating character for device string - dd = vfs_getDiskDeviceByID(device); - if (!dd) //the specified device was not found - return 0; - fileStartPosition = 5; - } - switch (dd->fileSystem) - { - case VFS_FS_FAT12: - return fat12_readFile(fileName+fileStartPosition, dd); - } - return 0; -} - - -byte *vfs_readSector(DiskDevice *dd, dword sector, byte *dest, dword sectors) -{ - byte *origDest = dest; - switch (dd->type) - { - case VFS_DISK_RD: - for (; sectors > 0; sectors--, dest += 512, sector++) - rd_readSector(dd, sector, dest); - return origDest; - } - return 0; -} - - -DiskDevice *vfs_getDiskDeviceByID(char *id) -{ - DiskDevice *dd = firstDiskDevice; - for (;;) - { - if (strcmp(dd->id, id)) - return dd; - dd = (DiskDevice *)dd->link; - if (!dd) - break; - } - return 0; -} - - - diff --git a/vfs.h b/vfs.h deleted file mode 100644 index b657087..0000000 --- a/vfs.h +++ /dev/null @@ -1,33 +0,0 @@ -// vfs.h -// Author: Josh Holtrop -// Created: 12/31/03 -// Modified: 01/04/04 - - -#define VFS_DISK_RD 1 -#define VFS_DISK_FD 2 -#define VFS_DISK_HD 3 - -#define VFS_FS_FAT12 1 - -#define VFS_LOC_FD0 1 - - -typedef struct { - dword type; - dword fileSystem; - dword location; - dword link; - char id[4]; -} __attribute__((packed)) DiskDevice; - - -void vfs_init(); -byte *vfs_readFile(char *fileName); -byte *vfs_readSector(DiskDevice *dd, dword sector, byte *dest, dword sectors); -DiskDevice *vfs_getDiskDeviceByID(char *id); - -DiskDevice *rootDevice = 0; -DiskDevice *firstDiskDevice = 0; - -