]> git.pld-linux.org Git - packages/NetworkManager.git/blob - systemd-fallback.patch
7ad09edaad270c56c409b7dd198e263d5be5fe9e
[packages/NetworkManager.git] / systemd-fallback.patch
1 --- NetworkManager-0.9.8.0/configure.ac~        2013-02-21 14:04:19.582661393 +0100
2 +++ NetworkManager-0.9.8.0/configure.ac 2013-02-21 14:23:32.286416661 +0100
3 @@ -283,7 +283,7 @@
4  AM_CONDITIONAL(SESSION_TRACKING_CK, test "$with_session_tracking" = "consolekit")
5  AM_CONDITIONAL(SESSION_TRACKING_SYSTEMD, test "xwith_session_tracking" = "systemd")
6  if test "$with_session_tracking" = "systemd"; then
7 -       PKG_CHECK_MODULES(SYSTEMD_LOGIN, [libsystemd-login])
8 +       PKG_CHECK_MODULES(SYSTEMD_LOGIN, [libsystemd-daemon libsystemd-login])
9         AC_SUBST(SYSTEMD_LOGIN_CFLAGS)
10         AC_SUBST(SYSTEMD_LOGIN_LIBS)
11  fi
12 --- NetworkManager-0.9.10.0/src/nm-session-monitor-systemd.c.orig       2014-07-04 02:44:13.000000000 +0200
13 +++ NetworkManager-0.9.10.0/src/nm-session-monitor-systemd.c    2014-07-05 09:46:03.260229549 +0200
14 @@ -28,6 +28,10 @@
15  #include <glib/gstdio.h>
16  #include <systemd/sd-login.h>
17  #include <stdlib.h>
18 +#include <systemd/sd-daemon.h>
19 +#include <sys/stat.h>
20 +#include <gio/gio.h>
21 +#include "nm-logging.h"
22  
23  #include "nm-session-utils.h"
24  #include "nm-session-monitor.h"
25 @@ -108,10 +112,20 @@ sd_source_new (void)
26         return source;
27  }
28  
29 +/********************************************************************/
30 +
31 +#define CKDB_PATH "/var/run/ConsoleKit/database"
32 +
33  struct _NMSessionMonitor {
34         GObject parent_instance;
35  
36         GSource *sd_source;
37 +
38 +       GKeyFile *database;
39 +       GFileMonitor *database_monitor;
40 +       time_t database_mtime;
41 +       GHashTable *sessions_by_uid;
42 +       GHashTable *sessions_by_user;
43  };
44  
45  struct _NMSessionMonitorClass {
46 @@ -131,6 +145,215 @@ G_DEFINE_TYPE (NMSessionMonitor, nm_sess
47  
48  /* ---------------------------------------------------------------------------------------------------- */
49  
50 +typedef struct {
51 +       char *user;
52 +       uid_t uid;
53 +       gboolean local;
54 +       gboolean active;
55 +} Session;
56 +
57 +static void
58 +session_free (Session *s)
59 +{
60 +       g_free (s->user);
61 +       memset (s, 0, sizeof (Session));
62 +       g_free (s);
63 +}
64 +
65 +static gboolean
66 +check_key (GKeyFile *keyfile, const char *group, const char *key, GError **error)
67 +{
68 +       if (g_key_file_has_key (keyfile, group, key, error))
69 +               return TRUE;
70 +
71 +       if (!error) {
72 +               g_set_error (error,
73 +                                NM_SESSION_MONITOR_ERROR,
74 +                                NM_SESSION_MONITOR_ERROR_MALFORMED_DATABASE,
75 +                                "ConsoleKit database " CKDB_PATH " group '%s' had no '%s' key",
76 +                                group, key);
77 +       }
78 +       return FALSE;
79 +}
80 +
81 +static Session *
82 +session_new (GKeyFile *keyfile, const char *group, GError **error)
83 +{
84 +       GError *local = NULL;
85 +       Session *s;
86 +       const char *uname = NULL;
87 +
88 +       s = g_new0 (Session, 1);
89 +       g_assert (s);
90 +
91 +       s->uid = G_MAXUINT; /* paranoia */
92 +       if (!check_key (keyfile, group, "uid", &local))
93 +               goto error;
94 +       s->uid = (uid_t) g_key_file_get_integer (keyfile, group, "uid", &local);
95 +       if (local)
96 +               goto error;
97 +
98 +       if (!check_key (keyfile, group, "is_active", &local))
99 +               goto error;
100 +       s->active = g_key_file_get_boolean (keyfile, group, "is_active", &local);
101 +       if (local)
102 +               goto error;
103 +
104 +       if (!check_key (keyfile, group, "is_local", &local))
105 +               goto error;
106 +       s->local = g_key_file_get_boolean (keyfile, group, "is_local", &local);
107 +       if (local)
108 +               goto error;
109 +
110 +       if (!nm_session_uid_to_user (s->uid, &uname, error))
111 +               return FALSE;
112 +       s->user = g_strdup (uname);
113 +
114 +       return s;
115 +
116 +error:
117 +       session_free (s);
118 +       g_propagate_error (error, local);
119 +       return NULL;
120 +}
121 +
122 +static void
123 +session_merge (Session *src, Session *dest)
124 +{
125 +       g_return_if_fail (src != NULL);
126 +       g_return_if_fail (dest != NULL);
127 +
128 +       g_warn_if_fail (g_strcmp0 (src->user, dest->user) == 0);
129 +       g_warn_if_fail (src->uid == dest->uid);
130 +
131 +       dest->local = (dest->local || src->local);
132 +       dest->active = (dest->active || src->active);
133 +}
134 +
135 +/********************************************************************/
136 +
137 +static void
138 +free_database (NMSessionMonitor *self)
139 +{
140 +       if (self->database != NULL) {
141 +               g_key_file_free (self->database);
142 +               self->database = NULL;
143 +       }
144 +
145 +       g_hash_table_remove_all (self->sessions_by_uid);
146 +       g_hash_table_remove_all (self->sessions_by_user);
147 +}
148 +
149 +static gboolean
150 +reload_database (NMSessionMonitor *self, GError **error)
151 +{
152 +       struct stat statbuf;
153 +       char **groups = NULL;
154 +       gsize len = 0, i;
155 +       Session *s;
156 +
157 +       free_database (self);
158 +
159 +       errno = 0;
160 +       if (stat (CKDB_PATH, &statbuf) != 0) {
161 +               g_set_error (error,
162 +                            NM_SESSION_MONITOR_ERROR,
163 +                            errno == ENOENT ? NM_SESSION_MONITOR_ERROR_NO_DATABASE : NM_SESSION_MONITOR_ERROR_IO_ERROR,
164 +                            "Error statting file " CKDB_PATH ": %s",
165 +                            strerror (errno));
166 +               goto error;
167 +       }
168 +       self->database_mtime = statbuf.st_mtime;
169 +
170 +       self->database = g_key_file_new ();
171 +       if (!g_key_file_load_from_file (self->database, CKDB_PATH, G_KEY_FILE_NONE, error))
172 +               goto error;
173 +
174 +       groups = g_key_file_get_groups (self->database, &len);
175 +       if (!groups) {
176 +               g_set_error_literal (error,
177 +                                    NM_SESSION_MONITOR_ERROR,
178 +                                    NM_SESSION_MONITOR_ERROR_IO_ERROR,
179 +                                    "Could not load groups from " CKDB_PATH "");
180 +               goto error;
181 +       }
182 +
183 +       for (i = 0; i < len; i++) {
184 +               Session *found;
185 +
186 +               if (!g_str_has_prefix (groups[i], "Session "))
187 +                       continue;
188 +
189 +               s = session_new (self->database, groups[i], error);
190 +               if (!s)
191 +                       goto error;
192 +
193 +               found = g_hash_table_lookup (self->sessions_by_user, (gpointer) s->user);
194 +               if (found) {
195 +                       session_merge (s, found);
196 +                       session_free (s);
197 +               } else {
198 +                       /* Entirely new user */
199 +                       g_hash_table_insert (self->sessions_by_user, (gpointer) s->user, s);
200 +                       g_hash_table_insert (self->sessions_by_uid, GUINT_TO_POINTER (s->uid), s);
201 +               }
202 +       }
203 +
204 +       g_strfreev (groups);
205 +       return TRUE;
206 +
207 +error:
208 +       if (groups)
209 +               g_strfreev (groups);
210 +       free_database (self);
211 +       return FALSE;
212 +}
213 +
214 +static gboolean
215 +ensure_database (NMSessionMonitor *self, GError **error)
216 +{
217 +       gboolean ret = FALSE;
218 +
219 +       if (self->database != NULL) {
220 +               struct stat statbuf;
221 +
222 +               errno = 0;
223 +               if (stat (CKDB_PATH, &statbuf) != 0) {
224 +                       g_set_error (error,
225 +                                    NM_SESSION_MONITOR_ERROR,
226 +                                    errno == ENOENT ? NM_SESSION_MONITOR_ERROR_NO_DATABASE : NM_SESSION_MONITOR_ERROR_IO_ERROR,
227 +                                    "Error statting file " CKDB_PATH " to check timestamp: %s",
228 +                                    strerror (errno));
229 +                       goto out;
230 +               }
231 +
232 +               if (statbuf.st_mtime == self->database_mtime) {
233 +                       ret = TRUE;
234 +                       goto out;
235 +               }
236 +       }
237 +
238 +       ret = reload_database (self, error);
239 +
240 +out:
241 +       return ret;
242 +}
243 +
244 +static void
245 +on_file_monitor_changed (GFileMonitor *    file_monitor,
246 +                         GFile *           file,
247 +                         GFile *           other_file,
248 +                         GFileMonitorEvent event_type,
249 +                         gpointer          user_data)
250 +{
251 +       NMSessionMonitor *self = NM_SESSION_MONITOR (user_data);
252 +
253 +       /* throw away cache */
254 +       free_database (self);
255 +
256 +       g_signal_emit (self, signals[CHANGED_SIGNAL], 0);
257 +}
258 +
259  static gboolean
260  sessions_changed (gpointer user_data)
261  {
262 @@ -144,9 +367,50 @@ sessions_changed (gpointer user_data)
263  static void
264  nm_session_monitor_init (NMSessionMonitor *monitor)
265  {
266 -       monitor->sd_source = sd_source_new ();
267 -       g_source_set_callback (monitor->sd_source, sessions_changed, monitor, NULL);
268 -       g_source_attach (monitor->sd_source, NULL);
269 +       if (sd_booted () > 0) {
270 +               monitor->sd_source = sd_source_new ();
271 +               g_source_set_callback (monitor->sd_source, sessions_changed, monitor, NULL);
272 +               g_source_attach (monitor->sd_source, NULL);
273 +
274 +               monitor->database_monitor = NULL;
275 +               monitor->database = NULL;
276 +       } else {
277 +               monitor->sd_source = NULL;
278 +
279 +               GError *error = NULL;
280 +               GFile *file;
281 +
282 +               /* Sessions-by-user is responsible for destroying the Session objects */
283 +               monitor->sessions_by_user = g_hash_table_new_full (g_str_hash, g_str_equal,
284 +                                                               NULL, (GDestroyNotify) session_free);
285 +               monitor->sessions_by_uid = g_hash_table_new (g_direct_hash, g_direct_equal);
286 +
287 +
288 +               error = NULL;
289 +               if (!ensure_database (monitor, &error)) {
290 +                       /* Ignore the first error if the CK database isn't found yet */
291 +                       if (g_error_matches (error,
292 +                                            NM_SESSION_MONITOR_ERROR,
293 +                                            NM_SESSION_MONITOR_ERROR_NO_DATABASE) == FALSE) {
294 +                               nm_log_err (LOGD_CORE, "Error loading " CKDB_PATH ": %s", error->message);
295 +                       }
296 +                       g_error_free (error);
297 +               }
298 +
299 +               error = NULL;
300 +               file = g_file_new_for_path (CKDB_PATH);
301 +               monitor->database_monitor = g_file_monitor_file (file, G_FILE_MONITOR_NONE, NULL, &error);
302 +               g_object_unref (file);
303 +               if (monitor->database_monitor == NULL) {
304 +                       nm_log_err (LOGD_CORE, "Error monitoring " CKDB_PATH ": %s", error->message);
305 +                       g_error_free (error);
306 +               } else {
307 +                       g_signal_connect (monitor->database_monitor,
308 +                                         "changed",
309 +                                         G_CALLBACK (on_file_monitor_changed),
310 +                                         monitor);
311 +               }
312 +       }
313  }
314  
315  static void
316 @@ -159,6 +423,12 @@ nm_session_monitor_finalize (GObject *ob
317                 g_source_unref (monitor->sd_source);
318         }
319  
320 +       if (monitor->database_monitor != NULL)
321 +               g_object_unref (monitor->database_monitor);
322 +
323 +       if (monitor->database != NULL)
324 +               free_database (monitor);
325 +
326         if (G_OBJECT_CLASS (nm_session_monitor_parent_class)->finalize != NULL)
327                 G_OBJECT_CLASS (nm_session_monitor_parent_class)->finalize (object);
328  }
329 @@ -204,15 +474,36 @@ nm_session_monitor_user_has_session (NMS
330                                       uid_t *out_uid,
331                                       GError **error)
332  {
333 -       uid_t uid;
334 +       if (monitor->sd_source != NULL) {
335 +               uid_t uid;
336  
337 -       if (!nm_session_user_to_uid (username, &uid, error))
338 -               return FALSE;
339 +               if (!nm_session_user_to_uid (username, &uid, error))
340 +                       return FALSE;
341  
342 -       if (out_uid)
343 -               *out_uid = uid;
344 +               if (out_uid)
345 +                       *out_uid = uid;
346  
347 -       return nm_session_monitor_uid_has_session (monitor, uid, NULL, error);
348 +               return nm_session_monitor_uid_has_session (monitor, uid, NULL, error);
349 +       } else {
350 +               Session *s;
351 +
352 +               if (!ensure_database (monitor, error))
353 +                       return FALSE;
354 +
355 +               s = g_hash_table_lookup (monitor->sessions_by_user, (gpointer) username);
356 +               if (!s) {
357 +                       g_set_error (error,
358 +                                    NM_SESSION_MONITOR_ERROR,
359 +                                    NM_SESSION_MONITOR_ERROR_UNKNOWN_USER,
360 +                                    "No session found for user '%s'",
361 +                                    username);
362 +                       return FALSE;
363 +               }
364 +
365 +               if (out_uid)
366 +                       *out_uid = s->uid;
367 +               return TRUE;
368 +       }
369  }
370  
371  gboolean
372 @@ -220,12 +511,31 @@ nm_session_monitor_user_active (NMSessio
373                                  const char *username,
374                                  GError **error)
375  {
376 -       uid_t uid;
377 +       if (monitor->sd_source != NULL) {
378 +               uid_t uid;
379  
380 -       if (!nm_session_user_to_uid (username, &uid, error))
381 -               return FALSE;
382 +               if (!nm_session_user_to_uid (username, &uid, error))
383 +                       return FALSE;
384  
385 -       return nm_session_monitor_uid_active (monitor, uid, error);
386 +               return nm_session_monitor_uid_active (monitor, uid, error);
387 +       } else {
388 +               Session *s;
389 +
390 +               if (!ensure_database (monitor, error))
391 +                       return FALSE;
392 +
393 +               s = g_hash_table_lookup (monitor->sessions_by_user, (gpointer) username);
394 +               if (!s) {
395 +                       g_set_error (error,
396 +                                    NM_SESSION_MONITOR_ERROR,
397 +                                    NM_SESSION_MONITOR_ERROR_UNKNOWN_USER,
398 +                                    "No session found for user '%s'",
399 +                                    username);
400 +                       return FALSE;
401 +               }
402 +
403 +               return s->active;
404 +       }
405  }
406  
407  gboolean
408 @@ -234,19 +544,40 @@ nm_session_monitor_uid_has_session (NMSe
409                                      const char **out_user,
410                                      GError **error)
411  {
412 -       int num_sessions;
413 +       if (monitor->sd_source != NULL) {
414 +               int num_sessions;
415  
416 -       if (!nm_session_uid_to_user (uid, out_user, error))
417 -               return FALSE;
418 +               if (!nm_session_uid_to_user (uid, out_user, error))
419 +                       return FALSE;
420  
421 -       /* Get all sessions (including inactive ones) for the user */
422 -       num_sessions = sd_uid_get_sessions (uid, 0, NULL);
423 -       if (num_sessions < 0) {
424 -               nm_log_warn (LOGD_CORE, "Failed to get systemd sessions for uid %d: %d",
425 -                            uid, num_sessions);
426 -               return FALSE;
427 +               /* Get all sessions (including inactive ones) for the user */
428 +               num_sessions = sd_uid_get_sessions (uid, 0, NULL);
429 +               if (num_sessions < 0) {
430 +                       nm_log_warn (LOGD_CORE, "Failed to get systemd sessions for uid %d: %d",
431 +                                    uid, num_sessions);
432 +                       return FALSE;
433 +               }
434 +               return num_sessions > 0;
435 +       } else {
436 +               Session *s;
437 +
438 +               if (!ensure_database (monitor, error))
439 +                       return FALSE;
440 +
441 +               s = g_hash_table_lookup (monitor->sessions_by_uid, GUINT_TO_POINTER (uid));
442 +               if (!s) {
443 +                       g_set_error (error,
444 +                                    NM_SESSION_MONITOR_ERROR,
445 +                                    NM_SESSION_MONITOR_ERROR_UNKNOWN_USER,
446 +                                    "No session found for uid %d",
447 +                                    uid);
448 +                       return FALSE;
449 +               }
450 +
451 +               if (out_user)
452 +                       *out_user = s->user;
453 +               return TRUE;
454         }
455 -       return num_sessions > 0;
456  }
457  
458  gboolean
459 @@ -254,14 +585,33 @@ nm_session_monitor_uid_active (NMSession
460                                 uid_t uid,
461                                 GError **error)
462  {
463 -       int num_sessions;
464 +       if (monitor->sd_source != NULL) {
465 +               int num_sessions;
466  
467 -       /* Get active sessions for the user */
468 -       num_sessions = sd_uid_get_sessions (uid, 1, NULL);
469 -       if (num_sessions < 0) {
470 -               nm_log_warn (LOGD_CORE, "Failed to get active systemd sessions for uid %d: %d",
471 -                            uid, num_sessions);
472 -               return FALSE;
473 +               /* Get active sessions for the user */
474 +               num_sessions = sd_uid_get_sessions (uid, 1, NULL);
475 +               if (num_sessions < 0) {
476 +                       nm_log_warn (LOGD_CORE, "Failed to get active systemd sessions for uid %d: %d",
477 +                                    uid, num_sessions);
478 +                       return FALSE;
479 +               }
480 +               return num_sessions > 0;
481 +       } else {
482 +               Session *s;
483 +
484 +               if (!ensure_database (monitor, error))
485 +                       return FALSE;
486 +
487 +               s = g_hash_table_lookup (monitor->sessions_by_uid, GUINT_TO_POINTER (uid));
488 +               if (!s) {
489 +                       g_set_error (error,
490 +                                    NM_SESSION_MONITOR_ERROR,
491 +                                    NM_SESSION_MONITOR_ERROR_UNKNOWN_USER,
492 +                                    "No session found for uid '%d'",
493 +                                    uid);
494 +                       return FALSE;
495 +               }
496 +
497 +               return s->active;
498         }
499 -       return num_sessions > 0;
500  }
501 --- NetworkManager-0.9.10.0/src/nm-sleep-monitor-systemd.c.orig 2014-07-04 02:44:13.000000000 +0200
502 +++ NetworkManager-0.9.10.0/src/nm-sleep-monitor-systemd.c      2014-07-05 09:49:32.623554089 +0200
503 @@ -26,6 +26,7 @@
504  #include <glib/gi18n.h>
505  #include <gio/gio.h>
506  #include <gio/gunixfdlist.h>
507 +#include <systemd/sd-daemon.h>
508  
509  #include "nm-logging.h"
510  #include "nm-dbus-manager.h"
511 @@ -36,12 +37,15 @@
512  #define SD_PATH              "/org/freedesktop/login1"
513  #define SD_INTERFACE         "org.freedesktop.login1.Manager"
514  
515 +#define UPOWER_DBUS_SERVICE "org.freedesktop.UPower"
516  
517  struct _NMSleepMonitor {
518         GObject parent_instance;
519  
520         GDBusProxy *sd_proxy;
521         gint inhibit_fd;
522 +       
523 +       DBusGProxy *upower_proxy;
524  };
525  
526  struct _NMSleepMonitorClass {
527 @@ -63,6 +67,20 @@ G_DEFINE_TYPE (NMSleepMonitor, nm_sleep_
528  
529  /********************************************************************/
530  
531 +static void
532 +upower_sleeping_cb (DBusGProxy *proxy, gpointer user_data)
533 +{
534 +        nm_log_dbg (LOGD_SUSPEND, "Received UPower sleeping signal");
535 +        g_signal_emit (user_data, signals[SLEEPING], 0);
536 +}
537 +
538 +static void
539 +upower_resuming_cb (DBusGProxy *proxy, gpointer user_data)
540 +{
541 +        nm_log_dbg (LOGD_SUSPEND, "Received UPower resuming signal");
542 +        g_signal_emit (user_data, signals[RESUMING], 0);
543 +}
544 +
545  static gboolean
546  drop_inhibitor (NMSleepMonitor *self)
547  {
548 @@ -164,9 +182,34 @@ sleep_setup (NMSleepMonitor *self)
549  static void
550  nm_sleep_monitor_init (NMSleepMonitor *self)
551  {
552 -       self->inhibit_fd = -1;
553 -       sleep_setup (self);
554 -       take_inhibitor (self);
555 +       if (sd_booted () > 0) {
556 +               self->inhibit_fd = -1;
557 +               sleep_setup (self);
558 +               take_inhibitor (self);
559 +       } else {
560 +               NMDBusManager *dbus_mgr;
561 +               DBusGConnection *bus;
562 +
563 +               dbus_mgr = nm_dbus_manager_get ();
564 +        bus = nm_dbus_manager_get_connection (dbus_mgr);
565 +        self->upower_proxy = dbus_g_proxy_new_for_name (bus,
566 +                                                        UPOWER_DBUS_SERVICE,
567 +                                                        "/org/freedesktop/UPower",
568 +                                                        "org.freedesktop.UPower");
569 +        if (self->upower_proxy) {
570 +                       dbus_g_proxy_add_signal (self->upower_proxy, "Sleeping", G_TYPE_INVALID);
571 +                       dbus_g_proxy_connect_signal (self->upower_proxy, "Sleeping",
572 +                                                                                G_CALLBACK (upower_sleeping_cb),
573 +                                                                                self, NULL);
574 +
575 +                       dbus_g_proxy_add_signal (self->upower_proxy, "Resuming", G_TYPE_INVALID);
576 +                       dbus_g_proxy_connect_signal (self->upower_proxy, "Resuming",
577 +                                                                                G_CALLBACK (upower_resuming_cb),
578 +                                                                                self, NULL);
579 +        } else
580 +                               nm_log_warn (LOGD_SUSPEND, "could not initialize UPower D-Bus proxy");
581 +        g_object_unref (dbus_mgr);
582 +       }
583  }
584  
585  static void
586 @@ -174,9 +217,14 @@ finalize (GObject *object)
587  {
588         NMSleepMonitor *self = NM_SLEEP_MONITOR (object);
589  
590 -       drop_inhibitor (self);
591 -       if (self->sd_proxy)
592 -               g_object_unref (self->sd_proxy);
593 +       if (sd_booted () > 0) {
594 +               drop_inhibitor (self);
595 +               if (self->sd_proxy)
596 +                       g_object_unref (self->sd_proxy);
597 +       } else {
598 +               if (self->upower_proxy)
599 +                       g_object_unref (self->upower_proxy);
600 +       }
601  
602         if (G_OBJECT_CLASS (nm_sleep_monitor_parent_class)->finalize != NULL)
603                 G_OBJECT_CLASS (nm_sleep_monitor_parent_class)->finalize (object);
This page took 0.066722 seconds and 2 git commands to generate.