[CRIU] [PATCH 2/8] compel: Get syscall injection point in compel
Cyrill Gorcunov
gorcunov at openvz.org
Mon Nov 21 10:26:14 PST 2016
From: Pavel Emelyanov <xemul at virtuozzo.com>
The ictx->syscall_ip is the address of any x-able VMA.
CRIU knows this as it parses the smaps file (heavily).
For others compel just parses /proc/pid/maps file.
Signed-off-by: Pavel Emelyanov <xemul at virtuozzo.com>
---
compel/src/lib/infect.c | 43 +++++++++++++++++++++++++++++++++++++++++++
1 file changed, 43 insertions(+)
diff --git a/compel/src/lib/infect.c b/compel/src/lib/infect.c
index aee125d28f2f..98f1c80ca8bf 100644
--- a/compel/src/lib/infect.c
+++ b/compel/src/lib/infect.c
@@ -926,6 +926,41 @@ err:
return NULL;
}
+/*
+ * Find first executable VMA that would fit the initial
+ * syscall injection.
+ */
+static unsigned long find_executable_area(int pid)
+{
+ char aux[128];
+ FILE *f;
+ unsigned long ret = (unsigned long)MAP_FAILED;
+
+ sprintf(aux, "/proc/%d/%maps", pid);
+ f = fopen(aux, "r");
+ if (!f)
+ goto out;
+
+ while (fgets(aux, sizeof(aux), f)) {
+ unsigned long start, end;
+ char *f;
+
+ start = strtoul(aux, &f, 16);
+ end = strtoul(f + 1, &f, 16);
+
+ /* f now points at " rwx" (yes, with space) part */
+ if (f[3] == 'x') {
+ BUG_ON(end - start < PARASITE_START_AREA_MIN);
+ ret = start;
+ break;
+ }
+ }
+
+ fclose(f);
+out:
+ return ret;
+}
+
struct parasite_ctl *compel_prepare(int pid)
{
struct parasite_ctl *ctl;
@@ -937,8 +972,16 @@ struct parasite_ctl *compel_prepare(int pid)
ictx = &ctl->ictx;
ictx->task_size = task_size();
+ ictx->syscall_ip = find_executable_area(pid);
+ if (ictx->syscall_ip == (unsigned long)MAP_FAILED)
+ goto err;
+
out:
return ctl;
+
+err:
+ free(ctl);
+ goto out;
}
static bool task_in_parasite(struct parasite_ctl *ctl, user_regs_struct_t *regs)
--
2.7.4
More information about the CRIU
mailing list