IOR
parse_options.c
Go to the documentation of this file.
1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2  * vim:expandtab:shiftwidth=8:tabstop=8:
3  */
4 /******************************************************************************\
5 * *
6 * Copyright (c) 2003, The Regents of the University of California *
7 * See the file COPYRIGHT for a complete copyright notice and license. *
8 * *
9 ********************************************************************************
10 *
11 * Parse commandline functions.
12 *
13 \******************************************************************************/
14 
15 #ifdef HAVE_CONFIG_H
16 #include "config.h"
17 #endif
18 
19 #include <stdio.h>
20 #include <stdlib.h>
21 #include <ctype.h>
22 #include <string.h>
23 
24 
25 #include "utilities.h"
26 #include "ior.h"
27 #include "aiori.h"
28 #include "parse_options.h"
29 #include "option.h"
30 #include "aiori.h"
31 
32 #define ISPOWEROFTWO(x) ((x != 0) && !(x & (x - 1)))
33 
35 
36 
37 static size_t NodeMemoryStringToBytes(char *size_str)
38 {
39  int percent;
40  int rc;
41  long page_size;
42  long num_pages;
43  long long mem;
44 
45  rc = sscanf(size_str, " %d %% ", &percent);
46  if (rc == 0)
47  return (size_t) string_to_bytes(size_str);
48  if (percent > 100 || percent < 0)
49  ERR("percentage must be between 0 and 100");
50 
51  page_size = sysconf(_SC_PAGESIZE);
52 #ifdef _SC_PHYS_PAGES
53  num_pages = sysconf(_SC_PHYS_PAGES);
54  if (num_pages == -1)
55  ERR("sysconf(_SC_PHYS_PAGES) is not supported");
56 #else
57  ERR("sysconf(_SC_PHYS_PAGES) is not supported");
58 #endif
59  mem = page_size * num_pages;
60 
61  return mem / 100 * percent;
62 }
63 
64 
65 /*
66  * Check and correct all settings of each test in queue for correctness.
67  */
68 static void CheckRunSettings(IOR_test_t *tests)
69 {
70  IOR_test_t *ptr;
71  IOR_param_t *params;
72 
73  for (ptr = tests; ptr != NULL; ptr = ptr->next) {
74  params = &ptr->params;
75 
76  /* If no write/read/check action requested, set both write and read */
77  if (params->writeFile == FALSE
78  && params->readFile == FALSE
79  && params->checkWrite == FALSE
80  && params->checkRead == FALSE) {
81  params->readFile = TRUE;
82  params->writeFile = TRUE;
83  }
84 
85  /* If only read or write is requested, then fix the default
86  * openFlags to not be open RDWR. It matters in the case
87  * of HDFS, which doesn't support opening RDWR.
88  * (We assume int-valued params are exclusively 0 or 1.)
89  */
90  if ((params->openFlags & IOR_RDWR)
91  && ((params->readFile | params->checkRead)
92  ^ (params->writeFile | params->checkWrite))
93  && (params->openFlags & IOR_RDWR)) {
94 
95  params->openFlags &= ~(IOR_RDWR);
96  if (params->readFile | params->checkRead) {
97  params->openFlags |= IOR_RDONLY;
98  params->openFlags &= ~(IOR_CREAT|IOR_EXCL);
99  }
100  else
101  params->openFlags |= IOR_WRONLY;
102  }
103 
104  }
105 }
106 
107 /*
108  * Set flags from commandline string/value pairs.
109  */
110 void DecodeDirective(char *line, IOR_param_t *params)
111 {
112  char option[MAX_STR];
113  char value[MAX_STR];
114  int rc;
115  int initialized;
116 
117  rc = sscanf(line, " %[^=# \t\r\n] = %[^# \t\r\n] ", option, value);
118  if (rc != 2 && rank == 0) {
119  fprintf(out_logfile, "Syntax error in configuration options: %s\n",
120  line);
121  MPI_CHECK(MPI_Initialized(&initialized), "MPI_Initialized() error");
122  if (initialized)
123  MPI_CHECK(MPI_Abort(MPI_COMM_WORLD, -1), "MPI_Abort() error");
124  else
125  exit(-1);
126  }
127  if (strcasecmp(option, "api") == 0) {
128  params->api = strdup(value);
129  } else if (strcasecmp(option, "summaryFile") == 0) {
130  if (rank == 0){
131  out_resultfile = fopen(value, "w");
132  if (out_resultfile == NULL){
133  FAIL("Cannot open output file for writes!");
134  }
135  printf("Writing output to %s\n", value);
136  }
137  } else if (strcasecmp(option, "summaryFormat") == 0) {
138  if(strcasecmp(value, "default") == 0){
140  }else if(strcasecmp(value, "JSON") == 0){
142  }else if(strcasecmp(value, "CSV") == 0){
144  }else{
145  FAIL("Unknown summaryFormat");
146  }
147  } else if (strcasecmp(option, "refnum") == 0) {
148  params->referenceNumber = atoi(value);
149  } else if (strcasecmp(option, "debug") == 0) {
150  params->debug = strdup(value);
151  } else if (strcasecmp(option, "platform") == 0) {
152  params->platform = strdup(value);
153  } else if (strcasecmp(option, "testfile") == 0) {
154  params->testFileName = strdup(value);
155  } else if (strcasecmp(option, "hintsfilename") == 0) {
156  params->hintsFileName = strdup(value);
157  } else if (strcasecmp(option, "deadlineforstonewalling") == 0) {
158  params->deadlineForStonewalling = atoi(value);
159  } else if (strcasecmp(option, "stoneWallingWearOut") == 0) {
160  params->stoneWallingWearOut = atoi(value);
161  } else if (strcasecmp(option, "stoneWallingWearOutIterations") == 0) {
162  params->stoneWallingWearOutIterations = atoll(value);
163  } else if (strcasecmp(option, "stoneWallingStatusFile") == 0) {
164  params->stoneWallingStatusFile = strdup(value);
165  } else if (strcasecmp(option, "maxtimeduration") == 0) {
166  params->maxTimeDuration = atoi(value);
167  } else if (strcasecmp(option, "outlierthreshold") == 0) {
168  params->outlierThreshold = atoi(value);
169  } else if (strcasecmp(option, "nodes") == 0) {
170  params->nodes = atoi(value);
171  } else if (strcasecmp(option, "repetitions") == 0) {
172  params->repetitions = atoi(value);
173  } else if (strcasecmp(option, "intertestdelay") == 0) {
174  params->interTestDelay = atoi(value);
175  } else if (strcasecmp(option, "readfile") == 0) {
176  params->readFile = atoi(value);
177  } else if (strcasecmp(option, "writefile") == 0) {
178  params->writeFile = atoi(value);
179  } else if (strcasecmp(option, "fileperproc") == 0) {
180  params->filePerProc = atoi(value);
181  } else if (strcasecmp(option, "taskpernodeoffset") == 0) {
182  params->taskPerNodeOffset = atoi(value);
183  } else if (strcasecmp(option, "reordertasksconstant") == 0) {
184  params->reorderTasks = atoi(value);
185  } else if (strcasecmp(option, "reordertasksrandom") == 0) {
186  params->reorderTasksRandom = atoi(value);
187  } else if (strcasecmp(option, "reordertasksrandomSeed") == 0) {
188  params->reorderTasksRandomSeed = atoi(value);
189  } else if (strcasecmp(option, "reordertasks") == 0) {
190  /* Backwards compatibility for the "reorderTasks" option.
191  MUST follow the other longer reordertasks checks. */
192  params->reorderTasks = atoi(value);
193  } else if (strcasecmp(option, "checkwrite") == 0) {
194  params->checkWrite = atoi(value);
195  } else if (strcasecmp(option, "checkread") == 0) {
196  params->checkRead = atoi(value);
197  } else if (strcasecmp(option, "keepfile") == 0) {
198  params->keepFile = atoi(value);
199  } else if (strcasecmp(option, "keepfilewitherror") == 0) {
200  params->keepFileWithError = atoi(value);
201  } else if (strcasecmp(option, "multiFile") == 0) {
202  params->multiFile = atoi(value);
203  } else if (strcasecmp(option, "quitonerror") == 0) {
204  params->quitOnError = atoi(value);
205  } else if (strcasecmp(option, "segmentcount") == 0) {
206  params->segmentCount = string_to_bytes(value);
207  } else if (strcasecmp(option, "blocksize") == 0) {
208  params->blockSize = string_to_bytes(value);
209  } else if (strcasecmp(option, "transfersize") == 0) {
210  params->transferSize = string_to_bytes(value);
211  } else if (strcasecmp(option, "setalignment") == 0) {
212  params->setAlignment = string_to_bytes(value);
213  } else if (strcasecmp(option, "singlexferattempt") == 0) {
214  params->singleXferAttempt = atoi(value);
215  } else if (strcasecmp(option, "individualdatasets") == 0) {
216  params->individualDataSets = atoi(value);
217  } else if (strcasecmp(option, "intraTestBarriers") == 0) {
218  params->intraTestBarriers = atoi(value);
219  } else if (strcasecmp(option, "nofill") == 0) {
220  params->noFill = atoi(value);
221  } else if (strcasecmp(option, "verbose") == 0) {
222  params->verbose = atoi(value);
223  } else if (strcasecmp(option, "settimestampsignature") == 0) {
224  params->setTimeStampSignature = atoi(value);
225  } else if (strcasecmp(option, "collective") == 0) {
226  params->collective = atoi(value);
227  } else if (strcasecmp(option, "preallocate") == 0) {
228  params->preallocate = atoi(value);
229  } else if (strcasecmp(option, "storefileoffset") == 0) {
230  params->storeFileOffset = atoi(value);
231  } else if (strcasecmp(option, "usefileview") == 0) {
232  params->useFileView = atoi(value);
233  } else if (strcasecmp(option, "usesharedfilepointer") == 0) {
234  params->useSharedFilePointer = atoi(value);
235  } else if (strcasecmp(option, "useo_direct") == 0) {
236  params->useO_DIRECT = atoi(value);
237  } else if (strcasecmp(option, "usestrideddatatype") == 0) {
238  params->useStridedDatatype = atoi(value);
239  } else if (strcasecmp(option, "showhints") == 0) {
240  params->showHints = atoi(value);
241  } else if (strcasecmp(option, "uniqueDir") == 0) {
242  params->uniqueDir = atoi(value);
243  } else if (strcasecmp(option, "useexistingtestfile") == 0) {
244  params->useExistingTestFile = atoi(value);
245  } else if (strcasecmp(option, "fsyncperwrite") == 0) {
246  params->fsyncPerWrite = atoi(value);
247  } else if (strcasecmp(option, "fsync") == 0) {
248  params->fsync = atoi(value);
249  } else if (strcasecmp(option, "randomoffset") == 0) {
250  params->randomOffset = atoi(value);
251  } else if (strcasecmp(option, "memoryPerTask") == 0) {
252  params->memoryPerTask = string_to_bytes(value);
253  params->memoryPerNode = 0;
254  } else if (strcasecmp(option, "memoryPerNode") == 0) {
255  params->memoryPerNode = NodeMemoryStringToBytes(value);
256  params->memoryPerTask = 0;
257  } else if (strcasecmp(option, "lustrestripecount") == 0) {
258 #ifndef HAVE_LUSTRE_LUSTRE_USER_H
259  ERR("ior was not compiled with Lustre support");
260 #endif
261  params->lustre_stripe_count = atoi(value);
262  params->lustre_set_striping = 1;
263  } else if (strcasecmp(option, "lustrestripesize") == 0) {
264 #ifndef HAVE_LUSTRE_LUSTRE_USER_H
265  ERR("ior was not compiled with Lustre support");
266 #endif
267  params->lustre_stripe_size = string_to_bytes(value);
268  params->lustre_set_striping = 1;
269  } else if (strcasecmp(option, "lustrestartost") == 0) {
270 #ifndef HAVE_LUSTRE_LUSTRE_USER_H
271  ERR("ior was not compiled with Lustre support");
272 #endif
273  params->lustre_start_ost = atoi(value);
274  params->lustre_set_striping = 1;
275  } else if (strcasecmp(option, "lustreignorelocks") == 0) {
276 #ifndef HAVE_LUSTRE_LUSTRE_USER_H
277  ERR("ior was not compiled with Lustre support");
278 #endif
279  params->lustre_ignore_locks = atoi(value);
280  } else if (strcasecmp(option, "gpfshintaccess") == 0) {
281 #ifndef HAVE_GPFS_FCNTL_H
282  ERR("ior was not compiled with GPFS hint support");
283 #endif
284  params->gpfs_hint_access = atoi(value);
285  } else if (strcasecmp(option, "gpfsreleasetoken") == 0) {
286 #ifndef HAVE_GPFS_FCNTL_H
287  ERR("ior was not compiled with GPFS hint support");
288 #endif
289  params->gpfs_release_token = atoi(value);
290  } else if (strcasecmp(option, "beegfsNumTargets") == 0) {
291 #ifndef HAVE_BEEGFS_BEEGFS_H
292  ERR("ior was not compiled with BeeGFS support");
293 #endif
294  params->beegfs_numTargets = atoi(value);
295  if (params->beegfs_numTargets < 1)
296  ERR("beegfsNumTargets must be >= 1");
297  } else if (strcasecmp(option, "beegfsChunkSize") == 0) {
298  #ifndef HAVE_BEEGFS_BEEGFS_H
299  ERR("ior was not compiled with BeeGFS support");
300  #endif
301  params->beegfs_chunkSize = string_to_bytes(value);
302  if (!ISPOWEROFTWO(params->beegfs_chunkSize) || params->beegfs_chunkSize < (1<<16))
303  ERR("beegfsChunkSize must be a power of two and >64k");
304  } else if (strcasecmp(option, "numtasks") == 0) {
305  params->numTasks = atoi(value);
306  } else if (strcasecmp(option, "summaryalways") == 0) {
307  params->summary_every_test = atoi(value);
308  } else {
309  if (rank == 0)
310  fprintf(out_logfile, "Unrecognized parameter \"%s\"\n",
311  option);
312  MPI_CHECK(MPI_Initialized(&initialized), "MPI_Initialized() error");
313  if (initialized)
314  MPI_CHECK(MPI_Abort(MPI_COMM_WORLD, -1), "MPI_Abort() error");
315  else
316  exit(-1);
317  }
318 }
319 
320 /*
321  * Parse a single line, which may contain multiple comma-seperated directives
322  */
323 void ParseLine(char *line, IOR_param_t * test)
324 {
325  char *start, *end;
326 
327  start = line;
328  do {
329  end = strchr(start, ',');
330  if (end != NULL)
331  *end = '\0';
332  DecodeDirective(start, test);
333  start = end + 1;
334  } while (end != NULL);
335 }
336 
337 /*
338  * Determines if the string "haystack" contains only the string "needle", and
339  * possibly whitespace before and after needle. Function is case insensitive.
340  */
341 int contains_only(char *haystack, char *needle)
342 {
343  char *ptr, *end;
344 
345  end = haystack + strlen(haystack);
346  /* skip over leading shitspace */
347  for (ptr = haystack; ptr < end; ptr++) {
348  if (!isspace(*ptr))
349  break;
350  }
351  /* check for "needle" */
352  if (strncasecmp(ptr, needle, strlen(needle)) != 0)
353  return 0;
354  /* make sure the rest of the line is only whitspace as well */
355  for (ptr += strlen(needle); ptr < end; ptr++) {
356  if (!isspace(*ptr))
357  return 0;
358  }
359 
360  return 1;
361 }
362 
363 /*
364  * Read the configuration script, allocating and filling in the structure of
365  * global parameters.
366  */
367 IOR_test_t *ReadConfigScript(char *scriptName)
368 {
369  int test_num = 0;
370  int runflag = 0;
371  char linebuf[MAX_STR];
372  char empty[MAX_STR];
373  FILE *file;
374  IOR_test_t *head = NULL;
375  IOR_test_t *tail = NULL;
376 
377  /* Initialize the first test */
378  head = CreateTest(&initialTestParams, test_num++);
379  tail = head;
380 
381  /* open the script */
382  file = fopen(scriptName, "r");
383  if (file == NULL)
384  ERR("fopen() failed");
385 
386  /* search for the "IOR START" line */
387  while (fgets(linebuf, MAX_STR, file) != NULL) {
388  if (contains_only(linebuf, "ior start")) {
389  break;
390  }
391  }
392 
393  /* Iterate over a block of IOR commands */
394  while (fgets(linebuf, MAX_STR, file) != NULL) {
395  /* skip empty lines */
396  if (sscanf(linebuf, "%s", empty) == -1)
397  continue;
398  /* skip lines containing only comments */
399  if (sscanf(linebuf, " #%s", empty) == 1)
400  continue;
401  if (contains_only(linebuf, "ior stop")) {
402  break;
403  } else if (contains_only(linebuf, "run")) {
404  if (runflag) {
405  /* previous line was a "run" as well
406  create duplicate test */
407  tail->next = CreateTest(&tail->params, test_num++);
408  AllocResults(tail);
409  tail = tail->next;
410  }
411  runflag = 1;
412  } else if (runflag) {
413  /* If this directive was preceded by a "run" line, then
414  create and initialize a new test structure */
415  runflag = 0;
416  tail->next = CreateTest(&tail->params, test_num++);
417  AllocResults(tail);
418  tail = tail->next;
419  ParseLine(linebuf, &tail->params);
420  } else {
421  ParseLine(linebuf, &tail->params);
422  }
423  }
424 
425  /* close the script */
426  if (fclose(file) != 0)
427  ERR("fclose() of script file failed");
428  AllocResults(tail);
429 
430  return head;
431 }
432 
433 
435 
436 static void decodeDirectiveWrapper(char *line){
437  DecodeDirective(line, parameters);
438 }
439 
440 /*
441  * Parse Commandline.
442  */
443 IOR_test_t *ParseCommandLine(int argc, char **argv)
444 {
445  char * testscripts = NULL;
446  int toggleG = FALSE;
447  char * buffer_type = "";
448  char * memoryPerNode = NULL;
449  init_IOR_Param_t(& initialTestParams);
450  parameters = & initialTestParams;
451 
452  char APIs[1024];
453  aiori_supported_apis(APIs);
454  char apiStr[1024];
455  sprintf(apiStr, "API for I/O [%s]", APIs);
456 
457  option_help options [] = {
458  {'a', NULL, apiStr, OPTION_OPTIONAL_ARGUMENT, 's', & initialTestParams.api},
459  {'A', NULL, "refNum -- user supplied reference number to include in the summary", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.referenceNumber},
460  {'b', NULL, "blockSize -- contiguous bytes to write per task (e.g.: 8, 4k, 2m, 1g)", OPTION_OPTIONAL_ARGUMENT, 'l', & initialTestParams.blockSize},
461  {'B', NULL, "useO_DIRECT -- uses O_DIRECT for POSIX, bypassing I/O buffers", OPTION_FLAG, 'd', & initialTestParams.useO_DIRECT},
462  {'c', NULL, "collective -- collective I/O", OPTION_FLAG, 'd', & initialTestParams.collective},
463  {'C', NULL, "reorderTasks -- changes task ordering to n+1 ordering for readback", OPTION_FLAG, 'd', & initialTestParams.reorderTasks},
464  {'d', NULL, "interTestDelay -- delay between reps in seconds", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.interTestDelay},
465  {'D', NULL, "deadlineForStonewalling -- seconds before stopping write or read phase", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.deadlineForStonewalling},
466  {.help=" -O stoneWallingWearOut=1 -- once the stonewalling timout is over, all process finish to access the amount of data", .arg = OPTION_OPTIONAL_ARGUMENT},
467  {.help=" -O stoneWallingWearOutIterations=N -- stop after processing this number of iterations, needed for reading data back written with stoneWallingWearOut", .arg = OPTION_OPTIONAL_ARGUMENT},
468  {.help=" -O stoneWallingStatusFile=FILE -- this file keeps the number of iterations from stonewalling during write and allows to use them for read", .arg = OPTION_OPTIONAL_ARGUMENT},
469  {'e', NULL, "fsync -- perform sync operation after each block write", OPTION_FLAG, 'd', & initialTestParams.fsync},
470  {'E', NULL, "useExistingTestFile -- do not remove test file before write access", OPTION_FLAG, 'd', & initialTestParams.useExistingTestFile},
471  {'f', NULL, "scriptFile -- test script name", OPTION_OPTIONAL_ARGUMENT, 's', & testscripts},
472  {'F', NULL, "filePerProc -- file-per-process", OPTION_FLAG, 'd', & initialTestParams.filePerProc},
473  {'g', NULL, "intraTestBarriers -- use barriers between open, write/read, and close", OPTION_FLAG, 'd', & initialTestParams.intraTestBarriers},
474  /* This option toggles between Incompressible Seed and Time stamp sig based on -l,
475  * so we'll toss the value in both for now, and sort it out in initialization
476  * after all the arguments are in and we know which it keep.
477  */
478  {'G', NULL, "setTimeStampSignature -- set value for time stamp signature/random seed", OPTION_OPTIONAL_ARGUMENT, 'd', & toggleG},
479  {'H', NULL, "showHints -- show hints", OPTION_FLAG, 'd', & initialTestParams.showHints},
480  {'i', NULL, "repetitions -- number of repetitions of test", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.repetitions},
481  {'I', NULL, "individualDataSets -- datasets not shared by all procs [not working]", OPTION_FLAG, 'd', & initialTestParams.individualDataSets},
482  {'j', NULL, "outlierThreshold -- warn on outlier N seconds from mean", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.outlierThreshold},
483  {'J', NULL, "setAlignment -- HDF5 alignment in bytes (e.g.: 8, 4k, 2m, 1g)", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.setAlignment},
484  {'k', NULL, "keepFile -- don't remove the test file(s) on program exit", OPTION_FLAG, 'd', & initialTestParams.keepFile},
485  {'K', NULL, "keepFileWithError -- keep error-filled file(s) after data-checking", OPTION_FLAG, 'd', & initialTestParams.keepFileWithError},
486  {'l', NULL, "datapacket type-- type of packet that will be created [offset|incompressible|timestamp|o|i|t]", OPTION_OPTIONAL_ARGUMENT, 's', & buffer_type},
487  {'m', NULL, "multiFile -- use number of reps (-i) for multiple file count", OPTION_FLAG, 'd', & initialTestParams.multiFile},
488  {'M', NULL, "memoryPerNode -- hog memory on the node (e.g.: 2g, 75%)", OPTION_OPTIONAL_ARGUMENT, 's', & memoryPerNode},
489  {'n', NULL, "noFill -- no fill in HDF5 file creation", OPTION_FLAG, 'd', & initialTestParams.noFill},
490  {'N', NULL, "numTasks -- number of tasks that should participate in the test", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.numTasks},
491  {'o', NULL, "testFile -- full name for test", OPTION_OPTIONAL_ARGUMENT, 's', & initialTestParams.testFileName},
492  {'O', NULL, "string of IOR directives (e.g. -O checkRead=1,lustreStripeCount=32)", OPTION_OPTIONAL_ARGUMENT, 'p', & decodeDirectiveWrapper},
493  {'p', NULL, "preallocate -- preallocate file size", OPTION_FLAG, 'd', & initialTestParams.preallocate},
494  {'P', NULL, "useSharedFilePointer -- use shared file pointer [not working]", OPTION_FLAG, 'd', & initialTestParams.useSharedFilePointer},
495  {'q', NULL, "quitOnError -- during file error-checking, abort on error", OPTION_FLAG, 'd', & initialTestParams.quitOnError},
496  {'Q', NULL, "taskPerNodeOffset for read tests use with -C & -Z options (-C constant N, -Z at least N)", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.taskPerNodeOffset},
497  {'r', NULL, "readFile -- read existing file", OPTION_FLAG, 'd', & initialTestParams.readFile},
498  {'R', NULL, "checkRead -- verify that the output of read matches the expected signature (used with -G)", OPTION_FLAG, 'd', & initialTestParams.checkRead},
499  {'s', NULL, "segmentCount -- number of segments", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.segmentCount},
500  {'S', NULL, "useStridedDatatype -- put strided access into datatype [not working]", OPTION_FLAG, 'd', & initialTestParams.useStridedDatatype},
501  {'t', NULL, "transferSize -- size of transfer in bytes (e.g.: 8, 4k, 2m, 1g)", OPTION_OPTIONAL_ARGUMENT, 'l', & initialTestParams.transferSize},
502  {'T', NULL, "maxTimeDuration -- max time in minutes executing repeated test; it aborts only between iterations and not within a test!", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.maxTimeDuration},
503  {'u', NULL, "uniqueDir -- use unique directory name for each file-per-process", OPTION_FLAG, 'd', & initialTestParams.uniqueDir},
504  {'U', NULL, "hintsFileName -- full name for hints file", OPTION_OPTIONAL_ARGUMENT, 's', & initialTestParams.hintsFileName},
505  {'v', NULL, "verbose -- output information (repeating flag increases level)", OPTION_FLAG, 'd', & initialTestParams.verbose},
506  {'V', NULL, "useFileView -- use MPI_File_set_view", OPTION_FLAG, 'd', & initialTestParams.useFileView},
507  {'w', NULL, "writeFile -- write file", OPTION_FLAG, 'd', & initialTestParams.writeFile},
508  {'W', NULL, "checkWrite -- check read after write", OPTION_FLAG, 'd', & initialTestParams.checkWrite},
509  {'x', NULL, "singleXferAttempt -- do not retry transfer if incomplete", OPTION_FLAG, 'd', & initialTestParams.singleXferAttempt},
510  {'X', NULL, "reorderTasksRandomSeed -- random seed for -Z option", OPTION_OPTIONAL_ARGUMENT, 'd', & initialTestParams.reorderTasksRandomSeed},
511  {'Y', NULL, "fsyncPerWrite -- perform sync operation after every write operation", OPTION_FLAG, 'd', & initialTestParams.fsyncPerWrite},
512  {'z', NULL, "randomOffset -- access is to random, not sequential, offsets within a file", OPTION_FLAG, 'd', & initialTestParams.randomOffset},
513  {'Z', NULL, "reorderTasksRandom -- changes task ordering to random ordering for readback", OPTION_FLAG, 'd', & initialTestParams.reorderTasksRandom},
514  {.help=" -O summaryFile=FILE -- store result data into this file", .arg = OPTION_OPTIONAL_ARGUMENT},
515  {.help=" -O summaryFormat=[default,JSON,CSV] -- use the format for outputing the summary", .arg = OPTION_OPTIONAL_ARGUMENT},
516  LAST_OPTION,
517  };
518 
519  IOR_test_t *tests = NULL;
520 
521  GetPlatformName(initialTestParams.platform);
522  airoi_parse_options(argc, argv, options);
523 
524  if (toggleG){
525  initialTestParams.setTimeStampSignature = toggleG;
526  initialTestParams.incompressibleSeed = toggleG;
527  }
528 
529  if (buffer_type[0] != 0){
530  switch(buffer_type[0]) {
531  case 'i': /* Incompressible */
532  initialTestParams.dataPacketType = incompressible;
533  break;
534  case 't': /* timestamp */
535  initialTestParams.dataPacketType = timestamp;
536  break;
537  case 'o': /* offset packet */
538  initialTestParams.storeFileOffset = TRUE;
539  initialTestParams.dataPacketType = offset;
540  break;
541  default:
542  fprintf(out_logfile,
543  "Unknown arguement for -l %s; generic assumed\n", buffer_type);
544  break;
545  }
546  }
547  if (memoryPerNode){
548  initialTestParams.memoryPerNode = NodeMemoryStringToBytes(optarg);
549  }
550  const ior_aiori_t * backend = aiori_select(initialTestParams.api);
551  if (backend == NULL)
552  ERR_SIMPLE("unrecognized I/O API");
553 
554  initialTestParams.backend = backend;
555  initialTestParams.apiVersion = backend->get_version();
556 
557  if (testscripts){
558  tests = ReadConfigScript(testscripts);
559  }else{
560  tests = CreateTest(&initialTestParams, 0);
561  AllocResults(tests);
562  }
563 
564  CheckRunSettings(tests);
565 
566  return (tests);
567 }
const void * backend
Definition: ior.h:82
int reorderTasks
Definition: ior.h:105
int uniqueDir
Definition: ior.h:128
int lustre_stripe_count
Definition: ior.h:187
IOR_offset_t setAlignment
Definition: ior.h:165
int quitOnError
Definition: ior.h:114
int reorderTasksRandomSeed
Definition: ior.h:108
int showHints
Definition: ior.h:126
static void CheckRunSettings(IOR_test_t *tests)
Definition: parse_options.c:68
int lustre_stripe_size
Definition: ior.h:188
int multiFile
Definition: ior.h:99
#define ERR(MSG)
Definition: iordef.h:169
#define LAST_OPTION
Definition: option.h:36
unsigned int incompressibleSeed
Definition: ior.h:143
char * GetPlatformName()
Definition: ior.c:657
int filePerProc
Definition: ior.h:104
int noFill
Definition: ior.h:164
int repetitions
Definition: ior.h:97
IOR_offset_t segmentCount
Definition: ior.h:116
int useStridedDatatype
Definition: ior.h:124
CURLcode rc
Definition: aiori-S3.c:121
int keepFile
Definition: ior.h:111
int contains_only(char *haystack, char *needle)
int checkRead
Definition: ior.h:110
enum OutputFormat_t outputFormat
Definition: utilities.c:65
int useSharedFilePointer
Definition: ior.h:123
char *(* get_version)()
Definition: aiori.h:74
IOR_offset_t transferSize
Definition: ior.h:118
size_t memoryPerNode
Definition: ior.h:146
IOR_param_t params
Definition: ior.h:224
int gpfs_release_token
Definition: ior.h:195
IOR_param_t initialTestParams
Definition: parse_options.c:34
int storeFileOffset
Definition: ior.h:130
char * apiVersion
Definition: ior.h:88
int summary_every_test
Definition: ior.h:127
int setTimeStampSignature
Definition: ior.h:139
#define IOR_RDONLY
Definition: aiori.h:33
unsigned int openFlags
Definition: ior.h:85
int fsyncPerWrite
Definition: ior.h:152
int interTestDelay
Definition: ior.h:100
int lustre_start_ost
Definition: ior.h:189
#define ERR_SIMPLE(MSG)
Definition: iordef.h:178
int maxTimeDuration
Definition: ior.h:136
char * testFileName
Definition: ior.h:90
void aiori_supported_apis(char *APIs)
Definition: aiori.c:84
char * stoneWallingStatusFile
Definition: ior.h:134
int taskPerNodeOffset
Definition: ior.h:106
#define IOR_CREAT
Definition: aiori.h:37
const ior_aiori_t * aiori_select(const char *api)
Definition: aiori.c:184
#define IOR_EXCL
Definition: aiori.h:39
int fsync
Definition: ior.h:153
char * hintsFileName
Definition: ior.h:92
struct IOR_test_t * next
Definition: ior.h:226
int outlierThreshold
Definition: ior.h:137
int intraTestBarriers
Definition: ior.h:202
void DecodeDirective(char *line, IOR_param_t *params)
int reorderTasksRandom
Definition: ior.h:107
int checkWrite
Definition: ior.h:109
static size_t NodeMemoryStringToBytes(char *size_str)
Definition: parse_options.c:37
int verbose
Definition: ior.h:138
#define MPI_CHECK(MPI_STATUS, MSG)
Definition: iordef.h:192
char * platform
Definition: ior.h:89
int singleXferAttempt
Definition: ior.h:151
Definition: ior.h:47
FILE * out_resultfile
Definition: utilities.c:64
static option_help options[]
Definition: aiori-DUMMY.c:31
int stoneWallingWearOut
Definition: ior.h:132
static const ior_aiori_t * backend
Definition: ior.c:43
IOR_test_t * CreateTest(IOR_param_t *init_params, int test_num)
Definition: ior.c:523
#define IOR_WRONLY
Definition: aiori.h:34
int keepFileWithError
Definition: ior.h:112
#define FALSE
Definition: iordef.h:71
int useExistingTestFile
Definition: ior.h:129
enum PACKET_TYPE dataPacketType
Definition: ior.h:147
int beegfs_numTargets
Definition: ior.h:198
void init_IOR_Param_t(IOR_param_t *p)
Definition: ior.c:168
int useFileView
Definition: ior.h:122
int readFile
Definition: ior.h:102
int nodes
Definition: ior.h:95
int randomOffset
Definition: ior.h:144
int numTasks
Definition: ior.h:94
size_t memoryPerTask
Definition: ior.h:145
int referenceNumber
Definition: ior.h:86
int lustre_ignore_locks
Definition: ior.h:191
int individualDataSets
Definition: ior.h:163
int writeFile
Definition: ior.h:103
int64_t string_to_bytes(char *size_str)
Definition: option.c:13
Definition: ior.h:46
uint64_t stoneWallingWearOutIterations
Definition: ior.h:133
#define MAX_STR
Definition: iordef.h:109
int collective
Definition: ior.h:115
static void decodeDirectiveWrapper(char *line)
#define FAIL(msg)
Definition: utilities.h:47
IOR_test_t * ReadConfigScript(char *scriptName)
void ParseLine(char *line, IOR_param_t *test)
static IOR_param_t * parameters
#define IOR_RDWR
Definition: aiori.h:35
char * debug
Definition: ior.h:83
IOR_test_t * ParseCommandLine(int argc, char **argv)
int preallocate
Definition: ior.h:121
int deadlineForStonewalling
Definition: ior.h:131
char * api
Definition: ior.h:87
#define ISPOWEROFTWO(x)
Definition: parse_options.c:32
FILE * out_logfile
Definition: utilities.c:63
int rank
Definition: utilities.c:57
int useO_DIRECT
Definition: ior.h:125
int gpfs_hint_access
Definition: ior.h:194
IOR_offset_t blockSize
Definition: ior.h:117
#define TRUE
Definition: iordef.h:75
int lustre_set_striping
Definition: ior.h:190
void airoi_parse_options(int argc, char **argv, option_help *global_options)
Definition: aiori.c:64
int beegfs_chunkSize
Definition: ior.h:199
#define NULL
Definition: iordef.h:79
void AllocResults(IOR_test_t *test)
Definition: ior.c:502