diff options
Diffstat (limited to 'highlight.c')
-rw-r--r-- | highlight.c | 295 |
1 files changed, 287 insertions, 8 deletions
diff --git a/highlight.c b/highlight.c index 6ebcb00f..941b649e 100644 --- a/highlight.c +++ b/highlight.c @@ -40,7 +40,7 @@ static void highlight_universal_internal( wchar_t * buff, /** The environment variables used to specify the color of different tokens. */ -static wchar_t *hightlight_var[] = +static wchar_t *highlight_var[] = { L"fish_color_normal", L"fish_color_command", @@ -52,24 +52,23 @@ static wchar_t *hightlight_var[] = L"fish_color_comment", L"fish_color_match", L"fish_color_search_match", - L"fish_color_pager_prefix", - L"fish_color_pager_completion", - L"fish_color_pager_description", - L"fish_color_pager_progress" + L"fish_color_operator", + L"fish_color_escape" } ; +#define VAR_COUNT ( sizeof(highlight_var)/sizeof(wchar_t *) ) int highlight_get_color( int highlight ) { if( highlight < 0 ) return FISH_COLOR_NORMAL; - if( highlight >= (12) ) + if( highlight >= VAR_COUNT ) return FISH_COLOR_NORMAL; - wchar_t *val = env_get( hightlight_var[highlight]); + wchar_t *val = env_get( highlight_var[highlight]); if( val == 0 ) - val = env_get( hightlight_var[HIGHLIGHT_NORMAL]); + val = env_get( highlight_var[HIGHLIGHT_NORMAL]); if( val == 0 ) { @@ -79,6 +78,280 @@ int highlight_get_color( int highlight ) return output_color_code( val ); } +static void highlight_param( const wchar_t * buff, + int *color, + int pos, + array_list_t *error ) +{ + + + int mode = 0; + int in_pos, len = wcslen( buff ); + int bracket_count=0; + wchar_t c; + + for( in_pos=0; + in_pos<len; + in_pos++ ) + { + c = buff[in_pos]; + switch( mode ) + { + + /* + Mode 0 means unquoted string + */ + case 0: + { + if( c == L'\\' ) + { + int start_pos = in_pos; + + switch( buff[++in_pos] ) + { + case L'n': + case L'r': + case L't': + case L'b': + case L'e': + { + color[start_pos]=HIGHLIGHT_ESCAPE; + color[in_pos+1]=HIGHLIGHT_NORMAL; + break; + } + + case L'u': + case L'U': + case L'x': + case L'X': + case L'0': + case L'1': + case L'2': + case L'3': + case L'4': + case L'5': + case L'6': + case L'7': + { + int i; + long long res=0; + int chars=2; + int base=16; + + int byte = 0; + wchar_t max_val = ASCII_MAX; + + switch( buff[in_pos] ) + { + case L'u': + { + chars=4; + max_val = UCS2_MAX; + break; + } + + case L'U': + { + chars=8; + max_val = WCHAR_MAX; + break; + } + + case L'x': + { + break; + } + + case L'X': + { + byte=1; + max_val = BYTE_MAX; + break; + } + + default: + { + base=8; + chars=3; + in_pos--; + break; + } + } + + for( i=0; i<chars; i++ ) + { + int d = convert_digit( buff[++in_pos],base); + + if( d < 0 ) + { + in_pos--; + break; + } + + res=(res*base)|d; + } + + if( (res <= max_val) ) + { + color[start_pos] = HIGHLIGHT_ESCAPE; + color[in_pos+1] = HIGHLIGHT_NORMAL; + } + else + { + color[start_pos] = HIGHLIGHT_ERROR; + color[in_pos+1] = HIGHLIGHT_NORMAL; + } + + break; + } + } + } + else + { + switch( buff[in_pos]){ + case L'~': + case L'%': + { + if( in_pos == 0 ) + { + color[in_pos] = HIGHLIGHT_OPERATOR; + color[in_pos+1] = HIGHLIGHT_NORMAL; + } + break; + } + + case L'*': + case L'?': + case L'$': + { + color[in_pos] = HIGHLIGHT_OPERATOR; + color[in_pos+1] = HIGHLIGHT_NORMAL; + break; + } + + case L'{': + { + bracket_count++; + break; + } + + case L'}': + { + bracket_count--; + break; + } + + case L',': + { + if( bracket_count ) + { + color[in_pos] = HIGHLIGHT_OPERATOR; + color[in_pos+1] = HIGHLIGHT_NORMAL; + } + + break; + } + + case L'\'': + { + mode = 1; + break; + } + + case L'\"': + { + mode = 2; + break; + } + + } + } + break; + } + + /* + Mode 1 means single quoted string, i.e 'foo' + */ + case 1: + { + if( c == L'\\' ) + { + int start_pos = in_pos; + switch( buff[++in_pos] ) + { + case '\\': + case L'\'': + { + color[start_pos] = HIGHLIGHT_ESCAPE; + color[in_pos+1] = HIGHLIGHT_NORMAL; + break; + } + + case 0: + { + return; + } + + } + + } + if( c == L'\'' ) + { + mode = 0; + } + + break; + } + + /* + Mode 2 means double quoted string, i.e. "foo" + */ + case 2: + { + switch( c ) + { + case '"': + { + mode = 0; + break; + } + + case '\\': + { + int start_pos = in_pos; + switch( buff[++in_pos] ) + { + case L'\0': + { + return; + } + + case '\\': + case L'$': + case '"': + { + color[start_pos] = HIGHLIGHT_ESCAPE; + color[in_pos+1] = HIGHLIGHT_NORMAL; + break; + } + } + break; + } + + case '$': + { + color[in_pos] = HIGHLIGHT_OPERATOR; + color[in_pos+1] = HIGHLIGHT_NORMAL; + break; + } + + } + break; + } + } + } +} + void highlight_shell( wchar_t * buff, int *color, @@ -125,6 +398,12 @@ void highlight_shell( wchar_t * buff, { color[ tok_get_pos( &tok ) ] = HIGHLIGHT_PARAM; } + + highlight_param( param, + &color[tok_get_pos( &tok )], + pos-tok_get_pos( &tok ), + error ); + } else { |