Login
[x]
Log in using an account from:
Fedora Account System
Red Hat Associate
Red Hat Customer
Or login using a Red Hat Bugzilla account
Forgot Password
Login:
Hide Forgot
Create an Account
Red Hat Bugzilla – Attachment 314573 Details for
Bug 459337
dm-snap.c: Data read from snapshot may be corrupt if origin is being written to simultaneously
[?]
New
Simple Search
Advanced Search
My Links
Browse
Requests
Reports
Current State
Search
Tabular reports
Graphical reports
Duplicates
Other Reports
User Changes
Plotly Reports
Bug Status
Bug Severity
Non-Defaults
|
Product Dashboard
Help
Page Help!
Bug Writing Guidelines
What's new
Browser Support Policy
5.0.4.rh83 Release notes
FAQ
Guides index
User guide
Web Services
Contact
Legal
This site requires JavaScript to be enabled to function correctly, please enable it.
second testcase
testcase-read-snapshot-vs-write-origin-2.c (text/plain), 6.76 KB, created by
Mikuláš Patočka
on 2008-08-19 21:05:55 UTC
(
hide
)
Description:
second testcase
Filename:
MIME Type:
Creator:
Mikuláš Patočka
Created:
2008-08-19 21:05:55 UTC
Size:
6.76 KB
patch
obsolete
>#define _XOPEN_SOURCE 500 >#define _GNU_SOURCE >#include <stdio.h> >#include <stdlib.h> >#include <unistd.h> >#include <fcntl.h> >#include <string.h> >#include <errno.h> >#include <malloc.h> >#include <pthread.h> >#include <asm/unistd.h> > >/* > * A testcase for a race-condition in dm-snapshots. > * > * Change "VG" symbol to a volume group name that you are using. > * The group should be on real disk with NCQ disabled. > * No virtualization, no network disks, no ramdisk, no pagecache-backed loopback > * (dm-loop is OK) > * Use a CFQ disk scheduler on the physical device. > * > * You may tune the parameters with this #defines, if you have too fast disk, > * try increasing number of threads. > * > * How does it work: > * It creates 10MB logical volume, fills it with a pattern and creates > * snapshot. > * Then, it spawns 10 threads, and synchronizes them so that the main > * thread simultaneously starts writing to the main volume and 10 helper > * threads start reading the snapshot. > * All the threads run in lockstep, operating on the same block > * simultaneously (note the unusual use of 3 rw-locks for maintaining the > * lockstep). > * The reader threads have much lower I/O priority than the main writing > * thread, so that their reads will be submitted, but will eventually wait > * until the main thread does its relocate and write. The readers will then > * read from the old overwritten area and signal an error. > */ > >#define VG "vg1" >#define LV "test_lv" >#define LV_SNAP "test_snap" >#define MEGABYTES "12" >#define SNAP_MEGABYTES "16" >#define THREADS 10 >#define BS 4096 >#define ORIG_PATTERN 'p' >#define NEW_PATTERN 'n' > >enum { > IOPRIO_CLASS_NONE, > IOPRIO_CLASS_RT, > IOPRIO_CLASS_BE, > IOPRIO_CLASS_IDLE, >}; > >enum { > IOPRIO_WHO_PROCESS = 1, > IOPRIO_WHO_PGRP, > IOPRIO_WHO_USER, >}; > >#define IOPRIO_CLASS_SHIFT 13 > >static inline int ioprio_set(int which, int who, int ioprio) >{ > return syscall(__NR_ioprio_set, which, who, ioprio); >} > >static inline int ioprio_get(int which, int who) >{ > return syscall(__NR_ioprio_get, which, who); >} > >#define PRIO_READER ((IOPRIO_CLASS_IDLE << IOPRIO_CLASS_SHIFT) | 0xff) >#define PRIO_WRITER (IOPRIO_CLASS_RT << IOPRIO_CLASS_SHIFT) > >static void do_cmd(char *cmd, int ign_err) >{ > int r; > fprintf(stderr, "* %s\n", cmd); > r = system(cmd); > if (r) { > if (r == -1) { > perror("system"); > } else { > if (ign_err) return; > fprintf(stderr, "return code %x\n", r); > } > exit(1); > } >} > >static char pattern[BS]; > >static int h_orig, h_snap; >static int n; >static long long test_of; >static pthread_rwlock_t rw_lock_1; >static pthread_rwlock_t rw_lock_2; >static pthread_rwlock_t rw_lock_3; >static volatile int started = 0; > >static void pthread_error(int r) >{ > fprintf(stderr, "pthread_error: %s\n", strerror(r)); > exit(1); >} > >static void *test_read(void *of) >{ > int r; > char *t = memalign(BS, BS); > if (!t) perror("memalign"), exit(1); > if ((r = pread(h_snap, t, BS, *(long long *)of)) != BS) { > fprintf(stderr, "can't read (%d): %s\n", r, strerror(errno)); > exit(1); > } > if (memcmp(pattern, t, BS)) { > int i; > for (i = 0; i < BS; i++) if (t[i] != pattern[i]) break; > fprintf(stderr, "!!!! SNAPSHOT VOLUME DAMAGE AT BLOCK OFFSET %llX, BYTE OFFSET %X: %02x != %02x\n", *(long long *)of, i, (unsigned char)t[i], (unsigned char)pattern[i]); > exit(2); > } > free(t); > return NULL; >} > >static void *test_thread(void *_) >{ > int r; > //fprintf(stderr, "start\n"); > if ((r = ioprio_set(IOPRIO_WHO_PROCESS, 0, PRIO_READER))) perror("ioprio_set"), exit(1); > if ((r = pthread_rwlock_rdlock(&rw_lock_2))) pthread_error(r); > started = 1; > if ((r = ioprio_get(IOPRIO_WHO_PROCESS, 0)) != PRIO_READER) { > if (r == -1) perror("ioprio_get"); > else fprintf(stderr, "reader priority not set: %x\n", r); > exit(1); > } > again: > if ((r = pthread_rwlock_rdlock(&rw_lock_1))) pthread_error(r); > if ((r = pthread_rwlock_unlock(&rw_lock_2))) pthread_error(r); > if (test_of == -1) { > if ((r = pthread_rwlock_unlock(&rw_lock_1))) pthread_error(r); > //fprintf(stderr, "return\n"); > return NULL; > } > //fprintf(stderr, "test(%lld)\n", test_of); > test_read(&test_of); > if ((r = pthread_rwlock_rdlock(&rw_lock_3))) pthread_error(r); > if ((r = pthread_rwlock_unlock(&rw_lock_1))) pthread_error(r); > if ((r = pthread_rwlock_rdlock(&rw_lock_2))) pthread_error(r); > if ((r = pthread_rwlock_unlock(&rw_lock_3))) pthread_error(r); > goto again; >} > >int main(void) >{ > int i, j, r; > char *np; > pthread_t thr[THREADS]; > > memset(pattern, ORIG_PATTERN, sizeof pattern); > > do_cmd("lvremove -f "VG"/"LV_SNAP"", 1); > do_cmd("lvremove -f "VG"/"LV"", 1); > do_cmd("lvcreate -L "MEGABYTES" -n "LV" "VG"", 0); > > h_orig = open("/dev/mapper/"VG"-"LV"", O_RDWR); > if (h_orig < 0) perror("open orig"), exit(1); > n = 0; > while (write(h_orig, pattern, BS) == BS) { > n++; > fprintf(stderr, "creating %llx...\r", (long long)n * BS); > } > if (fsync(h_orig)) perror("fsync"), exit(1); > fprintf(stderr,"\n"); > lseek(h_orig, 0, SEEK_SET); > close(h_orig); > > do_cmd("lvcreate -L "SNAP_MEGABYTES" -n "LV_SNAP" -s "VG"/"LV"", 0); > > h_orig = open("/dev/mapper/"VG"-"LV"", O_RDWR | O_DIRECT); > if (h_orig < 0) perror("open orig"), exit(1); > > h_snap = open("/dev/mapper/"VG"-"LV_SNAP"", O_RDONLY | O_DIRECT); > if (h_snap < 0) perror("open snap"), exit(1); > > if ((r = pthread_rwlock_init(&rw_lock_1, NULL))) pthread_error(r); > if ((r = pthread_rwlock_init(&rw_lock_2, NULL))) pthread_error(r); > if ((r = pthread_rwlock_init(&rw_lock_3, NULL))) pthread_error(r); > if ((r = pthread_rwlock_wrlock(&rw_lock_1))) pthread_error(r); > if ((r = pthread_rwlock_wrlock(&rw_lock_3))) pthread_error(r); > > if ((r = ioprio_set(IOPRIO_WHO_PROCESS, 0, PRIO_WRITER))) perror("ioprio_set"), exit(1); > > for (j = 0; j < THREADS; j++) { > if ((r = pthread_create(&thr[j], NULL, test_thread, NULL))) pthread_error(r); > } > while (!started) usleep(1000); > > if ((r = ioprio_get(IOPRIO_WHO_PROCESS, 0)) != PRIO_WRITER) { > if (r == -1) perror("ioprio_get"); > else fprintf(stderr, "writer priority not set: %x\n", r); > exit(1); > } > > np = memalign(BS, BS); > if (!np) perror("memalign"), exit(1); > memset(np, NEW_PATTERN, BS); > for (i = 0; i < n; i++) { > test_of = (off_t)i * BS; > fprintf(stderr, "testing %llx...\r", test_of); > if ((r = pthread_rwlock_unlock(&rw_lock_1))) pthread_error(r); > if (pwrite(h_orig, np, BS, test_of) != BS) { > fprintf(stderr, "can't write (%d): %s\n", r, strerror(errno)); > exit(1); > } > if ((r = pthread_rwlock_wrlock(&rw_lock_2))) pthread_error(r); > if ((r = pthread_rwlock_unlock(&rw_lock_3))) pthread_error(r); > if ((r = pthread_rwlock_wrlock(&rw_lock_1))) pthread_error(r); > if ((r = pthread_rwlock_unlock(&rw_lock_2))) pthread_error(r); > if ((r = pthread_rwlock_wrlock(&rw_lock_3))) pthread_error(r); > } > fprintf(stderr,"\n"); > > test_of = -1; > if ((r = pthread_rwlock_unlock(&rw_lock_1))) pthread_error(r); > > for (j = 0; j < THREADS; j++) { > if ((r = pthread_join(thr[j], NULL))) pthread_error(r); > } > > fprintf(stderr, "TEST PASSED OK.\n"); > > return 0; >}
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Raw
Actions:
View
Attachments on
bug 459337
:
314570
|
314571
|
314572
| 314573