diff --git a/src/bio_helper.c b/src/bio_helper.c index 56ac483a..995d3271 100644 --- a/src/bio_helper.c +++ b/src/bio_helper.c @@ -44,11 +44,10 @@ struct request_queue *dattobd_bio_get_queue(struct bio *bio) */ void dattobd_bio_set_dev(struct bio *bio, struct block_device *bdev) { -#ifdef HAVE_BIO_BI_BDEV - //#if LINUX_VERSION_CODE < KERNEL_VERSION(4,14,0) - bio->bi_bdev = bdev; -#else +#ifdef HAVE_BIO_SET_DEV bio_set_dev(bio, bdev); +#else + bio->bi_bdev = bdev; #endif } diff --git a/src/configure-tests/feature-tests/bio_set_dev.c b/src/configure-tests/feature-tests/bio_set_dev.c new file mode 100644 index 00000000..b9e15b94 --- /dev/null +++ b/src/configure-tests/feature-tests/bio_set_dev.c @@ -0,0 +1,19 @@ +// SPDX-License-Identifier: GPL-2.0-only + +/* + * Feature test: detect presence of bio_set_dev(bio, bdev) + */ + +#include "includes.h" + +MODULE_LICENSE("GPL"); + +static inline void dummy(void) +{ + struct bio *b = NULL; + struct block_device *d = NULL; + /* compile-time presence check */ + bio_set_dev(b, d); +} + + diff --git a/src/cow_manager.c b/src/cow_manager.c index b5f79648..ac0d1bb9 100644 --- a/src/cow_manager.c +++ b/src/cow_manager.c @@ -505,8 +505,16 @@ int cow_sync_and_close(struct cow_manager *cm) if (ret) goto error; - ret = cow_get_file_extents(cm->dev, cm->dfilp->filp); - if(ret) goto error; + /* + * If the fs support fiemap, we need to get the extents of the file, + * otherwise it is ignored. + */ + if (cm->dfilp->filp->f_inode->i_op && cm->dfilp->filp->f_inode->i_op->fiemap) { + ret = cow_get_file_extents(cm->dev, cm->dfilp->filp); + if(ret) goto error; + } else { + LOG_WARN("fiemap not supported, ignoring extents processing."); + } if (cm->dfilp){ __close_and_destroy_dattobd_mutable_file(cm->dfilp); @@ -605,6 +613,7 @@ int cow_reload(const char *path, uint64_t elements, unsigned long sect_size, int ret; unsigned long i; struct cow_manager *cm; + struct snap_device *dev; LOG_DEBUG("allocating cow manager"); cm = kzalloc(sizeof(struct cow_manager), GFP_KERNEL); @@ -654,25 +663,31 @@ int cow_reload(const char *path, uint64_t elements, unsigned long sect_size, cm->sects[i].has_data = 1; } + /* Get the dev of the cow manager and set the dev of the cow manager*/ + dev = container_of(cm_out, struct snap_device, sd_cow); + LOG_DEBUG("cow_reload, setting dev of cow manager, cm: %p, dev: %p", cm, dev); + cm->dev = dev; + *cm_out = cm; return 0; error: LOG_ERROR(ret, "error during cow manager initialization"); - if (cm->dfilp){ - __close_and_destroy_dattobd_mutable_file(cm->dfilp); - cm->dfilp = NULL; - } - if (cm->sects) { - if (cm->flags & (1 << COW_VMALLOC_UPPER)) - vfree(cm->sects); - else - kfree(cm->sects); - } + if (cm) { + if (cm->dfilp){ + __close_and_destroy_dattobd_mutable_file(cm->dfilp); + cm->dfilp = NULL; + } - if (cm) + if (cm->sects) { + if (cm->flags & (1 << COW_VMALLOC_UPPER)) + vfree(cm->sects); + else + kfree(cm->sects); + } kfree(cm); + } *cm_out = NULL; return ret; @@ -775,21 +790,23 @@ int cow_init(struct snap_device *dev, const char *path, uint64_t elements, unsig error: LOG_ERROR(ret, "error during cow manager initialization"); - if (cm->dfilp){ - file_unlink(cm->dfilp); - __close_and_destroy_dattobd_mutable_file(cm->dfilp); - cm->dfilp = NULL; - } - if (cm->sects) { - if (cm->flags & (1 << COW_VMALLOC_UPPER)) - vfree(cm->sects); - else - kfree(cm->sects); - } + if (cm) { + if (cm->dfilp){ + file_unlink(cm->dfilp); + __close_and_destroy_dattobd_mutable_file(cm->dfilp); + cm->dfilp = NULL; + } + + if (cm->sects) { + if (cm->flags & (1 << COW_VMALLOC_UPPER)) + vfree(cm->sects); + else + kfree(cm->sects); + } - if (cm) kfree(cm); + } *cm_out = NULL; return ret; diff --git a/src/ioctl_handlers.c b/src/ioctl_handlers.c index 7763f2f1..7597ad8f 100644 --- a/src/ioctl_handlers.c +++ b/src/ioctl_handlers.c @@ -453,6 +453,7 @@ static int ioctl_expand_cow_file(uint64_t size, unsigned int minor) if(ret) goto error; + put_snap_device_array(snap_devices); return 0; error: diff --git a/src/proc_seq_file.c b/src/proc_seq_file.c index cc9a2484..7faeb7a9 100644 --- a/src/proc_seq_file.c +++ b/src/proc_seq_file.c @@ -245,8 +245,13 @@ static int dattobd_proc_show(struct seq_file *m, void *v) static int dattobd_proc_open(struct inode *inode, struct file *filp) { - mutex_lock(&ioctl_mutex); - return seq_open(filp, &dattobd_seq_proc_ops); + int ret; + mutex_lock(&ioctl_mutex); + ret = seq_open(filp, &dattobd_seq_proc_ops); + if (ret) { + mutex_unlock(&ioctl_mutex); + } + return ret; } static int dattobd_proc_release(struct inode *inode, struct file *file)