test.c revision 844ea60273f4e7862150d9c6430cdb15768e2f34
1#include <stdio.h> 2#include <stdlib.h> 3#include <string.h> 4 5#include "../fio.h" 6#include "../gettime.h" 7#include "../time.h" 8#include "../verify.h" 9 10#include "../crc/md5.h" 11#include "../crc/crc64.h" 12#include "../crc/crc32.h" 13#include "../crc/crc32c.h" 14#include "../crc/crc16.h" 15#include "../crc/crc7.h" 16#include "../crc/sha1.h" 17#include "../crc/sha256.h" 18#include "../crc/sha512.h" 19#include "../crc/xxhash.h" 20 21#define CHUNK 131072U 22#define NR_CHUNKS 2048U 23 24struct test_type { 25 const char *name; 26 unsigned int mask; 27 uint64_t (*fn)(void); 28}; 29 30enum { 31 T_MD5 = 1U << 0, 32 T_CRC64 = 1U << 1, 33 T_CRC32 = 1U << 2, 34 T_CRC32C = 1U << 3, 35 T_CRC16 = 1U << 4, 36 T_CRC7 = 1U << 5, 37 T_SHA1 = 1U << 6, 38 T_SHA256 = 1U << 7, 39 T_SHA512 = 1U << 8, 40 T_XXHASH = 1U << 9, 41}; 42 43static void randomize_buf(void *buf, unsigned int size, int seed) 44{ 45 struct frand_state state; 46 47 init_rand_seed(&state, seed); 48 fill_random_buf(&state, buf, size); 49} 50 51static uint64_t t_md5(void) 52{ 53 uint32_t digest[4]; 54 struct fio_md5_ctx ctx = { .hash = digest }; 55 struct timeval s; 56 uint64_t ret; 57 void *buf; 58 int i; 59 60 fio_md5_init(&ctx); 61 62 buf = malloc(CHUNK); 63 randomize_buf(buf, CHUNK, 0x8989); 64 65 fio_gettime(&s, NULL); 66 for (i = 0; i < NR_CHUNKS; i++) 67 fio_md5_update(&ctx, buf, CHUNK); 68 69 ret = utime_since_now(&s); 70 free(buf); 71 return ret; 72} 73 74static uint64_t t_crc64(void) 75{ 76 struct timeval s; 77 uint64_t ret; 78 void *buf; 79 int i; 80 81 buf = malloc(CHUNK); 82 randomize_buf(buf, CHUNK, 0x8989); 83 84 fio_gettime(&s, NULL); 85 for (i = 0; i < NR_CHUNKS; i++) 86 fio_crc64(buf, CHUNK); 87 88 ret = utime_since_now(&s); 89 free(buf); 90 return ret; 91} 92 93static uint64_t t_crc32(void) 94{ 95 struct timeval s; 96 uint64_t ret; 97 void *buf; 98 int i; 99 100 buf = malloc(CHUNK); 101 randomize_buf(buf, CHUNK, 0x8989); 102 103 fio_gettime(&s, NULL); 104 for (i = 0; i < NR_CHUNKS; i++) 105 fio_crc32(buf, CHUNK); 106 107 ret = utime_since_now(&s); 108 free(buf); 109 return ret; 110} 111 112static uint64_t t_crc32c(void) 113{ 114 struct timeval s; 115 uint64_t ret; 116 void *buf; 117 int i; 118 119 buf = malloc(CHUNK); 120 randomize_buf(buf, CHUNK, 0x8989); 121 122 fio_gettime(&s, NULL); 123 for (i = 0; i < NR_CHUNKS; i++) 124 fio_crc32c(buf, CHUNK); 125 126 ret = utime_since_now(&s); 127 free(buf); 128 return ret; 129} 130 131static uint64_t t_crc16(void) 132{ 133 struct timeval s; 134 uint64_t ret; 135 void *buf; 136 int i; 137 138 buf = malloc(CHUNK); 139 randomize_buf(buf, CHUNK, 0x8989); 140 141 fio_gettime(&s, NULL); 142 for (i = 0; i < NR_CHUNKS; i++) 143 fio_crc16(buf, CHUNK); 144 145 ret = utime_since_now(&s); 146 free(buf); 147 return ret; 148} 149 150static uint64_t t_crc7(void) 151{ 152 struct timeval s; 153 uint64_t ret; 154 void *buf; 155 int i; 156 157 buf = malloc(CHUNK); 158 randomize_buf(buf, CHUNK, 0x8989); 159 160 fio_gettime(&s, NULL); 161 for (i = 0; i < NR_CHUNKS; i++) 162 fio_crc7(buf, CHUNK); 163 164 ret = utime_since_now(&s); 165 free(buf); 166 return ret; 167} 168 169static uint64_t t_sha1(void) 170{ 171 uint32_t sha[5]; 172 struct fio_sha1_ctx ctx = { .H = sha }; 173 struct timeval s; 174 uint64_t ret; 175 void *buf; 176 int i; 177 178 fio_sha1_init(&ctx); 179 180 buf = malloc(CHUNK); 181 randomize_buf(buf, CHUNK, 0x8989); 182 183 fio_gettime(&s, NULL); 184 for (i = 0; i < NR_CHUNKS; i++) 185 fio_sha1_update(&ctx, buf, CHUNK); 186 187 ret = utime_since_now(&s); 188 free(buf); 189 return ret; 190} 191 192static uint64_t t_sha256(void) 193{ 194 uint8_t sha[64]; 195 struct fio_sha256_ctx ctx = { .buf = sha }; 196 struct timeval s; 197 uint64_t ret; 198 void *buf; 199 int i; 200 201 fio_sha256_init(&ctx); 202 203 buf = malloc(CHUNK); 204 randomize_buf(buf, CHUNK, 0x8989); 205 206 fio_gettime(&s, NULL); 207 for (i = 0; i < NR_CHUNKS; i++) 208 fio_sha256_update(&ctx, buf, CHUNK); 209 210 ret = utime_since_now(&s); 211 free(buf); 212 return ret; 213} 214 215static uint64_t t_sha512(void) 216{ 217 uint8_t sha[128]; 218 struct fio_sha512_ctx ctx = { .buf = sha }; 219 struct timeval s; 220 uint64_t ret; 221 void *buf; 222 int i; 223 224 fio_sha512_init(&ctx); 225 226 buf = malloc(CHUNK); 227 randomize_buf(buf, CHUNK, 0x8989); 228 229 fio_gettime(&s, NULL); 230 for (i = 0; i < NR_CHUNKS; i++) 231 fio_sha512_update(&ctx, buf, CHUNK); 232 233 ret = utime_since_now(&s); 234 free(buf); 235 return ret; 236} 237 238static uint64_t t_xxhash(void) 239{ 240 void *state; 241 struct timeval s; 242 uint64_t ret; 243 void *buf; 244 int i; 245 246 state = XXH32_init(0x8989); 247 248 buf = malloc(CHUNK); 249 randomize_buf(buf, CHUNK, 0x8989); 250 251 fio_gettime(&s, NULL); 252 for (i = 0; i < NR_CHUNKS; i++) 253 XXH32_update(state, buf, CHUNK); 254 255 XXH32_digest(state); 256 ret = utime_since_now(&s); 257 free(buf); 258 return ret; 259} 260 261static struct test_type t[] = { 262 { 263 .name = "md5", 264 .mask = T_MD5, 265 .fn = t_md5, 266 }, 267 { 268 .name = "crc64", 269 .mask = T_CRC64, 270 .fn = t_crc64, 271 }, 272 { 273 .name = "crc32", 274 .mask = T_CRC32, 275 .fn = t_crc32, 276 }, 277 { 278 .name = "crc32c", 279 .mask = T_CRC32C, 280 .fn = t_crc32c, 281 }, 282 { 283 .name = "crc16", 284 .mask = T_CRC16, 285 .fn = t_crc16, 286 }, 287 { 288 .name = "crc7", 289 .mask = T_CRC7, 290 .fn = t_crc7, 291 }, 292 { 293 .name = "sha1", 294 .mask = T_SHA1, 295 .fn = t_sha1, 296 }, 297 { 298 .name = "sha256", 299 .mask = T_SHA256, 300 .fn = t_sha256, 301 }, 302 { 303 .name = "sha512", 304 .mask = T_SHA512, 305 .fn = t_sha512, 306 }, 307 { 308 .name = "xxhash", 309 .mask = T_XXHASH, 310 .fn = t_xxhash, 311 }, 312 { 313 .name = NULL, 314 }, 315}; 316 317static unsigned int get_test_mask(const char *type) 318{ 319 char *ostr, *str = strdup(type); 320 unsigned int mask; 321 char *name; 322 int i; 323 324 ostr = str; 325 mask = 0; 326 while ((name = strsep(&str, ",")) != NULL) { 327 for (i = 0; t[i].name; i++) { 328 if (!strcmp(t[i].name, name)) { 329 mask |= t[i].mask; 330 break; 331 } 332 } 333 } 334 335 free(ostr); 336 return mask; 337} 338 339static int list_types(void) 340{ 341 int i; 342 343 for (i = 0; t[i].name; i++) 344 printf("%s\n", t[i].name); 345 346 return 0; 347} 348 349int fio_crctest(const char *type) 350{ 351 unsigned int test_mask = 0; 352 uint64_t mb = CHUNK * NR_CHUNKS; 353 int i; 354 355 crc32c_intel_probe(); 356 357 if (!type) 358 test_mask = ~0U; 359 else if (!strcmp(type, "help") || !strcmp(type, "list")) 360 return list_types(); 361 else 362 test_mask = get_test_mask(type); 363 364 for (i = 0; t[i].name; i++) { 365 double mb_sec; 366 uint64_t usec; 367 368 if (!(t[i].mask & test_mask)) 369 continue; 370 371 usec = t[i].fn(); 372 mb_sec = (double) mb / (double) usec; 373 mb_sec /= (1.024 * 1.024); 374 printf("%s:\t%.2f MB/sec\n", t[i].name, mb_sec); 375 } 376 377 return 0; 378} 379