📄 xsc.cpp
字号:
g_iGenerateXSE = TRUE;
// Initialize the source code list
InitLinkedList ( & g_SourceCode );
// Initialize the tables
InitLinkedList ( & g_FuncTable );
InitLinkedList ( & g_SymbolTable );
InitLinkedList ( & g_StringTable );
}
/******************************************************************************************
*
* ShutDown ()
*
* Shuts down the compiler.
*/
void ShutDown ()
{
// Free the source code
FreeLinkedList ( & g_SourceCode );
// Free the tables
FreeLinkedList ( & g_FuncTable );
FreeLinkedList ( & g_SymbolTable );
FreeLinkedList ( & g_StringTable );
}
/******************************************************************************************
*
* LoadSourceFile ()
*
* Loads the source file into memory.
*/
void LoadSourceFile ()
{
// ---- Open the input file
FILE * pSourceFile;
if ( ! ( pSourceFile = fopen ( g_pstrSourceFilename, "r" ) ) )
ExitOnError ( "Could not open source file for input" );
// ---- Load the source code
// Loop through each line of code in the file
while ( ! feof ( pSourceFile ) )
{
// Allocate space for the next line
char * pstrCurrLine = ( char * ) malloc ( MAX_SOURCE_LINE_SIZE + 1 );
// Clear the string buffer in case the next line is empty or invalid
pstrCurrLine [ 0 ] = '\0';
// Read the line from the file
fgets ( pstrCurrLine, MAX_SOURCE_LINE_SIZE, pSourceFile );
// Add it to the source code linked list
AddNode ( & g_SourceCode, pstrCurrLine );
}
// ---- Close the file
fclose ( pSourceFile );
}
/******************************************************************************************
*
* CompileSourceFile ()
*
* Compiles the high-level source file to its XVM assembly equivelent.
*/
void CompileSourceFile ()
{
// Add two temporary variables for evaluating expressions
g_iTempVar0SymbolIndex = AddSymbol ( TEMP_VAR_0, 1, SCOPE_GLOBAL, SYMBOL_TYPE_VAR );
g_iTempVar1SymbolIndex = AddSymbol ( TEMP_VAR_1, 1, SCOPE_GLOBAL, SYMBOL_TYPE_VAR );
// Parse the source file to create an I-code representation
ParseSourceCode ();
}
/******************************************************************************************
*
* PrintCompileStats ()
*
* Prints miscellaneous compilation stats.
*/
void PrintCompileStats ()
{
// ---- Calculate statistics
// Symbols
int iVarCount = 0,
iArrayCount = 0,
iGlobalCount = 0;
// Traverse the list to count each symbol type
for ( int iCurrSymbolIndex = 0; iCurrSymbolIndex < g_SymbolTable.iNodeCount; ++ iCurrSymbolIndex )
{
// Create a pointer to the current symbol structure
SymbolNode * pCurrSymbol = GetSymbolByIndex ( iCurrSymbolIndex );
// It's an array if the size is greater than 1
if ( pCurrSymbol->iSize > 1 )
++ iArrayCount;
// It's a variable otherwise
else
++ iVarCount;
// It's a global if it's stack index is nonnegative
if ( pCurrSymbol->iScope == 0 )
++ iGlobalCount;
}
// Instructions
int iInstrCount = 0;
// Host API Calls
int iHostAPICallCount = 0;
// Traverse the list to count each symbol type
for ( int iCurrFuncIndex = 1; iCurrFuncIndex <= g_FuncTable.iNodeCount; ++ iCurrFuncIndex )
{
// Create a pointer to the current function structure
FuncNode * pCurrFunc = GetFuncByIndex ( iCurrFuncIndex );
// Determine if the function is part of the host API
++ iHostAPICallCount;
// Add the function's I-code instructions to the running total
iInstrCount += pCurrFunc->ICodeStream.iNodeCount;
}
// Print out final calculations
printf ( "%s created successfully!\n\n", g_pstrOutputFilename );
printf ( "Source Lines Processed: %d\n", g_SourceCode.iNodeCount );
printf ( " Stack Size: " );
if ( g_ScriptHeader.iStackSize )
printf ( "%d", g_ScriptHeader.iStackSize );
else
printf ( "Default" );
printf ( "\n" );
printf ( " Priority: " );
switch ( g_ScriptHeader.iPriorityType )
{
case PRIORITY_USER:
printf ( "%dms Timeslice", g_ScriptHeader.iUserPriority );
break;
case PRIORITY_LOW:
printf ( PRIORITY_LOW_KEYWORD );
break;
case PRIORITY_MED:
printf ( PRIORITY_MED_KEYWORD );
break;
case PRIORITY_HIGH:
printf ( PRIORITY_HIGH_KEYWORD );
break;
default:
printf ( "Default" );
break;
}
printf ( "\n" );
printf ( " Instructions Emitted: %d\n", iInstrCount );
printf ( " Variables: %d\n", iVarCount );
printf ( " Arrays: %d\n", iArrayCount );
printf ( " Globals: %d\n", iGlobalCount);
printf ( " String Literals: %d\n", g_StringTable.iNodeCount );
printf ( " Host API Calls: %d\n", iHostAPICallCount );
printf ( " Functions: %d\n", g_FuncTable.iNodeCount );
printf ( " _Main () Present: " );
if ( g_ScriptHeader.iIsMainFuncPresent )
printf ( "Yes (Index %d)\n", g_ScriptHeader.iMainFuncIndex );
else
printf ( "No\n" );
printf ( "\n" );
}
/******************************************************************************************
*
* AssmblOutputFile ()
*
* Invokes the XASM assembler to create an executable .XSE file from the resulting .XASM
* assembly file.
*/
void AssmblOutputFile ()
{
// Command-line parameters to pass to XASM
char * ppstrCmmndLineParams [ 3 ];
// Set the first parameter to "XASM" (not that it really matters)
ppstrCmmndLineParams [ 0 ] = ( char * ) malloc ( strlen ( "XASM" ) + 1 );
strcpy ( ppstrCmmndLineParams [ 0 ], "XASM" );
// Copy the .XASM filename into the second parameter
ppstrCmmndLineParams [ 1 ] = ( char * ) malloc ( strlen ( g_pstrOutputFilename ) + 1 );
strcpy ( ppstrCmmndLineParams [ 1 ], g_pstrOutputFilename );
// Set the third parameter to NULL
ppstrCmmndLineParams [ 2 ] = NULL;
// Invoke the assembler
spawnv ( P_WAIT, "XASM.exe", ppstrCmmndLineParams );
// Free the command-line parameters
free ( ppstrCmmndLineParams [ 0 ] );
free ( ppstrCmmndLineParams [ 1 ] );
}
/******************************************************************************************
*
* Exit ()
*
* Exits the program.
*/
void Exit ()
{
// Give allocated resources a chance to be freed
ShutDown ();
// Exit the program
exit ( 0 );
}
// ---- Main ----------------------------------------------------------------------------------
main ( int argc, char * argv [] )
{
// Print the logo
PrintLogo ();
// Validate the command line argument count
if ( argc < 2 )
{
// If at least one filename isn't present, print the usage info and exit
PrintUsage ();
return 0;
}
// Verify the filenames
VerifyFilenames ( argc, argv );
// Initialize the compiler
Init ();
// Read in the command line parameters
ReadCmmndLineParams ( argc, argv );
// ---- Begin the compilation process (front end)
// Load the source file into memory
LoadSourceFile ();
// Preprocess the source file
PreprocessSourceFile ();
// ---- Compile the source code to I-code
printf ( "Compiling %s...\n\n", g_pstrSourceFilename );
CompileSourceFile ();
// ---- Emit XVM assembly from the I-code representation (back end)
EmitCode ();
// Print out compilation statistics
PrintCompileStats ();
// Free resources and perform general cleanup
ShutDown ();
// Invoke XASM to assemble the output file to create the .XSE, unless the user requests
// otherwise
if ( g_iGenerateXSE )
AssmblOutputFile ();
// Delete the output (assembly) file unless the user requested it to be preserved
if ( ! g_iPreserveOutputFile )
remove ( g_pstrOutputFilename );
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -