diff options
author | Keir Fraser <keir.fraser@citrix.com> | 2009-12-17 06:27:57 +0000 |
---|---|---|
committer | Keir Fraser <keir.fraser@citrix.com> | 2009-12-17 06:27:57 +0000 |
commit | 4515e6d82b23366933055b0ad60d8ed89f5a2b92 (patch) | |
tree | c07557a5b58cadbd0de42669b2ed898b37626e76 /tools/blktap2 | |
parent | 06d2e6455f6333c7049f72d41f8c89a1a9884e51 (diff) | |
download | xen-4515e6d82b23366933055b0ad60d8ed89f5a2b92.tar.gz xen-4515e6d82b23366933055b0ad60d8ed89f5a2b92.tar.bz2 xen-4515e6d82b23366933055b0ad60d8ed89f5a2b92.zip |
Reads from read only parent disk images are intercepted, and are used to detect
potentially sharable memory pages.
Signed-off-by: Grzegorz Milos <Grzegorz.Milos@citrix.com>
Diffstat (limited to 'tools/blktap2')
-rw-r--r-- | tools/blktap2/drivers/Makefile | 3 | ||||
-rw-r--r-- | tools/blktap2/drivers/tapdisk-vbd.c | 52 | ||||
-rw-r--r-- | tools/blktap2/drivers/tapdisk.h | 2 |
3 files changed, 54 insertions, 3 deletions
diff --git a/tools/blktap2/drivers/Makefile b/tools/blktap2/drivers/Makefile index 97f27b56d3..b70ca7ddc0 100644 --- a/tools/blktap2/drivers/Makefile +++ b/tools/blktap2/drivers/Makefile @@ -14,6 +14,7 @@ CFLAGS += -Wno-unused CFLAGS += -fno-strict-aliasing CFLAGS += -I../lib -I../../libxc CFLAGS += -I../include -I../../include +CFLAGS += $(CFLAGS_libxenctrl) CFLAGS += -I $(LIBAIO_DIR) CFLAGS += -I $(MEMSHR_DIR) CFLAGS += -D_GNU_SOURCE @@ -37,7 +38,7 @@ else CRYPT_LIB += -lcrypto endif -LDFLAGS_img := $(CRYPT_LIB) -lpthread -lz -lm +LDFLAGS_img := $(LDFLAGS_libxenctrl) $(CRYPT_LIB) -lpthread -lz -lm LIBS += -L$(LIBVHDDIR) -lvhd diff --git a/tools/blktap2/drivers/tapdisk-vbd.c b/tools/blktap2/drivers/tapdisk-vbd.c index 07504cf7da..14507b3830 100644 --- a/tools/blktap2/drivers/tapdisk-vbd.c +++ b/tools/blktap2/drivers/tapdisk-vbd.c @@ -1418,11 +1418,26 @@ tapdisk_vbd_complete_vbd_request(td_vbd_t *vbd, td_vbd_request_t *vreq) } } +static uint64_t +tapdisk_vbd_breq_get_sector(blkif_request_t *breq, td_request_t treq) +{ + int seg, nsects; + uint64_t sector_nr = breq->sector_number; + + for(seg=0; seg < treq.sidx; seg++) { + nsects = breq->seg[seg].last_sect - breq->seg[seg].first_sect + 1; + sector_nr += nsects; + } + + return sector_nr; +} + static void __tapdisk_vbd_complete_td_request(td_vbd_t *vbd, td_vbd_request_t *vreq, td_request_t treq, int res) { int err; + td_image_t *image = treq.image; err = (res <= 0 ? res : -res); vbd->secs_pending -= treq.secs; @@ -1440,7 +1455,18 @@ __tapdisk_vbd_complete_td_request(td_vbd_t *vbd, td_vbd_request_t *vreq, (treq.op == TD_OP_WRITE ? "write" : "read"), treq.secs, treq.sec); } - } + } else + if(treq.op == TD_OP_READ && td_flag_test(image->flags, TD_OPEN_RDONLY)) { + uint64_t hnd = treq.memshr_hnd; + uint16_t uid = image->memshr_id; + blkif_request_t *breq = &vreq->req; + uint64_t sec = tapdisk_vbd_breq_get_sector(breq, treq); + int secs = breq->seg[treq.sidx].last_sect - + breq->seg[treq.sidx].first_sect + 1; + + if(hnd != 0) + memshr_vbd_complete_ro_request(hnd, uid, sec, secs); + } tapdisk_vbd_complete_vbd_request(vbd, vreq); } @@ -1492,7 +1518,29 @@ __tapdisk_vbd_reissue_td_request(td_vbd_t *vbd, break; case TD_OP_READ: - td_queue_read(parent, treq); + if(td_flag_test(parent->flags, TD_OPEN_RDONLY)) + { + int ret, seg = treq.sidx; + blkif_request_t *breq = &vreq->req; + + ret = memshr_vbd_issue_ro_request(treq.buf, + breq->seg[seg].gref, + parent->memshr_id, + treq.sec, + treq.secs, + &treq.memshr_hnd); + if(ret == 0) + { + /* Reset memshr handle. This'll prevent + * memshr_vbd_complete_ro_request being called */ + treq.memshr_hnd = 0; + td_complete_request(treq, 0); + } + else + td_queue_read(parent, treq); + } + else + td_queue_read(parent, treq); break; } diff --git a/tools/blktap2/drivers/tapdisk.h b/tools/blktap2/drivers/tapdisk.h index b1a91c77f2..bd6835e5e8 100644 --- a/tools/blktap2/drivers/tapdisk.h +++ b/tools/blktap2/drivers/tapdisk.h @@ -131,6 +131,8 @@ struct td_request { uint64_t id; int sidx; void *private; + + uint64_t memshr_hnd; }; /* |