mirror of
https://github.com/checkpoint-restore/criu.git
synced 2026-07-25 11:04:35 +00:00
locks: Add c/r of non broken leases (kernel>=v4.1)
Leases in breaking state are not supported. In that case criu will report an error during the dumping. Also lock info in /proc/<pid>/fdinfo should be presented (since kernel 4.1). Before taking out new lease it modifies process fsuid to match file uid (see fcntl F_SETLEASE). Signed-off-by: Pavel Begunkov <asml.silence@gmail.com> Signed-off-by: Andrei Vagin <avagin@virtuozzo.com>
This commit is contained in:
parent
641d5ff987
commit
37028d86d7
3 changed files with 44 additions and 0 deletions
|
|
@ -5,6 +5,7 @@
|
|||
#include <string.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/fsuid.h>
|
||||
#include <sys/sysmacros.h>
|
||||
|
||||
#include "cr_options.h"
|
||||
|
|
@ -292,6 +293,9 @@ int note_file_lock(struct pid *pid, int fd, int lfd, struct fd_parms *p)
|
|||
*/
|
||||
if (fl->fl_owner != pid->real)
|
||||
continue;
|
||||
} else if (fl->fl_kind == FL_LEASE) {
|
||||
pr_err("Leases are not supported for kernel <= v4.0");
|
||||
return -1;
|
||||
} else /* fl->fl_kind == FL_FLOCK || fl->fl_kind == FL_OFD */ {
|
||||
int ret;
|
||||
|
||||
|
|
@ -329,6 +333,30 @@ int note_file_lock(struct pid *pid, int fd, int lfd, struct fd_parms *p)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int set_file_lease(int fd, int type)
|
||||
{
|
||||
int old_fsuid, ret;
|
||||
struct stat st;
|
||||
|
||||
if (fstat(fd, &st)) {
|
||||
pr_perror("Can't get file stat (%i)\n", fd);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/*
|
||||
* An unprivileged process may take out a lease only if
|
||||
* uid of the file matches the fsuid of the process.
|
||||
*/
|
||||
old_fsuid = setfsuid(st.st_uid);
|
||||
|
||||
ret = fcntl(fd, F_SETLEASE, type);
|
||||
if (ret < 0)
|
||||
pr_perror("Can't set lease\n");
|
||||
|
||||
setfsuid(old_fsuid);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int restore_file_lock(FileLockEntry *fle)
|
||||
{
|
||||
int ret = -1;
|
||||
|
|
@ -395,6 +423,16 @@ static int restore_file_lock(FileLockEntry *fle)
|
|||
pr_err("Can not set ofd lock!\n");
|
||||
goto err;
|
||||
}
|
||||
} else if (fle->flag & FL_LEASE) {
|
||||
pr_info("(lease)flag: %d, type: %d, pid: %d, fd: %d, "
|
||||
"start: %8"PRIx64", len: %8"PRIx64"\n",
|
||||
fle->flag, fle->type, fle->pid, fle->fd,
|
||||
fle->start, fle->len);
|
||||
ret = set_file_lease(fle->fd, fle->type);
|
||||
if (ret < 0) {
|
||||
pr_perror("Can't set lease!\n");
|
||||
goto err;
|
||||
}
|
||||
} else {
|
||||
pr_err("Unknown file lock style!\n");
|
||||
goto err;
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@
|
|||
#define FL_POSIX 1
|
||||
#define FL_FLOCK 2
|
||||
#define FL_OFD 4
|
||||
#define FL_LEASE 8
|
||||
|
||||
/* for posix fcntl() and lockf() */
|
||||
#ifndef F_RDLCK
|
||||
|
|
|
|||
|
|
@ -2087,6 +2087,8 @@ static int parse_file_lock_buf(char *buf, struct file_lock *fl,
|
|||
fl->fl_kind = FL_FLOCK;
|
||||
else if (!strcmp(fl_flag, "OFDLCK"))
|
||||
fl->fl_kind = FL_OFD;
|
||||
else if (!strcmp(fl_flag, "LEASE"))
|
||||
fl->fl_kind = FL_LEASE;
|
||||
else
|
||||
fl->fl_kind = FL_UNKNOWN;
|
||||
|
||||
|
|
@ -2103,6 +2105,9 @@ static int parse_file_lock_buf(char *buf, struct file_lock *fl,
|
|||
pr_err("Unknown lock option!\n");
|
||||
return -1;
|
||||
}
|
||||
} else if (fl->fl_kind == FL_LEASE && !strcmp(fl_type, "BREAKING")) {
|
||||
pr_err("Breaking leases are not supported (%d): %s\n",
|
||||
num, buf);
|
||||
} else {
|
||||
if (!strcmp(fl_option, "UNLCK")) {
|
||||
fl->fl_ltype |= F_UNLCK;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue