srcfile.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 2,229 行 · 第 1/5 页
C
2,229 行
boolean SrcFileProcessOnce( // CHECK WHETHER WE HAVE TO OPEN THE FILE
char *name )
{
SRCFILE old; // - existing SRCFILE
old = srcFileGetUnique( name );
if( old != NULL ) {
if( old->once_only ) {
return( TRUE );
}
if( old->guard_state == GUARD_IFNDEF ) {
if( MacroExists( old->ifndef_name, old->ifndef_len ) ) {
return( TRUE );
}
}
}
return( FALSE );
}
//---------------------------------------------------------------------------
// The following routines permit the standard SrcFile interface to be
// employed while scanning characters from a command-line buffer.
//---------------------------------------------------------------------------
void SrcFileCmdLnDummyOpen( // OPEN DUMMY FILE FOR COMMAND LINE
void )
{
SRCFILE cmd_file; // - command file
cmd_file = srcFileAlloc( NULL, NULL );
cmd_file->cmdline = TRUE;
setGuardState( GUARD_IFNDEF );
}
void SrcFileCmdLnDummyClose( // CLOSE DUMMY FILE FOR COMMAND LINE
void )
{
SRCFILE cmd_file; // - command file
cmd_file = srcFile;
SrcFileClose( FALSE );
// CarveFree( carveSrcFile, cmd_file );
}
int SrcFileCmdLnGetChar( // GET NEXT CHARACTER FOR CMD-LINE FILE
void )
{
int return_eol; // - TRUE => return end of line
int next_char; // - next character
SRCFILE sf; // - source file for command line
sf = srcFile;
if( sf->cmdlneof ) {
next_char = LCHR_EOF;
} else if( sf->cmdlneol ) {
next_char = '\n';
sf->cmdlneof = TRUE;
} else {
if( sf->ignore_swend ) {
return_eol = CmdScanBufferEnd();
} else {
return_eol = CmdScanSwEnd();
}
if( return_eol ) {
sf->cmdlneol = TRUE;
next_char = '\r';
} else {
next_char = CmdScanChar();
}
}
CurrChar = next_char;
return next_char;
}
void SrcFileTraceBack( // INDICATE SRCFILE USED IN TRACE-BACK
SRCFILE sf ) // - source-file in message
{
traced_back = sf;
}
boolean SrcFileTraceBackReqd( // DETERMINE IF MSG TRACE-BACK REQ'D
SRCFILE sf ) // - source-file in message
{
return (sf != NULL ) && ( sf != traced_back );
}
SRCFILE SrcFileTraceBackFile( // GET SRCFILE TRACED BACK
void )
{
return traced_back;
}
boolean SrcFileSame( // ARE THESE SRC FILES THE SAME FILE?
SRCFILE f1, // - src-file 1
SRCFILE f2 ) // - src-file 2
{
_FIND_ACTUAL( f1 );
_FIND_ACTUAL( f2 );
return( f1 == f2 );
}
unsigned SrcFileIndex( // GET INDEX OF THIS SRCFILE
SRCFILE sf ) // - the source file
{
return sf->index;
}
static boolean srcFileCacheClose( boolean close_all_ok )
{
SRCFILE curr;
SRCFILE last;
SRCFILE multiple_cached;
OPEN_FILE *uncache;
OPEN_FILE *active;
multiple_cached = NULL;
last = NULL;
for( curr = srcFile; curr != NULL; curr = curr->parent ) {
if( curr->uncached ) {
continue;
}
active = curr->active;
if( active == NULL ) {
continue;
}
if( active->fp == stdin ) {
continue;
}
multiple_cached = last;
last = curr;
}
if( last == NULL ) {
return( FALSE );
}
if( multiple_cached == NULL && !close_all_ok ) {
return( FALSE );
}
_FIND_ACTUAL( last );
last->uncached = TRUE;
uncache = last->active;
uncache->pos = SysTell( fileno( uncache->fp ) );
SrcFileFClose( uncache->fp );
uncache->fp = NULL;
return( TRUE );
}
static boolean recursiveIncludeDetected( char *name )
{
SRCFILE curr;
for( curr = srcFile; curr != NULL; curr = curr->parent ) {
if( ! MacroStateMatchesCurrent( &(curr->macro_state) ) ) {
/* any open before this will never match */
break;
}
if( strcmp( name, curr->name ) == 0 ) {
CErr2p( ERR_RECURSIVE_FILE_INCLUDE, name );
return( TRUE );
}
}
return( FALSE );
}
FILE *SrcFileFOpen( char *name, src_file_open kind )
{
FILE *fp;
char *mode;
static char *file_kind[] = { "rb", "r", "rb", "w", "wb" };
mode = file_kind[ kind ];
for(;;) {
fp = fopen( name, mode );
if( fp != NULL ) {
if( recursiveIncludeDetected( name ) ) {
fclose( fp );
fp = NULL;
}
break;
}
if( errno != ENOMEM && errno != ENFILE && errno != EMFILE ) break;
if( ! srcFileCacheClose( kind == SFO_SOURCE_FILE ) ) break;
}
return( fp );
}
int SrcFileFClose( FILE *fp )
{
if( fp == stdin ) return( 0 );
return( fclose( fp ) );
}
static void markFreeSrcFile( void *p )
{
SRCFILE s = p;
s->free = TRUE;
}
static void saveSrcFile( void *e, carve_walk_base *d )
{
SRCFILE sister_save;
SRCFILE parent_save;
SRCFILE unique_save;
OPEN_FILE *active_save;
char *name_save;
char *ifndef_save;
size_t name_len;
size_t ifndef_len;
SRCFILE s = e;
if( s->free ) {
return;
}
sister_save = s->sister;
s->sister = SrcFileGetIndex( sister_save );
parent_save = s->parent;
s->parent = SrcFileGetIndex( parent_save );
unique_save = s->unique;
s->unique = SrcFileGetIndex( unique_save );
active_save = s->active;
s->active = NULL;
name_save = s->name;
ifndef_save = s->ifndef_name;
name_len = 0;
if( name_save != NULL ) {
name_len = strlen( name_save ) + 1;
}
s->name = (char *) name_len;
ifndef_len = 0;
if( ifndef_save != NULL ) {
ifndef_len = s->ifndef_len + 1;
}
s->ifndef_name = (char *) ifndef_len;
PCHWriteCVIndex( d->index );
PCHWrite( s, sizeof( *s ) );
if( name_len != 0 ) {
PCHWrite( name_save, name_len );
}
if( ifndef_len != 0 ) {
PCHWrite( ifndef_save, ifndef_len );
}
s->sister = sister_save;
s->parent = parent_save;
s->unique = unique_save;
s->active = active_save;
s->name = name_save;
s->ifndef_name = ifndef_save;
}
static void writeRoDirs( void )
{
DIR_LIST *curr;
unsigned len;
RingIterBeg( roDirs, curr ) {
len = strlen( curr->name ) + 1;
PCHWriteUInt( len );
PCHWrite( curr->name, len );
} RingIterEnd( curr );
PCHWriteUInt( 0 );
}
pch_status PCHWriteSrcFiles( void )
{
SRCFILE unique_srcfiles;
cv_index terminator = CARVE_NULL_INDEX;
auto carve_walk_base dsrc;
unique_srcfiles = SrcFileGetIndex( srcFilesUnique );
PCHWrite( &unique_srcfiles, sizeof( unique_srcfiles ) );
CarveWalkAllFree( carveSrcFile, markFreeSrcFile );
CarveWalkAll( carveSrcFile, saveSrcFile, &dsrc );
PCHWriteCVIndex( terminator );
writeRoDirs();
return( PCHCB_OK );
}
static void readRoDirs( void )
{
unsigned len;
char *dirname;
auto char buff[_MAX_PATH];
for(;;) {
len = PCHReadUInt();
if( len == 0 ) break;
dirname = PCHReadLocate( buff, len );
addRoDir( dirname );
}
}
pch_status PCHReadSrcFiles( void )
{
SRCFILE unique_srcfiles;
char *buff;
size_t buff_len;
SRCFILE s;
SRCFILE n;
cv_index si;
size_t name_len;
size_t ifndef_len;
auto cvinit_t data;
// primarySrcFile will already be set properly so it is unaffected by PCH
PCHRead( &unique_srcfiles, sizeof( unique_srcfiles ) );
unique_srcfiles = SrcFileMapIndex( unique_srcfiles );
buff_len = 80;
buff = CMemAlloc( buff_len );
CarveInitStart( carveSrcFile, &data );
for(;;) {
si = PCHReadCVIndex();
if( si == CARVE_NULL_INDEX ) break;
s = CarveInitElement( &data, si );
PCHRead( s, sizeof( *s ) );
s->sister = SrcFileMapIndex( s->sister );
s->parent = SrcFileMapIndex( s->parent );
s->unique = SrcFileMapIndex( s->unique );
s->active = NULL;
s->full_name = NULL;
MacroStateClear( &(s->macro_state) );
name_len = (size_t) s->name;
if( name_len != 0 ) {
if( name_len > buff_len ) {
CMemFree( buff );
buff_len = name_len;
buff = CMemAlloc( buff_len );
}
PCHRead( buff, name_len );
s->name = FNameAdd( buff );
} else {
s->name = NULL;
}
ifndef_len = (size_t) s->ifndef_name;
if( ifndef_len != 0 ) {
if( ifndef_len > buff_len ) {
CMemFree( buff );
buff_len = ifndef_len;
buff = CMemAlloc( buff_len );
}
PCHRead( buff, ifndef_len );
s->ifndef_name = strpermsave( buff );
} else {
s->ifndef_name = NULL;
}
}
for( s = unique_srcfiles; s != NULL; s = n ) {
n = s->unique;
if( ! IsSrcFilePrimary( s ) ) {
srcFileAddUnique( s );
}
}
CMemFree( buff );
readRoDirs();
return( PCHCB_OK );
}
SRCFILE SrcFileGetIndex( SRCFILE e )
{
return( CarveGetIndex( carveSrcFile, e ) );
}
SRCFILE SrcFileMapIndex( SRCFILE e )
{
return( CarveMapIndex( carveSrcFile, e ) );
}
pch_status PCHInitSrcFiles( boolean writing )
{
cv_index n;
if( writing ) {
n = CarveLastValidIndex( carveSrcFile );
PCHWriteCVIndex( n );
} else {
alternateCarveSrcFile = carveSrcFile;
carveSrcFile = CarveCreate( sizeof( *srcFile ), BLOCK_SRCFILE );
n = PCHReadCVIndex();
CarveMapOptimize( carveSrcFile, n );
}
return( PCHCB_OK );
}
pch_status PCHFiniSrcFiles( boolean writing )
{
if( !writing ) {
carve_t tmp;
tmp = carveSrcFile;
carveSrcFile = alternateCarveSrcFile;
CarveMapUnoptimize( tmp );
alternateCarveSrcFile = tmp;
}
return( PCHCB_OK );
}
void SrcFileSetTab( unsigned tab )
{
switch( tab ) {
case 1:
case 2:
case 4:
case 8:
case 16:
tabWidth = tab;
break;
}
}
void SrcFileOnceOnly( // CURRENT SRCFILE CAN BE SKIPPED IF #INCLUDE AGAIN
void )
{
SRCFILE srcfile; // - current source file
srcfile = srcFile;
if( srcfile != NULL ) {
srcfile->once_only = TRUE;
}
}
void SrcFileSetSwEnd( // SET CURRENT SRCFILE IGNORE CMDLINE SW END STATUS
boolean val ) // - value to use to set status
{
SRCFILE srcfile; // - current source file
srcfile = srcFile;
if( srcfile != NULL && srcfile->cmdline ) {
if( val ) {
srcfile->ignore_swend = TRUE;
} else {
srcfile->ignore_swend = FALSE;
}
}
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?