Commit 9cd5e5c0 authored by Philip Carns's avatar Philip Carns

get fscanf working

- includes regression test for fprintf and fscanf
- apparently you have to wrap __isoc99_fscanf instead of fscanf
  sometimes
parent 106767d3
......@@ -6,8 +6,6 @@
/* TODO list (general) for this module:
* - add stdio page to darshan-job-summary
* - add regression test cases for all functions captured here
* - especially the scanf and printf variants with variable arguments
* - figure out what to do about posix module compatibility
* - remove stdio counters in POSIX or keep and set to -1?
* - affected counters in posix module:
......@@ -117,6 +115,7 @@ DARSHAN_FORWARD_DECL(getw, int, (FILE *stream));
DARSHAN_FORWARD_DECL(_IO_getc, int, (FILE *stream));
DARSHAN_FORWARD_DECL(_IO_putc, int, (int, FILE *stream));
DARSHAN_FORWARD_DECL(fscanf, int, (FILE *stream, const char *format, ...));
DARSHAN_FORWARD_DECL(__isoc99_fscanf, int, (FILE *stream, const char *format, ...));
DARSHAN_FORWARD_DECL(vfscanf, int, (FILE *stream, const char *format, va_list ap));
DARSHAN_FORWARD_DECL(fgets, char*, (char *s, int size, FILE *stream));
DARSHAN_FORWARD_DECL(fseek, int, (FILE *stream, long offset, int whence));
......@@ -672,6 +671,38 @@ size_t DARSHAN_DECL(getw)(FILE *stream)
return(ret);
}
/* NOTE: some glibc versions use __isoc99_fscanf as the underlying symbol
* rather than fscanf
*/
int DARSHAN_DECL(__isoc99_fscanf)(FILE *stream, const char *format, ...)
{
int ret;
double tm1, tm2;
va_list ap;
long start_off, end_off;
MAP_OR_FAIL(vfscanf);
tm1 = darshan_core_wtime();
/* NOTE: we intentionally switch to vfscanf here to handle the variable
* length arguments.
*/
start_off = ftell(stream);
va_start(ap, format);
ret = __real_vfscanf(stream, format, ap);
va_end(ap);
end_off = ftell(stream);
tm2 = darshan_core_wtime();
STDIO_LOCK();
stdio_runtime_initialize();
if(ret != 0)
STDIO_RECORD_READ(stream, (end_off-start_off), tm1, tm2);
STDIO_UNLOCK();
return(ret);
}
int DARSHAN_DECL(fscanf)(FILE *stream, const char *format, ...)
{
......
......@@ -26,3 +26,4 @@
--wrap=fsetpos
--wrap=fsetpos64
--wrap=rewind
--wrap=__isoc99_fscanf
#!/bin/bash
PROG=fprintf-fscanf-test
# set log file path; remove previous log if present
export DARSHAN_LOGFILE=$DARSHAN_TMP/${PROG}.darshan
rm -f ${DARSHAN_LOGFILE}
# compile
$DARSHAN_CC $DARSHAN_TESTDIR/test-cases/src/${PROG}.c -o $DARSHAN_TMP/${PROG}
if [ $? -ne 0 ]; then
echo "Error: failed to compile ${PROG}" 1>&2
exit 1
fi
# execute
$DARSHAN_RUNJOB $DARSHAN_TMP/${PROG} -f $DARSHAN_TMP/${PROG}.tmp.dat
if [ $? -ne 0 ]; then
echo "Error: failed to execute ${PROG}" 1>&2
exit 1
fi
# parse log
$DARSHAN_PATH/bin/darshan-parser $DARSHAN_LOGFILE > $DARSHAN_TMP/${PROG}.darshan.txt
if [ $? -ne 0 ]; then
echo "Error: failed to parse ${DARSHAN_LOGFILE}" 1>&2
exit 1
fi
# check results
STDIO_OPENS=`grep STDIO_OPENS $DARSHAN_TMP/${PROG}.darshan.txt | cut -f 5`
if [ ! "$STDIO_OPENS" -eq 4 ]; then
echo "Error: STDIO open count of $STDIO_OPENS is incorrect" 1>&2
exit 1
fi
# this will check fprintf counting
STDIO_BYTES_WRITTEN=`grep STDIO_BYTES_WRITTEN $DARSHAN_TMP/${PROG}.darshan.txt | cut -f 5`
if [ ! "$STDIO_BYTES_WRITTEN" -eq 15 ]; then
echo "Error: STDIO bytes written count of $STDIO_BYTES_WRITTEN is incorrect" 1>&2
exit 1
fi
# this will check fscanf counting
STDIO_BYTES_READ=`grep STDIO_BYTES_READ $DARSHAN_TMP/${PROG}.darshan.txt | cut -f 5`
if [ ! "$STDIO_BYTES_READ" -eq 15 ]; then
echo "Error: STDIO bytes read count of $STDIO_BYTES_READ is incorrect" 1>&2
exit 1
fi
exit 0
/*
* (C) 1995-2001 Clemson University and Argonne National Laboratory.
*
* See COPYING in top-level directory.
*/
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#include <sys/time.h>
#include <mpi.h>
#include <errno.h>
#include <getopt.h>
/* DEFAULT VALUES FOR OPTIONS */
static char opt_file[256] = "test-fprintf-fscanf.out";
/* function prototypes */
static int parse_args(int argc, char **argv);
static void usage(void);
/* global vars */
static int mynod = 0;
static int nprocs = 1;
int main(int argc, char **argv)
{
int namelen;
char processor_name[MPI_MAX_PROCESSOR_NAME];
FILE *file;
char buffer[128] = {0};
int number = 0;
/* startup MPI and determine the rank of this process */
MPI_Init(&argc,&argv);
MPI_Comm_size(MPI_COMM_WORLD, &nprocs);
MPI_Comm_rank(MPI_COMM_WORLD, &mynod);
MPI_Get_processor_name(processor_name, &namelen);
/* parse the command line arguments */
parse_args(argc, argv);
if (mynod == 0) printf("# Using stdio calls.\n");
file = fopen(opt_file, "w+");
if(!file)
{
perror("fopen");
return(-1);
}
if(mynod == 0)
{
fprintf(file, "a number: %d", 12345);
fseek(file, 0, SEEK_SET);
fscanf(file, "a number: %d", &number);
}
fclose(file);
MPI_Finalize();
return(0);
}
static int parse_args(int argc, char **argv)
{
int c;
while ((c = getopt(argc, argv, "f:")) != EOF) {
switch (c) {
case 'f': /* filename */
strncpy(opt_file, optarg, 255);
break;
case '?': /* unknown */
if (mynod == 0)
usage();
exit(1);
default:
break;
}
}
return(0);
}
static void usage(void)
{
printf("Usage: stdio-test [<OPTIONS>...]\n");
printf("\n<OPTIONS> is one of\n");
printf(" -f filename [default: /foo/test.out]\n");
printf(" -h print this help\n");
}
/*
* Local variables:
* c-indent-level: 3
* c-basic-offset: 3
* tab-width: 3
*
* vim: ts=3
* End:
*/
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment