// #include #include #include #include #define NDEBUG #include #include "writeengine.h" using namespace std; void timespec_sub(const struct timespec& tv1, const struct timespec& tv2, struct timespec& diff) { if (tv2.tv_nsec < tv1.tv_nsec) { diff.tv_sec = tv2.tv_sec - tv1.tv_sec - 1; diff.tv_nsec = tv1.tv_nsec - tv2.tv_nsec; } else { diff.tv_sec = tv2.tv_sec - tv1.tv_sec; diff.tv_nsec = tv2.tv_nsec - tv1.tv_nsec; } } // TODO: // add getopt for CLAs // add threads for reading a file // add threads for reading multiple files // main() // int main(int argc, char** argv) { uint64_t acc = 0; uint64_t readBlocks = 0; // read size ib blocks uint64_t readSize = 0; // read size ib bytes uint64_t readBufferSz = 0; const uint64_t blockSize = 8192; char* alignedbuff = 0; boost::scoped_array realbuff; const unsigned pageSize = 4096; // getpagesize(); WriteEngine::FileOp fFileOp; BRM::OID_t oid; char fname[256]; struct timespec tm; struct timespec tm2; struct timespec tm3; struct timespec starttm; struct timespec endtm; struct timespec tottm; bool odirect = true; int fd = 0; char response = 'Y'; if (argc <= 1) { cerr << "usage: testread " << endl; return -1; } oid = atoi(argv[1]); if (oid <= 0) exit(-1); if (argc >= 2) { readBlocks = atoi(argv[2]); if (readBlocks <= 0) readBlocks = 8; } if (argc >= 4) { odirect = false; } readSize = readBlocks * blockSize; readBufferSz = readSize + pageSize; realbuff.reset(new char[readBufferSz]); if (realbuff.get() == 0) { cerr << "thr_popper: Can't allocate space for a whole extent in memory" << endl; return 0; } if (fFileOp.getFileName(oid, fname) != WriteEngine::NO_ERROR) { fname[0] = 0; throw std::runtime_error("fileOp.getFileName failed"); } else { cout << "Reading oid: " << oid << " od: " << odirect << " file: " << fname << endl; } #if __LP64__ alignedbuff = (char*)((((ptrdiff_t)realbuff.get() >> 12) << 12) + pageSize); #else alignedbuff = (char*)(((((ptrdiff_t)realbuff.get() >> 12) << 12) & 0xffffffff) + pageSize); #endif idbassert(((ptrdiff_t)alignedbuff - (ptrdiff_t)realbuff.get()) < (ptrdiff_t)pageSize); idbassert(((ptrdiff_t)alignedbuff % pageSize) == 0); if (odirect) fd = open(fname, O_RDONLY | O_DIRECT | O_LARGEFILE | O_NOATIME); else fd = open(fname, O_RDONLY | O_LARGEFILE | O_NOATIME); if (fd < 0) { cerr << "Open failed" << endl; perror("open"); throw runtime_error("Error opening file"); } while (toupper(response) != 'N') { uint64_t i = 1; uint64_t rCnt = 0; clock_gettime(CLOCK_REALTIME, &starttm); while (i != 0) { // clock_gettime(CLOCK_REALTIME, &tm); i = pread(fd, alignedbuff, readSize, acc); // clock_gettime(CLOCK_REALTIME, &tm2); idbassert(i == 0 || i == readSize); idbassert(i % pageSize == 0); idbassert(acc % pageSize == 0); if (i < 0 && errno == EINTR) { timespec_sub(tm, tm2, tm3); cout << "* " << i << " " << right << setw(2) << setfill(' ') << tm3.tv_sec << "." << right << setw(9) << setfill('0') << tm3.tv_nsec << endl; continue; } else if (i < 0) { timespec_sub(tm, tm2, tm3); cout << "* i: " << i << " sz: " << readSize << " acc: " << acc << right << setw(2) << setfill(' ') << tm3.tv_sec << " " << right << tm3.tv_nsec << endl; perror("pread"); // make loop exit i = 0; } acc += i; if (i > 0) rCnt++; // timespec_sub(tm, tm2, tm3); // cout // << i << " " // << right << setw(2) << setfill(' ') << tm3.tv_sec << " " // << right << tm3.tv_nsec // << endl; } // while(acc... clock_gettime(CLOCK_REALTIME, &endtm); timespec_sub(starttm, endtm, tottm); cout << "Total reads: " << rCnt << " sz: " << acc / (1024 * 1024) << "MB" << " tm: " << tottm.tv_sec << "secs " << tottm.tv_nsec << "ns" << endl; cout << "Repeat the last scan[Y,N]?" << endl; cin >> response; acc = 0; } // while response... close(fd); return 0; } // main