commit e013179427bcb18684f8b9f41f1bdb16c668bb66 Author: Jiayi Yin Date: Sun Mar 16 16:10:18 2025 +0000 init diff --git a/CVE-2019-10063.patch b/CVE-2019-10063.patch new file mode 100644 index 0000000..95629c6 --- /dev/null +++ b/CVE-2019-10063.patch @@ -0,0 +1,26 @@ +From a9107feeb4b8275b78965b36bf21b92d5724699e Mon Sep 17 00:00:00 2001 +From: Ryan Gonzalez +Date: Mon, 25 Mar 2019 13:00:15 -0500 +Subject: [PATCH] run: Only compare the lowest 32 ioctl arg bits for TIOCSTI + +Closes #2782. + +Closes: #2783 +Approved by: alexlarsson +--- + common/flatpak-run.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 42e8bc05c6..b03c215bf2 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2475,7 +2475,7 @@ setup_seccomp (FlatpakBwrap *bwrap, + {SCMP_SYS (clone), &SCMP_A0 (SCMP_CMP_MASKED_EQ, CLONE_NEWUSER, CLONE_NEWUSER)}, + + /* Don't allow faking input to the controlling tty (CVE-2017-5226) */ +- {SCMP_SYS (ioctl), &SCMP_A1 (SCMP_CMP_EQ, (int) TIOCSTI)}, ++ {SCMP_SYS (ioctl), &SCMP_A1 (SCMP_CMP_MASKED_EQ, 0xFFFFFFFFu, (int) TIOCSTI)}, + }; + + struct diff --git a/CVE-2019-8308.patch b/CVE-2019-8308.patch new file mode 100644 index 0000000..37695b2 --- /dev/null +++ b/CVE-2019-8308.patch @@ -0,0 +1,67 @@ +From f2af3137e3e5bdd54cad646046da82218aec3fa7 Mon Sep 17 00:00:00 2001 +From: Alexander Larsson +Date: Sun, 10 Feb 2019 18:23:44 +0100 +Subject: [PATCH] Don't expose /proc when running apply_extra + +As shown by CVE-2019-5736, it is sometimes possible for the sandbox +app to access outside files using /proc/self/exe. This is not +typically an issue for flatpak as the sandbox runs as the user which +has no permissions to e.g. modify the host files. + +However, when installing apps using extra-data into the system repo +we *do* actually run a sandbox as root. So, in this case we disable mounting +/proc in the sandbox, which will neuter attacks like this. + +--- + common/flatpak-common-types-private.h | 1 + + common/flatpak-dir.c | 2 +- + common/flatpak-run.c | 6 +++++- + 3 files changed, 7 insertions(+), 2 deletions(-) + +diff --git a/common/flatpak-common-types-private.h b/common/flatpak-common-types-private.h +index e361777..b8f76b9 100644 +--- a/common/flatpak-common-types-private.h ++++ b/common/flatpak-common-types-private.h +@@ -45,6 +45,7 @@ typedef enum { + FLATPAK_RUN_FLAG_NO_DOCUMENTS_PORTAL = (1 << 15), + FLATPAK_RUN_FLAG_BLUETOOTH = (1 << 16), + FLATPAK_RUN_FLAG_CANBUS = (1 << 17), ++ FLATPAK_RUN_FLAG_NO_PROC = (1 << 19), + } FlatpakRunFlags; + + typedef struct FlatpakDir FlatpakDir; +diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c +index 236de4b..56bca24 100644 +--- a/common/flatpak-dir.c ++++ b/common/flatpak-dir.c +@@ -6511,7 +6511,7 @@ apply_extra_data (FlatpakDir *self, + NULL); + + if (!flatpak_run_setup_base_argv (bwrap, runtime_files, NULL, runtime_ref_parts[2], +- FLATPAK_RUN_FLAG_NO_SESSION_HELPER, ++ FLATPAK_RUN_FLAG_NO_SESSION_HELPER | FLATPAK_RUN_FLAG_NO_PROC, + error)) + return FALSE; + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index cd6672e..c5fe6dc 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2357,9 +2357,13 @@ flatpak_run_setup_base_argv (FlatpakBwrap *bwrap, + "# Disable user pkcs11 config, because the host modules don't work in the runtime\n" + "user-config: none\n"; + ++ if ((flags & FLATPAK_RUN_FLAG_NO_PROC) == 0) ++ flatpak_bwrap_add_args (bwrap, ++ "--proc", "/proc", ++ NULL); ++ + flatpak_bwrap_add_args (bwrap, + "--unshare-pid", +- "--proc", "/proc", + "--dir", "/tmp", + "--dir", "/var/tmp", + "--dir", "/run/host", +-- +2.30.0 + diff --git a/CVE-2021-21261-1.patch b/CVE-2021-21261-1.patch new file mode 100644 index 0000000..4e8b279 --- /dev/null +++ b/CVE-2021-21261-1.patch @@ -0,0 +1,156 @@ +From b04ab0f0c4fe4970737187a76389b20029e27488 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Tue, 12 Jan 2021 12:21:31 +0000 +Subject: [PATCH] run: Convert all environment variables into bwrap + arguments + +This avoids some of them being filtered out by a setuid bwrap. It also +means that if they came from an untrusted source, they cannot be used +to inject arbitrary code into a non-setuid bwrap via mechanisms like +LD_PRELOAD. + +Because they get bundled into a memfd or temporary file, they do not +actually appear in argv, ensuring that they remain inaccessible to +processes running under a different uid (which is important if their +values are tokens or other secrets). + +Signed-off-by: Simon McVittie +Part-of: https://github.com/flatpak/flatpak/security/advisories/GHSA-4ppf-fxf6-vxg2 +--- + common/flatpak-bwrap-private.h | 3 +++ + common/flatpak-bwrap.c | 43 ++++++++++++++++++++++++++++++++++ + common/flatpak-run.c | 24 ++++++++++++------- + 3 files changed, 61 insertions(+), 9 deletions(-) + +--- flatpak.orig/common/flatpak-bwrap-private.h ++++ flatpak/common/flatpak-bwrap-private.h +@@ -43,6 +43,8 @@ void flatpak_bwrap_unset_env (F + const char *variable); + void flatpak_bwrap_add_arg (FlatpakBwrap *bwrap, + const char *arg); ++void flatpak_bwrap_take_arg (FlatpakBwrap *bwrap, ++ char *arg); + void flatpak_bwrap_add_noinherit_fd (FlatpakBwrap *bwrap, + int fd); + void flatpak_bwrap_add_fd (FlatpakBwrap *bwrap, +@@ -73,6 +75,7 @@ void flatpak_bwrap_add_bind_arg + const char *type, + const char *src, + const char *dest); ++void flatpak_bwrap_envp_to_args (FlatpakBwrap *bwrap); + gboolean flatpak_bwrap_bundle_args (FlatpakBwrap *bwrap, + int start, + int end, +--- flatpak.orig/common/flatpak-bwrap.c ++++ flatpak/common/flatpak-bwrap.c +@@ -108,6 +108,18 @@ flatpak_bwrap_add_arg (FlatpakBwrap *bwr + g_ptr_array_add (bwrap->argv, g_strdup (arg)); + } + ++/* ++ * flatpak_bwrap_take_arg: ++ * @arg: (transfer full): Take ownership of this argument ++ * ++ * Add @arg to @bwrap's argv, taking ownership of the pointer. ++ */ ++void ++flatpak_bwrap_take_arg (FlatpakBwrap *bwrap, char *arg) ++{ ++ g_ptr_array_add (bwrap->argv, arg); ++} ++ + void + flatpak_bwrap_finish (FlatpakBwrap *bwrap) + { +@@ -273,6 +285,37 @@ flatpak_bwrap_add_bind_arg (FlatpakBwrap + } + } + ++/* ++ * Convert bwrap->envp into a series of --setenv arguments for bwrap(1), ++ * assumed to be applied to an empty environment. Reset envp to be an ++ * empty environment. ++ */ ++void ++flatpak_bwrap_envp_to_args (FlatpakBwrap *bwrap) ++{ ++ gsize i; ++ ++ for (i = 0; bwrap->envp[i] != NULL; i++) ++ { ++ char *key_val = bwrap->envp[i]; ++ char *eq = strchr (key_val, '='); ++ ++ if (eq) ++ { ++ flatpak_bwrap_add_arg (bwrap, "--setenv"); ++ flatpak_bwrap_take_arg (bwrap, g_strndup (key_val, eq - key_val)); ++ flatpak_bwrap_add_arg (bwrap, eq + 1); ++ } ++ else ++ { ++ g_warn_if_reached (); ++ } ++ } ++ ++ g_strfreev (g_steal_pointer (&bwrap->envp)); ++ bwrap->envp = g_strdupv (flatpak_bwrap_empty_env); ++} ++ + gboolean + flatpak_bwrap_bundle_args (FlatpakBwrap *bwrap, + int start, +--- flatpak.orig/common/flatpak-run.c ++++ flatpak/common/flatpak-run.c +@@ -1120,15 +1120,6 @@ flatpak_run_add_environment_args (Flatpa + flatpak_run_add_system_dbus_args (bwrap, proxy_arg_bwrap, context, flags); + flatpak_run_add_a11y_dbus_args (bwrap, proxy_arg_bwrap, context, flags); + +- if (g_environ_getenv (bwrap->envp, "LD_LIBRARY_PATH") != NULL) +- { +- /* LD_LIBRARY_PATH is overridden for setuid helper, so pass it as cmdline arg */ +- flatpak_bwrap_add_args (bwrap, +- "--setenv", "LD_LIBRARY_PATH", g_environ_getenv (bwrap->envp, "LD_LIBRARY_PATH"), +- NULL); +- flatpak_bwrap_unset_env (bwrap, "LD_LIBRARY_PATH"); +- } +- + /* Must run this before spawning the dbus proxy, to ensure it + ends up in the app cgroup */ + if (!flatpak_run_in_transient_unit (app_id, &my_error)) +@@ -3139,6 +3130,8 @@ flatpak_run_app (const char *app_ref + command = default_command; + } + ++ flatpak_bwrap_envp_to_args (bwrap); ++ + if (!flatpak_bwrap_bundle_args (bwrap, 1, -1, FALSE, error)) + return FALSE; + +@@ -3161,6 +3154,12 @@ flatpak_run_app (const char *app_ref + char pid_str[64]; + g_autofree char *pid_path = NULL; + ++ /* flatpak_bwrap_envp_to_args() moved the environment variables to ++ * be set into --setenv instructions in argv, so the environment ++ * in which the bwrap command runs must be empty. */ ++ g_assert (bwrap->envp != NULL); ++ g_assert (bwrap->envp[0] == NULL); ++ + if (!g_spawn_async (NULL, + (char **) bwrap->argv->pdata, + bwrap->envp, +@@ -3185,6 +3184,13 @@ flatpak_run_app (const char *app_ref + + /* Ensure we unset O_CLOEXEC */ + flatpak_bwrap_child_setup_cb (bwrap->fds); ++ ++ /* flatpak_bwrap_envp_to_args() moved the environment variables to ++ * be set into --setenv instructions in argv, so the environment ++ * in which the bwrap command runs must be empty. */ ++ g_assert (bwrap->envp != NULL); ++ g_assert (bwrap->envp[0] == NULL); ++ + if (execvpe (flatpak_get_bwrap (), (char **) bwrap->argv->pdata, bwrap->envp) == -1) + { + g_set_error_literal (error, G_IO_ERROR, g_io_error_from_errno (errno), diff --git a/CVE-2021-21261-2.patch b/CVE-2021-21261-2.patch new file mode 100644 index 0000000..8250a84 --- /dev/null +++ b/CVE-2021-21261-2.patch @@ -0,0 +1,228 @@ +From 1b82bf2f9df06ee60d222b4fb45fe3490d05ef94 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Mon, 11 Jan 2021 14:51:36 +0000 +Subject: [PATCH] common: Move flatpak_buffer_to_sealed_memfd_or_tmpfile + to its own file + +We'll need this to use it in flatpak-portal without pulling the rest of +the common/ directory. + +Signed-off-by: Simon McVittie +--- + common/Makefile.am.inc | 2 + + common/flatpak-utils-memfd-private.h | 32 ++++++++++ + common/flatpak-utils-memfd.c | 90 ++++++++++++++++++++++++++++ + common/flatpak-utils-private.h | 1 + + common/flatpak-utils.c | 50 ---------------- + 5 files changed, 125 insertions(+), 50 deletions(-) + create mode 100644 common/flatpak-utils-memfd-private.h + create mode 100644 common/flatpak-utils-memfd.c + +--- flatpak.orig/common/Makefile.am.inc ++++ flatpak/common/Makefile.am.inc +@@ -96,6 +96,8 @@ libflatpak_common_la_SOURCES = \ + common/flatpak-utils.c \ + common/flatpak-utils-http.c \ + common/flatpak-utils-http-private.h \ ++ common/flatpak-utils-memfd.c \ ++ common/flatpak-utils-memfd-private.h \ + common/flatpak-utils-private.h \ + common/flatpak-chain-input-stream.c \ + common/flatpak-chain-input-stream-private.h \ +--- /dev/null ++++ flatpak/common/flatpak-utils-memfd-private.h +@@ -0,0 +1,32 @@ ++/* ++ * Copyright © 2014 Red Hat, Inc ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU Lesser General Public ++ * License as published by the Free Software Foundation; either ++ * version 2.1 of the License, or (at your option) any later version. ++ * ++ * This library is distributed in the hope that it will be useful, ++ * but WITHOUT ANY WARRANTY; without even the implied warranty of ++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ++ * Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public ++ * License along with this library. If not, see . ++ * ++ * Authors: ++ * Alexander Larsson ++ */ ++ ++#ifndef __FLATPAK_UTILS_MEMFD_H__ ++#define __FLATPAK_UTILS_MEMFD_H__ ++ ++#include "libglnx/libglnx.h" ++ ++gboolean flatpak_buffer_to_sealed_memfd_or_tmpfile (GLnxTmpfile *tmpf, ++ const char *name, ++ const char *str, ++ size_t len, ++ GError **error); ++ ++#endif /* __FLATPAK_UTILS_MEMFD_H__ */ +--- /dev/null ++++ flatpak/common/flatpak-utils-memfd.c +@@ -0,0 +1,90 @@ ++/* ++ * Copyright © 2014 Red Hat, Inc ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU Lesser General Public ++ * License as published by the Free Software Foundation; either ++ * version 2.1 of the License, or (at your option) any later version. ++ * ++ * This library is distributed in the hope that it will be useful, ++ * but WITHOUT ANY WARRANTY; without even the implied warranty of ++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ++ * Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public ++ * License along with this library. If not, see . ++ * ++ * Authors: ++ * Alexander Larsson ++ */ ++ ++#include "config.h" ++ ++#include "flatpak-utils-memfd-private.h" ++ ++#include "valgrind-private.h" ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++/* If memfd_create() is available, generate a sealed memfd with contents of ++ * @str. Otherwise use an O_TMPFILE @tmpf in anonymous mode, write @str to ++ * @tmpf, and lseek() back to the start. See also similar uses in e.g. ++ * rpm-ostree for running dracut. ++ */ ++gboolean ++flatpak_buffer_to_sealed_memfd_or_tmpfile (GLnxTmpfile *tmpf, ++ const char *name, ++ const char *str, ++ size_t len, ++ GError **error) ++{ ++ if (len == -1) ++ len = strlen (str); ++ glnx_autofd int memfd = memfd_create (name, MFD_CLOEXEC | MFD_ALLOW_SEALING); ++ int fd; /* Unowned */ ++ if (memfd != -1) ++ { ++ fd = memfd; ++ } ++ else ++ { ++ /* We use an anonymous fd (i.e. O_EXCL) since we don't want ++ * the target container to potentially be able to re-link it. ++ */ ++ if (!G_IN_SET (errno, ENOSYS, EOPNOTSUPP)) ++ return glnx_throw_errno_prefix (error, "memfd_create"); ++ if (!glnx_open_anonymous_tmpfile (O_RDWR | O_CLOEXEC, tmpf, error)) ++ return FALSE; ++ fd = tmpf->fd; ++ } ++ if (ftruncate (fd, len) < 0) ++ return glnx_throw_errno_prefix (error, "ftruncate"); ++ if (glnx_loop_write (fd, str, len) < 0) ++ return glnx_throw_errno_prefix (error, "write"); ++ if (lseek (fd, 0, SEEK_SET) < 0) ++ return glnx_throw_errno_prefix (error, "lseek"); ++ if (memfd != -1) ++ { ++ /* Valgrind doesn't currently handle G_ADD_SEALS, so lets not seal when debugging... */ ++ if ((!RUNNING_ON_VALGRIND) && ++ fcntl (memfd, F_ADD_SEALS, F_SEAL_SHRINK | F_SEAL_GROW | F_SEAL_WRITE | F_SEAL_SEAL) < 0) ++ return glnx_throw_errno_prefix (error, "fcntl(F_ADD_SEALS)"); ++ /* The other values can stay default */ ++ tmpf->fd = glnx_steal_fd (&memfd); ++ tmpf->initialized = TRUE; ++ } ++ return TRUE; ++} +--- flatpak.orig/common/flatpak-utils-private.h ++++ flatpak/common/flatpak-utils-private.h +@@ -32,6 +32,7 @@ + #include "flatpak-context-private.h" + #include "flatpak-error.h" + #include "flatpak-utils-http-private.h" ++#include "flatpak-utils-memfd-private.h" + #include + #include + +--- flatpak.orig/common/flatpak-utils.c ++++ flatpak/common/flatpak-utils.c +@@ -2280,56 +2280,6 @@ flatpak_file_rename (GFile *from, + return TRUE; + } + +-/* If memfd_create() is available, generate a sealed memfd with contents of +- * @str. Otherwise use an O_TMPFILE @tmpf in anonymous mode, write @str to +- * @tmpf, and lseek() back to the start. See also similar uses in e.g. +- * rpm-ostree for running dracut. +- */ +-gboolean +-flatpak_buffer_to_sealed_memfd_or_tmpfile (GLnxTmpfile *tmpf, +- const char *name, +- const char *str, +- size_t len, +- GError **error) +-{ +- if (len == -1) +- len = strlen (str); +- glnx_autofd int memfd = memfd_create (name, MFD_CLOEXEC | MFD_ALLOW_SEALING); +- int fd; /* Unowned */ +- if (memfd != -1) +- { +- fd = memfd; +- } +- else +- { +- /* We use an anonymous fd (i.e. O_EXCL) since we don't want +- * the target container to potentially be able to re-link it. +- */ +- if (!G_IN_SET (errno, ENOSYS, EOPNOTSUPP)) +- return glnx_throw_errno_prefix (error, "memfd_create"); +- if (!glnx_open_anonymous_tmpfile (O_RDWR | O_CLOEXEC, tmpf, error)) +- return FALSE; +- fd = tmpf->fd; +- } +- if (ftruncate (fd, len) < 0) +- return glnx_throw_errno_prefix (error, "ftruncate"); +- if (glnx_loop_write (fd, str, len) < 0) +- return glnx_throw_errno_prefix (error, "write"); +- if (lseek (fd, 0, SEEK_SET) < 0) +- return glnx_throw_errno_prefix (error, "lseek"); +- if (memfd != -1) +- { +- /* Valgrind doesn't currently handle G_ADD_SEALS, so lets not seal when debugging... */ +- if ((!RUNNING_ON_VALGRIND) && +- fcntl (memfd, F_ADD_SEALS, F_SEAL_SHRINK | F_SEAL_GROW | F_SEAL_WRITE | F_SEAL_SEAL) < 0) +- return glnx_throw_errno_prefix (error, "fcntl(F_ADD_SEALS)"); +- /* The other values can stay default */ +- tmpf->fd = glnx_steal_fd (&memfd); +- tmpf->initialized = TRUE; +- } +- return TRUE; +-} +- + gboolean + flatpak_open_in_tmpdir_at (int tmpdir_fd, + int mode, diff --git a/CVE-2021-21261-3.patch b/CVE-2021-21261-3.patch new file mode 100644 index 0000000..8a1d5d1 --- /dev/null +++ b/CVE-2021-21261-3.patch @@ -0,0 +1,204 @@ +From 7a93013153a425d4cb8466cd9b665b98e713451d Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Sun, 10 Jan 2021 16:18:58 +0000 +Subject: [PATCH] context: Add --env-fd option + +This allows environment variables to be added to the context without +making their values visible to processes running under a different uid, +which might be significant if the variable's value is a token or some +other secret value. + +Signed-off-by: Simon McVittie +Part-of: https://github.com/flatpak/flatpak/security/advisories/GHSA-4ppf-fxf6-vxg2 +--- + common/flatpak-context.c | 60 ++++++++++++++++++++++++++++++++++++ + doc/flatpak-build-finish.xml | 18 +++++++++++ + doc/flatpak-build.xml | 18 +++++++++++ + doc/flatpak-override.xml | 18 +++++++++++ + doc/flatpak-run.xml | 18 +++++++++++ + 5 files changed, 132 insertions(+) + +--- flatpak.orig/common/flatpak-context.c ++++ flatpak/common/flatpak-context.c +@@ -1040,6 +1040,65 @@ option_env_cb (const gchar *option_name, + } + + static gboolean ++option_env_fd_cb (const gchar *option_name, ++ const gchar *value, ++ gpointer data, ++ GError **error) ++{ ++ FlatpakContext *context = data; ++ g_autoptr(GBytes) env_block = NULL; ++ gsize remaining; ++ const char *p; ++ guint64 fd; ++ gchar *endptr; ++ ++ fd = g_ascii_strtoull (value, &endptr, 10); ++ ++ if (endptr == NULL || *endptr != '\0' || fd > G_MAXINT) ++ return glnx_throw (error, "Not a valid file descriptor: %s", value); ++ ++ env_block = glnx_fd_readall_bytes ((int) fd, NULL, error); ++ ++ if (env_block == NULL) ++ return FALSE; ++ ++ p = g_bytes_get_data (env_block, &remaining); ++ ++ /* env_block might not be \0-terminated */ ++ while (remaining > 0) ++ { ++ size_t len = strnlen (p, remaining); ++ const char *equals; ++ ++ g_assert (len <= remaining); ++ ++ equals = memchr (p, '=', len); ++ ++ if (equals == NULL || equals == p) ++ return glnx_throw (error, ++ "Environment variable must be given in the form VARIABLE=VALUE, not %.*s", (int) len, p); ++ ++ flatpak_context_set_env_var (context, ++ g_strndup (p, equals - p), ++ g_strndup (equals + 1, len - (equals - p) - 1)); ++ p += len; ++ remaining -= len; ++ ++ if (remaining > 0) ++ { ++ g_assert (*p == '\0'); ++ p += 1; ++ remaining -= 1; ++ } ++ } ++ ++ if (fd >= 3) ++ close (fd); ++ ++ return TRUE; ++} ++ ++static gboolean + option_own_name_cb (const gchar *option_name, + const gchar *value, + gpointer data, +@@ -1206,6 +1265,7 @@ static GOptionEntry context_options[] = + { "filesystem", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_filesystem_cb, N_("Expose filesystem to app (:ro for read-only)"), N_("FILESYSTEM[:ro]") }, + { "nofilesystem", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_nofilesystem_cb, N_("Don't expose filesystem to app"), N_("FILESYSTEM") }, + { "env", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_env_cb, N_("Set environment variable"), N_("VAR=VALUE") }, ++ { "env-fd", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_env_fd_cb, N_("Read environment variables in env -0 format from FD"), N_("FD") }, + { "own-name", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_own_name_cb, N_("Allow app to own name on the session bus"), N_("DBUS_NAME") }, + { "talk-name", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_talk_name_cb, N_("Allow app to talk to name on the session bus"), N_("DBUS_NAME") }, + { "system-own-name", 0, G_OPTION_FLAG_IN_MAIN, G_OPTION_ARG_CALLBACK, &option_system_own_name_cb, N_("Allow app to own name on the system bus"), N_("DBUS_NAME") }, +--- flatpak.orig/doc/flatpak-build-finish.xml ++++ flatpak/doc/flatpak-build-finish.xml +@@ -277,6 +277,24 @@ key=v1;v2; + + + ++ ++ ++ ++ Read environment variables from the file descriptor ++ FD, and set them as if ++ via . This can be used to avoid ++ environment variables and their values becoming visible ++ to other users. ++ ++ Each environment variable is in the form ++ VAR=VALUE ++ followed by a zero byte. This is the same format used by ++ env -0 and ++ /proc/*/environ. ++ ++ ++ ++ + + + +--- flatpak.orig/doc/flatpak-build.xml ++++ flatpak/doc/flatpak-build.xml +@@ -284,6 +284,24 @@ key=v1;v2; + + + ++ ++ ++ ++ Read environment variables from the file descriptor ++ FD, and set them as if ++ via . This can be used to avoid ++ environment variables and their values becoming visible ++ to other users. ++ ++ Each environment variable is in the form ++ VAR=VALUE ++ followed by a zero byte. This is the same format used by ++ env -0 and ++ /proc/*/environ. ++ ++ ++ ++ + + + +--- flatpak.orig/doc/flatpak-override.xml ++++ flatpak/doc/flatpak-override.xml +@@ -258,6 +258,24 @@ key=v1;v2; + + + ++ ++ ++ ++ Read environment variables from the file descriptor ++ FD, and set them as if ++ via . This can be used to avoid ++ environment variables and their values becoming visible ++ to other users. ++ ++ Each environment variable is in the form ++ VAR=VALUE ++ followed by a zero byte. This is the same format used by ++ env -0 and ++ /proc/*/environ. ++ ++ ++ ++ + + + +--- flatpak.orig/doc/flatpak-run.xml ++++ flatpak/doc/flatpak-run.xml +@@ -361,6 +361,24 @@ key=v1;v2; + + + ++ ++ ++ ++ Read environment variables from the file descriptor ++ FD, and set them as if ++ via . This can be used to avoid ++ environment variables and their values becoming visible ++ to other users. ++ ++ Each environment variable is in the form ++ VAR=VALUE ++ followed by a zero byte. This is the same format used by ++ env -0 and ++ /proc/*/environ. ++ ++ ++ ++ + + + diff --git a/CVE-2021-21261-4.patch b/CVE-2021-21261-4.patch new file mode 100644 index 0000000..2f644ae --- /dev/null +++ b/CVE-2021-21261-4.patch @@ -0,0 +1,138 @@ +From ce6a6e593310d42f7aecddb88d98e759f22ab6db Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Tue, 12 Jan 2021 12:25:59 +0000 +Subject: [PATCH] portal: Convert --env in extra-args into --env-fd + +This hides overridden variables from the command-line, which means +processes running under other uids can't see them in /proc/*/cmdline, +which might be important if they contain secrets. + +Signed-off-by: Simon McVittie +Part-of: https://github.com/flatpak/flatpak/security/advisories/GHSA-4ppf-fxf6-vxg2 +--- + portal/Makefile.am.inc | 4 ++- + portal/flatpak-portal.c | 65 ++++++++++++++++++++++++++++++++++++++++- + 2 files changed, 67 insertions(+), 2 deletions(-) + +--- flatpak.orig/portal/Makefile.am.inc ++++ flatpak/portal/Makefile.am.inc +@@ -29,11 +29,13 @@ flatpak_portal_SOURCES = \ + portal/flatpak-portal-app-info.h \ + common/flatpak-portal-error.c \ + common/flatpak-portal-error.h \ ++ common/flatpak-utils-memfd.c \ ++ common/flatpak-utils-memfd-private.h \ + $(NULL) + + BUILT_SOURCES += $(nodist_flatpak_portal_SOURCES) + CLEANFILES += $(nodist_flatpak_portal_SOURCES) + +-flatpak_portal_LDADD = $(AM_LDADD) $(BASE_LIBS) ++flatpak_portal_LDADD = $(AM_LDADD) $(BASE_LIBS) libglnx.la + flatpak_portal_CFLAGS = $(AM_CFLAGS) $(BASE_CFLAGS) -DFLATPAK_COMPILATION + flatpak_portal_CPPFLAGS = $(AM_CPPFLAGS) -I$(builddir)/portal +--- flatpak.orig/portal/flatpak-portal.c ++++ flatpak/portal/flatpak-portal.c +@@ -32,6 +32,14 @@ + #include "flatpak-portal.h" + #include "flatpak-portal-app-info.h" + #include "flatpak-portal-error.h" ++#include "flatpak-utils-memfd-private.h" ++ ++/* Syntactic sugar added in newer GLib, which makes the error paths more ++ * clearly correct */ ++#ifndef G_DBUS_METHOD_INVOCATION_HANDLED ++# define G_DBUS_METHOD_INVOCATION_HANDLED TRUE ++# define G_DBUS_METHOD_INVOCATION_UNHANDLED FALSE ++#endif + + #define IDLE_TIMEOUT_SECS 10 * 60 + +@@ -166,9 +174,16 @@ typedef struct + int fd_map_len; + gboolean set_tty; + int tty; ++ int env_fd; + } ChildSetupData; + + static void ++drop_cloexec (int fd) ++{ ++ fcntl (fd, F_SETFD, 0); ++} ++ ++static void + child_setup_func (gpointer user_data) + { + ChildSetupData *data = (ChildSetupData *) user_data; +@@ -176,6 +191,9 @@ child_setup_func (gpointer user_data) + sigset_t set; + int i; + ++ if (data->env_fd != -1) ++ drop_cloexec (data->env_fd); ++ + /* Unblock all signals */ + sigemptyset (&set); + if (pthread_sigmask (SIG_SETMASK, &set, NULL) == -1) +@@ -321,6 +339,9 @@ handle_spawn (PortalFlatpak *obj + g_auto(GStrv) sandbox_expose = NULL; + g_auto(GStrv) sandbox_expose_ro = NULL; + gboolean sandboxed; ++ g_autoptr(GString) env_string = g_string_new (""); ++ ++ child_setup_data.env_fd = -1; + + app_info = g_object_get_data (G_OBJECT (invocation), "app-info"); + g_assert (app_info != NULL); +@@ -505,7 +526,49 @@ handle_spawn (PortalFlatpak *obj + else + { + for (i = 0; extra_args != NULL && extra_args[i] != NULL; i++) +- g_ptr_array_add (flatpak_argv, g_strdup (extra_args[i])); ++ { ++ if (g_str_has_prefix (extra_args[i], "--env=")) ++ { ++ const char *var_val = extra_args[i] + strlen ("--env="); ++ ++ if (var_val[0] == '\0' || var_val[0] == '=') ++ { ++ g_warning ("Environment variable in extra-args has empty name"); ++ continue; ++ } ++ ++ if (strchr (var_val, '=') == NULL) ++ { ++ g_warning ("Environment variable in extra-args has no value"); ++ continue; ++ } ++ ++ g_string_append (env_string, var_val); ++ g_string_append_c (env_string, '\0'); ++ } ++ else ++ { ++ g_ptr_array_add (flatpak_argv, g_strdup (extra_args[i])); ++ } ++ } ++ } ++ ++ if (env_string->len > 0) ++ { ++ g_auto(GLnxTmpfile) env_tmpf = { 0, }; ++ ++ if (!flatpak_buffer_to_sealed_memfd_or_tmpfile (&env_tmpf, "environ", ++ env_string->str, ++ env_string->len, &error)) ++ { ++ g_dbus_method_invocation_return_gerror (invocation, error); ++ return G_DBUS_METHOD_INVOCATION_HANDLED; ++ } ++ ++ child_setup_data.env_fd = glnx_steal_fd (&env_tmpf.fd); ++ g_ptr_array_add (flatpak_argv, ++ g_strdup_printf ("--env-fd=%d", ++ child_setup_data.env_fd)); + } + + /* Inherit launcher network access from launcher, unless diff --git a/CVE-2021-21261-5.patch b/CVE-2021-21261-5.patch new file mode 100644 index 0000000..9f49a3b --- /dev/null +++ b/CVE-2021-21261-5.patch @@ -0,0 +1,67 @@ +From f527eaeb132dcd5bb06115b987d6a6f8bfafac9b Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Sun, 10 Jan 2021 16:25:29 +0000 +Subject: [PATCH] portal: Do not use caller-supplied variables in + environment + +If the caller specifies a variable that can be used to inject arbitrary +code into processes, we must not allow it to enter the environment +block used to run `flatpak run`, which runs unsandboxed. + +This change requires the previous commit "context: Add --env-fd option", +which adds infrastructure used here. + +To be secure, this change also requires the previous commit +"run: Convert all environment variables into bwrap arguments", which +protects a non-setuid bwrap(1) from the same attack. + +Signed-off-by: Simon McVittie +Part-of: https://github.com/flatpak/flatpak/security/advisories/GHSA-4ppf-fxf6-vxg2 +--- + portal/flatpak-portal.c | 28 +++++++++++++++++++++++++++- + 1 file changed, 27 insertions(+), 1 deletion(-) + +--- flatpak.orig/portal/flatpak-portal.c ++++ flatpak/portal/flatpak-portal.c +@@ -506,6 +506,13 @@ handle_spawn (PortalFlatpak *obj + else + env = g_get_environ (); + ++ /* Let the environment variables given by the caller override the ones ++ * from extra_args. Don't add them to @env, because they are controlled ++ * by our caller, which might be trying to use them to inject code into ++ * flatpak(1); add them to the environment block instead. ++ * ++ * We don't use --env= here, so that if the values are something that ++ * should not be exposed to other uids, they can remain confidential. */ + n_envs = g_variant_n_children (arg_envs); + for (i = 0; i < n_envs; i++) + { +@@ -513,7 +520,26 @@ handle_spawn (PortalFlatpak *obj + const char *val = NULL; + g_variant_get_child (arg_envs, i, "{&s&s}", &var, &val); + +- env = g_environ_setenv (env, var, val, TRUE); ++ if (var[0] == '\0') ++ { ++ g_dbus_method_invocation_return_error (invocation, G_DBUS_ERROR, ++ G_DBUS_ERROR_INVALID_ARGS, ++ "Environment variable cannot have empty name"); ++ return G_DBUS_METHOD_INVOCATION_HANDLED; ++ } ++ ++ if (strchr (var, '=') != NULL) ++ { ++ g_dbus_method_invocation_return_error (invocation, G_DBUS_ERROR, ++ G_DBUS_ERROR_INVALID_ARGS, ++ "Environment variable name cannot contain '='"); ++ return G_DBUS_METHOD_INVOCATION_HANDLED; ++ } ++ ++ g_string_append (env_string, var); ++ g_string_append_c (env_string, '='); ++ g_string_append (env_string, val); ++ g_string_append_c (env_string, '\0'); + } + + g_ptr_array_add (flatpak_argv, g_strdup ("flatpak")); diff --git a/CVE-2021-21381-1.patch b/CVE-2021-21381-1.patch new file mode 100644 index 0000000..1aaa456 --- /dev/null +++ b/CVE-2021-21381-1.patch @@ -0,0 +1,23 @@ +From 652a28ffab67cb6cd7d12dc3a93979bcd3731c7f Mon Sep 17 00:00:00 2001 +From: Ryan Gonzalez +Date: Tue, 2 Mar 2021 13:20:07 -0600 +Subject: [PATCH] Disallow @@ and @@u usage in desktop files + +Fixes #4146. +--- + common/flatpak-dir.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c +index e6e4d6fb3..7d3374dad 100644 +--- a/common/flatpak-dir.c ++++ b/common/flatpak-dir.c +@@ -5828,6 +5828,8 @@ export_desktop_file (const char *app, + g_string_append_printf (new_exec, " @@ %s @@", arg); + else if (strcasecmp (arg, "%u") == 0) + g_string_append_printf (new_exec, " @@u %s @@", arg); ++ else if (strcmp (arg, "@@") == 0 || strcmp (arg, "@@u") == 0) ++ g_print (_("Skipping invalid Exec argument %s\n"), arg); + else + g_string_append_printf (new_exec, " %s", arg); + } diff --git a/CVE-2021-21381-2.patch b/CVE-2021-21381-2.patch new file mode 100644 index 0000000..2a4a3d6 --- /dev/null +++ b/CVE-2021-21381-2.patch @@ -0,0 +1,27 @@ +From 1e7e8fdb24b51078f4c48e0711e24a14930ba1f0 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Fri, 5 Mar 2021 13:49:36 +0000 +Subject: [PATCH] dir: Reserve the whole @@ prefix + +If we add new features analogous to file forwarding later, we might +find that we need a different magic token. Let's reserve the whole +@@* namespace so we can call it @@something-else. + +Signed-off-by: Simon McVittie +--- + common/flatpak-dir.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c +index 7d3374dad..facfab37a 100644 +--- a/common/flatpak-dir.c ++++ b/common/flatpak-dir.c +@@ -5828,7 +5828,7 @@ export_desktop_file (const char *app, + g_string_append_printf (new_exec, " @@ %s @@", arg); + else if (strcasecmp (arg, "%u") == 0) + g_string_append_printf (new_exec, " @@u %s @@", arg); +- else if (strcmp (arg, "@@") == 0 || strcmp (arg, "@@u") == 0) ++ else if (g_str_has_prefix (arg, "@@")) + g_print (_("Skipping invalid Exec argument %s\n"), arg); + else + g_string_append_printf (new_exec, " %s", arg); diff --git a/CVE-2021-21381-3.patch b/CVE-2021-21381-3.patch new file mode 100644 index 0000000..ceb4fcc --- /dev/null +++ b/CVE-2021-21381-3.patch @@ -0,0 +1,34 @@ +From 46b3ede5241561c7d588951048c687c5075a3eac Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Fri, 5 Mar 2021 13:51:33 +0000 +Subject: [PATCH] dir: Refuse to export .desktop files with suspicious uses of + @@ tokens + +This is either a malicious/compromised app trying to do an attack, or +a mistake that will break handling of %f, %u and so on. Either way, +if we refuse to export the .desktop file, resulting in installation +failing, then it makes the rejection more obvious than quietly +removing the magic tokens. + +Signed-off-by: Simon McVittie +--- + common/flatpak-dir.c | 6 +++++- + 1 file changed, 5 insertions(+), 1 deletion(-) + +diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c +index facfab37a..c5edf346f 100644 +--- a/common/flatpak-dir.c ++++ b/common/flatpak-dir.c +@@ -5829,7 +5829,11 @@ export_desktop_file (const char *app, + else if (strcasecmp (arg, "%u") == 0) + g_string_append_printf (new_exec, " @@u %s @@", arg); + else if (g_str_has_prefix (arg, "@@")) +- g_print (_("Skipping invalid Exec argument %s\n"), arg); ++ { ++ flatpak_fail_error (error, FLATPAK_ERROR_EXPORT_FAILED, ++ _("Invalid Exec argument %s"), arg); ++ goto out; ++ } + else + g_string_append_printf (new_exec, " %s", arg); + } diff --git a/backport-0001-CVE-2021-41133.patch b/backport-0001-CVE-2021-41133.patch new file mode 100644 index 0000000..41f759c --- /dev/null +++ b/backport-0001-CVE-2021-41133.patch @@ -0,0 +1,146 @@ +From e26ac7586c392b5eb35ff4609fe232c52523b2cf Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 11:53:23 +0100 +Subject: [PATCH] run: Add an errno value to seccomp filters + +At the moment, if we block a syscall we always make it fail with EPERM, +but this is risky: user-space libraries can start to use new replacements +for old syscalls at any time, and will often treat EPERM as a fatal error. +For new syscalls, we should make the syscall fail with ENOSYS, which is +indistinguishable from running on an older kernel and will cause fallback +to an older implementation, for example clone3() to clone(). + +In future we should probably move from EPERM to ENOSYS for some of the +syscalls we already block, but for now keep the status quo. + +This is a prerequisite for fixing the vulnerability tracked as +GHSA-67h7-w3jq-vh4q. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/e26ac7586c392b5eb35ff4609fe232c52523b2cf + +--- + common/flatpak-run.c | 62 +++++++++++++++++++++++++------------------- + 1 file changed, 36 insertions(+), 26 deletions(-) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 79b30cb..7476d86 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2098,54 +2098,56 @@ setup_seccomp (FlatpakBwrap *bwrap, + struct + { + int scall; ++ int errnum; + struct scmp_arg_cmp *arg; + } syscall_blacklist[] = { + /* Block dmesg */ +- {SCMP_SYS (syslog)}, ++ {SCMP_SYS (syslog), EPERM}, + /* Useless old syscall */ +- {SCMP_SYS (uselib)}, ++ {SCMP_SYS (uselib), EPERM}, + /* Don't allow disabling accounting */ +- {SCMP_SYS (acct)}, ++ {SCMP_SYS (acct), EPERM}, + /* 16-bit code is unnecessary in the sandbox, and modify_ldt is a + historic source of interesting information leaks. */ +- {SCMP_SYS (modify_ldt)}, ++ {SCMP_SYS (modify_ldt), EPERM}, + /* Don't allow reading current quota use */ +- {SCMP_SYS (quotactl)}, ++ {SCMP_SYS (quotactl), EPERM}, + + /* Don't allow access to the kernel keyring */ +- {SCMP_SYS (add_key)}, +- {SCMP_SYS (keyctl)}, +- {SCMP_SYS (request_key)}, ++ {SCMP_SYS (add_key), EPERM}, ++ {SCMP_SYS (keyctl), EPERM}, ++ {SCMP_SYS (request_key), EPERM}, + + /* Scary VM/NUMA ops */ +- {SCMP_SYS (move_pages)}, +- {SCMP_SYS (mbind)}, +- {SCMP_SYS (get_mempolicy)}, +- {SCMP_SYS (set_mempolicy)}, +- {SCMP_SYS (migrate_pages)}, ++ {SCMP_SYS (move_pages), EPERM}, ++ {SCMP_SYS (mbind), EPERM}, ++ {SCMP_SYS (get_mempolicy), EPERM}, ++ {SCMP_SYS (set_mempolicy), EPERM}, ++ {SCMP_SYS (migrate_pages), EPERM}, + + /* Don't allow subnamespace setups: */ +- {SCMP_SYS (unshare)}, +- {SCMP_SYS (mount)}, +- {SCMP_SYS (pivot_root)}, +- {SCMP_SYS (clone), &SCMP_A0 (SCMP_CMP_MASKED_EQ, CLONE_NEWUSER, CLONE_NEWUSER)}, ++ {SCMP_SYS (unshare), EPERM}, ++ {SCMP_SYS (mount), EPERM}, ++ {SCMP_SYS (pivot_root), EPERM}, ++ {SCMP_SYS (clone), EPERM, &SCMP_A0 (SCMP_CMP_MASKED_EQ, CLONE_NEWUSER, CLONE_NEWUSER)}, + + /* Don't allow faking input to the controlling tty (CVE-2017-5226) */ +- {SCMP_SYS (ioctl), &SCMP_A1 (SCMP_CMP_MASKED_EQ, 0xFFFFFFFFu, (int) TIOCSTI)}, ++ {SCMP_SYS (ioctl), EPERM, &SCMP_A1 (SCMP_CMP_MASKED_EQ, 0xFFFFFFFFu, (int) TIOCSTI)}, + }; + + struct + { + int scall; ++ int errnum; + struct scmp_arg_cmp *arg; + } syscall_nondevel_blacklist[] = { + /* Profiling operations; we expect these to be done by tools from outside + * the sandbox. In particular perf has been the source of many CVEs. + */ +- {SCMP_SYS (perf_event_open)}, ++ {SCMP_SYS (perf_event_open), EPERM}, + /* Don't allow you to switch to bsd emulation or whatnot */ +- {SCMP_SYS (personality), &SCMP_A0 (SCMP_CMP_NE, allowed_personality)}, +- {SCMP_SYS (ptrace)} ++ {SCMP_SYS (personality), EPERM, &SCMP_A0 (SCMP_CMP_NE, allowed_personality)}, ++ {SCMP_SYS (ptrace), EPERM} + }; + /* Blacklist all but unix, inet, inet6 and netlink */ + struct +@@ -2230,10 +2232,14 @@ setup_seccomp (FlatpakBwrap *bwrap, + for (i = 0; i < G_N_ELEMENTS (syscall_blacklist); i++) + { + int scall = syscall_blacklist[i].scall; ++ int errnum = syscall_blacklist[i].errnum; ++ ++ g_return_val_if_fail (errnum == EPERM || errnum == ENOSYS, FALSE); ++ + if (syscall_blacklist[i].arg) +- r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (EPERM), scall, 1, *syscall_blacklist[i].arg); ++ r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 1, *syscall_blacklist[i].arg); + else +- r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (EPERM), scall, 0); ++ r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 0); + if (r < 0 && r == -EFAULT /* unknown syscall */) + return flatpak_fail_error (error, FLATPAK_ERROR_SETUP_FAILED, _("Failed to block syscall %d"), scall); + } +@@ -2243,10 +2249,14 @@ setup_seccomp (FlatpakBwrap *bwrap, + for (i = 0; i < G_N_ELEMENTS (syscall_nondevel_blacklist); i++) + { + int scall = syscall_nondevel_blacklist[i].scall; ++ int errnum = syscall_nondevel_blacklist[i].errnum; ++ ++ g_return_val_if_fail (errnum == EPERM || errnum == ENOSYS, FALSE); ++ + if (syscall_nondevel_blacklist[i].arg) +- r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (EPERM), scall, 1, *syscall_nondevel_blacklist[i].arg); ++ r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 1, *syscall_nondevel_blacklist[i].arg); + else +- r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (EPERM), scall, 0); ++ r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 0); + + if (r < 0 && r == -EFAULT /* unknown syscall */) + return flatpak_fail_error (error, FLATPAK_ERROR_SETUP_FAILED, _("Failed to block syscall %d"), scall); +-- +2.19.1 + diff --git a/backport-0001-CVE-2021-43860.patch b/backport-0001-CVE-2021-43860.patch new file mode 100644 index 0000000..dd6bfb4 --- /dev/null +++ b/backport-0001-CVE-2021-43860.patch @@ -0,0 +1,36 @@ +From 65cbfac982cb1c83993a9e19aa424daee8e9f042 Mon Sep 17 00:00:00 2001 +From: Alexander Larsson +Date: Wed, 12 Jan 2022 11:00:56 +0100 +Subject: [PATCH] Ensure that bundles have metadata on install + +If we have a bundle without metadata we wouldn't properly present +the permissions in the transaction. + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/65cbfac982cb1c83993a9e19aa424daee8e9f042 + +--- + common/flatpak-dir.c | 7 +++++++ + 1 file changed, 7 insertions(+) + +diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c +index 56bca24..d6929ba 100644 +--- a/common/flatpak-dir.c ++++ b/common/flatpak-dir.c +@@ -7608,6 +7608,13 @@ flatpak_dir_ensure_bundle_remote (FlatpakDir *self, + if (metadata == NULL) + return NULL; + ++ /* If we rely on metadata (to e.g. print permissions), check it exists before creating the remote */ ++ if (out_metadata && fp_metadata == NULL) ++ { ++ flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, "No metadata in bundler header"); ++ return NULL; ++ } ++ + gpg_data = extra_gpg_data ? extra_gpg_data : included_gpg_data; + + parts = flatpak_decompose_ref (ref, error); +-- +2.27.0 + diff --git a/backport-0001-CVE-2022-21682.patch b/backport-0001-CVE-2022-21682.patch new file mode 100644 index 0000000..a1251ca --- /dev/null +++ b/backport-0001-CVE-2022-21682.patch @@ -0,0 +1,60 @@ +From 949a3ec479d5ca0c962cf12adec70aea30bf0186 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Mon, 20 Jan 2020 19:20:14 +0000 +Subject: [PATCH] context: Generalize handling of special filesystems a bit + +Currently there are only "home" and "host", but I'm going to add one +that represents /usr and friends (/usr, /lib, ...), and one for /etc. +These differ from ordinary filesystem mounts because they are redirected +into /run/host to avoid conflicting with the runtime. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/949a3ec479d5ca0c962cf12adec70aea30bf0186 + +--- + common/flatpak-context.c | 13 ++++++++----- + 1 file changed, 8 insertions(+), 5 deletions(-) + +diff --git a/common/flatpak-context.c b/common/flatpak-context.c +index 6df9b1e..4892d7b 100644 +--- a/common/flatpak-context.c ++++ b/common/flatpak-context.c +@@ -78,6 +78,12 @@ const char *flatpak_context_features[] = { + NULL + }; + ++const char *flatpak_context_special_filesystems[] = { ++ "home", ++ "host", ++ NULL ++}; ++ + FlatpakContext * + flatpak_context_new (void) + { +@@ -747,9 +753,7 @@ flatpak_context_verify_filesystem (const char *filesystem_and_mode, + { + g_autofree char *filesystem = parse_filesystem_flags (filesystem_and_mode, NULL); + +- if (strcmp (filesystem, "host") == 0) +- return TRUE; +- if (strcmp (filesystem, "home") == 0) ++ if (g_strv_contains (flatpak_context_special_filesystems, filesystem)) + return TRUE; + if (get_xdg_user_dir_from_string (filesystem, NULL, NULL, NULL)) + return TRUE; +@@ -1988,8 +1992,7 @@ flatpak_context_export (FlatpakContext *context, + const char *filesystem = key; + FlatpakFilesystemMode mode = GPOINTER_TO_INT (value); + +- if (strcmp (filesystem, "host") == 0 || +- strcmp (filesystem, "home") == 0) ++ if (g_strv_contains (flatpak_context_special_filesystems, filesystem)) + continue; + + if (g_str_has_prefix (filesystem, "xdg-")) +-- +2.27.0 + diff --git a/backport-0002-CVE-2021-41133.patch b/backport-0002-CVE-2021-41133.patch new file mode 100644 index 0000000..7899c17 --- /dev/null +++ b/backport-0002-CVE-2021-41133.patch @@ -0,0 +1,34 @@ +From 89ae9fe74c6d445bb1b3a40e568d77cf5de47e48 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 12:44:04 +0100 +Subject: [PATCH] run: Add cross-references for some other seccomp syscall + filters + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/89ae9fe74c6d445bb1b3a40e568d77cf5de47e48 + +--- + common/flatpak-run.c | 4 ++++ + 1 file changed, 4 insertions(+) + + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 7476d86..f2f296e 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2093,6 +2093,10 @@ setup_seccomp (FlatpakBwrap *bwrap, + * https://git.gnome.org/browse/linux-user-chroot + * in src/setup-seccomp.c + * ++ * Other useful resources: ++ * https://github.com/systemd/systemd/blob/HEAD/src/shared/seccomp-util.c ++ * https://github.com/moby/moby/blob/HEAD/profiles/seccomp/default.json ++ * + **** END NOTE ON CODE SHARING + */ + struct +-- +2.19.1 + diff --git a/backport-0002-CVE-2021-43860.patch b/backport-0002-CVE-2021-43860.patch new file mode 100644 index 0000000..4f1ec85 --- /dev/null +++ b/backport-0002-CVE-2021-43860.patch @@ -0,0 +1,115 @@ +From ba818f504c926baaf6e362be8159cfacf994310e Mon Sep 17 00:00:00 2001 +From: Ryan Gonzalez +Date: Thu, 23 Dec 2021 18:30:17 -0600 +Subject: [PATCH] Fix metadata file contents after null terminators being + ignored + +In particular, if a null terminator is placed inside the metadata file, +Flatpak will only compare the text *before* it to the value of +xa.metadata, but the full file will be parsed when permissions are set +at runtime. This means that any app can include a null terminator in its +permissions metadata, and Flatpak will only show the user the +permissions *preceding* the terminator during install, but the +permissions *after* the terminator are applied at runtime. + +Fixes GHSA-qpjc-vq3c-572j / CVE-2021-43860 + +Signed-off-by: Ryan Gonzalez + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/ba818f504c926baaf6e362be8159cfacf994310e + +--- + common/flatpak-dir.c | 5 +++-- + common/flatpak-transaction.c | 4 ++-- + common/flatpak-utils.c | 9 +++++---- + 3 files changed, 10 insertions(+), 8 deletions(-) + +diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c +index 56bca24..5af4b4b 100644 +--- a/common/flatpak-dir.c ++++ b/common/flatpak-dir.c +@@ -6608,6 +6608,7 @@ flatpak_dir_deploy (FlatpakDir *self, + g_autoptr(GFile) metadata_file = NULL; + g_autofree char *metadata_contents = NULL; + g_autofree char *application_runtime = NULL; ++ gsize metadata_size = 0; + gboolean is_app; + + if (!flatpak_dir_ensure_repo (self, cancellable, error)) +@@ -6850,12 +6851,12 @@ flatpak_dir_deploy (FlatpakDir *self, + + metadata_file = g_file_resolve_relative_path (checkoutdir, "metadata"); + if (g_file_load_contents (metadata_file, NULL, +- &metadata_contents, NULL, NULL, NULL)) ++ &metadata_contents, &metadata_size, NULL, NULL)) + { + g_autoptr(GKeyFile) keyfile = g_key_file_new (); + if (!g_key_file_load_from_data (keyfile, + metadata_contents, +- -1, ++ metadata_size, + 0, error)) + return FALSE; + +diff --git a/common/flatpak-transaction.c b/common/flatpak-transaction.c +index 396d75c..4e19e5d 100644 +--- a/common/flatpak-transaction.c ++++ b/common/flatpak-transaction.c +@@ -1604,7 +1604,7 @@ flatpak_transaction_add_ref (FlatpakTransaction *self, + + op = flatpak_transaction_add_op (self, remote, ref, subpaths, commit, bundle, kind); + if (external_metadata) +- op->external_metadata = g_bytes_new (external_metadata, strlen (external_metadata) + 1); ++ op->external_metadata = g_bytes_new (external_metadata, strlen (external_metadata)); + + return TRUE; + } +@@ -1839,7 +1839,7 @@ load_deployed_metadata (FlatpakTransaction *self, const char *ref) + return NULL; + } + +- return g_bytes_new_take (g_steal_pointer (&metadata_contents), metadata_contents_length + 1); ++ return g_bytes_new_take (g_steal_pointer (&metadata_contents), metadata_contents_length); + } + + static void +diff --git a/common/flatpak-utils.c b/common/flatpak-utils.c +index 23b72d6..accf230 100644 +--- a/common/flatpak-utils.c ++++ b/common/flatpak-utils.c +@@ -4674,6 +4674,7 @@ flatpak_pull_from_bundle (OstreeRepo *repo, + GCancellable *cancellable, + GError **error) + { ++ gsize metadata_size = 0; + g_autofree char *metadata_contents = NULL; + g_autofree char *to_checksum = NULL; + +@@ -4691,6 +4692,8 @@ flatpak_pull_from_bundle (OstreeRepo *repo, + if (metadata == NULL) + return FALSE; + ++ metadata_size = strlen (metadata_contents); ++ + if (!ostree_repo_get_remote_option (repo, remote, "collection-id", NULL, + &remote_collection_id, NULL)) + remote_collection_id = NULL; +@@ -4760,12 +4763,10 @@ flatpak_pull_from_bundle (OstreeRepo *repo, + cancellable, error) < 0) + return FALSE; + +- /* Null terminate */ +- g_output_stream_write (G_OUTPUT_STREAM (data_stream), "\0", 1, NULL, NULL); +- + metadata_valid = + metadata_contents != NULL && +- strcmp (metadata_contents, g_memory_output_stream_get_data (data_stream)) == 0; ++ metadata_size == g_memory_output_stream_get_data_size (data_stream) && ++ memcmp (metadata_contents, g_memory_output_stream_get_data (data_stream), metadata_size) == 0; + } + else + { +-- +2.27.0 + diff --git a/backport-0002-CVE-2022-21682.patch b/backport-0002-CVE-2022-21682.patch new file mode 100644 index 0000000..c13dca4 --- /dev/null +++ b/backport-0002-CVE-2022-21682.patch @@ -0,0 +1,276 @@ +From 517ad25b5fe83376af258acef646551cb97af97c Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Mon, 10 Aug 2020 23:58:11 +0100 +Subject: [PATCH] context: Only parse filesystem/mode strings in one place + +This gives us the ability for the parse function (the former verify +function) to carry out a normalization step as well. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/517ad25b5fe83376af258acef646551cb97af97c + +--- + common/flatpak-context.c | 77 +++++++++++++++++--------------- + common/flatpak-exports-private.h | 1 + + common/flatpak-exports.c | 14 +++--- + 3 files changed, 48 insertions(+), 44 deletions(-) + +diff --git a/common/flatpak-context.c b/common/flatpak-context.c +index 4892d7b..3a99646 100644 +--- a/common/flatpak-context.c ++++ b/common/flatpak-context.c +@@ -92,6 +92,7 @@ flatpak_context_new (void) + context = g_slice_new0 (FlatpakContext); + context->env_vars = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_free); + context->persistent = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); ++ /* filename or special filesystem name => FlatpakFilesystemMode */ + context->filesystems = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); + context->session_bus_policy = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); + context->system_bus_policy = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); +@@ -748,19 +749,23 @@ parse_filesystem_flags (const char *filesystem, + } + + static gboolean +-flatpak_context_verify_filesystem (const char *filesystem_and_mode, +- GError **error) ++flatpak_context_parse_filesystem (const char *filesystem_and_mode, ++ char **filesystem_out, ++ FlatpakFilesystemMode *mode_out, ++ GError **error) + { +- g_autofree char *filesystem = parse_filesystem_flags (filesystem_and_mode, NULL); ++ g_autofree char *filesystem = parse_filesystem_flags (filesystem_and_mode, mode_out); + +- if (g_strv_contains (flatpak_context_special_filesystems, filesystem)) +- return TRUE; +- if (get_xdg_user_dir_from_string (filesystem, NULL, NULL, NULL)) +- return TRUE; +- if (g_str_has_prefix (filesystem, "~/")) +- return TRUE; +- if (g_str_has_prefix (filesystem, "/")) +- return TRUE; ++ if (g_strv_contains (flatpak_context_special_filesystems, filesystem) || ++ get_xdg_user_dir_from_string (filesystem, NULL, NULL, NULL) || ++ g_str_has_prefix (filesystem, "~/") || ++ g_str_has_prefix (filesystem, "/")) ++ { ++ if (filesystem_out != NULL) ++ *filesystem_out = g_steal_pointer (&filesystem); ++ ++ return TRUE; ++ } + + g_set_error (error, G_OPTION_ERROR, G_OPTION_ERROR_FAILED, + _("Unknown filesystem location %s, valid locations are: host, home, xdg-*[/...], ~/dir, /dir"), filesystem); +@@ -768,24 +773,13 @@ flatpak_context_verify_filesystem (const char *filesystem_and_mode, + } + + static void +-flatpak_context_add_filesystem (FlatpakContext *context, +- const char *what) ++flatpak_context_take_filesystem (FlatpakContext *context, ++ char *fs, ++ FlatpakFilesystemMode mode) + { +- FlatpakFilesystemMode mode; +- char *fs = parse_filesystem_flags (what, &mode); +- + g_hash_table_insert (context->filesystems, fs, GINT_TO_POINTER (mode)); + } + +-static void +-flatpak_context_remove_filesystem (FlatpakContext *context, +- const char *what) +-{ +- g_hash_table_insert (context->filesystems, +- parse_filesystem_flags (what, NULL), +- NULL); +-} +- + void + flatpak_context_merge (FlatpakContext *context, + FlatpakContext *other) +@@ -999,11 +993,13 @@ option_filesystem_cb (const gchar *option_name, + GError **error) + { + FlatpakContext *context = data; ++ g_autofree char *fs = NULL; ++ FlatpakFilesystemMode mode; + +- if (!flatpak_context_verify_filesystem (value, error)) ++ if (!flatpak_context_parse_filesystem (value, &fs, &mode, error)) + return FALSE; + +- flatpak_context_add_filesystem (context, value); ++ flatpak_context_take_filesystem (context, g_steal_pointer (&fs), mode); + return TRUE; + } + +@@ -1014,11 +1010,14 @@ option_nofilesystem_cb (const gchar *option_name, + GError **error) + { + FlatpakContext *context = data; ++ g_autofree char *fs = NULL; ++ FlatpakFilesystemMode mode; + +- if (!flatpak_context_verify_filesystem (value, error)) ++ if (!flatpak_context_parse_filesystem (value, &fs, &mode, error)) + return FALSE; + +- flatpak_context_remove_filesystem (context, value); ++ flatpak_context_take_filesystem (context, g_steal_pointer (&fs), ++ FLATPAK_FILESYSTEM_MODE_NONE); + return TRUE; + } + +@@ -1441,14 +1440,18 @@ flatpak_context_load_metadata (FlatpakContext *context, + for (i = 0; filesystems[i] != NULL; i++) + { + const char *fs = parse_negated (filesystems[i], &remove); +- if (!flatpak_context_verify_filesystem (fs, NULL)) ++ g_autofree char *filesystem = NULL; ++ FlatpakFilesystemMode mode; ++ ++ if (!flatpak_context_parse_filesystem (fs, &filesystem, &mode, NULL)) + g_debug ("Unknown filesystem type %s", filesystems[i]); + else + { + if (remove) +- flatpak_context_remove_filesystem (context, fs); ++ flatpak_context_take_filesystem (context, g_steal_pointer (&filesystem), ++ FLATPAK_FILESYSTEM_MODE_NONE); + else +- flatpak_context_add_filesystem (context, fs); ++ flatpak_context_take_filesystem (context, g_steal_pointer (&filesystem), mode); + } + } + } +@@ -1674,7 +1677,7 @@ flatpak_context_save_metadata (FlatpakContext *context, + { + FlatpakFilesystemMode mode = GPOINTER_TO_INT (value); + +- if (mode != 0) ++ if (mode != FLATPAK_FILESYSTEM_MODE_NONE) + g_ptr_array_add (array, unparse_filesystem_flags (key, mode)); + else + g_ptr_array_add (array, g_strconcat ("!", key, NULL)); +@@ -1781,7 +1784,7 @@ flatpak_context_save_metadata (FlatpakContext *context, + void + flatpak_context_allow_host_fs (FlatpakContext *context) + { +- flatpak_context_add_filesystem (context, "host"); ++ flatpak_context_take_filesystem (context, g_strdup ("host"), FLATPAK_FILESYSTEM_MODE_READ_WRITE); + } + + gboolean +@@ -1846,7 +1849,7 @@ flatpak_context_to_args (FlatpakContext *context, + { + FlatpakFilesystemMode mode = GPOINTER_TO_INT (value); + +- if (mode != 0) ++ if (mode != FLATPAK_FILESYSTEM_MODE_NONE) + { + g_autofree char *fs = unparse_filesystem_flags (key, mode); + g_ptr_array_add (args, g_strdup_printf ("--filesystem=%s", fs)); +@@ -1949,7 +1952,7 @@ flatpak_context_export (FlatpakContext *context, + gpointer key, value; + + fs_mode = (FlatpakFilesystemMode) g_hash_table_lookup (context->filesystems, "host"); +- if (fs_mode != 0) ++ if (fs_mode != FLATPAK_FILESYSTEM_MODE_NONE) + { + DIR *dir; + struct dirent *dirent; +@@ -1978,7 +1981,7 @@ flatpak_context_export (FlatpakContext *context, + } + + home_mode = (FlatpakFilesystemMode) g_hash_table_lookup (context->filesystems, "home"); +- if (home_mode != 0) ++ if (home_mode != FLATPAK_FILESYSTEM_MODE_NONE) + { + g_debug ("Allowing homedir access"); + home_access = TRUE; +diff --git a/common/flatpak-exports-private.h b/common/flatpak-exports-private.h +index 64cf59a..e4b2c14 100644 +--- a/common/flatpak-exports-private.h ++++ b/common/flatpak-exports-private.h +@@ -26,6 +26,7 @@ + + /* In numerical order of more privs */ + typedef enum { ++ FLATPAK_FILESYSTEM_MODE_NONE = 0, + FLATPAK_FILESYSTEM_MODE_READ_ONLY = 1, + FLATPAK_FILESYSTEM_MODE_READ_WRITE = 2, + FLATPAK_FILESYSTEM_MODE_CREATE = 3, +diff --git a/common/flatpak-exports.c b/common/flatpak-exports.c +index 21a8b17..d31ef95 100644 +--- a/common/flatpak-exports.c ++++ b/common/flatpak-exports.c +@@ -80,7 +80,7 @@ make_relative (const char *base, const char *path) + } + + #define FAKE_MODE_DIR -1 /* Ensure a dir, either on tmpfs or mapped parent */ +-#define FAKE_MODE_TMPFS 0 ++#define FAKE_MODE_TMPFS FLATPAK_FILESYSTEM_MODE_NONE + #define FAKE_MODE_SYMLINK G_MAXINT + + typedef struct +@@ -278,7 +278,7 @@ flatpak_exports_append_bwrap_args (FlatpakExports *exports, + } + } + +- if (exports->host_fs != 0) ++ if (exports->host_fs != FLATPAK_FILESYSTEM_MODE_NONE) + { + if (g_file_test ("/usr", G_FILE_TEST_IS_DIR)) + flatpak_bwrap_add_args (bwrap, +@@ -337,7 +337,7 @@ flatpak_exports_path_get_mode (FlatpakExports *exports, + break; + } + +- return 0; ++ return FLATPAK_FILESYSTEM_MODE_NONE; + } + + if (S_ISLNK (st.st_mode)) +@@ -347,7 +347,7 @@ flatpak_exports_path_get_mode (FlatpakExports *exports, + int j; + + if (resolved == NULL) +- return 0; ++ return FLATPAK_FILESYSTEM_MODE_NONE; + + path2_builder = g_string_new (resolved); + +@@ -361,7 +361,7 @@ flatpak_exports_path_get_mode (FlatpakExports *exports, + } + } + else if (parts[i + 1] == NULL) +- return 0; /* Last part was not mapped */ ++ return FLATPAK_FILESYSTEM_MODE_NONE; /* Last part was not mapped */ + } + + if (is_readonly) +@@ -374,7 +374,7 @@ gboolean + flatpak_exports_path_is_visible (FlatpakExports *exports, + const char *path) + { +- return flatpak_exports_path_get_mode (exports, path) > 0; ++ return flatpak_exports_path_get_mode (exports, path) > FLATPAK_FILESYSTEM_MODE_NONE; + } + + static gboolean +@@ -605,7 +605,7 @@ flatpak_exports_add_path_expose_or_hide (FlatpakExports *exports, + FlatpakFilesystemMode mode, + const char *path) + { +- if (mode == 0) ++ if (mode == FLATPAK_FILESYSTEM_MODE_NONE) + flatpak_exports_add_path_tmpfs (exports, path); + else + flatpak_exports_add_path_expose (exports, mode, path); +-- +2.27.0 + diff --git a/backport-0003-CVE-2021-41133.patch b/backport-0003-CVE-2021-41133.patch new file mode 100644 index 0000000..0b542af --- /dev/null +++ b/backport-0003-CVE-2021-41133.patch @@ -0,0 +1,254 @@ +From 26b12484eb8a6219b9e7aa287b298a894b2f34ca Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 14:17:04 +0100 +Subject: [PATCH] common: Add a list of recently-added Linux syscalls + +Historically, syscalls could take arbitrarily-different values on +different architectures, but new syscalls are added with syscall numbers +that align on each architecture. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/26b12484eb8a6219b9e7aa287b298a894b2f34ca + +--- + + common/Makefile.am.inc | 1 + + common/flatpak-run.c | 2 + + common/flatpak-syscalls-private.h | 197 ++++++++++++++++++++++++++++++ + 3 files changed, 200 insertions(+) + create mode 100644 common/flatpak-syscalls-private.h + + +diff --git a/common/Makefile.am.inc b/common/Makefile.am.inc +index 794bd4e..986a1ea 100644 +--- a/common/Makefile.am.inc ++++ b/common/Makefile.am.inc +@@ -85,6 +85,7 @@ libflatpak_common_la_SOURCES = \ + common/flatpak-dir.c \ + common/flatpak-dir-private.h \ + common/flatpak-run.c \ ++ common/flatpak-syscalls-private.h \ + common/flatpak-run-private.h \ + common/flatpak-context.c \ + common/flatpak-context-private.h \ +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index f2f296e..de3dd38 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -33,6 +33,8 @@ + #include + #include + ++#include "flatpak-syscalls-private.h" ++ + #ifdef ENABLE_SECCOMP + #include + #endif +diff --git a/common/flatpak-syscalls-private.h b/common/flatpak-syscalls-private.h +new file mode 100644 +index 0000000..04eb38c +--- /dev/null ++++ b/common/flatpak-syscalls-private.h +@@ -0,0 +1,197 @@ ++/* ++ * Copyright 2021 Collabora Ltd. ++ * SPDX-License-Identifier: LGPL-2.1-or-later ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU Lesser General Public ++ * License as published by the Free Software Foundation; either ++ * version 2.1 of the License, or (at your option) any later version. ++ * ++ * This library is distributed in the hope that it will be useful, ++ * but WITHOUT ANY WARRANTY; without even the implied warranty of ++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ++ * Lesser General Public License for more details. ++ * ++ * You should have received a copy of the GNU Lesser General Public ++ * License along with this library. If not, see . ++ */ ++ ++#pragma once ++ ++#include ++ ++#if defined(_MIPS_SIM) ++# if _MIPS_SIM == _MIPS_SIM_ABI32 ++# define FLATPAK_MISSING_SYSCALL_BASE 4000 ++# elif _MIPS_SIM == _MIPS_SIM_ABI64 ++# define FLATPAK_MISSING_SYSCALL_BASE 5000 ++# elif _MIPS_SIM == _MIPS_SIM_NABI32 ++# define FLATPAK_MISSING_SYSCALL_BASE 6000 ++# else ++# error "Unknown MIPS ABI" ++# endif ++#endif ++ ++#if defined(__ia64__) ++# define FLATPAK_MISSING_SYSCALL_BASE 1024 ++#endif ++ ++#if defined(__alpha__) ++# define FLATPAK_MISSING_SYSCALL_BASE 110 ++#endif ++ ++#if defined(__x86_64__) && defined(__ILP32__) ++# define FLATPAK_MISSING_SYSCALL_BASE 0x40000000 ++#endif ++ ++/* ++ * FLATPAK_MISSING_SYSCALL_BASE: ++ * ++ * Number to add to the syscall numbers of recently-added syscalls ++ * to get the appropriate syscall for the current ABI. ++ */ ++#ifndef FLATPAK_MISSING_SYSCALL_BASE ++# define FLATPAK_MISSING_SYSCALL_BASE 0 ++#endif ++ ++#ifndef __NR_open_tree ++# define __NR_open_tree (FLATPAK_MISSING_SYSCALL_BASE + 428) ++#endif ++#ifndef __SNR_open_tree ++# define __SNR_open_tree __NR_open_tree ++#endif ++ ++#ifndef __NR_move_mount ++# define __NR_move_mount (FLATPAK_MISSING_SYSCALL_BASE + 429) ++#endif ++#ifndef __SNR_move_mount ++# define __SNR_move_mount __NR_move_mount ++#endif ++ ++#ifndef __NR_fsopen ++# define __NR_fsopen (FLATPAK_MISSING_SYSCALL_BASE + 430) ++#endif ++#ifndef __SNR_fsopen ++# define __SNR_fsopen __NR_fsopen ++#endif ++ ++#ifndef __NR_fsconfig ++# define __NR_fsconfig (FLATPAK_MISSING_SYSCALL_BASE + 431) ++#endif ++#ifndef __SNR_fsconfig ++# define __SNR_fsconfig __NR_fsconfig ++#endif ++ ++#ifndef __NR_fsmount ++# define __NR_fsmount (FLATPAK_MISSING_SYSCALL_BASE + 432) ++#endif ++#ifndef __SNR_fsmount ++# define __SNR_fsmount __NR_fsmount ++#endif ++ ++#ifndef __NR_fspick ++# define __NR_fspick (FLATPAK_MISSING_SYSCALL_BASE + 433) ++#endif ++#ifndef __SNR_fspick ++# define __SNR_fspick __NR_fspick ++#endif ++ ++#ifndef __NR_pidfd_open ++# define __NR_pidfd_open (FLATPAK_MISSING_SYSCALL_BASE + 434) ++#endif ++#ifndef __SNR_pidfd_open ++# define __SNR_pidfd_open __NR_pidfd_open ++#endif ++ ++#ifndef __NR_clone3 ++# define __NR_clone3 (FLATPAK_MISSING_SYSCALL_BASE + 435) ++#endif ++#ifndef __SNR_clone3 ++# define __SNR_clone3 __NR_clone3 ++#endif ++ ++#ifndef __NR_close_range ++# define __NR_close_range (FLATPAK_MISSING_SYSCALL_BASE + 436) ++#endif ++#ifndef __SNR_close_range ++# define __SNR_close_range __NR_close_range ++#endif ++ ++#ifndef __NR_openat2 ++# define __NR_openat2 (FLATPAK_MISSING_SYSCALL_BASE + 437) ++#endif ++#ifndef __SNR_openat2 ++# define __SNR_openat2 __NR_openat2 ++#endif ++ ++#ifndef __NR_pidfd_getfd ++# define __NR_pidfd_getfd (FLATPAK_MISSING_SYSCALL_BASE + 438) ++#endif ++#ifndef __SNR_pidfd_getfd ++# define __SNR_pidfd_getfd __NR_pidfd_getfd ++#endif ++ ++#ifndef __NR_faccessat2 ++# define __NR_faccessat2 (FLATPAK_MISSING_SYSCALL_BASE + 439) ++#endif ++#ifndef __SNR_faccessat2 ++# define __SNR_faccessat2 __NR_faccessat2 ++#endif ++ ++#ifndef __NR_process_madvise ++# define __NR_process_madvise (FLATPAK_MISSING_SYSCALL_BASE + 440) ++#endif ++#ifndef __SNR_process_madvise ++# define __SNR_process_madvise __NR_process_madvise ++#endif ++ ++#ifndef __NR_epoll_pwait2 ++# define __NR_epoll_pwait2 (FLATPAK_MISSING_SYSCALL_BASE + 441) ++#endif ++#ifndef __SNR_epoll_pwait2 ++# define __SNR_epoll_pwait2 __NR_epoll_pwait2 ++#endif ++ ++#ifndef __NR_mount_setattr ++# define __NR_mount_setattr (FLATPAK_MISSING_SYSCALL_BASE + 442) ++#endif ++#ifndef __SNR_mount_setattr ++# define __SNR_mount_setattr __NR_mount_setattr ++#endif ++ ++#ifndef __NR_quotactl_fd ++# define __NR_quotactl_fd (FLATPAK_MISSING_SYSCALL_BASE + 443) ++#endif ++#ifndef __SNR_quotactl_fd ++# define __SNR_quotactl_fd __NR_quotactl_fd ++#endif ++ ++#ifndef __NR_landlock_create_ruleset ++# define __NR_landlock_create_ruleset (FLATPAK_MISSING_SYSCALL_BASE + 444) ++#endif ++#ifndef __SNR_landlock_create_ruleset ++# define __SNR_landlock_create_ruleset __NR_landlock_create_ruleset ++#endif ++ ++#ifndef __NR_landlock_add_rule ++# define __NR_landlock_add_rule (FLATPAK_MISSING_SYSCALL_BASE + 445) ++#endif ++#ifndef __SNR_landlock_add_rule ++# define __SNR_landlock_add_rule __NR_landlock_add_rule ++#endif ++ ++#ifndef __NR_landlock_restrict_self ++# define __NR_landlock_restrict_self (FLATPAK_MISSING_SYSCALL_BASE + 446) ++#endif ++#ifndef __SNR_landlock_restrict_self ++# define __SNR_landlock_restrict_self __NR_landlock_restrict_self ++#endif ++ ++#ifndef __NR_memfd_secret ++# define __NR_memfd_secret (FLATPAK_MISSING_SYSCALL_BASE + 447) ++#endif ++#ifndef __SNR_memfd_secret ++# define __SNR_memfd_secret __NR_memfd_secret ++#endif ++ ++/* Last updated: Linux 5.14, syscall numbers < 448 */ +-- +2.19.1 + diff --git a/backport-0003-CVE-2021-43860.patch b/backport-0003-CVE-2021-43860.patch new file mode 100644 index 0000000..8a935f1 --- /dev/null +++ b/backport-0003-CVE-2021-43860.patch @@ -0,0 +1,136 @@ +From d9a8f9d8ccc0b7c1135d0ecde006a75d25f66aee Mon Sep 17 00:00:00 2001 +From: Alexander Larsson +Date: Mon, 10 Jan 2022 16:43:08 +0100 +Subject: [PATCH] Transaction: Fail the resolve if xa.metadata invalid or + missing + +If we fail to parse xa.metadata from the summary cache or the commit +xa.metadata we fail the resolve. + +If xa.metadata is missing in the commit we fail the resolve (it is +always set in the summary cache, because summary update converts +missing xa.metadata to "", so we either get that, or cache miss which +leads to resolving from the commit. + +This means that op->resolved_metadata is always set during install and +updates, which means we will show the app permissions. The transaction +will also always make sure that this data actually matches what gets +deployed. + +Before this change an invalid metadata in the summary cache could lead +to a NULL resolved_metadata, which means we wouldn't print the app +permissions, yet we would still deploy some metadata file that could +have permissions. (NOTE: It would fail to deploy unless the +xa.metadata in the commit matched the metadata file, but in this +corner case we would't compare the summary and commit metadata, so +they may differ.) + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/d9a8f9d8ccc0b7c1135d0ecde006a75d25f66aee + +--- + common/flatpak-transaction.c | 36 +++++++++++++++++++++--------------- + 1 file changed, 21 insertions(+), 15 deletions(-) + +diff --git a/common/flatpak-transaction.c b/common/flatpak-transaction.c +index 4e19e5d..2134a3e 100644 +--- a/common/flatpak-transaction.c ++++ b/common/flatpak-transaction.c +@@ -1842,11 +1842,12 @@ load_deployed_metadata (FlatpakTransaction *self, const char *ref) + return g_bytes_new_take (g_steal_pointer (&metadata_contents), metadata_contents_length); + } + +-static void ++static gboolean + mark_op_resolved (FlatpakTransactionOperation *op, + const char *commit, + GBytes *metadata, +- GBytes *old_metadata) ++ GBytes *old_metadata, ++ GError **error) + { + g_debug ("marking op %s:%s resolved to %s", kind_to_str (op->kind), op->ref, commit ? commit : "-"); + +@@ -1860,13 +1861,12 @@ mark_op_resolved (FlatpakTransactionOperation *op, + if (metadata) + { + g_autoptr(GKeyFile) metakey = g_key_file_new (); +- if (g_key_file_load_from_bytes (metakey, metadata, G_KEY_FILE_NONE, NULL)) +- { +- op->resolved_metadata = g_bytes_ref (metadata); +- op->resolved_metakey = g_steal_pointer (&metakey); +- } +- else +- g_message ("Warning: Failed to parse metadata for %s\n", op->ref); ++ if (!g_key_file_load_from_bytes (metakey, metadata, G_KEY_FILE_NONE, NULL)) ++ return flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, ++ _("Invalid .flatpakref: %s"), op->ref); ++ ++ op->resolved_metadata = g_bytes_ref (metadata); ++ op->resolved_metakey = g_steal_pointer (&metakey); + } + if (old_metadata) + { +@@ -1877,8 +1877,13 @@ mark_op_resolved (FlatpakTransactionOperation *op, + op->resolved_old_metakey = g_steal_pointer (&metakey); + } + else +- g_message ("Warning: Failed to parse old metadata for %s\n", op->ref); ++ { ++ /* This shouldn't happen, but a NULL old metadata is safe (all permisssions are considered new) */ ++ g_message ("Warning: Failed to parse old metadata for %s\n", op->ref); ++ } + } ++ ++ return TRUE; + } + + static gboolean +@@ -1922,7 +1927,7 @@ resolve_p2p_ops (FlatpakTransaction *self, + g_autoptr(GBytes) old_metadata_bytes = NULL; + + old_metadata_bytes = load_deployed_metadata (self, op->ref); +- mark_op_resolved (op, resolve->resolved_commit, resolve->resolved_metadata, old_metadata_bytes); ++ mark_op_resolved (op, resolve->resolved_commit, resolve->resolved_metadata, old_metadata_bytes,error); + } + + return TRUE; +@@ -1960,14 +1965,15 @@ resolve_ops (FlatpakTransaction *self, + /* We resolve to the deployed metadata, becasue we need it to uninstall related ops */ + + metadata_bytes = load_deployed_metadata (self, op->ref); +- mark_op_resolved (op, NULL, metadata_bytes, NULL); ++ mark_op_resolved (op, NULL, metadata_bytes, NULL,error); + continue; + } + + if (op->kind == FLATPAK_TRANSACTION_OPERATION_INSTALL_BUNDLE) + { + g_assert (op->commit != NULL); +- mark_op_resolved (op, op->commit, op->external_metadata, NULL); ++ if (!mark_op_resolved (op, op->commit, NULL, NULL, error)) ++ return FALSE; + continue; + } + +@@ -1993,7 +1999,7 @@ resolve_ops (FlatpakTransaction *self, + metadata_bytes = g_bytes_new (xa_metadata, strlen (xa_metadata) + 1); + + old_metadata_bytes = load_deployed_metadata (self, op->ref); +- mark_op_resolved (op, checksum, metadata_bytes, old_metadata_bytes); ++ mark_op_resolved (op, checksum, metadata_bytes, old_metadata_bytes,error); + } + else if (state->collection_id == NULL) /* In the non-p2p case we have all the info available in the summary, so use it */ + { +@@ -2031,7 +2037,7 @@ resolve_ops (FlatpakTransaction *self, + metadata_bytes = g_bytes_new (metadata, strlen (metadata) + 1); + + old_metadata_bytes = load_deployed_metadata (self, op->ref); +- mark_op_resolved (op, checksum, metadata_bytes, old_metadata_bytes); ++ mark_op_resolved (op, checksum, metadata_bytes, old_metadata_bytes,error); + } + else + { +-- +2.27.0 + diff --git a/backport-0003-CVE-2022-21682.patch b/backport-0003-CVE-2022-21682.patch new file mode 100644 index 0000000..5d2ac39 --- /dev/null +++ b/backport-0003-CVE-2022-21682.patch @@ -0,0 +1,49 @@ +From 5a83c73ed859fe3e4bd93a228a4bc8981d649c5e Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Thu, 27 Aug 2020 18:01:12 +0100 +Subject: [PATCH] context: Implement MODE_NONE in unparse_filesystem_flags + +flatpak doesn't yet use -Wswitch-enum, but perhaps it should at some +point. Now that FLATPAK_FILESYSTEM_MODE_NONE is a member of the enum, +it should be handled; and if we're doing that, we might as well make +the same function fully responsible for it. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/5a83c73ed859fe3e4bd93a228a4bc8981d649c5e + +--- + common/flatpak-context.c | 9 +++++---- + 1 file changed, 5 insertions(+), 4 deletions(-) + +diff --git a/common/flatpak-context.c b/common/flatpak-context.c +index 3a99646..0d53b13 100644 +--- a/common/flatpak-context.c ++++ b/common/flatpak-context.c +@@ -697,6 +697,10 @@ unparse_filesystem_flags (const char *path, + case FLATPAK_FILESYSTEM_MODE_READ_WRITE: + break; + ++ case FLATPAK_FILESYSTEM_MODE_NONE: ++ g_string_insert_c (s, 0, '!'); ++ break; ++ + default: + g_warning ("Unexpected filesystem mode %d", mode); + break; +@@ -1677,10 +1681,7 @@ flatpak_context_save_metadata (FlatpakContext *context, + { + FlatpakFilesystemMode mode = GPOINTER_TO_INT (value); + +- if (mode != FLATPAK_FILESYSTEM_MODE_NONE) +- g_ptr_array_add (array, unparse_filesystem_flags (key, mode)); +- else +- g_ptr_array_add (array, g_strconcat ("!", key, NULL)); ++ g_ptr_array_add (array, unparse_filesystem_flags (key, mode)); + } + + g_key_file_set_string_list (metakey, +-- +2.27.0 + diff --git a/backport-0004-CVE-2021-41133.patch b/backport-0004-CVE-2021-41133.patch new file mode 100644 index 0000000..f2e5c02 --- /dev/null +++ b/backport-0004-CVE-2021-41133.patch @@ -0,0 +1,43 @@ +From a10f52a7565c549612c92b8e736a6698a53db330 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 11:59:00 +0100 +Subject: [PATCH] run: Block clone3() in sandbox + +clone3() can be used to implement clone() with CLONE_NEWUSER, allowing +a sandboxed process to get CAP_SYS_ADMIN in a new namespace and +manipulate its root directory. We need to block this so that AF_UNIX-based +socket servers (X11, Wayland, etc.) can rely on +/proc/PID/root/.flatpak-info existing for all Flatpak-sandboxed apps. + +Partially fixes GHSA-67h7-w3jq-vh4q. + +Thanks: an anonymous reporter +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/a10f52a7565c549612c92b8e736a6698a53db330 + +--- + common/flatpak-run.c | 6 ++++++ + 1 file changed, 6 insertions(+) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index de3dd38..818df58 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2139,6 +2139,12 @@ setup_seccomp (FlatpakBwrap *bwrap, + + /* Don't allow faking input to the controlling tty (CVE-2017-5226) */ + {SCMP_SYS (ioctl), EPERM, &SCMP_A1 (SCMP_CMP_MASKED_EQ, 0xFFFFFFFFu, (int) TIOCSTI)}, ++ ++ /* seccomp can't look into clone3()'s struct clone_args to check whether ++ * the flags are OK, so we have no choice but to block clone3(). ++ * Return ENOSYS so user-space will fall back to clone(). ++ * (GHSA-67h7-w3jq-vh4q; see also https://github.com/moby/moby/commit/9f6b562d) */ ++ {SCMP_SYS (clone3), ENOSYS}, + }; + + struct +-- +2.19.1 + diff --git a/backport-0004-CVE-2021-43860.patch b/backport-0004-CVE-2021-43860.patch new file mode 100644 index 0000000..de528a8 --- /dev/null +++ b/backport-0004-CVE-2021-43860.patch @@ -0,0 +1,210 @@ +From 54ec1a482dfc668127eaae57f135e6a8e0bc52da Mon Sep 17 00:00:00 2001 +From: Phaedrus Leeds +Date: Tue, 28 Dec 2021 11:48:16 -0800 +Subject: [PATCH] Add test for metadata validation + +This tests for invalid metadata, missing xa.metadata and mismatched +values in xa.metadata and the real metadata, including the embedded +null leading to the hidden permissions of CVE-2021-43860. + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/54ec1a482dfc668127eaae57f135e6a8e0bc52da + +--- + tests/Makefile-test-matrix.am.inc | 1 + + tests/Makefile.am.inc | 1 + + tests/test-metadata-validation.sh | 158 ++++++++++++++++++++++++++++++ + 3 files changed, 160 insertions(+) + create mode 100644 tests/test-metadata-validation.sh + +diff --git a/tests/Makefile-test-matrix.am.inc b/tests/Makefile-test-matrix.am.inc +index fcbfcd9..afde01c 100644 +--- a/tests/Makefile-test-matrix.am.inc ++++ b/tests/Makefile-test-matrix.am.inc +@@ -17,6 +17,7 @@ TEST_MATRIX_DIST= \ + tests/test-basic.sh \ + tests/test-build-update-repo.sh \ + tests/test-http-utils.sh \ ++ tests/test-metadata-validation.sh \ + tests/test-extensions.sh \ + tests/test-oci.sh \ + tests/test-unsigned-summaries.sh \ +diff --git a/tests/Makefile.am.inc b/tests/Makefile.am.inc +index d72de8a..b9a6f61 100644 +--- a/tests/Makefile.am.inc ++++ b/tests/Makefile.am.inc +@@ -93,6 +93,7 @@ TEST_MATRIX_SOURCE = \ + tests/test-http-utils.sh \ + tests/test-run.sh{{user+system},{nodeltas+deltas}} \ + tests/test-repo.sh{user+system+collections+collections-server-only} \ ++ tests/test-metadata-validation.sh \ + tests/test-extensions.sh \ + tests/test-bundle.sh{user+system} \ + tests/test-oci.sh \ +diff --git a/tests/test-metadata-validation.sh b/tests/test-metadata-validation.sh +new file mode 100644 +index 0000000..7e3efcc +--- /dev/null ++++ b/tests/test-metadata-validation.sh +@@ -0,0 +1,158 @@ ++#!/bin/bash ++# ++# Copyright (C) 2021 Matthew Leeds ++# ++# SPDX-License-Identifier: LGPL-2.0-or-later ++ ++set -euo pipefail ++ ++. $(dirname $0)/libtest.sh ++ ++echo "1..7" ++ ++setup_repo ++ ++COUNTER=1 ++ ++create_app () { ++ local OPTIONS="$1" ++ local DIR=`mktemp -d` ++ ++ mkdir ${DIR}/files ++ echo $COUNTER > ${DIR}/files/counter ++ let COUNTER=COUNTER+1 ++ ++ local INVALID="" ++ if [[ $OPTIONS =~ "invalid" ]]; then ++ INVALID=invalidkeyfileline ++ fi ++ cat > ${DIR}/metadata <> ${DIR}/metadata ++ fi ++ if [[ $OPTIONS =~ "hidden" ]]; then ++ echo -ne "\0" >> ${DIR}/metadata ++ echo -e "\nfilesystems=home;" >> ${DIR}/metadata ++ fi ++ local XA_METADATA=--add-metadata-string=xa.metadata="$(head -n6 ${DIR}/metadata)"$'\n' ++ if [[ $OPTIONS =~ "no-xametadata" ]]; then ++ XA_METADATA="--add-metadata-string=xa.nometadata=1" ++ fi ++ ostree commit --repo=repos/test --branch=app/org.test.Malicious/${ARCH}/master ${FL_GPGARGS} "$XA_METADATA" ${DIR}/ ++ if [[ $OPTIONS =~ "no-cache-in-summary" ]]; then ++ ostree --repo=repos/test ${FL_GPGARGS} summary -u ++ # force use of legacy summary format ++ rm -rf repos/test/summary.idx repos/test/summaries ++ else ++ update_repo ++ fi ++ rm -rf ${DIR} ++} ++ ++cleanup_repo () { ++ ostree refs --repo=repos/test --delete app/org.test.Malicious/${ARCH}/master ++ update_repo ++} ++ ++create_app "hidden" ++ ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with hidden permissions" ++fi ++ ++assert_file_has_content install-error-log "not matching expected metadata" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with hidden permissions can't be installed (CVE-2021-43860)" ++ ++create_app no-xametadata ++ ++# The install will fail because the metadata in the summary doesn't match the metadata on the commit ++# The missing xa.metadata in the commit got turned into "" in the xa.cache ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with missing xa.metadata" ++fi ++ ++assert_file_has_content install-error-log "not matching expected metadata" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with no xa.metadata can't be installed" ++ ++create_app "no-xametadata no-cache-in-summary" ++ ++# The install will fail because there's no metadata in the summary or on the commit ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with missing metadata" ++fi ++assert_file_has_content install-error-log "No xa.metadata in local commit" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with no xa.metadata and no metadata in summary can't be installed" ++ ++create_app "invalid" ++ ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with invalid metadata" ++fi ++assert_file_has_content install-error-log "Metadata for .* is invalid" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with invalid metadata (in summary) can't be installed" ++ ++create_app "invalid no-cache-in-summary" ++ ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with invalid metadata" ++fi ++assert_file_has_content install-error-log "Metadata for .* is invalid" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with invalid metadata (in commit) can't be installed" ++ ++create_app "mismatch no-cache-in-summary" ++ ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with non-matching metadata" ++fi ++assert_file_has_content install-error-log "Commit metadata for .* not matching expected metadata" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with mismatched metadata (in commit) can't be installed" ++ ++create_app "mismatch" ++ ++if ${FLATPAK} ${U} install -y test-repo org.test.Malicious 2>install-error-log; then ++ assert_not_reached "Should not be able to install app with non-matching metadata" ++fi ++assert_file_has_content install-error-log "Commit metadata for .* not matching expected metadata" ++ ++assert_not_has_dir $FL_DIR/app/org.test.Malicious/current/active ++ ++cleanup_repo ++ ++ok "app with mismatched metadata (in summary) can't be installed" +-- +2.27.0 + diff --git a/backport-0004-CVE-2022-21682.patch b/backport-0004-CVE-2022-21682.patch new file mode 100644 index 0000000..a759a18 --- /dev/null +++ b/backport-0004-CVE-2022-21682.patch @@ -0,0 +1,47 @@ +From 55b27b1393a3880b79dfe108b6f13f1a2fa1888b Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 26 Aug 2020 20:25:15 +0100 +Subject: [PATCH] context: Expose flatpak_context_parse_filesystem for testing + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/55b27b1393a3880b79dfe108b6f13f1a2fa1888b + +--- + common/flatpak-context-private.h | 5 +++++ + common/flatpak-context.c | 2 +- + 2 files changed, 6 insertions(+), 1 deletion(-) + +diff --git a/common/flatpak-context-private.h b/common/flatpak-context-private.h +index f47079b..d84f4e0 100644 +--- a/common/flatpak-context-private.h ++++ b/common/flatpak-context-private.h +@@ -79,6 +79,11 @@ extern const char *flatpak_context_devices[]; + extern const char *flatpak_context_features[]; + extern const char *flatpak_context_shares[]; + ++gboolean flatpak_context_parse_filesystem (const char *filesystem_and_mode, ++ char **filesystem_out, ++ FlatpakFilesystemMode *mode_out, ++ GError **error); ++ + FlatpakContext *flatpak_context_new (void); + void flatpak_context_free (FlatpakContext *context); + void flatpak_context_merge (FlatpakContext *context, +diff --git a/common/flatpak-context.c b/common/flatpak-context.c +index 0d53b13..3b2bcfe 100644 +--- a/common/flatpak-context.c ++++ b/common/flatpak-context.c +@@ -752,7 +752,7 @@ parse_filesystem_flags (const char *filesystem, + return g_string_free (g_steal_pointer (&s), FALSE); + } + +-static gboolean ++gboolean + flatpak_context_parse_filesystem (const char *filesystem_and_mode, + char **filesystem_out, + FlatpakFilesystemMode *mode_out, +-- +2.27.0 + diff --git a/backport-0005-CVE-2021-41133.patch b/backport-0005-CVE-2021-41133.patch new file mode 100644 index 0000000..5fc0d66 --- /dev/null +++ b/backport-0005-CVE-2021-41133.patch @@ -0,0 +1,45 @@ +From 9766ee05b1425db397d2cf23afd24c7f6146a69f Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 12:45:54 +0100 +Subject: [PATCH] run: Disallow recently-added mount-manipulation syscalls + +If we don't allow mount() then we shouldn't allow these either. + +Partially fixes GHSA-67h7-w3jq-vh4q. + +Thanks: an anonymous reporter +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/9766ee05b1425db397d2cf23afd24c7f6146a69f + +--- + common/flatpak-run.c | 12 ++++++++++++ + 1 file changed, 12 insertions(+) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 818df58..0fbd5a9 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2145,6 +2145,18 @@ setup_seccomp (FlatpakBwrap *bwrap, + * Return ENOSYS so user-space will fall back to clone(). + * (GHSA-67h7-w3jq-vh4q; see also https://github.com/moby/moby/commit/9f6b562d) */ + {SCMP_SYS (clone3), ENOSYS}, ++ ++ /* New mount manipulation APIs can also change our VFS. There's no ++ * legitimate reason to do these in the sandbox, so block all of them ++ * rather than thinking about which ones might be dangerous. ++ * (GHSA-67h7-w3jq-vh4q) */ ++ {SCMP_SYS (open_tree), ENOSYS}, ++ {SCMP_SYS (move_mount), ENOSYS}, ++ {SCMP_SYS (fsopen), ENOSYS}, ++ {SCMP_SYS (fsconfig), ENOSYS}, ++ {SCMP_SYS (fsmount), ENOSYS}, ++ {SCMP_SYS (fspick), ENOSYS}, ++ {SCMP_SYS (mount_setattr), ENOSYS}, + }; + + struct +-- +2.19.1 + diff --git a/backport-0005-CVE-2022-21682.patch b/backport-0005-CVE-2022-21682.patch new file mode 100644 index 0000000..f4a19ff --- /dev/null +++ b/backport-0005-CVE-2022-21682.patch @@ -0,0 +1,81 @@ +From aafe1d36e0225f54db8ca2ba03d8b1981c2d09e0 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 26 Aug 2020 19:05:21 +0100 +Subject: [PATCH] context: Do some syntactic normalization on filesystems + +Paths containing ".." are rejected: they're almost certainly a +terrible idea. + +Paths containing "." or multiple slashes are syntactically normalized. + +This assumes that nobody is going to use "--filesystem=/foo/bar/" to +mean "make /foo/bar available, unless it's a non-directory, in which +case fail". + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/aafe1d36e0225f54db8ca2ba03d8b1981c2d09e0 + +--- + common/flatpak-context.c | 44 ++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 44 insertions(+) + +diff --git a/common/flatpak-context.c b/common/flatpak-context.c +index 3b2bcfe..84b292e 100644 +--- a/common/flatpak-context.c ++++ b/common/flatpak-context.c +@@ -759,6 +759,50 @@ flatpak_context_parse_filesystem (const char *filesystem_and_mode, + GError **error) + { + g_autofree char *filesystem = parse_filesystem_flags (filesystem_and_mode, mode_out); ++ char *slash; ++ ++ slash = strchr (filesystem, '/'); ++ ++ /* Forbid /../ in paths */ ++ if (slash != NULL) ++ { ++ if (g_str_has_prefix (slash + 1, "../") || ++ g_str_has_suffix (slash + 1, "/..") || ++ strstr (slash + 1, "/../") != NULL) ++ { ++ g_set_error (error, G_OPTION_ERROR, G_OPTION_ERROR_BAD_VALUE, ++ _("Filesystem location \"%s\" contains \"..\""), ++ filesystem); ++ return FALSE; ++ } ++ ++ /* Convert "//" and "/./" to "/" */ ++ for (; slash != NULL; slash = strchr (slash + 1, '/')) ++ { ++ while (TRUE) ++ { ++ if (slash[1] == '/') ++ memmove (slash + 1, slash + 2, strlen (slash + 2) + 1); ++ else if (slash[1] == '.' && slash[2] == '/') ++ memmove (slash + 1, slash + 3, strlen (slash + 3) + 1); ++ else ++ break; ++ } ++ } ++ ++ /* Eliminate trailing "/." or "/". */ ++ while (TRUE) ++ { ++ slash = strrchr (filesystem, '/'); ++ ++ if (slash != NULL && ++ ((slash != filesystem && slash[1] == '\0') || ++ (slash[1] == '.' && slash[2] == '\0'))) ++ *slash = '\0'; ++ else ++ break; ++ } ++ } + + if (g_strv_contains (flatpak_context_special_filesystems, filesystem) || + get_xdg_user_dir_from_string (filesystem, NULL, NULL, NULL) || +-- +2.27.0 + diff --git a/backport-0006-CVE-2021-41133.patch b/backport-0006-CVE-2021-41133.patch new file mode 100644 index 0000000..79321c3 --- /dev/null +++ b/backport-0006-CVE-2021-41133.patch @@ -0,0 +1,34 @@ +From 4c34815784e9ffda5733225c7d95824f96375e36 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 14:19:31 +0100 +Subject: [PATCH] run: Block setns() + +If we don't allow unshare() or clone() with CLONE_NEWUSER, we also +shouldn't allow joining an existing (but different) namespace. + +Partially fixes GHSA-67h7-w3jq-vh4q. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/4c34815784e9ffda5733225c7d95824f96375e36 + +--- + common/flatpak-run.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 0fbd5a9..458e3c3 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2133,6 +2133,7 @@ setup_seccomp (FlatpakBwrap *bwrap, + + /* Don't allow subnamespace setups: */ + {SCMP_SYS (unshare), EPERM}, ++ {SCMP_SYS (setns), EPERM}, + {SCMP_SYS (mount), EPERM}, + {SCMP_SYS (pivot_root), EPERM}, + {SCMP_SYS (clone), EPERM, &SCMP_A0 (SCMP_CMP_MASKED_EQ, CLONE_NEWUSER, CLONE_NEWUSER)}, +-- +2.19.1 + diff --git a/backport-0006-CVE-2022-21682.patch b/backport-0006-CVE-2022-21682.patch new file mode 100644 index 0000000..1cbe9a9 --- /dev/null +++ b/backport-0006-CVE-2022-21682.patch @@ -0,0 +1,381 @@ +From 5709f1aaed6579f0136976e14e7f3cae399134ca Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Sun, 16 Jan 2022 12:42:30 +0000 +Subject: [PATCH] context: Introduce new --nofilesystem=host:reset + +This reintroduces the special case that existed in Flatpak 1.12.3, but +under a different name, so that it will be backwards-compatible. With +this change, flatpak-builder will be able to resolve CVE-2022-21682 by +using --filesystem=host:reset. + +We want to implement this as a suffix rather than as a new keyword, +because unknown suffixes are ignored with a warning, rather than causing +a fatal error. This means that the new version of flatpak-builder will +be able to run against older versions of flatpak: it will still be +vulnerable to CVE-2022-21682 in that situation, but at least it will run. + +Co-authored-by: Alexander Larsson + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/5709f1aaed6579f0136976e14e7f3cae399134ca + +--- + common/flatpak-context-private.h | 1 + + common/flatpak-context.c | 166 ++++++++++++++++++++++++++++--- + doc/flatpak-override.xml | 8 ++ + doc/flatpak-run.xml | 8 ++ + 4 files changed, 169 insertions(+), 14 deletions(-) + +diff --git a/common/flatpak-context-private.h b/common/flatpak-context-private.h +index d84f4e0..2d2a40e 100644 +--- a/common/flatpak-context-private.h ++++ b/common/flatpak-context-private.h +@@ -80,6 +80,7 @@ extern const char *flatpak_context_features[]; + extern const char *flatpak_context_shares[]; + + gboolean flatpak_context_parse_filesystem (const char *filesystem_and_mode, ++ gboolean negated, + char **filesystem_out, + FlatpakFilesystemMode *mode_out, + GError **error); +diff --git a/common/flatpak-context.c b/common/flatpak-context.c +index 84b292e..30a84bd 100644 +--- a/common/flatpak-context.c ++++ b/common/flatpak-context.c +@@ -81,6 +81,7 @@ const char *flatpak_context_features[] = { + const char *flatpak_context_special_filesystems[] = { + "home", + "host", ++ "host-reset", + NULL + }; + +@@ -699,6 +700,12 @@ unparse_filesystem_flags (const char *path, + + case FLATPAK_FILESYSTEM_MODE_NONE: + g_string_insert_c (s, 0, '!'); ++ ++ if (g_str_has_suffix (s->str, "-reset")) ++ { ++ g_string_truncate (s, s->len - 6); ++ g_string_append (s, ":reset"); ++ } + break; + + default: +@@ -711,11 +718,14 @@ unparse_filesystem_flags (const char *path, + + static char * + parse_filesystem_flags (const char *filesystem, +- FlatpakFilesystemMode *mode_out) ++ gboolean negated, ++ FlatpakFilesystemMode *mode_out, ++ GError **error) + { + g_autoptr(GString) s = g_string_new (""); + const char *p, *suffix; + FlatpakFilesystemMode mode; ++ gboolean reset = FALSE; + + p = filesystem; + while (*p != 0 && *p != ':') +@@ -730,7 +740,31 @@ parse_filesystem_flags (const char *filesystem, + g_string_append_c (s, *p++); + } + +- mode = FLATPAK_FILESYSTEM_MODE_READ_WRITE; ++ if (negated) ++ mode = FLATPAK_FILESYSTEM_MODE_NONE; ++ else ++ mode = FLATPAK_FILESYSTEM_MODE_READ_WRITE; ++ ++ if (g_str_equal (s->str, "host-reset")) ++ { ++ reset = TRUE; ++ ++ if (!negated) ++ { ++ g_set_error (error, G_OPTION_ERROR, G_OPTION_ERROR_FAILED, ++ "Filesystem token \"%s\" is only applicable for --nofilesystem", ++ s->str); ++ return NULL; ++ } ++ ++ if (*p != '\0') ++ { ++ g_set_error (error, G_OPTION_ERROR, G_OPTION_ERROR_FAILED, ++ "Filesystem token \"%s\" cannot be used with a suffix", ++ s->str); ++ return NULL; ++ } ++ } + + if (*p == ':') + { +@@ -742,10 +776,63 @@ parse_filesystem_flags (const char *filesystem, + mode = FLATPAK_FILESYSTEM_MODE_READ_WRITE; + else if (strcmp (suffix, "create") == 0) + mode = FLATPAK_FILESYSTEM_MODE_CREATE; ++ else if (strcmp (suffix, "reset") == 0) ++ reset = TRUE; + else if (*suffix != 0) + g_warning ("Unexpected filesystem suffix %s, ignoring", suffix); ++ ++ if (negated && mode != FLATPAK_FILESYSTEM_MODE_NONE) ++ { ++ g_warning ("Filesystem suffix \"%s\" is not applicable for --nofilesystem", ++ suffix); ++ mode = FLATPAK_FILESYSTEM_MODE_NONE; ++ } ++ ++ if (reset) ++ { ++ if (!negated) ++ { ++ g_set_error (error, G_OPTION_ERROR, G_OPTION_ERROR_FAILED, ++ "Filesystem suffix \"%s\" only applies to --nofilesystem", ++ suffix); ++ return NULL; ++ } ++ ++ if (!g_str_equal (s->str, "host")) ++ { ++ g_set_error (error, G_OPTION_ERROR, G_OPTION_ERROR_FAILED, ++ "Filesystem suffix \"%s\" can only be applied to " ++ "--nofilesystem=host", ++ suffix); ++ return NULL; ++ } ++ ++ /* We internally handle host:reset (etc) as host-reset, only exposing it as a flag in the public ++ part to allow it to be ignored (with a warning) for old flatpak versions */ ++ g_string_append (s, "-reset"); ++ } + } + ++ /* Postcondition check: the code above should make some results ++ * impossible */ ++ if (negated) ++ { ++ g_assert (mode == FLATPAK_FILESYSTEM_MODE_NONE); ++ } ++ else ++ { ++ g_assert (mode > FLATPAK_FILESYSTEM_MODE_NONE); ++ /* This flag is only applicable to --nofilesystem */ ++ g_assert (!reset); ++ } ++ ++ /* Postcondition check: filesystem token is host-reset iff reset flag ++ * was found */ ++ if (reset) ++ g_assert (g_str_equal (s->str, "host-reset")); ++ else ++ g_assert (!g_str_equal (s->str, "host-reset")); ++ + if (mode_out) + *mode_out = mode; + +@@ -754,13 +841,18 @@ parse_filesystem_flags (const char *filesystem, + + gboolean + flatpak_context_parse_filesystem (const char *filesystem_and_mode, ++ gboolean negated, + char **filesystem_out, + FlatpakFilesystemMode *mode_out, + GError **error) + { +- g_autofree char *filesystem = parse_filesystem_flags (filesystem_and_mode, mode_out); ++ g_autofree char *filesystem = NULL; + char *slash; + ++ filesystem = parse_filesystem_flags (filesystem_and_mode, negated, mode_out, error); ++ if (filesystem == NULL) ++ return FALSE; ++ + slash = strchr (filesystem, '/'); + + /* Forbid /../ in paths */ +@@ -825,6 +917,14 @@ flatpak_context_take_filesystem (FlatpakContext *context, + char *fs, + FlatpakFilesystemMode mode) + { ++ /* Special case: --nofilesystem=host-reset implies --nofilesystem=host. ++ * --filesystem=host-reset (or host:reset) is not allowed. */ ++ if (g_str_equal (fs, "host-reset")) ++ { ++ g_return_if_fail (mode == FLATPAK_FILESYSTEM_MODE_NONE); ++ g_hash_table_insert (context->filesystems, g_strdup ("host"), GINT_TO_POINTER (mode)); ++ } ++ + g_hash_table_insert (context->filesystems, fs, GINT_TO_POINTER (mode)); + } + +@@ -856,6 +956,14 @@ flatpak_context_merge (FlatpakContext *context, + while (g_hash_table_iter_next (&iter, &key, &value)) + g_hash_table_insert (context->persistent, g_strdup (key), value); + ++ /* We first handle host:reset, as it overrides all other keys from the parent */ ++ if (g_hash_table_lookup_extended (other->filesystems, "host-reset", NULL, &value)) ++ { ++ g_warn_if_fail (GPOINTER_TO_INT (value) == FLATPAK_FILESYSTEM_MODE_NONE); ++ g_hash_table_remove_all (context->filesystems); ++ } ++ ++ /* Then set the new ones, which includes propagating host:reset. */ + g_hash_table_iter_init (&iter, other->filesystems); + while (g_hash_table_iter_next (&iter, &key, &value)) + g_hash_table_insert (context->filesystems, g_strdup (key), value); +@@ -1044,7 +1152,7 @@ option_filesystem_cb (const gchar *option_name, + g_autofree char *fs = NULL; + FlatpakFilesystemMode mode; + +- if (!flatpak_context_parse_filesystem (value, &fs, &mode, error)) ++ if (!flatpak_context_parse_filesystem (value, FALSE, &fs, &mode, error)) + return FALSE; + + flatpak_context_take_filesystem (context, g_steal_pointer (&fs), mode); +@@ -1061,7 +1169,7 @@ option_nofilesystem_cb (const gchar *option_name, + g_autofree char *fs = NULL; + FlatpakFilesystemMode mode; + +- if (!flatpak_context_parse_filesystem (value, &fs, &mode, error)) ++ if (!flatpak_context_parse_filesystem (value, TRUE, &fs, &mode, error)) + return FALSE; + + flatpak_context_take_filesystem (context, g_steal_pointer (&fs), +@@ -1491,15 +1599,13 @@ flatpak_context_load_metadata (FlatpakContext *context, + g_autofree char *filesystem = NULL; + FlatpakFilesystemMode mode; + +- if (!flatpak_context_parse_filesystem (fs, &filesystem, &mode, NULL)) ++ if (!flatpak_context_parse_filesystem (fs, remove, ++ &filesystem, &mode, NULL)) + g_debug ("Unknown filesystem type %s", filesystems[i]); + else + { +- if (remove) +- flatpak_context_take_filesystem (context, g_steal_pointer (&filesystem), +- FLATPAK_FILESYSTEM_MODE_NONE); +- else +- flatpak_context_take_filesystem (context, g_steal_pointer (&filesystem), mode); ++ g_assert (mode == FLATPAK_FILESYSTEM_MODE_NONE || !remove); ++ flatpak_context_take_filesystem (context, g_steal_pointer (&filesystem), mode); + } + } + } +@@ -1720,11 +1826,24 @@ flatpak_context_save_metadata (FlatpakContext *context, + { + g_autoptr(GPtrArray) array = g_ptr_array_new_with_free_func (g_free); + ++ /* Serialize host-reset first, because order can matter in ++ * corner cases. */ ++ if (g_hash_table_lookup_extended (context->filesystems, "host-reset", ++ NULL, &value)) ++ { ++ g_warn_if_fail (GPOINTER_TO_INT (value) == FLATPAK_FILESYSTEM_MODE_NONE); ++ g_ptr_array_add (array, g_strdup ("!host:reset")); ++ } ++ + g_hash_table_iter_init (&iter, context->filesystems); + while (g_hash_table_iter_next (&iter, &key, &value)) + { + FlatpakFilesystemMode mode = GPOINTER_TO_INT (value); + ++ /* We already did this */ ++ if (g_str_equal (key, "host-reset")) ++ continue; ++ + g_ptr_array_add (array, unparse_filesystem_flags (key, mode)); + } + +@@ -1829,7 +1948,8 @@ flatpak_context_save_metadata (FlatpakContext *context, + void + flatpak_context_allow_host_fs (FlatpakContext *context) + { +- flatpak_context_take_filesystem (context, g_strdup ("host"), FLATPAK_FILESYSTEM_MODE_READ_WRITE); ++ flatpak_context_take_filesystem (context, g_strdup ("host"), ++ FLATPAK_FILESYSTEM_MODE_READ_WRITE); + } + + gboolean +@@ -1889,18 +2009,36 @@ flatpak_context_to_args (FlatpakContext *context, + g_ptr_array_add (args, g_strdup_printf ("--system-%s-name=%s", flatpak_policy_to_string (policy), name)); + } + ++ /* Serialize host-reset first, because order can matter in ++ * corner cases. */ ++ if (g_hash_table_lookup_extended (context->filesystems, "host-reset", ++ NULL, &value)) ++ { ++ g_warn_if_fail (GPOINTER_TO_INT (value) == FLATPAK_FILESYSTEM_MODE_NONE); ++ g_ptr_array_add (args, g_strdup ("--nofilesystem=host:reset")); ++ } ++ + g_hash_table_iter_init (&iter, context->filesystems); + while (g_hash_table_iter_next (&iter, &key, &value)) + { ++ g_autofree char *fs = NULL; + FlatpakFilesystemMode mode = GPOINTER_TO_INT (value); + ++ /* We already did this */ ++ if (g_str_equal (key, "host-reset")) ++ continue; ++ ++ fs = unparse_filesystem_flags (key, mode); ++ + if (mode != FLATPAK_FILESYSTEM_MODE_NONE) + { +- g_autofree char *fs = unparse_filesystem_flags (key, mode); + g_ptr_array_add (args, g_strdup_printf ("--filesystem=%s", fs)); + } + else +- g_ptr_array_add (args, g_strdup_printf ("--nofilesystem=%s", (char *) key)); ++ { ++ g_assert (fs[0] == '!'); ++ g_ptr_array_add (args, g_strdup_printf ("--nofilesystem=%s", &fs[1])); ++ } + } + } + +diff --git a/doc/flatpak-override.xml b/doc/flatpak-override.xml +index 60fa58c..bddb36e 100644 +--- a/doc/flatpak-override.xml ++++ b/doc/flatpak-override.xml +@@ -221,6 +221,14 @@ + xdg-music, xdg-pictures, xdg-public-share, xdg-templates, xdg-videos, + an absolute path, or a homedir-relative path like ~/dir. + This option can be used multiple times. ++ ++ As a special case, ++ ++ will ignore all ++ permissions inherited from the app manifest or a ++ lower-precedence layer of overrides, in addition to ++ having the behaviour of ++ . + + + +diff --git a/doc/flatpak-run.xml b/doc/flatpak-run.xml +index 8e1a3fd..be77092 100644 +--- a/doc/flatpak-run.xml ++++ b/doc/flatpak-run.xml +@@ -324,6 +324,14 @@ + xdg-music, xdg-pictures, xdg-public-share, xdg-templates, xdg-videos, + an absolute path, or a homedir-relative path like ~/dir. + This option can be used multiple times. ++ ++ As a special case, ++ ++ will ignore all ++ permissions inherited from the app manifest or ++ flatpak-override1, ++ in addition to having the behaviour of ++ . + + + +-- +2.27.0 + diff --git a/backport-0007-CVE-2021-41133.patch b/backport-0007-CVE-2021-41133.patch new file mode 100644 index 0000000..42e6ca4 --- /dev/null +++ b/backport-0007-CVE-2021-41133.patch @@ -0,0 +1,35 @@ +From 1330662f33a55e88bfe18e76de28b7922d91a999 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 14:20:29 +0100 +Subject: [PATCH] run: Don't allow unmounting filesystems + +If we don't allow mounting filesystems, we shouldn't allow unmounting +either. + +Partially fixes GHSA-67h7-w3jq-vh4q. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/1330662f33a55e88bfe18e76de28b7922d91a999 + +--- + common/flatpak-run.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 458e3c3..3a229b9 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2135,6 +2135,8 @@ setup_seccomp (FlatpakBwrap *bwrap, + {SCMP_SYS (unshare), EPERM}, + {SCMP_SYS (setns), EPERM}, + {SCMP_SYS (mount), EPERM}, ++ {SCMP_SYS (umount), EPERM}, ++ {SCMP_SYS (umount2), EPERM}, + {SCMP_SYS (pivot_root), EPERM}, + {SCMP_SYS (clone), EPERM, &SCMP_A0 (SCMP_CMP_MASKED_EQ, CLONE_NEWUSER, CLONE_NEWUSER)}, + +-- +2.19.1 + diff --git a/backport-0008-CVE-2021-41133.patch b/backport-0008-CVE-2021-41133.patch new file mode 100644 index 0000000..d850d77 --- /dev/null +++ b/backport-0008-CVE-2021-41133.patch @@ -0,0 +1,34 @@ +From 462fca2c666e0cd2b60d6d2593a7216a83047aaf Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Wed, 1 Sep 2021 14:21:04 +0100 +Subject: [PATCH] run: Don't allow chroot() + +If we don't allow pivot_root() then there seems no reason why we should +allow chroot(). + +Partially fixes GHSA-67h7-w3jq-vh4q. + +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/462fca2c666e0cd2b60d6d2593a7216a83047aaf + +--- + common/flatpak-run.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 3a229b9..c2c0218 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2138,6 +2138,7 @@ setup_seccomp (FlatpakBwrap *bwrap, + {SCMP_SYS (umount), EPERM}, + {SCMP_SYS (umount2), EPERM}, + {SCMP_SYS (pivot_root), EPERM}, ++ {SCMP_SYS (chroot), EPERM}, + {SCMP_SYS (clone), EPERM, &SCMP_A0 (SCMP_CMP_MASKED_EQ, CLONE_NEWUSER, CLONE_NEWUSER)}, + + /* Don't allow faking input to the controlling tty (CVE-2017-5226) */ +-- +2.19.1 + diff --git a/backport-Fix-handling-of-syscalls-only-allowed-by-devel.patch b/backport-Fix-handling-of-syscalls-only-allowed-by-devel.patch new file mode 100644 index 0000000..9e5c474 --- /dev/null +++ b/backport-Fix-handling-of-syscalls-only-allowed-by-devel.patch @@ -0,0 +1,33 @@ +From 3fc8c672676ae016f8e7cc90481b2feecbad9861 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Fri, 8 Oct 2021 19:00:13 +0100 +Subject: [PATCH] Fix handling of syscalls only allowed by --devel + +This was incorrectly looking at errno instead of -r. + +Fixes: 0b38b0f0 "run: Handle unknown syscalls as intended" +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/3fc8c672676ae016f8e7cc90481b2feecbad9861 + +--- + common/flatpak-run.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index 11f2f19..0130aef 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2296,7 +2296,7 @@ setup_seccomp (FlatpakBwrap *bwrap, + r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 0); + + /* See above for the meaning of EFAULT. */ +- if (errno == EFAULT) ++ if (r == -EFAULT) + flatpak_debug2 ("Unable to block syscall %d: syscall not known to libseccomp?", + scall); + else if (r < 0) +-- +2.19.1 + diff --git a/backport-run-Handle-unknown-syscalls-as-intended.patch b/backport-run-Handle-unknown-syscalls-as-intended.patch new file mode 100644 index 0000000..63fde0a --- /dev/null +++ b/backport-run-Handle-unknown-syscalls-as-intended.patch @@ -0,0 +1,72 @@ +From d419fa67038370e4f4c3ce8c3b5f672d4876cfc8 Mon Sep 17 00:00:00 2001 +From: Simon McVittie +Date: Fri, 8 Oct 2021 17:05:07 +0100 +Subject: [PATCH] run: Handle unknown syscalls as intended + +The error-handling here was + + if (r < 0 && r == -EFAULT) + +but Alex says it was almost certainly intended to be + + if (r < 0 && r != -EFAULT) + +so that syscalls not known to libseccomp are not a fatal error. + +Instead of literally making that change, emit a debug message on -EFAULT +so we can see what is going on. + +This temporarily weakens our defence against CVE-2021-41133 +(GHSA-67h7-w3jq-vh4q) in order to avoid regressions: if the installed +version of libseccomp does not know about the recently-added syscalls, +but the kernel does, then we will not prevent non-native executables +from using those syscalls. + +Resolves: https://github.com/flatpak/flatpak/issues/4458 +Signed-off-by: Simon McVittie + +Conflict:NA +Reference:https://github.com/flatpak/flatpak/commit/d419fa67038370e4f4c3ce8c3b5f672d4876cfc8 + +--- + common/flatpak-run.c | 17 +++++++++++++++-- + 1 file changed, 15 insertions(+), 2 deletions(-) + +diff --git a/common/flatpak-run.c b/common/flatpak-run.c +index c2c0218..11f2f19 100644 +--- a/common/flatpak-run.c ++++ b/common/flatpak-run.c +@@ -2268,7 +2268,16 @@ setup_seccomp (FlatpakBwrap *bwrap, + r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 1, *syscall_blacklist[i].arg); + else + r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 0); +- if (r < 0 && r == -EFAULT /* unknown syscall */) ++ ++ /* EFAULT means "internal libseccomp error", but in practice we get ++ * this for syscall numbers added via flatpak-syscalls-private.h ++ * when trying to filter them on a non-native architecture, because ++ * libseccomp cannot map the syscall number to a name and back to a ++ * number for the non-native architecture. */ ++ if (r == -EFAULT) ++ flatpak_debug2 ("Unable to block syscall %d: syscall not known to libseccomp?", ++ scall); ++ else if (r < 0) + return flatpak_fail_error (error, FLATPAK_ERROR_SETUP_FAILED, _("Failed to block syscall %d"), scall); + } + +@@ -2286,7 +2295,11 @@ setup_seccomp (FlatpakBwrap *bwrap, + else + r = seccomp_rule_add (seccomp, SCMP_ACT_ERRNO (errnum), scall, 0); + +- if (r < 0 && r == -EFAULT /* unknown syscall */) ++ /* See above for the meaning of EFAULT. */ ++ if (errno == EFAULT) ++ flatpak_debug2 ("Unable to block syscall %d: syscall not known to libseccomp?", ++ scall); ++ else if (r < 0) + return flatpak_fail_error (error, FLATPAK_ERROR_SETUP_FAILED, _("Failed to block syscall %d"), scall); + } + } +-- +2.19.1 + diff --git a/flatpak-1.0.3.tar.xz b/flatpak-1.0.3.tar.xz new file mode 100644 index 0000000..4a7735c Binary files /dev/null and b/flatpak-1.0.3.tar.xz differ diff --git a/flatpak.spec b/flatpak.spec new file mode 100644 index 0000000..fdd2839 --- /dev/null +++ b/flatpak.spec @@ -0,0 +1,156 @@ +Name: flatpak +Version: 1.0.3 +Release: 9 +Summary: Application deployment framework for desktop apps +License: LGPLv2+ +URL: http://flatpak.org/ +Source0: https://github.com/flatpak/flatpak/releases/download/%{version}/%{name}-%{version}.tar.xz +Patch0000: modify-automake-version.patch +Patch0001: CVE-2021-21261-1.patch +Patch0002: CVE-2021-21261-2.patch +Patch0003: CVE-2021-21261-3.patch +Patch0004: CVE-2021-21261-4.patch +Patch0005: CVE-2021-21261-5.patch +Patch0006: CVE-2021-21381-1.patch +Patch0007: CVE-2021-21381-2.patch +Patch0008: CVE-2021-21381-3.patch +Patch0009: CVE-2019-8308.patch +Patch0010: CVE-2019-10063.patch +Patch6000: backport-0001-CVE-2021-41133.patch +Patch6001: backport-0002-CVE-2021-41133.patch +Patch6002: backport-0003-CVE-2021-41133.patch +Patch6003: backport-0004-CVE-2021-41133.patch +Patch6004: backport-0005-CVE-2021-41133.patch +Patch6005: backport-0006-CVE-2021-41133.patch +Patch6006: backport-0007-CVE-2021-41133.patch +Patch6007: backport-0008-CVE-2021-41133.patch +Patch6008: backport-run-Handle-unknown-syscalls-as-intended.patch +Patch6009: backport-Fix-handling-of-syscalls-only-allowed-by-devel.patch +Patch6010: backport-0001-CVE-2021-43860.patch +Patch6011: backport-0002-CVE-2021-43860.patch +Patch6012: backport-0003-CVE-2021-43860.patch +Patch6013: backport-0004-CVE-2021-43860.patch +Patch6014: backport-0001-CVE-2022-21682.patch +Patch6015: backport-0002-CVE-2022-21682.patch +Patch6016: backport-0003-CVE-2022-21682.patch +Patch6017: backport-0004-CVE-2022-21682.patch +Patch6018: backport-0005-CVE-2022-21682.patch +Patch6019: backport-0006-CVE-2022-21682.patch + +BuildRequires: pkgconfig(appstream-glib) pkgconfig(gio-unix-2.0) pkgconfig(gobject-introspection-1.0) >= 1.40.0 pkgconfig(json-glib-1.0) pkgconfig(libarchive) >= 2.8.0 +BuildRequires: pkgconfig(libsoup-2.4) pkgconfig(libxml-2.0) >= 2.4 pkgconfig(ostree-1) >= 2018.7 pkgconfig(polkit-gobject-1) pkgconfig(libseccomp) pkgconfig(xau) +BuildRequires: bison bubblewrap >= 0.2.1 docbook-dtds docbook-style-xsl gettext gpgme-devel libcap-devel systemd /usr/bin/xmlto /usr/bin/xsltproc +Requires: ostree%{?_isa} >= 2018.7 bubblewrap >= 0.2.1 ostree-libs%{?_isa} >= 2018.7 +Recommends: /usr/bin/p11-kit xdg-desktop-portal > 0.10 +Provides: %{name}-libs = %{version}-%{release} +Obsoletes: %{name}-libs + +%description +flatpak is a system for building, distributing and running sandboxed desktop +applications on Linux. See https://wiki.gnome.org/Projects/SandboxedApps for +more information. + +%package devel +Summary: Development files for %{name} +License: LGPLv2+ +Requires: %{name}%{?_isa} = %{version}-%{release} + +%description devel +This package contains the pkg-config file and development headers for %{name}. + +%package_help + +%prep +%autosetup -n %{name}-%{version} -p1 + +%build +(if ! test -x configure; then NOCONFIGURE=1 ./autogen.sh; CONFIGFLAGS=--enable-gtk-doc; fi; + %configure --with-priv-mode=none \ + --with-system-bubblewrap --enable-docbook-docs $CONFIGFLAGS) +%make_build V=1 +sed -i 's/idm[0-9]\{5,32\}\"/idm123456789123456\"/g' %{_builddir}/flatpak-1.0.3/doc/flatpak-docs.html + +%install +%make_install +install -pm 644 NEWS README.md %{buildroot}/%{_pkgdocdir} +install -d %{buildroot}%{_localstatedir}/lib/flatpak +install -d %{buildroot}%{_sysconfdir}/flatpak/remotes.d +rm -f %{buildroot}%{_libdir}/libflatpak.la +%find_lang %{name} + +%post +flatpak remote-list --system &> /dev/null || : +%ldconfig_scriptlets libs + +%files -f %{name}.lang +%license COPYING +%doc %{_pkgdocdir} +%{_bindir}/flatpak +%{_bindir}/flatpak-bisect +%{_bindir}/flatpak-coredumpctl +%{_datadir}/bash-completion +%{_datadir}/dbus-1/interfaces/org.freedesktop.Flatpak.xml +%{_datadir}/dbus-1/interfaces/org.freedesktop.portal.Flatpak.xml +%{_datadir}/dbus-1/services/org.freedesktop.Flatpak.service +%{_datadir}/dbus-1/services/org.freedesktop.portal.Flatpak.service +%{_datadir}/dbus-1/system-services/org.freedesktop.Flatpak.SystemHelper.service +%{_datadir}/gdm/env.d +%{_datadir}/%{name} +%{_datadir}/polkit-1/actions/org.freedesktop.Flatpak.policy +%{_datadir}/polkit-1/rules.d/org.freedesktop.Flatpak.rules +%{_datadir}/zsh/site-functions +%{_libexecdir}/flatpak-dbus-proxy +%{_libexecdir}/flatpak-portal +%{_libexecdir}/flatpak-session-helper +%{_libexecdir}/flatpak-system-helper +%dir %{_localstatedir}/lib/flatpak +%{_sysconfdir}/dbus-1/system.d/org.freedesktop.Flatpak.SystemHelper.conf +%{_sysconfdir}/flatpak/remotes.d +%{_sysconfdir}/profile.d/flatpak.sh +%{_unitdir}/flatpak-system-helper.service +%{_userunitdir}/flatpak-portal.service +%{_userunitdir}/flatpak-session-helper.service +%{_userunitdir}/dbus.service.d +%{_libdir}/girepository-1.0/Flatpak-1.0.typelib +%{_libdir}/libflatpak.so.* + +%files devel +%{_datadir}/gir-1.0/Flatpak-1.0.gir +%{_datadir}/gtk-doc/ +%{_includedir}/%{name}/ +%{_libdir}/libflatpak.so +%{_libdir}/pkgconfig/%{name}.pc + +%files help +%{_mandir}/man1/%{name}*.1* +%{_mandir}/man5/%{name}-metadata.5* +%{_mandir}/man5/flatpak-flatpakref.5* +%{_mandir}/man5/flatpak-flatpakrepo.5* +%{_mandir}/man5/flatpak-installation.5* +%{_mandir}/man5/flatpak-remote.5* + +%changelog +* Tue Feb 15 2022 dongyuzhen - 1.0.3-9 +- Fix CVE-2022-21682 + +* Sat Jan 29 2022 dongyuzhen - 1.0.3-8 +- Fix CVE-2021-43860 + +* Wed Oct 20 2021 zhanzhimin - 1.0.3-7 +- Fix CVE-2021-41133 + +* Mon Sep 27 2021 houyingchao - 1.0.3-6 +- Fix CVE-2019-10063 + +* Mon Apr 12 2021 wangyue - 1.0.3-5 +- Fix CVE-2019-8308 + +* Wed Mar 24 2021 wangxiao - 1.0.3-4 +- Fix CVE-2021-21381 + +* Sun Feb 07 2021 wangxiao - 1.0.3-3 +- Modify automake version +- Fix CVE-2021-21261 + +* Thu Nov 21 2019 openEuler Buildteam - 1.0.3-2 +- Package init diff --git a/modify-automake-version.patch b/modify-automake-version.patch new file mode 100644 index 0000000..2020df1 --- /dev/null +++ b/modify-automake-version.patch @@ -0,0 +1,42 @@ +From b3dc7f6af7f2812d5b4a42592976c5b9d7febaad Mon Sep 17 00:00:00 2001 +From: wangxiao65 +Date: Sun, 7 Feb 2021 12:02:08 +0800 +Subject: [PATCH] modify automake version +When Makefile.am is modified, automake needs to be executed. +if the version of automake in the compile enviroment is inconsistent +with the version specified in configure, the compile will fail. + +--- + configure | 2 +- + configure.ac | 2 +- + 2 files changed, 2 insertions(+), 2 deletions(-) + +diff --git a/configure b/configure +index 13abc0a..da4fa78 100755 +--- a/configure ++++ b/configure +@@ -12762,7 +12762,7 @@ CC=$lt_save_CC + ac_config_headers="$ac_config_headers config.h" + + +-am__api_version='1.15' ++am__api_version='1.16' + + # Find a good install program. We prefer a C program (faster), + # so one script is as good as another. But avoid the broken or +diff --git a/configure.ac b/configure.ac +index 202ffc8..4ca143e 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -48,7 +48,7 @@ LT_INIT([disable-static]) + AC_CONFIG_SRCDIR([common/flatpak-dir.c]) + AC_CONFIG_HEADERS([config.h]) + AC_CONFIG_MACRO_DIR([m4]) +-AM_INIT_AUTOMAKE([1.13.4 no-define no-dist-gzip dist-xz tar-ustar foreign subdir-objects]) ++AM_INIT_AUTOMAKE([1.16.2 no-define no-dist-gzip dist-xz tar-ustar foreign subdir-objects]) + AC_PROG_SED + AC_PROG_YACC + +-- +2.23.0 +