mirror of
https://github.com/fish-shell/fish-shell
synced 2024-12-26 12:53:13 +00:00
Add %o, %x and %X formats to *wprintf fallback implemnentation
darcs-hash:20060212112030-ac50b-1e3153c25dca3d2e12a8eb0e65da29bf70fa0d2e.gz
This commit is contained in:
parent
5718ea41df
commit
7c7f744b4c
2 changed files with 147 additions and 108 deletions
24
fish_tests.c
24
fish_tests.c
|
@ -41,6 +41,7 @@
|
|||
#include "output.h"
|
||||
#include "exec.h"
|
||||
#include "event.h"
|
||||
#include "halloc_util.h"
|
||||
|
||||
/**
|
||||
Number of laps to run performance testing loop
|
||||
|
@ -327,7 +328,7 @@ static void sb_test()
|
|||
|
||||
sb_init( &b );
|
||||
|
||||
if( res=sb_printf( &b, L"%ls%s", L"Testing ", "string_buffer_t " ) == -1 )
|
||||
if( (res=sb_printf( &b, L"%ls%s", L"Testing ", "string_buffer_t " )) == -1 )
|
||||
{
|
||||
err( L"Error %d while testing stringbuffers", res );
|
||||
}
|
||||
|
@ -336,7 +337,22 @@ static void sb_test()
|
|||
{
|
||||
err( L"Error %d while testing stringbuffers", res );
|
||||
}
|
||||
|
||||
say( (wchar_t *)b.buff );
|
||||
|
||||
sb_clear( &b );
|
||||
|
||||
#define NUM_ANS L"-7 99999999 1234567 deadbeef DEADBEEFDEADBEEF"
|
||||
|
||||
sb_printf( &b, L"%d %u %o %x %llX", -7, 99999999, 01234567, 0xdeadbeef, 0xdeadbeefdeadbeefll );
|
||||
if( wcscmp( (wchar_t *)b.buff, NUM_ANS) != 0 )
|
||||
{
|
||||
err( L"numerical formating is broken, '%ls' != '%ls'", (wchar_t *)b.buff, NUM_ANS );
|
||||
}
|
||||
else
|
||||
say( L"numerical formating works" );
|
||||
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -533,7 +549,7 @@ static int expand_test( const wchar_t *in, int flags, ... )
|
|||
wchar_t *arg;
|
||||
|
||||
al_init( &out );
|
||||
expand_string( wcsdup(in), &out, flags);
|
||||
expand_string( 0, wcsdup(in), &out, flags);
|
||||
|
||||
va_start( va, flags );
|
||||
|
||||
|
@ -669,7 +685,7 @@ int main( int argc, char **argv )
|
|||
say( L"Lines beginning with '(ignore):' are not errors, they are warning messages\ngenerated by the fish parser library when given broken input, and can be\nignored. All actual errors begin with 'Error:'." );
|
||||
|
||||
proc_init();
|
||||
output_init();
|
||||
halloc_util_init();
|
||||
event_init();
|
||||
exec_init();
|
||||
parser_init();
|
||||
|
@ -701,7 +717,7 @@ int main( int argc, char **argv )
|
|||
wutil_destroy();
|
||||
exec_destroy();
|
||||
event_destroy();
|
||||
output_destroy();
|
||||
proc_destroy();
|
||||
halloc_util_destroy();
|
||||
|
||||
}
|
||||
|
|
231
wutil.c
231
wutil.c
|
@ -350,19 +350,18 @@ void pad( void (*writer)(wchar_t), int count)
|
|||
are secretly a wrapper around this function. vgprintf does not
|
||||
implement all the filters supported by printf, only those that are
|
||||
currently used by fish. vgprintf internally uses snprintf to
|
||||
implement the %f %d and %u filters.
|
||||
implement the number outputs, such as %f and %x.
|
||||
|
||||
Currently supported functionality:
|
||||
|
||||
- precision specification, both through .* and .N
|
||||
- width specification through * and N
|
||||
- Padding through * and N
|
||||
- Right padding using the - prefix
|
||||
- long versions of all filters thorugh l and ll prefix
|
||||
- Character outout using %c
|
||||
- Character output using %c
|
||||
- String output through %s
|
||||
- Floating point number output through %f
|
||||
- Integer output through %d or %i
|
||||
- Unsigned integer output through %u
|
||||
- Left padding using the - prefix
|
||||
- Integer output through %d, %i, %u, %o, %x and %X
|
||||
|
||||
For a full description on the usage of *printf, see use 'man 3 printf'.
|
||||
*/
|
||||
|
@ -452,7 +451,7 @@ static int vgwprintf( void (*writer)(wchar_t),
|
|||
count += maxi( width-1, 0 );
|
||||
}
|
||||
|
||||
c = is_long?va_arg(va, wchar_t):btowc(va_arg(va, int));
|
||||
c = is_long?va_arg(va, wint_t):btowc(va_arg(va, int));
|
||||
if( precision != 0 )
|
||||
writer( c );
|
||||
|
||||
|
@ -522,115 +521,138 @@ static int vgwprintf( void (*writer)(wchar_t),
|
|||
|
||||
case L'd':
|
||||
case L'i':
|
||||
{
|
||||
char str[32];
|
||||
char *pos;
|
||||
|
||||
switch( is_long )
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
int d = va_arg( va, int );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, "%.*d", precision, d );
|
||||
else
|
||||
snprintf( str, 32, "%d", d );
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case 1:
|
||||
{
|
||||
long d = va_arg( va, long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, "%.*ld", precision, d );
|
||||
else
|
||||
snprintf( str, 32, "%ld", d );
|
||||
break;
|
||||
}
|
||||
|
||||
case 2:
|
||||
{
|
||||
long long d = va_arg( va, long long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, "%.*lld", precision, d );
|
||||
else
|
||||
snprintf( str, 32, "%lld", d );
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
return -1;
|
||||
}
|
||||
|
||||
if( (width >= 0) && pad_left )
|
||||
{
|
||||
pad( writer, width-strlen(str) );
|
||||
count +=maxi(width-strlen(str), 0 );
|
||||
}
|
||||
|
||||
pos = str;
|
||||
|
||||
while( *pos )
|
||||
{
|
||||
writer( *(pos++) );
|
||||
count++;
|
||||
}
|
||||
|
||||
if( (width >= 0) && !pad_left )
|
||||
{
|
||||
pad( writer, width-strlen(str) );
|
||||
count += maxi(width-strlen(str), 0 );
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case L'o':
|
||||
case L'u':
|
||||
case L'x':
|
||||
case L'X':
|
||||
{
|
||||
char str[32];
|
||||
char str[33];
|
||||
char *pos;
|
||||
char format[16];
|
||||
int len;
|
||||
|
||||
format[0]=0;
|
||||
strcat( format, "%");
|
||||
if( precision >= 0 )
|
||||
strcat( format, ".*" );
|
||||
switch( is_long )
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
unsigned d = va_arg( va, unsigned );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, "%.*u", precision, d );
|
||||
else
|
||||
snprintf( str, 32, "%u", d );
|
||||
break;
|
||||
}
|
||||
|
||||
case 1:
|
||||
{
|
||||
unsigned long d = va_arg( va, unsigned long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, "%.*lu", precision, d );
|
||||
else
|
||||
snprintf( str, 32, "%lu", d );
|
||||
break;
|
||||
}
|
||||
|
||||
case 2:
|
||||
{
|
||||
unsigned long long d = va_arg( va, unsigned long long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, "%.*llu", precision, d );
|
||||
else
|
||||
snprintf( str, 32, "%llu", d );
|
||||
strcat( format, "ll" );
|
||||
break;
|
||||
case 1:
|
||||
strcat( format, "l" );
|
||||
break;
|
||||
}
|
||||
|
||||
len = strlen(format);
|
||||
format[len++]=(char)*filter;
|
||||
format[len]=0;
|
||||
|
||||
switch( *filter )
|
||||
{
|
||||
case L'd':
|
||||
case L'i':
|
||||
{
|
||||
|
||||
switch( is_long )
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
int d = va_arg( va, int );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, format, precision, d );
|
||||
else
|
||||
snprintf( str, 32, format, d );
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case 1:
|
||||
{
|
||||
long d = va_arg( va, long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, format, precision, d );
|
||||
else
|
||||
snprintf( str, 32, format, d );
|
||||
break;
|
||||
}
|
||||
|
||||
case 2:
|
||||
{
|
||||
long long d = va_arg( va, long long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, format, precision, d );
|
||||
else
|
||||
snprintf( str, 32, format, d );
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
debug( 0, L"Invalid length modifier in string %ls\n", filter_org );
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
|
||||
}
|
||||
|
||||
case L'u':
|
||||
case L'o':
|
||||
case L'x':
|
||||
case L'X':
|
||||
{
|
||||
|
||||
switch( is_long )
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
unsigned d = va_arg( va, unsigned );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, format, precision, d );
|
||||
else
|
||||
snprintf( str, 32, format, d );
|
||||
break;
|
||||
}
|
||||
|
||||
case 1:
|
||||
{
|
||||
unsigned long d = va_arg( va, unsigned long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, format, precision, d );
|
||||
else
|
||||
snprintf( str, 32, format, d );
|
||||
break;
|
||||
}
|
||||
|
||||
case 2:
|
||||
{
|
||||
unsigned long long d = va_arg( va, unsigned long long );
|
||||
if( precision >= 0 )
|
||||
snprintf( str, 32, format, precision, d );
|
||||
else
|
||||
snprintf( str, 32, format, d );
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
debug( 0, L"Invalid length modifier in string %ls\n", filter_org );
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
|
||||
}
|
||||
|
||||
default:
|
||||
debug( 0, L"Invalid filter %ls in string %ls\n", *filter, filter_org );
|
||||
return -1;
|
||||
|
||||
}
|
||||
|
||||
|
||||
if( (width >= 0) && pad_left )
|
||||
{
|
||||
pad( writer, width-strlen(str) );
|
||||
count += maxi( width-strlen(str), 0 );
|
||||
int l = maxi(width-strlen(str), 0 );
|
||||
pad( writer, l );
|
||||
count += l;
|
||||
}
|
||||
|
||||
pos = str;
|
||||
|
@ -643,8 +665,9 @@ static int vgwprintf( void (*writer)(wchar_t),
|
|||
|
||||
if( (width >= 0) && !pad_left )
|
||||
{
|
||||
pad( writer, width-strlen(str) );
|
||||
count += maxi( width-strlen(str), 0 );
|
||||
int l = maxi(width-strlen(str), 0 );
|
||||
pad( writer, l );
|
||||
count += l;
|
||||
}
|
||||
|
||||
break;
|
||||
|
@ -705,7 +728,7 @@ static int vgwprintf( void (*writer)(wchar_t),
|
|||
}
|
||||
default:
|
||||
debug( 0, L"Unknown switch %lc in string %ls\n", *filter, filter_org );
|
||||
// exit(1);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
|
Loading…
Reference in a new issue