📄 tiotest.c
字号:
timer_start( &(d->writeTimings) ); for(i = 0; i < blocks; i++) { struct timeval tv_start, tv_stop; double value; gettimeofday(&tv_start, NULL);#ifdef USE_MMAP memcpy(file_loc + i * d->blockSize,buf,d->blockSize);#else if( write( fd, buf, d->blockSize ) != d->blockSize ) { perror("Error writing to file"); break; }#endif d->blocksWritten++; gettimeofday(&tv_stop, NULL); value = tv_stop.tv_sec - tv_start.tv_sec; value += (tv_stop.tv_usec - tv_start.tv_usec)/1000000.0; if (value > d->writeLatency.max) d->writeLatency.max = value; d->writeLatency.avg += value; d->writeLatency.count++; if (value > (double)LATENCY_STAT1) d->writeLatency.count1++; if (value > (double)LATENCY_STAT2) d->writeLatency.count2++; } #ifdef USE_MMAP munmap(file_loc,bytesize);#endif fsync(fd); close(fd); timer_stop( &(d->writeTimings) ); return 0;}void* do_random_write_test( ThreadData *d ){ int i; char *buf = d->buffer; toff_t blocks=(d->fileSizeInMBytes*MBYTE/d->blockSize); int fd; toff_t offset; ssize_t bytesWritten; int openFlags = O_WRONLY; unsigned int seed = get_random_seed(); if( args.syncWriting ) openFlags |= O_SYNC;#ifdef LARGEFILES openFlags |= O_LARGEFILE;#endif fd = open(d->fileName, openFlags); if(fd == -1) { fprintf(stderr, "%s: %s\n", strerror(errno), d->fileName); return 0; } if (args.debugLevel > 1) { fprintf(stderr, "do_random_write_test: Initial seek %lu\n", d->fileOffset); fflush(stderr); } if( tlseek( fd, d->fileOffset, SEEK_SET ) != d->fileOffset ) { report_seek_error(d->fileOffset, d->blocksRandomWritten); close(fd); return 0; } timer_start( &(d->randomWriteTimings) ); for(i = 0; i < d->numRandomOps; i++) { struct timeval tv_start, tv_stop; double value; offset = get_random_offset(blocks-1, &seed) * d->blockSize; if(args.debugLevel > 10) { fprintf(stderr, "Thread: %u chose seek of %Lu\n", (unsigned)getpid(), (long long)offset ); fflush(stderr); } if( tlseek( fd, offset, SEEK_SET ) != offset ) { report_seek_error(offset, d->blocksRandomWritten); break; } gettimeofday(&tv_start, NULL); if( (bytesWritten = write( fd, buf, d->blockSize )) != d->blockSize ) { report_random_write_error(offset, bytesWritten, d->blocksRandomWritten); break; } d->blocksRandomWritten++; gettimeofday(&tv_stop, NULL); value = tv_stop.tv_sec - tv_start.tv_sec; value += (tv_stop.tv_usec - tv_start.tv_usec)/1000000.0; if (value > d->randomWriteLatency.max) d->randomWriteLatency.max = value; d->randomWriteLatency.avg += value; d->randomWriteLatency.count++; if (value > (double)LATENCY_STAT1) d->randomWriteLatency.count1++; if (value > (double)LATENCY_STAT2) d->randomWriteLatency.count2++; } fsync(fd); close(fd); timer_stop( &(d->randomWriteTimings) ); return 0;}void* do_read_test( ThreadData *d ){ char *buf = d->buffer; int fd; toff_t blocks=(d->fileSizeInMBytes*MBYTE)/d->blockSize; toff_t i; int openFlags = O_RDONLY; #ifdef USE_MMAP toff_t bytesize=blocks*d->blockSize; /* truncates down to BS multiple */ void *file_loc;#endif#ifdef LARGEFILES openFlags |= O_LARGEFILE;#endif fd = open(d->fileName, openFlags); if(fd == -1) { fprintf(stderr, "%s: %s\n", strerror(errno), d->fileName); return 0; } if (args.debugLevel > 1) { fprintf(stderr, "do_read_test: initial seek %lu\n", d->fileOffset); fflush(stderr); }#ifdef USE_MMAP file_loc=mmap(NULL,bytesize,PROT_READ,MAP_SHARED,fd,d->fileOffset); if(file_loc == MAP_FAILED) { perror("Error mmap()ing file"); close(fd); return 0; }# ifdef USE_MADVISE /* madvise(file_loc,bytesize,MADV_DONTNEED); */ madvise(file_loc,bytesize,MADV_RANDOM);# endif#else if( tlseek( fd, d->fileOffset, SEEK_SET ) != d->fileOffset ) { report_seek_error(d->fileOffset, d->blocksRandomWritten); close(fd); return 0; }#endif timer_start( &(d->readTimings) ); for(i = 0; i < blocks; i++) { struct timeval tv_start, tv_stop; double value; gettimeofday(&tv_start, NULL);#ifdef USE_MMAP memcpy(buf,file_loc + i * d->blockSize,d->blockSize);#else if( read( fd, buf, d->blockSize ) != d->blockSize ) { perror("Error read from file"); break; }#endif gettimeofday(&tv_stop, NULL); value = tv_stop.tv_sec - tv_start.tv_sec; value += (tv_stop.tv_usec - tv_start.tv_usec)/1000000.0; if (value > d->readLatency.max) d->readLatency.max = value; d->readLatency.avg += value; d->readLatency.count++; if (value > (double)LATENCY_STAT1) d->readLatency.count1++; if (value > (double)LATENCY_STAT2) d->readLatency.count2++; if( args.consistencyCheckData ) { if( crc32(buf, d->blockSize, 0) != d->bufferCrc ) { fprintf(stderr, "io error: crc read error in file %s " "on block %lu\n", d->fileName, d->blocksRead ); exit(10); } } d->blocksRead++; } timer_stop( &(d->readTimings) );#ifdef MMAP munmap(file_loc,bytesize);#endif close(fd); return 0;}void* do_random_read_test( ThreadData *d ){ int i; char *buf = d->buffer; toff_t blocks=(d->fileSizeInMBytes*MBYTE/d->blockSize); int fd; toff_t offset; ssize_t bytesRead; int openFlags = O_RDONLY; unsigned int seed = get_random_seed();#ifdef LARGEFILES openFlags |= O_LARGEFILE;#endif fd = open(d->fileName, openFlags); if(fd == -1) { fprintf(stderr, "%s: %s\n", strerror(errno), d->fileName); return 0; } if (args.debugLevel > 1) { fprintf(stderr, "do_random_read_test: initial seek %lu\n", d->fileOffset); fflush(stderr); } if( tlseek( fd, d->fileOffset, SEEK_SET ) != d->fileOffset ) { report_seek_error(d->fileOffset, d->blocksRandomWritten); close(fd); return 0; } timer_start( &(d->randomReadTimings) ); for(i = 0; i < d->numRandomOps; i++) { struct timeval tv_start, tv_stop; double value; offset = get_random_offset(blocks-1, &seed) * d->blockSize + d->fileOffset; if(args.debugLevel > 10) { fprintf(stderr, "Thread: %u chose seek of %Lu\n", (unsigned)getpid(), (long long)offset ); fflush(stderr); } if( tlseek( fd, offset, SEEK_SET ) != offset ) { report_seek_error(offset, d->blocksRandomRead); break; } gettimeofday(&tv_start, NULL); if( (bytesRead = read( fd, buf, d->blockSize )) != d->blockSize ) { report_read_error(offset, bytesRead, d->blocksRandomRead); break; } gettimeofday(&tv_stop, NULL); value = tv_stop.tv_sec - tv_start.tv_sec; value += (tv_stop.tv_usec - tv_start.tv_usec)/1000000.0; if (value > d->randomReadLatency.max) d->randomReadLatency.max = value; d->randomReadLatency.avg += value; d->randomReadLatency.count++; if (value > (double)LATENCY_STAT1) d->randomReadLatency.count1++; if (value > (double)LATENCY_STAT2) d->randomReadLatency.count2++; if( args.consistencyCheckData ) { if( crc32(buf, d->blockSize, 0) != d->bufferCrc ) { fprintf(stderr, "io error: crc seek/read error in file %s " "on block %lu\n", d->fileName, d->blocksRandomRead ); exit(11); } } d->blocksRandomRead++; } timer_stop( &(d->randomReadTimings) ); close(fd); return 0;}clock_t get_time(){ struct tms buf; return times(&buf);}unsigned int get_random_seed(){ unsigned int seed; struct timeval r; if(gettimeofday( &r, NULL ) == 0) { seed = r.tv_usec; } else { seed = 0x12345678; } return seed;}inline const toff_t get_random_offset(const toff_t max, unsigned int *seed){#if (RAND_MAX < 2147483647) unsigned long rr_max = RAND_MAX;#endif unsigned long rr = rand_r(seed);/* This should fix bug in glibc < 2.1.3 which returns too high random numbers*/ if( rr > RAND_MAX ) { rr &= RAND_MAX; }/* This is for braindead unixes having 15bit RAND_MAX :) The whole random stuff would need rethinking. If this didn't have to be portable /dev/urandom would be the best choice.*/#if (RAND_MAX < 2147483647) rr |= rand_r(seed) << 16; rr_max = rr_max << 16;#endif#if 0 return (toff_t) ((double)(max) * rr / (rr_max + 1.0));#else return (toff_t) (rr % max);#endif}void timer_init(Timings *t){ memset( t, 0, sizeof(Timings) );}void timer_start(Timings *t){ struct rusage ru; if(gettimeofday( &(t->startRealTime), NULL )) { perror("Error in gettimeofday\n"); exit(10); } if(getrusage( RUSAGE_SELF, &ru )) { perror("Error in getrusage\n"); exit(11); } memcpy( &(t->startUserTime), &(ru.ru_utime), sizeof( struct timeval )); memcpy( &(t->startSysTime), &(ru.ru_stime), sizeof( struct timeval ));}void timer_stop(Timings *t){ struct rusage ru; if(gettimeofday( &(t->stopRealTime), NULL )) { perror("Error in gettimeofday\n"); exit(10); } if( getrusage( RUSAGE_SELF, &ru )) { perror("Error in getrusage\n"); exit(11); } memcpy( &(t->stopUserTime), &(ru.ru_utime), sizeof( struct timeval )); memcpy( &(t->stopSysTime), &(ru.ru_stime), sizeof( struct timeval ));}const double timer_realtime(const Timings *t){ double value; value = t->stopRealTime.tv_sec - t->startRealTime.tv_sec; value += (t->stopRealTime.tv_usec - t->startRealTime.tv_usec)/1000000.0; return value;}const double timer_usertime(const Timings *t){ double value; value = t->stopUserTime.tv_sec - t->startUserTime.tv_sec; value += (t->stopUserTime.tv_usec - t->startUserTime.tv_usec)/1000000.0; return value;}const double timer_systime(const Timings *t){ double value; value = t->stopSysTime.tv_sec - t->startSysTime.tv_sec; value += (t->stopSysTime.tv_usec - t->startSysTime.tv_usec)/1000000.0; return value;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -