static void vhd_index_complete_meta_read(void *arg, struct tiocb *tiocb, int err) { int i; uint32_t blk; td_request_t treq; vhd_index_t *index; vhd_index_block_t *block; vhd_index_request_t *req, *r, *tmp; req = (vhd_index_request_t *)arg; index = req->index; blk = req->treq.sec / index->vhdi.spb; block = vhd_index_get_block(index, blk); ASSERT(block && td_flag_test(block->state, VHD_INDEX_BLOCK_READ_PENDING)); td_flag_clear(block->state, VHD_INDEX_BLOCK_READ_PENDING); if (err) { memset(block->vhdi_block.table, 0, block->table_size); vhd_index_block_for_each_request(block, r, tmp) vhd_index_signal_completion(index, r, err); return; } for (i = 0; i < block->vhdi_block.entries; i++) vhdi_entry_in(block->vhdi_block.table + i); td_flag_set(block->state, VHD_INDEX_BLOCK_VALID); vhd_index_block_for_each_request(block, r, tmp) { treq = r->treq; vhd_index_free_request(index, r); vhd_index_queue_read(index->driver, treq); }
int td_close(td_image_t *image) { td_driver_t *driver; driver = image->driver; if (!driver) return -ENODEV; driver->refcnt--; if (!driver->refcnt && td_flag_test(driver->state, TD_DRIVER_OPEN)) { driver->ops->td_close(driver); td_flag_clear(driver->state, TD_DRIVER_OPEN); } DPRINTF("closed image %s (%d users, state: 0x%08x, type: %d)\n", driver->name, driver->refcnt, driver->state, driver->type); return 0; }
int tapdisk_vbd_open_vdi(td_vbd_t *vbd, const char *name, td_flag_t flags, int prt_devnum) { char *tmp = vbd->name; int err; if (!list_empty(&vbd->images)) { err = -EBUSY; goto fail; } if (!name && !vbd->name) { err = -EINVAL; goto fail; } if (name) { vbd->name = strdup(name); if (!vbd->name) { err = -errno; goto fail; } } err = tapdisk_image_open_chain(vbd->name, flags, prt_devnum, &vbd->images); if (err) goto fail; td_flag_clear(vbd->state, TD_VBD_CLOSED); vbd->flags = flags; if (td_flag_test(vbd->flags, TD_OPEN_LOG_DIRTY)) { err = tapdisk_vbd_add_dirty_log(vbd); if (err) goto fail; } if (td_flag_test(vbd->flags, TD_OPEN_ADD_CACHE)) { err = tapdisk_vbd_add_block_cache(vbd); if (err) goto fail; } if (td_flag_test(vbd->flags, TD_OPEN_LOCAL_CACHE)) { err = tapdisk_vbd_add_local_cache(vbd); if (err) goto fail; } err = tapdisk_vbd_validate_chain(vbd); if (err) goto fail; if (td_flag_test(vbd->flags, TD_OPEN_SECONDARY)) { err = tapdisk_vbd_add_secondary(vbd); if (err) { if (vbd->nbd_mirror_failed != 1) goto fail; INFO("Ignoring failed NBD secondary attach\n"); err = 0; } } if (tmp != vbd->name) free(tmp); return err; fail: if (vbd->name != tmp) { free(vbd->name); vbd->name = tmp; } if (!list_empty(&vbd->images)) tapdisk_image_close_chain(&vbd->images); vbd->flags = 0; return err; }