1 #include <mpi.h> 2 #include <stdio.h> 3 #include <stdlib.h> 4 #include <cassert> 5 #include <cstring> 6 #include <string> 7 #include <sstream> 8 #include "phIO.h" 9 #include "phComm.h" 10 #include "phio_base.h" 11 #include "ph_mpi_help.h" 12 13 14 #ifndef PHASTAIO_TIMERS_ON 15 #define PHASTAIO_TIMERS_ON 0 16 #endif 17 struct phastaio_stats { 18 double readTime; 19 double writeTime; 20 double openTime; 21 double closeTime; 22 size_t readBytes; 23 size_t writeBytes; 24 size_t reads; 25 size_t writes; 26 }; 27 phastaio_stats phio_global_stats; 28 29 namespace { 30 inline double getTime() { 31 return MPI_Wtime(); 32 } 33 inline size_t getSize(const char* t) { 34 std::string type(t); 35 if(type == "integer") 36 return sizeof(int); 37 else if(type == "double") 38 return sizeof(double); 39 else { 40 assert(0); 41 exit(EXIT_FAILURE); 42 } 43 } 44 } 45 46 #define PHIO_TRACING 0 47 namespace { 48 void trace(const char* key, const char* aux="", void* obj=NULL) { 49 if(PHIO_TRACING) 50 fprintf(stderr, "PHIO_TRACE entering %s %s %p\n", key, aux, obj); 51 } 52 void printMinMaxAvg(const char* key, size_t v) { 53 int val = static_cast<int>(v); 54 int min = ph_min_int(val); 55 int max = ph_max_int(val); 56 long tot = ph_add_long(static_cast<long>(val)); 57 double avg = tot/static_cast<double>(ph_peers()); 58 if(!ph_self()) 59 fprintf(stderr, "phio_%s min max avg %d %d %f\n", 60 key, min, max, avg); 61 } 62 63 void printMinMaxAvg(const char* key, double v) { 64 double min = ph_min_double(v); 65 double max = ph_max_double(v); 66 double tot = ph_add_double(v); 67 double avg = tot/ph_peers(); 68 if(!ph_self()) 69 fprintf(stderr, "phio_%s min max avg %f %f %f\n", 70 key, min, max, avg); 71 } 72 } 73 74 #ifdef __cplusplus 75 extern "C" { 76 #endif 77 78 void phio_printStats() { 79 const int mebi=1024*1024; 80 printMinMaxAvg("reads",phio_getReads()); 81 printMinMaxAvg("writes",phio_getWrites()); 82 printMinMaxAvg("readTime (s)",phio_getReadTime()); 83 printMinMaxAvg("writeTime (s)", phio_getWriteTime()); 84 printMinMaxAvg("openTime (s)", phio_getOpenTime()); 85 printMinMaxAvg("closeTime (s)", phio_getCloseTime()); 86 printMinMaxAvg("readBytes (B)", phio_getReadBytes()); 87 printMinMaxAvg("writeBytes (B)", phio_getWriteBytes()); 88 printMinMaxAvg("readBandwidth (MiB/s)", 89 (phio_getReadBytes()/phio_getReadTime())/mebi); 90 printMinMaxAvg("writeBandwidth (MiB/s)", 91 (phio_getWriteBytes()/phio_getWriteTime())/mebi); 92 } 93 94 void phio_initStats() { 95 phio_global_stats.readTime = 0; 96 phio_global_stats.writeTime = 0; 97 phio_global_stats.openTime = 0; 98 phio_global_stats.closeTime = 0; 99 phio_global_stats.readBytes = 0; 100 phio_global_stats.writeBytes = 0; 101 phio_global_stats.reads = 0; 102 phio_global_stats.writes = 0; 103 } 104 105 size_t phio_getReads() { 106 return phio_global_stats.reads; 107 } 108 109 size_t phio_getWrites() { 110 return phio_global_stats.writes; 111 } 112 113 double phio_getReadTime() { 114 return phio_global_stats.readTime; 115 } 116 117 double phio_getWriteTime() { 118 return phio_global_stats.writeTime; 119 } 120 121 double phio_getOpenTime() { 122 return phio_global_stats.openTime; 123 } 124 125 double phio_getCloseTime() { 126 return phio_global_stats.closeTime; 127 } 128 129 size_t phio_getReadBytes() { 130 return phio_global_stats.readBytes; 131 } 132 133 size_t phio_getWriteBytes() { 134 return phio_global_stats.writeBytes; 135 } 136 137 void phio_readheader( 138 phio_fp f, 139 const char keyphrase[], 140 void* valueArray, 141 int* nItems, 142 const char datatype[], 143 const char iotype[] ) { 144 f->ops->readheader(f->file, keyphrase, valueArray, 145 nItems, datatype, iotype); 146 } 147 void phio_writeheader( 148 phio_fp f, 149 const char keyphrase[], 150 const void* valueArray, 151 const int* nItems, 152 const int* ndataItems, 153 const char datatype[], 154 const char iotype[] ) { 155 f->ops->writeheader(f->file, keyphrase, valueArray, 156 nItems, ndataItems, datatype, iotype); 157 } 158 void phio_readdatablock( 159 phio_fp f, 160 const char keyphrase[], 161 void* valueArray, 162 int* nItems, 163 const char datatype[], 164 const char iotype[] ) { 165 const double t0 = getTime(); 166 f->ops->readdatablock(f->file, keyphrase, valueArray, 167 nItems, datatype, iotype); 168 phio_global_stats.readBytes += (*nItems)*getSize(datatype); 169 phio_global_stats.readTime += getTime()-t0; 170 phio_global_stats.reads++; 171 } 172 void phio_writedatablock( 173 phio_fp f, 174 const char keyphrase[], 175 const void* valueArray, 176 const int* nItems, 177 const char datatype[], 178 const char iotype[]) { 179 const double t0 = getTime(); 180 f->ops->writedatablock(f->file, keyphrase, valueArray, 181 nItems, datatype, iotype); 182 phio_global_stats.writeBytes += (*nItems)*getSize(datatype); 183 phio_global_stats.writeTime += getTime()-t0; 184 phio_global_stats.writes++; 185 } 186 187 void phio_constructName( 188 phio_fp f, 189 const char inName[], 190 char* outName) { 191 f->ops->constructname(inName, outName); 192 } 193 194 void phio_openfile( 195 const char filename[], 196 phio_fp f) { 197 const double t0 = getTime(); 198 trace("openfile",filename,f); 199 f->ops->openfile(filename, f); 200 phio_global_stats.openTime += getTime()-t0; 201 } 202 203 void phio_closefile(phio_fp f) { 204 const double t0 = getTime(); 205 trace("closefile","unknown",f); 206 f->ops->closefile(f); 207 phio_global_stats.closeTime += getTime()-t0; 208 } 209 210 void phio_appendInt(char* dest, int v) { 211 std::stringstream ss; 212 ss << dest << v << '.'; 213 std::string s = ss.str(); 214 strcpy(dest, s.c_str()); 215 } 216 217 #ifdef __cplusplus 218 } 219 #endif 220