[Bug c/15058] New: unsigned long long mishandled in function's va_args list

BStrauss-gcc at feliscatus dot org gcc-bugzilla@gcc.gnu.org
Wed Apr 21 22:38:00 GMT 2004


Using the test program below, there is a specious NULL entry in the va_args 
list.

Output (unsigned long case, then unsigned long long case):

Test: # c %d - %s
          1....%d: 0x00000000 '0'
          2....%s: 0x08048868 'nonsense'
Test: # c %d - %s %s
          1....%d: 0x00000000 '0'
          2....%s: 0x00000000 '(null)'
          3....%s: 0x0804887e 'stuff'

(See the #2 - NULL)

Test program:
===============================================================
$ cat x.c
#include <stdio.h>
#include <time.h>
#include <unistd.h>
#include <stdarg.h>

static void fnprintf(FILE* fd, char* buf, size_t sizeofbuf, char* format, ...) 
{

  va_list va_ap;
  int rc;

#ifdef DEBUG
  int cnt=0, d;
  char *s, *fmt, *fmtSave;

  printf("Test:\n%s\n", format);

  va_start (va_ap, format);

  fmtSave = fmt = (char*)strdup(format);
  while (fmt[0] != '\0') {
    if(fmt[0] == '%') {
      fmt++;
      if(fmt[0] == '-') fmt++;
      while((fmt[0] >= '0') && (fmt[0] <= '9')) fmt++;
      switch(fmt[0]) {
        case 's': /* string */
          s = va_arg(va_ap, char *);
          printf("\t%3d....%%s: 0x%08x '%s'\n", ++cnt, s, s);
          break;
        case 'd': /* int */
          d = va_arg(va_ap, int);
          printf("\t%3d....%%d: 0x%08x '%d'\n", ++cnt, d, d);
          break;
      }
    }
    fmt++;
  }
  if(fmtSave != NULL) free(fmtSave);
  va_end(va_ap);
#endif

  memset(&va_ap, 0, sizeof(va_ap));

  va_start (va_ap, format);

  rc = vsnprintf(buf, sizeofbuf, format, va_ap);
  
  if((rc < 0) || (rc >= sizeofbuf))
    printf("Buffer too short");
  else 
    fwrite(buf, 1, strlen(buf), fd);

  va_end (va_ap);
}

int main(int argc, char *argv[]) {
  char buf[200];
  FILE* fd;
  unsigned long long ullCount[3];
  unsigned long ulCount[3];

  printf("started\n");

  memset(&buf, 0, sizeof(buf));
  memset(&ulCount, 0, sizeof(ulCount));
  memset(&ullCount, 0, sizeof(ullCount));

  fd = fopen("/tmp/junk", "w");

  fnprintf(fd, buf, sizeof(buf), "# c %d - %s\n", ulCount[2], "nonsense");
  fnprintf(fd, buf, sizeof(buf), "# c %d - %s %s\n", ullCount[2], "stuff");

  fclose(fd);
}

===============================================================

Compile lines are (to show the list):
$ gcc -g -o x x.c -DDEBUG

or (no list)
$ gcc -g -o x x.c

Either case, run:

$ ./x

Output in

$ cat /tmp/junk

# c 0 - nonsense
# c 0 - (null) stuff


==============================================================

$ gcc -v
Reading specs from /usr/lib/gcc-lib/i386-redhat-linux/3.2.2/specs
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man --
infodir=/usr/share/info --enable-shared --enable-threads=posix --disable-
checking --with-system-zlib --enable-__cxa_atexit --host=i386-redhat-linux
Thread model: posix
gcc version 3.2.2 20030222 (Red Hat Linux 3.2.2-5)

-- 
           Summary: unsigned long long mishandled in function's va_args list
           Product: gcc
           Version: 3.2.2
            Status: UNCONFIRMED
          Severity: normal
          Priority: P2
         Component: c
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: BStrauss-gcc at feliscatus dot org
                CC: gcc-bugs at gcc dot gnu dot org
 GCC build triplet: i686-pc-linux-gnu
  GCC host triplet: i686-pc-linux-gnu
GCC target triplet: i686-pc-linux-gnu


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=15058



More information about the Gcc-bugs mailing list