enable printing of 64-bit ints with gcc.

This commit is contained in:
Tomas Hruby 2009-11-11 12:15:08 +00:00
parent b3b0a18403
commit 04db2d7184
3 changed files with 45 additions and 10 deletions

View file

@ -42,12 +42,12 @@ gnum(register const char *f, int *ip, va_list *app)
static char * static char *
o_print(va_list *ap, int flags, char *s, char c, int precision, int is_signed) o_print(va_list *ap, int flags, char *s, char c, int precision, int is_signed)
{ {
long signed_val; printval_s_t signed_val;
unsigned long unsigned_val; printval_u_t unsigned_val;
char *old_s = s; char *old_s = s;
int base; int base;
switch (flags & (FL_SHORT | FL_LONG)) { switch (flags & (FL_SHORT | FL_LONG | FL_LONGLONG)) {
case FL_SHORT: case FL_SHORT:
if (is_signed) { if (is_signed) {
signed_val = (short) va_arg(*ap, int); signed_val = (short) va_arg(*ap, int);
@ -62,6 +62,15 @@ o_print(va_list *ap, int flags, char *s, char c, int precision, int is_signed)
unsigned_val = va_arg(*ap, unsigned long); unsigned_val = va_arg(*ap, unsigned long);
} }
break; break;
#if defined(__LONG_LONG_SUPPORTED)
case FL_LONG | FL_LONGLONG:
if (is_signed) {
signed_val = va_arg(*ap, long long);
} else {
unsigned_val = va_arg(*ap, unsigned long long);
}
break;
#endif
default: default:
if (is_signed) { if (is_signed) {
signed_val = va_arg(*ap, int); signed_val = va_arg(*ap, int);
@ -171,11 +180,27 @@ _doprnt(register const char *fmt, va_list ap, FILE *stream)
s = s1 = buf; s = s1 = buf;
flags &= ~FL_NOMORE;
do {
switch (*fmt) { switch (*fmt) {
case 'h': flags |= FL_SHORT; fmt++; break; case 'h':
case 'l': flags |= FL_LONG; fmt++; break; flags |= FL_SHORT;
case 'L': flags |= FL_LONGDOUBLE; fmt++; break; break;
case 'l':
if(flags & FL_LONG)
flags |= FL_LONGLONG;
else
flags |= FL_LONG;
break;
case 'L':
flags |= FL_LONGDOUBLE;
break;
default:
flags |= FL_NOMORE;
continue;
} }
fmt++;
} while(!(flags & FL_NOMORE));
switch (c = *fmt++) { switch (c = *fmt++) {
default: default:

View file

@ -8,7 +8,7 @@
/* This routine is used in doprnt.c as well as in tmpfile.c and tmpnam.c. */ /* This routine is used in doprnt.c as well as in tmpfile.c and tmpnam.c. */
char * char *
_i_compute(unsigned long val, int base, char *s, int nrdigits) _i_compute(printval_u_t val, int base, char *s, int nrdigits)
{ {
int c; int c;

View file

@ -4,15 +4,24 @@
/* $Header$ */ /* $Header$ */
#include <stdio.h> #include <stdio.h>
#include <ansi.h>
#define io_testflag(p,x) ((p)->_flags & (x)) #define io_testflag(p,x) ((p)->_flags & (x))
#include <stdarg.h> #include <stdarg.h>
#if defined(__LONG_LONG_SUPPORTED)
typedef long long printval_s_t;
typedef unsigned long long printval_u_t;
#else
typedef long printval_s_t;
typedef unsigned long printval_u_t;
#endif
#ifdef _ANSI #ifdef _ANSI
int _doprnt(const char *format, va_list ap, FILE *stream); int _doprnt(const char *format, va_list ap, FILE *stream);
int _doscan(FILE * stream, const char *format, va_list ap); int _doscan(FILE * stream, const char *format, va_list ap);
char *_i_compute(unsigned long val, int base, char *s, int nrdigits); char *_i_compute(printval_u_t val, int base, char *s, int nrdigits);
char *_f_print(va_list *ap, int flags, char *s, char c, int precision); char *_f_print(va_list *ap, int flags, char *s, char c, int precision);
void __cleanup(void); void __cleanup(void);
@ -38,3 +47,4 @@ char *_fcvt(long double value, int ndigit, int *decpt, int *sign);
#define FL_SIGNEDCONV 0x0400 /* may contain a sign */ #define FL_SIGNEDCONV 0x0400 /* may contain a sign */
#define FL_NOASSIGN 0x0800 /* do not assign (in scanf) */ #define FL_NOASSIGN 0x0800 /* do not assign (in scanf) */
#define FL_NOMORE 0x1000 /* all flags collected */ #define FL_NOMORE 0x1000 /* all flags collected */
#define FL_LONGLONG 0x2000 /* 64-bit for ints */