📄 console.cpp
字号:
{
Data[0] = (*ConReadMem)( ConBaseAddr+ConWriteStartAddr[ConContext]+(i*ConWriteUnitSize[ConContext]), ConWriteUnitSize[ConContext] );
switch ( ConWriteUnitSize[ConContext] )
{
default:
case 1: printf("%08lX: %02lX \'",ConWriteStartAddr[ConContext]+(i*ConWriteUnitSize[ConContext]),Data[0]); break;
case 2: printf("%08lX: %04lX \'",ConWriteStartAddr[ConContext]+(i*ConWriteUnitSize[ConContext]),Data[0]); break;
case 4: printf("%08lX: %08lX \'",ConWriteStartAddr[ConContext]+(i*ConWriteUnitSize[ConContext]),Data[0]); break;
}
ConPrintCharData( &(Data[0]), ConWriteUnitSize[ConContext] );
printf( "\'>" );
for ( ci=progress=0,Str[0]='\0'; progress==0; )
{
switch ( Str[ci] = (char)getch() )
{
case '\r': // CR
case '\n': // LF
case ' ': // SPACE
case '\t': // TAB
// Go to next location.
progress = 1;
break;
case '-': // MINUS
// Go to previous location.
putch( Str[ci] );
progress = -1;
break;
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
// Only hex values are supported.
putch( Str[ci++] );
break;
case 8: // BACKSPACE
if ( ci > 0 )
{
putch( 8 );
putch( ' ' );
putch( 8 );
ci--;
}
break;
case 'q': // Q
case 'Q': // Q
case '.': // PERIOD
// Exit MODIFY mode.
putch( Str[ci] );
progress = 1;
exit = 1;
i--;
break;
default:
// All other characters are not supported.
putch( '\a' ); // Ring bell.
break;
}
}
putch( '\n' );
Str[ci] = '\0';
if ( !exit && ci>0 )
{
UInt32 UserValue;
ConParseNumber( Str, 16, &UserValue );
(*ConWriteMem)( ConBaseAddr+ConWriteStartAddr[ConContext]+(i*ConWriteUnitSize[ConContext]), UserValue, ConWriteUnitSize[ConContext] );
}
if ( progress != 0 )
i += progress;
}
ConWriteLen[ConContext] = (i * ConWriteUnitSize[ConContext]);
}
ConWriteStartAddr[ConContext] += ConWriteLen[ConContext];
return TRUE;
}
int ConParseCommand( char* Str, int DefaultNumBytes, int* pUnitSize )
//
// This function checks the given Str and verifies that it follows
// the typical single digit command optionally suffixed with a unit size.
// For instance, the Dump command could be one of the following:
// "D", "D8", "D16", "D32".
// If the command is not followed by a number, then it will return the
// DefaultNumBytes passed in.
//
// PARAMETERS:
//
// Str [in] - The command name to verify.
// DefaultNumBytes [in] - This will be used if no unit size is specified.
// pUnitSize [out] - The number of bytes the command prefers.
// Return Value [out] - Zero (0) if successful.
//
{
UInt32 Value;
int iN = ConParseCommandLen( Str );
if ( iN == 0 )
*pUnitSize = DefaultNumBytes;
else
switch ( Str[iN] )
{
case '\0':
*pUnitSize = DefaultNumBytes;
break;
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
if ( ConParseNumber(Str+iN,10,&Value) )
return -1; // ERROR: Not a number.
if ( Value==0 || (Value%8) )
return -1; // ERROR: Only support multiples of 8.
*pUnitSize = Value / 8;
break;
default:
return -1; // ERROR: This isn't the right command.
}
return 0; // SUCCESS
}
int ConParseCommandLen( char* Str )
//
// This function returns the character length of the command name portion of
// Str. For instance, the Dump command could be one of the following:
// "D", "D8", "D16", "D32".
// In that case, the value 1 will be returned.
//
// PARAMETERS:
//
// Str [in] - The command name to verify.
// Return Value [out] - Length of command name.
//
{
int i;
for ( i=0; Str[i]!='\0'; i++ )
{
switch ( Str[i] )
{
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
case ' ': case '\t':
return i;
break;
default:
break;
}
}
return i;
}
int ConParseStartAddr( char* Str, UInt32 DefaultAddr, UInt32 OldLen, UInt32* pStartAddr )
//
// This function processes the given Str as a StartAddr term.
//
// PARAMETERS:
//
// Str [in] - Term that represents StartAddr.
// DefaultAddr [in] - If term wasn't given, this value is returned.
// OldLen [in] - Len range that was used in a previous command.
// pStartAddr [out] - Start address.
// Return Value [out] - Zero (0) if successful.
//
{
switch ( Str[0] )
{
case '\0':
*pStartAddr = DefaultAddr;
break;
case '.': // Use old StartAddr.
if ( Str[1] == '.' )
OldLen *= 2; // Wants prior to old StartAddr.
if ( OldLen > DefaultAddr )
*pStartAddr = 0;
else
*pStartAddr = DefaultAddr - OldLen;
break;
default:
if ( ConParseNumber(Str,16,pStartAddr) )
return -1; // FAILURE
break;
}
return 0; // SUCCESS
}
int ConParseLen( char* Str, UInt32 StartAddr, int UnitSize, UInt32 DefaultLen, UInt32* pLen )
//
// This function processes the given Str as a EndAddr|Len term.
//
// PARAMETERS:
//
// Str [in] - Term that represents EndAddr|Len.
// StartAddr [in] - If this term is an EndAddr, then this function
// will return (StartAddr-EndAddr).
// UnitSize [in] - Unit size (#bytes) you want the return value.
// DefaultLen [in] - If term is =='.', this value is returned.
// pLen [out] - Len.
// Return Value [out] - Zero (0) if successful.
//
{
UInt32 EndAddr;
switch ( Str[0] )
{
case '\0':
// No param was given.
*pLen = DefaultLen;
break;
case '.':
*pLen = DefaultLen;
break;
case 'l':
case 'L':
if ( ConParseNumber(Str+1,16,pLen) )
return -1; // FAILURE
*pLen *= UnitSize;
break;
default:
if ( ConParseNumber(Str,16,&EndAddr) )
return -1; // FAILURE
if ( EndAddr < StartAddr )
*pLen = 0;
*pLen = EndAddr - StartAddr + 1;
break;
}
return 0;
}
int ConParseNumber( char* Str, int DefaultRadix, UInt32* pNumber )
//
// This function processes the given Str as a number term.
//
// PARAMETERS:
//
// Str [in] - Term that represents the number.
// DefaultRadix [in] - If a radix prefix isn't given, this base is used.
// pNumber [out] - The number parsed from Str.
// Return Value [out] - Zero (0) if successful.
//
{
UInt32 RadixUsed;
if ( isnumber(Str,strlen(Str),DefaultRadix,&RadixUsed) )
{
*pNumber = atoi32( Str, RadixUsed );
return 0; // SUCCESS
}
if ( ConScript )
return ConScript( Str, strlen(Str), pNumber );
return -1; // FAILURE
}
int ConParseData( arglist* pArgs, int* pnArgs, int DefaultRadix, int argstart, int argc, argvtype argv )
//
// Given a start position in argv, this function treats all following
// terms as DATA values and returns them into a provided array.
//
// PARAMETERS:
//
// pArgs [out] - An array of UInt32s that will contain end result.
// pnArgs [out] - The number of DATA values found.
// argstart [in] - The first data term in argv.
// argc [in] - Standard argc.
// argv [in] - Standard argv.
// Return Value [out] - Zero (0) if successful. On failure, this value
// will be the index of argv that failed. For
// instance, 3 means the 3rd (absolute) arg failed.
//
{
int argi;
*pnArgs = 0;
for ( argi=argstart; argi<argc && *pnArgs<arglistlen; argi++ )
{
if ( argv[argi][0]=='\"' || argv[argi][0]=='\'' )
{
int i=1;
while ( argv[argi][i]!=argv[argi][0] && argv[argi][i]!='\0' && *pnArgs<arglistlen )
{
if ( argv[argi][i] == '\\' )
{
i++;
switch ( argv[argi][i] )
{
case '0':
(*pArgs)[(*pnArgs)++] = (UInt32)'\0';
break;
case 'a':
(*pArgs)[(*pnArgs)++] = (UInt32)'\a';
break;
case 'b':
(*pArgs)[(*pnArgs)++] = (UInt32)'\b';
break;
case 'r':
(*pArgs)[(*pnArgs)++] = (UInt32)'\r';
break;
case 'n':
(*pArgs)[(*pnArgs)++] = (UInt32)'\n';
break;
case 't':
(*pArgs)[(*pnArgs)++] = (UInt32)'\t';
break;
default:
(*pArgs)[(*pnArgs)++] = (UInt32)argv[argi][i];
break;
}
}
else
(*pArgs)[(*pnArgs)++] = (UInt32)argv[argi][i];
i++;
}
if ( (argv[argi][i+1]!=' '||argv[argi][i+1]!='\t') && argv[argi][i+1]!='\0' )
return argi; // FAILURE: the string ends with other characters, ie. "text"junk
}
else
{
if ( ConParseNumber(argv[argi],DefaultRadix,&((*pArgs)[(*pnArgs)++])) )
return argi; // FAILURE: not a proper number.
}
}
return 0; // SUCCESS
}
static void ConPrintCharData( UInt32* pData, int UnitSize )
//
// Prints a character visual representation of the Value given.
//
// PARAMETERS:
//
// pData [in] - Memory to start displaying.
// UnitSize [in] - Number of bytes to display.
//
{
int i;
for ( i=0; i<UnitSize; i++ )
{
UInt8 c = (UInt8)( (pData[0]>>(i*4)) & 0xFF );
printf( "%c", (char)((c<32||c>126)?'.':c) );
}
}
UInt32 ConReadTradMemory( UInt32 Addr, int UnitSize )
//
// A workhorse method used to read from traditional memory.
//
{
UInt32 RetVal = 0;
switch ( UnitSize )
{
default:
case 1: RetVal = (UInt32)( *(pUInt8)(Addr) ); break;
case 2: RetVal = (UInt32)( *(pUInt16)(Addr) ); break;
case 4: RetVal = (UInt32)( *(pUInt32)(Addr) ); break;
}
return RetVal;
}
void ConWriteTradMemory( UInt32 Addr, UInt32 Data, int UnitSize )
//
// A workhorse method used to write to traditional memory.
//
{
switch ( UnitSize )
{
default:
case 1: *(pUInt8)(Addr) = (UInt8)Data; break;
case 2: *(pUInt16)(Addr) = (UInt16)Data; break;
case 4: *(pUInt32)(Addr) = (UInt32)Data; break;
}
}
Boolean ConNextLine( int iLine, int Halt )
//
// A workhorse method used to halt the display whenever iLine==Halt.
// NOTE: iLine must be 1-Based.
//
{
int ch;
if ( Halt && (iLine%Halt)==0 )
{
int i, len;
len = printf( "-- more -- [ESC to exit]" );
ch = getch( );
if (ch == 0)
ch = getch( ); // get extended character
for ( i=0; i<len; i++ )
{
putch( 8 );
putch( ' ' );
putch( 8 );
}
if (ch == ESC)
return FALSE;
else
return TRUE;
}
return TRUE;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -