Hello community,
here is the log from the commit of package criu for openSUSE:Factory checked in at 2017-06-30 18:43:06
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/criu (Old)
and /work/SRC/openSUSE:Factory/.criu.new (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "criu"
Fri Jun 30 18:43:06 2017 rev:34 rq:507279 version:3.2.1
Changes:
--------
--- /work/SRC/openSUSE:Factory/criu/criu.changes 2017-06-22 10:40:40.587224838 +0200
+++ /work/SRC/openSUSE:Factory/.criu.new/criu.changes 2017-06-30 18:43:47.890011554 +0200
@@ -1,0 +2,7 @@
+Fri Jun 30 11:33:54 CEST 2017 - tiwai(a)suse.de
+
+- update to criu 3.2.1: bug fix release,
+ * Restoring a stack fails on recent kernels due to kernel changes
+ * Restoring on a host with LSM profiles failed
+
+-------------------------------------------------------------------
Old:
----
criu-3.2.tar.bz2
New:
----
criu-3.2.1.tar.bz2
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ criu.spec ++++++
--- /var/tmp/diff_new_pack.hg6xmI/_old 2017-06-30 18:43:48.389941236 +0200
+++ /var/tmp/diff_new_pack.hg6xmI/_new 2017-06-30 18:43:48.389941236 +0200
@@ -17,7 +17,7 @@
Name: criu
-Version: 3.2
+Version: 3.2.1
Release: 0
Summary: Checkpoint/Restore In Userspace Tools
License: GPL-2.0
++++++ criu-3.2.tar.bz2 -> criu-3.2.1.tar.bz2 ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/.travis.yml new/criu-3.2.1/.travis.yml
--- old/criu-3.2/.travis.yml 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/.travis.yml 2017-06-28 07:49:36.000000000 +0200
@@ -22,3 +22,4 @@
after_success:
- ccache -s
- make -C scripts/travis after_success
+group: deprecated-2017Q2
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/Makefile.versions new/criu-3.2.1/Makefile.versions
--- old/criu-3.2/Makefile.versions 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/Makefile.versions 2017-06-28 07:49:36.000000000 +0200
@@ -2,7 +2,7 @@
# CRIU version.
CRIU_VERSION_MAJOR := 3
CRIU_VERSION_MINOR := 2
-CRIU_VERSION_SUBLEVEL :=
+CRIU_VERSION_SUBLEVEL := 1
CRIU_VERSION_EXTRA :=
CRIU_VERSION_NAME := Tin Hoopoe
CRIU_VERSION := $(CRIU_VERSION_MAJOR)$(if $(CRIU_VERSION_MINOR),.$(CRIU_VERSION_MINOR))$(if $(CRIU_VERSION_SUBLEVEL),.$(CRIU_VERSION_SUBLEVEL))$(if $(CRIU_VERSION_EXTRA),.$(CRIU_VERSION_EXTRA))
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/cr-dump.c new/criu-3.2.1/criu/cr-dump.c
--- old/criu-3.2/criu/cr-dump.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/cr-dump.c 2017-06-28 07:49:36.000000000 +0200
@@ -1539,6 +1539,9 @@
if (kerndat_init())
goto err;
+ if (lsm_check_opts())
+ goto err;
+
if (irmap_load_cache())
goto err;
@@ -1689,6 +1692,9 @@
if (kerndat_init())
goto err;
+ if (lsm_check_opts())
+ goto err;
+
if (irmap_load_cache())
goto err;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/cr-restore.c new/criu-3.2.1/criu/cr-restore.c
--- old/criu-3.2/criu/cr-restore.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/cr-restore.c 2017-06-28 07:49:36.000000000 +0200
@@ -2134,6 +2134,9 @@
if (kerndat_init())
goto err;
+ if (lsm_check_opts())
+ goto err;
+
timing_start(TIME_RESTORE);
if (cpu_init() < 0)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/crtools.c new/criu-3.2.1/criu/crtools.c
--- old/criu-3.2/criu/crtools.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/crtools.c 2017-06-28 07:49:36.000000000 +0200
@@ -511,8 +511,8 @@
return -1;
break;
case 1071:
- if (parse_lsm_arg(optarg) < 0)
- return -1;
+ opts.lsm_profile = optarg;
+ opts.lsm_supplied = true;
break;
case 1072:
opts.timeout = atoi(optarg);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/include/kerndat.h new/criu-3.2.1/criu/include/kerndat.h
--- old/criu-3.2/criu/include/kerndat.h 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/include/kerndat.h 2017-06-28 07:49:36.000000000 +0200
@@ -1,6 +1,8 @@
#ifndef __CR_KERNDAT_H__
#define __CR_KERNDAT_H__
+#include <stdbool.h>
+
#include "int.h"
struct stat;
@@ -44,6 +46,8 @@
unsigned int has_xtlocks;
unsigned long mmap_min_addr;
bool has_tcp_half_closed;
+ bool stack_guard_gap_hidden;
+ int lsm;
};
extern struct kerndat_s kdat;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/include/lsm.h new/criu-3.2.1/criu/include/lsm.h
--- old/criu-3.2/criu/include/lsm.h 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/include/lsm.h 2017-06-28 07:49:36.000000000 +0200
@@ -33,5 +33,5 @@
*/
int render_lsm_profile(char *profile, char **val);
-extern int parse_lsm_arg(char *arg);
+extern int lsm_check_opts(void);
#endif /* __CR_LSM_H__ */
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/include/mem.h new/criu-3.2.1/criu/include/mem.h
--- old/criu-3.2/criu/include/mem.h 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/include/mem.h 2017-06-28 07:49:36.000000000 +0200
@@ -9,11 +9,13 @@
struct vm_area_list;
struct page_pipe;
struct pstree_item;
+struct vma_area;
struct mem_dump_ctl {
bool pre_dump;
};
+extern bool vma_has_guard_gap_hidden(struct vma_area *vma);
extern bool page_in_parent(bool dirty);
extern int prepare_mm_pid(struct pstree_item *i);
extern void prepare_cow_vmas(void);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/kerndat.c new/criu-3.2.1/criu/kerndat.c
--- old/criu-3.2/criu/kerndat.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/kerndat.c 2017-06-28 07:49:36.000000000 +0200
@@ -563,6 +563,80 @@
return 0;
}
+static int kerndat_detect_stack_guard_gap(void)
+{
+ int num, ret = -1, detected = 0;
+ unsigned long start, end;
+ char r, w, x, s;
+ char buf[1024];
+ FILE *maps;
+ void *mem;
+
+ mem = mmap(NULL, (3ul << 20), PROT_READ | PROT_WRITE,
+ MAP_PRIVATE | MAP_ANONYMOUS | MAP_GROWSDOWN, -1, 0);
+ if (mem == MAP_FAILED) {
+ pr_perror("Can't mmap stack area");
+ return -1;
+ }
+ munmap(mem, (3ul << 20));
+
+ mem = mmap(mem + (2ul << 20), (1ul << 20), PROT_READ | PROT_WRITE,
+ MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED | MAP_GROWSDOWN, -1, 0);
+ if (mem == MAP_FAILED) {
+ pr_perror("Can't mmap stack area");
+ return -1;
+ }
+
+ maps = fopen("/proc/self/maps", "r");
+ if (maps == NULL) {
+ munmap(mem, 4096);
+ return -1;
+ }
+
+ while (fgets(buf, sizeof(buf), maps)) {
+ num = sscanf(buf, "%lx-%lx %c%c%c%c",
+ &start, &end, &r, &w, &x, &s);
+ if (num < 6) {
+ pr_err("Can't parse: %s\n", buf);
+ goto err;
+ }
+
+ /*
+ * When reading /proc/$pid/[s]maps the
+ * start/end addresses migh be cutted off
+ * with PAGE_SIZE on kernels prior 4.12
+ * (see kernel commit 1be7107fbe18ee).
+ *
+ * Same time there was semi-complete
+ * patch released which hitted a number
+ * of repos (Ubuntu, Fedora) where instead
+ * of PAGE_SIZE the 1M gap is cutted off.
+ */
+ if (start == (unsigned long)mem) {
+ kdat.stack_guard_gap_hidden = false;
+ detected = 1;
+ break;
+ } else if (start == ((unsigned long)mem + (1ul << 20))) {
+ pr_warn("Unsupported stack guard detected, confused but continue\n");
+ kdat.stack_guard_gap_hidden = true;
+ detected = 1;
+ break;
+ } else if (start == ((unsigned long)mem + PAGE_SIZE)) {
+ kdat.stack_guard_gap_hidden = true;
+ detected = 1;
+ break;
+ }
+ }
+
+ if (detected)
+ ret = 0;
+
+err:
+ munmap(mem, (1ul << 20));
+ fclose(maps);
+ return ret;
+}
+
#define KERNDAT_CACHE_FILE KDAT_RUNDIR"/criu.kdat"
#define KERNDAT_CACHE_FILE_TMP KDAT_RUNDIR"/.criu.kdat"
@@ -676,6 +750,8 @@
ret = kerndat_compat_restore();
if (!ret)
ret = kerndat_has_memfd_create();
+ if (!ret)
+ ret = kerndat_detect_stack_guard_gap();
kerndat_lsm();
kerndat_mmap_min_addr();
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/lsm.c new/criu-3.2.1/criu/lsm.c
--- old/criu-3.2/criu/lsm.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/lsm.c 2017-06-28 07:49:36.000000000 +0200
@@ -5,6 +5,7 @@
#include <sys/types.h>
#include <unistd.h>
+#include "kerndat.h"
#include "config.h"
#include "pstree.h"
#include "util.h"
@@ -19,10 +20,6 @@
#include <selinux/selinux.h>
#endif
-static Lsmtype lsmtype;
-static int (*get_label)(pid_t, char **) = NULL;
-static char *name = NULL;
-
static int apparmor_get_label(pid_t pid, char **profile_name)
{
FILE *f;
@@ -109,18 +106,8 @@
void kerndat_lsm(void)
{
- /* On restore, if someone passes --lsm-profile, we might end up doing
- * detection twice, once during flag parsing and once for
- * kerndat_init(). Let's detect when we've already done detection
- * and not do it again.
- */
- if (name)
- return;
-
if (access(AA_SECURITYFS_PATH, F_OK) == 0) {
- get_label = apparmor_get_label;
- lsmtype = LSMTYPE__APPARMOR;
- name = "apparmor";
+ kdat.lsm = LSMTYPE__APPARMOR;
return;
}
@@ -131,37 +118,47 @@
* well.
*/
if (access("/sys/fs/selinux", F_OK) == 0) {
- get_label = selinux_get_label;
- lsmtype = LSMTYPE__SELINUX;
- name = "selinux";
+ kdat.lsm = LSMTYPE__SELINUX;
return;
}
#endif
- get_label = NULL;
- lsmtype = LSMTYPE__NO_LSM;
- name = "none";
+ kdat.lsm = LSMTYPE__NO_LSM;
}
Lsmtype host_lsm_type(void)
{
- return lsmtype;
+ return kdat.lsm;
}
int collect_lsm_profile(pid_t pid, CredsEntry *ce)
{
- ce->lsm_profile = NULL;
+ int ret;
- if (lsmtype == LSMTYPE__NO_LSM)
- return 0;
+ ce->lsm_profile = NULL;
- if (get_label(pid, &ce->lsm_profile) < 0)
- return -1;
+ switch (kdat.lsm) {
+ case LSMTYPE__NO_LSM:
+ ret = 0;
+ break;
+ case LSMTYPE__APPARMOR:
+ ret = apparmor_get_label(pid, &ce->lsm_profile);
+ break;
+#ifdef CONFIG_HAS_SELINUX
+ case LSMTYPE__SELINUX:
+ ret = selinux_get_label(pid, &ce->lsm_profile);
+ break;
+#endif
+ default:
+ BUG();
+ ret = -1;
+ break;
+ }
if (ce->lsm_profile)
pr_info("%d has lsm profile %s\n", pid, ce->lsm_profile);
- return 0;
+ return ret;
}
// in inventory.c
@@ -169,7 +166,7 @@
int validate_lsm(char *lsm_profile)
{
- if (image_lsm == LSMTYPE__NO_LSM || image_lsm == lsmtype)
+ if (image_lsm == LSMTYPE__NO_LSM || image_lsm == kdat.lsm)
return 0;
/*
@@ -189,7 +186,7 @@
{
*val = NULL;
- switch (lsmtype) {
+ switch (kdat.lsm) {
case LSMTYPE__APPARMOR:
if (strcmp(profile, "unconfined") != 0 && asprintf(val, "changeprofile %s", profile) < 0) {
pr_err("allocating lsm profile failed\n");
@@ -211,43 +208,42 @@
return 0;
}
-int parse_lsm_arg(char *arg)
+int lsm_check_opts(void)
{
char *aux;
- kerndat_lsm();
+ if (!opts.lsm_supplied)
+ return 0;
- aux = strchr(arg, ':');
+ aux = strchr(opts.lsm_profile, ':');
if (aux == NULL) {
- pr_err("invalid argument %s for --lsm-profile\n", arg);
+ pr_err("invalid argument %s for --lsm-profile\n", opts.lsm_profile);
return -1;
}
*aux = '\0';
aux++;
- if (strcmp(arg, "apparmor") == 0) {
- if (lsmtype != LSMTYPE__APPARMOR) {
+ if (strcmp(opts.lsm_profile, "apparmor") == 0) {
+ if (kdat.lsm != LSMTYPE__APPARMOR) {
pr_err("apparmor LSM specified but apparmor not supported by kernel\n");
return -1;
}
opts.lsm_profile = aux;
- } else if (strcmp(arg, "selinux") == 0) {
- if (lsmtype != LSMTYPE__SELINUX) {
+ } else if (strcmp(opts.lsm_profile, "selinux") == 0) {
+ if (kdat.lsm != LSMTYPE__SELINUX) {
pr_err("selinux LSM specified but selinux not supported by kernel\n");
return -1;
}
opts.lsm_profile = aux;
- } else if (strcmp(arg, "none") == 0) {
+ } else if (strcmp(opts.lsm_profile, "none") == 0) {
opts.lsm_profile = NULL;
} else {
- pr_err("unknown lsm %s\n", arg);
+ pr_err("unknown lsm %s\n", opts.lsm_profile);
return -1;
}
- opts.lsm_supplied = true;
-
return 0;
}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/mem.c new/criu-3.2.1/criu/mem.c
--- old/criu-3.2/criu/mem.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/mem.c 2017-06-28 07:49:36.000000000 +0200
@@ -499,7 +499,7 @@
if (vma_area_is_private(vma, kdat.task_size)) {
ri->vmas.priv_size += vma_area_len(vma);
- if (vma->e->flags & MAP_GROWSDOWN)
+ if (vma_has_guard_gap_hidden(vma))
ri->vmas.priv_size += PAGE_SIZE;
}
@@ -634,7 +634,7 @@
* A grow-down VMA has a guard page, which protect a VMA below it.
* So one more page is mapped here to restore content of the first page
*/
- if (vma->e->flags & MAP_GROWSDOWN)
+ if (vma_has_guard_gap_hidden(vma))
vma->e->start -= PAGE_SIZE;
size = vma_entry_len(vma->e);
@@ -686,7 +686,7 @@
*/
paddr = decode_pointer(vma->pvma->premmaped_addr);
- if (vma->e->flags & MAP_GROWSDOWN)
+ if (vma_has_guard_gap_hidden(vma))
paddr -= PAGE_SIZE;
addr = mremap(paddr, size, size,
@@ -702,7 +702,7 @@
pr_debug("\tpremap %#016"PRIx64"-%#016"PRIx64" -> %016lx\n",
vma->e->start, vma->e->end, (unsigned long)addr);
- if (vma->e->flags & MAP_GROWSDOWN) { /* Skip gurad page */
+ if (vma_has_guard_gap_hidden(vma)) { /* Skip gurad page */
vma->e->start += PAGE_SIZE;
vma->premmaped_addr += PAGE_SIZE;
}
@@ -717,7 +717,8 @@
static inline bool vma_force_premap(struct vma_area *vma, struct list_head *head)
{
/*
- * Growsdown VMAs always have one guard page at the
+ * On kernels with 4K guard pages, growsdown VMAs
+ * always have one guard page at the
* beginning and sometimes this page contains data.
* In case the VMA is premmaped, we premmap one page
* larger VMA. In case of in place restore we can only
@@ -1046,6 +1047,11 @@
return ret;
}
+bool vma_has_guard_gap_hidden(struct vma_area *vma)
+{
+ return kdat.stack_guard_gap_hidden && (vma->e->flags & MAP_GROWSDOWN);
+}
+
/*
* A gard page must be unmapped after restoring content and
* forking children to restore COW memory.
@@ -1055,6 +1061,9 @@
struct vma_area *vma;
struct list_head *vmas = &rsti(t)->vmas.h;
+ if (!kdat.stack_guard_gap_hidden)
+ return 0;
+
list_for_each_entry(vma, vmas, list) {
if (!vma_area_is(vma, VMA_PREMMAPED))
continue;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/criu/proc_parse.c new/criu-3.2.1/criu/proc_parse.c
--- old/criu-3.2/criu/proc_parse.c 2017-06-19 11:59:14.000000000 +0200
+++ new/criu-3.2.1/criu/proc_parse.c 2017-06-28 07:49:36.000000000 +0200
@@ -25,6 +25,7 @@
#include "kerndat.h"
#include "vdso.h"
#include "vma.h"
+#include "mem.h"
#include "bfd.h"
#include "proc_parse.h"
#include "fdinfo.h"
@@ -637,7 +638,7 @@
}
/* Add a guard page only if here is enough space for it */
- if ((vma_area->e->flags & MAP_GROWSDOWN) &&
+ if (vma_has_guard_gap_hidden(vma_area) &&
*prev_end < vma_area->e->start)
vma_area->e->start -= PAGE_SIZE; /* Guard page */
*prev_end = vma_area->e->end;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/test/zdtm/static/grow_map.desc new/criu-3.2.1/test/zdtm/static/grow_map.desc
--- old/criu-3.2/test/zdtm/static/grow_map.desc 1970-01-01 01:00:00.000000000 +0100
+++ new/criu-3.2.1/test/zdtm/static/grow_map.desc 2017-06-28 07:49:36.000000000 +0200
@@ -0,0 +1 @@
+{'flags': 'noauto'}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/test/zdtm/static/grow_map02.desc new/criu-3.2.1/test/zdtm/static/grow_map02.desc
--- old/criu-3.2/test/zdtm/static/grow_map02.desc 1970-01-01 01:00:00.000000000 +0100
+++ new/criu-3.2.1/test/zdtm/static/grow_map02.desc 2017-06-28 07:49:36.000000000 +0200
@@ -0,0 +1 @@
+{'flags': 'noauto'}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/criu-3.2/test/zdtm/static/grow_map03.desc new/criu-3.2.1/test/zdtm/static/grow_map03.desc
--- old/criu-3.2/test/zdtm/static/grow_map03.desc 1970-01-01 01:00:00.000000000 +0100
+++ new/criu-3.2.1/test/zdtm/static/grow_map03.desc 2017-06-28 07:49:36.000000000 +0200
@@ -0,0 +1 @@
+{'flags': 'noauto'}