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

#include "alloc-util.h"
#include "efi-loader.h"
#include "env-util.h"
#include "parse-util.h"
#include "path-util.h"
#include "stat-util.h"
#include "strv.h"
#include "tpm-pcr.h"
#include "utf8.h"

#if ENABLE_EFI

static int read_usec(const char *variable, usec_t *ret) {
        _cleanup_free_ char *j = NULL;
        uint64_t x = 0;
        int r;

        assert(variable);
        assert(ret);

        r = efi_get_variable_string(variable, &j);
        if (r < 0)
                return r;

        r = safe_atou64(j, &x);
        if (r < 0)
                return r;

        *ret = x;
        return 0;
}

int efi_loader_get_boot_usec(usec_t *ret_firmware, usec_t *ret_loader) {
        uint64_t x, y;
        int r;

        assert(ret_firmware);
        assert(ret_loader);

        if (!is_efi_boot())
                return -EOPNOTSUPP;

        r = read_usec(EFI_LOADER_VARIABLE(LoaderTimeInitUSec), &x);
        if (r < 0)
                return log_debug_errno(r, "Failed to read LoaderTimeInitUSec: %m");

        r = read_usec(EFI_LOADER_VARIABLE(LoaderTimeExecUSec), &y);
        if (r < 0)
                return log_debug_errno(r, "Failed to read LoaderTimeExecUSec: %m");

        if (y == 0 || y < x || y - x > USEC_PER_HOUR)
                return log_debug_errno(SYNTHETIC_ERRNO(EIO),
                                       "Bad LoaderTimeInitUSec=%"PRIu64", LoaderTimeExecUSec=%" PRIu64"; refusing.",
                                       x, y);

        *ret_firmware = x;
        *ret_loader = y;
        return 0;
}

int efi_loader_get_device_part_uuid(sd_id128_t *ret) {
        _cleanup_free_ char *p = NULL;
        int r;
        unsigned parsed[16];

        if (!is_efi_boot())
                return -EOPNOTSUPP;

        r = efi_get_variable_string(EFI_LOADER_VARIABLE(LoaderDevicePartUUID), &p);
        if (r < 0)
                return r;

        if (sscanf(p, SD_ID128_UUID_FORMAT_STR,
                   &parsed[0], &parsed[1], &parsed[2], &parsed[3],
                   &parsed[4], &parsed[5], &parsed[6], &parsed[7],
                   &parsed[8], &parsed[9], &parsed[10], &parsed[11],
                   &parsed[12], &parsed[13], &parsed[14], &parsed[15]) != 16)
                return -EIO;

        if (ret)
                for (unsigned i = 0; i < ELEMENTSOF(parsed); i++)
                        ret->bytes[i] = parsed[i];

        return 0;
}

int efi_loader_get_entries(char ***ret) {
        _cleanup_free_ char16_t *entries = NULL;
        _cleanup_strv_free_ char **l = NULL;
        size_t size;
        int r;

        assert(ret);

        if (!is_efi_boot())
                return -EOPNOTSUPP;

        r = efi_get_variable(EFI_LOADER_VARIABLE(LoaderEntries), NULL, (void**) &entries, &size);
        if (r < 0)
                return r;

        /* The variable contains a series of individually NUL terminated UTF-16 strings. */

        for (size_t i = 0, start = 0;; i++) {
                _cleanup_free_ char *decoded = NULL;
                bool end;

                /* Is this the end of the variable's data? */
                end = i * sizeof(char16_t) >= size;

                /* Are we in the middle of a string? (i.e. not at the end of the variable, nor at a NUL terminator?) If
                 * so, let's go to the next entry. */
                if (!end && entries[i] != 0)
                        continue;

                /* We reached the end of a string, let's decode it into UTF-8 */
                decoded = utf16_to_utf8(entries + start, (i - start) * sizeof(char16_t));
                if (!decoded)
                        return -ENOMEM;

                if (efi_loader_entry_name_valid(decoded)) {
                        r = strv_consume(&l, TAKE_PTR(decoded));
                        if (r < 0)
                                return r;
                } else
                        log_debug("Ignoring invalid loader entry '%s'.", decoded);

                /* We reached the end of the variable */
                if (end)
                        break;

                /* Continue after the NUL byte */
                start = i + 1;
        }

        *ret = TAKE_PTR(l);
        return 0;
}

int efi_loader_get_features(uint64_t *ret) {
        _cleanup_free_ void *v = NULL;
        size_t s;
        int r;

        assert(ret);

        if (!is_efi_boot()) {
                *ret = 0;
                return 0;
        }

        r = efi_get_variable(EFI_LOADER_VARIABLE(LoaderFeatures), NULL, &v, &s);
        if (r == -ENOENT) {
                _cleanup_free_ char *info = NULL;

                /* The new (v240+) LoaderFeatures variable is not supported, let's see if it's systemd-boot at all */
                r = efi_get_variable_string(EFI_LOADER_VARIABLE(LoaderInfo), &info);
                if (r < 0) {
                        if (r != -ENOENT)
                                return r;

                        /* Variable not set, definitely means not systemd-boot */

                } else if (first_word(info, "systemd-boot")) {

                        /* An older systemd-boot version. Let's hardcode the feature set, since it was pretty
                         * static in all its versions. */

                        *ret = EFI_LOADER_FEATURE_CONFIG_TIMEOUT |
                                EFI_LOADER_FEATURE_ENTRY_DEFAULT |
                                EFI_LOADER_FEATURE_ENTRY_ONESHOT;

                        return 0;
                }

                /* No features supported */
                *ret = 0;
                return 0;
        }
        if (r < 0)
                return r;

        if (s != sizeof(uint64_t))
                return log_debug_errno(SYNTHETIC_ERRNO(EINVAL),
                                       "LoaderFeatures EFI variable doesn't have the right size.");

        memcpy(ret, v, sizeof(uint64_t));
        return 0;
}

int efi_stub_get_features(uint64_t *ret) {
        _cleanup_free_ void *v = NULL;
        size_t s;
        int r;

        assert(ret);

        if (!is_efi_boot()) {
                *ret = 0;
                return 0;
        }

        r = efi_get_variable(EFI_LOADER_VARIABLE(StubFeatures), NULL, &v, &s);
        if (r == -ENOENT) {
                _cleanup_free_ char *info = NULL;

                /* The new (v252+) StubFeatures variable is not supported, let's see if it's systemd-stub at all */
                r = efi_get_variable_string(EFI_LOADER_VARIABLE(StubInfo), &info);
                if (r < 0) {
                        if (r != -ENOENT)
                                return r;

                        /* Variable not set, definitely means not systemd-stub */

                } else if (first_word(info, "systemd-stub")) {

                        /* An older systemd-stub version. Let's hardcode the feature set, since it was pretty
                         * static in all its versions. */

                        *ret = EFI_STUB_FEATURE_REPORT_BOOT_PARTITION;
                        return 0;
                }

                /* No features supported */
                *ret = 0;
                return 0;
        }
        if (r < 0)
                return r;

        if (s != sizeof(uint64_t))
                return log_debug_errno(SYNTHETIC_ERRNO(EINVAL),
                                       "StubFeatures EFI variable doesn't have the right size.");

        memcpy(ret, v, sizeof(uint64_t));
        return 0;
}

int efi_stub_measured(int log_level) {
        _cleanup_free_ char *pcr_string = NULL;
        unsigned pcr_nr;
        int r;

        /* Checks if we are booted on a kernel with sd-stub which measured the kernel into PCR 11. Or in
         * other words, if we are running on a TPM enabled UKI.
         *
         * Returns == 0 and > 0 depending on the result of the test. Returns -EREMOTE if we detected a stub
         * being used, but it measured things into a different PCR than we are configured for in
         * userspace. (i.e. we expect PCR 11 being used for this by both sd-stub and us) */

        r = getenv_bool_secure("SYSTEMD_FORCE_MEASURE"); /* Give user a chance to override the variable test,
                                                          * for debugging purposes */
        if (r >= 0)
                return r;
        if (r != -ENXIO)
                log_debug_errno(r, "Failed to parse $SYSTEMD_FORCE_MEASURE, ignoring: %m");

        if (!is_efi_boot())
                return 0;

        r = efi_get_variable_string(EFI_LOADER_VARIABLE(StubPcrKernelImage), &pcr_string);
        if (r == -ENOENT)
                return 0;
        if (r < 0)
                return log_full_errno(log_level, r,
                                      "Failed to get StubPcrKernelImage EFI variable: %m");

        r = safe_atou(pcr_string, &pcr_nr);
        if (r < 0)
                return log_full_errno(log_level, r,
                                      "Failed to parse StubPcrKernelImage EFI variable: %s", pcr_string);
        if (pcr_nr != TPM_PCR_INDEX_KERNEL_IMAGE)
                return log_full_errno(log_level, SYNTHETIC_ERRNO(EREMOTE),
                                      "Kernel stub measured kernel image into PCR %u, which is different than expected %u.",
                                      pcr_nr, TPM_PCR_INDEX_KERNEL_IMAGE);

        return 1;
}

int efi_loader_get_config_timeout_one_shot(usec_t *ret) {
        _cleanup_free_ char *v = NULL;
        static struct stat cache_stat = {};
        struct stat new_stat;
        static usec_t cache;
        uint64_t sec;
        int r;

        assert(ret);

        /* stat() the EFI variable, to see if the mtime changed. If it did, we need to cache again. */
        if (stat(EFIVAR_PATH(EFI_LOADER_VARIABLE(LoaderConfigTimeoutOneShot)), &new_stat) < 0)
                return -errno;

        if (stat_inode_unmodified(&new_stat, &cache_stat)) {
                *ret = cache;
                return 0;
        }

        r = efi_get_variable_string(EFI_LOADER_VARIABLE(LoaderConfigTimeoutOneShot), &v);
        if (r < 0)
                return r;

        r = safe_atou64(v, &sec);
        if (r < 0)
                return r;
        if (sec > USEC_INFINITY / USEC_PER_SEC)
                return -ERANGE;

        cache_stat = new_stat;
        *ret = cache = sec * USEC_PER_SEC; /* return in µs */
        return 0;
}

int efi_loader_update_entry_one_shot_cache(char **cache, struct stat *cache_stat) {
        _cleanup_free_ char *v = NULL;
        struct stat new_stat;
        int r;

        assert(cache);
        assert(cache_stat);

        /* stat() the EFI variable, to see if the mtime changed. If it did we need to cache again. */
        if (stat(EFIVAR_PATH(EFI_LOADER_VARIABLE(LoaderEntryOneShot)), &new_stat) < 0)
                return -errno;

        if (stat_inode_unmodified(&new_stat, cache_stat))
                return 0;

        r = efi_get_variable_string(EFI_LOADER_VARIABLE(LoaderEntryOneShot), &v);
        if (r < 0)
                return r;

        if (!efi_loader_entry_name_valid(v))
                return -EINVAL;

        *cache_stat = new_stat;
        free_and_replace(*cache, v);

        return 0;
}

#endif

bool efi_loader_entry_name_valid(const char *s) {
        if (!filename_is_valid(s)) /* Make sure entry names fit in filenames */
                return false;

        return in_charset(s, ALPHANUMERICAL "+-_.");
}
