C iotest

From RoggeWiki
Revision as of 08:06, 11 June 2015 by Wikiadmin (talk | contribs) (Created page with " #include <stdio.h> #include <stdlib.h> #include <fcntl.h> #include <sys/types.h> #include <time.h> #define MB (1024 * 1024) #define REP_INTERVAL 2 char *Block; c...")
(diff) ← Older revision | Latest revision (diff) | Newer revision → (diff)
Jump to navigation Jump to search
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/types.h>
#include <time.h>

#define MB (1024 * 1024)
#define REP_INTERVAL 2 

char *Block;
char *flname;
long int sz;
long long int lsz, lbytes, tbytes, pos;
int  fd, bs, Rsecs;
time_t start, st2, endt;
int    elaps, speed;
long   int bytes, kbytes;
float  perc;

long int MinSpeed, MaxSpeed;
long int Wspeed, Rspeed, Sspeed;        /* Write, Read, Search          */ 

char *cp;
long long int i;
long long int count;
int  Ln;
/************************************************************************/
void StTest (void)
{
   start    = time(0L);
   st2      = start;
   lbytes   = 0;
   tbytes   = 0;
   Ln       = 0;
   MinSpeed = 0;
   MaxSpeed = 0;
}
/************************************************************************/
void CalcSpeed (long long bytes, time_t st,time_t en)
{
   elaps = en - st;
   if (elaps <= 0)
      speed = 0;
   else
      speed = (unsigned long int) ((bytes / 1024) / elaps); 

   if (speed > MaxSpeed || MaxSpeed == 0)
      MaxSpeed = speed; 

   if (speed < MinSpeed || MinSpeed == 0)
      MinSpeed = speed;

   if ((++Ln % 15) == 0)
      printf("\n");
}
/************************************************************************/
int main (int argc,char **argv)
{
   int flags; 

   if (argc < 4)
   {
      fprintf(stderr,"Ruurd Beerstra's simple I/O performance Measurement Tool.\n");
      fprintf(stderr,"Usage: %s filename MBs BlockSize SeekTime\n",argv[0]);
      fprintf(stderr,"Creates the named file 'filename' and writes BlockSize KB size blocks\n");
      fprintf(stderr,"until the number of MB's is reached.\n");
      fprintf(stderr,"Then it reads the file sequentially, followed by SeekTime\n");
      fprintf(stderr,"seconds of random access. It reports all the achieved speeds. So:\n\n");
      fprintf(stderr,"%s garbage 5000 32 60\n\n",argv[0]);
      fprintf(stderr,"Creates a file 5000 MB in size by writing 32KB blocks, reports the speed,\n");
      fprintf(stderr,"reads the file sequentially, reports the speed, then reads random\n");
      fprintf(stderr,"32 KB blocks from the file for 60 seconds and reports the speed.\n");
      fprintf(stderr,"The file is removed aty the end of the proces.\n");
      fprintf(stderr,"When an environment variable O_DIRECT exists, the file is opened in DIRECT mode.\n");
      fprintf(stderr,"When an environment variable O_CIO exists, the file is opened in Concurent I/O mode.\n");
      fprintf(stderr,"When an environment variable NULL_BLOCK exists, the file contains only bytes with\n");
      fprintf(stderr,"the value zero, otherwise a randomly filled block is used.\n"); 

      exit(1);
   } 

   flname = argv[1];
  sscanf(argv[2],"%d",&sz);            /* Size of the file (MB)        */
  sscanf(argv[3],"%d",&bs);            /* Block size (KB)              */
  sscanf(argv[4],"%d",&Rsecs);         /* Minutes to read random       */
  lsz   = (long long int) sz * (long long) MB;
  bs    = bs * 1024;
  Block = calloc(bs,1);
  if (!Block)
  {
     printf("Out of memory\n");
     exit(1);
  }
  srand(time(0L));
  count = ((lsz / ((long long) bs))) + 1;
  printf("Creating file %s of %ld MB (%lld blocks of %d bytes, or %lld bytes)...\n",flname,sz,count,bs,lsz);
  if (getenv("NULL_BLOCK") == NULL)
  {
     printf("Using a block filled with RANDOM data\n");
     cp = Block;
     for (i = 0; i < bs; i++)          /* Initialize with garbage      */
        *cp++ = (unsigned char) (drand48() * 256);
  }
  else
     printf("Using a block filled with NULL bytes\n");
  printf("Removing file %s...",flname); fflush(stdout);
  unlink(flname);
  printf("Done\n");
  flags = O_CREAT | O_RDWR;
  if (getenv("O_DIRECT"))
     flags |= O_DIRECT;
  if (getenv("O_CIO"))
     flags |= O_CIO;
  fd = open64(flname,flags,0666);
  if (fd < 0)
  {
     perror("open");
     exit(1);
  }
  StTest();
  for (i = 0; i < count; i++)
  {
     if (write(fd,Block,bs) != bs)
     {
        perror("write");
        exit(1);
     }
     lbytes += bs;
     tbytes += bs;
     endt = time(0L);
     if (endt >= st2 + REP_INTERVAL)
     {
        perc = (float) ((tbytes * 100) / lsz);
        CalcSpeed(lbytes,st2,endt);
        printf("Sequential write speed: %d KB/sec, %3.2f%% done \r",speed,perc);
        fflush(stdout);
        lbytes = 0;
        st2    = endt;
     }
  }
  CalcSpeed(tbytes,start,time(0L));
  printf("\nSummary: wrote %ldMB in %d secs: %ld KB/sec, Min=%d, Max=%d\n",sz,elaps,speed,MinSpeed,MaxSpeed);
  printf("Syncing file (flush cache)..."); fflush(stdout);
  fsync(fd);
  CalcSpeed(tbytes,start,time(0L));
  printf("done!  Adjusted speed (with sync): %ld KB/sec, Min=%d, Max=%d\n",speed,MinSpeed,MaxSpeed);
  Wspeed = speed;
  printf("Reading sequentially...\n");
  llseek(fd,0,0);
  StTest();
  while (read(fd,Block,bs) == bs)
  {
     lbytes += bs;
     tbytes += bs;
     endt = time(0L);
     if (endt >= st2 + REP_INTERVAL)
     {
        perc  = (float) ((tbytes * 100) / lsz);
        CalcSpeed(lbytes,st2,endt);
        printf("Sequential read speed: %d KB/sec, %3.2f%% done \r",speed,perc);
        fflush(stdout);
        lbytes = 0;
        st2    = endt;
     }
  }
  CalcSpeed(tbytes,start,time(0L));
  printf("\nSummary: Read %ldMB in %d secs: %ld KB/sec, Min=%d, Max=%d\n",sz,elaps,speed,MinSpeed,MaxSpeed);
  Rspeed = speed;
  printf("Reading random positions of %d KB\n",bs / 1024);
  StTest();
  Rsecs  = time(0L) + Rsecs;
  while (time(0L) < Rsecs)
   {
      pos = (lsz * drand48());
      pos = pos / 4096;                 /* Afronden op 4KB page         */
      pos = pos * 4096;
      llseek(fd,pos,0);                 /* Large seek                   */
      if (read(fd,Block,bs) != bs)      /* groot block lezen.           */
         perror("Read error");

      lbytes += bs;
      tbytes += bs;
      count++; 

      endt = time(0L);
      if (endt >= st2 + REP_INTERVAL)
      {
         CalcSpeed(lbytes,st2,endt);
         printf("Random read speed: %d KB/sec, %lld Reads of %ld KB \r",speed,count,bs / 1024);
         fflush(stdout);

         lbytes = 0;
         count  = 0;
         st2    = endt;
      }
   }

   endt  = time(0L);
   CalcSpeed(tbytes,start,endt);
   printf("\nSummary: Read %ldMB in %d secs: %ld KB/sec, Min=%d, Max=%d\n",tbytes / MB,elaps,speed,MinSpeed,MaxSpeed);
   Sspeed = speed;

   printf("Einde test: Write: %ld KB/sec, Read: %ld KB/sec, Seek: %ld KB/sec\n",Wspeed,Rspeed,Sspeed);
   printf("Removing file %s\n",flname);
   unlink(flname);
  exit(0);
}
/************************************************************************/