[systemd-devel] [PATCH] timedated: gather timezone from /etc/localtime sym target
Shawn Landen
shawnlandden at gmail.com
Mon Aug 6 17:31:03 PDT 2012
keep other method for now, consider dropping later.
Supporting relative links here could be problematic as timezones in
/usr/share/zoneinfo are often themselves symlinks (and symlinks to
symlinks), so this implamentation only only support absolute links.
---
src/timedate/timedated.c | 28 ++++++++++++++++++++++++++++
1 file changed, 28 insertions(+)
diff --git a/src/timedate/timedated.c b/src/timedate/timedated.c
index 09fd808..456e409 100644
--- a/src/timedate/timedated.c
+++ b/src/timedate/timedated.c
@@ -24,6 +24,7 @@
#include <errno.h>
#include <string.h>
#include <unistd.h>
+#include <sys/stat.h>
#include "util.h"
#include "strv.h"
@@ -174,9 +175,35 @@ static void verify_timezone(void) {
static int read_data(void) {
int r;
+ struct stat st;
free_data();
+ r = lstat("/etc/localtime", &st);
+ if (r < 0) {
+ log_warning("lstat() of %s failed: %m", "/etc/localtime");
+ } else if (!S_ISLNK(st.st_mode)) {
+ log_warning("/etc/localtime should be an absolute symlink to a timezone data file in /usr/share/zoneinfo/");
+ } else {
+ char *t;
+
+ r = readlink_malloc("/etc/localtime", &t);
+ if (r < 0) {
+ log_warning("Failed to get target of %s: %m", "/etc/localtime");
+ } else if (!startswith(t, "/usr/share/zoneinfo/")) {
+ log_warning("/etc/localtime should be an absolute symlink to a timezone data file in /usr/share/zoneinfo/");
+ } else {
+ tz.zone = strdup(t + strlen("/usr/share/zoneinfo/"));
+ free(t);
+ if (!tz.zone)
+ return log_oom();
+
+ goto have_timezone;
+ }
+
+ free(t);
+ }
+
r = read_one_line_file("/etc/timezone", &tz.zone);
if (r < 0) {
if (r != -ENOENT)
@@ -192,6 +219,7 @@ static int read_data(void) {
#endif
}
+have_timezone:
if (isempty(tz.zone)) {
free(tz.zone);
tz.zone = NULL;
--
1.7.10.4
More information about the systemd-devel
mailing list