Skip to content

Commit 1a7a118

Browse files
committed
ioping: cleanup statistics
Signed-off-by: Konstantin Khlebnikov <koct9i@gmail.com>
1 parent 20e14e1 commit 1a7a118

File tree

1 file changed

+158
-155
lines changed

1 file changed

+158
-155
lines changed

ioping.c

Lines changed: 158 additions & 155 deletions
Original file line numberDiff line numberDiff line change
@@ -1070,20 +1070,98 @@ static void random_memory(void *buf, size_t len)
10701070
}
10711071
}
10721072

1073+
struct statistics {
1074+
long long start, finish, load_time;
1075+
long long count, valid, too_slow, too_fast;
1076+
long long min, max;
1077+
double sum, sum2, avg, mdev;
1078+
double speed, iops, load_speed, load_iops;
1079+
long long size, load_size;
1080+
};
1081+
1082+
static void start_statistics(struct statistics *s, unsigned long long start) {
1083+
memset(s, 0, sizeof(*s));
1084+
s->min = LLONG_MAX;
1085+
s->max = LLONG_MIN;
1086+
s->start = start;
1087+
}
1088+
1089+
static void add_statistics(struct statistics *s, long long val) {
1090+
s->count++;
1091+
if (val < min_valid_time) {
1092+
s->too_fast++;
1093+
} else if (val > max_valid_time) {
1094+
s->too_slow++;
1095+
} else {
1096+
s->valid++;
1097+
s->sum += val;
1098+
s->sum2 += (double)val * val;
1099+
if (val < s->min)
1100+
s->min = val;
1101+
if (val > s->max)
1102+
s->max = val;
1103+
}
1104+
}
1105+
1106+
static void merge_statistics(struct statistics *s, struct statistics *o) {
1107+
s->count += o->count;
1108+
s->too_fast += o->too_fast;
1109+
s->too_slow += o->too_slow;
1110+
if (o->valid) {
1111+
s->valid += o->valid;
1112+
s->sum += o->sum;
1113+
s->sum2 += o->sum2;
1114+
if (o->min < s->min)
1115+
s->min = o->min;
1116+
if (o->max > s->max)
1117+
s->max = o->max;
1118+
}
1119+
}
1120+
1121+
static void finish_statistics(struct statistics *s, unsigned long long finish) {
1122+
s->finish = finish;
1123+
s->load_time = finish - s->start;
1124+
1125+
if (s->valid) {
1126+
s->avg = s->sum / s->valid;
1127+
s->mdev = sqrt(s->sum2 / s->valid - s->avg * s->avg);
1128+
} else {
1129+
s->min = 0;
1130+
s->max = 0;
1131+
}
1132+
1133+
if (s->sum)
1134+
s->iops = (double)NSEC_PER_SEC * s->valid / s->sum;
1135+
1136+
if (s->load_time)
1137+
s->load_iops = (double)NSEC_PER_SEC * s->count / s->load_time;
1138+
1139+
s->speed = s->iops * size;
1140+
s->load_speed = s->load_iops * size;
1141+
s->size = s->valid * size;
1142+
s->load_size = s->count * size;
1143+
}
1144+
1145+
static void dump_statistics(struct statistics *s) {
1146+
printf("%lu %.0f %.0f %.0f %lu %.0f %lu %.0f %lu %lu\n",
1147+
(unsigned long)s->valid, s->sum,
1148+
s->iops, s->speed,
1149+
(unsigned long)s->min, s->avg,
1150+
(unsigned long)s->max, s->mdev,
1151+
(unsigned long)s->count,
1152+
(unsigned long)s->load_time);
1153+
}
1154+
10731155
int main (int argc, char **argv)
10741156
{
10751157
ssize_t ret_size;
10761158
struct stat st;
10771159
int ret;
10781160

1079-
long long request, part_request;
1080-
long long too_fast = 0, too_slow = 0;
1081-
long long total_valid, part_valid;
1082-
long long time_start, time_total, this_time;
1083-
double part_min, part_max, time_min, time_max;
1084-
double time_sum, time_sum2, time_mdev, time_avg;
1085-
double part_sum, part_sum2, part_mdev, part_avg;
1086-
long long time_now, time_next, part_start, period_deadline;
1161+
struct statistics part, total;
1162+
1163+
long long request, this_time;
1164+
long long time_now, time_next, period_deadline;
10871165

10881166
setvbuf(stdout, NULL, _IOLBF, 0);
10891167

@@ -1248,30 +1326,22 @@ int main (int argc, char **argv)
12481326
set_signal();
12491327

12501328
request = 0;
1251-
total_valid = 0;
12521329
woffset = 0;
12531330

1254-
part_request = 0;
1255-
part_valid = 0;
1256-
1257-
part_min = time_min = LLONG_MAX;
1258-
part_max = time_max = LLONG_MIN;
1259-
part_sum = time_sum = 0;
1260-
part_sum2 = time_sum2 = 0;
1331+
time_now = now();
12611332

1262-
time_start = now();
1263-
part_start = time_start;
1333+
start_statistics(&part, time_now);
1334+
start_statistics(&total, time_now);
12641335

12651336
if (deadline)
1266-
deadline += time_start;
1337+
deadline += time_now;
12671338

1268-
period_deadline = time_start + period_time;
1339+
period_deadline = time_now + period_time;
12691340

1270-
time_next = time_start;
1341+
time_next = time_now;
12711342

12721343
while (!exiting) {
12731344
request++;
1274-
part_request++;
12751345

12761346
if (randomize)
12771347
woffset = random64() % (wsize / size) * size;
@@ -1297,6 +1367,7 @@ int main (int argc, char **argv)
12971367
this_time = now();
12981368

12991369
ret_size = make_request(fd, buf, size, offset + woffset);
1370+
13001371
if (ret_size < 0) {
13011372
if (errno != EINTR)
13021373
err(3, "request failed");
@@ -1315,18 +1386,9 @@ int main (int argc, char **argv)
13151386

13161387
if (request == 1) {
13171388
/* warmup */
1318-
} else if (this_time < min_valid_time) {
1319-
too_fast++;
1320-
} else if (this_time > max_valid_time) {
1321-
too_slow++;
1389+
part.count++;
13221390
} else {
1323-
part_valid++;
1324-
part_sum += this_time;
1325-
part_sum2 += this_time * this_time;
1326-
if (this_time < part_min)
1327-
part_min = this_time;
1328-
if (this_time > part_max)
1329-
part_max = this_time;
1391+
add_statistics(&part, this_time);
13301392
}
13311393

13321394
if (!quiet) {
@@ -1343,9 +1405,9 @@ int main (int argc, char **argv)
13431405
printf(" (too fast)");
13441406
} else if (this_time > max_valid_time) {
13451407
printf(" (too slow)");
1346-
} else if (part_valid > 5 && part_min < part_max) {
1347-
int percent = (this_time - part_min) * 100 /
1348-
(part_max - part_min);
1408+
} else if (part.valid > 5 && part.min < part.max) {
1409+
int percent = (this_time - part.min) * 100 /
1410+
(part.max - part.min);
13491411
if (percent < 5)
13501412
printf(" (fast)");
13511413
else if (percent > 95)
@@ -1354,48 +1416,13 @@ int main (int argc, char **argv)
13541416
printf("\n");
13551417
}
13561418

1357-
if ((period_request && (part_request >= period_request)) ||
1419+
if ((period_request && (part.count >= period_request)) ||
13581420
(period_time && (time_next >= period_deadline))) {
1359-
1360-
time_sum += part_sum;
1361-
time_sum2 += part_sum2;
1362-
if (part_min < time_min)
1363-
time_min = part_min;
1364-
if (part_max > time_max)
1365-
time_max = part_max;
1366-
1367-
if (part_valid) {
1368-
part_avg = part_sum / part_valid;
1369-
part_mdev = sqrt(part_sum2 / part_valid -
1370-
part_avg * part_avg);
1371-
} else {
1372-
part_min = 0;
1373-
part_avg = 0;
1374-
part_max = 0;
1375-
part_mdev = 0;
1376-
part_sum = 0.1;
1377-
}
1378-
1379-
printf("%lu %.0f %.0f %.0f %.0f %.0f %.0f %.0f %lu %lu\n",
1380-
(unsigned long)part_valid, part_sum,
1381-
1. * NSEC_PER_SEC *
1382-
part_valid / part_sum,
1383-
1. * NSEC_PER_SEC *
1384-
part_valid * size / part_sum,
1385-
part_min, part_avg,
1386-
part_max, part_mdev,
1387-
(unsigned long)part_request,
1388-
(unsigned long)(time_now - part_start));
1389-
1390-
part_min = LLONG_MAX;
1391-
part_max = LLONG_MIN;
1392-
part_sum = part_sum2 = 0;
1393-
part_request = 0;
1394-
total_valid += part_valid;
1395-
part_valid = 0;
1396-
1397-
part_start = time_now;
1398-
period_deadline = part_start + period_time;
1421+
finish_statistics(&part, time_now);
1422+
dump_statistics(&part);
1423+
merge_statistics(&total, &part);
1424+
start_statistics(&part, time_now);
1425+
period_deadline = time_now + period_time;
13991426
}
14001427

14011428
if (!randomize) {
@@ -1423,87 +1450,63 @@ int main (int argc, char **argv)
14231450
}
14241451

14251452
time_now = now();
1426-
time_total = time_now - time_start;
1427-
if (!time_total)
1428-
time_total = 1;
1429-
1430-
time_sum += part_sum;
1431-
time_sum2 += part_sum2;
1432-
if (part_min < time_min)
1433-
time_min = part_min;
1434-
if (part_max > time_max)
1435-
time_max = part_max;
1436-
total_valid += part_valid;
1437-
1438-
if (total_valid) {
1439-
time_avg = time_sum / total_valid;
1440-
time_mdev = sqrt(time_sum2 / total_valid - time_avg * time_avg);
1441-
} else {
1442-
time_min = 0;
1443-
time_avg = 0;
1444-
time_max = 0;
1445-
time_mdev = 0;
1446-
time_sum = 0.1;
1447-
}
1453+
finish_statistics(&part, time_now);
1454+
merge_statistics(&total, &part);
1455+
finish_statistics(&total, time_now);
14481456

14491457
if (batch_mode) {
1450-
printf("%lu %.0f %.0f %.0f %.0f %.0f %.0f %.0f %lu %lu\n",
1451-
(unsigned long)total_valid, time_sum,
1452-
1. * NSEC_PER_SEC *
1453-
total_valid / time_sum,
1454-
1. * NSEC_PER_SEC *
1455-
total_valid * size / time_sum,
1456-
time_min, time_avg,
1457-
time_max, time_mdev,
1458-
(unsigned long)request,
1459-
(unsigned long)time_total);
1460-
} else if (!quiet || (!period_time && !period_request)) {
1461-
printf("\n--- %s (%s %s", path, fstype, device);
1462-
if (device_size)
1463-
print_size(device_size);
1464-
printf(") ioping statistics ---\n");
1465-
print_int(total_valid);
1466-
printf(" requests completed in ");
1467-
print_time(time_sum);
1468-
printf(", ");
1469-
print_size((long long)total_valid * size);
1470-
printf(" %s, ", write_read_test ? "transferred" :
1471-
write_test ? "written" : "read");
1472-
print_int(1. * NSEC_PER_SEC * total_valid / time_sum);
1473-
printf(" iops, ");
1474-
print_size(1. * NSEC_PER_SEC * total_valid * size / time_sum);
1475-
printf("/s\n");
1476-
1477-
if (too_fast) {
1478-
print_int(too_fast);
1479-
printf(" too fast, ");
1480-
}
1481-
if (too_slow) {
1482-
print_int(too_slow);
1483-
printf(" too slow, ");
1484-
}
1485-
printf("total ");
1486-
print_int(request);
1487-
printf(" requests in ");
1488-
print_time(time_total);
1489-
printf(", ");
1490-
print_size((long long)request * size);
1491-
printf(", ");
1492-
print_int(1. * NSEC_PER_SEC * request / time_total);
1493-
printf(" iops, ");
1494-
print_size(1. * NSEC_PER_SEC * request * size / time_total);
1495-
printf("/s\n");
1496-
1497-
printf("min/avg/max/mdev = ");
1498-
print_time(time_min);
1499-
printf(" / ");
1500-
print_time(time_avg);
1501-
printf(" / ");
1502-
print_time(time_max);
1503-
printf(" / ");
1504-
print_time(time_mdev);
1505-
printf("\n");
1458+
dump_statistics(&total);
1459+
return 0;
1460+
}
1461+
1462+
if (quiet && (period_time || period_request))
1463+
return 0;
1464+
1465+
printf("\n--- %s (%s %s", path, fstype, device);
1466+
if (device_size)
1467+
print_size(device_size);
1468+
printf(") ioping statistics ---\n");
1469+
print_int(total.valid);
1470+
printf(" requests completed in ");
1471+
print_time(total.sum);
1472+
printf(", ");
1473+
print_size(total.size);
1474+
printf("%s, ", write_read_test ? "" :
1475+
write_test ? " written" : " read");
1476+
print_int(total.iops);
1477+
printf(" iops, ");
1478+
print_size(total.speed);
1479+
printf("/s\n");
1480+
1481+
if (total.too_fast) {
1482+
print_int(total.too_fast);
1483+
printf(" too fast, ");
1484+
}
1485+
if (total.too_slow) {
1486+
print_int(total.too_slow);
1487+
printf(" too slow, ");
15061488
}
1489+
printf("generated ");
1490+
print_int(total.count);
1491+
printf(" requests in ");
1492+
print_time(total.load_time);
1493+
printf(", ");
1494+
print_size(total.load_size);
1495+
printf(", ");
1496+
print_int(total.load_iops);
1497+
printf(" iops, ");
1498+
print_size(total.load_speed);
1499+
printf("/s\n");
1500+
1501+
printf("min/avg/max/mdev = ");
1502+
print_time(total.min);
1503+
printf(" / ");
1504+
print_time(total.avg);
1505+
printf(" / ");
1506+
print_time(total.max);
1507+
printf(" / ");
1508+
print_time(total.mdev);
1509+
printf("\n");
15071510

15081511
return 0;
15091512
}

0 commit comments

Comments
 (0)