From 8f1c7c1e44a4cc8870eb2b2a71da323e265881b4 Mon Sep 17 00:00:00 2001 From: Jinshan Xiong Date: Sat, 20 Jan 2018 19:45:50 +0000 Subject: [PATCH] LU-10418 flr: revise lease API Introduce two lease API llapi_lease_{acquire,release}() to replace confusing llapi_lease_{get,put}(). Rename llapi_lease_ext_get() to llapi_lease_set(). Implement new mirror_extend_layout() to separate lfs_migrate(). Signed-off-by: Jinshan Xiong Change-Id: I88ab1f7f27aa81c44418aecf31c9e89e494fc01e Reviewed-on: https://review.whamcloud.com/30363 Tested-by: Jenkins Reviewed-by: Bobi Jam Tested-by: Maloo Reviewed-by: Andreas Dilger --- lustre/include/lustre/lustreapi.h | 8 +- lustre/include/uapi/linux/lustre/lustre_user.h | 3 +- lustre/llite/file.c | 67 ++++++++++----- lustre/tests/mirror_io.c | 8 +- lustre/tests/multiop.c | 6 +- lustre/tests/swap_lock_test.c | 64 +++++++-------- lustre/utils/lfs.c | 108 ++++++++++++++++++++----- lustre/utils/liblustreapi_lease.c | 98 +++++++++++++++------- 8 files changed, 248 insertions(+), 114 deletions(-) diff --git a/lustre/include/lustre/lustreapi.h b/lustre/include/lustre/lustreapi.h index a434d10..0a8d1c0 100644 --- a/lustre/include/lustre/lustreapi.h +++ b/lustre/include/lustre/lustreapi.h @@ -461,10 +461,12 @@ int llapi_json_add_item(struct llapi_json_item_list **item_list, char *key, int llapi_json_write_list(struct llapi_json_item_list **item_list, FILE *fp); /* File lease */ -int llapi_lease_get(int fd, int mode); +int llapi_lease_acquire(int fd, enum ll_lease_mode mode); +int llapi_lease_release(int fd); +int llapi_lease_set(int fd, const struct ll_ioc_lease *data); int llapi_lease_check(int fd); -int llapi_lease_put(int fd); -extern int llapi_lease_get_ext(int fd, struct ll_ioc_lease *data); +int llapi_lease_get(int fd, int mode); /* obsoleted */ +int llapi_lease_put(int fd); /* obsoleted */ /* Group lock */ int llapi_group_lock(int fd, int gid); diff --git a/lustre/include/uapi/linux/lustre/lustre_user.h b/lustre/include/uapi/linux/lustre/lustre_user.h index 4e70006..09c139e 100644 --- a/lustre/include/uapi/linux/lustre/lustre_user.h +++ b/lustre/include/uapi/linux/lustre/lustre_user.h @@ -334,6 +334,7 @@ enum ll_lease_mode { enum ll_lease_flags { LL_LEASE_RESYNC = 0x1, LL_LEASE_RESYNC_DONE = 0x2, + LL_LEASE_LAYOUT_MERGE = 0x4, }; #define IOC_IDS_MAX 4096 @@ -941,8 +942,6 @@ struct if_quotactl { #define SWAP_LAYOUTS_KEEP_MTIME (1 << 2) #define SWAP_LAYOUTS_KEEP_ATIME (1 << 3) #define SWAP_LAYOUTS_CLOSE (1 << 4) -#define MERGE_LAYOUTS_CLOSE (1 << 5) -#define INTENT_LAYOUTS_CLOSE (SWAP_LAYOUTS_CLOSE | MERGE_LAYOUTS_CLOSE) /* Swap XATTR_NAME_HSM as well, only on the MDT so far */ #define SWAP_LAYOUTS_MDS_HSM (1 << 31) diff --git a/lustre/llite/file.c b/lustre/llite/file.c index 4c398be..626615f 100644 --- a/lustre/llite/file.c +++ b/lustre/llite/file.c @@ -933,12 +933,10 @@ static int ll_check_swap_layouts_validity(struct inode *inode1, } static int ll_swap_layouts_close(struct obd_client_handle *och, - struct inode *inode, struct inode *inode2, - int intent) + struct inode *inode, struct inode *inode2) { const struct lu_fid *fid1 = ll_inode2fid(inode); const struct lu_fid *fid2; - enum mds_op_bias bias; int rc; ENTRY; @@ -956,21 +954,11 @@ static int ll_swap_layouts_close(struct obd_client_handle *och, if (rc == 0) GOTO(out_free_och, rc = -EINVAL); - switch (intent) { - case SWAP_LAYOUTS_CLOSE: - bias = MDS_CLOSE_LAYOUT_SWAP; - break; - case MERGE_LAYOUTS_CLOSE: - bias = MDS_CLOSE_LAYOUT_MERGE; - break; - default: - GOTO(out_free_och, rc = -EOPNOTSUPP); - } - /* Close the file and {swap,merge} layouts between inode & inode2. * NB: lease lock handle is released in mdc_close_layout_swap_pack() * because we still need it to pack l_remote_handle to MDT. */ - rc = ll_close_inode_openhandle(inode, och, bias, inode2); + rc = ll_close_inode_openhandle(inode, och, MDS_CLOSE_LAYOUT_SWAP, + inode2); och = NULL; /* freed in ll_close_inode_openhandle() */ @@ -2900,6 +2888,7 @@ static long ll_file_unlock_lease(struct file *file, struct ll_ioc_lease *ioc, bool lease_broken; fmode_t fmode = 0; enum mds_op_bias bias = 0; + struct file *layout_file = NULL; void *data = NULL; size_t data_size = 0; long rc; @@ -2917,7 +2906,8 @@ static long ll_file_unlock_lease(struct file *file, struct ll_ioc_lease *ioc, fmode = och->och_flags; - if (ioc->lil_flags & LL_LEASE_RESYNC_DONE) { + switch (ioc->lil_flags) { + case LL_LEASE_RESYNC_DONE: if (ioc->lil_count > IOC_IDS_MAX) GOTO(out, rc = -EINVAL); @@ -2930,6 +2920,32 @@ static long ll_file_unlock_lease(struct file *file, struct ll_ioc_lease *ioc, GOTO(out, rc = -EFAULT); bias = MDS_CLOSE_RESYNC_DONE; + break; + case LL_LEASE_LAYOUT_MERGE: { + int fd; + + if (ioc->lil_count != 1) + GOTO(out, rc = -EINVAL); + + arg += sizeof(*ioc); + if (copy_from_user(&fd, (void __user *)arg, sizeof(__u32))) + GOTO(out, rc = -EFAULT); + + layout_file = fget(fd); + if (!layout_file) + GOTO(out, rc = -EBADF); + + if ((file->f_flags & O_ACCMODE) == O_RDONLY || + (layout_file->f_flags & O_ACCMODE) == O_RDONLY) + GOTO(out, rc = -EPERM); + + data = file_inode(layout_file); + bias = MDS_CLOSE_LAYOUT_MERGE; + break; + } + default: + /* without close intent */ + break; } rc = ll_lease_close_intent(och, inode, &lease_broken, bias, data); @@ -2945,8 +2961,17 @@ static long ll_file_unlock_lease(struct file *file, struct ll_ioc_lease *ioc, EXIT; out: - if (data) - OBD_FREE(data, data_size); + switch (ioc->lil_flags) { + case LL_LEASE_RESYNC_DONE: + if (data) + OBD_FREE(data, data_size); + break; + case LL_LEASE_LAYOUT_MERGE: + if (layout_file) + fput(layout_file); + break; + } + if (!rc) rc = ll_lease_type_from_fmode(fmode); RETURN(rc); @@ -3069,7 +3094,6 @@ ll_file_ioctl(struct file *file, unsigned int cmd, unsigned long arg) case LL_IOC_LOV_SWAP_LAYOUTS: { struct file *file2; struct lustre_swap_layouts lsl; - __u64 intent; if (copy_from_user(&lsl, (char __user *)arg, sizeof(struct lustre_swap_layouts))) @@ -3086,8 +3110,7 @@ ll_file_ioctl(struct file *file, unsigned int cmd, unsigned long arg) if ((file2->f_flags & O_ACCMODE) == O_RDONLY) GOTO(out, rc = -EPERM); - intent = lsl.sl_flags & INTENT_LAYOUTS_CLOSE; - if (intent) { + if (lsl.sl_flags & SWAP_LAYOUTS_CLOSE) { struct inode *inode2; struct ll_inode_info *lli; struct obd_client_handle *och = NULL; @@ -3102,7 +3125,7 @@ ll_file_ioctl(struct file *file, unsigned int cmd, unsigned long arg) if (och == NULL) GOTO(out, rc = -ENOLCK); inode2 = file_inode(file2); - rc = ll_swap_layouts_close(och, inode, inode2, intent); + rc = ll_swap_layouts_close(och, inode, inode2); } else { rc = ll_swap_layouts(file, file2, &lsl); } diff --git a/lustre/tests/mirror_io.c b/lustre/tests/mirror_io.c index bf48699..5deaeba 100644 --- a/lustre/tests/mirror_io.c +++ b/lustre/tests/mirror_io.c @@ -403,10 +403,10 @@ static void mirror_resync(int argc, char *argv[]) ioc->lil_mode = LL_LEASE_WRLCK; ioc->lil_flags = LL_LEASE_RESYNC; - rc = llapi_lease_get_ext(fd, ioc); + rc = llapi_lease_set(fd, ioc); if (rc < 0) free(ioc); - syserr(rc < 0, "llapi_lease_get_ext resync"); + syserr(rc < 0, "llapi_lease_set resync"); if (error_inject & AFTER_RESYNC_START) { free(ioc); @@ -506,8 +506,8 @@ static void mirror_resync(int argc, char *argv[]) if (error_inject & OPEN_TEST_FILE) /* break lease */ close(open(argv[optind], O_RDONLY)); - rc = llapi_lease_get_ext(fd, ioc); - syserr(rc <= 0, "llapi_lease_get_ext resync failed"); + rc = llapi_lease_set(fd, ioc); + syserr(rc <= 0, "llapi_lease_set resync failed"); free(ioc); close(fd); diff --git a/lustre/tests/multiop.c b/lustre/tests/multiop.c index 1a7d184..32dcb93 100644 --- a/lustre/tests/multiop.c +++ b/lustre/tests/multiop.c @@ -310,13 +310,13 @@ int main(int argc, char **argv) commands++; switch (*commands) { case 'U': - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); break; case 'R': - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); break; case 'W': - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); break; default: errx(-1, "unknown mode: %c", *commands); diff --git a/lustre/tests/swap_lock_test.c b/lustre/tests/swap_lock_test.c index 91dee2e..e79b4d8 100644 --- a/lustre/tests/swap_lock_test.c +++ b/lustre/tests/swap_lock_test.c @@ -298,7 +298,7 @@ static void test15(void) fd = create_file("foo1", 1000, 'x'); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); close(fd); @@ -307,7 +307,7 @@ static void test15(void) fd = open(filename, O_RDONLY); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); @@ -320,7 +320,7 @@ static void test15(void) fd = open(filename, O_WRONLY); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); @@ -333,7 +333,7 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); @@ -346,7 +346,7 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); @@ -359,7 +359,7 @@ static void test15(void) fd = open(filename, O_WRONLY); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == -EPERM, "cannot get lease '%s': %s", filename, strerror(-rc)); @@ -373,7 +373,7 @@ static void test15(void) fd = open(filename, O_RDONLY); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == -EPERM, "cannot get lease '%s': %s", filename, strerror(-rc)); @@ -387,10 +387,10 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == -EBUSY, "can get lease '%s': %s", filename, strerror(-rc)); @@ -404,10 +404,10 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == -EBUSY, "can get lease '%s': %s", filename, strerror(-rc)); @@ -421,14 +421,14 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); ASSERTF(rc == LL_LEASE_RDLCK, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); ASSERTF(rc == LL_LEASE_RDLCK, "was not able to put back lease '%s': %s", filename, strerror(-rc)); @@ -436,7 +436,7 @@ static void test15(void) ASSERTF(rc == 0, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); close(fd); @@ -445,14 +445,14 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); ASSERTF(rc == LL_LEASE_WRLCK, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); ASSERTF(rc == LL_LEASE_WRLCK, "was not able to put back lease '%s': %s", filename, strerror(-rc)); @@ -460,7 +460,7 @@ static void test15(void) ASSERTF(rc == 0, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); close(fd); @@ -470,20 +470,20 @@ static void test15(void) ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); for (i = 0; i < 1000; i++) { - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); ASSERTF(rc == LL_LEASE_WRLCK, "was not able to put back lease '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); ASSERTF(rc == LL_LEASE_RDLCK, "was not able to put back lease '%s': %s", filename, strerror(-rc)); @@ -495,14 +495,14 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); ASSERTF(rc == LL_LEASE_WRLCK, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); ASSERTF(rc == LL_LEASE_WRLCK, "was not able to put back lease '%s': %s", filename, strerror(-rc)); @@ -510,7 +510,7 @@ static void test15(void) ASSERTF(rc == 0, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); close(fd); @@ -519,14 +519,14 @@ static void test15(void) fd = open(filename, O_RDWR); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); rc = llapi_lease_check(fd); ASSERTF(rc == LL_LEASE_RDLCK, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_put(fd); + rc = llapi_lease_release(fd); ASSERTF(rc == LL_LEASE_RDLCK, "was not able to put back lease '%s': %s", filename, strerror(-rc)); @@ -534,7 +534,7 @@ static void test15(void) ASSERTF(rc == 0, "invalid lease type on '%s': %s", filename, strerror(-rc)); - rc = llapi_lease_get(fd, LL_LEASE_WRLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_WRLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); close(fd); @@ -568,7 +568,7 @@ static void test16(void) O_RDWR | O_NOATIME | O_NONBLOCK | O_NOFOLLOW); ASSERTF(fd >= 0, "open failed for '%s': %s", filename, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", filename, strerror(-rc)); close(fd); @@ -590,7 +590,7 @@ static void test17(void) fd = open(mainpath, O_DIRECTORY); ASSERTF(fd >= 0, "open failed for '%s': %s", mainpath, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == -ENOTTY, "can get lease on directory '%s': %s", mainpath, strerror(-rc)); @@ -600,7 +600,7 @@ static void test17(void) fd = open(fsmountdir, O_DIRECTORY); ASSERTF(fd >= 0, "open failed for '%s': %s", mainpath, strerror(errno)); - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); ASSERTF(rc == -ENOTTY, "can get lease on directory '%s': %s", mainpath, strerror(-rc)); @@ -785,7 +785,7 @@ static void test40(void) fd1 = create_file("foo1", foo1_size, 'x'); fd2 = create_file("foo2", foo2_size, 'y'); - rc = llapi_lease_get(fd1, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd1, LL_LEASE_RDLCK); ASSERTF(rc == 0, "cannot get lease '%s': %s", mainpath, strerror(-rc)); rc = llapi_lease_check(fd1); @@ -799,7 +799,7 @@ static void test40(void) rc = llapi_lease_check(fd1); ASSERTF(rc == 0, "lease not lost on '%s': %s", mainpath, strerror(-rc)); - rc = llapi_lease_put(fd1); + rc = llapi_lease_release(fd1); ASSERTF(rc == -ENOLCK, "was able to put back lease: %s", strerror(-rc)); diff --git a/lustre/utils/lfs.c b/lustre/utils/lfs.c index f1e22b8..a957a2a 100644 --- a/lustre/utils/lfs.c +++ b/lustre/utils/lfs.c @@ -1010,7 +1010,7 @@ static int lfs_migrate(char *name, __u64 migration_flags, goto out; } - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); if (rc < 0) { error_loc = "cannot get lease"; goto out; @@ -1018,16 +1018,14 @@ static int lfs_migrate(char *name, __u64 migration_flags, rc = migrate_nonblock(fd, fdv); if (rc < 0) { - llapi_lease_put(fd); + llapi_lease_release(fd); goto out; } /* Atomically put lease, swap layouts and close. * for a migration we need to check data version on file did * not change. */ - rc = llapi_fswap_layouts(fd, fdv, 0, 0, - migration_flags & MIGRATION_MIRROR ? - MERGE_LAYOUTS_CLOSE : SWAP_LAYOUTS_CLOSE); + rc = llapi_fswap_layouts(fd, fdv, 0, 0, SWAP_LAYOUTS_CLOSE); if (rc < 0) { error_loc = "cannot swap layout"; goto out; @@ -1401,6 +1399,7 @@ static int mirror_extend_file(const char *fname, const char *victim_file, int fdv = -1; struct stat stbuf; struct stat stbuf_v; + struct ll_ioc_lease *data = NULL; int rc; fd = open(fname, O_RDWR); @@ -1436,7 +1435,7 @@ static int mirror_extend_file(const char *fname, const char *victim_file, goto out; } - rc = llapi_lease_get(fd, LL_LEASE_RDLCK); + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); if (rc < 0) { error_loc = "cannot get lease"; goto out; @@ -1474,31 +1473,99 @@ static int mirror_extend_file(const char *fname, const char *victim_file, goto out; } - /* Atomically put lease, swap layouts and close. - * for a migration we need to check data version on file did - * not change. */ - rc = llapi_fswap_layouts(fd, fdv, 0, 0, MERGE_LAYOUTS_CLOSE); + /* Atomically put lease, merge layouts and close. */ + data = calloc(1, offsetof(typeof(*data), lil_ids[1])); + if (!data) { + error_loc = "memory allocation"; + goto out; + } + data->lil_mode = LL_LEASE_UNLCK; + data->lil_flags = LL_LEASE_LAYOUT_MERGE; + data->lil_count = 1; + data->lil_ids[0] = fdv; + rc = llapi_lease_set(fd, data); if (rc < 0) { - error_loc = "cannot swap layout"; + error_loc = "cannot merge layout"; + goto out; + } else if (rc == 0) { + rc = -EBUSY; + error_loc = "lost lease lock"; goto out; } + rc = 0; out: + if (data) + free(data); if (fd >= 0) close(fd); - if (fdv >= 0) close(fdv); - if (!rc) (void) unlink(victim_file); - if (rc < 0) fprintf(stderr, "error: %s: %s: %s: %s\n", progname, fname, error_loc, strerror(-rc)); return rc; } +static int mirror_extend_layout(char *name, struct llapi_layout *layout) +{ + struct ll_ioc_lease *data = NULL; + int fd = -1; + int fdv = -1; + int rc; + + rc = migrate_open_files(name, NULL, layout, &fd, &fdv); + if (rc < 0) + goto out; + + rc = llapi_lease_acquire(fd, LL_LEASE_RDLCK); + if (rc < 0) { + error_loc = "cannot get lease"; + goto out; + } + + rc = migrate_nonblock(fd, fdv); + if (rc < 0) { + llapi_lease_release(fd); + goto out; + } + + /* Atomically put lease, merge layouts and close. */ + data = calloc(1, offsetof(typeof(*data), lil_ids[1])); + if (!data) { + error_loc = "memory allocation"; + goto out; + } + data->lil_mode = LL_LEASE_UNLCK; + data->lil_flags = LL_LEASE_LAYOUT_MERGE; + data->lil_count = 1; + data->lil_ids[0] = fdv; + rc = llapi_lease_set(fd, data); + if (rc < 0) { + error_loc = "cannot merge layout"; + goto out; + } else if (rc == 0) { + rc = -EBUSY; + error_loc = "lost lease lock"; + goto out; + } + rc = 0; + +out: + if (data) + free(data); + if (fd >= 0) + close(fd); + if (fdv >= 0) + close(fdv); + if (rc < 0) + fprintf(stderr, "error: %s: %s: %s: %s\n", + progname, name, error_loc, strerror(-rc)); + return rc; +} + static int mirror_extend(char *fname, struct mirror_args *mirror_list, enum mirror_flags mirror_flags) { @@ -1516,9 +1583,8 @@ static int mirror_extend(char *fname, struct mirror_args *mirror_list, __u32 mirror_count = mirror_list->m_count; while (mirror_count > 0) { - rc = lfs_migrate(fname, - MIGRATION_NONBLOCK | MIGRATION_MIRROR, - NULL, mirror_list->m_layout); + rc = mirror_extend_layout(fname, + mirror_list->m_layout); if (rc) break; @@ -6870,9 +6936,9 @@ int lfs_mirror_resync_file(const char *fname, struct ll_ioc_lease *ioc, ioc->lil_mode = LL_LEASE_WRLCK; ioc->lil_flags = LL_LEASE_RESYNC; - rc = llapi_lease_get_ext(fd, ioc); + rc = llapi_lease_set(fd, ioc); if (rc < 0) { - fprintf(stderr, "%s: '%s' llapi_lease_get_ext resync failed: " + fprintf(stderr, "%s: '%s' llapi_lease_set resync failed: " "%s.\n", progname, fname, strerror(errno)); goto close_fd; } @@ -6971,7 +7037,7 @@ int lfs_mirror_resync_file(const char *fname, struct ll_ioc_lease *ioc, llapi_layout_free(layout); - rc = llapi_lease_get_ext(fd, ioc); + rc = llapi_lease_set(fd, ioc); if (rc <= 0) { if (rc == 0) /* lost lease lock */ rc = -EBUSY; @@ -6980,7 +7046,7 @@ int lfs_mirror_resync_file(const char *fname, struct ll_ioc_lease *ioc, goto close_fd; } /** - * llapi_lease_get_ext returns lease mode when it request to unlock + * llapi_lease_set returns lease mode when it request to unlock * the lease lock */ rc = 0; diff --git a/lustre/utils/liblustreapi_lease.c b/lustre/utils/liblustreapi_lease.c index 8869754..60ad9bc 100644 --- a/lustre/utils/liblustreapi_lease.c +++ b/lustre/utils/liblustreapi_lease.c @@ -36,7 +36,7 @@ #include #include "lustreapi_internal.h" -static inline const char *lease_mode2str(int mode) +static inline const char *lease_mode2str(enum ll_lease_mode mode) { switch (mode) { case LL_LEASE_WRLCK: return "WRITE"; @@ -47,18 +47,18 @@ static inline const char *lease_mode2str(int mode) } /** - * Extend lease get support. + * Extend lease set support. * - * \param fd File to get lease on. + * \param fd File to set lease on. * \param data ll_ioc_lease data. * - * For getting lease lock, it will return zero for success. For unlock, it will + * For setting lease lock, it will return zero for success. For unlock, it will * return the lock type it owned for succuess. * * \retval >= 0 on success. * \retval -errno on error. */ -int llapi_lease_get_ext(int fd, struct ll_ioc_lease *data) +int llapi_lease_set(int fd, const struct ll_ioc_lease *data) { int rc; @@ -66,38 +66,32 @@ int llapi_lease_get_ext(int fd, struct ll_ioc_lease *data) if (rc < 0) { rc = -errno; - /* exclude ENOTTY in case this is an old kernel that only - * supports LL_IOC_SET_LEASE_OLD */ - if (rc != -ENOTTY) - llapi_error(LLAPI_MSG_ERROR, rc, - "cannot get %s lease, ext %x", - lease_mode2str(data->lil_mode), - data->lil_flags); + llapi_error(LLAPI_MSG_ERROR, rc, "cannot get %s lease, ext %x", + lease_mode2str(data->lil_mode), data->lil_flags); } return rc; } /** - * Get a lease on an open file. + * Acquire a lease on an open file. * * \param fd File to get the lease on. * \param mode Lease mode, either LL_LEASE_RDLCK or LL_LEASE_WRLCK. * - * \see llapi_lease_get_ext(). + * \see llapi_lease_release(). * * \retval >= 0 on success. * \retval -errno on error. */ -int llapi_lease_get(int fd, int mode) +int llapi_lease_acquire(int fd, enum ll_lease_mode mode) { - struct ll_ioc_lease data = { 0 }; + struct ll_ioc_lease data = { .lil_mode = mode }; int rc; if (mode != LL_LEASE_RDLCK && mode != LL_LEASE_WRLCK) return -EINVAL; - data.lil_mode = mode; - rc = llapi_lease_get_ext(fd, &data); + rc = llapi_lease_set(fd, &data); if (rc == -ENOTTY) { rc = ioctl(fd, LL_IOC_SET_LEASE_OLD, mode); if (rc < 0) @@ -108,6 +102,41 @@ int llapi_lease_get(int fd, int mode) } /** + * Release a lease. + * + * \param fd File to remove the lease from. + * + * \retval type of the lease that was removed (LL_LEASE_READ or LL_LEASE_WRITE). + * \retval 0 if no lease was present. + * \retval -errno on error. + */ +int llapi_lease_release(int fd) +{ + struct ll_ioc_lease data = { .lil_mode = LL_LEASE_UNLCK }; + + return llapi_lease_set(fd, &data); +} + +/** + * Release a lease with intent operation. This API will release the lease + * and execute the intent operation atomically. + * + * \param fd File to remove the lease from. + * + * \retval type of the lease that was removed (LL_LEASE_READ or LL_LEASE_WRITE). + * \retval 0 if no lease was present. + * \retval -EBUSY lease broken, intent operation not executed. + * \retval -errno on error. + */ +int llapi_lease_release_intent(int fd, struct ll_ioc_lease *data) +{ + if (data->lil_mode != LL_LEASE_UNLCK) + return -EINVAL; + + return llapi_lease_set(fd, data); +} + +/** * Check if a lease is still set on a file. * * \param fd File to check the lease on. @@ -129,17 +158,32 @@ int llapi_lease_check(int fd) } /** - * Remove a lease. - * - * \param fd File to remove the lease from. - * - * \retval type of the lease that was removed (LL_LEASE_READ or LL_LEASE_WRITE). - * \retval 0 if no lease was present. - * \retval -errno on error. + * XXX: This is an obsoleted API - do not use it any more. + */ +int llapi_lease_get(int fd, int mode) +{ + int rc; + + if (mode != LL_LEASE_RDLCK && mode != LL_LEASE_WRLCK) + return -EINVAL; + + rc = ioctl(fd, LL_IOC_SET_LEASE_OLD, mode); + if (rc < 0) + rc = -errno; + + return rc; +} + +/** + * XXX: This is an obsoleted API - do not use it any more. */ int llapi_lease_put(int fd) { - struct ll_ioc_lease data = { .lil_mode = LL_LEASE_UNLCK }; + int rc; - return llapi_lease_get_ext(fd, &data); + rc = ioctl(fd, LL_IOC_SET_LEASE_OLD, LL_LEASE_UNLCK); + if (rc < 0) + rc = -errno; + + return rc; } -- 1.8.3.1