sd-login: return size of arrays as return value in functions that generate an array
authorLennart Poettering <lennart@poettering.net>
Fri, 29 Jul 2011 01:08:49 +0000 (03:08 +0200)
committerLennart Poettering <lennart@poettering.net>
Fri, 29 Jul 2011 01:14:06 +0000 (03:14 +0200)
src/sd-login.c
src/sd-login.h
src/test-login.c
src/util.c

index d44a1fc..2489d78 100644 (file)
@@ -251,9 +251,6 @@ static int uid_get_array(uid_t uid, const char *variable, char ***array) {
         char **a;
         int r;
 
-        if (!array)
-                return -EINVAL;
-
         if (asprintf(&p, "/run/systemd/users/%lu", (unsigned long) uid) < 0)
                 return -ENOMEM;
 
@@ -266,7 +263,8 @@ static int uid_get_array(uid_t uid, const char *variable, char ***array) {
                 free(s);
 
                 if (r == -ENOENT) {
-                        *array = NULL;
+                        if (array)
+                                *array = NULL;
                         return 0;
                 }
 
@@ -274,7 +272,8 @@ static int uid_get_array(uid_t uid, const char *variable, char ***array) {
         }
 
         if (!s) {
-                *array = NULL;
+                if (array)
+                        *array = NULL;
                 return 0;
         }
 
@@ -284,8 +283,15 @@ static int uid_get_array(uid_t uid, const char *variable, char ***array) {
         if (!a)
                 return -ENOMEM;
 
-        *array = a;
-        return 0;
+        strv_uniq(a);
+        r = strv_length(a);
+
+        if (array)
+                *array = a;
+        else
+                strv_free(a);
+
+        return r;
 }
 
 _public_ int sd_uid_get_sessions(uid_t uid, int require_active, char ***sessions) {
@@ -445,9 +451,6 @@ _public_ int sd_seat_get_sessions(const char *seat, char ***sessions, uid_t **ui
         if (!seat)
                 return -EINVAL;
 
-        if (!sessions && !uids)
-                return -EINVAL;
-
         p = strappend("/run/systemd/seats/", seat);
         if (!p)
                 return -ENOMEM;
@@ -464,7 +467,7 @@ _public_ int sd_seat_get_sessions(const char *seat, char ***sessions, uid_t **ui
                 return r;
         }
 
-        if (sessions && s) {
+        if (s) {
                 a = strv_split(s, " ");
                 if (!a) {
                         free(s);
@@ -510,8 +513,12 @@ _public_ int sd_seat_get_sessions(const char *seat, char ***sessions, uid_t **ui
 
         free(t);
 
+        r = strv_length(a);
+
         if (sessions)
                 *sessions = a;
+        else
+                strv_free(a);
 
         if (uids)
                 *uids = b;
@@ -519,7 +526,7 @@ _public_ int sd_seat_get_sessions(const char *seat, char ***sessions, uid_t **ui
         if (n_uids)
                 *n_uids = n;
 
-        return 0;
+        return r;
 }
 
 _public_ int sd_seat_can_multi_session(const char *seat) {
@@ -553,18 +560,10 @@ _public_ int sd_seat_can_multi_session(const char *seat) {
 }
 
 _public_ int sd_get_seats(char ***seats) {
-
-        if (!seats)
-                return -EINVAL;
-
         return get_files_in_directory("/run/systemd/seats/", seats);
 }
 
 _public_ int sd_get_sessions(char ***sessions) {
-
-        if (!sessions)
-                return -EINVAL;
-
         return get_files_in_directory("/run/systemd/sessions/", sessions);
 }
 
@@ -574,9 +573,6 @@ _public_ int sd_get_uids(uid_t **users) {
         unsigned n = 0;
         uid_t *l = NULL;
 
-        if (!users)
-                return -EINVAL;
-
         d = opendir("/run/systemd/users/");
         for (;;) {
                 struct dirent buffer, *de;
@@ -601,30 +597,34 @@ _public_ int sd_get_uids(uid_t **users) {
                 if (k < 0)
                         continue;
 
-                if ((unsigned) r >= n) {
-                        uid_t *t;
+                if (users) {
+                        if ((unsigned) r >= n) {
+                                uid_t *t;
 
-                        n = MAX(16, 2*r);
-                        t = realloc(l, sizeof(uid_t) * n);
-                        if (!t) {
-                                r = -ENOMEM;
-                                goto finish;
-                        }
+                                n = MAX(16, 2*r);
+                                t = realloc(l, sizeof(uid_t) * n);
+                                if (!t) {
+                                        r = -ENOMEM;
+                                        goto finish;
+                                }
 
-                        l = t;
-                }
+                                l = t;
+                        }
 
-                assert((unsigned) r < n);
-                l[r++] = uid;
+                        assert((unsigned) r < n);
+                        l[r++] = uid;
+                } else
+                        r++;
         }
 
 finish:
         if (d)
                 closedir(d);
 
-        if (r >= 0)
-                *users = l;
-        else
+        if (r >= 0) {
+                if (users)
+                        *users = l;
+        } else
                 free(l);
 
         return r;
index 1623a7d..7102eb8 100644 (file)
@@ -32,7 +32,8 @@
  *
  * Free the data we return with libc free().
  *
- * We return error codes as negative errno, kernel-style.
+ * We return error codes as negative errno, kernel-style. 0 or
+ * positive on success.
  *
  * These functions access data in /proc, /sys/fs/cgroup and /run. All
  * of these are virtual file systems, hence the accesses are
@@ -59,12 +60,14 @@ int sd_uid_get_state(uid_t uid, char**state);
  * look for active sessions only. */
 int sd_uid_is_on_seat(uid_t uid, int require_active, const char *seat);
 
-/* Return sessions of user. If require_active is true will look
- * for active sessions only. */
+/* Return sessions of user. If require_active is true will look for
+ * active sessions only. Returns number of sessions as return
+ * value. If sessions is NULL will just return number of sessions. */
 int sd_uid_get_sessions(uid_t uid, int require_active, char ***sessions);
 
 /* Return seats of user is on. If require_active is true will look for
- * active seats only.  */
+ * active seats only.  Returns number of seats. If seats is NULL will
+ * just return number of seats.*/
 int sd_uid_get_seats(uid_t uid, int require_active, char ***seats);
 
 /* Return 1 if the session is a active */
@@ -79,19 +82,24 @@ int sd_session_get_seat(const char *session, char **seat);
 /* Return active session and user of seat */
 int sd_seat_get_active(const char *seat, char **session, uid_t *uid);
 
-/* Return sessions and users on seat */
+/* Return sessions and users on seat. Returns number of sessions as
+ * return value. If sessions is NULL returs only the number of
+ * sessions. */
 int sd_seat_get_sessions(const char *seat, char ***sessions, uid_t **uid, unsigned *n_uids);
 
 /* Return whether the seat is multi-session capable */
 int sd_seat_can_multi_session(const char *seat);
 
-/* Get all seats */
+/* Get all seats, store in *seats. Returns the number of seats. If
+ * seats is NULL only returns number of seats. */
 int sd_get_seats(char ***seats);
 
-/* Get all sessions */
+/* Get all sessions, store in *seessions. Returns the number of
+ * sessions. If sessions is NULL only returns number of sessions. */
 int sd_get_sessions(char ***sessions);
 
-/* Get all logged in users */
+/* Get all logged in users, store in *users. Returns the number of
+ * users. If users is NULL only returns the number of users. */
 int sd_get_uids(uid_t **users);
 
 /* Monitor object */
index 9cd9c27..59b46a1 100644 (file)
@@ -48,18 +48,24 @@ int main(int argc, char* argv[]) {
 
         r = sd_uid_get_sessions(u2, false, &sessions);
         assert_se(r >= 0);
+        assert_se(r == (int) strv_length(sessions));
         assert_se(t = strv_join(sessions, ", "));
         strv_free(sessions);
         printf("sessions = %s\n", t);
         free(t);
 
+        assert_se(r == sd_uid_get_sessions(u2, false, NULL));
+
         r = sd_uid_get_seats(u2, false, &seats);
         assert_se(r >= 0);
+        assert_se(r == (int) strv_length(seats));
         assert_se(t = strv_join(seats, ", "));
         strv_free(seats);
         printf("seats = %s\n", t);
         free(t);
 
+        assert_se(r == sd_uid_get_seats(u2, false, NULL));
+
         r = sd_session_is_active(session);
         assert_se(r >= 0);
         printf("active = %s\n", yes_no(r));
@@ -88,7 +94,10 @@ int main(int argc, char* argv[]) {
         printf("session2 = %s\n", session2);
         printf("uid2 = %lu\n", (unsigned long) u2);
 
-        assert_se(sd_seat_get_sessions(seat, &sessions, &uids, &n) >= 0);
+        r = sd_seat_get_sessions(seat, &sessions, &uids, &n);
+        assert_se(r >= 0);
+        printf("n_sessions = %i\n", r);
+        assert_se(r == (int) strv_length(sessions));
         assert_se(t = strv_join(sessions, ", "));
         strv_free(sessions);
         printf("sessions = %s\n", t);
@@ -99,23 +108,35 @@ int main(int argc, char* argv[]) {
         printf("\n");
         free(uids);
 
+        assert_se(sd_seat_get_sessions(seat, NULL, NULL, NULL) == r);
+
         free(session);
         free(state);
         free(session2);
         free(seat);
 
-        assert_se(sd_get_seats(&seats) >= 0);
+        r = sd_get_seats(&seats);
+        assert_se(r >= 0);
+        assert_se(r == (int) strv_length(seats));
         assert_se(t = strv_join(seats, ", "));
         strv_free(seats);
+        printf("n_seats = %i\n", r);
         printf("seats = %s\n", t);
         free(t);
 
-        assert_se(sd_get_sessions(&sessions) >= 0);
+        assert_se(sd_get_seats(NULL) == r);
+
+        r = sd_get_sessions(&sessions);
+        assert_se(r >= 0);
+        assert_se(r == (int) strv_length(sessions));
         assert_se(t = strv_join(sessions, ", "));
         strv_free(sessions);
+        printf("n_sessions = %i\n", r);
         printf("sessions = %s\n", t);
         free(t);
 
+        assert_se(sd_get_sessions(NULL) == r);
+
         r = sd_get_uids(&uids);
         assert_se(r >= 0);
 
@@ -123,25 +144,27 @@ int main(int argc, char* argv[]) {
         for (k = 0; k < r; k++)
                 printf(" %lu", (unsigned long) uids[k]);
         printf("\n");
-
         free(uids);
 
-        r = sd_login_monitor_new("session", &m);
-        assert_se(r >= 0);
+        printf("n_uids = %i\n", r);
+        assert_se(sd_get_uids(NULL) == r);
+
+        /* r = sd_login_monitor_new("session", &m); */
+        /* assert_se(r >= 0); */
 
-        zero(pollfd);
-        pollfd.fd = sd_login_monitor_get_fd(m);
-        pollfd.events = POLLIN;
+        /* zero(pollfd); */
+        /* pollfd.fd = sd_login_monitor_get_fd(m); */
+        /* pollfd.events = POLLIN; */
 
-        for (n = 0; n < 5; n++) {
-                r = poll(&pollfd, 1, -1);
-                assert_se(r >= 0);
+        /* for (n = 0; n < 5; n++) { */
+        /*         r = poll(&pollfd, 1, -1); */
+        /*         assert_se(r >= 0); */
 
-                sd_login_monitor_flush(m);
-                printf("Wake!\n");
-        }
+        /*         sd_login_monitor_flush(m); */
+        /*         printf("Wake!\n"); */
+        /* } */
 
-        sd_login_monitor_unref(m);
+        /* sd_login_monitor_unref(m); */
 
         return 0;
 }
index 45b578b..cbfac6e 100644 (file)
@@ -5432,7 +5432,10 @@ int get_files_in_directory(const char *path, char ***list) {
         char **l = NULL;
 
         assert(path);
-        assert(list);
+
+        /* Returns all files in a directory in *list, and the number
+         * of files as return value. If list is NULL returns only the
+         * number */
 
         d = opendir(path);
         for (;;) {
@@ -5453,37 +5456,41 @@ int get_files_in_directory(const char *path, char ***list) {
                 if (!dirent_is_file(de))
                         continue;
 
-                if ((unsigned) r >= n) {
-                        char **t;
+                if (list) {
+                        if ((unsigned) r >= n) {
+                                char **t;
 
-                        n = MAX(16, 2*r);
-                        t = realloc(l, sizeof(char*) * n);
-                        if (!t) {
-                                r = -ENOMEM;
-                                goto finish;
-                        }
+                                n = MAX(16, 2*r);
+                                t = realloc(l, sizeof(char*) * n);
+                                if (!t) {
+                                        r = -ENOMEM;
+                                        goto finish;
+                                }
 
-                        l = t;
-                }
+                                l = t;
+                        }
 
-                assert((unsigned) r < n);
+                        assert((unsigned) r < n);
 
-                l[r] = strdup(de->d_name);
-                if (!l[r]) {
-                        r = -ENOMEM;
-                        goto finish;
-                }
+                        l[r] = strdup(de->d_name);
+                        if (!l[r]) {
+                                r = -ENOMEM;
+                                goto finish;
+                        }
 
-                l[++r] = NULL;
+                        l[++r] = NULL;
+                } else
+                        r++;
         }
 
 finish:
         if (d)
                 closedir(d);
 
-        if (r >= 0)
-                *list = l;
-        else
+        if (r >= 0) {
+                if (list)
+                        *list = l;
+        } else
                 strv_free(l);
 
         return r;