mirror of
https://github.com/fish-shell/fish-shell
synced 2025-01-14 22:14:53 +00:00
Only complelete valid command types as subcommands for 'command' or 'builtin' builtins. Also make sure that the '--' switch is understood by the completions
darcs-hash:20061214000326-ac50b-3ee9130ebb3fcc9b2723686945cfca055c4f44a4.gz
This commit is contained in:
parent
9a8e5e64ed
commit
1289e03134
1 changed files with 169 additions and 88 deletions
103
complete.c
103
complete.c
|
@ -1315,7 +1315,10 @@ static const wchar_t *complete_function_desc( const wchar_t *fn )
|
||||||
\param comp the list to add all completions to
|
\param comp the list to add all completions to
|
||||||
*/
|
*/
|
||||||
static void complete_cmd( const wchar_t *cmd,
|
static void complete_cmd( const wchar_t *cmd,
|
||||||
array_list_t *comp )
|
array_list_t *comp,
|
||||||
|
int use_function,
|
||||||
|
int use_builtin,
|
||||||
|
int use_command )
|
||||||
{
|
{
|
||||||
wchar_t *path;
|
wchar_t *path;
|
||||||
wchar_t *path_cpy;
|
wchar_t *path_cpy;
|
||||||
|
@ -1331,6 +1334,9 @@ static void complete_cmd( const wchar_t *cmd,
|
||||||
int prev_count = al_get_count( comp );
|
int prev_count = al_get_count( comp );
|
||||||
|
|
||||||
if( (wcschr( cmd, L'/') != 0) || (cmd[0] == L'~' ) )
|
if( (wcschr( cmd, L'/') != 0) || (cmd[0] == L'~' ) )
|
||||||
|
{
|
||||||
|
|
||||||
|
if( use_command )
|
||||||
{
|
{
|
||||||
|
|
||||||
array_list_t tmp;
|
array_list_t tmp;
|
||||||
|
@ -1345,8 +1351,12 @@ static void complete_cmd( const wchar_t *cmd,
|
||||||
}
|
}
|
||||||
al_destroy( &tmp );
|
al_destroy( &tmp );
|
||||||
}
|
}
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
if( use_command )
|
||||||
|
{
|
||||||
|
|
||||||
path = env_get(L"PATH");
|
path = env_get(L"PATH");
|
||||||
if( path )
|
if( path )
|
||||||
{
|
{
|
||||||
|
@ -1388,28 +1398,41 @@ static void complete_cmd( const wchar_t *cmd,
|
||||||
complete_cmd_desc( cmd, comp );
|
complete_cmd_desc( cmd, comp );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
These return the original strings - don't free them
|
These return the original strings - don't free them
|
||||||
*/
|
*/
|
||||||
|
|
||||||
al_init( &possible_comp );
|
al_init( &possible_comp );
|
||||||
|
|
||||||
|
if( use_function )
|
||||||
|
{
|
||||||
|
|
||||||
function_get_names( &possible_comp, cmd[0] == L'_' );
|
function_get_names( &possible_comp, cmd[0] == L'_' );
|
||||||
copy_strings_with_prefix( comp, cmd, COMPLETE_FUNCTION_DESC, &complete_function_desc, &possible_comp );
|
copy_strings_with_prefix( comp, cmd, COMPLETE_FUNCTION_DESC, &complete_function_desc, &possible_comp );
|
||||||
|
}
|
||||||
|
|
||||||
al_truncate( &possible_comp, 0 );
|
al_truncate( &possible_comp, 0 );
|
||||||
|
|
||||||
|
if( use_builtin )
|
||||||
|
{
|
||||||
|
|
||||||
builtin_get_names( &possible_comp );
|
builtin_get_names( &possible_comp );
|
||||||
copy_strings_with_prefix( comp, cmd, COMPLETE_BUILTIN_DESC, &builtin_get_desc, &possible_comp );
|
copy_strings_with_prefix( comp, cmd, COMPLETE_BUILTIN_DESC, &builtin_get_desc, &possible_comp );
|
||||||
|
|
||||||
|
}
|
||||||
al_destroy( &possible_comp );
|
al_destroy( &possible_comp );
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if( use_builtin || (use_function && function_exists( L"cd") ) )
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
Tab complete implicit cd for directories in CDPATH
|
Tab complete implicit cd for directories in CDPATH
|
||||||
*/
|
*/
|
||||||
if( cmd[0] != L'/' && ( wcsncmp( cmd, L"./", 2 )!=0) )
|
if( cmd[0] != L'/' && ( wcsncmp( cmd, L"./", 2 )!=0) )
|
||||||
{
|
{
|
||||||
|
|
||||||
for( nxt_path = wcstok( cdpath_cpy, ARRAY_SEP_STR, &state );
|
for( nxt_path = wcstok( cdpath_cpy, ARRAY_SEP_STR, &state );
|
||||||
nxt_path != 0;
|
nxt_path != 0;
|
||||||
nxt_path = wcstok( 0, ARRAY_SEP_STR, &state) )
|
nxt_path = wcstok( 0, ARRAY_SEP_STR, &state) )
|
||||||
|
@ -1434,7 +1457,7 @@ static void complete_cmd( const wchar_t *cmd,
|
||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
free( cdpath_cpy );
|
free( cdpath_cpy );
|
||||||
|
@ -1672,9 +1695,8 @@ static int complete_param( wchar_t *cmd_orig,
|
||||||
}
|
}
|
||||||
else if( popt[0] == L'-' )
|
else if( popt[0] == L'-' )
|
||||||
{
|
{
|
||||||
/* Check if the previous option has any specified
|
/* Set to true if we found a matching old-style switch */
|
||||||
arguments to match against */
|
int old_style_match = 0;
|
||||||
int found_old = 0;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
If we are using old style long options, check for them
|
If we are using old style long options, check for them
|
||||||
|
@ -1686,7 +1708,7 @@ static int complete_param( wchar_t *cmd_orig,
|
||||||
{
|
{
|
||||||
if( param_match_old( o, popt ) && condition_test( o->condition ))
|
if( param_match_old( o, popt ) && condition_test( o->condition ))
|
||||||
{
|
{
|
||||||
found_old = 1;
|
old_style_match = 1;
|
||||||
use_common &= ((o->result_mode & NO_COMMON )==0);
|
use_common &= ((o->result_mode & NO_COMMON )==0);
|
||||||
use_files &= ((o->result_mode & NO_FILES )==0);
|
use_files &= ((o->result_mode & NO_FILES )==0);
|
||||||
complete_from_args( str, o->comp, C_(o->desc), comp_out );
|
complete_from_args( str, o->comp, C_(o->desc), comp_out );
|
||||||
|
@ -1699,7 +1721,7 @@ static int complete_param( wchar_t *cmd_orig,
|
||||||
style options. We check if any short (or gnu style
|
style options. We check if any short (or gnu style
|
||||||
options do.
|
options do.
|
||||||
*/
|
*/
|
||||||
if( !found_old )
|
if( !old_style_match )
|
||||||
{
|
{
|
||||||
for( o = i->first_option; o; o=o->next )
|
for( o = i->first_option; o; o=o->next )
|
||||||
{
|
{
|
||||||
|
@ -2037,6 +2059,9 @@ void complete( const wchar_t *cmd,
|
||||||
int pos;
|
int pos;
|
||||||
int done=0;
|
int done=0;
|
||||||
int cursor_pos;
|
int cursor_pos;
|
||||||
|
int use_command = 1;
|
||||||
|
int use_function = 1;
|
||||||
|
int use_builtin = 1;
|
||||||
|
|
||||||
CHECK( cmd, );
|
CHECK( cmd, );
|
||||||
CHECK( comp, );
|
CHECK( comp, );
|
||||||
|
@ -2098,10 +2123,32 @@ void complete( const wchar_t *cmd,
|
||||||
switch( tok_last_type( &tok ) )
|
switch( tok_last_type( &tok ) )
|
||||||
{
|
{
|
||||||
case TOK_STRING:
|
case TOK_STRING:
|
||||||
|
{
|
||||||
if( !had_cmd )
|
if( !had_cmd )
|
||||||
{
|
{
|
||||||
if( parser_is_subcommand( tok_last( &tok ) ) )
|
wchar_t *ncmd = tok_last( &tok );
|
||||||
|
if( parser_is_subcommand( ncmd ) )
|
||||||
|
{
|
||||||
|
if( wcscmp( ncmd, L"builtin" )==0)
|
||||||
|
{
|
||||||
|
use_function = 0;
|
||||||
|
use_command = 0;
|
||||||
|
use_builtin = 1;
|
||||||
|
}
|
||||||
|
else if( wcscmp( ncmd, L"command" )==0)
|
||||||
|
{
|
||||||
|
use_command = 1;
|
||||||
|
use_function = 0;
|
||||||
|
use_builtin = 0;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
int is_ddash = wcscmp( ncmd, L"--" ) != 0;
|
||||||
|
|
||||||
|
if( is_ddash ||
|
||||||
|
( (use_command && use_function && use_builtin ) ) )
|
||||||
|
{
|
||||||
|
|
||||||
free( current_command );
|
free( current_command );
|
||||||
current_command = wcsdup( tok_last( &tok ) );
|
current_command = wcsdup( tok_last( &tok ) );
|
||||||
|
@ -2109,15 +2156,20 @@ void complete( const wchar_t *cmd,
|
||||||
on_command = (pos <= tok_get_pos( &tok) + wcslen( tok_last( &tok ) ) );
|
on_command = (pos <= tok_get_pos( &tok) + wcslen( tok_last( &tok ) ) );
|
||||||
had_cmd=1;
|
had_cmd=1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
case TOK_END:
|
case TOK_END:
|
||||||
case TOK_PIPE:
|
case TOK_PIPE:
|
||||||
case TOK_BACKGROUND:
|
case TOK_BACKGROUND:
|
||||||
had_cmd=0;
|
had_cmd=0;
|
||||||
|
use_command = 1;
|
||||||
|
use_function = 1;
|
||||||
|
use_builtin = 1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
|
||||||
case TOK_ERROR:
|
case TOK_ERROR:
|
||||||
end_loop=1;
|
end_loop=1;
|
||||||
break;
|
break;
|
||||||
|
@ -2144,11 +2196,40 @@ void complete( const wchar_t *cmd,
|
||||||
prev_token = prev_begin ? wcsndup( prev_begin, prev_end - prev_begin ): wcsdup(L"");
|
prev_token = prev_begin ? wcsndup( prev_begin, prev_end - prev_begin ): wcsdup(L"");
|
||||||
|
|
||||||
// debug( 0, L"on_command: %d, %ls %ls\n", on_command, current_command, current_token );
|
// debug( 0, L"on_command: %d, %ls %ls\n", on_command, current_command, current_token );
|
||||||
|
|
||||||
|
/*
|
||||||
|
Check if we are using the 'command' or 'builtin' builtins
|
||||||
|
_and_ we are writing a switch ionstead of a command. In that
|
||||||
|
case, complete using the builtins completions, not using a
|
||||||
|
subcommand.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if( (on_command || (wcscmp( current_token, L"--" ) == 0 ) ) &&
|
||||||
|
(current_token[0] == L'-') &&
|
||||||
|
!(use_command && use_function && use_builtin ) )
|
||||||
|
{
|
||||||
|
free( current_command );
|
||||||
|
if( use_command == 0 )
|
||||||
|
current_command = wcsdup( L"builtin" );
|
||||||
|
else
|
||||||
|
current_command = wcsdup( L"command" );
|
||||||
|
|
||||||
|
had_cmd = 1;
|
||||||
|
on_command = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
Use command completions if in between commands
|
||||||
|
*/
|
||||||
if( !had_cmd )
|
if( !had_cmd )
|
||||||
{
|
{
|
||||||
on_command=1;
|
on_command=1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
We don't want these to be null
|
||||||
|
*/
|
||||||
|
|
||||||
if( !current_token )
|
if( !current_token )
|
||||||
{
|
{
|
||||||
current_token = wcsdup(L"");
|
current_token = wcsdup(L"");
|
||||||
|
@ -2170,7 +2251,7 @@ void complete( const wchar_t *cmd,
|
||||||
{
|
{
|
||||||
/* Complete command filename */
|
/* Complete command filename */
|
||||||
complete_cmd( current_token,
|
complete_cmd( current_token,
|
||||||
comp );
|
comp, use_function, use_builtin, use_command );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue