faa5684d9dafa369551c41c4faf045b2fa4ad469
[fio.git] / verify.c
1 /*
2  * IO verification helpers
3  */
4 #include <unistd.h>
5 #include <fcntl.h>
6 #include <string.h>
7 #include <assert.h>
8 #include <pthread.h>
9
10 #include "fio.h"
11 #include "verify.h"
12 #include "smalloc.h"
13
14 #include "crc/md5.h"
15 #include "crc/crc64.h"
16 #include "crc/crc32.h"
17 #include "crc/crc32c.h"
18 #include "crc/crc16.h"
19 #include "crc/crc7.h"
20 #include "crc/sha256.h"
21 #include "crc/sha512.h"
22 #include "crc/sha1.h"
23
24 static void fill_random_bytes(struct thread_data *td, void *p, unsigned int len)
25 {
26         unsigned int todo;
27         int r;
28
29         while (len) {
30                 r = os_random_long(&td->verify_state);
31
32                 /*
33                  * lrand48_r seems to be broken and only fill the bottom
34                  * 32-bits, even on 64-bit archs with 64-bit longs
35                  */
36                 todo = sizeof(r);
37                 if (todo > len)
38                         todo = len;
39
40                 memcpy(p, &r, todo);
41
42                 len -= todo;
43                 p += todo;
44         }
45 }
46
47 static void fill_pattern(struct thread_data *td, void *p, unsigned int len)
48 {
49         switch (td->o.verify_pattern_bytes) {
50         case 0:
51                 dprint(FD_VERIFY, "fill random bytes len=%u\n", len);
52                 fill_random_bytes(td, p, len);
53                 break;
54         case 1:
55                 dprint(FD_VERIFY, "fill verify pattern b=0 len=%u\n", len);
56                 memset(p, td->o.verify_pattern[0], len);
57                 break;
58         default: {
59                 unsigned int i = 0, size = 0;
60                 unsigned char *b = p;
61
62                 dprint(FD_VERIFY, "fill verify pattern b=%d len=%u\n",
63                                         td->o.verify_pattern_bytes, len);
64
65                 while (i < len) {
66                         size = td->o.verify_pattern_bytes;
67                         if (size > (len - i))
68                                 size = len - i;
69                         memcpy(b+i, td->o.verify_pattern, size);
70                         i += size;
71                 }
72                 break;
73                 }
74         }
75 }
76
77 static void memswp(void *buf1, void *buf2, unsigned int len)
78 {
79         char swap[200];
80
81         assert(len <= sizeof(swap));
82
83         memcpy(&swap, buf1, len);
84         memcpy(buf1, buf2, len);
85         memcpy(buf2, &swap, len);
86 }
87
88 static void hexdump(void *buffer, int len)
89 {
90         unsigned char *p = buffer;
91         int i;
92
93         for (i = 0; i < len; i++)
94                 log_info("%02x", p[i]);
95         log_info("\n");
96 }
97
98 /*
99  * Prepare for seperation of verify_header and checksum header
100  */
101 static inline unsigned int __hdr_size(int verify_type)
102 {
103         unsigned int len = len;
104
105         switch (verify_type) {
106         case VERIFY_NONE:
107         case VERIFY_NULL:
108                 len = 0;
109                 break;
110         case VERIFY_MD5:
111                 len = sizeof(struct vhdr_md5);
112                 break;
113         case VERIFY_CRC64:
114                 len = sizeof(struct vhdr_crc64);
115                 break;
116         case VERIFY_CRC32C:
117         case VERIFY_CRC32:
118         case VERIFY_CRC32C_INTEL:
119                 len = sizeof(struct vhdr_crc32);
120                 break;
121         case VERIFY_CRC16:
122                 len = sizeof(struct vhdr_crc16);
123                 break;
124         case VERIFY_CRC7:
125                 len = sizeof(struct vhdr_crc7);
126                 break;
127         case VERIFY_SHA256:
128                 len = sizeof(struct vhdr_sha256);
129                 break;
130         case VERIFY_SHA512:
131                 len = sizeof(struct vhdr_sha512);
132                 break;
133         case VERIFY_META:
134                 len = sizeof(struct vhdr_meta);
135                 break;
136         case VERIFY_SHA1:
137                 len = sizeof(struct vhdr_sha1);
138                 break;
139         default:
140                 log_err("fio: unknown verify header!\n");
141                 assert(0);
142         }
143
144         return len + sizeof(struct verify_header);
145 }
146
147 static inline unsigned int hdr_size(struct verify_header *hdr)
148 {
149         return __hdr_size(hdr->verify_type);
150 }
151
152 static void *hdr_priv(struct verify_header *hdr)
153 {
154         void *priv = hdr;
155
156         return priv + sizeof(struct verify_header);
157 }
158
159 /*
160  * Return data area 'header_num'
161  */
162 static inline void *io_u_verify_off(struct verify_header *hdr,
163                                     struct io_u *io_u, unsigned char header_num)
164 {
165         return io_u->buf + header_num * hdr->len + hdr_size(hdr);
166 }
167
168 static int verify_io_u_meta(struct verify_header *hdr, struct thread_data *td,
169                             struct io_u *io_u, unsigned int header_num)
170 {
171         struct vhdr_meta *vh = hdr_priv(hdr);
172
173         dprint(FD_VERIFY, "meta verify io_u %p, len %u\n", io_u, hdr->len);
174
175         if (vh->offset != io_u->offset + header_num * td->o.verify_interval) {
176                 log_err("meta: verify failed at %llu/%u\n",
177                                 io_u->offset + header_num * hdr->len, hdr->len);
178                 return EILSEQ;
179         }
180
181         return 0;
182 }
183
184 static int verify_io_u_sha512(struct verify_header *hdr, struct io_u *io_u,
185                               unsigned int header_num)
186 {
187         void *p = io_u_verify_off(hdr, io_u, header_num);
188         struct vhdr_sha512 *vh = hdr_priv(hdr);
189         uint8_t sha512[128];
190         struct sha512_ctx sha512_ctx = {
191                 .buf = sha512,
192         };
193
194         dprint(FD_VERIFY, "sha512 verify io_u %p, len %u\n", io_u, hdr->len);
195
196         sha512_init(&sha512_ctx);
197         sha512_update(&sha512_ctx, p, hdr->len - hdr_size(hdr));
198
199         if (memcmp(vh->sha512, sha512_ctx.buf, sizeof(sha512))) {
200                 log_err("sha512: verify failed at %llu/%u\n",
201                                 io_u->offset + header_num * hdr->len, hdr->len);
202                 hexdump(vh->sha512, sizeof(vh->sha512));
203                 hexdump(sha512_ctx.buf, sizeof(sha512));
204                 return EILSEQ;
205         }
206
207         return 0;
208 }
209
210 static int verify_io_u_sha256(struct verify_header *hdr, struct io_u *io_u,
211                               unsigned int header_num)
212 {
213         void *p = io_u_verify_off(hdr, io_u, header_num);
214         struct vhdr_sha256 *vh = hdr_priv(hdr);
215         uint8_t sha256[128];
216         struct sha256_ctx sha256_ctx = {
217                 .buf = sha256,
218         };
219
220         dprint(FD_VERIFY, "sha256 verify io_u %p, len %u\n", io_u, hdr->len);
221
222         sha256_init(&sha256_ctx);
223         sha256_update(&sha256_ctx, p, hdr->len - hdr_size(hdr));
224
225         if (memcmp(vh->sha256, sha256_ctx.buf, sizeof(sha256))) {
226                 log_err("sha256: verify failed at %llu/%u\n",
227                                 io_u->offset + header_num * hdr->len, hdr->len);
228                 hexdump(vh->sha256, sizeof(vh->sha256));
229                 hexdump(sha256_ctx.buf, sizeof(sha256));
230                 return EILSEQ;
231         }
232
233         return 0;
234 }
235
236 static int verify_io_u_sha1(struct verify_header *hdr, struct io_u *io_u,
237                             unsigned int header_num)
238 {
239         void *p = io_u_verify_off(hdr, io_u, header_num);
240         struct vhdr_sha1 *vh = hdr_priv(hdr);
241         uint32_t sha1[5];
242         struct sha1_ctx sha1_ctx = {
243                 .H = sha1,
244         };
245
246         dprint(FD_VERIFY, "sha1 verify io_u %p, len %u\n", io_u, hdr->len);
247
248         sha1_init(&sha1_ctx);
249         sha1_update(&sha1_ctx, p, hdr->len - hdr_size(hdr));
250
251         if (memcmp(vh->sha1, sha1_ctx.H, sizeof(sha1))) {
252                 log_err("sha1: verify failed at %llu/%u\n",
253                                 io_u->offset + header_num * hdr->len, hdr->len);
254                 hexdump(vh->sha1, sizeof(vh->sha1));
255                 hexdump(sha1_ctx.H, sizeof(sha1));
256                 return EILSEQ;
257         }
258
259         return 0;
260 }
261
262 static int verify_io_u_crc7(struct verify_header *hdr, struct io_u *io_u,
263                             unsigned char header_num)
264 {
265         void *p = io_u_verify_off(hdr, io_u, header_num);
266         struct vhdr_crc7 *vh = hdr_priv(hdr);
267         unsigned char c;
268
269         dprint(FD_VERIFY, "crc7 verify io_u %p, len %u\n", io_u, hdr->len);
270
271         c = crc7(p, hdr->len - hdr_size(hdr));
272
273         if (c != vh->crc7) {
274                 log_err("crc7: verify failed at %llu/%u\n",
275                                 io_u->offset + header_num * hdr->len, hdr->len);
276                 log_err("crc7: wanted %x, got %x\n", vh->crc7, c);
277                 return EILSEQ;
278         }
279
280         return 0;
281 }
282
283 static int verify_io_u_crc16(struct verify_header *hdr, struct io_u *io_u,
284                              unsigned int header_num)
285 {
286         void *p = io_u_verify_off(hdr, io_u, header_num);
287         struct vhdr_crc16 *vh = hdr_priv(hdr);
288         unsigned short c;
289
290         dprint(FD_VERIFY, "crc16 verify io_u %p, len %u\n", io_u, hdr->len);
291
292         c = crc16(p, hdr->len - hdr_size(hdr));
293
294         if (c != vh->crc16) {
295                 log_err("crc16: verify failed at %llu/%u\n",
296                                 io_u->offset + header_num * hdr->len, hdr->len);
297                 log_err("crc16: wanted %x, got %x\n", vh->crc16, c);
298                 return EILSEQ;
299         }
300
301         return 0;
302 }
303
304 static int verify_io_u_crc64(struct verify_header *hdr, struct io_u *io_u,
305                              unsigned int header_num)
306 {
307         void *p = io_u_verify_off(hdr, io_u, header_num);
308         struct vhdr_crc64 *vh = hdr_priv(hdr);
309         unsigned long long c;
310
311         dprint(FD_VERIFY, "crc64 verify io_u %p, len %u\n", io_u, hdr->len);
312
313         c = crc64(p, hdr->len - hdr_size(hdr));
314
315         if (c != vh->crc64) {
316                 log_err("crc64: verify failed at %llu/%u\n",
317                                 io_u->offset + header_num * hdr->len,
318                                 hdr->len);
319                 log_err("crc64: wanted %llx, got %llx\n",
320                                         (unsigned long long) vh->crc64, c);
321                 return EILSEQ;
322         }
323
324         return 0;
325 }
326
327 static int verify_io_u_crc32(struct verify_header *hdr, struct io_u *io_u,
328                              unsigned int header_num)
329 {
330         void *p = io_u_verify_off(hdr, io_u, header_num);
331         struct vhdr_crc32 *vh = hdr_priv(hdr);
332         uint32_t c;
333
334         dprint(FD_VERIFY, "crc32 verify io_u %p, len %u\n", io_u, hdr->len);
335
336         c = crc32(p, hdr->len - hdr_size(hdr));
337
338         if (c != vh->crc32) {
339                 log_err("crc32: verify failed at %llu/%u\n",
340                                 io_u->offset + header_num * hdr->len, hdr->len);
341                 log_err("crc32: wanted %x, got %x\n", vh->crc32, c);
342                 return EILSEQ;
343         }
344
345         return 0;
346 }
347
348 static int verify_io_u_crc32c(struct verify_header *hdr, struct io_u *io_u,
349                               unsigned int header_num)
350 {
351         void *p = io_u_verify_off(hdr, io_u, header_num);
352         struct vhdr_crc32 *vh = hdr_priv(hdr);
353         uint32_t c;
354
355         dprint(FD_VERIFY, "crc32c verify io_u %p, len %u\n", io_u, hdr->len);
356
357         if (hdr->verify_type == VERIFY_CRC32C_INTEL)
358                 c = crc32c_intel(p, hdr->len - hdr_size(hdr));
359         else
360                 c = crc32c(p, hdr->len - hdr_size(hdr));
361
362         if (c != vh->crc32) {
363                 log_err("crc32c: verify failed at %llu/%u\n",
364                                 io_u->offset + header_num * hdr->len, hdr->len);
365                 log_err("crc32c: wanted %x, got %x\n", vh->crc32, c);
366                 return EILSEQ;
367         }
368
369         return 0;
370 }
371
372 static int verify_io_u_md5(struct verify_header *hdr, struct io_u *io_u,
373                            unsigned int header_num)
374 {
375         void *p = io_u_verify_off(hdr, io_u, header_num);
376         struct vhdr_md5 *vh = hdr_priv(hdr);
377         uint32_t hash[MD5_HASH_WORDS];
378         struct md5_ctx md5_ctx = {
379                 .hash = hash,
380         };
381
382         dprint(FD_VERIFY, "md5 verify io_u %p, len %u\n", io_u, hdr->len);
383
384         md5_init(&md5_ctx);
385         md5_update(&md5_ctx, p, hdr->len - hdr_size(hdr));
386
387         if (memcmp(vh->md5_digest, md5_ctx.hash, sizeof(hash))) {
388                 log_err("md5: verify failed at %llu/%u\n",
389                                 io_u->offset + header_num * hdr->len, hdr->len);
390                 hexdump(vh->md5_digest, sizeof(vh->md5_digest));
391                 hexdump(md5_ctx.hash, sizeof(hash));
392                 return EILSEQ;
393         }
394
395         return 0;
396 }
397
398 static unsigned int hweight8(unsigned int w)
399 {
400         unsigned int res = w - ((w >> 1) & 0x55);
401
402         res = (res & 0x33) + ((res >> 2) & 0x33);
403         return (res + (res >> 4)) & 0x0F;
404 }
405
406 int verify_io_u_pattern(char *pattern, unsigned long pattern_size,
407                         char *buf, unsigned int len, unsigned int mod)
408 {
409         unsigned int i;
410
411         for (i = 0; i < len; i++) {
412                 if (buf[i] != pattern[mod]) {
413                         unsigned int bits;
414
415                         bits = hweight8(buf[i] ^ pattern[mod]);
416                         log_err("fio: got pattern %x, wanted %x. Bad bits %d\n",
417                                 buf[i], pattern[mod], bits);
418                         log_err("fio: bad pattern block offset %u\n", i);
419                         return EILSEQ;
420                 }
421                 mod++;
422                 if (mod == pattern_size)
423                         mod = 0;
424         }
425
426         return 0;
427 }
428
429 /*
430  * Push IO verification to a separate thread
431  */
432 int verify_io_u_async(struct thread_data *td, struct io_u *io_u)
433 {
434         if (io_u->file)
435                 put_file_log(td, io_u->file);
436
437         io_u->file = NULL;
438
439         pthread_mutex_lock(&td->io_u_lock);
440         flist_del(&io_u->list);
441         flist_add_tail(&io_u->list, &td->verify_list);
442         pthread_mutex_unlock(&td->io_u_lock);
443
444         pthread_cond_signal(&td->verify_cond);
445         io_u->flags |= IO_U_F_FREE_DEF;
446         return 0;
447 }
448
449 int verify_io_u(struct thread_data *td, struct io_u *io_u)
450 {
451         struct verify_header *hdr;
452         unsigned int hdr_size, hdr_inc, hdr_num = 0;
453         void *p;
454         int ret;
455
456         if (td->o.verify == VERIFY_NULL || io_u->ddir != DDIR_READ)
457                 return 0;
458
459         hdr_inc = io_u->buflen;
460         if (td->o.verify_interval)
461                 hdr_inc = td->o.verify_interval;
462
463         ret = 0;
464         for (p = io_u->buf; p < io_u->buf + io_u->buflen;
465              p += hdr_inc, hdr_num++) {
466                 if (ret && td->o.verify_fatal) {
467                         td->terminate = 1;
468                         break;
469                 }
470                 hdr_size = __hdr_size(td->o.verify);
471                 if (td->o.verify_offset)
472                         memswp(p, p + td->o.verify_offset, hdr_size);
473                 hdr = p;
474
475                 if (hdr->fio_magic != FIO_HDR_MAGIC) {
476                         log_err("Bad verify header %x\n", hdr->fio_magic);
477                         return EILSEQ;
478                 }
479
480                 if (td->o.verify_pattern_bytes) {
481                         dprint(FD_VERIFY, "pattern verify io_u %p, len %u\n",
482                                                                 io_u, hdr->len);
483                         ret = verify_io_u_pattern(td->o.verify_pattern,
484                                   td->o.verify_pattern_bytes,
485                                   p + hdr_size,
486                                   hdr_inc - hdr_size,
487                                   hdr_size % td->o.verify_pattern_bytes);
488                         /*
489                          * Also verify the meta data, if applicable
490                          */
491                         if (hdr->verify_type == VERIFY_META)
492                                 ret |= verify_io_u_meta(hdr, td, io_u, hdr_num);
493
494                         if (ret)
495                                 log_err("fio: verify failed at %llu/%u\n",
496                                         io_u->offset + hdr_num * hdr->len,
497                                         hdr->len);
498                         continue;
499                 }
500
501                 switch (hdr->verify_type) {
502                 case VERIFY_MD5:
503                         ret = verify_io_u_md5(hdr, io_u, hdr_num);
504                         break;
505                 case VERIFY_CRC64:
506                         ret = verify_io_u_crc64(hdr, io_u, hdr_num);
507                         break;
508                 case VERIFY_CRC32C:
509                 case VERIFY_CRC32C_INTEL:
510                         ret = verify_io_u_crc32c(hdr, io_u, hdr_num);
511                         break;
512                 case VERIFY_CRC32:
513                         ret = verify_io_u_crc32(hdr, io_u, hdr_num);
514                         break;
515                 case VERIFY_CRC16:
516                         ret = verify_io_u_crc16(hdr, io_u, hdr_num);
517                         break;
518                 case VERIFY_CRC7:
519                         ret = verify_io_u_crc7(hdr, io_u, hdr_num);
520                         break;
521                 case VERIFY_SHA256:
522                         ret = verify_io_u_sha256(hdr, io_u, hdr_num);
523                         break;
524                 case VERIFY_SHA512:
525                         ret = verify_io_u_sha512(hdr, io_u, hdr_num);
526                         break;
527                 case VERIFY_META:
528                         ret = verify_io_u_meta(hdr, td, io_u, hdr_num);
529                         break;
530                 case VERIFY_SHA1:
531                         ret = verify_io_u_sha1(hdr, io_u, hdr_num);
532                         break;
533                 default:
534                         log_err("Bad verify type %u\n", hdr->verify_type);
535                         ret = EINVAL;
536                 }
537         }
538
539         return ret;
540 }
541
542 static void fill_meta(struct verify_header *hdr, struct thread_data *td,
543                       struct io_u *io_u, unsigned int header_num)
544 {
545         struct vhdr_meta *vh = hdr_priv(hdr);
546
547         vh->thread = td->thread_number;
548
549         vh->time_sec = io_u->start_time.tv_sec;
550         vh->time_usec = io_u->start_time.tv_usec;
551
552         vh->numberio = td->io_issues[DDIR_WRITE];
553
554         vh->offset = io_u->offset + header_num * td->o.verify_interval;
555 }
556
557 static void fill_sha512(struct verify_header *hdr, void *p, unsigned int len)
558 {
559         struct vhdr_sha512 *vh = hdr_priv(hdr);
560         struct sha512_ctx sha512_ctx = {
561                 .buf = vh->sha512,
562         };
563
564         sha512_init(&sha512_ctx);
565         sha512_update(&sha512_ctx, p, len);
566 }
567
568 static void fill_sha256(struct verify_header *hdr, void *p, unsigned int len)
569 {
570         struct vhdr_sha256 *vh = hdr_priv(hdr);
571         struct sha256_ctx sha256_ctx = {
572                 .buf = vh->sha256,
573         };
574
575         sha256_init(&sha256_ctx);
576         sha256_update(&sha256_ctx, p, len);
577 }
578
579 static void fill_sha1(struct verify_header *hdr, void *p, unsigned int len)
580 {
581         struct vhdr_sha1 *vh = hdr_priv(hdr);
582         struct sha1_ctx sha1_ctx = {
583                 .H = vh->sha1,
584         };
585
586         sha1_init(&sha1_ctx);
587         sha1_update(&sha1_ctx, p, len);
588 }
589
590 static void fill_crc7(struct verify_header *hdr, void *p, unsigned int len)
591 {
592         struct vhdr_crc7 *vh = hdr_priv(hdr);
593
594         vh->crc7 = crc7(p, len);
595 }
596
597 static void fill_crc16(struct verify_header *hdr, void *p, unsigned int len)
598 {
599         struct vhdr_crc16 *vh = hdr_priv(hdr);
600
601         vh->crc16 = crc16(p, len);
602 }
603
604 static void fill_crc32(struct verify_header *hdr, void *p, unsigned int len)
605 {
606         struct vhdr_crc32 *vh = hdr_priv(hdr);
607
608         vh->crc32 = crc32(p, len);
609 }
610
611 static void fill_crc32c(struct verify_header *hdr, void *p, unsigned int len)
612 {
613         struct vhdr_crc32 *vh = hdr_priv(hdr);
614
615         if (hdr->verify_type == VERIFY_CRC32C_INTEL)
616                 vh->crc32 = crc32c_intel(p, len);
617         else
618                 vh->crc32 = crc32c(p, len);
619 }
620
621 static void fill_crc64(struct verify_header *hdr, void *p, unsigned int len)
622 {
623         struct vhdr_crc64 *vh = hdr_priv(hdr);
624
625         vh->crc64 = crc64(p, len);
626 }
627
628 static void fill_md5(struct verify_header *hdr, void *p, unsigned int len)
629 {
630         struct vhdr_md5 *vh = hdr_priv(hdr);
631         struct md5_ctx md5_ctx = {
632                 .hash = (uint32_t *) vh->md5_digest,
633         };
634
635         md5_init(&md5_ctx);
636         md5_update(&md5_ctx, p, len);
637 }
638
639 /*
640  * fill body of io_u->buf with random data and add a header with the
641  * crc32 or md5 sum of that data.
642  */
643 void populate_verify_io_u(struct thread_data *td, struct io_u *io_u)
644 {
645         struct verify_header *hdr;
646         void *p = io_u->buf, *data;
647         unsigned int hdr_inc, data_len, header_num = 0;
648
649         if (td->o.verify == VERIFY_NULL)
650                 return;
651
652         fill_pattern(td, p, io_u->buflen);
653
654         hdr_inc = io_u->buflen;
655         if (td->o.verify_interval)
656                 hdr_inc = td->o.verify_interval;
657
658         for (; p < io_u->buf + io_u->buflen; p += hdr_inc) {
659                 hdr = p;
660
661                 hdr->fio_magic = FIO_HDR_MAGIC;
662                 hdr->verify_type = td->o.verify;
663                 hdr->len = hdr_inc;
664                 data_len = hdr_inc - hdr_size(hdr);
665
666                 data = p + hdr_size(hdr);
667                 switch (td->o.verify) {
668                 case VERIFY_MD5:
669                         dprint(FD_VERIFY, "fill md5 io_u %p, len %u\n",
670                                                         io_u, hdr->len);
671                         fill_md5(hdr, data, data_len);
672                         break;
673                 case VERIFY_CRC64:
674                         dprint(FD_VERIFY, "fill crc64 io_u %p, len %u\n",
675                                                         io_u, hdr->len);
676                         fill_crc64(hdr, data, data_len);
677                         break;
678                 case VERIFY_CRC32C:
679                 case VERIFY_CRC32C_INTEL:
680                         dprint(FD_VERIFY, "fill crc32c io_u %p, len %u\n",
681                                                         io_u, hdr->len);
682                         fill_crc32c(hdr, data, data_len);
683                         break;
684                 case VERIFY_CRC32:
685                         dprint(FD_VERIFY, "fill crc32 io_u %p, len %u\n",
686                                                         io_u, hdr->len);
687                         fill_crc32(hdr, data, data_len);
688                         break;
689                 case VERIFY_CRC16:
690                         dprint(FD_VERIFY, "fill crc16 io_u %p, len %u\n",
691                                                         io_u, hdr->len);
692                         fill_crc16(hdr, data, data_len);
693                         break;
694                 case VERIFY_CRC7:
695                         dprint(FD_VERIFY, "fill crc7 io_u %p, len %u\n",
696                                                         io_u, hdr->len);
697                         fill_crc7(hdr, data, data_len);
698                         break;
699                 case VERIFY_SHA256:
700                         dprint(FD_VERIFY, "fill sha256 io_u %p, len %u\n",
701                                                         io_u, hdr->len);
702                         fill_sha256(hdr, data, data_len);
703                         break;
704                 case VERIFY_SHA512:
705                         dprint(FD_VERIFY, "fill sha512 io_u %p, len %u\n",
706                                                         io_u, hdr->len);
707                         fill_sha512(hdr, data, data_len);
708                         break;
709                 case VERIFY_META:
710                         dprint(FD_VERIFY, "fill meta io_u %p, len %u\n",
711                                                         io_u, hdr->len);
712                         fill_meta(hdr, td, io_u, header_num);
713                         break;
714                 case VERIFY_SHA1:
715                         dprint(FD_VERIFY, "fill sha1 io_u %p, len %u\n",
716                                                         io_u, hdr->len);
717                         fill_sha1(hdr, data, data_len);
718                         break;
719                 default:
720                         log_err("fio: bad verify type: %d\n", td->o.verify);
721                         assert(0);
722                 }
723                 if (td->o.verify_offset)
724                         memswp(p, p + td->o.verify_offset, hdr_size(hdr));
725                 header_num++;
726         }
727 }
728
729 int get_next_verify(struct thread_data *td, struct io_u *io_u)
730 {
731         struct io_piece *ipo = NULL;
732
733         /*
734          * this io_u is from a requeue, we already filled the offsets
735          */
736         if (io_u->file)
737                 return 0;
738
739         if (!RB_EMPTY_ROOT(&td->io_hist_tree)) {
740                 struct rb_node *n = rb_first(&td->io_hist_tree);
741
742                 ipo = rb_entry(n, struct io_piece, rb_node);
743                 rb_erase(n, &td->io_hist_tree);
744         } else if (!flist_empty(&td->io_hist_list)) {
745                 ipo = flist_entry(td->io_hist_list.next, struct io_piece, list);
746                 flist_del(&ipo->list);
747         }
748
749         if (ipo) {
750                 io_u->offset = ipo->offset;
751                 io_u->buflen = ipo->len;
752                 io_u->file = ipo->file;
753
754                 if (!fio_file_open(io_u->file)) {
755                         int r = td_io_open_file(td, io_u->file);
756
757                         if (r) {
758                                 dprint(FD_VERIFY, "failed file %s open\n",
759                                                 io_u->file->file_name);
760                                 return 1;
761                         }
762                 }
763
764                 get_file(ipo->file);
765                 assert(fio_file_open(io_u->file));
766                 io_u->ddir = DDIR_READ;
767                 io_u->xfer_buf = io_u->buf;
768                 io_u->xfer_buflen = io_u->buflen;
769                 free(ipo);
770                 dprint(FD_VERIFY, "get_next_verify: ret io_u %p\n", io_u);
771                 return 0;
772         }
773
774         dprint(FD_VERIFY, "get_next_verify: empty\n");
775         return 1;
776 }
777
778 static void *verify_async_thread(void *data)
779 {
780         struct thread_data *td = data;
781         struct io_u *io_u;
782         int ret = 0;
783
784         if (td->o.verify_cpumask_set &&
785             fio_setaffinity(td->pid, td->o.verify_cpumask)) {
786                 log_err("fio: failed setting verify thread affinity\n");
787                 goto done;
788         }
789
790         do {
791                 FLIST_HEAD(list);
792
793                 read_barrier();
794                 if (td->verify_thread_exit)
795                         break;
796
797                 pthread_mutex_lock(&td->io_u_lock);
798
799                 while (flist_empty(&td->verify_list) &&
800                        !td->verify_thread_exit) {
801                         ret = pthread_cond_wait(&td->verify_cond,
802                                                         &td->io_u_lock);
803                         if (ret) {
804                                 pthread_mutex_unlock(&td->io_u_lock);
805                                 break;
806                         }
807                 }
808
809                 flist_splice_init(&td->verify_list, &list);
810                 pthread_mutex_unlock(&td->io_u_lock);
811
812                 if (flist_empty(&list))
813                         continue;
814
815                 while (!flist_empty(&list)) {
816                         io_u = flist_entry(list.next, struct io_u, list);
817                         flist_del_init(&io_u->list);
818
819                         ret = verify_io_u(td, io_u);
820                         put_io_u(td, io_u);
821                         if (!ret)
822                                 continue;
823                         if (td->o.continue_on_error &&
824                             td_non_fatal_error(ret)) {
825                                 update_error_count(td, ret);
826                                 td_clear_error(td);
827                                 ret = 0;
828                         }
829                 }
830         } while (!ret);
831
832         if (ret) {
833                 td_verror(td, ret, "async_verify");
834                 td->terminate = 1;
835         }
836
837 done:
838         pthread_mutex_lock(&td->io_u_lock);
839         td->nr_verify_threads--;
840         pthread_mutex_unlock(&td->io_u_lock);
841
842         pthread_cond_signal(&td->free_cond);
843         return NULL;
844 }
845
846 int verify_async_init(struct thread_data *td)
847 {
848         int i, ret;
849
850         td->verify_thread_exit = 0;
851
852         td->verify_threads = malloc(sizeof(pthread_t) * td->o.verify_async);
853         for (i = 0; i < td->o.verify_async; i++) {
854                 ret = pthread_create(&td->verify_threads[i], NULL,
855                                         verify_async_thread, td);
856                 if (ret) {
857                         log_err("fio: async verify creation failed: %s\n",
858                                         strerror(ret));
859                         break;
860                 }
861                 ret = pthread_detach(td->verify_threads[i]);
862                 if (ret) {
863                         log_err("fio: async verify thread detach failed: %s\n",
864                                         strerror(ret));
865                         break;
866                 }
867                 td->nr_verify_threads++;
868         }
869
870         if (i != td->o.verify_async) {
871                 log_err("fio: only %d verify threads started, exiting\n", i);
872                 td->verify_thread_exit = 1;
873                 write_barrier();
874                 pthread_cond_broadcast(&td->verify_cond);
875                 return 1;
876         }
877
878         return 0;
879 }
880
881 void verify_async_exit(struct thread_data *td)
882 {
883         td->verify_thread_exit = 1;
884         write_barrier();
885         pthread_cond_broadcast(&td->verify_cond);
886
887         pthread_mutex_lock(&td->io_u_lock);
888
889         while (td->nr_verify_threads)
890                 pthread_cond_wait(&td->free_cond, &td->io_u_lock);
891
892         pthread_mutex_unlock(&td->io_u_lock);
893         free(td->verify_threads);
894         td->verify_threads = NULL;
895 }