chiark / gitweb /
shared: move fdset.c from core/ to shared/ since it is used by more than the core now
[elogind.git] / src / core / manager.c
index 1ddd8bae62497407e555bbe4cfa47a03f507754e..a3839e1538e29cf61ac4613871f07b650ca49e3c 100644 (file)
@@ -706,6 +706,16 @@ int manager_startup(Manager *m, FILE *serialization, FDSet *fds) {
                         r = q;
         }
 
+        /* Any fds left? Find some unit which wants them. This is
+         * useful to allow container managers to pass some file
+         * descriptors to us pre-initialized. This enables
+         * socket-based activation of entire containers. */
+        if (fdset_size(fds) > 0) {
+                q = manager_distribute_fds(m, fds);
+                if (q < 0)
+                        r = q;
+        }
+
         /* Third, fire things up! */
         q = manager_coldplug(m);
         if (q < 0)
@@ -1166,7 +1176,8 @@ static int manager_process_signal_fd(Manager *m) {
         assert(m);
 
         for (;;) {
-                if ((n = read(m->signal_watch.fd, &sfsi, sizeof(sfsi))) != sizeof(sfsi)) {
+                n = read(m->signal_watch.fd, &sfsi, sizeof(sfsi));
+                if (n != sizeof(sfsi)) {
 
                         if (n >= 0)
                                 return -EIO;
@@ -1807,7 +1818,8 @@ int manager_open_serialization(Manager *m, FILE **_f) {
         log_debug("Serializing state to %s", path);
         free(path);
 
-        if (!(f = fdopen(fd, "w+")))
+        f = fdopen(fd, "w+");
+        if (!f)
                 return -errno;
 
         *_f = f;
@@ -1965,7 +1977,8 @@ int manager_deserialize(Manager *m, FILE *f, FDSet *fds) {
                 if ((r = manager_load_unit(m, strstrip(name), NULL, NULL, &u)) < 0)
                         goto finish;
 
-                if ((r = unit_deserialize(u, f, fds)) < 0)
+                r = unit_deserialize(u, f, fds);
+                if (r < 0)
                         goto finish;
         }
 
@@ -1981,6 +1994,28 @@ finish:
         return r;
 }
 
+int manager_distribute_fds(Manager *m, FDSet *fds) {
+        Unit *u;
+        Iterator i;
+        int r;
+
+        assert(m);
+
+        HASHMAP_FOREACH(u, m->units, i) {
+
+                if (fdset_size(fds) <= 0)
+                        break;
+
+                if (UNIT_VTABLE(u)->distribute_fds) {
+                        r = UNIT_VTABLE(u)->distribute_fds(u, fds);
+                        if (r < 0)
+                                return r;
+                }
+        }
+
+        return 0;
+}
+
 int manager_reload(Manager *m) {
         int r, q;
         FILE *f;