Skip to content

Commit

Permalink
Add the possibility for functions which do not shadow the arguments o…
Browse files Browse the repository at this point in the history
…f the calling function

darcs-hash:20070422221033-ac50b-d9544c87d0ddab10f7f503b5a1707292f266efe4.gz
  • Loading branch information
liljencrantz committed Apr 22, 2007
1 parent 2b7535b commit ee94424
Show file tree
Hide file tree
Showing 6 changed files with 105 additions and 81 deletions.
62 changes: 23 additions & 39 deletions builtin.c
Original file line number Diff line number Diff line change
Expand Up @@ -1084,16 +1084,6 @@ static int builtin_functions( wchar_t **argv )

}

typedef struct function_data
{
wchar_t *name;
wchar_t *description;
array_list_t *events;
array_list_t *named_arguments;
}
function_data_t;



/**
The function builtin, used for providing subroutines.
Expand All @@ -1108,7 +1098,7 @@ static int builtin_function( wchar_t **argv )
int i;
array_list_t *named_arguments=0;
wchar_t *name = 0;

int shadows = 1;

woptind=0;

Expand Down Expand Up @@ -1146,6 +1136,10 @@ static int builtin_function( wchar_t **argv )
L"argument-names", no_argument, 0, 'a'
}
,
{
L"no-scope-shadowing", no_argument, 0, 'S'
}
,
{
0, 0, 0, 0
}
Expand All @@ -1158,7 +1152,7 @@ static int builtin_function( wchar_t **argv )

int opt = wgetopt_long( argc,
argv,
L"d:s:j:p:v:ha",
L"d:s:j:p:v:haS",
long_options,
&opt_index );
if( opt == -1 )
Expand Down Expand Up @@ -1312,7 +1306,10 @@ static int builtin_function( wchar_t **argv )
named_arguments = al_halloc( current_block );
break;


case 'S':
shadows = 0;
break;

case 'h':
builtin_print_help( argv[0], sb_out );
return STATUS_BUILTIN_OK;
Expand Down Expand Up @@ -1431,6 +1428,7 @@ static int builtin_function( wchar_t **argv )
d->description=desc?halloc_wcsdup( current_block, desc):0;
d->events = events;
d->named_arguments = named_arguments;
d->shadows = shadows;

for( i=0; i<al_get_count( events ); i++ )
{
Expand Down Expand Up @@ -2691,31 +2689,6 @@ static int builtin_begin( wchar_t **argv )
return proc_get_last_status();
}

/**
Define the function specified by the function_data_t structure.
*/
static void builtin_end_add_function_def( function_data_t *d )
{
/**
Copy the text from the beginning of the function
until the end command and use as the new definition
for the specified function
*/

wchar_t *def = wcsndup( parser_get_buffer()+current_block->tok_pos,
parser_get_job_pos()-current_block->tok_pos );

function_add( d->name,
def,
d->description,
d->events,
d->named_arguments );

free( def );

}



/**
Builtin for ending a block of code, such as a for-loop or an if statement.
Expand Down Expand Up @@ -2801,7 +2774,18 @@ static int builtin_end( wchar_t **argv )

if( d )
{
builtin_end_add_function_def( d );
/**
Copy the text from the beginning of the function
until the end command and use as the new definition
for the specified function
*/

wchar_t *def = wcsndup( parser_get_buffer()+current_block->tok_pos,
parser_get_job_pos()-current_block->tok_pos );
d->definition = def;

function_add( d );
free( def );
}
else
{
Expand Down
4 changes: 3 additions & 1 deletion exec.c
Original file line number Diff line number Diff line change
Expand Up @@ -994,6 +994,7 @@ void exec( job_t *j )
const wchar_t * orig_def;
wchar_t * def=0;
array_list_t *named_arguments;
int shadows;


/*
Expand All @@ -1005,6 +1006,7 @@ void exec( job_t *j )
signal_unblock();
orig_def = function_get_definition( p->argv[0] );
named_arguments = function_get_named_arguments( p->argv[0] );
shadows = function_get_shadows( p->argv[0] );

signal_block();

Expand All @@ -1018,7 +1020,7 @@ void exec( job_t *j )
break;
}

parser_push_block( FUNCTION_CALL );
parser_push_block( shadows?FUNCTION_CALL:FUNCTION_CALL_NO_SHADOW );

current_block->param2.function_call_process = p;
current_block->param1.function_call_name = halloc_register( current_block, wcsdup( p->argv[0] ) );
Expand Down
84 changes: 48 additions & 36 deletions function.c
Original file line number Diff line number Diff line change
Expand Up @@ -60,8 +60,10 @@ typedef struct
Flag for specifying that this function was automatically loaded
*/
int is_autoload;

int shadows;
}
function_data_t;
function_internal_data_t;

/**
Table containing all functions
Expand All @@ -83,8 +85,8 @@ static int load( const wchar_t *name )
{
int was_autoload = is_autoload;
int res;
function_data_t *data;
data = (function_data_t *)hash_get( &function, name );
function_internal_data_t *data;
data = (function_internal_data_t *)hash_get( &function, name );
if( data && !data->is_autoload )
return 0;

Expand Down Expand Up @@ -165,46 +167,43 @@ void function_destroy()
}


void function_add( const wchar_t *name,
const wchar_t *val,
const wchar_t *desc,
array_list_t *events,
array_list_t *named_arguments )
void function_add( function_data_t *data )
{
int i;
wchar_t *cmd_end;
function_data_t *d;
function_internal_data_t *d;

CHECK( name, );
CHECK( val, );
CHECK( data->name, );
CHECK( data->definition, );

function_remove( name );
function_remove( data->name );

d = halloc( 0, sizeof( function_data_t ) );
d = halloc( 0, sizeof( function_internal_data_t ) );
d->definition_offset = parse_util_lineno( parser_get_buffer(), current_block->tok_pos )-1;
d->cmd = halloc_wcsdup( d, val );
d->cmd = halloc_wcsdup( d, data->definition );

if( named_arguments )
if( data->named_arguments )
{
d->named_arguments = al_halloc( d );

for( i=0; i<al_get_count( named_arguments ); i++ )
for( i=0; i<al_get_count( data->named_arguments ); i++ )
{
al_push( d->named_arguments, halloc_wcsdup( d, (wchar_t *)al_get( named_arguments, i ) ) );
al_push( d->named_arguments, halloc_wcsdup( d, (wchar_t *)al_get( data->named_arguments, i ) ) );
}
}

cmd_end = d->cmd + wcslen(d->cmd)-1;

d->desc = desc?halloc_wcsdup( d, desc ):0;
d->desc = data->description?halloc_wcsdup( d, data->description ):0;
d->definition_file = intern(reader_current_filename());
d->is_autoload = is_autoload;

hash_put( &function, intern(name), d );
d->shadows = data->shadows;

hash_put( &function, intern(data->name), d );

for( i=0; i<al_get_count( events ); i++ )
for( i=0; i<al_get_count( data->events ); i++ )
{
event_add_handler( (event_t *)al_get( events, i ) );
event_add_handler( (event_t *)al_get( data->events, i ) );
}

}
Expand All @@ -225,7 +224,7 @@ void function_remove( const wchar_t *name )
{
void *key;
void *dv;
function_data_t *d;
function_internal_data_t *d;
event_t ev;

CHECK( name, );
Expand All @@ -235,7 +234,7 @@ void function_remove( const wchar_t *name )
&key,
&dv );

d=(function_data_t *)dv;
d=(function_internal_data_t *)dv;

if( !key )
return;
Expand All @@ -259,39 +258,52 @@ void function_remove( const wchar_t *name )

const wchar_t *function_get_definition( const wchar_t *name )
{
function_data_t *data;
function_internal_data_t *data;

CHECK( name, 0 );

load( name );
data = (function_data_t *)hash_get( &function, name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return 0;
return data->cmd;
}

array_list_t *function_get_named_arguments( const wchar_t *name )
{
function_data_t *data;
function_internal_data_t *data;

CHECK( name, 0 );

load( name );
data = (function_data_t *)hash_get( &function, name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return 0;
return data->named_arguments;
}

int function_get_shadows( const wchar_t *name )
{
function_internal_data_t *data;

CHECK( name, 0 );

load( name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return 0;
return data->shadows;
}


const wchar_t *function_get_desc( const wchar_t *name )
{
function_data_t *data;
function_internal_data_t *data;

CHECK( name, 0 );

load( name );
data = (function_data_t *)hash_get( &function, name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return 0;

Expand All @@ -300,13 +312,13 @@ const wchar_t *function_get_desc( const wchar_t *name )

void function_set_desc( const wchar_t *name, const wchar_t *desc )
{
function_data_t *data;
function_internal_data_t *data;

CHECK( name, );
CHECK( desc, );

load( name );
data = (function_data_t *)hash_get( &function, name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return;

Expand Down Expand Up @@ -377,11 +389,11 @@ void function_get_names( array_list_t *list, int get_hidden )

const wchar_t *function_get_definition_file( const wchar_t *name )
{
function_data_t *data;
function_internal_data_t *data;

CHECK( name, 0 );

data = (function_data_t *)hash_get( &function, name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return 0;

Expand All @@ -391,11 +403,11 @@ const wchar_t *function_get_definition_file( const wchar_t *name )

int function_get_definition_offset( const wchar_t *name )
{
function_data_t *data;
function_internal_data_t *data;

CHECK( name, -1 );

data = (function_data_t *)hash_get( &function, name );
data = (function_internal_data_t *)hash_get( &function, name );
if( data == 0 )
return -1;

Expand Down
26 changes: 21 additions & 5 deletions function.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,21 @@

#include "util.h"

/**
Structure describing a function
*/
typedef struct function_data
{
wchar_t *name;
wchar_t *description;
wchar_t *definition;
array_list_t *events;
array_list_t *named_arguments;
int shadows;
}
function_data_t;


/**
Initialize function data
*/
Expand All @@ -28,11 +43,7 @@ void function_destroy();
Add an function. The parameters values are copied and should be
freed by the caller.
*/
void function_add( const wchar_t *name,
const wchar_t *val,
const wchar_t *desc,
array_list_t *events,
array_list_t *named_arguments );
void function_add( function_data_t *data );

/**
Remove the function with the specified name.
Expand Down Expand Up @@ -92,4 +103,9 @@ int function_get_definition_offset( const wchar_t *name );
*/
array_list_t *function_get_named_arguments( const wchar_t *name );

/**
Returns whether this function shadows variables of the underlying function
*/
int function_get_shadows( const wchar_t *name );

#endif
Loading

0 comments on commit ee94424

Please sign in to comment.