More work on instancing the parser

This commit is contained in:
ridiculousfish 2012-01-19 10:28:44 -08:00
parent fa796d668f
commit 3d8face1f9
5 changed files with 49 additions and 37 deletions

View file

@ -2714,7 +2714,7 @@ static int builtin_cd( parser_t &parser, wchar_t **argv )
Implementation of the builtin count command, used to count the Implementation of the builtin count command, used to count the
number of arguments sent to it. number of arguments sent to it.
*/ */
static int builtin_count( wchar_t ** argv ) static int builtin_count( parser_t &parser, wchar_t ** argv )
{ {
int argc; int argc;
argc = builtin_count_args( argv ); argc = builtin_count_args( argv );
@ -3851,19 +3851,19 @@ static int internal_help( wchar_t *cmd )
} }
int builtin_run( wchar_t **argv, io_data_t *io ) int builtin_run( parser_t &parser, wchar_t **argv, io_data_t *io )
{ {
int (*cmd)(wchar_t **argv)=0; int (*cmd)(parser_t &parser, wchar_t **argv)=0;
real_io = io; real_io = io;
CHECK( argv, STATUS_BUILTIN_ERROR ); CHECK( argv, STATUS_BUILTIN_ERROR );
CHECK( argv[0], STATUS_BUILTIN_ERROR ); CHECK( argv[0], STATUS_BUILTIN_ERROR );
cmd = (int (*)(wchar_t **))hash_get( &builtin, argv[0] ); cmd = (int (*)(parser_t &parser, wchar_t **))hash_get( &builtin, argv[0] );
if( argv[1] != 0 && !internal_help(argv[0]) ) if( argv[1] != 0 && !internal_help(argv[0]) )
{ {
if( argv[2] == 0 && (parser_is_help( argv[1], 0 ) ) ) if( argv[2] == 0 && (parser.is_help( argv[1], 0 ) ) )
{ {
builtin_print_help( parser, argv[0], sb_out ); builtin_print_help( parser, argv[0], sb_out );
return STATUS_BUILTIN_OK; return STATUS_BUILTIN_OK;
@ -3874,7 +3874,7 @@ int builtin_run( wchar_t **argv, io_data_t *io )
{ {
int status; int status;
status = cmd(argv); status = cmd(parser, argv);
return status; return status;
} }

View file

@ -157,7 +157,7 @@ void builtin_pop_io(parser_t &parser);
/** /**
Return a one-line description of the specified builtin Return a one-line description of the specified builtin
*/ */
const wchar_t *builtin_get_desc( parser_t &parser, const wchar_t *b ); const wchar_t *builtin_get_desc( const wchar_t *b );
/** /**

View file

@ -232,7 +232,7 @@ static int builtin_commandline( parser_t &parser, wchar_t **argv )
int search_mode = 0; int search_mode = 0;
wchar_t *begin, *end; wchar_t *begin, *end;
current_buffer = (wchar_t *)builtin_complete_get_temporary_buffer(); current_buffer = (wchar_t *)builtin_complete_get_temporary_buffer(parser);
if( current_buffer ) if( current_buffer )
{ {
current_cursor_pos = wcslen( current_buffer ); current_cursor_pos = wcslen( current_buffer );

View file

@ -390,11 +390,6 @@ static std::vector<wcstring> forbidden_function;
*/ */
static int job_start_pos; static int job_start_pos;
/**
List of all profiling data
*/
static array_list_t profile_data;
/** /**
Keeps track of how many recursive eval calls have been made. Eval Keeps track of how many recursive eval calls have been made. Eval
doesn't call itself directly, recursion happens on blocks and on doesn't call itself directly, recursion happens on blocks and on
@ -433,6 +428,29 @@ typedef struct
wchar_t *cmd; wchar_t *cmd;
} profile_element_t; } profile_element_t;
struct profile_item_t {
/**
Time spent executing the specified command, including parse time for nested blocks.
*/
int exec;
/**
Time spent parsing the specified command, including execution time for command substitutions.
*/
int parse;
/**
The block level of the specified command. nested blocks and command substitutions both increase the block level.
*/
int level;
/**
If the execution of this command was skipped.
*/
int skipped;
/**
The command string.
*/
wcstring cmd;
};
/** /**
Return the current number of block nestings Return the current number of block nestings
*/ */
@ -666,14 +684,6 @@ void error( int ec, int p, const wchar_t *str, ... )
} }
void parser_init()
{
if( profile )
{
al_init( &profile_data);
}
}
/** /**
Print profiling information to the specified stream Print profiling information to the specified stream
*/ */
@ -765,7 +775,7 @@ void parser_destroy()
{ {
if( fwprintf( f, if( fwprintf( f,
_(L"Time\tSum\tCommand\n"), _(L"Time\tSum\tCommand\n"),
al_get_count( &profile_data ) ) < 0 ) profile_items.size() ) < 0 )
{ {
wperror( L"fwprintf" ); wperror( L"fwprintf" );
} }
@ -779,7 +789,6 @@ void parser_destroy()
wperror( L"fclose" ); wperror( L"fclose" );
} }
} }
al_destroy( &profile_data );
} }
if( lineinfo ) if( lineinfo )
@ -2291,24 +2300,24 @@ static void skipped_exec( job_t * j )
\param tok The tokenizer to read tokens from \param tok The tokenizer to read tokens from
*/ */
static void eval_job( tokenizer *tok ) static void eval_job( parser_t &parser, tokenizer *tok )
{ {
job_t *j; job_t *j;
int start_pos = job_start_pos = tok_get_pos( tok ); int start_pos = job_start_pos = tok_get_pos( tok );
long long t1=0, t2=0, t3=0; long long t1=0, t2=0, t3=0;
profile_element_t *p=0;
profile_item_t *profile_item = NULL;
int skip = 0; int skip = 0;
int job_begin_pos, prev_tokenizer_pos; int job_begin_pos, prev_tokenizer_pos;
if( profile ) if( profile )
{ {
p=(profile_element_t*)malloc( sizeof(profile_element_t)); parser.profile_items.resize(parser.profile_items.size() + 1);
if( !p ) profile_item = &parser.profile_items.back();
DIE_MEM(); profile_item->cmd = L"";
p->cmd=0; profile_item->skipped = 1;
al_push( &profile_data, p );
p->skipped=1;
t1 = get_time(); t1 = get_time();
} }
@ -2364,8 +2373,8 @@ static void eval_job( tokenizer *tok )
if( profile ) if( profile )
{ {
t2 = get_time(); t2 = get_time();
p->cmd = wcsdup( j->command ); profile_item->cmd = wcsdup( j->command );
p->skipped=current_block->skip; profile_item->skipped=current_block->skip;
} }
skip |= current_block->skip; skip |= current_block->skip;
@ -2394,9 +2403,9 @@ static void eval_job( tokenizer *tok )
if( profile ) if( profile )
{ {
t3 = get_time(); t3 = get_time();
p->level=eval_level; profile_item->level=eval_level;
p->parse = t2-t1; profile_item->parse = t2-t1;
p->exec=t3-t2; profile_item->exec=t3-t2;
} }
if( current_block->type == WHILE ) if( current_block->type == WHILE )
@ -2551,7 +2560,7 @@ int eval( const wchar_t *cmd, io_data_t *io, enum block_type_t block_type )
!sanity_check() && !sanity_check() &&
!exit_status() ) !exit_status() )
{ {
eval_job( current_tokenizer ); eval_job( parser, current_tokenizer );
event_fire( NULL ); event_fire( NULL );
} }

View file

@ -187,6 +187,8 @@ enum parser_type_t {
PARSER_TYPE_COMPLETIONS_ONLY PARSER_TYPE_COMPLETIONS_ONLY
}; };
struct profile_item_t;
class parser_t { class parser_t {
private: private:
std::vector<block_t> blocks; std::vector<block_t> blocks;
@ -196,6 +198,7 @@ class parser_t {
parser_t& operator=(const parser_t&); parser_t& operator=(const parser_t&);
public: public:
std::vector<profile_item_t> profile_items;
/** Create a parser of the given type */ /** Create a parser of the given type */
parser_t(enum parser_type_t type); parser_t(enum parser_type_t type);