00001
00002
00003
00004
00005
00006
00007
00008
00009
00010 #include "console.h"
00011
00012
00013 #define COLOUR_VIDEO 0xB8000
00014 #define MONO_VIDEO 0xB0000
00015
00016
00017 long consoleCols = 80;
00018 long consoleLines = 24;
00019
00020 long consoleBytesPerLine = 80 * 2;
00021 long consoleTotalBytes = 4000;
00022
00023 char consoleAttrib = 15;
00024
00025
00026 static int consoleXPos, consoleYPos;
00027
00028
00029 static volatile unsigned char *consoleAddr;
00030
00031 void (*consoleOut)(const char *format, ...);
00032
00033 void consoleInit(void) {
00034 consoleClear();
00035 consoleOut = (void (*)(const char *, ...))printf;
00036 return;
00037 }
00038
00039
00040 void consoleClear (void) {
00041 int i;
00042
00043
00044 consoleAddr = (unsigned char *) COLOUR_VIDEO;
00045
00046 for (i = 0; i < consoleCols * consoleLines * 2; i++)
00047 *(consoleAddr + i) = 0;
00048
00049 consoleXPos = 0;
00050 consoleYPos = 0;
00051 }
00052
00053
00054
00055
00056 static void itoa (char *buf, int base, int d, signed int length) {
00057 char *p = buf;
00058 char *p1, *p2;
00059 unsigned long ud = d;
00060 int divisor = 10;
00061
00062
00063 if (base == 'd' && d < 0) {
00064 *p++ = '-';
00065 buf++;
00066 ud = -d;
00067 } else if (base == 'x')
00068 divisor = 16;
00069
00070
00071 do {
00072 int remainder = ud % divisor;
00073
00074 *p++ = (remainder < 10) ? remainder + '0' : remainder + 'a' - 10;
00075 length--;
00076 } while (ud /= divisor);
00077
00078 while(length > 0) {
00079 *p++ = '0';
00080 length--;
00081 }
00082
00083
00084 *p = 0;
00085
00086
00087 p1 = buf;
00088 p2 = p - 1;
00089 while (p1 < p2) {
00090 char tmp = *p1;
00091 *p1 = *p2;
00092 *p2 = tmp;
00093 p1++;
00094 p2--;
00095 }
00096 }
00097
00098
00099 static void putchar (int c) {
00100 if (c == '\n' || c == '\r') {
00101 newline:
00102 consoleXPos = 0;
00103 consoleYPos++;
00104 if(consoleYPos >= consoleLines) {
00105 consoleYPos = consoleLines;
00106
00107 memcpy(consoleAddr,
00108 consoleAddr + consoleBytesPerLine,
00109 consoleTotalBytes - consoleBytesPerLine );
00110
00111 memset(consoleAddr + consoleTotalBytes - consoleBytesPerLine,
00112 0,
00113 consoleBytesPerLine);
00114 }
00115 return;
00116 } else if (c == '\t') {
00117 consoleXPos += (8 - (consoleXPos & 7));
00118 return;
00119 }
00120
00121 *(consoleAddr + (consoleXPos + consoleYPos * consoleCols) * 2) = c & 0xFF;
00122 *(consoleAddr + (consoleXPos + consoleYPos * consoleCols) * 2 + 1) = consoleAttrib;
00123
00124 consoleXPos++;
00125 if (consoleXPos >= consoleCols)
00126 goto newline;
00127 }
00128
00129
00130
00131 void printf (const char *format, ...) {
00132 char **arg = (char **) &format;
00133 int c;
00134 char buf[20];
00135 int length;
00136
00137 arg++;
00138
00139 while ((c = *format++) != 0) {
00140 length = 0;
00141 if (c != '%')
00142 putchar (c);
00143 else {
00144 char *p;
00145
00146 c = *format++;
00147 while(c >= '0' && c <= '9') {
00148 length *= 10;
00149 length += c - '0';
00150 c = *format++;
00151 }
00152 switch (c) {
00153 case 'd':
00154 case 'u':
00155 case 'x':
00156 itoa (buf, c, *((int *) arg++), length);
00157 p = buf;
00158 goto string;
00159 break;
00160
00161 case 's':
00162 p = *arg++;
00163 if (! p)
00164 p = "(null)";
00165
00166 string:
00167 while (*p)
00168 putchar (*p++);
00169 break;
00170
00171 default:
00172 putchar (*((int *) arg++));
00173 break;
00174 }
00175 }
00176 }
00177 }