diff options
author | Yu Watanabe <watanabe.yu+github@gmail.com> | 2022-12-20 19:09:58 +0100 |
---|---|---|
committer | Luca Boccassi <bluca@debian.org> | 2023-01-23 12:30:03 +0100 |
commit | 8589823f9d9187bde27ab41a157f07afd59deaad (patch) | |
tree | 79ef0be3cc5d6919b9a84d966e99b1bf0f766a7d /src/locale | |
parent | locale: make errors in writing files not critical (diff) | |
download | systemd-8589823f9d9187bde27ab41a157f07afd59deaad.tar.xz systemd-8589823f9d9187bde27ab41a157f07afd59deaad.zip |
locale: also save XKB settings to vconsole.conf
Closes #24228.
Replaces #25412.
Diffstat (limited to 'src/locale')
-rw-r--r-- | src/locale/localed-util.c | 51 | ||||
-rw-r--r-- | src/locale/localed-util.h | 1 | ||||
-rw-r--r-- | src/locale/localed.c | 14 | ||||
-rw-r--r-- | src/locale/test-localed-util.c | 2 |
4 files changed, 54 insertions, 14 deletions
diff --git a/src/locale/localed-util.c b/src/locale/localed-util.c index 99f76a14bc..003663054c 100644 --- a/src/locale/localed-util.c +++ b/src/locale/localed-util.c @@ -149,6 +149,7 @@ static void context_clear_x11(Context *c) { assert(c); x11_context_clear(&c->x11_from_xorg); + x11_context_clear(&c->x11_from_vc); } static void context_clear_vconsole(Context *c) { @@ -175,6 +176,9 @@ void context_clear(Context *c) { static X11Context *context_get_x11_context(Context *c) { assert(c); + if (!x11_context_isempty(&c->x11_from_vc)) + return &c->x11_from_vc; + if (!x11_context_isempty(&c->x11_from_xorg)) return &c->x11_from_xorg; @@ -182,7 +186,8 @@ static X11Context *context_get_x11_context(Context *c) { } X11Context *context_get_x11_context_safe(Context *c) { - return &ASSERT_PTR(c)->x11_from_xorg; + assert(c); + return context_get_x11_context(c) ?: &c->x11_from_vc; } int locale_read_data(Context *c, sd_bus_message *m) { @@ -233,10 +238,15 @@ int vconsole_read_data(Context *c, sd_bus_message *m) { c->vc_stat = st; context_clear_vconsole(c); + x11_context_clear(&c->x11_from_vc); return parse_env_file_fd(fd, "/etc/vconsole.conf", "KEYMAP", &c->vc_keymap, - "KEYMAP_TOGGLE", &c->vc_keymap_toggle); + "KEYMAP_TOGGLE", &c->vc_keymap_toggle, + "XKB_LAYOUT", &c->x11_from_vc.layout, + "XKB_MODEL", &c->x11_from_vc.model, + "XKB_VARIANT", &c->x11_from_vc.variant, + "XKB_OPTIONS", &c->x11_from_vc.options); } int x11_read_data(Context *c, sd_bus_message *m) { @@ -248,6 +258,15 @@ int x11_read_data(Context *c, sd_bus_message *m) { assert(c); + r = vconsole_read_data(c, m); + if (r < 0) + return r; + + if (!x11_context_isempty(&c->x11_from_vc)) { + log_debug("XKB settings loaded from vconsole.conf, not reading xorg.conf.d/00-keyboard.conf."); + return 0; + } + /* Do not try to re-read the file within single bus operation. */ if (m) { if (m == c->x11_cache) @@ -345,10 +364,18 @@ int x11_read_data(Context *c, sd_bus_message *m) { int vconsole_write_data(Context *c) { _cleanup_strv_free_ char **l = NULL; + const X11Context *xc; int r; assert(c); + xc = context_get_x11_context(c); + + /* If the X11 context is from xorg.conf, then sync one from vconsole.conf with it. */ + r = x11_context_copy(&c->x11_from_vc, xc); + if (r < 0) + return r; + r = load_env_file(NULL, "/etc/vconsole.conf", &l); if (r < 0 && r != -ENOENT) return r; @@ -361,6 +388,22 @@ int vconsole_write_data(Context *c) { if (r < 0) return r; + r = strv_env_assign(&l, "XKB_LAYOUT", xc ? empty_to_null(xc->layout) : NULL); + if (r < 0) + return r; + + r = strv_env_assign(&l, "XKB_MODEL", xc ? empty_to_null(xc->model) : NULL); + if (r < 0) + return r; + + r = strv_env_assign(&l, "XKB_VARIANT", xc ? empty_to_null(xc->variant) : NULL); + if (r < 0) + return r; + + r = strv_env_assign(&l, "XKB_OPTIONS", xc ? empty_to_null(xc->options) : NULL); + if (r < 0) + return r; + if (strv_isempty(l)) { if (unlink("/etc/vconsole.conf") < 0) return errno == ENOENT ? 0 : -errno; @@ -493,6 +536,10 @@ int vconsole_convert_to_x11(Context *c) { assert(c); + /* If Context.x11_from_vc is empty, then here we update Context.x11_from_xorg, as the caller may + * already have been called context_get_x11_context() or _safe(), and otherwise the caller's + * X11Context may be outdated. The updated context will be copied to Context.x11_from_vc in + * vconsole_write_data() if necessary. */ xc = context_get_x11_context_safe(c); if (isempty(c->vc_keymap)) { diff --git a/src/locale/localed-util.h b/src/locale/localed-util.h index 36c6d903f2..a3e763f850 100644 --- a/src/locale/localed-util.h +++ b/src/locale/localed-util.h @@ -22,6 +22,7 @@ typedef struct Context { sd_bus_message *x11_cache; struct stat x11_stat; X11Context x11_from_xorg; + X11Context x11_from_vc; sd_bus_message *vc_cache; struct stat vc_stat; diff --git a/src/locale/localed.c b/src/locale/localed.c index 0312963f3e..68c014fd47 100644 --- a/src/locale/localed.c +++ b/src/locale/localed.c @@ -621,12 +621,6 @@ static int method_set_x11_keyboard(sd_bus_message *m, void *userdata, sd_bus_err return log_oom(); if (convert) { - r = vconsole_read_data(c, m); - if (r < 0) { - log_error_errno(r, "Failed to read virtual console keymap data: %m"); - return sd_bus_error_set_errnof(error, r, "Failed to read virtual console keymap data: %m"); - } - r = x11_convert_to_vconsole(c); if (r < 0) { log_error_errno(r, "Failed to convert keymap data: %m"); @@ -637,11 +631,9 @@ static int method_set_x11_keyboard(sd_bus_message *m, void *userdata, sd_bus_err convert = r > 0; } - if (convert) { - r = vconsole_write_data(c); - if (r < 0) - log_warning_errno(r, "Failed to update vconsole.conf, ignoring: %m"); - } + r = vconsole_write_data(c); + if (r < 0) + log_warning_errno(r, "Failed to update vconsole.conf, ignoring: %m"); r = x11_write_data(c); if (r < 0) diff --git a/src/locale/test-localed-util.c b/src/locale/test-localed-util.c index d99ccba748..3d96b3aa85 100644 --- a/src/locale/test-localed-util.c +++ b/src/locale/test-localed-util.c @@ -72,7 +72,7 @@ TEST(find_legacy_keymap) { TEST(vconsole_convert_to_x11) { _cleanup_(context_clear) Context c = {}; - X11Context *xc = &c.x11_from_xorg; + X11Context *xc = &c.x11_from_vc; log_info("/* test emptying first (:) */"); assert_se(free_and_strdup(&xc->layout, "foo") >= 0); |