/* SPDX-License-Identifier: LGPL-2.1-or-later */

#include "fd-util.h"
#include "fileio.h"
#include "format-util.h"
#include "fs-util.h"
#include "nspawn-bind-user.h"
#include "nspawn.h"
#include "path-util.h"
#include "user-util.h"
#include "userdb.h"

#define MAP_UID_START 60514
#define MAP_UID_END 60577

static int check_etc_passwd_collisions(
                const char *directory,
                const char *name,
                uid_t uid) {

        _cleanup_fclose_ FILE *f = NULL;
        int r;

        assert(directory);
        assert(name || uid_is_valid(uid));

        r = chase_symlinks_and_fopen_unlocked("/etc/passwd", directory, CHASE_PREFIX_ROOT, "re", &f, NULL);
        if (r == -ENOENT)
                return 0; /* no user database? then no user, hence no collision */
        if (r < 0)
                return log_error_errno(r, "Failed to open /etc/passwd of container: %m");

        for (;;) {
                struct passwd *pw;

                r = fgetpwent_sane(f, &pw);
                if (r < 0)
                        return log_error_errno(r, "Failed to iterate through /etc/passwd of container: %m");
                if (r == 0) /* EOF */
                        return 0; /* no collision */

                if (name && streq_ptr(pw->pw_name, name))
                        return 1; /* name collision */
                if (uid_is_valid(uid) && pw->pw_uid == uid)
                        return 1; /* UID collision */
        }
}

static int check_etc_group_collisions(
                const char *directory,
                const char *name,
                gid_t gid) {

        _cleanup_fclose_ FILE *f = NULL;
        int r;

        assert(directory);
        assert(name || gid_is_valid(gid));

        r = chase_symlinks_and_fopen_unlocked("/etc/group", directory, CHASE_PREFIX_ROOT, "re", &f, NULL);
        if (r == -ENOENT)
                return 0; /* no group database? then no group, hence no collision */
        if (r < 0)
                return log_error_errno(r, "Failed to open /etc/group of container: %m");

        for (;;) {
                struct group *gr;

                r = fgetgrent_sane(f, &gr);
                if (r < 0)
                        return log_error_errno(r, "Failed to iterate through /etc/group of container: %m");
                if (r == 0)
                        return 0; /* no collision */

                if (name && streq_ptr(gr->gr_name, name))
                        return 1; /* name collision */
                if (gid_is_valid(gid) && gr->gr_gid == gid)
                        return 1; /* gid collision */
        }
}

static int convert_user(
                const char *directory,
                UserRecord *u,
                GroupRecord *g,
                uid_t allocate_uid,
                UserRecord **ret_converted_user,
                GroupRecord **ret_converted_group) {

        _cleanup_(group_record_unrefp) GroupRecord *converted_group = NULL;
        _cleanup_(user_record_unrefp) UserRecord *converted_user = NULL;
        _cleanup_free_ char *h = NULL;
        JsonVariant *p, *hp = NULL;
        int r;

        assert(u);
        assert(g);
        assert(u->gid == g->gid);

        r = check_etc_passwd_collisions(directory, u->user_name, UID_INVALID);
        if (r < 0)
                return r;
        if (r > 0)
                return log_error_errno(SYNTHETIC_ERRNO(EBUSY),
                                       "Sorry, the user '%s' already exists in the container.", u->user_name);

        r = check_etc_group_collisions(directory, g->group_name, GID_INVALID);
        if (r < 0)
                return r;
        if (r > 0)
                return log_error_errno(SYNTHETIC_ERRNO(EBUSY),
                                       "Sorry, the group '%s' already exists in the container.", g->group_name);

        h = path_join("/run/host/home/", u->user_name);
        if (!h)
                return log_oom();

        /* Acquire the source hashed password array as-is, so that it retains the JSON_VARIANT_SENSITIVE flag */
        p = json_variant_by_key(u->json, "privileged");
        if (p)
                hp = json_variant_by_key(p, "hashedPassword");

        r = user_record_build(
                        &converted_user,
                        JSON_BUILD_OBJECT(
                                        JSON_BUILD_PAIR("userName", JSON_BUILD_STRING(u->user_name)),
                                        JSON_BUILD_PAIR("uid", JSON_BUILD_UNSIGNED(allocate_uid)),
                                        JSON_BUILD_PAIR("gid", JSON_BUILD_UNSIGNED(allocate_uid)),
                                        JSON_BUILD_PAIR_CONDITION(u->disposition >= 0, "disposition", JSON_BUILD_STRING(user_disposition_to_string(u->disposition))),
                                        JSON_BUILD_PAIR("homeDirectory", JSON_BUILD_STRING(h)),
                                        JSON_BUILD_PAIR("service", JSON_BUILD_STRING("io.systemd.NSpawn")),
                                        JSON_BUILD_PAIR_CONDITION(!strv_isempty(u->hashed_password), "privileged", JSON_BUILD_OBJECT(
                                                                                  JSON_BUILD_PAIR("hashedPassword", JSON_BUILD_VARIANT(hp))))));
        if (r < 0)
                return log_error_errno(r, "Failed to build container user record: %m");

        r = group_record_build(
                        &converted_group,
                        JSON_BUILD_OBJECT(
                                        JSON_BUILD_PAIR("groupName", JSON_BUILD_STRING(g->group_name)),
                                        JSON_BUILD_PAIR("gid", JSON_BUILD_UNSIGNED(allocate_uid)),
                                        JSON_BUILD_PAIR_CONDITION(g->disposition >= 0, "disposition", JSON_BUILD_STRING(user_disposition_to_string(g->disposition))),
                                        JSON_BUILD_PAIR("service", JSON_BUILD_STRING("io.systemd.NSpawn"))));
        if (r < 0)
                return log_error_errno(r, "Failed to build container group record: %m");

        *ret_converted_user = TAKE_PTR(converted_user);
        *ret_converted_group = TAKE_PTR(converted_group);

        return 0;
}

static int find_free_uid(const char *directory, uid_t max_uid, uid_t *current_uid) {
        int r;

        assert(directory);
        assert(current_uid);

        for (;; (*current_uid) ++) {
                if (*current_uid > MAP_UID_END || *current_uid > max_uid)
                        return log_error_errno(
                                        SYNTHETIC_ERRNO(EBUSY),
                                        "No suitable available UID in range " UID_FMT "…" UID_FMT " in container detected, can't map user.",
                                        MAP_UID_START, MAP_UID_END);

                r = check_etc_passwd_collisions(directory, NULL, *current_uid);
                if (r < 0)
                        return r;
                if (r > 0) /* already used */
                        continue;

                /* We want to use the UID also as GID, hence check for it in /etc/group too */
                r = check_etc_group_collisions(directory, NULL, (gid_t) *current_uid);
                if (r < 0)
                        return r;
                if (r == 0) /* free! yay! */
                        return 0;
        }
}

BindUserContext* bind_user_context_free(BindUserContext *c) {
        if (!c)
                return NULL;

        assert(c->n_data == 0 || c->data);

        for (size_t i = 0; i < c->n_data; i++) {
                user_record_unref(c->data[i].host_user);
                group_record_unref(c->data[i].host_group);
                user_record_unref(c->data[i].payload_user);
                group_record_unref(c->data[i].payload_group);
        }

        return mfree(c);
}

int bind_user_prepare(
                const char *directory,
                char **bind_user,
                uid_t uid_shift,
                uid_t uid_range,
                CustomMount **custom_mounts,
                size_t *n_custom_mounts,
                BindUserContext **ret) {

        _cleanup_(bind_user_context_freep) BindUserContext *c = NULL;
        uid_t current_uid = MAP_UID_START;
        char **n;
        int r;

        assert(custom_mounts);
        assert(n_custom_mounts);
        assert(ret);

        /* This resolves the users specified in 'bind_user', generates a minimalized JSON user + group record
         * for it to stick in the container, allocates a UID/GID for it, and updates the custom mount table,
         * to include an appropriate bind mount mapping.
         *
         * This extends the passed custom_mounts/n_custom_mounts with the home directories, and allocates a
         * new BindUserContext for the user records */

        if (strv_isempty(bind_user)) {
                *ret = NULL;
                return 0;
        }

        c = new0(BindUserContext, 1);
        if (!c)
                return log_oom();

        STRV_FOREACH(n, bind_user) {
                _cleanup_(user_record_unrefp) UserRecord *u = NULL, *cu = NULL;
                _cleanup_(group_record_unrefp) GroupRecord *g = NULL, *cg = NULL;
                _cleanup_free_ char *sm = NULL, *sd = NULL;
                CustomMount *cm;

                r = userdb_by_name(*n, USERDB_DONT_SYNTHESIZE, &u);
                if (r < 0)
                        return log_error_errno(r, "Failed to resolve user '%s': %m", *n);

                /* For now, let's refuse mapping the root/nobody users explicitly. The records we generate
                 * are strictly additive, nss-systemd is typically placed last in /etc/nsswitch.conf. Thus
                 * even if we wanted, we couldn't override the root or nobody user records. Note we also
                 * check for name conflicts in /etc/passwd + /etc/group later on, which would usually filter
                 * out root/nobody too, hence these checks might appear redundant — but they actually are
                 * not, as we want to support environments where /etc/passwd and /etc/group are non-existent,
                 * and the user/group databases fully synthesized at runtime. Moreover, the name of the
                 * user/group name of the "nobody" account differs between distros, hence a check by numeric
                 * UID is safer. */
                if (u->uid == 0 || streq(u->user_name, "root"))
                        return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Mapping 'root' user not supported, sorry.");
                if (u->uid == UID_NOBODY || STR_IN_SET(u->user_name, NOBODY_USER_NAME, "nobody"))
                        return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Mapping 'nobody' user not supported, sorry.");

                if (u->uid >= uid_shift && u->uid < uid_shift + uid_range)
                        return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "UID of user '%s' to map is already in container UID range, refusing.", u->user_name);

                r = groupdb_by_gid(u->gid, USERDB_DONT_SYNTHESIZE, &g);
                if (r < 0)
                        return log_error_errno(r, "Failed to resolve group of user '%s': %m", u->user_name);

                if (g->gid >= uid_shift && g->gid < uid_shift + uid_range)
                        return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "GID of group '%s' to map is already in container GID range, refusing.", g->group_name);

                /* We want to synthesize exactly one user + group from the host into the container. This only
                 * makes sense if the user on the host has its own private group. We can't reasonably check
                 * this, so we just check of the name of user and group match.
                 *
                 * One of these days we might want to support users in a shared/common group too, but it's
                 * not clear to me how this would have to be mapped, precisely given that the common group
                 * probably already exists in the container. */
                if (!streq(u->user_name, g->group_name))
                        return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP),
                                               "Sorry, mapping users without private groups is currently not supported.");

                r = find_free_uid(directory, uid_range, &current_uid);
                if (r < 0)
                        return r;

                r = convert_user(directory, u, g, current_uid, &cu, &cg);
                if (r < 0)
                        return r;

                if (!GREEDY_REALLOC(c->data, c->n_data + 1))
                        return log_oom();

                sm = strdup(u->home_directory);
                if (!sm)
                        return log_oom();

                sd = strdup(cu->home_directory);
                if (!sd)
                        return log_oom();

                cm = reallocarray(*custom_mounts, sizeof(CustomMount), *n_custom_mounts + 1);
                if (!cm)
                        return log_oom();

                *custom_mounts = cm;

                (*custom_mounts)[(*n_custom_mounts)++] = (CustomMount) {
                        .type = CUSTOM_MOUNT_BIND,
                        .source = TAKE_PTR(sm),
                        .destination = TAKE_PTR(sd),
                };

                c->data[c->n_data++] = (BindUserData) {
                        .host_user = TAKE_PTR(u),
                        .host_group = TAKE_PTR(g),
                        .payload_user = TAKE_PTR(cu),
                        .payload_group = TAKE_PTR(cg),
                };

                current_uid++;
        }

        *ret = TAKE_PTR(c);
        return 1;
}

static int write_and_symlink(
                const char *root,
                JsonVariant *v,
                const char *name,
                uid_t uid,
                const char *suffix,
                WriteStringFileFlags extra_flags) {

        _cleanup_free_ char *j = NULL, *f = NULL, *p = NULL, *q = NULL;
        int r;

        assert(root);
        assert(v);
        assert(name);
        assert(uid_is_valid(uid));
        assert(suffix);

        r = json_variant_format(v, JSON_FORMAT_NEWLINE, &j);
        if (r < 0)
                return log_error_errno(r, "Failed to format user record JSON: %m");

        f = strjoin(name, suffix);
        if (!f)
                return log_oom();

        p = path_join(root, "/run/host/userdb/", f);
        if (!p)
                return log_oom();

        if (asprintf(&q, "%s/run/host/userdb/" UID_FMT "%s", root, uid, suffix) < 0)
                return log_oom();

        if (symlink(f, q) < 0)
                return log_error_errno(errno, "Failed to create symlink '%s': %m", q);

        r = userns_lchown(q, 0, 0);
        if (r < 0)
                return log_error_errno(r, "Failed to adjust access mode of '%s': %m", q);

        r = write_string_file(p, j, WRITE_STRING_FILE_CREATE|extra_flags);
        if (r < 0)
                return log_error_errno(r, "Failed to write %s: %m", p);

        r = userns_lchown(p, 0, 0);
        if (r < 0)
                return log_error_errno(r, "Failed to adjust access mode of '%s': %m", p);

        return 0;
}

int bind_user_setup(
                const BindUserContext *c,
                const char *root) {

        static const UserRecordLoadFlags strip_flags = /* Removes privileged info */
                USER_RECORD_REQUIRE_REGULAR|
                USER_RECORD_STRIP_PRIVILEGED|
                USER_RECORD_ALLOW_PER_MACHINE|
                USER_RECORD_ALLOW_BINDING|
                USER_RECORD_ALLOW_SIGNATURE|
                USER_RECORD_PERMISSIVE;
        static const UserRecordLoadFlags shadow_flags = /* Extracts privileged info */
                USER_RECORD_STRIP_REGULAR|
                USER_RECORD_ALLOW_PRIVILEGED|
                USER_RECORD_STRIP_PER_MACHINE|
                USER_RECORD_STRIP_BINDING|
                USER_RECORD_STRIP_SIGNATURE|
                USER_RECORD_EMPTY_OK|
                USER_RECORD_PERMISSIVE;
        int r;

        assert(root);

        if (!c || c->n_data == 0)
                return 0;

        r = userns_mkdir(root, "/run/host", 0755, 0, 0);
        if (r < 0)
                return log_error_errno(r, "Failed to create /run/host: %m");

        r = userns_mkdir(root, "/run/host/home", 0755, 0, 0);
        if (r < 0)
                return log_error_errno(r, "Failed to create /run/host/userdb: %m");

        r = userns_mkdir(root, "/run/host/userdb", 0755, 0, 0);
        if (r < 0)
                return log_error_errno(r, "Failed to create /run/host/userdb: %m");

        for (size_t i = 0; i < c->n_data; i++) {
                _cleanup_(group_record_unrefp) GroupRecord *stripped_group = NULL, *shadow_group = NULL;
                _cleanup_(user_record_unrefp) UserRecord *stripped_user = NULL, *shadow_user = NULL;
                const BindUserData *d = c->data + i;

                /* First, write shadow (i.e. privileged) data for group record */
                r = group_record_clone(d->payload_group, shadow_flags, &shadow_group);
                if (r < 0)
                        return log_error_errno(r, "Failed to extract privileged information from group record: %m");

                if (!json_variant_is_blank_object(shadow_group->json)) {
                        r = write_and_symlink(
                                        root,
                                        shadow_group->json,
                                        d->payload_group->group_name,
                                        d->payload_group->gid,
                                        ".group-privileged",
                                        WRITE_STRING_FILE_MODE_0600);
                        if (r < 0)
                                return r;
                }

                /* Second, write main part of group record. */
                r = group_record_clone(d->payload_group, strip_flags, &stripped_group);
                if (r < 0)
                        return log_error_errno(r, "Failed to strip privileged information from group record: %m");

                r = write_and_symlink(
                                root,
                                stripped_group->json,
                                d->payload_group->group_name,
                                d->payload_group->gid,
                                ".group",
                                0);
                if (r < 0)
                        return r;

                /* Third, write out user shadow data. i.e. extract privileged info from user record */
                r = user_record_clone(d->payload_user, shadow_flags, &shadow_user);
                if (r < 0)
                        return log_error_errno(r, "Failed to extract privileged information from user record: %m");

                if (!json_variant_is_blank_object(shadow_user->json)) {
                        r = write_and_symlink(
                                        root,
                                        shadow_user->json,
                                        d->payload_user->user_name,
                                        d->payload_user->uid,
                                        ".user-privileged",
                                        WRITE_STRING_FILE_MODE_0600);
                        if (r < 0)
                                return r;
                }

                /* Finally write out the main part of the user record */
                r = user_record_clone(d->payload_user, strip_flags, &stripped_user);
                if (r < 0)
                        return log_error_errno(r, "Failed to strip privileged information from user record: %m");

                r = write_and_symlink(
                                root,
                                stripped_user->json,
                                d->payload_user->user_name,
                                d->payload_user->uid,
                                ".user",
                                0);
                if (r < 0)
                        return r;
        }

        return 1;
}
