Author: sir_richard Date: Wed Sep 15 18:30:06 2010 New Revision: 48778 URL: http://svn.reactos.org/svn/reactos?rev=48778&view=rev Log: Patch by Anton Yarotsky: [NTOSKRNL]: Implement CmdPutString command, and add log message types. Kernel version/build, processor, and RAM, now appear on EMS screen (due to InbvDisplayString), as well as loaded drivers. Next steps are to support log entries and a flag to route debug output (a ReactOS-specific feature request).
Modified: trunk/reactos/ntoskrnl/ex/hdlsterm.c trunk/reactos/ntoskrnl/include/internal/hdl.h Modified: trunk/reactos/ntoskrnl/ex/hdlsterm.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ex/hdlsterm.c?rev=48778&r1=48777&r2=48778&view=diff ============================================================================== --- trunk/reactos/ntoskrnl/ex/hdlsterm.c [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ex/hdlsterm.c [iso-8859-1] Wed Sep 15 18:30:06 2010 @@ -20,7 +20,7 @@ VOID NTAPI HdlspSendStringAtBaud( - IN PCHAR String + IN PUCHAR String ) { /* Send every byte */ @@ -51,8 +51,8 @@ if (!HeadlessGlobals->TerminalEnabled) return STATUS_UNSUCCESSFUL; /* Cleanup the screen and reset the cursor */ - HdlspSendStringAtBaud("\x1B[2J"); - HdlspSendStringAtBaud("\x1B[H"); + HdlspSendStringAtBaud((PUCHAR)"\x1B[2J"); + HdlspSendStringAtBaud((PUCHAR)"\x1B[H"); /* Enable FIFO */ InbvPortEnableFifo(HeadlessGlobals->TerminalPort, TRUE); @@ -109,6 +109,10 @@ /* Log entries are not yet supported */ DPRINT1("FIXME: No Headless logging support\n"); + /* Allocate temporary buffer */ + HeadlessGlobals->TmpBuffer = ExAllocatePoolWithTag(NonPagedPool, 80, 'sldH'); + if (!HeadlessGlobals->TmpBuffer) return; + /* Windows seems to apply some special hacks for 9600 bps */ if (HeadlessGlobals->TerminalBaudRate == 9600) { @@ -117,6 +121,77 @@ /* Enable the terminal */ HdlspEnableTerminal(TRUE); +} + +VOID +NTAPI +HdlspPutString( + IN PUCHAR String + ) +{ + PUCHAR Dest = HeadlessGlobals->TmpBuffer; + UCHAR Char = 0; + + /* Scan each character */ + while (*String != ANSI_NULL) + { + /* Check for rotate, send existing buffer and restart from where we are */ + if (Dest >= &HeadlessGlobals->TmpBuffer[79]) + { + HeadlessGlobals->TmpBuffer[79] = ANSI_NULL; + HdlspSendStringAtBaud(HeadlessGlobals->TmpBuffer); + Dest = HeadlessGlobals->TmpBuffer; + } + else + { + /* Get the current character and check for special graphical chars */ + Char = *String; + if (Char & 0x80) + { + switch (Char) + { + case 0xB0: case 0xB3: case 0xBA: + Char = '|'; + break; + case 0xB1: case 0xDC: case 0xDD: case 0xDE: case 0xDF: + Char = '%'; + break; + case 0xB2: case 0xDB: + Char = '#'; + break; + case 0xA9: case 0xAA: case 0xBB: case 0xBC: case 0xBF: + case 0xC0: case 0xC8: case 0xC9: case 0xD9: case 0xDA: + Char = '+'; + break; + case 0xC4: + Char = '-'; + break; + case 0xCD: + Char = '='; + break; + } + } + + /* Anything else must be Unicode */ + if (Char & 0x80) + { + /* Can't do Unicode yet */ + UNIMPLEMENTED; + } + else + { + /* Add the modified char to the temporary buffer */ + *Dest++ = Char; + } + + /* Check the next char */ + String++; + } + } + + /* Finish and send */ + *Dest = ANSI_NULL; + HdlspSendStringAtBaud(HeadlessGlobals->TmpBuffer); } /* @@ -132,8 +207,107 @@ OUT PSIZE_T OutputBufferSize ) { + NTSTATUS Status = STATUS_NOT_IMPLEMENTED; + ASSERT(HeadlessGlobals != NULL); +// ASSERT(HeadlessGlobals->PageLockHandle != NULL); + + /* FIXME: This should be using the headless spinlock */ + + /* Ignore non-reentrant commands */ + if ((Command != HeadlessCmdAddLogEntry) && + (Command != HeadlessCmdStartBugCheck) && + (Command != HeadlessCmdSendBlueScreenData) && + (Command != HeadlessCmdDoBugCheckProcessing)) + { + if (HeadlessGlobals->ProcessingCmd) return STATUS_UNSUCCESSFUL; + + /* Don't allow these commands next time */ + HeadlessGlobals->ProcessingCmd = TRUE; + } + + /* Handle each command */ + switch (Command) + { + case HeadlessCmdEnableTerminal: + break; + case HeadlessCmdCheckForReboot: + break; + + case HeadlessCmdPutString: + + /* Validate the existence of an input buffer */ + if (!InputBuffer) + { + Status = STATUS_INVALID_PARAMETER; + goto Reset; + } + + /* Terminal should be on */ + if (HeadlessGlobals->TerminalEnabled) + { + /* Print each byte in the string making sure VT100 chars are used */ + PHEADLESS_CMD_PUT_STRING PutString = (PVOID)InputBuffer; + HdlspPutString(PutString->String); + } + + /* Return success either way */ + Status = STATUS_SUCCESS; + break; + case HeadlessCmdClearDisplay: + break; + case HeadlessCmdClearToEndOfDisplay: + break; + case HeadlessCmdClearToEndOfLine: + break; + case HeadlessCmdDisplayAttributesOff: + break; + case HeadlessCmdDisplayInverseVideo: + break; + case HeadlessCmdSetColor: + break; + case HeadlessCmdPositionCursor: + break; + case HeadlessCmdTerminalPoll: + break; + case HeadlessCmdGetByte: + break; + case HeadlessCmdGetLine: + break; + case HeadlessCmdStartBugCheck: + break; + case HeadlessCmdDoBugCheckProcessing: + break; + case HeadlessCmdQueryInformation: + break; + case HeadlessCmdAddLogEntry: + break; + case HeadlessCmdDisplayLog: + break; + case HeadlessCmdSetBlueScreenData: + break; + case HeadlessCmdSendBlueScreenData: + break; + case HeadlessCmdQueryGUID: + break; + case HeadlessCmdPutData: + break; + default: + break; + } + +Reset: + /* Unset prcessing state */ + if ((Command != HeadlessCmdAddLogEntry) && + (Command != HeadlessCmdStartBugCheck) && + (Command != HeadlessCmdSendBlueScreenData) && + (Command != HeadlessCmdDoBugCheckProcessing)) + { + ASSERT(HeadlessGlobals->ProcessingCmd == TRUE); + HeadlessGlobals->ProcessingCmd = FALSE; + } + //UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + return STATUS_SUCCESS; } /* EOF */ Modified: trunk/reactos/ntoskrnl/include/internal/hdl.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/include/internal/hdl.h?rev=48778&r1=48777&r2=48778&view=diff ============================================================================== --- trunk/reactos/ntoskrnl/include/internal/hdl.h [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/include/internal/hdl.h [iso-8859-1] Wed Sep 15 18:30:06 2010 @@ -31,6 +31,33 @@ #else #define HDLTRACE(x, ...) DPRINT(__VA_ARGS__) #endif + +// +// Well-known messages that Io and Pnp post to the kernel log +// +typedef enum _HEADLESS_LOG_MESSAGE +{ + HeadlessLogDriverLoad = 1, + HeadlessLogDriverSuccess, + HeadlessLogDriverFailed, + HeadlessLogEventFailed, + HeadlessLogObjectFailed, + HeadlessLogDirectoryFailed, + HeadlessLogPnpFailed, + HeadlessLogPnpFailed2, + HeadlessLogBootDriversFailed, + HeadlessLogNtdllFailed, + HeadlessLogSystemDriversFailed, + HeadlessLogReassignSystemRootFailed, + HeadlessLogProtectSystemRootFailed, + HeadlessLogConvertSystemRootFailed, + HeadlessLogConvertDeviceNameFailed, + HeadlessLogGroupOrderListFailed, + HeadlessLogGroupTableFailed + // + // There are more, but not applicable to ReactOS, I believe + // +} HEADLESS_LOG_MESSAGE; // // Headless Log Entry @@ -123,6 +150,11 @@ HeadlessCmdPutData } HEADLESS_CMD, *PHEADLESS_CMD; +typedef struct _HEADLESS_CMD_PUT_STRING +{ + UCHAR String[1]; +} HEADLESS_CMD_PUT_STRING, *PHEADLESS_CMD_PUT_STRING; + NTSTATUS NTAPI HeadlessDispatch(