From 2b590e135f53a1bd3e771bdc555f7bf28c4cd232 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 3 Mar 2011 23:03:26 +0100 Subject: [PATCH] readahead: disable collector automatically on read-only media --- TODO | 2 -- src/readahead-collect.c | 10 +++++++++- src/readahead-common.c | 35 +++++++++++++++++++++++++++++++++++ src/readahead-common.h | 1 + src/readahead-replay.c | 5 ++++- 5 files changed, 49 insertions(+), 4 deletions(-) diff --git a/TODO b/TODO index b7c1bacb5..848ea2138 100644 --- a/TODO +++ b/TODO @@ -40,8 +40,6 @@ Features: * invoke vhangup() before and after invoking getty -* skip readahead on physically r/o media - * support "auto" and "comment=systemd.automount" at the same time for an fstab entry * Make use of UnknownInterface, UnknownObject diff --git a/src/readahead-collect.c b/src/readahead-collect.c index 330d10776..0970b5841 100644 --- a/src/readahead-collect.c +++ b/src/readahead-collect.c @@ -639,6 +639,7 @@ static int parse_argv(int argc, char *argv[]) { int main(int argc, char *argv[]) { int r; + const char *root; log_set_target(LOG_TARGET_SYSLOG_OR_KMSG); log_parse_environment(); @@ -647,6 +648,13 @@ int main(int argc, char *argv[]) { if ((r = parse_argv(argc, argv)) <= 0) return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS; + root = optind < argc ? argv[optind] : "/"; + + if (fs_on_read_only(root) > 0) { + log_info("Disabling readahead collector due to read-only media."); + return 0; + } + if (!enough_ram()) { log_info("Disabling readahead collector due to low memory."); return 0; @@ -663,7 +671,7 @@ int main(int argc, char *argv[]) { shared->collect = getpid(); __sync_synchronize(); - if (collect(optind < argc ? argv[optind] : "/") < 0) + if (collect(root) < 0) return 1; return 0; diff --git a/src/readahead-common.c b/src/readahead-common.c index 85e3227f6..e991dfd05 100644 --- a/src/readahead-common.c +++ b/src/readahead-common.c @@ -114,6 +114,41 @@ finish: return b; } +int fs_on_read_only(const char *p) { + struct stat st; + struct udev *udev = NULL; + struct udev_device *udev_device = NULL; + bool b = false; + const char *read_only; + + assert(p); + + if (stat(p, &st) < 0) + return -errno; + + if (major(st.st_dev) == 0) + return false; + + if (!(udev = udev_new())) + return -ENOMEM; + + if (!(udev_device = udev_device_new_from_devnum(udev, 'b', st.st_dev))) + goto finish; + + if ((read_only = udev_device_get_sysattr_value(udev_device, "ro"))) + if ((b = streq(read_only, "1"))) + goto finish; + +finish: + if (udev_device) + udev_device_unref(udev_device); + + if (udev) + udev_unref(udev); + + return b; +} + bool enough_ram(void) { struct sysinfo si; diff --git a/src/readahead-common.h b/src/readahead-common.h index 964ca1f2f..167df316d 100644 --- a/src/readahead-common.h +++ b/src/readahead-common.h @@ -32,6 +32,7 @@ int file_verify(int fd, const char *fn, off_t file_size_max, struct stat *st); int fs_on_ssd(const char *p); +int fs_on_read_only(const char *p); bool enough_ram(void); diff --git a/src/readahead-replay.c b/src/readahead-replay.c index cd89654f9..3bea9295f 100644 --- a/src/readahead-replay.c +++ b/src/readahead-replay.c @@ -333,6 +333,7 @@ static int parse_argv(int argc, char *argv[]) { int main(int argc, char*argv[]) { int r; + const char *root; log_set_target(LOG_TARGET_SYSLOG_OR_KMSG); log_parse_environment(); @@ -341,6 +342,8 @@ int main(int argc, char*argv[]) { if ((r = parse_argv(argc, argv)) <= 0) return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS; + root = optind < argc ? argv[optind] : "/"; + if (!enough_ram()) { log_info("Disabling readahead replay due to low memory."); return 0; @@ -357,7 +360,7 @@ int main(int argc, char*argv[]) { shared->replay = getpid(); __sync_synchronize(); - if (replay(optind < argc ? argv[optind] : "/") < 0) + if (replay(root) < 0) return 1; return 0; -- 2.30.2