213 lines
5.9 KiB
C
Executable file
213 lines
5.9 KiB
C
Executable file
/*
|
|
File: Console.C
|
|
|
|
Author: R. Bettati
|
|
Department of Computer Science
|
|
Texas A&M University
|
|
Date : 09/02/2009
|
|
|
|
*/
|
|
|
|
/*--------------------------------------------------------------------------*/
|
|
/* DEFINES */
|
|
/*--------------------------------------------------------------------------*/
|
|
|
|
#define CONSOLE_START_ADDRESS (unsigned short *)0xB8000
|
|
|
|
/*--------------------------------------------------------------------------*/
|
|
/* INCLUDES */
|
|
/*--------------------------------------------------------------------------*/
|
|
|
|
#include "console.H"
|
|
|
|
#include "utils.H"
|
|
#include "machine.H"
|
|
|
|
/*--------------------------------------------------------------------------*/
|
|
/* DATA STRUCTURES */
|
|
/*--------------------------------------------------------------------------*/
|
|
|
|
/* -- (none) -- */
|
|
|
|
/*--------------------------------------------------------------------------*/
|
|
/* CONSTANTS */
|
|
/*--------------------------------------------------------------------------*/
|
|
|
|
/* -- (none) -- */
|
|
|
|
/*--------------------------------------------------------------------------*/
|
|
/* FORWARDS */
|
|
/*--------------------------------------------------------------------------*/
|
|
|
|
/* -- (none) -- */
|
|
|
|
/*--------------------------------------------------------------------------*/
|
|
/* METHODS FOR CLASS C o n s o l e */
|
|
/*--------------------------------------------------------------------------*/
|
|
|
|
/* -- GLOBAL VARIABLES -- */
|
|
|
|
int Console::attrib; /* background and foreground color */
|
|
int Console::csr_x; /* position of cursor */
|
|
int Console::csr_y;
|
|
unsigned short * Console::textmemptr; /* text pointer */
|
|
|
|
/* -- CONSTRUCTOR -- */
|
|
|
|
void Console::init(unsigned char _fore_color,
|
|
unsigned char _back_color) {
|
|
set_TextColor(_fore_color, _back_color);
|
|
csr_x = 0;
|
|
csr_y = 0;
|
|
textmemptr = CONSOLE_START_ADDRESS;
|
|
cls();
|
|
}
|
|
|
|
|
|
void Console::scroll() {
|
|
|
|
/* A blank is defined as a space... we need to give it
|
|
* backcolor too */
|
|
unsigned blank = 0x20 | (attrib << 8);
|
|
|
|
/* Row 25 is the end, this means we need to scroll up */
|
|
if(csr_y >= 25)
|
|
{
|
|
/* Move the current text chunk that makes up the screen
|
|
* back in the buffer by a line */
|
|
unsigned temp = csr_y - 25 + 1;
|
|
memcpy ((char*)textmemptr, (char*)(textmemptr + temp * 80), (25 - temp) * 80 * 2);
|
|
|
|
/* Finally, we set the chunk of memory that occupies
|
|
* the last line of text to our 'blank' character */
|
|
memsetw (textmemptr + (25 - temp) * 80, blank, 80);
|
|
csr_y = 25 - 1;
|
|
}
|
|
}
|
|
|
|
|
|
void Console::move_cursor() {
|
|
|
|
/* The equation for finding the index in a linear
|
|
* chunk of memory can be represented by:
|
|
* Index = [(y * width) + x] */
|
|
unsigned temp = csr_y * 80 + csr_x;
|
|
|
|
/* This sends a command to indicies 14 and 15 in the
|
|
* Console Control Register of the VGA controller. These
|
|
* are the high and low bytes of the index that show
|
|
* where the hardware cursor is to be 'blinking'. To
|
|
* learn more, you should look up some VGA specific
|
|
* programming documents. A great start to graphics:
|
|
* http://www.brackeen.com/home/vga */
|
|
Machine::outportb(0x3D4, (char)14);
|
|
//outportb(0x3D5, temp >> 8);
|
|
Machine::outportb(0x3D4, 15);
|
|
//outportb(0x3D5, (char)temp);
|
|
}
|
|
|
|
/* Clear the screen */
|
|
void Console::cls() {
|
|
|
|
/* Again, we need the 'short' that will be used to
|
|
* represent a space with color */
|
|
unsigned blank = 0x20 | (attrib << 8);
|
|
|
|
/* Sets the entire screen to spaces in our current
|
|
* color */
|
|
for(int i = 0; i < 25; i++)
|
|
memsetw (textmemptr + i * 80, blank, 80);
|
|
|
|
/* Update out virtual cursor, and then move the
|
|
* hardware cursor */
|
|
csr_x = 0;
|
|
csr_y = 0;
|
|
move_cursor();
|
|
}
|
|
|
|
/* Puts a single character on the screen */
|
|
void Console::putch(const char _c){
|
|
|
|
|
|
/* Handle a backspace, by moving the cursor back one space */
|
|
if(_c == 0x08)
|
|
{
|
|
if(csr_x != 0) csr_x--;
|
|
}
|
|
/* Handles a tab by incrementing the cursor's x, but only
|
|
* to a point that will make it divisible by 8 */
|
|
else if(_c == 0x09)
|
|
{
|
|
csr_x = (csr_x + 8) & ~(8 - 1);
|
|
}
|
|
/* Handles a 'Carriage Return', which simply brings the
|
|
* cursor back to the margin */
|
|
else if(_c == '\r')
|
|
{
|
|
csr_x = 0;
|
|
}
|
|
/* We handle our newlines the way DOS and the BIOS do: we
|
|
* treat it as if a 'CR' was also there, so we bring the
|
|
* cursor to the margin and we increment the 'y' value */
|
|
else if(_c == '\n')
|
|
{
|
|
csr_x = 0;
|
|
csr_y++;
|
|
}
|
|
/* Any character greater than and including a space, is a
|
|
* printable character. The equation for finding the index
|
|
* in a linear chunk of memory can be represented by:
|
|
* Index = [(y * width) + x] */
|
|
else if(_c >= ' ')
|
|
{
|
|
unsigned short * where = textmemptr + (csr_y * 80 + csr_x);
|
|
*where = _c | (attrib << 8); /* Character AND attributes: color */
|
|
csr_x++;
|
|
}
|
|
|
|
/* If the cursor has reached the edge of the screen's width, we
|
|
* insert a new line in there */
|
|
if(csr_x >= 80)
|
|
{
|
|
csr_x = 0;
|
|
csr_y++;
|
|
}
|
|
|
|
/* Scroll the screen if needed, and finally move the cursor */
|
|
scroll();
|
|
move_cursor();
|
|
}
|
|
|
|
/* Uses the above routine to output a string... */
|
|
void Console::puts(const char * _s) {
|
|
|
|
for (int i = 0; i < strlen(_s); i++) {
|
|
putch(_s[i]);
|
|
}
|
|
}
|
|
|
|
void Console::puti(const int _n) {
|
|
char foostr[15];
|
|
|
|
int2str(_n, foostr);
|
|
puts(foostr);
|
|
}
|
|
|
|
void Console::putui(const unsigned int _n) {
|
|
char foostr[15];
|
|
|
|
uint2str(_n, foostr);
|
|
putch('<');
|
|
puts(foostr);
|
|
putch('>');
|
|
}
|
|
|
|
|
|
/* -- COLOR CONTROL -- */
|
|
void Console::set_TextColor(const unsigned char _forecolor,
|
|
const unsigned char _backcolor) {
|
|
/* Top 4 bytes are the background, bottom 4 bytes
|
|
* are the foreground color */
|
|
attrib = (_backcolor << 4) | (_forecolor & 0x0F);
|
|
}
|
|
|