chiark
/
gitweb
/
~ianmdlvl
/
elogind.git
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
getty: don't parse console= anymore, use /sys/class/tty/console/active instead
[elogind.git]
/
src
/
cgroup-util.c
diff --git
a/src/cgroup-util.c
b/src/cgroup-util.c
index 26e8f691d3ebfd1598d676cbf44e573853c804cd..b68b9ad3a33a20c9c85e2e0c7a5d495e3f7cb71a 100644
(file)
--- a/
src/cgroup-util.c
+++ b/
src/cgroup-util.c
@@
-1,4
+1,4
@@
-/*-*- Mode: C; c-basic-offset: 8 -*-*/
+/*-*- Mode: C; c-basic-offset: 8
; indent-tabs-mode: nil
-*-*/
/***
This file is part of systemd.
/***
This file is part of systemd.
@@
-25,6
+25,8
@@
#include <string.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>
#include <stdlib.h>
#include <dirent.h>
+#include <sys/stat.h>
+#include <sys/types.h>
#include "cgroup-util.h"
#include "log.h"
#include "cgroup-util.h"
#include "log.h"
@@
-164,12
+166,12
@@
int cg_rmdir(const char *controller, const char *path) {
return r < 0 ? -errno : 0;
}
return r < 0 ? -errno : 0;
}
-int cg_kill(const char *controller, const char *path, int sig, bool ignore_self) {
+int cg_kill(const char *controller, const char *path, int sig, bool ignore_self
, Set *s
) {
bool done = false;
bool done = false;
- Set *s;
int r, ret = 0;
pid_t my_pid;
FILE *f = NULL;
int r, ret = 0;
pid_t my_pid;
FILE *f = NULL;
+ Set *allocated_set = NULL;
assert(controller);
assert(path);
assert(controller);
assert(path);
@@
-179,17
+181,18
@@
int cg_kill(const char *controller, const char *path, int sig, bool ignore_self)
* is repeated until no further processes are added to the
* tasks list, to properly handle forking processes */
* is repeated until no further processes are added to the
* tasks list, to properly handle forking processes */
- if (!(s = set_new(trivial_hash_func, trivial_compare_func)))
- return -ENOMEM;
+ if (!s)
+ if (!(s = allocated_set = set_new(trivial_hash_func, trivial_compare_func)))
+ return -ENOMEM;
my_pid = getpid();
do {
my_pid = getpid();
do {
- pid_t pid;
+ pid_t pid
= 0
;
done = true;
if ((r = cg_enumerate_processes(controller, path, &f)) < 0) {
done = true;
if ((r = cg_enumerate_processes(controller, path, &f)) < 0) {
- if (ret >= 0)
+ if (ret >= 0
&& r != -ENOENT
)
ret = r;
goto finish;
ret = r;
goto finish;
@@
-205,8
+208,8
@@
int cg_kill(const char *controller, const char *path, int sig, bool ignore_self)
/* If we haven't killed this process yet, kill
* it */
/* If we haven't killed this process yet, kill
* it */
- if (kill(pid, sig) < 0
&& errno != ESRCH
) {
- if (ret >= 0)
+ if (kill(pid, sig) < 0) {
+ if (ret >= 0
&& errno != ESRCH
)
ret = -errno;
} else if (ret == 0)
ret = 1;
ret = -errno;
} else if (ret == 0)
ret = 1;
@@
-238,7
+241,8
@@
int cg_kill(const char *controller, const char *path, int sig, bool ignore_self)
} while (!done);
finish:
} while (!done);
finish:
- set_free(s);
+ if (allocated_set)
+ set_free(allocated_set);
if (f)
fclose(f);
if (f)
fclose(f);
@@
-246,19
+250,24
@@
finish:
return ret;
}
return ret;
}
-int cg_kill_recursive(const char *controller, const char *path, int sig, bool ignore_self, bool rem) {
+int cg_kill_recursive(const char *controller, const char *path, int sig, bool ignore_self, bool rem
, Set *s
) {
int r, ret = 0;
DIR *d = NULL;
char *fn;
int r, ret = 0;
DIR *d = NULL;
char *fn;
+ Set *allocated_set = NULL;
assert(path);
assert(controller);
assert(sig >= 0);
assert(path);
assert(controller);
assert(sig >= 0);
- ret = cg_kill(controller, path, sig, ignore_self);
+ if (!s)
+ if (!(s = allocated_set = set_new(trivial_hash_func, trivial_compare_func)))
+ return -ENOMEM;
+
+ ret = cg_kill(controller, path, sig, ignore_self, s);
if ((r = cg_enumerate_subgroups(controller, path, &d)) < 0) {
if ((r = cg_enumerate_subgroups(controller, path, &d)) < 0) {
- if (ret >= 0)
+ if (ret >= 0
&& r != -ENOENT
)
ret = r;
goto finish;
ret = r;
goto finish;
@@
-277,7
+286,7
@@
int cg_kill_recursive(const char *controller, const char *path, int sig, bool ig
goto finish;
}
goto finish;
}
- r = cg_kill_recursive(controller, p, sig, ignore_self, rem);
+ r = cg_kill_recursive(controller, p, sig, ignore_self, rem
, s
);
free(p);
if (r != 0 && ret >= 0)
free(p);
if (r != 0 && ret >= 0)
@@
-289,7
+298,9
@@
int cg_kill_recursive(const char *controller, const char *path, int sig, bool ig
if (rem)
if ((r = cg_rmdir(controller, path)) < 0) {
if (rem)
if ((r = cg_rmdir(controller, path)) < 0) {
- if (ret >= 0)
+ if (ret >= 0 &&
+ r != -ENOENT &&
+ r != -EBUSY)
ret = r;
}
ret = r;
}
@@
-297,6
+308,9
@@
finish:
if (d)
closedir(d);
if (d)
closedir(d);
+ if (allocated_set)
+ set_free(allocated_set);
+
return ret;
}
return ret;
}
@@
-307,24
+321,25
@@
int cg_kill_recursive_and_wait(const char *controller, const char *path, bool re
assert(controller);
/* This safely kills all processes; first it sends a SIGTERM,
assert(controller);
/* This safely kills all processes; first it sends a SIGTERM,
- * then checks 8 times after 50ms whether the group is
- * now empty, and finally kills everything that is left with
- * SIGKILL */
+ * then checks 8 times after 200ms whether the group is now
+ * empty, then kills everything that is left with SIGKILL and
+ * finally checks 5 times after 200ms each whether the group
+ * is finally empty. */
- for (i = 0; i < 1
0
; i++) {
+ for (i = 0; i < 1
5
; i++) {
int sig, r;
if (i <= 0)
sig = SIGTERM;
int sig, r;
if (i <= 0)
sig = SIGTERM;
- else if (i
>
= 9)
+ else if (i
=
= 9)
sig = SIGKILL;
else
sig = 0;
sig = SIGKILL;
else
sig = 0;
- if ((r = cg_kill_recursive(controller, path, sig, true, rem)) <= 0)
+ if ((r = cg_kill_recursive(controller, path, sig, true, rem
, NULL
)) <= 0)
return r;
return r;
- usleep(
5
0 * USEC_PER_MSEC);
+ usleep(
20
0 * USEC_PER_MSEC);
}
return 0;
}
return 0;
@@
-347,11
+362,11
@@
int cg_migrate(const char *controller, const char *from, const char *to, bool ig
my_pid = getpid();
do {
my_pid = getpid();
do {
- pid_t pid;
+ pid_t pid
= 0
;
done = true;
if ((r = cg_enumerate_tasks(controller, from, &f)) < 0) {
done = true;
if ((r = cg_enumerate_tasks(controller, from, &f)) < 0) {
- if (ret >= 0)
+ if (ret >= 0
&& r != -ENOENT
)
ret = r;
goto finish;
ret = r;
goto finish;
@@
-369,7
+384,7
@@
int cg_migrate(const char *controller, const char *from, const char *to, bool ig
continue;
if ((r = cg_attach(controller, to, pid)) < 0) {
continue;
if ((r = cg_attach(controller, to, pid)) < 0) {
- if (ret >= 0)
+ if (ret >= 0
&& r != -ESRCH
)
ret = r;
} else if (ret == 0)
ret = 1;
ret = r;
} else if (ret == 0)
ret = 1;
@@
-417,7
+432,7
@@
int cg_migrate_recursive(const char *controller, const char *from, const char *t
ret = cg_migrate(controller, from, to, ignore_self);
if ((r = cg_enumerate_subgroups(controller, from, &d)) < 0) {
ret = cg_migrate(controller, from, to, ignore_self);
if ((r = cg_enumerate_subgroups(controller, from, &d)) < 0) {
- if (ret >= 0)
+ if (ret >= 0
&& r != -ENOENT
)
ret = r;
goto finish;
}
ret = r;
goto finish;
}
@@
-447,7
+462,9
@@
int cg_migrate_recursive(const char *controller, const char *from, const char *t
if (rem)
if ((r = cg_rmdir(controller, from)) < 0) {
if (rem)
if ((r = cg_rmdir(controller, from)) < 0) {
- if (ret >= 0)
+ if (ret >= 0 &&
+ r != -ENOENT &&
+ r != -EBUSY)
ret = r;
}
ret = r;
}
@@
-479,7
+496,7
@@
int cg_get_path(const char *controller, const char *path, const char *suffix, ch
else
p = controller;
else
p = controller;
- if (asprintf(&mp, "/cgroup/%s", p) < 0)
+ if (asprintf(&mp, "/
sys/fs/
cgroup/%s", p) < 0)
return -ENOMEM;
if ((r = path_is_mount_point(mp)) <= 0) {
return -ENOMEM;
if ((r = path_is_mount_point(mp)) <= 0) {
@@
-517,7
+534,7
@@
int cg_trim(const char *controller, const char *path, bool delete_root) {
r = rm_rf(fs, true, delete_root);
free(fs);
r = rm_rf(fs, true, delete_root);
free(fs);
- return r;
+ return r
== -ENOENT ? 0 : r
;
}
int cg_delete(const char *controller, const char *path) {
}
int cg_delete(const char *controller, const char *path) {
@@
-533,7
+550,7
@@
int cg_delete(const char *controller, const char *path) {
r = cg_migrate_recursive(controller, path, parent, false, true);
free(parent);
r = cg_migrate_recursive(controller, path, parent, false, true);
free(parent);
- return r;
+ return r
== -ENOENT ? 0 : r
;
}
int cg_create(const char *controller, const char *path) {
}
int cg_create(const char *controller, const char *path) {
@@
-546,7
+563,17
@@
int cg_create(const char *controller, const char *path) {
if ((r = cg_get_path(controller, path, NULL, &fs)) < 0)
return r;
if ((r = cg_get_path(controller, path, NULL, &fs)) < 0)
return r;
- r = mkdir_p(fs, 0755);
+ r = mkdir_parents(fs, 0755);
+
+ if (r >= 0) {
+ if (mkdir(fs, 0755) >= 0)
+ r = 1;
+ else if (errno == EEXIST)
+ r = 0;
+ else
+ r = -errno;
+ }
+
free(fs);
return r;
free(fs);
return r;
@@
-577,7
+604,7
@@
int cg_attach(const char *controller, const char *path, pid_t pid) {
}
int cg_create_and_attach(const char *controller, const char *path, pid_t pid) {
}
int cg_create_and_attach(const char *controller, const char *path, pid_t pid) {
- int r;
+ int r
, q
;
assert(controller);
assert(path);
assert(controller);
assert(path);
@@
-586,8
+613,8
@@
int cg_create_and_attach(const char *controller, const char *path, pid_t pid) {
if ((r = cg_create(controller, path)) < 0)
return r;
if ((r = cg_create(controller, path)) < 0)
return r;
- if ((
r
= cg_attach(controller, path, pid)) < 0)
- return
r
;
+ if ((
q
= cg_attach(controller, path, pid)) < 0)
+ return
q
;
/* This does not remove the cgroup on failure */
/* This does not remove the cgroup on failure */
@@
-646,6
+673,9
@@
int cg_get_by_pid(const char *controller, pid_t pid, char **path) {
f = fopen(fs, "re");
free(fs);
f = fopen(fs, "re");
free(fs);
+ if (!f)
+ return errno == ENOENT ? -ESRCH : -errno;
+
cs = strlen(controller);
while (!feof(f)) {
cs = strlen(controller);
while (!feof(f)) {
@@
-722,10
+752,8
@@
int cg_install_release_agent(const char *controller, const char *agent) {
free(fs);
fs = NULL;
free(fs);
fs = NULL;
- if ((r = cg_get_path(controller, NULL, "notify_on_release", &fs)) < 0) {
- r = -ENOMEM;
+ if ((r = cg_get_path(controller, NULL, "notify_on_release", &fs)) < 0)
goto finish;
goto finish;
- }
free(contents);
contents = NULL;
free(contents);
contents = NULL;
@@
-754,16
+782,16
@@
finish:
}
int cg_is_empty(const char *controller, const char *path, bool ignore_self) {
}
int cg_is_empty(const char *controller, const char *path, bool ignore_self) {
- pid_t pid;
+ pid_t pid
= 0
;
int r;
int r;
- FILE *f;
+ FILE *f
= NULL
;
bool found = false;
assert(controller);
assert(path);
if ((r = cg_enumerate_tasks(controller, path, &f)) < 0)
bool found = false;
assert(controller);
assert(path);
if ((r = cg_enumerate_tasks(controller, path, &f)) < 0)
- return r;
+ return r
== -ENOENT ? 1 : r
;
while ((r = cg_read_pid(f, &pid)) > 0) {
while ((r = cg_read_pid(f, &pid)) > 0) {
@@
-794,7
+822,7
@@
int cg_is_empty_recursive(const char *controller, const char *path, bool ignore_
return r;
if ((r = cg_enumerate_subgroups(controller, path, &d)) < 0)
return r;
if ((r = cg_enumerate_subgroups(controller, path, &d)) < 0)
- return r;
+ return r
== -ENOENT ? 1 : r
;
while ((r = cg_read_subgroup(d, &fn)) > 0) {
char *p = NULL;
while ((r = cg_read_subgroup(d, &fn)) > 0) {
char *p = NULL;
@@
-914,7
+942,7
@@
int cg_fix_path(const char *path, char **result) {
/* First check if it already is a filesystem path */
if (path_is_absolute(path) &&
/* First check if it already is a filesystem path */
if (path_is_absolute(path) &&
- path_startswith(path, "/cgroup") &&
+ path_startswith(path, "/
sys/fs/
cgroup") &&
access(path, F_OK) >= 0) {
if (!(t = strdup(path)))
access(path, F_OK) >= 0) {
if (!(t = strdup(path)))