1147 lines
22 KiB
C
1147 lines
22 KiB
C
//
|
||
// DISPLAY OSCHOOSE SCREENS
|
||
//
|
||
|
||
#include <nt.h>
|
||
#include <ntrtl.h>
|
||
#include <nturtl.h>
|
||
#include <ntseapi.h>
|
||
|
||
#include <windows.h>
|
||
#include <winsock.h>
|
||
|
||
#undef ERROR
|
||
|
||
#include <stdio.h>
|
||
|
||
|
||
CHAR DomainName[64];
|
||
CHAR UserName[64];
|
||
CHAR Password[64];
|
||
|
||
VOID
|
||
BiosConsoleWrite(
|
||
IN ULONG FileId,
|
||
OUT PUCHAR Buffer,
|
||
IN ULONG Length,
|
||
OUT PULONG Count
|
||
);
|
||
|
||
|
||
ULONG __cdecl
|
||
BiosConsoleGetKey(
|
||
void
|
||
);
|
||
|
||
ULONG __cdecl
|
||
BiosConsoleGetCounter(
|
||
void
|
||
);
|
||
|
||
#include "..\boot\oschoice\oscheap.c"
|
||
#define _BUILDING_OSDISP_
|
||
#include "..\boot\oschoice\parse.c"
|
||
|
||
#if DBG
|
||
ULONG NetDebugFlag =
|
||
DEBUG_ERROR |
|
||
DEBUG_OSC;
|
||
#endif
|
||
|
||
//
|
||
// This is declared and expected by parse.c, so we defined the functions
|
||
// for the macros it uses (GET_KEY and GET_COUNTER) and NULL the rest out.
|
||
//
|
||
|
||
EXTERNAL_SERVICES_TABLE ServicesTable = {
|
||
NULL, // RebootProcessor
|
||
NULL, // DiskIOSystem
|
||
BiosConsoleGetKey,
|
||
BiosConsoleGetCounter,
|
||
NULL, // Reboot
|
||
NULL, // AbiosServices
|
||
NULL, // DetectHardware
|
||
NULL, // HardwareCursor
|
||
NULL, // GetDateTime
|
||
NULL, // ComPort
|
||
NULL, // IsMcaMachine
|
||
NULL, // GetStallCount
|
||
NULL, // InitializeDisplayForNt
|
||
NULL, // GetMemoryDescriptor
|
||
NULL, // GetEddsSector
|
||
NULL, // GetElToritoStatus
|
||
NULL // GetExtendedInt13Params
|
||
};
|
||
PEXTERNAL_SERVICES_TABLE ExternalServicesTable = &ServicesTable;
|
||
|
||
//
|
||
// This is used by the ArcWrite function -- it only cares about the firmware vector
|
||
// which is the 28th entry.
|
||
//
|
||
|
||
PVOID FirmwareVector[38] = {
|
||
NULL, NULL, NULL, NULL, NULL,
|
||
NULL, NULL, NULL, NULL, NULL,
|
||
NULL, NULL, NULL, NULL, NULL,
|
||
NULL, NULL, NULL, NULL, NULL,
|
||
NULL, NULL, NULL, NULL, NULL,
|
||
NULL, NULL, (PVOID)BiosConsoleWrite, NULL, NULL,
|
||
NULL, NULL, NULL, NULL, NULL,
|
||
NULL, NULL, NULL
|
||
};
|
||
|
||
SYSTEM_PARAMETER_BLOCK GlobalSystemBlock = {
|
||
0, // Signature
|
||
0, // Length
|
||
0, // Version
|
||
0, // Revision
|
||
NULL, // RestartBlock
|
||
NULL, // DebugBlock
|
||
NULL, // GenerateExceptionVector
|
||
NULL, // TlbMissExceptionVector
|
||
sizeof(FirmwareVector),
|
||
FirmwareVector,
|
||
0, // VendorVectorLength
|
||
NULL, // VendorVector
|
||
0, // AdapterCount
|
||
0, // Adapter0Type
|
||
0, // Adapter0Length
|
||
NULL // Adapter0Vector
|
||
};
|
||
|
||
|
||
|
||
|
||
//
|
||
// Current screen position.
|
||
//
|
||
USHORT TextColumn = 0;
|
||
USHORT TextRow = 0;
|
||
|
||
//
|
||
// Height and width of the console.
|
||
//
|
||
USHORT ScreenWidthCells;
|
||
USHORT ScreenHeightCells;
|
||
|
||
//
|
||
// Current text attribute
|
||
//
|
||
UCHAR TextCurrentAttribute = 0x07; // start with white on black.
|
||
|
||
//
|
||
// Standard input and output handles.
|
||
//
|
||
HANDLE StandardInput;
|
||
HANDLE StandardOutput;
|
||
|
||
UCHAR EightySpaces[] =
|
||
" ";
|
||
|
||
//
|
||
// defines for doing console I/O
|
||
//
|
||
#define CSI 0x95
|
||
#define SGR_INVERSE 7
|
||
#define SGR_NORMAL 0
|
||
|
||
//
|
||
// static data for console I/O
|
||
//
|
||
BOOLEAN ControlSequence=FALSE;
|
||
BOOLEAN EscapeSequence=FALSE;
|
||
BOOLEAN FontSelection=FALSE;
|
||
BOOLEAN HighIntensity=FALSE;
|
||
BOOLEAN Blink=FALSE;
|
||
ULONG PCount=0;
|
||
|
||
#define CONTROL_SEQUENCE_MAX_PARAMETER 10
|
||
ULONG Parameter[CONTROL_SEQUENCE_MAX_PARAMETER];
|
||
|
||
#define KEY_INPUT_BUFFER_SIZE 16
|
||
UCHAR KeyBuffer[KEY_INPUT_BUFFER_SIZE];
|
||
ULONG KeyBufferEnd=0;
|
||
ULONG KeyBufferStart=0;
|
||
|
||
//
|
||
// array for translating between ANSI colors and the VGA standard
|
||
//
|
||
UCHAR TranslateColor[] = {0,4,2,6,1,5,3,7};
|
||
|
||
#define ASCI_ESC 0x1b
|
||
|
||
|
||
//
|
||
// Need this to link.
|
||
//
|
||
|
||
ULONG BlConsoleOutDeviceId = 0;
|
||
|
||
|
||
|
||
CHAR
|
||
BlProcessScreen(
|
||
IN PCHAR InputString,
|
||
OUT PCHAR OutputString
|
||
);
|
||
|
||
CHAR g_OutputString[1024];
|
||
|
||
int __cdecl
|
||
main (argc, argv)
|
||
int argc;
|
||
char *argv[];
|
||
{
|
||
DWORD Error;
|
||
int i;
|
||
HANDLE hFile;
|
||
DWORD fileSize, bytesRead;
|
||
PCHAR fileBuffer;
|
||
CONSOLE_SCREEN_BUFFER_INFO bufferInfo;
|
||
CONSOLE_CURSOR_INFO cursorInfo;
|
||
COORD coord;
|
||
PCHAR pszScreenName;
|
||
CHAR LastKey;
|
||
|
||
if (argc < 2) {
|
||
printf("USAGE: %s [screen-file-name]\n", argv[0]);
|
||
return -1;
|
||
}
|
||
|
||
//
|
||
// Set up the console correctly. We allocate our own and resize
|
||
// it to 80 x 25.
|
||
//
|
||
|
||
FreeConsole();
|
||
AllocConsole();
|
||
|
||
StandardInput = GetStdHandle(STD_INPUT_HANDLE);
|
||
StandardOutput = GetStdHandle(STD_OUTPUT_HANDLE);
|
||
|
||
ScreenWidthCells = 81;
|
||
ScreenHeightCells = 25;
|
||
|
||
coord.X = ScreenWidthCells;
|
||
coord.Y = ScreenHeightCells;
|
||
|
||
SetConsoleScreenBufferSize(StandardOutput, coord);
|
||
|
||
//
|
||
// This actually turns *off* most processing.
|
||
//
|
||
|
||
SetConsoleMode(StandardInput, ENABLE_PROCESSED_INPUT);
|
||
|
||
//
|
||
// Hide the cursor.
|
||
//
|
||
|
||
cursorInfo.dwSize = 1;
|
||
cursorInfo.bVisible = FALSE;
|
||
|
||
SetConsoleCursorInfo(StandardOutput, &cursorInfo);
|
||
|
||
//
|
||
// Open the first parameter as a file.
|
||
//
|
||
pszScreenName = argv[1];
|
||
|
||
NextScreen:
|
||
hFile = CreateFileA(pszScreenName, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL);
|
||
|
||
if (hFile == INVALID_HANDLE_VALUE ) {
|
||
printf("Could not open %s!\n", argv[1]);
|
||
return -1;
|
||
}
|
||
|
||
fileSize = GetFileSize(hFile, NULL);
|
||
|
||
printf("File %s is %d bytes\n", argv[1], fileSize);
|
||
|
||
fileBuffer = LocalAlloc(0, fileSize+1);
|
||
if (fileBuffer == NULL) {
|
||
printf("Allocate failed!\n");
|
||
return -1;
|
||
}
|
||
|
||
if (!ReadFile(hFile, fileBuffer, fileSize, &bytesRead, NULL)) {
|
||
printf("Read failed\n");
|
||
return -1;
|
||
}
|
||
|
||
if (bytesRead != fileSize) {
|
||
printf("Too few bytes read\n");
|
||
return -1;
|
||
}
|
||
|
||
CloseHandle(hFile);
|
||
|
||
fileBuffer[fileSize] = '\0';
|
||
|
||
LastKey = BlProcessScreen(fileBuffer, g_OutputString);
|
||
if (SpecialAction == ACTION_REFRESH)
|
||
goto NextScreen;
|
||
|
||
{
|
||
PCHAR psz = strchr( g_OutputString, '\n' );
|
||
if ( psz )
|
||
*psz = '\0';
|
||
pszScreenName = g_OutputString;
|
||
if ( strcmp( pszScreenName, "REBOOT" ) != 0
|
||
&& strcmp( pszScreenName, "LAUNCH" ) != 0 \
|
||
&& strcmp( pszScreenName, "" ) != 0 ) {
|
||
// add the extension and jump to the next screen
|
||
strcat( g_OutputString, ".osc" );
|
||
goto NextScreen;
|
||
}
|
||
}
|
||
//
|
||
// I can't figure out how to write to the old console -- so for
|
||
// now just display it and pause.
|
||
//
|
||
|
||
BlpClearScreen();
|
||
|
||
SetConsoleTextAttribute(StandardOutput, 0x7);
|
||
|
||
printf("String returned was <%s>\n", g_OutputString);
|
||
printf("Press any key to exit\n");
|
||
|
||
|
||
while (GET_KEY() == 0) {
|
||
;
|
||
}
|
||
|
||
}
|
||
|
||
|
||
|
||
VOID
|
||
TextGetCursorPosition(
|
||
OUT PULONG X,
|
||
OUT PULONG Y
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Gets the position of the soft cursor.
|
||
|
||
Arguments:
|
||
|
||
X - Receives column coordinate of where character would be written.
|
||
|
||
Y - Receives row coordinate of where next character would be written.
|
||
|
||
Returns:
|
||
|
||
Nothing.
|
||
|
||
--*/
|
||
|
||
{
|
||
*X = (ULONG)TextColumn;
|
||
*Y = (ULONG)TextRow;
|
||
}
|
||
|
||
|
||
VOID
|
||
TextSetCursorPosition(
|
||
IN ULONG X,
|
||
IN ULONG Y
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Moves the location of the software cursor to the specified X,Y position
|
||
on screen.
|
||
|
||
Arguments:
|
||
|
||
X - Supplies the X-position of the cursor
|
||
|
||
Y - Supplies the Y-position of the cursor
|
||
|
||
Return Value:
|
||
|
||
None.
|
||
|
||
--*/
|
||
|
||
{
|
||
COORD coord;
|
||
|
||
TextColumn = (USHORT)X;
|
||
TextRow = (USHORT)Y;
|
||
|
||
coord.X = (USHORT)X;
|
||
coord.Y = (USHORT)Y;
|
||
|
||
SetConsoleCursorPosition(StandardOutput, coord);
|
||
}
|
||
|
||
|
||
VOID
|
||
TextSetCurrentAttribute(
|
||
IN UCHAR Attribute
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Sets the character attribute to be used for subsequent text display.
|
||
|
||
Arguments:
|
||
|
||
Returns:
|
||
|
||
Nothing.
|
||
|
||
--*/
|
||
|
||
{
|
||
TextCurrentAttribute = Attribute;
|
||
|
||
SetConsoleTextAttribute(StandardOutput, Attribute);
|
||
}
|
||
|
||
|
||
UCHAR
|
||
TextGetCurrentAttribute(
|
||
VOID
|
||
)
|
||
{
|
||
return(TextCurrentAttribute);
|
||
}
|
||
|
||
|
||
PUCHAR
|
||
TextCharOut(
|
||
IN PUCHAR pc
|
||
)
|
||
{
|
||
DWORD numWritten;
|
||
|
||
WriteConsoleA(StandardOutput, pc, 1, &numWritten, NULL);
|
||
|
||
return(pc+1);
|
||
}
|
||
|
||
|
||
VOID
|
||
TextClearToEndOfLine(
|
||
VOID
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Clears from the current cursor position to the end of the line
|
||
by writing blanks with the current video attribute.
|
||
|
||
Arguments:
|
||
|
||
None
|
||
|
||
Returns:
|
||
|
||
Nothing
|
||
|
||
|
||
--*/
|
||
|
||
{
|
||
unsigned u;
|
||
ULONG OldX,OldY;
|
||
UCHAR temp;
|
||
|
||
//
|
||
// Fill with blanks up to char before cursor position.
|
||
//
|
||
temp = ' ';
|
||
TextGetCursorPosition(&OldX,&OldY);
|
||
for(u=TextColumn; u<ScreenWidthCells; u++) {
|
||
TextCharOut(&temp);
|
||
}
|
||
TextSetCursorPosition(OldX,OldY);
|
||
}
|
||
|
||
|
||
VOID
|
||
TextClearFromStartOfLine(
|
||
VOID
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Clears from the start of the line to the current cursor position
|
||
by writing blanks with the current video attribute.
|
||
The cursor position is not changed.
|
||
|
||
Arguments:
|
||
|
||
None
|
||
|
||
Returns:
|
||
|
||
Nothing
|
||
|
||
--*/
|
||
|
||
{
|
||
unsigned u;
|
||
ULONG OldX,OldY;
|
||
UCHAR temp = ' ';
|
||
|
||
//
|
||
// Fill with blanks up to char before cursor position.
|
||
//
|
||
TextGetCursorPosition(&OldX,&OldY);
|
||
TextSetCursorPosition(0,OldY);
|
||
for(u=0; u<TextColumn; u++) {
|
||
TextCharOut(&temp);
|
||
}
|
||
TextSetCursorPosition(OldX,OldY);
|
||
}
|
||
|
||
VOID
|
||
TextClearToEndOfDisplay(
|
||
VOID
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Clears from the current cursor position to the end of the video
|
||
display by writing blanks with the current video attribute.
|
||
The cursor position is not changed.
|
||
|
||
Arguments:
|
||
|
||
None
|
||
|
||
Returns:
|
||
|
||
Nothing
|
||
|
||
--*/
|
||
|
||
{
|
||
USHORT x,y;
|
||
ULONG OldX,OldY;
|
||
DWORD numWritten;
|
||
|
||
TextGetCursorPosition(&OldX,&OldY);
|
||
|
||
//
|
||
// Clear current line
|
||
//
|
||
TextClearToEndOfLine();
|
||
|
||
//
|
||
// Clear the remaining lines
|
||
//
|
||
|
||
for(y=TextRow+1; y<ScreenHeightCells; y++) {
|
||
|
||
TextSetCursorPosition(0, y);
|
||
WriteConsoleA(StandardOutput, EightySpaces, ScreenWidthCells, &numWritten, NULL);
|
||
|
||
}
|
||
|
||
TextSetCursorPosition(OldX,OldY);
|
||
}
|
||
|
||
|
||
VOID
|
||
TextClearDisplay(
|
||
VOID
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Clears the video display and positions the cursor
|
||
at the upper left corner of the screen (0,0).
|
||
|
||
Arguments:
|
||
|
||
None
|
||
|
||
Returns:
|
||
|
||
Nothing
|
||
|
||
--*/
|
||
|
||
{
|
||
USHORT y;
|
||
DWORD numWritten;
|
||
|
||
//
|
||
// Clear screen.
|
||
//
|
||
for(y=0; y<ScreenHeightCells; y++) {
|
||
|
||
TextSetCursorPosition(0, y);
|
||
WriteConsoleA(StandardOutput, EightySpaces, ScreenWidthCells, &numWritten, NULL);
|
||
|
||
}
|
||
TextSetCursorPosition(0,0);
|
||
}
|
||
|
||
|
||
|
||
//
|
||
// This function was stolen from ..\lib\i386\biosdrv.c (except the return
|
||
// type was changed to VOID).
|
||
//
|
||
|
||
VOID
|
||
BiosConsoleWrite(
|
||
IN ULONG FileId,
|
||
OUT PUCHAR Buffer,
|
||
IN ULONG Length,
|
||
OUT PULONG Count
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Outputs to the console. (In this case, the VGA display)
|
||
|
||
Arguments:
|
||
|
||
FileId - Supplies the FileId to be written (should always be 1 for this
|
||
function)
|
||
|
||
Buffer - Supplies characters to be output
|
||
|
||
Length - Supplies the length of the buffer (in bytes)
|
||
|
||
Count - Returns the actual number of bytes written
|
||
|
||
Return Value:
|
||
|
||
ESUCCESS - Console write completed succesfully.
|
||
|
||
--*/
|
||
{
|
||
ARC_STATUS Status;
|
||
PUCHAR String;
|
||
ULONG Index;
|
||
UCHAR a;
|
||
PUCHAR p;
|
||
|
||
//
|
||
// Process each character in turn.
|
||
//
|
||
|
||
Status = ESUCCESS;
|
||
String = (PUCHAR)Buffer;
|
||
|
||
for ( *Count = 0 ;
|
||
*Count < Length ;
|
||
(*Count)++, String++ ) {
|
||
|
||
//
|
||
// If we're in the middle of a control sequence, continue scanning,
|
||
// otherwise process character.
|
||
//
|
||
|
||
if (ControlSequence) {
|
||
|
||
//
|
||
// If the character is a digit, update parameter value.
|
||
//
|
||
|
||
if ((*String >= '0') && (*String <= '9')) {
|
||
Parameter[PCount] = Parameter[PCount] * 10 + *String - '0';
|
||
continue;
|
||
}
|
||
|
||
//
|
||
// If we are in the middle of a font selection sequence, this
|
||
// character must be a 'D', otherwise reset control sequence.
|
||
//
|
||
|
||
if (FontSelection) {
|
||
|
||
//if (*String == 'D') {
|
||
//
|
||
// //
|
||
// // Other fonts not implemented yet.
|
||
// //
|
||
//
|
||
//} else {
|
||
//}
|
||
|
||
ControlSequence = FALSE;
|
||
FontSelection = FALSE;
|
||
continue;
|
||
}
|
||
|
||
switch (*String) {
|
||
|
||
//
|
||
// If a semicolon, move to the next parameter.
|
||
//
|
||
|
||
case ';':
|
||
|
||
PCount++;
|
||
if (PCount > CONTROL_SEQUENCE_MAX_PARAMETER) {
|
||
PCount = CONTROL_SEQUENCE_MAX_PARAMETER;
|
||
}
|
||
Parameter[PCount] = 0;
|
||
break;
|
||
|
||
//
|
||
// If a 'J', erase part or all of the screen.
|
||
//
|
||
|
||
case 'J':
|
||
|
||
switch (Parameter[0]) {
|
||
case 0:
|
||
//
|
||
// Erase to end of the screen
|
||
//
|
||
TextClearToEndOfDisplay();
|
||
break;
|
||
|
||
case 1:
|
||
//
|
||
// Erase from the beginning of the screen
|
||
//
|
||
break;
|
||
|
||
default:
|
||
//
|
||
// Erase entire screen
|
||
//
|
||
TextClearDisplay();
|
||
break;
|
||
}
|
||
|
||
ControlSequence = FALSE;
|
||
break;
|
||
|
||
//
|
||
// If a 'K', erase part or all of the line.
|
||
//
|
||
|
||
case 'K':
|
||
|
||
switch (Parameter[0]) {
|
||
|
||
//
|
||
// Erase to end of the line.
|
||
//
|
||
|
||
case 0:
|
||
TextClearToEndOfLine();
|
||
break;
|
||
|
||
//
|
||
// Erase from the beginning of the line.
|
||
//
|
||
|
||
case 1:
|
||
TextClearFromStartOfLine();
|
||
break;
|
||
|
||
//
|
||
// Erase entire line.
|
||
//
|
||
|
||
default :
|
||
TextClearFromStartOfLine();
|
||
TextClearToEndOfLine();
|
||
break;
|
||
}
|
||
|
||
ControlSequence = FALSE;
|
||
break;
|
||
|
||
//
|
||
// If a 'H', move cursor to position.
|
||
//
|
||
|
||
case 'H':
|
||
TextSetCursorPosition(Parameter[1]-1, Parameter[0]-1);
|
||
ControlSequence = FALSE;
|
||
break;
|
||
|
||
//
|
||
// If a ' ', could be a FNT selection command.
|
||
//
|
||
|
||
case ' ':
|
||
FontSelection = TRUE;
|
||
break;
|
||
|
||
case 'm':
|
||
//
|
||
// Select action based on each parameter.
|
||
//
|
||
// Blink and HighIntensity are by default disabled
|
||
// each time a new SGR is specified, unless they are
|
||
// explicitly specified again, in which case these
|
||
// will be set to TRUE at that time.
|
||
//
|
||
|
||
HighIntensity = FALSE;
|
||
Blink = FALSE;
|
||
|
||
for ( Index = 0 ; Index <= PCount ; Index++ ) {
|
||
switch (Parameter[Index]) {
|
||
|
||
//
|
||
// Attributes off.
|
||
//
|
||
|
||
case 0:
|
||
TextSetCurrentAttribute(7);
|
||
HighIntensity = FALSE;
|
||
Blink = FALSE;
|
||
break;
|
||
|
||
//
|
||
// High Intensity.
|
||
//
|
||
|
||
case 1:
|
||
TextSetCurrentAttribute(0xf);
|
||
HighIntensity = TRUE;
|
||
break;
|
||
|
||
//
|
||
// Underscored.
|
||
//
|
||
|
||
case 4:
|
||
break;
|
||
|
||
//
|
||
// Blink.
|
||
//
|
||
|
||
case 5:
|
||
TextSetCurrentAttribute(0x87);
|
||
Blink = TRUE;
|
||
break;
|
||
|
||
//
|
||
// Reverse Video.
|
||
//
|
||
|
||
case 7:
|
||
TextSetCurrentAttribute(0x70);
|
||
HighIntensity = FALSE;
|
||
Blink = FALSE;
|
||
break;
|
||
|
||
//
|
||
// Font selection, not implemented yet.
|
||
//
|
||
|
||
case 10:
|
||
case 11:
|
||
case 12:
|
||
case 13:
|
||
case 14:
|
||
case 15:
|
||
case 16:
|
||
case 17:
|
||
case 18:
|
||
case 19:
|
||
break;
|
||
|
||
//
|
||
// Foreground Color
|
||
//
|
||
|
||
case 30:
|
||
case 31:
|
||
case 32:
|
||
case 33:
|
||
case 34:
|
||
case 35:
|
||
case 36:
|
||
case 37:
|
||
a = TextGetCurrentAttribute();
|
||
a &= 0x70;
|
||
a |= TranslateColor[Parameter[Index]-30];
|
||
if (HighIntensity) {
|
||
a |= 0x08;
|
||
}
|
||
if (Blink) {
|
||
a |= 0x80;
|
||
}
|
||
TextSetCurrentAttribute(a);
|
||
break;
|
||
|
||
//
|
||
// Background Color
|
||
//
|
||
|
||
case 40:
|
||
case 41:
|
||
case 42:
|
||
case 43:
|
||
case 44:
|
||
case 45:
|
||
case 46:
|
||
case 47:
|
||
a = TextGetCurrentAttribute();
|
||
a &= 0x8f;
|
||
a |= TranslateColor[Parameter[Index]-40] << 4;
|
||
TextSetCurrentAttribute(a);
|
||
break;
|
||
|
||
default:
|
||
break;
|
||
}
|
||
}
|
||
|
||
default:
|
||
ControlSequence = FALSE;
|
||
break;
|
||
}
|
||
|
||
//
|
||
// This is not a control sequence, check for escape sequence.
|
||
//
|
||
|
||
} else {
|
||
|
||
//
|
||
// If escape sequence, check for control sequence, otherwise
|
||
// process single character.
|
||
//
|
||
|
||
if (EscapeSequence) {
|
||
|
||
//
|
||
// Check for '[', means control sequence, any other following
|
||
// character is ignored.
|
||
//
|
||
|
||
if (*String == '[') {
|
||
|
||
ControlSequence = TRUE;
|
||
|
||
//
|
||
// Initialize first parameter.
|
||
//
|
||
|
||
PCount = 0;
|
||
Parameter[0] = 0;
|
||
}
|
||
EscapeSequence = FALSE;
|
||
|
||
//
|
||
// This is not a control or escape sequence, process single character.
|
||
//
|
||
|
||
} else {
|
||
|
||
switch (*String) {
|
||
//
|
||
// Check for escape sequence.
|
||
//
|
||
|
||
case ASCI_ESC:
|
||
EscapeSequence = TRUE;
|
||
break;
|
||
|
||
default:
|
||
p = TextCharOut(String);
|
||
//
|
||
// Each pass through the loop increments String by 1.
|
||
// If we output a dbcs char we need to increment by
|
||
// one more.
|
||
//
|
||
(*Count) += (p - String) - 1;
|
||
String += (p - String) - 1;
|
||
break;
|
||
}
|
||
|
||
}
|
||
}
|
||
}
|
||
return;
|
||
}
|
||
|
||
|
||
ULONG __cdecl
|
||
BiosConsoleGetKey(
|
||
VOID
|
||
)
|
||
{
|
||
INPUT_RECORD inputRecord;
|
||
DWORD numRead;
|
||
|
||
//
|
||
// Loop until we see a key event or nothing.
|
||
//
|
||
|
||
while (TRUE) {
|
||
|
||
PeekConsoleInput(
|
||
StandardInput,
|
||
&inputRecord,
|
||
1,
|
||
&numRead);
|
||
|
||
if (numRead == 0) {
|
||
|
||
//
|
||
// We read nothing -- sleep for a bit (since callers tend to loop
|
||
// calling this) and return.
|
||
//
|
||
|
||
Sleep(100);
|
||
return 0;
|
||
}
|
||
|
||
ReadConsoleInput(
|
||
StandardInput,
|
||
&inputRecord,
|
||
1,
|
||
&numRead);
|
||
|
||
if (inputRecord.EventType != KEY_EVENT) {
|
||
continue;
|
||
}
|
||
|
||
//
|
||
// We had a key event -- process the key down ones.
|
||
//
|
||
|
||
if (inputRecord.Event.KeyEvent.bKeyDown) {
|
||
|
||
//
|
||
// Construct the correct scancode/ASCII value combination.
|
||
//
|
||
|
||
//
|
||
// HACK: shift-tab needs to be special-cased for some reason.
|
||
//
|
||
|
||
if ((inputRecord.Event.KeyEvent.uChar.AsciiChar == 0x09) &&
|
||
((inputRecord.Event.KeyEvent.dwControlKeyState & SHIFT_PRESSED) != 0)) {
|
||
|
||
return 0x0f00;
|
||
|
||
} else {
|
||
|
||
return
|
||
(((inputRecord.Event.KeyEvent.wVirtualScanCode) & 0xff) << 8) +
|
||
inputRecord.Event.KeyEvent.uChar.AsciiChar;
|
||
|
||
}
|
||
|
||
}
|
||
|
||
}
|
||
|
||
}
|
||
|
||
ULONG __cdecl
|
||
BiosConsoleGetCounter(
|
||
VOID
|
||
)
|
||
{
|
||
//
|
||
// GetTickCount is in milliseconds, we want an 18.2/sec counter
|
||
//
|
||
|
||
return (GetTickCount() * 182) / 10000;
|
||
|
||
}
|
||
|
||
|
||
|
||
//
|
||
// These two functions were taken from ..\lib\regboot.c.
|
||
//
|
||
VOID
|
||
BlpPositionCursor(
|
||
IN ULONG Column,
|
||
IN ULONG Row
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Sets the position of the cursor on the screen.
|
||
|
||
Arguments:
|
||
|
||
Column - supplies new Column for the cursor position.
|
||
|
||
Row - supplies new Row for the cursor position.
|
||
|
||
Return Value:
|
||
|
||
None.
|
||
|
||
--*/
|
||
|
||
{
|
||
CHAR Buffer[16];
|
||
ULONG Count;
|
||
|
||
sprintf(Buffer, ASCI_CSI_OUT "%d;%dH", Row, Column);
|
||
|
||
PRINTL(Buffer);
|
||
|
||
}
|
||
|
||
|
||
VOID
|
||
BlpClearScreen(
|
||
VOID
|
||
)
|
||
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Clears the screen.
|
||
|
||
Arguments:
|
||
|
||
None
|
||
|
||
Return Value:
|
||
|
||
None.
|
||
|
||
--*/
|
||
|
||
{
|
||
CHAR Buffer[16];
|
||
ULONG Count;
|
||
|
||
sprintf(Buffer, ASCI_CSI_OUT "2J");
|
||
|
||
PRINTL(Buffer);
|
||
|
||
}
|
||
|