[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [RFC v1 5/5] VBD: enlarge max segment per request in blkfront
add segring support in blkback Signed-off-by: Ronghui Duan <ronghui.duan@xxxxxxxxx> diff --git a/drivers/block/xen-blkback/blkback.c b/drivers/block/xen-blkback/blkback.c index 45eda98..0bbc226 100644 --- a/drivers/block/xen-blkback/blkback.c +++ b/drivers/block/xen-blkback/blkback.c @@ -60,6 +60,10 @@ static int xen_blkif_reqs = 64; module_param_named(reqs, xen_blkif_reqs, int, 0); MODULE_PARM_DESC(reqs, "Number of blkback requests to allocate"); +int blkback_ring_type = 2; +module_param_named(blk_ring_type, blkback_ring_type, int, 0); +MODULE_PARM_DESC(blk_ring_type, "type of ring for blk device"); + /* Run-time switchable: /sys/module/blkback/parameters/ */ static unsigned int log_stats; module_param(log_stats, int, 0644); @@ -125,7 +129,7 @@ static struct pending_req *alloc_req(struct xen_blkif *blkif) struct xen_blkbk *blkbk = blkif->blkbk; struct pending_req *req = NULL; unsigned long flags; - unsigned int max_seg = BLKIF_MAX_SEGMENTS_PER_REQUEST; + unsigned int max_seg = blkif->ops->max_seg; spin_lock_irqsave(&blkbk->pending_free_lock, flags); if (!list_empty(&blkbk->pending_free)) { @@ -315,8 +319,10 @@ static void xen_blkbk_unmap(struct pending_req *req) for (i = 0; i < req->nr_pages; i++) { handle = pending_handle(req, i); - if (handle == BLKBACK_INVALID_HANDLE) + if (handle == BLKBACK_INVALID_HANDLE) { + printk("BLKBACK_INVALID_HANDLE\n"); continue; + } gnttab_set_unmap_op(&unmap[invcount], vaddr(req, i), GNTMAP_host_map, handle); pending_handle(req, i) = BLKBACK_INVALID_HANDLE; @@ -486,6 +492,12 @@ void *get_back_ring(struct xen_blkif *blkif) return (void *)&blkif->blk_rings; } +void *get_back_ring_v2(struct xen_blkif *blkif) +{ + return (void *)&blkif->blk_rings_v2; +} + + void copy_blkif_req(struct xen_blkif *blkif, RING_IDX rc) { struct blkif_request *req = (struct blkif_request *)blkif->req; @@ -506,12 +518,48 @@ void copy_blkif_req(struct xen_blkif *blkif, RING_IDX rc) } } +void copy_blkif_req_v2(struct xen_blkif *blkif, RING_IDX rc) +{ + struct blkif_request_header *req = (struct blkif_request_header *)blkif->req; + union blkif_back_rings_v2 *blk_rings = &blkif->blk_rings_v2; + switch (blkif->blk_protocol) { + case BLKIF_PROTOCOL_NATIVE: + memcpy(req, RING_GET_REQUEST(&blk_rings->native, rc), + sizeof(struct blkif_request_header)); + break; + case BLKIF_PROTOCOL_X86_32: + blkif_get_x86_32_req_v2(req, RING_GET_REQUEST(&blk_rings->x86_32, rc)); + break; + case BLKIF_PROTOCOL_X86_64: + blkif_get_x86_64_req_v2(req, RING_GET_REQUEST(&blk_rings->x86_64, rc)); + break; + default: + BUG(); + } +} + void copy_blkif_seg_req(struct xen_blkif *blkif) { struct blkif_request *req = (struct blkif_request *)blkif->req; blkif->seg_req = req->u.rw.seg; } + +void copy_blkif_seg_req_v2(struct xen_blkif *blkif) +{ + struct blkif_request_header *req = (struct blkif_request_header *)blkif->req; + struct blkif_segment_back_ring *blk_segrings = &blkif->blk_segrings; + int i; + RING_IDX rc; + + rc = blk_segrings->req_cons; + for (i = 0; i < req->u.rw.nr_segments; i++) { + memcpy(&blkif->seg_req[i], RING_GET_REQUEST(blk_segrings, rc++), + sizeof(struct blkif_request_segment)); + } + blk_segrings->req_cons = rc; +} + /* * Function to copy the from the ring buffer the 'struct blkif_request' * (which has the sectors we want, number of them, grant references, etc), @@ -587,10 +635,12 @@ do_block_io_op(struct xen_blkif *blkif) return more_to_do; } + /* * Transmutation of the 'struct blkif_request' to a proper 'struct bio' * and call the 'submit_bio' to pass it to the underlying storage. */ + static int dispatch_rw_block_io(struct xen_blkif *blkif, struct pending_req *pending_req) { @@ -774,54 +824,89 @@ static int dispatch_rw_block_io(struct xen_blkif *blkif, return -EIO; } -struct blkif_segment_back_ring * - get_seg_back_ring(struct xen_blkif *blkif) +void push_back_ring_rsp(struct xen_blkif *blkif, int nr_page, int *notify) { - return NULL; + union blkif_back_rings *blk_rings = &blkif->blk_rings; + + blk_rings->common.rsp_prod_pvt++; + RING_PUSH_RESPONSES_AND_CHECK_NOTIFY(&blk_rings->common, *notify); } -void push_back_ring_rsp(union blkif_back_rings *blk_rings, int nr_page, int *notify) +void push_back_ring_rsp_v2(struct xen_blkif *blkif, int nr_page, int *notify) { + union blkif_back_rings_v2 *blk_rings = &blkif->blk_rings_v2; + struct blkif_segment_back_ring *blk_segrings = &blkif->blk_segrings; + blk_rings->common.rsp_prod_pvt++; + blk_segrings->rsp_prod_pvt += nr_page; + RING_PUSH_RESPONSES(blk_segrings); RING_PUSH_RESPONSES_AND_CHECK_NOTIFY(&blk_rings->common, *notify); } -/* - * Put a response on the ring on how the operation fared. - */ -static void make_response(struct xen_blkif *blkif, u64 id, - unsigned short op, int nr_page, int st) +void copy_response(struct xen_blkif *blkif, struct blkif_response *resp) { - struct blkif_response resp; - unsigned long flags; - union blkif_back_rings *blk_rings = - (union blkif_back_rings *)blkif->ops->get_back_ring(blkif); - int notify; + union blkif_back_rings *blk_rings = &blkif->blk_rings; + + switch (blkif->blk_protocol) { + case BLKIF_PROTOCOL_NATIVE: + memcpy(RING_GET_RESPONSE(&blk_rings->native, blk_rings->native.rsp_prod_pvt), + resp, sizeof(*resp)); + break; + case BLKIF_PROTOCOL_X86_32: + memcpy(RING_GET_RESPONSE(&blk_rings->x86_32, blk_rings->x86_32.rsp_prod_pvt), + resp, sizeof(*resp)); + break; + case BLKIF_PROTOCOL_X86_64: + memcpy(RING_GET_RESPONSE(&blk_rings->x86_64, blk_rings->x86_64.rsp_prod_pvt), + resp, sizeof(*resp)); + break; + default: + BUG(); + } - resp.id = id; - resp.operation = op; - resp.status = st; +} - spin_lock_irqsave(&blkif->blk_ring_lock, flags); - /* Place on the response ring for the relevant domain. */ +void copy_response_v2(struct xen_blkif *blkif, struct blkif_response *resp) +{ + union blkif_back_rings_v2 *blk_rings = &blkif->blk_rings_v2; + switch (blkif->blk_protocol) { case BLKIF_PROTOCOL_NATIVE: memcpy(RING_GET_RESPONSE(&blk_rings->native, blk_rings->native.rsp_prod_pvt), - &resp, sizeof(resp)); + resp, sizeof(*resp)); break; case BLKIF_PROTOCOL_X86_32: memcpy(RING_GET_RESPONSE(&blk_rings->x86_32, blk_rings->x86_32.rsp_prod_pvt), - &resp, sizeof(resp)); + resp, sizeof(*resp)); break; case BLKIF_PROTOCOL_X86_64: memcpy(RING_GET_RESPONSE(&blk_rings->x86_64, blk_rings->x86_64.rsp_prod_pvt), - &resp, sizeof(resp)); + resp, sizeof(*resp)); break; default: BUG(); } +} - blkif->ops->push_back_ring_rsp(blk_rings, nr_page, ¬ify); +/* + * Put a response on the ring on how the operation fared. + */ +static void make_response(struct xen_blkif *blkif, u64 id, + unsigned short op, int nr_page, int st) +{ + struct blkif_response resp; + unsigned long flags; + int notify; + + resp.id = id; + resp.operation = op; + resp.status = st; + + spin_lock_irqsave(&blkif->blk_ring_lock, flags); + /* Place on the response ring for the relevant domain. */ + blkif->ops->copy_response(blkif, &resp); + + blkif->ops->push_back_ring_rsp(blkif, nr_page, ¬ify); spin_unlock_irqrestore(&blkif->blk_ring_lock, flags); if (notify) @@ -895,9 +980,19 @@ struct blkback_ring_operation blkback_ring_ops = { .copy_blkif_req = copy_blkif_req, .copy_blkif_seg_req = copy_blkif_seg_req, .push_back_ring_rsp = push_back_ring_rsp, + .copy_response = copy_response, .max_seg = BLKIF_MAX_SEGMENTS_PER_REQUEST, }; +struct blkback_ring_operation blkback_ring_ops_v2 = { + .get_back_ring = get_back_ring_v2, + .copy_blkif_req = copy_blkif_req_v2, + .copy_blkif_seg_req = copy_blkif_seg_req_v2, + .push_back_ring_rsp = push_back_ring_rsp_v2, + .copy_response = copy_response_v2, + .max_seg = BLKIF_MAX_SEGMENTS_PER_REQUEST_V2, +}; + static int __init xen_blkif_init(void) { int rc = 0; diff --git a/drivers/block/xen-blkback/common.h b/drivers/block/xen-blkback/common.h index 80e8acc..2e241a4 100644 --- a/drivers/block/xen-blkback/common.h +++ b/drivers/block/xen-blkback/common.h @@ -48,6 +48,7 @@ pr_debug(DRV_PFX "(%s:%d) " fmt ".\n", \ __func__, __LINE__, ##args) +extern int blkback_ring_type; /* Not a real protocol. Used to generate ring structs which contain * the elements common to all protocols only. This way we get a @@ -84,6 +85,22 @@ struct blkif_x86_32_request { } u; } __attribute__((__packed__)); +struct blkif_x86_32_request_rw_v2 { + uint8_t nr_segments; /* number of segments */ + blkif_vdev_t handle; /* only for read/write requests */ + uint64_t id; /* private guest value, echoed in resp */ + blkif_sector_t sector_number;/* start sector idx on disk (r/w only) */ + uint64_t seg_id;/* segment offset in the segment ring */ +} __attribute__((__packed__)); + +struct blkif_x86_32_request_v2 { + uint8_t operation; /* BLKIF_OP_??? */ + union { + struct blkif_x86_32_request_rw_v2 rw; + struct blkif_x86_32_request_discard discard; + } u; +} __attribute__((__packed__)); + /* i386 protocol version */ #pragma pack(push, 4) struct blkif_x86_32_response { @@ -120,6 +137,23 @@ struct blkif_x86_64_request { } u; } __attribute__((__packed__)); +struct blkif_x86_64_request_rw_v2 { + uint8_t nr_segments; /* number of segments */ + blkif_vdev_t handle; /* only for read/write requests */ + uint32_t _pad1; /* offsetof(blkif_reqest..,u.rw.id)==8 */ + uint64_t id; + blkif_sector_t sector_number;/* start sector idx on disk (r/w only) */ + uint64_t seg_id;/* segment offset in the segment ring */ +} __attribute__((__packed__)); + +struct blkif_x86_64_request_v2 { + uint8_t operation; /* BLKIF_OP_??? */ + union { + struct blkif_x86_64_request_rw_v2 rw; + struct blkif_x86_64_request_discard discard; + } u; +} __attribute__((__packed__)); + struct blkif_x86_64_response { uint64_t __attribute__((__aligned__(8))) id; uint8_t operation; /* copied from request */ @@ -132,6 +166,10 @@ DEFINE_RING_TYPES(blkif_x86_32, struct blkif_x86_32_request, struct blkif_x86_32_response); DEFINE_RING_TYPES(blkif_x86_64, struct blkif_x86_64_request, struct blkif_x86_64_response); +DEFINE_RING_TYPES(blkif_x86_32_v2, struct blkif_x86_32_request_v2, + struct blkif_x86_32_response); +DEFINE_RING_TYPES(blkif_x86_64_v2, struct blkif_x86_64_request_v2, + struct blkif_x86_64_response); union blkif_back_rings { struct blkif_back_ring native; @@ -140,6 +178,13 @@ union blkif_back_rings { struct blkif_x86_64_back_ring x86_64; }; +union blkif_back_rings_v2 { + struct blkif_request_back_ring native; + struct blkif_common_back_ring common; + struct blkif_x86_32_v2_back_ring x86_32; + struct blkif_x86_64_v2_back_ring x86_64; +}; + enum blkif_protocol { BLKIF_PROTOCOL_NATIVE = 1, BLKIF_PROTOCOL_X86_32 = 2, @@ -175,7 +220,8 @@ struct blkback_ring_operation { void *(*get_back_ring) (struct xen_blkif *blkif); void (*copy_blkif_req) (struct xen_blkif *blkif, RING_IDX rc); void (*copy_blkif_seg_req) (struct xen_blkif *blkif); - void (*push_back_ring_rsp) (union blkif_back_rings *blk_rings, int nr_page, int *notify); + void (*push_back_ring_rsp) (struct xen_blkif *blkif, int nr_page, int *notify); + void (*copy_response) (struct xen_blkif *blkif, struct blkif_response *resp); unsigned int max_seg; }; @@ -190,7 +236,10 @@ struct xen_blkif { enum blkif_protocol blk_protocol; enum blkif_backring_type blk_backring_type; union blkif_back_rings blk_rings; + union blkif_back_rings_v2 blk_rings_v2; + struct blkif_segment_back_ring blk_segrings; void *blk_ring; + void *blk_segring; struct xen_blkbk *blkbk; /* The VBD attached to this interface. */ struct xen_vbd vbd; @@ -328,6 +377,31 @@ static inline void blkif_get_x86_32_req(struct blkif_request *dst, } } +static inline void blkif_get_x86_32_req_v2(struct blkif_request_header *dst, + struct blkif_x86_32_request_v2 *src) +{ + dst->operation = src->operation; + switch (src->operation) { + case BLKIF_OP_READ: + case BLKIF_OP_WRITE: + case BLKIF_OP_WRITE_BARRIER: + case BLKIF_OP_FLUSH_DISKCACHE: + dst->u.rw.nr_segments = src->u.rw.nr_segments; + dst->u.rw.handle = src->u.rw.handle; + dst->u.rw.id = src->u.rw.id; + dst->u.rw.sector_number = src->u.rw.sector_number; + dst->u.rw.seg_id = src->u.rw.seg_id; + barrier(); + break; + case BLKIF_OP_DISCARD: + dst->u.discard.flag = src->u.discard.flag; + dst->u.discard.sector_number = src->u.discard.sector_number; + dst->u.discard.nr_sectors = src->u.discard.nr_sectors; + break; + default: + break; + } +} static inline void blkif_get_x86_64_req(struct blkif_request *dst, struct blkif_x86_64_request *src) { @@ -359,4 +433,30 @@ static inline void blkif_get_x86_64_req(struct blkif_request *dst, } } +static inline void blkif_get_x86_64_req_v2(struct blkif_request_header *dst, + struct blkif_x86_64_request_v2 *src) +{ + dst->operation = src->operation; + switch (src->operation) { + case BLKIF_OP_READ: + case BLKIF_OP_WRITE: + case BLKIF_OP_WRITE_BARRIER: + case BLKIF_OP_FLUSH_DISKCACHE: + dst->u.rw.nr_segments = src->u.rw.nr_segments; + dst->u.rw.handle = src->u.rw.handle; + dst->u.rw.id = src->u.rw.id; + dst->u.rw.sector_number = src->u.rw.sector_number; + dst->u.rw.seg_id = src->u.rw.seg_id; + barrier(); + break; + case BLKIF_OP_DISCARD: + dst->u.discard.flag = src->u.discard.flag; + dst->u.discard.sector_number = src->u.discard.sector_number; + dst->u.discard.nr_sectors = src->u.discard.nr_sectors; + break; + default: + break; + } +} + #endif /* __XEN_BLKIF__BACKEND__COMMON_H__ */ diff --git a/drivers/block/xen-blkback/xenbus.c b/drivers/block/xen-blkback/xenbus.c index 8b0d496..4678533 100644 --- a/drivers/block/xen-blkback/xenbus.c +++ b/drivers/block/xen-blkback/xenbus.c @@ -36,7 +36,7 @@ static int connect_ring(struct backend_info *); static void backend_changed(struct xenbus_watch *, const char **, unsigned int); -extern struct blkback_ring_operation blkback_ring_ops; +extern struct blkback_ring_operation blkback_ring_ops, blkback_ring_ops_v2; struct xenbus_device *xen_blkbk_xenbus(struct backend_info *be) { @@ -176,6 +176,83 @@ static int xen_blkif_map(struct xen_blkif *blkif, unsigned long shared_page, return 0; } +static int +xen_blkif_map_segring(struct xen_blkif *blkif, unsigned long shared_page) +{ + struct blkif_segment_sring *sring; + int err; + + err = xenbus_map_ring_valloc(blkif->be->dev, shared_page, + &blkif->blk_segring); + + if (err < 0) + return err; + + sring = (struct blkif_segment_sring *)blkif->blk_segring; + BACK_RING_INIT(&blkif->blk_segrings, sring, PAGE_SIZE); + + return 0; +} + +static int xen_blkif_map_v2(struct xen_blkif *blkif, unsigned long shared_page, + unsigned int evtchn) +{ + int err; + + /* Already connected through? */ + if (blkif->irq) + return 0; + + err = xenbus_map_ring_valloc(blkif->be->dev, shared_page, + &blkif->blk_ring); + + if (err < 0) + return err; + + switch (blkif->blk_protocol) { + case BLKIF_PROTOCOL_NATIVE: + { + struct blkif_request_sring *sring; + sring = (struct blkif_request_sring *)blkif->blk_ring; + BACK_RING_INIT(&blkif->blk_rings_v2.native, sring, + PAGE_SIZE); + break; + } + case BLKIF_PROTOCOL_X86_32: + { + struct blkif_x86_32_v2_sring *sring_x86_32; + sring_x86_32 = (struct blkif_x86_32_v2_sring *)blkif->blk_ring; + BACK_RING_INIT(&blkif->blk_rings_v2.x86_32, sring_x86_32, + PAGE_SIZE); + break; + } + case BLKIF_PROTOCOL_X86_64: + { + struct blkif_x86_64_v2_sring *sring_x86_64; + sring_x86_64 = (struct blkif_x86_64_v2_sring *)blkif->blk_ring; + BACK_RING_INIT(&blkif->blk_rings_v2.x86_64, sring_x86_64, + PAGE_SIZE); + break; + } + default: + BUG(); + } + + + + err = bind_interdomain_evtchn_to_irqhandler(blkif->domid, evtchn, + xen_blkif_be_int, 0, + "blkif-backend", blkif); + if (err < 0) { + xenbus_unmap_ring_vfree(blkif->be->dev, blkif->blk_ring); + blkif->blk_rings_v2.common.sring = NULL; + return err; + } + blkif->irq = err; + + return 0; +} + static void xen_blkif_disconnect(struct xen_blkif *blkif) { if (blkif->xenblkd) { @@ -192,10 +269,18 @@ static void xen_blkif_disconnect(struct xen_blkif *blkif) blkif->irq = 0; } - if (blkif->blk_rings.common.sring) { + if (blkif->blk_backring_type == BACKRING_TYPE_1 && + blkif->blk_rings.common.sring) { xenbus_unmap_ring_vfree(blkif->be->dev, blkif->blk_ring); blkif->blk_rings.common.sring = NULL; } + if (blkif->blk_backring_type == BACKRING_TYPE_2 && + blkif->blk_rings_v2.common.sring) { + xenbus_unmap_ring_vfree(blkif->be->dev, blkif->blk_ring); + blkif->blk_rings_v2.common.sring = NULL; + xenbus_unmap_ring_vfree(blkif->be->dev, blkif->blk_segring); + blkif->blk_segrings.sring= NULL; + } } void xen_blkif_free(struct xen_blkif *blkif) @@ -476,6 +561,9 @@ static int xen_blkbk_probe(struct xenbus_device *dev, if (err) goto fail; + err = xenbus_printf(XBT_NIL, dev->nodename, "blkback-ring-type", + "%u", blkback_ring_type); + err = xenbus_switch_state(dev, XenbusStateInitWait); if (err) goto fail; @@ -722,25 +810,68 @@ static int connect_ring(struct backend_info *be) { struct xenbus_device *dev = be->dev; unsigned long ring_ref; + unsigned long segring_ref; unsigned int evtchn; + unsigned int ring_type; char protocol[64] = ""; int err; DPRINTK("%s", dev->otherend); - be->blkif->ops = &blkback_ring_ops; - be->blkif->req = kmalloc(sizeof(struct blkif_request), - GFP_KERNEL); - be->blkif->seg_req = kmalloc(sizeof(struct blkif_request_segment)* - be->blkif->ops->max_seg, GFP_KERNEL); - be->blkif->blk_backring_type = BACKRING_TYPE_1; - - err = xenbus_gather(XBT_NIL, dev->otherend, "ring-ref", "%lu", - &ring_ref, "event-channel", "%u", &evtchn, NULL); - if (err) { + + err = xenbus_scanf(XBT_NIL, dev->otherend, "blkfront-ring-type", "%u", + &ring_type); + if (err != 1) { + pr_info(DRV_PFX "using legacy blk ring\n"); + ring_type = 1; + } + + if (ring_type == 1) { + be->blkif->ops = &blkback_ring_ops; + be->blkif->blk_backring_type = BACKRING_TYPE_1; + be->blkif->req = kmalloc(sizeof(struct blkif_request), GFP_KERNEL); + be->blkif->seg_req = kmalloc(sizeof(struct blkif_request_segment)* + be->blkif->ops->max_seg, GFP_KERNEL); + if (!be->blkif->req || !be->blkif->seg_req) { + kfree(be->blkif->req); + kfree(be->blkif->seg_req); + xenbus_dev_fatal(dev, err, "no enough memory"); + return -ENOMEM; + } + err = xenbus_gather(XBT_NIL, dev->otherend, "ring-ref", "%lu", + &ring_ref, "event-channel", "%u", &evtchn, NULL); + if (err) { + xenbus_dev_fatal(dev, err, + "reading %s/ring-ref and event-channel", + dev->otherend); + return err; + } + } + else if (ring_type == 2){ + be->blkif->ops = &blkback_ring_ops_v2; + be->blkif->blk_backring_type = BACKRING_TYPE_2; + be->blkif->req = kmalloc(sizeof(struct blkif_request_header), GFP_KERNEL); + be->blkif->seg_req = kmalloc(sizeof(struct blkif_request_segment)* + be->blkif->ops->max_seg, GFP_KERNEL); + if (!be->blkif->req || !be->blkif->seg_req) { + kfree(be->blkif->req); + kfree(be->blkif->seg_req); + xenbus_dev_fatal(dev, err, "no enough memory"); + return -ENOMEM; + } + err = xenbus_gather(XBT_NIL, dev->otherend, "reqring-ref", "%lu", + &ring_ref, "event-channel", "%u", &evtchn, + "segring-ref", "%lu", &segring_ref, NULL); + if (err) { + xenbus_dev_fatal(dev, err, + "reading %s/ring/segring-ref and event-channel", + dev->otherend); + return err; + } + } + else { xenbus_dev_fatal(dev, err, - "reading %s/ring-ref and event-channel", - dev->otherend); - return err; + "unsupport %s blkfront ring", dev->otherend); + return -EINVAL; } be->blkif->blk_protocol = BLKIF_PROTOCOL_NATIVE; @@ -758,19 +889,51 @@ static int connect_ring(struct backend_info *be) xenbus_dev_fatal(dev, err, "unknown fe protocol %s", protocol); return -1; } - pr_info(DRV_PFX "ring-ref %ld, event-channel %d, protocol %d (%s)\n", - ring_ref, evtchn, be->blkif->blk_protocol, protocol); - /* Map the shared frame, irq etc. */ - err = xen_blkif_map(be->blkif, ring_ref, evtchn); - if (err) { - xenbus_dev_fatal(dev, err, "mapping ring-ref %lu port %u", - ring_ref, evtchn); - return err; + if (ring_type == 2) { + err = xen_blkif_map_segring(be->blkif, segring_ref); + if (err) { + xenbus_dev_fatal(dev, err, "mapping segment rinfs"); + return err; + } + err = xen_blkif_map_v2(be->blkif, ring_ref, evtchn); + if (err) { + xenbus_unmap_ring_vfree(be->blkif->be->dev, + be->blkif->blk_segring); + be->blkif->blk_segrings.sring = NULL; + xenbus_dev_fatal(dev, err, "mapping request rinfs"); + return err; + } + pr_info(DRV_PFX + "ring-ref %ld,segring-ref %ld,event-channel %d,protocol %d (%s)\n", + ring_ref, segring_ref, evtchn, be->blkif->blk_protocol, protocol); + } + else { + err = xen_blkif_map(be->blkif, ring_ref, evtchn); + if (err) { + xenbus_dev_fatal(dev, err, "mapping ring-ref %lu port %u", + ring_ref, evtchn); + return err; + } + pr_info(DRV_PFX "ring-ref %ld,event-channel %d,protocol %d (%s)\n", + ring_ref, evtchn, be->blkif->blk_protocol, protocol); } err = xen_blkif_init_blkbk(be->blkif); if (err) { + if (ring_type == 2) { + xenbus_unmap_ring_vfree(be->blkif->be->dev, + be->blkif->blk_segring); + be->blkif->blk_segrings.sring = NULL; + xenbus_unmap_ring_vfree(be->blkif->be->dev, + be->blkif->blk_ring); + be->blkif->blk_rings_v2.common.sring = NULL; + } + else { + xenbus_unmap_ring_vfree(be->blkif->be->dev, + be->blkif->blk_ring); + be->blkif->blk_rings.common.sring = NULL; + } xenbus_dev_fatal(dev, err, "xen blkif init blkbk fails\n"); return err; } -ronghui Attachment:
vbd_enlarge_segments_05.patch _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |