summaryrefslogtreecommitdiffstats
path: root/meta/recipes-core
diff options
context:
space:
mode:
Diffstat (limited to 'meta/recipes-core')
-rw-r--r--meta/recipes-core/busybox/busybox/0001-decompress_gunzip-Fix-DoS-if-gzip-is-corrupt.patch58
-rw-r--r--meta/recipes-core/busybox/busybox_1.32.0.bb3
-rw-r--r--meta/recipes-core/glib-2.0/glib-2.0/CVE-2021-27219.patch1444
-rw-r--r--meta/recipes-core/glib-2.0/glib-2.0_2.64.5.bb1
-rw-r--r--meta/recipes-core/glib-2.0/glib.inc4
-rw-r--r--meta/recipes-core/glibc/glibc-version.inc2
-rw-r--r--meta/recipes-core/glibc/glibc_2.32.bb3
-rw-r--r--meta/recipes-core/images/build-appliance-image_15.0.0.bb10
-rw-r--r--meta/recipes-core/initrdscripts/files/init-install-efi.sh5
-rw-r--r--meta/recipes-core/meta/buildtools-extended-tarball.bb10
-rw-r--r--meta/recipes-core/meta/cve-update-db-native.bb14
-rw-r--r--meta/recipes-core/ncurses/ncurses.inc5
-rw-r--r--meta/recipes-core/ovmf/ovmf-shell-image.bb1
-rw-r--r--meta/recipes-core/systemd/systemd-boot_246.9.bb (renamed from meta/recipes-core/systemd/systemd-boot_246.2.bb)0
-rw-r--r--meta/recipes-core/systemd/systemd-conf/wired.network1
-rw-r--r--meta/recipes-core/systemd/systemd-conf_246.9.bb (renamed from meta/recipes-core/systemd/systemd-conf_246.1.bb)3
-rw-r--r--meta/recipes-core/systemd/systemd.inc2
-rw-r--r--meta/recipes-core/systemd/systemd/0001-binfmt-Don-t-install-dependency-links-at-install-tim.patch36
-rw-r--r--meta/recipes-core/systemd/systemd/0001-logind-Restore-chvt-as-non-root-user-without-polkit.patch227
-rw-r--r--meta/recipes-core/systemd/systemd/0002-don-t-use-glibc-specific-qsort_r.patch55
-rw-r--r--meta/recipes-core/systemd/systemd_246.9.bb (renamed from meta/recipes-core/systemd/systemd_246.6.bb)19
21 files changed, 1828 insertions, 75 deletions
diff --git a/meta/recipes-core/busybox/busybox/0001-decompress_gunzip-Fix-DoS-if-gzip-is-corrupt.patch b/meta/recipes-core/busybox/busybox/0001-decompress_gunzip-Fix-DoS-if-gzip-is-corrupt.patch
new file mode 100644
index 0000000000..67c9f189cc
--- /dev/null
+++ b/meta/recipes-core/busybox/busybox/0001-decompress_gunzip-Fix-DoS-if-gzip-is-corrupt.patch
@@ -0,0 +1,58 @@
+From fe791386ebc270219ca00406c9fdadc5130b64ee Mon Sep 17 00:00:00 2001
+From: Samuel Sapalski <samuel.sapalski@nokia.com>
+Date: Wed, 3 Mar 2021 16:31:22 +0100
+Subject: [PATCH] decompress_gunzip: Fix DoS if gzip is corrupt
+
+On certain corrupt gzip files, huft_build will set the error bit on
+the result pointer. If afterwards abort_unzip is called huft_free
+might run into a segmentation fault or an invalid pointer to
+free(p).
+
+In order to mitigate this, we check in huft_free if the error bit
+is set and clear it before the linked list is freed.
+
+Signed-off-by: Samuel Sapalski <samuel.sapalski@nokia.com>
+Signed-off-by: Peter Kaestle <peter.kaestle@nokia.com>
+Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
+
+Upstream-Status: Backport
+CVE: CVE-2021-28831
+Signed-off-by: Chen Qi <Qi.Chen@windriver.com>
+---
+ archival/libarchive/decompress_gunzip.c | 12 ++++++++++--
+ 1 file changed, 10 insertions(+), 2 deletions(-)
+
+diff --git a/archival/libarchive/decompress_gunzip.c b/archival/libarchive/decompress_gunzip.c
+index eb3b64930..e93cd5005 100644
+--- a/archival/libarchive/decompress_gunzip.c
++++ b/archival/libarchive/decompress_gunzip.c
+@@ -220,10 +220,20 @@ static const uint8_t border[] ALIGN1 = {
+ * each table.
+ * t: table to free
+ */
++#define BAD_HUFT(p) ((uintptr_t)(p) & 1)
++#define ERR_RET ((huft_t*)(uintptr_t)1)
+ static void huft_free(huft_t *p)
+ {
+ huft_t *q;
+
++ /*
++ * If 'p' has the error bit set we have to clear it, otherwise we might run
++ * into a segmentation fault or an invalid pointer to free(p)
++ */
++ if (BAD_HUFT(p)) {
++ p = (huft_t*)((uintptr_t)(p) ^ (uintptr_t)(ERR_RET));
++ }
++
+ /* Go through linked list, freeing from the malloced (t[-1]) address. */
+ while (p) {
+ q = (--p)->v.t;
+@@ -289,8 +299,6 @@ static unsigned fill_bitbuffer(STATE_PARAM unsigned bitbuffer, unsigned *current
+ * or a valid pointer to a Huffman table, ORed with 0x1 if incompete table
+ * is given: "fixed inflate" decoder feeds us such data.
+ */
+-#define BAD_HUFT(p) ((uintptr_t)(p) & 1)
+-#define ERR_RET ((huft_t*)(uintptr_t)1)
+ static huft_t* huft_build(const unsigned *b, const unsigned n,
+ const unsigned s, const struct cp_ext *cp_ext,
+ unsigned *m)
diff --git a/meta/recipes-core/busybox/busybox_1.32.0.bb b/meta/recipes-core/busybox/busybox_1.32.0.bb
index 8e23b0d4a2..b91f7cf711 100644
--- a/meta/recipes-core/busybox/busybox_1.32.0.bb
+++ b/meta/recipes-core/busybox/busybox_1.32.0.bb
@@ -46,7 +46,8 @@ SRC_URI = "https://busybox.net/downloads/busybox-${PV}.tar.bz2;name=tarball \
file://0001-hwclock-make-glibc-2.31-compatible.patch \
file://rev.cfg \
file://pgrep.cfg \
-"
+ file://0001-decompress_gunzip-Fix-DoS-if-gzip-is-corrupt.patch \
+ "
SRC_URI_append_libc-musl = " file://musl.cfg "
SRC_URI[tarball.md5sum] = "9576986f1a960da471d03b72a62f13c7"
diff --git a/meta/recipes-core/glib-2.0/glib-2.0/CVE-2021-27219.patch b/meta/recipes-core/glib-2.0/glib-2.0/CVE-2021-27219.patch
new file mode 100644
index 0000000000..a4ec01134a
--- /dev/null
+++ b/meta/recipes-core/glib-2.0/glib-2.0/CVE-2021-27219.patch
@@ -0,0 +1,1444 @@
+commit b70039028b4a39ea071f6ed368a58ad5b5b90ba3
+Author: Anatol Belski <anbelski@microsoft.com>
+Date: Sun Mar 14 17:51:53 2021 +0000
+
+ backport: 2.64.5_CVE-2021-27219
+
+CVE: CVE-2021-27219
+Upstream-Status: Backport
+[https://gitlab.gnome.org/GNOME/glib/-/merge_requests/1926]
+
+Signed-off-by: Anatol Belski <anbelski@linux.microsoft.com>
+
+diff --git a/docs/reference/glib/meson.build b/docs/reference/glib/meson.build
+index 62d95f78d..7eebb04ac 100644
+--- a/docs/reference/glib/meson.build
++++ b/docs/reference/glib/meson.build
+@@ -22,6 +22,7 @@ if get_option('gtk_doc')
+ 'gprintfint.h',
+ 'gmirroringtable.h',
+ 'gscripttable.h',
++ 'gstrfuncsprivate.h',
+ 'glib-mirroring-tab',
+ 'gnulib',
+ 'pcre',
+diff --git a/gio/gdatainputstream.c b/gio/gdatainputstream.c
+index 2e7750cb5..2cdcbda19 100644
+--- a/gio/gdatainputstream.c
++++ b/gio/gdatainputstream.c
+@@ -27,6 +27,7 @@
+ #include "gioenumtypes.h"
+ #include "gioerror.h"
+ #include "glibintl.h"
++#include "gstrfuncsprivate.h"
+
+ #include <string.h>
+
+@@ -856,7 +857,7 @@ static gssize
+ scan_for_chars (GDataInputStream *stream,
+ gsize *checked_out,
+ const char *stop_chars,
+- gssize stop_chars_len)
++ gsize stop_chars_len)
+ {
+ GBufferedInputStream *bstream;
+ const char *buffer;
+@@ -952,7 +953,7 @@ typedef struct
+ gsize checked;
+
+ gchar *stop_chars;
+- gssize stop_chars_len;
++ gsize stop_chars_len;
+ gsize length;
+ } GDataInputStreamReadData;
+
+@@ -1078,12 +1079,17 @@ g_data_input_stream_read_async (GDataInputStream *stream,
+ {
+ GDataInputStreamReadData *data;
+ GTask *task;
++ gsize stop_chars_len_unsigned;
+
+ data = g_slice_new0 (GDataInputStreamReadData);
+- if (stop_chars_len == -1)
+- stop_chars_len = strlen (stop_chars);
+- data->stop_chars = g_memdup (stop_chars, stop_chars_len);
+- data->stop_chars_len = stop_chars_len;
++
++ if (stop_chars_len < 0)
++ stop_chars_len_unsigned = strlen (stop_chars);
++ else
++ stop_chars_len_unsigned = (gsize) stop_chars_len;
++
++ data->stop_chars = g_memdup2 (stop_chars, stop_chars_len_unsigned);
++ data->stop_chars_len = stop_chars_len_unsigned;
+ data->last_saw_cr = FALSE;
+
+ task = g_task_new (stream, cancellable, callback, user_data);
+@@ -1338,17 +1344,20 @@ g_data_input_stream_read_upto (GDataInputStream *stream,
+ gssize found_pos;
+ gssize res;
+ char *data_until;
++ gsize stop_chars_len_unsigned;
+
+ g_return_val_if_fail (G_IS_DATA_INPUT_STREAM (stream), NULL);
+
+ if (stop_chars_len < 0)
+- stop_chars_len = strlen (stop_chars);
++ stop_chars_len_unsigned = strlen (stop_chars);
++ else
++ stop_chars_len_unsigned = (gsize) stop_chars_len;
+
+ bstream = G_BUFFERED_INPUT_STREAM (stream);
+
+ checked = 0;
+
+- while ((found_pos = scan_for_chars (stream, &checked, stop_chars, stop_chars_len)) == -1)
++ while ((found_pos = scan_for_chars (stream, &checked, stop_chars, stop_chars_len_unsigned)) == -1)
+ {
+ if (g_buffered_input_stream_get_available (bstream) ==
+ g_buffered_input_stream_get_buffer_size (bstream))
+diff --git a/gio/gdbusconnection.c b/gio/gdbusconnection.c
+index 1a4dae3bd..9de661bde 100644
+--- a/gio/gdbusconnection.c
++++ b/gio/gdbusconnection.c
+@@ -110,6 +110,7 @@
+ #include "gasyncinitable.h"
+ #include "giostream.h"
+ #include "gasyncresult.h"
++#include "gstrfuncsprivate.h"
+ #include "gtask.h"
+ #include "gmarshal-internal.h"
+
+@@ -4007,7 +4008,7 @@ _g_dbus_interface_vtable_copy (const GDBusInterfaceVTable *vtable)
+ /* Don't waste memory by copying padding - remember to update this
+ * when changing struct _GDBusInterfaceVTable in gdbusconnection.h
+ */
+- return g_memdup ((gconstpointer) vtable, 3 * sizeof (gpointer));
++ return g_memdup2 ((gconstpointer) vtable, 3 * sizeof (gpointer));
+ }
+
+ static void
+@@ -4024,7 +4025,7 @@ _g_dbus_subtree_vtable_copy (const GDBusSubtreeVTable *vtable)
+ /* Don't waste memory by copying padding - remember to update this
+ * when changing struct _GDBusSubtreeVTable in gdbusconnection.h
+ */
+- return g_memdup ((gconstpointer) vtable, 3 * sizeof (gpointer));
++ return g_memdup2 ((gconstpointer) vtable, 3 * sizeof (gpointer));
+ }
+
+ static void
+diff --git a/gio/gdbusinterfaceskeleton.c b/gio/gdbusinterfaceskeleton.c
+index 4a06516c1..4a4b719a5 100644
+--- a/gio/gdbusinterfaceskeleton.c
++++ b/gio/gdbusinterfaceskeleton.c
+@@ -28,6 +28,7 @@
+ #include "gdbusmethodinvocation.h"
+ #include "gdbusconnection.h"
+ #include "gmarshal-internal.h"
++#include "gstrfuncsprivate.h"
+ #include "gtask.h"
+ #include "gioerror.h"
+
+@@ -701,7 +702,7 @@ add_connection_locked (GDBusInterfaceSkeleton *interface_,
+ * properly before building the hooked_vtable, so we create it
+ * once at the last minute.
+ */
+- interface_->priv->hooked_vtable = g_memdup (g_dbus_interface_skeleton_get_vtable (interface_), sizeof (GDBusInterfaceVTable));
++ interface_->priv->hooked_vtable = g_memdup2 (g_dbus_interface_skeleton_get_vtable (interface_), sizeof (GDBusInterfaceVTable));
+ interface_->priv->hooked_vtable->method_call = skeleton_intercept_handle_method_call;
+ }
+
+diff --git a/gio/gfile.c b/gio/gfile.c
+index a2ded14ea..25930435f 100644
+--- a/gio/gfile.c
++++ b/gio/gfile.c
+@@ -60,6 +60,7 @@
+ #include "gasyncresult.h"
+ #include "gioerror.h"
+ #include "glibintl.h"
++#include "gstrfuncsprivate.h"
+
+
+ /**
+@@ -7854,7 +7855,7 @@ measure_disk_usage_progress (gboolean reporting,
+ g_main_context_invoke_full (g_task_get_context (task),
+ g_task_get_priority (task),
+ measure_disk_usage_invoke_progress,
+- g_memdup (&progress, sizeof progress),
++ g_memdup2 (&progress, sizeof progress),
+ g_free);
+ }
+
+@@ -7872,7 +7873,7 @@ measure_disk_usage_thread (GTask *task,
+ data->progress_callback ? measure_disk_usage_progress : NULL, task,
+ &result.disk_usage, &result.num_dirs, &result.num_files,
+ &error))
+- g_task_return_pointer (task, g_memdup (&result, sizeof result), g_free);
++ g_task_return_pointer (task, g_memdup2 (&result, sizeof result), g_free);
+ else
+ g_task_return_error (task, error);
+ }
+@@ -7896,7 +7897,7 @@ g_file_real_measure_disk_usage_async (GFile *file,
+
+ task = g_task_new (file, cancellable, callback, user_data);
+ g_task_set_source_tag (task, g_file_real_measure_disk_usage_async);
+- g_task_set_task_data (task, g_memdup (&data, sizeof data), g_free);
++ g_task_set_task_data (task, g_memdup2 (&data, sizeof data), g_free);
+ g_task_set_priority (task, io_priority);
+
+ g_task_run_in_thread (task, measure_disk_usage_thread);
+diff --git a/gio/giowin32-private.c b/gio/giowin32-private.c
+index 7120ae0ea..47e840805 100644
+--- a/gio/giowin32-private.c
++++ b/gio/giowin32-private.c
+@@ -16,11 +16,12 @@
+ * along with this library; if not, see <http://www.gnu.org/licenses/>.
+ */
+
++#include "gstrfuncsprivate.h"
+
+-static gssize
++static gsize
+ g_utf16_len (const gunichar2 *str)
+ {
+- gssize result;
++ gsize result;
+
+ for (result = 0; str[0] != 0; str++, result++)
+ ;
+@@ -31,17 +32,20 @@ g_utf16_len (const gunichar2 *str)
+ static gunichar2 *
+ g_wcsdup (const gunichar2 *str, gssize str_len)
+ {
+- gssize str_size;
++ gsize str_len_unsigned;
++ gsize str_size;
+
+ g_return_val_if_fail (str != NULL, NULL);
+
+- if (str_len == -1)
+- str_len = g_utf16_len (str);
++ if (str_len < 0)
++ str_len_unsigned = g_utf16_len (str);
++ else
++ str_len_unsigned = (gsize) str_len;
+
+- g_assert (str_len <= G_MAXSIZE / sizeof (gunichar2) - 1);
+- str_size = (str_len + 1) * sizeof (gunichar2);
++ g_assert (str_len_unsigned <= G_MAXSIZE / sizeof (gunichar2) - 1);
++ str_size = (str_len_unsigned + 1) * sizeof (gunichar2);
+
+- return g_memdup (str, str_size);
++ return g_memdup2 (str, str_size);
+ }
+
+ static const gunichar2 *
+diff --git a/gio/gkeyfilesettingsbackend.c b/gio/gkeyfilesettingsbackend.c
+index cd5765afd..de216e615 100644
+--- a/gio/gkeyfilesettingsbackend.c
++++ b/gio/gkeyfilesettingsbackend.c
+@@ -33,6 +33,7 @@
+ #include "gfilemonitor.h"
+ #include "gsimplepermission.h"
+ #include "gsettingsbackendinternal.h"
++#include "gstrfuncsprivate.h"
+ #include "giomodule-priv.h"
+ #include "gportalsupport.h"
+
+@@ -145,8 +146,8 @@ convert_path (GKeyfileSettingsBackend *kfsb,
+ gchar **group,
+ gchar **basename)
+ {
+- gint key_len = strlen (key);
+- gint i;
++ gsize key_len = strlen (key);
++ const gchar *last_slash;
+
+ if (key_len < kfsb->prefix_len ||
+ memcmp (key, kfsb->prefix, kfsb->prefix_len) != 0)
+@@ -155,38 +156,48 @@ convert_path (GKeyfileSettingsBackend *kfsb,
+ key_len -= kfsb->prefix_len;
+ key += kfsb->prefix_len;
+
+- for (i = key_len; i >= 0; i--)
+- if (key[i] == '/')
+- break;
++ last_slash = strrchr (key, '/');
++
++ /* Disallow empty group names or key names */
++ if (key_len == 0 ||
++ (last_slash != NULL &&
++ (*(last_slash + 1) == '\0' ||
++ last_slash == key)))
++ return FALSE;
+
+ if (kfsb->root_group)
+ {
+ /* if a root_group was specified, make sure the user hasn't given
+ * a path that ghosts that group name
+ */
+- if (i == kfsb->root_group_len && memcmp (key, kfsb->root_group, i) == 0)
++ if (last_slash != NULL && (last_slash - key) == kfsb->root_group_len && memcmp (key, kfsb->root_group, last_slash - key) == 0)
+ return FALSE;
+ }
+ else
+ {
+ /* if no root_group was given, ensure that the user gave a path */
+- if (i == -1)
++ if (last_slash == NULL)
+ return FALSE;
+ }
+
+ if (group)
+ {
+- if (i >= 0)
++ if (last_slash != NULL)
+ {
+- *group = g_memdup (key, i + 1);
+- (*group)[i] = '\0';
++ *group = g_memdup2 (key, (last_slash - key) + 1);
++ (*group)[(last_slash - key)] = '\0';
+ }
+ else
+ *group = g_strdup (kfsb->root_group);
+ }
+
+ if (basename)
+- *basename = g_memdup (key + i + 1, key_len - i);
++ {
++ if (last_slash != NULL)
++ *basename = g_memdup2 (last_slash + 1, key_len - (last_slash - key));
++ else
++ *basename = g_strdup (key);
++ }
+
+ return TRUE;
+ }
+diff --git a/gio/gsettingsschema.c b/gio/gsettingsschema.c
+index 0b94f76f6..eb5a3b846 100644
+--- a/gio/gsettingsschema.c
++++ b/gio/gsettingsschema.c
+@@ -20,6 +20,7 @@
+
+ #include "gsettingsschema-internal.h"
+ #include "gsettings.h"
++#include "gstrfuncsprivate.h"
+
+ #include "gvdb/gvdb-reader.h"
+ #include "strinfo.c"
+@@ -1067,9 +1068,9 @@ g_settings_schema_list_children (GSettingsSchema *schema)
+
+ if (g_str_has_suffix (key, "/"))
+ {
+- gint length = strlen (key);
++ gsize length = strlen (key);
+
+- strv[j] = g_memdup (key, length);
++ strv[j] = g_memdup2 (key, length);
+ strv[j][length - 1] = '\0';
+ j++;
+ }
+diff --git a/gio/gsocket.c b/gio/gsocket.c
+index 2a15bdd22..554af026b 100644
+--- a/gio/gsocket.c
++++ b/gio/gsocket.c
+@@ -75,6 +75,7 @@
+ #include "gcredentialsprivate.h"
+ #include "glibintl.h"
+ #include "gioprivate.h"
++#include "gstrfuncsprivate.h"
+
+ #ifdef G_OS_WIN32
+ /* For Windows XP runtime compatibility, but use the system's if_nametoindex() if available */
+@@ -174,7 +175,7 @@ static gboolean g_socket_datagram_based_condition_wait (GDatagramBased
+ GError **error);
+
+ static GSocketAddress *
+-cache_recv_address (GSocket *socket, struct sockaddr *native, int native_len);
++cache_recv_address (GSocket *socket, struct sockaddr *native, size_t native_len);
+
+ static gssize
+ g_socket_receive_message_with_timeout (GSocket *socket,
+@@ -260,7 +261,7 @@ struct _GSocketPrivate
+ struct {
+ GSocketAddress *addr;
+ struct sockaddr *native;
+- gint native_len;
++ gsize native_len;
+ guint64 last_used;
+ } recv_addr_cache[RECV_ADDR_CACHE_SIZE];
+ };
+@@ -5259,14 +5260,14 @@ g_socket_send_messages_with_timeout (GSocket *socket,
+ }
+
+ static GSocketAddress *
+-cache_recv_address (GSocket *socket, struct sockaddr *native, int native_len)
++cache_recv_address (GSocket *socket, struct sockaddr *native, size_t native_len)
+ {
+ GSocketAddress *saddr;
+ gint i;
+ guint64 oldest_time = G_MAXUINT64;
+ gint oldest_index = 0;
+
+- if (native_len <= 0)
++ if (native_len == 0)
+ return NULL;
+
+ saddr = NULL;
+@@ -5274,7 +5275,7 @@ cache_recv_address (GSocket *socket, struct sockaddr *native, int native_len)
+ {
+ GSocketAddress *tmp = socket->priv->recv_addr_cache[i].addr;
+ gpointer tmp_native = socket->priv->recv_addr_cache[i].native;
+- gint tmp_native_len = socket->priv->recv_addr_cache[i].native_len;
++ gsize tmp_native_len = socket->priv->recv_addr_cache[i].native_len;
+
+ if (!tmp)
+ continue;
+@@ -5304,7 +5305,7 @@ cache_recv_address (GSocket *socket, struct sockaddr *native, int native_len)
+ g_free (socket->priv->recv_addr_cache[oldest_index].native);
+ }
+
+- socket->priv->recv_addr_cache[oldest_index].native = g_memdup (native, native_len);
++ socket->priv->recv_addr_cache[oldest_index].native = g_memdup2 (native, native_len);
+ socket->priv->recv_addr_cache[oldest_index].native_len = native_len;
+ socket->priv->recv_addr_cache[oldest_index].addr = g_object_ref (saddr);
+ socket->priv->recv_addr_cache[oldest_index].last_used = g_get_monotonic_time ();
+@@ -5452,6 +5453,9 @@ g_socket_receive_message_with_timeout (GSocket *socket,
+ /* do it */
+ while (1)
+ {
++ /* addrlen has to be of type int because that’s how WSARecvFrom() is defined */
++ G_STATIC_ASSERT (sizeof addr <= G_MAXINT);
++
+ addrlen = sizeof addr;
+ if (address)
+ result = WSARecvFrom (socket->priv->fd,
+diff --git a/gio/gtlspassword.c b/gio/gtlspassword.c
+index 1e437a7b6..bd86a6dfe 100644
+--- a/gio/gtlspassword.c
++++ b/gio/gtlspassword.c
+@@ -23,6 +23,7 @@
+ #include "glibintl.h"
+
+ #include "gioenumtypes.h"
++#include "gstrfuncsprivate.h"
+ #include "gtlspassword.h"
+
+ #include <string.h>
+@@ -287,9 +288,14 @@ g_tls_password_set_value (GTlsPassword *password,
+ g_return_if_fail (G_IS_TLS_PASSWORD (password));
+
+ if (length < 0)
+- length = strlen ((gchar *)value);
++ {
++ /* FIXME: g_tls_password_set_value_full() doesn’t support unsigned gsize */
++ gsize length_unsigned = strlen ((gchar *) value);
++ g_return_if_fail (length_unsigned <= G_MAXSSIZE);
++ length = (gssize) length_unsigned;
++ }
+
+- g_tls_password_set_value_full (password, g_memdup (value, length), length, g_free);
++ g_tls_password_set_value_full (password, g_memdup2 (value, (gsize) length), length, g_free);
+ }
+
+ /**
+diff --git a/gio/gwin32registrykey.c b/gio/gwin32registrykey.c
+index aa7819294..efb9ae713 100644
+--- a/gio/gwin32registrykey.c
++++ b/gio/gwin32registrykey.c
+@@ -28,6 +28,8 @@
+ #include <ntstatus.h>
+ #include <winternl.h>
+
++#include "gstrfuncsprivate.h"
++
+ #ifndef _WDMDDK_
+ typedef enum _KEY_INFORMATION_CLASS {
+ KeyBasicInformation,
+@@ -125,16 +127,34 @@ typedef enum
+ G_WIN32_REGISTRY_UPDATED_PATH = 1,
+ } GWin32RegistryKeyUpdateFlag;
+
++static gsize
++g_utf16_len (const gunichar2 *str)
++{
++ gsize result;
++
++ for (result = 0; str[0] != 0; str++, result++)
++ ;
++
++ return result;
++}
++
+ static gunichar2 *
+-g_wcsdup (const gunichar2 *str,
+- gssize str_size)
++g_wcsdup (const gunichar2 *str, gssize str_len)
+ {
+- if (str_size == -1)
+- {
+- str_size = wcslen (str) + 1;
+- str_size *= sizeof (gunichar2);
+- }
+- return g_memdup (str, str_size);
++ gsize str_len_unsigned;
++ gsize str_size;
++
++ g_return_val_if_fail (str != NULL, NULL);
++
++ if (str_len < 0)
++ str_len_unsigned = g_utf16_len (str);
++ else
++ str_len_unsigned = (gsize) str_len;
++
++ g_assert (str_len_unsigned <= G_MAXSIZE / sizeof (gunichar2) - 1);
++ str_size = (str_len_unsigned + 1) * sizeof (gunichar2);
++
++ return g_memdup2 (str, str_size);
+ }
+
+ /**
+@@ -247,7 +267,7 @@ g_win32_registry_value_iter_copy (const GWin32RegistryValueIter *iter)
+ new_iter->value_name_size = iter->value_name_size;
+
+ if (iter->value_data != NULL)
+- new_iter->value_data = g_memdup (iter->value_data, iter->value_data_size);
++ new_iter->value_data = g_memdup2 (iter->value_data, iter->value_data_size);
+
+ new_iter->value_data_size = iter->value_data_size;
+
+@@ -268,8 +288,8 @@ g_win32_registry_value_iter_copy (const GWin32RegistryValueIter *iter)
+ new_iter->value_data_expanded_charsize = iter->value_data_expanded_charsize;
+
+ if (iter->value_data_expanded_u8 != NULL)
+- new_iter->value_data_expanded_u8 = g_memdup (iter->value_data_expanded_u8,
+- iter->value_data_expanded_charsize);
++ new_iter->value_data_expanded_u8 = g_memdup2 (iter->value_data_expanded_u8,
++ iter->value_data_expanded_charsize);
+
+ new_iter->value_data_expanded_u8_size = iter->value_data_expanded_charsize;
+
+diff --git a/gio/tests/async-close-output-stream.c b/gio/tests/async-close-output-stream.c
+index 5f6620275..d3f97a119 100644
+--- a/gio/tests/async-close-output-stream.c
++++ b/gio/tests/async-close-output-stream.c
+@@ -24,6 +24,8 @@
+ #include <stdlib.h>
+ #include <string.h>
+
++#include "gstrfuncsprivate.h"
++
+ #define DATA_TO_WRITE "Hello world\n"
+
+ typedef struct
+@@ -147,9 +149,9 @@ prepare_data (SetupData *data,
+
+ data->expected_size = g_memory_output_stream_get_data_size (G_MEMORY_OUTPUT_STREAM (data->data_stream));
+
+- g_assert_cmpint (data->expected_size, >, 0);
++ g_assert_cmpuint (data->expected_size, >, 0);
+
+- data->expected_output = g_memdup (written, (guint)data->expected_size);
++ data->expected_output = g_memdup2 (written, data->expected_size);
+
+ /* then recreate the streams and prepare them for the asynchronous close */
+ destroy_streams (data);
+diff --git a/gio/tests/gdbus-export.c b/gio/tests/gdbus-export.c
+index fda654c44..10dd6d82f 100644
+--- a/gio/tests/gdbus-export.c
++++ b/gio/tests/gdbus-export.c
+@@ -23,6 +23,7 @@
+ #include <string.h>
+
+ #include "gdbus-tests.h"
++#include "gstrfuncsprivate.h"
+
+ /* all tests rely on a shared mainloop */
+ static GMainLoop *loop = NULL;
+@@ -671,7 +672,7 @@ subtree_introspect (GDBusConnection *connection,
+ g_assert_not_reached ();
+ }
+
+- return g_memdup (interfaces, 2 * sizeof (void *));
++ return g_memdup2 (interfaces, 2 * sizeof (void *));
+ }
+
+ static const GDBusInterfaceVTable *
+@@ -727,7 +728,7 @@ dynamic_subtree_introspect (GDBusConnection *connection,
+ {
+ const GDBusInterfaceInfo *interfaces[2] = { &dyna_interface_info, NULL };
+
+- return g_memdup (interfaces, 2 * sizeof (void *));
++ return g_memdup2 (interfaces, 2 * sizeof (void *));
+ }
+
+ static const GDBusInterfaceVTable *
+diff --git a/gio/tests/gsettings.c b/gio/tests/gsettings.c
+index baadca8f5..afe594a23 100644
+--- a/gio/tests/gsettings.c
++++ b/gio/tests/gsettings.c
+@@ -1,3 +1,4 @@
++#include <errno.h>
+ #include <stdlib.h>
+ #include <locale.h>
+ #include <libintl.h>
+@@ -1740,6 +1741,14 @@ key_changed_cb (GSettings *settings, const gchar *key, gpointer data)
+ (*b) = TRUE;
+ }
+
++typedef struct
++{
++ const gchar *path;
++ const gchar *root_group;
++ const gchar *keyfile_group;
++ const gchar *root_path;
++} KeyfileTestData;
++
+ /*
+ * Test that using a keyfile works
+ */
+@@ -1834,7 +1843,11 @@ test_keyfile (Fixture *fixture,
+ g_free (str);
+
+ g_settings_set (settings, "farewell", "s", "cheerio");
+-
++
++ /* Check that empty keys/groups are not allowed. */
++ g_assert_false (g_settings_is_writable (settings, ""));
++ g_assert_false (g_settings_is_writable (settings, "/"));
++
+ /* When executing as root, changing the mode of the keyfile will have
+ * no effect on the writability of the settings.
+ */
+@@ -1866,6 +1879,149 @@ test_keyfile (Fixture *fixture,
+ g_free (keyfile_path);
+ }
+
++/*
++ * Test that using a keyfile works with a schema with no path set.
++ */
++static void
++test_keyfile_no_path (Fixture *fixture,
++ gconstpointer user_data)
++{
++ const KeyfileTestData *test_data = user_data;
++ GSettingsBackend *kf_backend;
++ GSettings *settings;
++ GKeyFile *keyfile;
++ gboolean writable;
++ gchar *key = NULL;
++ GError *error = NULL;
++ gchar *keyfile_path = NULL, *store_path = NULL;
++
++ keyfile_path = g_build_filename (fixture->tmp_dir, "keyfile", NULL);
++ store_path = g_build_filename (keyfile_path, "gsettings.store", NULL);
++ kf_backend = g_keyfile_settings_backend_new (store_path, test_data->root_path, test_data->root_group);
++ settings = g_settings_new_with_backend_and_path ("org.gtk.test.no-path", kf_backend, test_data->path);
++ g_object_unref (kf_backend);
++
++ g_settings_reset (settings, "test-boolean");
++ g_assert_true (g_settings_get_boolean (settings, "test-boolean"));
++
++ writable = g_settings_is_writable (settings, "test-boolean");
++ g_assert_true (writable);
++ g_settings_set (settings, "test-boolean", "b", FALSE);
++
++ g_assert_false (g_settings_get_boolean (settings, "test-boolean"));
++
++ g_settings_delay (settings);
++ g_settings_set (settings, "test-boolean", "b", TRUE);
++ g_settings_apply (settings);
++
++ keyfile = g_key_file_new ();
++ g_assert_true (g_key_file_load_from_file (keyfile, store_path, 0, NULL));
++
++ g_assert_true (g_key_file_get_boolean (keyfile, test_data->keyfile_group, "test-boolean", NULL));
++
++ g_key_file_free (keyfile);
++
++ g_settings_reset (settings, "test-boolean");
++ g_settings_apply (settings);
++ keyfile = g_key_file_new ();
++ g_assert_true (g_key_file_load_from_file (keyfile, store_path, 0, NULL));
++
++ g_assert_false (g_key_file_get_string (keyfile, test_data->keyfile_group, "test-boolean", &error));
++ g_assert_error (error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_KEY_NOT_FOUND);
++ g_clear_error (&error);
++
++ /* Check that empty keys/groups are not allowed. */
++ g_assert_false (g_settings_is_writable (settings, ""));
++ g_assert_false (g_settings_is_writable (settings, "/"));
++
++ /* Keys which ghost the root group name are not allowed. This can only be
++ * tested when the path is `/` as otherwise it acts as a prefix and prevents
++ * any ghosting. */
++ if (g_str_equal (test_data->path, "/"))
++ {
++ key = g_strdup_printf ("%s/%s", test_data->root_group, "");
++ g_assert_false (g_settings_is_writable (settings, key));
++ g_free (key);
++
++ key = g_strdup_printf ("%s/%s", test_data->root_group, "/");
++ g_assert_false (g_settings_is_writable (settings, key));
++ g_free (key);
++
++ key = g_strdup_printf ("%s/%s", test_data->root_group, "test-boolean");
++ g_assert_false (g_settings_is_writable (settings, key));
++ g_free (key);
++ }
++
++ g_key_file_free (keyfile);
++ g_object_unref (settings);
++
++ /* Clean up the temporary directory. */
++ g_assert_cmpint (g_chmod (keyfile_path, 0777) == 0 ? 0 : errno, ==, 0);
++ g_assert_cmpint (g_remove (store_path) == 0 ? 0 : errno, ==, 0);
++ g_assert_cmpint (g_rmdir (keyfile_path) == 0 ? 0 : errno, ==, 0);
++ g_free (store_path);
++ g_free (keyfile_path);
++}
++
++/*
++ * Test that a keyfile rejects writes to keys outside its root path.
++ */
++static void
++test_keyfile_outside_root_path (Fixture *fixture,
++ gconstpointer user_data)
++{
++ GSettingsBackend *kf_backend;
++ GSettings *settings;
++ gchar *keyfile_path = NULL, *store_path = NULL;
++
++ keyfile_path = g_build_filename (fixture->tmp_dir, "keyfile", NULL);
++ store_path = g_build_filename (keyfile_path, "gsettings.store", NULL);
++ kf_backend = g_keyfile_settings_backend_new (store_path, "/tests/basic-types/", "root");
++ settings = g_settings_new_with_backend_and_path ("org.gtk.test.no-path", kf_backend, "/tests/");
++ g_object_unref (kf_backend);
++
++ g_assert_false (g_settings_is_writable (settings, "test-boolean"));
++
++ g_object_unref (settings);
++
++ /* Clean up the temporary directory. The keyfile probably doesn’t exist, so
++ * don’t error on failure. */
++ g_remove (store_path);
++ g_assert_cmpint (g_rmdir (keyfile_path) == 0 ? 0 : errno, ==, 0);
++ g_free (store_path);
++ g_free (keyfile_path);
++}
++
++/*
++ * Test that a keyfile rejects writes to keys in the root if no root group is set.
++ */
++static void
++test_keyfile_no_root_group (Fixture *fixture,
++ gconstpointer user_data)
++{
++ GSettingsBackend *kf_backend;
++ GSettings *settings;
++ gchar *keyfile_path = NULL, *store_path = NULL;
++
++ keyfile_path = g_build_filename (fixture->tmp_dir, "keyfile", NULL);
++ store_path = g_build_filename (keyfile_path, "gsettings.store", NULL);
++ kf_backend = g_keyfile_settings_backend_new (store_path, "/", NULL);
++ settings = g_settings_new_with_backend_and_path ("org.gtk.test.no-path", kf_backend, "/");
++ g_object_unref (kf_backend);
++
++ g_assert_false (g_settings_is_writable (settings, "test-boolean"));
++ g_assert_true (g_settings_is_writable (settings, "child/test-boolean"));
++
++ g_object_unref (settings);
++
++ /* Clean up the temporary directory. The keyfile probably doesn’t exist, so
++ * don’t error on failure. */
++ g_remove (store_path);
++ g_assert_cmpint (g_rmdir (keyfile_path) == 0 ? 0 : errno, ==, 0);
++ g_free (store_path);
++ g_free (keyfile_path);
++}
++
+ /* Test that getting child schemas works
+ */
+ static void
+@@ -2844,6 +3000,14 @@ main (int argc, char *argv[])
+ gchar *override_text;
+ gchar *enums;
+ gint result;
++ const KeyfileTestData keyfile_test_data_explicit_path = { "/tests/", "root", "tests", "/" };
++ const KeyfileTestData keyfile_test_data_empty_path = { "/", "root", "root", "/" };
++ const KeyfileTestData keyfile_test_data_long_path = {
++ "/tests/path/is/very/long/and/this/makes/some/comparisons/take/a/different/branch/",
++ "root",
++ "tests/path/is/very/long/and/this/makes/some/comparisons/take/a/different/branch",
++ "/"
++ };
+
+ /* Meson build sets this */
+ #ifdef TEST_LOCALE_PATH
+@@ -2967,6 +3131,11 @@ main (int argc, char *argv[])
+ }
+
+ g_test_add ("/gsettings/keyfile", Fixture, NULL, setup, test_keyfile, teardown);
++ g_test_add ("/gsettings/keyfile/explicit-path", Fixture, &keyfile_test_data_explicit_path, setup, test_keyfile_no_path, teardown);
++ g_test_add ("/gsettings/keyfile/empty-path", Fixture, &keyfile_test_data_empty_path, setup, test_keyfile_no_path, teardown);
++ g_test_add ("/gsettings/keyfile/long-path", Fixture, &keyfile_test_data_long_path, setup, test_keyfile_no_path, teardown);
++ g_test_add ("/gsettings/keyfile/outside-root-path", Fixture, NULL, setup, test_keyfile_outside_root_path, teardown);
++ g_test_add ("/gsettings/keyfile/no-root-group", Fixture, NULL, setup, test_keyfile_no_root_group, teardown);
+ g_test_add_func ("/gsettings/child-schema", test_child_schema);
+ g_test_add_func ("/gsettings/strinfo", test_strinfo);
+ g_test_add_func ("/gsettings/enums", test_enums);
+diff --git a/gio/tests/tls-interaction.c b/gio/tests/tls-interaction.c
+index 4f0737d7e..5661e8e0d 100644
+--- a/gio/tests/tls-interaction.c
++++ b/gio/tests/tls-interaction.c
+@@ -174,6 +174,38 @@ test_interaction_ask_password_finish_failure (GTlsInteraction *interaction,
+ }
+
+
++/* Return a copy of @str that is allocated in a silly way, to exercise
++ * custom free-functions. The returned pointer points to a copy of @str
++ * in a buffer of the form "BEFORE \0 str \0 AFTER". */
++static guchar *
++special_dup (const char *str)
++{
++ GString *buf = g_string_new ("BEFORE");
++ guchar *ret;
++
++ g_string_append_c (buf, '\0');
++ g_string_append (buf, str);
++ g_string_append_c (buf, '\0');
++ g_string_append (buf, "AFTER");
++ ret = (guchar *) g_string_free (buf, FALSE);
++ return ret + strlen ("BEFORE") + 1;
++}
++
++
++/* Free a copy of @str that was made with special_dup(), after asserting
++ * that it has not been corrupted. */
++static void
++special_free (gpointer p)
++{
++ gchar *s = p;
++ gchar *buf = s - strlen ("BEFORE") - 1;
++
++ g_assert_cmpstr (buf, ==, "BEFORE");
++ g_assert_cmpstr (s + strlen (s) + 1, ==, "AFTER");
++ g_free (buf);
++}
++
++
+ static GTlsInteractionResult
+ test_interaction_ask_password_sync_success (GTlsInteraction *interaction,
+ GTlsPassword *password,
+@@ -181,6 +213,8 @@ test_interaction_ask_password_sync_success (GTlsInteraction *interaction,
+ GError **error)
+ {
+ TestInteraction *self;
++ const guchar *value;
++ gsize len;
+
+ g_assert (TEST_IS_INTERACTION (interaction));
+ self = TEST_INTERACTION (interaction);
+@@ -192,6 +226,27 @@ test_interaction_ask_password_sync_success (GTlsInteraction *interaction,
+ g_assert (error != NULL);
+ g_assert (*error == NULL);
+
++ /* Exercise different ways to set the value */
++ g_tls_password_set_value (password, (const guchar *) "foo", 4);
++ len = 0;
++ value = g_tls_password_get_value (password, &len);
++ g_assert_cmpmem (value, len, "foo", 4);
++
++ g_tls_password_set_value (password, (const guchar *) "bar", -1);
++ len = 0;
++ value = g_tls_password_get_value (password, &len);
++ g_assert_cmpmem (value, len, "bar", 3);
++
++ g_tls_password_set_value_full (password, special_dup ("baa"), 4, special_free);
++ len = 0;
++ value = g_tls_password_get_value (password, &len);
++ g_assert_cmpmem (value, len, "baa", 4);
++
++ g_tls_password_set_value_full (password, special_dup ("baz"), -1, special_free);
++ len = 0;
++ value = g_tls_password_get_value (password, &len);
++ g_assert_cmpmem (value, len, "baz", 3);
++
+ /* Don't do this in real life. Include a null terminator for testing */
+ g_tls_password_set_value (password, (const guchar *)"the password", 13);
+ return G_TLS_INTERACTION_HANDLED;
+diff --git a/gio/win32/gwinhttpfile.c b/gio/win32/gwinhttpfile.c
+index cf5eed31d..246ec0578 100644
+--- a/gio/win32/gwinhttpfile.c
++++ b/gio/win32/gwinhttpfile.c
+@@ -29,6 +29,7 @@
+ #include "gio/gfile.h"
+ #include "gio/gfileattribute.h"
+ #include "gio/gfileinfo.h"
++#include "gstrfuncsprivate.h"
+ #include "gwinhttpfile.h"
+ #include "gwinhttpfileinputstream.h"
+ #include "gwinhttpfileoutputstream.h"
+@@ -393,10 +394,10 @@ g_winhttp_file_resolve_relative_path (GFile *file,
+ child = g_object_new (G_TYPE_WINHTTP_FILE, NULL);
+ child->vfs = winhttp_file->vfs;
+ child->url = winhttp_file->url;
+- child->url.lpszScheme = g_memdup (winhttp_file->url.lpszScheme, (winhttp_file->url.dwSchemeLength+1)*2);
+- child->url.lpszHostName = g_memdup (winhttp_file->url.lpszHostName, (winhttp_file->url.dwHostNameLength+1)*2);
+- child->url.lpszUserName = g_memdup (winhttp_file->url.lpszUserName, (winhttp_file->url.dwUserNameLength+1)*2);
+- child->url.lpszPassword = g_memdup (winhttp_file->url.lpszPassword, (winhttp_file->url.dwPasswordLength+1)*2);
++ child->url.lpszScheme = g_memdup2 (winhttp_file->url.lpszScheme, ((gsize) winhttp_file->url.dwSchemeLength + 1) * 2);
++ child->url.lpszHostName = g_memdup2 (winhttp_file->url.lpszHostName, ((gsize) winhttp_file->url.dwHostNameLength + 1) * 2);
++ child->url.lpszUserName = g_memdup2 (winhttp_file->url.lpszUserName, ((gsize) winhttp_file->url.dwUserNameLength + 1) * 2);
++ child->url.lpszPassword = g_memdup2 (winhttp_file->url.lpszPassword, ((gsize) winhttp_file->url.dwPasswordLength + 1) * 2);
+ child->url.lpszUrlPath = wnew_path;
+ child->url.dwUrlPathLength = wcslen (wnew_path);
+ child->url.lpszExtraInfo = NULL;
+diff --git a/glib/gbytes.c b/glib/gbytes.c
+index ec6923188..6f17d104c 100644
+--- a/glib/gbytes.c
++++ b/glib/gbytes.c
+@@ -34,6 +34,8 @@
+
+ #include <string.h>
+
++#include "gstrfuncsprivate.h"
++
+ /**
+ * GBytes:
+ *
+@@ -95,7 +97,7 @@ g_bytes_new (gconstpointer data,
+ {
+ g_return_val_if_fail (data != NULL || size == 0, NULL);
+
+- return g_bytes_new_take (g_memdup (data, size), size);
++ return g_bytes_new_take (g_memdup2 (data, size), size);
+ }
+
+ /**
+@@ -499,7 +501,7 @@ g_bytes_unref_to_data (GBytes *bytes,
+ * Copy: Non g_malloc (or compatible) allocator, or static memory,
+ * so we have to copy, and then unref.
+ */
+- result = g_memdup (bytes->data, bytes->size);
++ result = g_memdup2 (bytes->data, bytes->size);
+ *size = bytes->size;
+ g_bytes_unref (bytes);
+ }
+diff --git a/glib/gdir.c b/glib/gdir.c
+index 6b85e99c8..6747a8c6f 100644
+--- a/glib/gdir.c
++++ b/glib/gdir.c
+@@ -37,6 +37,7 @@
+ #include "gconvert.h"
+ #include "gfileutils.h"
+ #include "gstrfuncs.h"
++#include "gstrfuncsprivate.h"
+ #include "gtestutils.h"
+ #include "glibintl.h"
+
+@@ -112,7 +113,7 @@ g_dir_open_with_errno (const gchar *path,
+ return NULL;
+ #endif
+
+- return g_memdup (&dir, sizeof dir);
++ return g_memdup2 (&dir, sizeof dir);
+ }
+
+ /**
+diff --git a/glib/ghash.c b/glib/ghash.c
+index 0f1562a06..c1e15c957 100644
+--- a/glib/ghash.c
++++ b/glib/ghash.c
+@@ -34,6 +34,7 @@
+ #include "gmacros.h"
+ #include "glib-private.h"
+ #include "gstrfuncs.h"
++#include "gstrfuncsprivate.h"
+ #include "gatomic.h"
+ #include "gtestutils.h"
+ #include "gslice.h"
+@@ -962,7 +963,7 @@ g_hash_table_ensure_keyval_fits (GHashTable *hash_table, gpointer key, gpointer
+ if (hash_table->have_big_keys)
+ {
+ if (key != value)
+- hash_table->values = g_memdup (hash_table->keys, sizeof (gpointer) * hash_table->size);
++ hash_table->values = g_memdup2 (hash_table->keys, sizeof (gpointer) * hash_table->size);
+ /* Keys and values are both big now, so no need for further checks */
+ return;
+ }
+@@ -970,7 +971,7 @@ g_hash_table_ensure_keyval_fits (GHashTable *hash_table, gpointer key, gpointer
+ {
+ if (key != value)
+ {
+- hash_table->values = g_memdup (hash_table->keys, sizeof (guint) * hash_table->size);
++ hash_table->values = g_memdup2 (hash_table->keys, sizeof (guint) * hash_table->size);
+ is_a_set = FALSE;
+ }
+ }
+@@ -998,7 +999,7 @@ g_hash_table_ensure_keyval_fits (GHashTable *hash_table, gpointer key, gpointer
+
+ /* Just split if necessary */
+ if (is_a_set && key != value)
+- hash_table->values = g_memdup (hash_table->keys, sizeof (gpointer) * hash_table->size);
++ hash_table->values = g_memdup2 (hash_table->keys, sizeof (gpointer) * hash_table->size);
+
+ #endif
+ }
+diff --git a/glib/giochannel.c b/glib/giochannel.c
+index d16399846..b41381d38 100644
+--- a/glib/giochannel.c
++++ b/glib/giochannel.c
+@@ -37,6 +37,7 @@
+ #include "giochannel.h"
+
+ #include "gstrfuncs.h"
++#include "gstrfuncsprivate.h"
+ #include "gtestutils.h"
+ #include "glibintl.h"
+
+@@ -886,17 +887,26 @@ g_io_channel_set_line_term (GIOChannel *channel,
+ const gchar *line_term,
+ gint length)
+ {
++ guint length_unsigned;
++
+ g_return_if_fail (channel != NULL);
+ g_return_if_fail (line_term == NULL || length != 0); /* Disallow "" */
+
+ if (line_term == NULL)
+- length = 0;
+- else if (length < 0)
+- length = strlen (line_term);
++ length_unsigned = 0;
++ else if (length >= 0)
++ length_unsigned = (guint) length;
++ else
++ {
++ /* FIXME: We’re constrained by line_term_len being a guint here */
++ gsize length_size = strlen (line_term);
++ g_return_if_fail (length_size <= G_MAXUINT);
++ length_unsigned = (guint) length_size;
++ }
+
+ g_free (channel->line_term);
+- channel->line_term = line_term ? g_memdup (line_term, length) : NULL;
+- channel->line_term_len = length;
++ channel->line_term = line_term ? g_memdup2 (line_term, length_unsigned) : NULL;
++ channel->line_term_len = length_unsigned;
+ }
+
+ /**
+@@ -1673,10 +1683,10 @@ g_io_channel_read_line (GIOChannel *channel,
+
+ /* Copy the read bytes (including any embedded nuls) and nul-terminate.
+ * `USE_BUF (channel)->str` is guaranteed to be nul-terminated as it’s a
+- * #GString, so it’s safe to call g_memdup() with +1 length to allocate
++ * #GString, so it’s safe to call g_memdup2() with +1 length to allocate
+ * a nul-terminator. */
+ g_assert (USE_BUF (channel));
+- line = g_memdup (USE_BUF (channel)->str, got_length + 1);
++ line = g_memdup2 (USE_BUF (channel)->str, got_length + 1);
+ line[got_length] = '\0';
+ *str_return = g_steal_pointer (&line);
+ g_string_erase (USE_BUF (channel), 0, got_length);
+diff --git a/glib/gslice.c b/glib/gslice.c
+index 4c758c3be..bcdbb8853 100644
+--- a/glib/gslice.c
++++ b/glib/gslice.c
+@@ -41,6 +41,7 @@
+ #include "gmain.h"
+ #include "gmem.h" /* gslice.h */
+ #include "gstrfuncs.h"
++#include "gstrfuncsprivate.h"
+ #include "gutils.h"
+ #include "gtrashstack.h"
+ #include "gtestutils.h"
+@@ -350,7 +351,7 @@ g_slice_get_config_state (GSliceConfig ckey,
+ array[i++] = allocator->contention_counters[address];
+ array[i++] = allocator_get_magazine_threshold (allocator, address);
+ *n_values = i;
+- return g_memdup (array, sizeof (array[0]) * *n_values);
++ return g_memdup2 (array, sizeof (array[0]) * *n_values);
+ default:
+ return NULL;
+ }
+diff --git a/glib/gstrfuncsprivate.h b/glib/gstrfuncsprivate.h
+new file mode 100644
+index 000000000..85c88328a
+--- /dev/null
++++ b/glib/gstrfuncsprivate.h
+@@ -0,0 +1,55 @@
++/* GLIB - Library of useful routines for C programming
++ * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
++ *
++ * This library 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 <http://www.gnu.org/licenses/>.
++ */
++
++#include <glib.h>
++#include <string.h>
++
++/*
++ * g_memdup2:
++ * @mem: (nullable): the memory to copy.
++ * @byte_size: the number of bytes to copy.
++ *
++ * Allocates @byte_size bytes of memory, and copies @byte_size bytes into it
++ * from @mem. If @mem is %NULL it returns %NULL.
++ *
++ * This replaces g_memdup(), which was prone to integer overflows when
++ * converting the argument from a #gsize to a #guint.
++ *
++ * This static inline version is a backport of the new public API from
++ * GLib 2.68, kept internal to GLib for backport to older stable releases.
++ * See https://gitlab.gnome.org/GNOME/glib/-/issues/2319.
++ *
++ * Returns: (nullable): a pointer to the newly-allocated copy of the memory,
++ * or %NULL if @mem is %NULL.
++ * Since: 2.68
++ */
++static inline gpointer
++g_memdup2 (gconstpointer mem,
++ gsize byte_size)
++{
++ gpointer new_mem;
++
++ if (mem && byte_size != 0)
++ {
++ new_mem = g_malloc (byte_size);
++ memcpy (new_mem, mem, byte_size);
++ }
++ else
++ new_mem = NULL;
++
++ return new_mem;
++}
+diff --git a/glib/gtestutils.c b/glib/gtestutils.c
+index 18b117285..26d46ad75 100644
+--- a/glib/gtestutils.c
++++ b/glib/gtestutils.c
+@@ -49,6 +49,7 @@
+ #include "gpattern.h"
+ #include "grand.h"
+ #include "gstrfuncs.h"
++#include "gstrfuncsprivate.h"
+ #include "gtimer.h"
+ #include "gslice.h"
+ #include "gspawn.h"
+@@ -3803,7 +3804,7 @@ g_test_log_extract (GTestLogBuffer *tbuffer)
+ if (p <= tbuffer->data->str + mlength)
+ {
+ g_string_erase (tbuffer->data, 0, mlength);
+- tbuffer->msgs = g_slist_prepend (tbuffer->msgs, g_memdup (&msg, sizeof (msg)));
++ tbuffer->msgs = g_slist_prepend (tbuffer->msgs, g_memdup2 (&msg, sizeof (msg)));
+ return TRUE;
+ }
+
+diff --git a/glib/gvariant.c b/glib/gvariant.c
+index 77d7e746b..ef4257f6d 100644
+--- a/glib/gvariant.c
++++ b/glib/gvariant.c
+@@ -33,6 +33,7 @@
+
+ #include <string.h>
+
++#include "gstrfuncsprivate.h"
+
+ /**
+ * SECTION:gvariant
+@@ -725,7 +726,7 @@ g_variant_new_variant (GVariant *value)
+ g_variant_ref_sink (value);
+
+ return g_variant_new_from_children (G_VARIANT_TYPE_VARIANT,
+- g_memdup (&value, sizeof value),
++ g_memdup2 (&value, sizeof value),
+ 1, g_variant_is_trusted (value));
+ }
+
+@@ -1229,7 +1230,7 @@ g_variant_new_fixed_array (const GVariantType *element_type,
+ return NULL;
+ }
+
+- data = g_memdup (elements, n_elements * element_size);
++ data = g_memdup2 (elements, n_elements * element_size);
+ value = g_variant_new_from_data (array_type, data,
+ n_elements * element_size,
+ FALSE, g_free, data);
+@@ -1908,7 +1909,7 @@ g_variant_dup_bytestring (GVariant *value,
+ if (length)
+ *length = size;
+
+- return g_memdup (original, size + 1);
++ return g_memdup2 (original, size + 1);
+ }
+
+ /**
+diff --git a/glib/gvarianttype.c b/glib/gvarianttype.c
+index c46f1a2c6..585e29ab2 100644
+--- a/glib/gvarianttype.c
++++ b/glib/gvarianttype.c
+@@ -28,6 +28,7 @@
+
+ #include <string.h>
+
++#include "gstrfuncsprivate.h"
+
+ /**
+ * SECTION:gvarianttype
+@@ -1181,7 +1182,7 @@ g_variant_type_new_tuple (const GVariantType * const *items,
+ g_assert (offset < sizeof buffer);
+ buffer[offset++] = ')';
+
+- return (GVariantType *) g_memdup (buffer, offset);
++ return (GVariantType *) g_memdup2 (buffer, offset);
+ }
+
+ /**
+diff --git a/glib/meson.build b/glib/meson.build
+index 456e0c2a1..2e5cd77bb 100644
+--- a/glib/meson.build
++++ b/glib/meson.build
+@@ -268,6 +268,7 @@ glib_sources = files(
+ 'gslist.c',
+ 'gstdio.c',
+ 'gstrfuncs.c',
++ 'gstrfuncsprivate.h',
+ 'gstring.c',
+ 'gstringchunk.c',
+ 'gtestutils.c',
+diff --git a/glib/tests/array-test.c b/glib/tests/array-test.c
+index 1da514a3e..88f22de80 100644
+--- a/glib/tests/array-test.c
++++ b/glib/tests/array-test.c
+@@ -29,6 +29,8 @@
+ #include <string.h>
+ #include "glib.h"
+
++#include "gstrfuncsprivate.h"
++
+ /* Test data to be passed to any function which calls g_array_new(), providing
+ * the parameters for that call. Most #GArray tests should be repeated for all
+ * possible values of #ArrayTestData. */
+@@ -1917,7 +1919,7 @@ byte_array_new_take (void)
+ GByteArray *gbarray;
+ guint8 *data;
+
+- data = g_memdup ("woooweeewow", 11);
++ data = g_memdup2 ("woooweeewow", 11);
+ gbarray = g_byte_array_new_take (data, 11);
+ g_assert (gbarray->data == data);
+ g_assert_cmpuint (gbarray->len, ==, 11);
+diff --git a/glib/tests/io-channel.c b/glib/tests/io-channel.c
+index ff53fcef7..4a1b10876 100644
+--- a/glib/tests/io-channel.c
++++ b/glib/tests/io-channel.c
+@@ -49,8 +49,10 @@ test_read_line_embedded_nuls (void)
+ channel = g_io_channel_new_file (filename, "r", &local_error);
+ g_assert_no_error (local_error);
+
+- /* Only break on newline characters, not nuls. */
+- g_io_channel_set_line_term (channel, "\n", 1);
++ /* Only break on newline characters, not nuls.
++ * Use length -1 here to exercise glib#2323; the case where length > 0
++ * is covered in glib/tests/protocol.c. */
++ g_io_channel_set_line_term (channel, "\n", -1);
+ g_io_channel_set_encoding (channel, NULL, &local_error);
+ g_assert_no_error (local_error);
+
+diff --git a/glib/tests/option-context.c b/glib/tests/option-context.c
+index 149d22353..88d2b80d1 100644
+--- a/glib/tests/option-context.c
++++ b/glib/tests/option-context.c
+@@ -27,6 +27,8 @@
+ #include <string.h>
+ #include <locale.h>
+
++#include "gstrfuncsprivate.h"
++
+ static GOptionEntry main_entries[] = {
+ { "main-switch", 0, 0,
+ G_OPTION_ARG_NONE, NULL,
+@@ -256,7 +258,7 @@ join_stringv (int argc, char **argv)
+ static char **
+ copy_stringv (char **argv, int argc)
+ {
+- return g_memdup (argv, sizeof (char *) * (argc + 1));
++ return g_memdup2 (argv, sizeof (char *) * (argc + 1));
+ }
+
+ static void
+@@ -2323,7 +2325,7 @@ test_group_parse (void)
+ g_option_context_add_group (context, group);
+
+ argv = split_string ("program --test arg1 -f arg2 --group-test arg3 --frob arg4 -z arg5", &argc);
+- orig_argv = g_memdup (argv, (argc + 1) * sizeof (char *));
++ orig_argv = g_memdup2 (argv, (argc + 1) * sizeof (char *));
+
+ retval = g_option_context_parse (context, &argc, &argv, &error);
+
+diff --git a/glib/tests/strfuncs.c b/glib/tests/strfuncs.c
+index e1f9619c7..d968afff9 100644
+--- a/glib/tests/strfuncs.c
++++ b/glib/tests/strfuncs.c
+@@ -32,6 +32,8 @@
+ #include <string.h>
+ #include "glib.h"
+
++#include "gstrfuncsprivate.h"
++
+ #if defined (_MSC_VER) && (_MSC_VER <= 1800)
+ #define isnan(x) _isnan(x)
+
+@@ -219,6 +221,26 @@ test_memdup (void)
+ g_free (str_dup);
+ }
+
++/* Testing g_memdup2() function with various positive and negative cases */
++static void
++test_memdup2 (void)
++{
++ gchar *str_dup = NULL;
++ const gchar *str = "The quick brown fox jumps over the lazy dog";
++
++ /* Testing negative cases */
++ g_assert_null (g_memdup2 (NULL, 1024));
++ g_assert_null (g_memdup2 (str, 0));
++ g_assert_null (g_memdup2 (NULL, 0));
++
++ /* Testing normal usage cases */
++ str_dup = g_memdup2 (str, strlen (str) + 1);
++ g_assert_nonnull (str_dup);
++ g_assert_cmpstr (str, ==, str_dup);
++
++ g_free (str_dup);
++}
++
+ /* Testing g_strpcpy() function with various positive and negative cases */
+ static void
+ test_stpcpy (void)
+@@ -2523,6 +2545,7 @@ main (int argc,
+ g_test_add_func ("/strfuncs/has-prefix", test_has_prefix);
+ g_test_add_func ("/strfuncs/has-suffix", test_has_suffix);
+ g_test_add_func ("/strfuncs/memdup", test_memdup);
++ g_test_add_func ("/strfuncs/memdup2", test_memdup2);
+ g_test_add_func ("/strfuncs/stpcpy", test_stpcpy);
+ g_test_add_func ("/strfuncs/str_match_string", test_str_match_string);
+ g_test_add_func ("/strfuncs/str_tokenize_and_fold", test_str_tokenize_and_fold);
+diff --git a/gobject/gsignal.c b/gobject/gsignal.c
+index 45effa92d..effbfec62 100644
+--- a/gobject/gsignal.c
++++ b/gobject/gsignal.c
+@@ -28,6 +28,7 @@
+ #include <signal.h>
+
+ #include "gsignal.h"
++#include "gstrfuncsprivate.h"
+ #include "gtype-private.h"
+ #include "gbsearcharray.h"
+ #include "gvaluecollector.h"
+@@ -1809,7 +1810,7 @@ g_signal_newv (const gchar *signal_name,
+ node->single_va_closure_is_valid = FALSE;
+ node->flags = signal_flags & G_SIGNAL_FLAGS_MASK;
+ node->n_params = n_params;
+- node->param_types = g_memdup (param_types, sizeof (GType) * n_params);
++ node->param_types = g_memdup2 (param_types, sizeof (GType) * n_params);
+ node->return_type = return_type;
+ node->class_closure_bsa = NULL;
+ if (accumulator)
+diff --git a/gobject/gtype.c b/gobject/gtype.c
+index b5ef2d11e..8d152dccc 100644
+--- a/gobject/gtype.c
++++ b/gobject/gtype.c
+@@ -33,6 +33,7 @@
+
+ #include "glib-private.h"
+ #include "gconstructor.h"
++#include "gstrfuncsprivate.h"
+
+ #ifdef G_OS_WIN32
+ #include <windows.h>
+@@ -1470,7 +1471,7 @@ type_add_interface_Wm (TypeNode *node,
+ iholder->next = iface_node_get_holders_L (iface);
+ iface_node_set_holders_W (iface, iholder);
+ iholder->instance_type = NODE_TYPE (node);
+- iholder->info = info ? g_memdup (info, sizeof (*info)) : NULL;
++ iholder->info = info ? g_memdup2 (info, sizeof (*info)) : NULL;
+ iholder->plugin = plugin;
+
+ /* create an iface entry for this type */
+@@ -1731,7 +1732,7 @@ type_iface_retrieve_holder_info_Wm (TypeNode *iface,
+ INVALID_RECURSION ("g_type_plugin_*", iholder->plugin, NODE_NAME (iface));
+
+ check_interface_info_I (iface, instance_type, &tmp_info);
+- iholder->info = g_memdup (&tmp_info, sizeof (tmp_info));
++ iholder->info = g_memdup2 (&tmp_info, sizeof (tmp_info));
+ }
+
+ return iholder; /* we don't modify write lock upon returning NULL */
+@@ -2016,10 +2017,10 @@ type_iface_vtable_base_init_Wm (TypeNode *iface,
+ IFaceEntry *pentry = type_lookup_iface_entry_L (pnode, iface);
+
+ if (pentry)
+- vtable = g_memdup (pentry->vtable, iface->data->iface.vtable_size);
++ vtable = g_memdup2 (pentry->vtable, iface->data->iface.vtable_size);
+ }
+ if (!vtable)
+- vtable = g_memdup (iface->data->iface.dflt_vtable, iface->data->iface.vtable_size);
++ vtable = g_memdup2 (iface->data->iface.dflt_vtable, iface->data->iface.vtable_size);
+ entry->vtable = vtable;
+ vtable->g_type = NODE_TYPE (iface);
+ vtable->g_instance_type = NODE_TYPE (node);
+diff --git a/gobject/gtypemodule.c b/gobject/gtypemodule.c
+index 4ecaf8c88..20911fafd 100644
+--- a/gobject/gtypemodule.c
++++ b/gobject/gtypemodule.c
+@@ -19,6 +19,7 @@
+
+ #include <stdlib.h>
+
++#include "gstrfuncsprivate.h"
+ #include "gtypeplugin.h"
+ #include "gtypemodule.h"
+
+@@ -436,7 +437,7 @@ g_type_module_register_type (GTypeModule *module,
+ module_type_info->loaded = TRUE;
+ module_type_info->info = *type_info;
+ if (type_info->value_table)
+- module_type_info->info.value_table = g_memdup (type_info->value_table,
++ module_type_info->info.value_table = g_memdup2 (type_info->value_table,
+ sizeof (GTypeValueTable));
+
+ return module_type_info->type;
+diff --git a/gobject/tests/param.c b/gobject/tests/param.c
+index 93c3f4b94..0a77e51b7 100644
+--- a/gobject/tests/param.c
++++ b/gobject/tests/param.c
+@@ -2,6 +2,8 @@
+ #include <glib-object.h>
+ #include <stdlib.h>
+
++#include "gstrfuncsprivate.h"
++
+ static void
+ test_param_value (void)
+ {
+@@ -874,7 +876,7 @@ main (int argc, char *argv[])
+ test_path = g_strdup_printf ("/param/implement/subprocess/%d-%d-%d-%d",
+ data.change_this_flag, data.change_this_type,
+ data.use_this_flag, data.use_this_type);
+- test_data = g_memdup (&data, sizeof (TestParamImplementData));
++ test_data = g_memdup2 (&data, sizeof (TestParamImplementData));
+ g_test_add_data_func_full (test_path, test_data, test_param_implement_child, g_free);
+ g_free (test_path);
+ }
diff --git a/meta/recipes-core/glib-2.0/glib-2.0_2.64.5.bb b/meta/recipes-core/glib-2.0/glib-2.0_2.64.5.bb
index b9462bc945..ed7b649dc6 100644
--- a/meta/recipes-core/glib-2.0/glib-2.0_2.64.5.bb
+++ b/meta/recipes-core/glib-2.0/glib-2.0_2.64.5.bb
@@ -18,6 +18,7 @@ SRC_URI = "${GNOME_MIRROR}/glib/${SHRT_VER}/glib-${PV}.tar.xz \
file://0001-gio-tests-resources.c-comment-out-a-build-host-only-.patch \
file://tzdata-update.patch \
file://CVE-2020-35457.patch \
+ file://CVE-2021-27219.patch \
"
SRC_URI_append_class-native = " file://relocate-modules.patch"
diff --git a/meta/recipes-core/glib-2.0/glib.inc b/meta/recipes-core/glib-2.0/glib.inc
index e48b5cb67b..71777bc459 100644
--- a/meta/recipes-core/glib-2.0/glib.inc
+++ b/meta/recipes-core/glib-2.0/glib.inc
@@ -34,10 +34,6 @@ DEPENDS_append_class-target = "${@' gtk-doc' if d.getVar('GTKDOC_ENABLED') == 'T
GTKDOC_MESON_OPTION = "gtk_doc"
-# This avoids the need to depend on target python3, which in case of mingw is not even possible.
-# meson's python configuration pokes into python3 configuration, so this provides the native config to it.
-unset _PYTHON_SYSCONFIGDATA_NAME
-
S = "${WORKDIR}/glib-${PV}"
PACKAGECONFIG ??= "system-pcre libmount \
diff --git a/meta/recipes-core/glibc/glibc-version.inc b/meta/recipes-core/glibc/glibc-version.inc
index 1566056297..84d199bb1d 100644
--- a/meta/recipes-core/glibc/glibc-version.inc
+++ b/meta/recipes-core/glibc/glibc-version.inc
@@ -1,6 +1,6 @@
SRCBRANCH ?= "release/2.32/master"
PV = "2.32"
-SRCREV_glibc ?= "3de512be7ea6053255afed6154db9ee31d4e557a"
+SRCREV_glibc ?= "44b395932961a29825da4ad025124a6760858d9c"
SRCREV_localedef ?= "bd644c9e6f3e20c5504da1488448173c69c56c28"
GLIBC_GIT_URI ?= "git://sourceware.org/git/glibc.git"
diff --git a/meta/recipes-core/glibc/glibc_2.32.bb b/meta/recipes-core/glibc/glibc_2.32.bb
index b850c28c78..03aea52508 100644
--- a/meta/recipes-core/glibc/glibc_2.32.bb
+++ b/meta/recipes-core/glibc/glibc_2.32.bb
@@ -1,7 +1,8 @@
require glibc.inc
require glibc-version.inc
-CVE_CHECK_WHITELIST += "CVE-2020-10029"
+# whitelist CVE's with fixes in latest release/2.32/master branch
+CVE_CHECK_WHITELIST += "CVE-2019-25013 CVE-2020-10029 CVE-2020-27618 CVE-2021-27645 CVE-2021-3326"
DEPENDS += "gperf-native bison-native make-native"
diff --git a/meta/recipes-core/images/build-appliance-image_15.0.0.bb b/meta/recipes-core/images/build-appliance-image_15.0.0.bb
index 7f87c065db..9e944a2534 100644
--- a/meta/recipes-core/images/build-appliance-image_15.0.0.bb
+++ b/meta/recipes-core/images/build-appliance-image_15.0.0.bb
@@ -22,9 +22,9 @@ APPEND += "rootfstype=ext4 quiet"
DEPENDS = "zip-native python3-pip-native"
IMAGE_FSTYPES = "wic.vmdk"
-inherit core-image module-base setuptools3
+inherit core-image setuptools3
-SRCREV ?= "76dac9d657f3b2864dec3bfcd2ee392fafdcdfe6"
+SRCREV ?= "79c4792da2b400431c09d9a2f53efd4443812281"
SRC_URI = "git://git.yoctoproject.org/poky;branch=gatesgarth \
file://Yocto_Build_Appliance.vmx \
file://Yocto_Build_Appliance.vmxf \
@@ -61,12 +61,6 @@ fakeroot do_populate_poky_src () {
# Place the README_VirtualBox_Toaster file in builders home folder.
cp ${WORKDIR}/README_VirtualBox_Toaster.txt ${IMAGE_ROOTFS}/home/builder/
- # Create a symlink, needed for out-of-tree kernel modules build
- if [ ! -e ${IMAGE_ROOTFS}/lib/modules/${KERNEL_VERSION}/build ]; then
- rm -f ${IMAGE_ROOTFS}/lib/modules/${KERNEL_VERSION}/build
- lnr ${IMAGE_ROOTFS}${KERNEL_SRC_PATH} ${IMAGE_ROOTFS}/lib/modules/${KERNEL_VERSION}/build
- fi
-
echo "INHERIT += \"rm_work\"" >> ${IMAGE_ROOTFS}/home/builder/poky/build/conf/auto.conf
echo "export LC_ALL=en_US.utf8" >> ${IMAGE_ROOTFS}/home/builder/.bashrc
diff --git a/meta/recipes-core/initrdscripts/files/init-install-efi.sh b/meta/recipes-core/initrdscripts/files/init-install-efi.sh
index b6855b5aac..f667518b89 100644
--- a/meta/recipes-core/initrdscripts/files/init-install-efi.sh
+++ b/meta/recipes-core/initrdscripts/files/init-install-efi.sh
@@ -279,6 +279,11 @@ fi
umount /tgt_root
+# copy any extra files needed for ESP
+if [ -d /run/media/$1/esp ]; then
+ cp -r /run/media/$1/esp/* /boot
+fi
+
# Copy kernel artifacts. To add more artifacts just add to types
# For now just support kernel types already being used by something in OE-core
for types in bzImage zImage vmlinux vmlinuz fitImage; do
diff --git a/meta/recipes-core/meta/buildtools-extended-tarball.bb b/meta/recipes-core/meta/buildtools-extended-tarball.bb
index 0816486754..83e3fddccc 100644
--- a/meta/recipes-core/meta/buildtools-extended-tarball.bb
+++ b/meta/recipes-core/meta/buildtools-extended-tarball.bb
@@ -28,11 +28,21 @@ TOOLCHAIN_HOST_TASK += "\
nativesdk-libtool \
nativesdk-pkgconfig \
nativesdk-glibc-utils \
+ nativesdk-glibc-gconv-ibm850 \
+ nativesdk-glibc-gconv-iso8859-1 \
+ nativesdk-glibc-gconv-utf-16 \
+ nativesdk-glibc-gconv-cp1250 \
+ nativesdk-glibc-gconv-cp1251 \
+ nativesdk-glibc-gconv-cp1252 \
+ nativesdk-glibc-gconv-euc-jp \
+ nativesdk-glibc-gconv-libjis \
nativesdk-libxcrypt-dev \
nativesdk-parted \
nativesdk-dosfstools \
nativesdk-gptfdisk \
"
+# gconv-cp1250, cp1251 and euc-jp needed for iconv to work in vim builds
+# also copied list from uninative
TOOLCHAIN_OUTPUTNAME = "${SDK_ARCH}-buildtools-extended-nativesdk-standalone-${DISTRO_VERSION}"
diff --git a/meta/recipes-core/meta/cve-update-db-native.bb b/meta/recipes-core/meta/cve-update-db-native.bb
index cf62e1e32c..b073936298 100644
--- a/meta/recipes-core/meta/cve-update-db-native.bb
+++ b/meta/recipes-core/meta/cve-update-db-native.bb
@@ -138,14 +138,24 @@ def parse_node_and_insert(c, node, cveId):
for cpe in node.get('cpe_match', ()):
if not cpe['vulnerable']:
return
- cpe23 = cpe['cpe23Uri'].split(':')
+ cpe23 = cpe.get('cpe23Uri')
+ if not cpe23:
+ return
+ cpe23 = cpe23.split(':')
+ if len(cpe23) < 6:
+ return
vendor = cpe23[3]
product = cpe23[4]
version = cpe23[5]
+ if cpe23[6] == '*' or cpe23[6] == '-':
+ version_suffix = ""
+ else:
+ version_suffix = "_" + cpe23[6]
+
if version != '*' and version != '-':
# Version is defined, this is a '=' match
- yield [cveId, vendor, product, version, '=', '', '']
+ yield [cveId, vendor, product, version + version_suffix, '=', '', '']
elif version == '-':
# no version information is available
yield [cveId, vendor, product, version, '', '', '']
diff --git a/meta/recipes-core/ncurses/ncurses.inc b/meta/recipes-core/ncurses/ncurses.inc
index fe4e8a5d6e..ef59bc3b0a 100644
--- a/meta/recipes-core/ncurses/ncurses.inc
+++ b/meta/recipes-core/ncurses/ncurses.inc
@@ -324,3 +324,8 @@ FILES_${PN}-terminfo-base = "\
RSUGGESTS_${PN}-libtinfo = "${PN}-terminfo"
RRECOMMENDS_${PN}-libtinfo = "${PN}-terminfo-base"
+
+# Putting terminfo into the sysroot adds around 2800 files to
+# each recipe specific sysroot. We can live without this, particularly
+# as many recipes may have native and target copies.
+SYSROOT_DIRS_remove = "${datadir}"
diff --git a/meta/recipes-core/ovmf/ovmf-shell-image.bb b/meta/recipes-core/ovmf/ovmf-shell-image.bb
index 0d2b8bf52f..fd4fb5b732 100644
--- a/meta/recipes-core/ovmf/ovmf-shell-image.bb
+++ b/meta/recipes-core/ovmf/ovmf-shell-image.bb
@@ -1,4 +1,5 @@
DESCRIPTION = "boot image with UEFI shell and tools"
+COMPATIBLE_HOST_class-target='(i.86|x86_64).*'
# For this image recipe, only the wic format with a
# single vfat partition makes sense. Because we have no
diff --git a/meta/recipes-core/systemd/systemd-boot_246.2.bb b/meta/recipes-core/systemd/systemd-boot_246.9.bb
index f92c639810..f92c639810 100644
--- a/meta/recipes-core/systemd/systemd-boot_246.2.bb
+++ b/meta/recipes-core/systemd/systemd-boot_246.9.bb
diff --git a/meta/recipes-core/systemd/systemd-conf/wired.network b/meta/recipes-core/systemd/systemd-conf/wired.network
index dcf3534596..06d00ea1ba 100644
--- a/meta/recipes-core/systemd/systemd-conf/wired.network
+++ b/meta/recipes-core/systemd/systemd-conf/wired.network
@@ -1,6 +1,7 @@
[Match]
Name=en* eth*
KernelCommandLine=!nfsroot
+KernelCommandLine=!ip
[Network]
DHCP=yes
diff --git a/meta/recipes-core/systemd/systemd-conf_246.1.bb b/meta/recipes-core/systemd/systemd-conf_246.9.bb
index d9ec023bfd..9b797a91f4 100644
--- a/meta/recipes-core/systemd/systemd-conf_246.1.bb
+++ b/meta/recipes-core/systemd/systemd-conf_246.9.bb
@@ -23,9 +23,6 @@ do_install() {
# Based on change from YP bug 8141, OE commit 5196d7bacaef1076c361adaa2867be31759c1b52
do_install_append_qemuall() {
install -D -m0644 ${WORKDIR}/system.conf-qemuall ${D}${systemd_unitdir}/system.conf.d/01-${PN}.conf
-
- # Do not install wired.network for qemu bsps
- rm -rf ${D}${systemd_unitdir}/network
}
PACKAGE_ARCH = "${MACHINE_ARCH}"
diff --git a/meta/recipes-core/systemd/systemd.inc b/meta/recipes-core/systemd/systemd.inc
index 1733565fc0..b0f8a72bbe 100644
--- a/meta/recipes-core/systemd/systemd.inc
+++ b/meta/recipes-core/systemd/systemd.inc
@@ -14,7 +14,7 @@ LICENSE = "GPLv2 & LGPLv2.1"
LIC_FILES_CHKSUM = "file://LICENSE.GPL2;md5=751419260aa954499f7abaabaa882bbe \
file://LICENSE.LGPL2.1;md5=4fbd65380cdd255951079008b364516c"
-SRCREV = "2ee1c57c4ff4fd3349cf03c2e89fbd18ca0b3a4a"
+SRCREV = "90f7f6c5777e9e2a4990f299474f730459054bf4"
SRCBRANCH = "v246-stable"
SRC_URI = "git://github.com/systemd/systemd-stable.git;protocol=git;branch=${SRCBRANCH}"
diff --git a/meta/recipes-core/systemd/systemd/0001-binfmt-Don-t-install-dependency-links-at-install-tim.patch b/meta/recipes-core/systemd/systemd/0001-binfmt-Don-t-install-dependency-links-at-install-tim.patch
index 2676c144f2..643b9547b7 100644
--- a/meta/recipes-core/systemd/systemd/0001-binfmt-Don-t-install-dependency-links-at-install-tim.patch
+++ b/meta/recipes-core/systemd/systemd/0001-binfmt-Don-t-install-dependency-links-at-install-tim.patch
@@ -1,4 +1,4 @@
-From 564830719be2017c4953589d50f21a9e856a4ecc Mon Sep 17 00:00:00 2001
+From ad5b89a366785d8a19ba970f5b0c97b4de848fa3 Mon Sep 17 00:00:00 2001
From: Chen Qi <Qi.Chen@windriver.com>
Date: Thu, 21 Feb 2019 16:23:24 +0800
Subject: [PATCH] binfmt: Don't install dependency links at install time for
@@ -18,17 +18,16 @@ Signed-off-by: Khem Raj <raj.khem@gmail.com>
Signed-off-by: Chen Qi <Qi.Chen@windriver.com>
[rebased for systemd 243]
Signed-off-by: Scott Murray <scott.murray@konsulko.com>
-
---
units/meson.build | 6 ++----
units/proc-sys-fs-binfmt_misc.automount | 3 +++
units/systemd-binfmt.service.in | 4 ++++
3 files changed, 9 insertions(+), 4 deletions(-)
-Index: systemd-stable/units/meson.build
-===================================================================
---- systemd-stable.orig/units/meson.build
-+++ systemd-stable/units/meson.build
+diff --git a/units/meson.build b/units/meson.build
+index 031237c..0d43bdb 100644
+--- a/units/meson.build
++++ b/units/meson.build
@@ -54,8 +54,7 @@ units = [
['poweroff.target', '',
(with_runlevels ? 'runlevel0.target' : '')],
@@ -38,8 +37,8 @@ Index: systemd-stable/units/meson.build
+ ['proc-sys-fs-binfmt_misc.automount', 'ENABLE_BINFMT'],
['proc-sys-fs-binfmt_misc.mount', 'ENABLE_BINFMT'],
['reboot.target', '',
- (with_runlevels ? 'runlevel6.target ctrl-alt-del.target' : 'ctrl-alt-del.target')],
-@@ -162,8 +161,7 @@ in_units = [
+ 'ctrl-alt-del.target' + (with_runlevels ? ' runlevel6.target' : '')],
+@@ -164,8 +163,7 @@ in_units = [
['rc-local.service', 'HAVE_SYSV_COMPAT'],
['rescue.service', ''],
['systemd-backlight@.service', 'ENABLE_BACKLIGHT'],
@@ -49,10 +48,10 @@ Index: systemd-stable/units/meson.build
['systemd-bless-boot.service', 'ENABLE_EFI HAVE_BLKID'],
['systemd-boot-check-no-failures.service', ''],
['systemd-coredump@.service', 'ENABLE_COREDUMP'],
-Index: systemd-stable/units/proc-sys-fs-binfmt_misc.automount
-===================================================================
---- systemd-stable.orig/units/proc-sys-fs-binfmt_misc.automount
-+++ systemd-stable/units/proc-sys-fs-binfmt_misc.automount
+diff --git a/units/proc-sys-fs-binfmt_misc.automount b/units/proc-sys-fs-binfmt_misc.automount
+index 30a6bc9..4231f3b 100644
+--- a/units/proc-sys-fs-binfmt_misc.automount
++++ b/units/proc-sys-fs-binfmt_misc.automount
@@ -18,3 +18,6 @@ ConditionPathIsReadWrite=/proc/sys/
[Automount]
@@ -60,11 +59,11 @@ Index: systemd-stable/units/proc-sys-fs-binfmt_misc.automount
+
+[Install]
+WantedBy=sysinit.target
-Index: systemd-stable/units/systemd-binfmt.service.in
-===================================================================
---- systemd-stable.orig/units/systemd-binfmt.service.in
-+++ systemd-stable/units/systemd-binfmt.service.in
-@@ -14,6 +14,7 @@ Documentation=https://www.kernel.org/doc
+diff --git a/units/systemd-binfmt.service.in b/units/systemd-binfmt.service.in
+index e54e95e..372a598 100644
+--- a/units/systemd-binfmt.service.in
++++ b/units/systemd-binfmt.service.in
+@@ -14,6 +14,7 @@ Documentation=https://www.kernel.org/doc/html/latest/admin-guide/binfmt-misc.htm
Documentation=https://www.freedesktop.org/wiki/Software/systemd/APIFileSystems
DefaultDependencies=no
Conflicts=shutdown.target
@@ -79,3 +78,6 @@ Index: systemd-stable/units/systemd-binfmt.service.in
+
+[Install]
+WantedBy=sysinit.target
+--
+2.7.4
+
diff --git a/meta/recipes-core/systemd/systemd/0001-logind-Restore-chvt-as-non-root-user-without-polkit.patch b/meta/recipes-core/systemd/systemd/0001-logind-Restore-chvt-as-non-root-user-without-polkit.patch
new file mode 100644
index 0000000000..89ef39bc3e
--- /dev/null
+++ b/meta/recipes-core/systemd/systemd/0001-logind-Restore-chvt-as-non-root-user-without-polkit.patch
@@ -0,0 +1,227 @@
+From 150d9cade6d475570395cb418b824524dead9577 Mon Sep 17 00:00:00 2001
+From: Joshua Watt <JPEWhacker@gmail.com>
+Date: Fri, 30 Oct 2020 08:15:43 -0500
+Subject: [PATCH] logind: Restore chvt as non-root user without polkit
+
+4acf0cfd2f ("logind: check PolicyKit before allowing VT switch") broke
+the ability to write user sessions that run graphical sessions (e.g.
+weston/X11). This was partially amended in 19bb87fbfa ("login: allow
+non-console sessions to change vt") by changing the default PolicyKit
+policy so that non-root users are again allowed to switch the VT. This
+makes the policy when PolKit is not enabled (as on many embedded
+systems) match the default PolKit policy and allows launching graphical
+sessions as a non-root user.
+
+Closes #17473
+---
+ src/login/logind-dbus.c | 11 ++-------
+ src/login/logind-polkit.c | 26 +++++++++++++++++++++
+ src/login/logind-polkit.h | 10 ++++++++
+ src/login/logind-seat-dbus.c | 41 ++++-----------------------------
+ src/login/logind-session-dbus.c | 11 ++-------
+ src/login/meson.build | 1 +
+ 6 files changed, 46 insertions(+), 54 deletions(-)
+ create mode 100644 src/login/logind-polkit.c
+ create mode 100644 src/login/logind-polkit.h
+
+diff --git a/src/login/logind-dbus.c b/src/login/logind-dbus.c
+index 0f83ed99bc..a3765d88ba 100644
+--- a/src/login/logind-dbus.c
++++ b/src/login/logind-dbus.c
+@@ -30,6 +30,7 @@
+ #include "format-util.h"
+ #include "fs-util.h"
+ #include "logind-dbus.h"
++#include "logind-polkit.h"
+ #include "logind-seat-dbus.h"
+ #include "logind-session-dbus.h"
+ #include "logind-user-dbus.h"
+@@ -1047,15 +1048,7 @@ static int method_activate_session_on_seat(sd_bus_message *message, void *userda
+ return sd_bus_error_setf(error, BUS_ERROR_SESSION_NOT_ON_SEAT,
+ "Session %s not on seat %s", session_name, seat_name);
+
+- r = bus_verify_polkit_async(
+- message,
+- CAP_SYS_ADMIN,
+- "org.freedesktop.login1.chvt",
+- NULL,
+- false,
+- UID_INVALID,
+- &m->polkit_registry,
+- error);
++ r = check_polkit_chvt(message, m, error);
+ if (r < 0)
+ return r;
+ if (r == 0)
+diff --git a/src/login/logind-polkit.c b/src/login/logind-polkit.c
+new file mode 100644
+index 0000000000..9072570cc6
+--- /dev/null
++++ b/src/login/logind-polkit.c
+@@ -0,0 +1,26 @@
++/* SPDX-License-Identifier: LGPL-2.1+ */
++
++#include "bus-polkit.h"
++#include "logind-polkit.h"
++#include "missing_capability.h"
++#include "user-util.h"
++
++int check_polkit_chvt(sd_bus_message *message, Manager *manager, sd_bus_error *error) {
++#if ENABLE_POLKIT
++ return bus_verify_polkit_async(
++ message,
++ CAP_SYS_ADMIN,
++ "org.freedesktop.login1.chvt",
++ NULL,
++ false,
++ UID_INVALID,
++ &manager->polkit_registry,
++ error);
++#else
++ /* Allow chvt when polkit is not present. This allows a service to start a graphical session as a
++ * non-root user when polkit is not compiled in, matching the default polkit policy */
++ return 1;
++#endif
++}
++
++
+diff --git a/src/login/logind-polkit.h b/src/login/logind-polkit.h
+new file mode 100644
+index 0000000000..476c077a8a
+--- /dev/null
++++ b/src/login/logind-polkit.h
+@@ -0,0 +1,10 @@
++/* SPDX-License-Identifier: LGPL-2.1+ */
++#pragma once
++
++#include "sd-bus.h"
++
++#include "bus-object.h"
++#include "logind.h"
++
++int check_polkit_chvt(sd_bus_message *message, Manager *manager, sd_bus_error *error);
++
+diff --git a/src/login/logind-seat-dbus.c b/src/login/logind-seat-dbus.c
+index a945132284..f22e9e2734 100644
+--- a/src/login/logind-seat-dbus.c
++++ b/src/login/logind-seat-dbus.c
+@@ -9,6 +9,7 @@
+ #include "bus-polkit.h"
+ #include "bus-util.h"
+ #include "logind-dbus.h"
++#include "logind-polkit.h"
+ #include "logind-seat-dbus.h"
+ #include "logind-seat.h"
+ #include "logind-session-dbus.h"
+@@ -179,15 +180,7 @@ static int method_activate_session(sd_bus_message *message, void *userdata, sd_b
+ if (session->seat != s)
+ return sd_bus_error_setf(error, BUS_ERROR_SESSION_NOT_ON_SEAT, "Session %s not on seat %s", name, s->id);
+
+- r = bus_verify_polkit_async(
+- message,
+- CAP_SYS_ADMIN,
+- "org.freedesktop.login1.chvt",
+- NULL,
+- false,
+- UID_INVALID,
+- &s->manager->polkit_registry,
+- error);
++ r = check_polkit_chvt(message, s->manager, error);
+ if (r < 0)
+ return r;
+ if (r == 0)
+@@ -215,15 +208,7 @@ static int method_switch_to(sd_bus_message *message, void *userdata, sd_bus_erro
+ if (to <= 0)
+ return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid virtual terminal");
+
+- r = bus_verify_polkit_async(
+- message,
+- CAP_SYS_ADMIN,
+- "org.freedesktop.login1.chvt",
+- NULL,
+- false,
+- UID_INVALID,
+- &s->manager->polkit_registry,
+- error);
++ r = check_polkit_chvt(message, s->manager, error);
+ if (r < 0)
+ return r;
+ if (r == 0)
+@@ -243,15 +228,7 @@ static int method_switch_to_next(sd_bus_message *message, void *userdata, sd_bus
+ assert(message);
+ assert(s);
+
+- r = bus_verify_polkit_async(
+- message,
+- CAP_SYS_ADMIN,
+- "org.freedesktop.login1.chvt",
+- NULL,
+- false,
+- UID_INVALID,
+- &s->manager->polkit_registry,
+- error);
++ r = check_polkit_chvt(message, s->manager, error);
+ if (r < 0)
+ return r;
+ if (r == 0)
+@@ -271,15 +248,7 @@ static int method_switch_to_previous(sd_bus_message *message, void *userdata, sd
+ assert(message);
+ assert(s);
+
+- r = bus_verify_polkit_async(
+- message,
+- CAP_SYS_ADMIN,
+- "org.freedesktop.login1.chvt",
+- NULL,
+- false,
+- UID_INVALID,
+- &s->manager->polkit_registry,
+- error);
++ r = check_polkit_chvt(message, s->manager, error);
+ if (r < 0)
+ return r;
+ if (r == 0)
+diff --git a/src/login/logind-session-dbus.c b/src/login/logind-session-dbus.c
+index ccc5ac8df2..57c8a4e900 100644
+--- a/src/login/logind-session-dbus.c
++++ b/src/login/logind-session-dbus.c
+@@ -11,6 +11,7 @@
+ #include "fd-util.h"
+ #include "logind-brightness.h"
+ #include "logind-dbus.h"
++#include "logind-polkit.h"
+ #include "logind-seat-dbus.h"
+ #include "logind-session-dbus.h"
+ #include "logind-session-device.h"
+@@ -192,15 +193,7 @@ int bus_session_method_activate(sd_bus_message *message, void *userdata, sd_bus_
+ assert(message);
+ assert(s);
+
+- r = bus_verify_polkit_async(
+- message,
+- CAP_SYS_ADMIN,
+- "org.freedesktop.login1.chvt",
+- NULL,
+- false,
+- UID_INVALID,
+- &s->manager->polkit_registry,
+- error);
++ r = check_polkit_chvt(message, s->manager, error);
+ if (r < 0)
+ return r;
+ if (r == 0)
+diff --git a/src/login/meson.build b/src/login/meson.build
+index 0a7d3d5440..7e46be2add 100644
+--- a/src/login/meson.build
++++ b/src/login/meson.build
+@@ -26,6 +26,7 @@ liblogind_core_sources = files('''
+ logind-device.h
+ logind-inhibit.c
+ logind-inhibit.h
++ logind-polkit.c
+ logind-seat-dbus.c
+ logind-seat-dbus.h
+ logind-seat.c
+--
+2.28.0
+
diff --git a/meta/recipes-core/systemd/systemd/0002-don-t-use-glibc-specific-qsort_r.patch b/meta/recipes-core/systemd/systemd/0002-don-t-use-glibc-specific-qsort_r.patch
index 30fe9a14df..3be5095f07 100644
--- a/meta/recipes-core/systemd/systemd/0002-don-t-use-glibc-specific-qsort_r.patch
+++ b/meta/recipes-core/systemd/systemd/0002-don-t-use-glibc-specific-qsort_r.patch
@@ -1,4 +1,4 @@
-From 3eb12a6ba0bce149717eaabeb1505d379b3d705a Mon Sep 17 00:00:00 2001
+From 263e4100a849f28f62fcfcc1456e9e6de8ee836b Mon Sep 17 00:00:00 2001
From: Chen Qi <Qi.Chen@windriver.com>
Date: Mon, 25 Feb 2019 13:41:41 +0800
Subject: [PATCH] don't use glibc-specific qsort_r
@@ -12,16 +12,16 @@ Signed-off-by: Chen Qi <Qi.Chen@windriver.com>
Signed-off-by: Andrej Valek <andrej.valek@siemens.com>
---
- src/basic/sort-util.h | 14 ------------
- src/libsystemd/sd-hwdb/hwdb-util.c | 19 +++++++++++-----
- src/shared/format-table.c | 36 ++++++++++++++++++++----------
+ src/basic/sort-util.h | 14 --------------
+ src/libsystemd/sd-hwdb/hwdb-util.c | 19 ++++++++++++++-----
+ src/shared/format-table.c | 36 ++++++++++++++++++++++++------------
3 files changed, 38 insertions(+), 31 deletions(-)
-Index: systemd-stable/src/basic/sort-util.h
-===================================================================
---- systemd-stable.orig/src/basic/sort-util.h
-+++ systemd-stable/src/basic/sort-util.h
-@@ -54,17 +54,3 @@ static inline void _qsort_safe(void *bas
+diff --git a/src/basic/sort-util.h b/src/basic/sort-util.h
+index a8dc3bb..9541061 100644
+--- a/src/basic/sort-util.h
++++ b/src/basic/sort-util.h
+@@ -54,17 +54,3 @@ static inline void _qsort_safe(void *base, size_t nmemb, size_t size, __compar_f
int (*_func_)(const typeof(p[0])*, const typeof(p[0])*) = func; \
_qsort_safe((p), (n), sizeof((p)[0]), (__compar_fn_t) _func_); \
})
@@ -39,11 +39,11 @@ Index: systemd-stable/src/basic/sort-util.h
- int (*_func_)(const typeof(p[0])*, const typeof(p[0])*, typeof(userdata)) = func; \
- qsort_r_safe((p), (n), sizeof((p)[0]), (__compar_d_fn_t) _func_, userdata); \
- })
-Index: systemd-stable/src/libsystemd/sd-hwdb/hwdb-util.c
-===================================================================
---- systemd-stable.orig/src/libsystemd/sd-hwdb/hwdb-util.c
-+++ systemd-stable/src/libsystemd/sd-hwdb/hwdb-util.c
-@@ -128,9 +128,13 @@ static void trie_free(struct trie *trie)
+diff --git a/src/libsystemd/sd-hwdb/hwdb-util.c b/src/libsystemd/sd-hwdb/hwdb-util.c
+index 5c75216..3986fc8 100644
+--- a/src/libsystemd/sd-hwdb/hwdb-util.c
++++ b/src/libsystemd/sd-hwdb/hwdb-util.c
+@@ -128,9 +128,13 @@ static void trie_free(struct trie *trie) {
DEFINE_TRIVIAL_CLEANUP_FUNC(struct trie*, trie_free);
@@ -60,7 +60,7 @@ Index: systemd-stable/src/libsystemd/sd-hwdb/hwdb-util.c
}
static int trie_node_add_value(struct trie *trie, struct trie_node *node,
-@@ -158,7 +162,10 @@ static int trie_node_add_value(struct tr
+@@ -158,7 +162,10 @@ static int trie_node_add_value(struct trie *trie, struct trie_node *node,
.value_off = v,
};
@@ -72,7 +72,7 @@ Index: systemd-stable/src/libsystemd/sd-hwdb/hwdb-util.c
if (val) {
/* At this point we have 2 identical properties on the same match-string.
* Since we process files in order, we just replace the previous value. */
-@@ -184,7 +191,9 @@ static int trie_node_add_value(struct tr
+@@ -184,7 +191,9 @@ static int trie_node_add_value(struct trie *trie, struct trie_node *node,
.line_number = line_number,
};
node->values_count++;
@@ -83,11 +83,11 @@ Index: systemd-stable/src/libsystemd/sd-hwdb/hwdb-util.c
return 0;
}
-Index: systemd-stable/src/shared/format-table.c
-===================================================================
---- systemd-stable.orig/src/shared/format-table.c
-+++ systemd-stable/src/shared/format-table.c
-@@ -1246,31 +1246,33 @@ static int cell_data_compare(TableData *
+diff --git a/src/shared/format-table.c b/src/shared/format-table.c
+index 612402c..04638b2 100644
+--- a/src/shared/format-table.c
++++ b/src/shared/format-table.c
+@@ -1243,30 +1243,32 @@ static int cell_data_compare(TableData *a, size_t index_a, TableData *b, size_t
return CMP(index_a, index_b);
}
@@ -95,7 +95,6 @@ Index: systemd-stable/src/shared/format-table.c
+static Table *user_table;
+static int table_data_compare(const void *x, const void *y) {
+ const size_t *a = x, *b=y;
- size_t i;
int r;
- assert(t);
@@ -115,8 +114,8 @@ Index: systemd-stable/src/shared/format-table.c
return 1;
/* Order other lines by the sorting map */
-- for (i = 0; i < t->n_sort_map; i++) {
-+ for (i = 0; i < user_table->n_sort_map; i++) {
+- for (size_t i = 0; i < t->n_sort_map; i++) {
++ for (size_t i = 0; i < user_table->n_sort_map; i++) {
TableData *d, *dd;
- d = t->data[*a + t->sort_map[i]];
@@ -131,8 +130,8 @@ Index: systemd-stable/src/shared/format-table.c
}
/* Order identical lines by the order there were originally added in */
-@@ -1798,7 +1800,12 @@ int table_print(Table *t, FILE *f) {
- for (i = 0; i < n_rows; i++)
+@@ -1844,7 +1846,12 @@ int table_print(Table *t, FILE *f) {
+ for (size_t i = 0; i < n_rows; i++)
sorted[i] = i * t->n_columns;
- typesafe_qsort_r(sorted, n_rows, table_data_compare, t);
@@ -145,8 +144,8 @@ Index: systemd-stable/src/shared/format-table.c
}
if (t->display_map)
-@@ -2375,7 +2382,12 @@ int table_to_json(Table *t, JsonVariant
- for (i = 0; i < n_rows; i++)
+@@ -2440,7 +2447,12 @@ int table_to_json(Table *t, JsonVariant **ret) {
+ for (size_t i = 0; i < n_rows; i++)
sorted[i] = i * t->n_columns;
- typesafe_qsort_r(sorted, n_rows, table_data_compare, t);
diff --git a/meta/recipes-core/systemd/systemd_246.6.bb b/meta/recipes-core/systemd/systemd_246.9.bb
index 9215adf8dc..6524b8216a 100644
--- a/meta/recipes-core/systemd/systemd_246.6.bb
+++ b/meta/recipes-core/systemd/systemd_246.9.bb
@@ -21,6 +21,7 @@ SRC_URI += "file://touchscreen.rules \
file://0001-binfmt-Don-t-install-dependency-links-at-install-tim.patch \
file://0003-implment-systemd-sysv-install-for-OE.patch \
file://0001-systemd.pc.in-use-ROOTPREFIX-without-suffixed-slash.patch \
+ file://0001-logind-Restore-chvt-as-non-root-user-without-polkit.patch \
"
# patches needed by musl
@@ -134,7 +135,7 @@ PACKAGECONFIG[hibernate] = "-Dhibernate=true,-Dhibernate=false"
PACKAGECONFIG[hostnamed] = "-Dhostnamed=true,-Dhostnamed=false"
PACKAGECONFIG[idn] = "-Didn=true,-Didn=false"
PACKAGECONFIG[ima] = "-Dima=true,-Dima=false"
-# importd requires curl/xz/zlib/bzip2/gcrypt
+# importd requires journal-upload/xz/zlib/bzip2/gcrypt
PACKAGECONFIG[importd] = "-Dimportd=true,-Dimportd=false"
# Update NAT firewall rules
PACKAGECONFIG[iptc] = "-Dlibiptc=true,-Dlibiptc=false,iptables"
@@ -357,15 +358,15 @@ USERADD_PACKAGES = "${PN} ${PN}-extra-utils \
${@bb.utils.contains('PACKAGECONFIG', 'journal-upload', '${PN}-journal-upload', '', d)} \
"
GROUPADD_PARAM_${PN} = "-r systemd-journal"
-USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'coredump', '--system -d / -M --shell /bin/nologin systemd-coredump;', '', d)}"
-USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'networkd', '--system -d / -M --shell /bin/nologin systemd-network;', '', d)}"
+USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'coredump', '--system -d / -M --shell /sbin/nologin systemd-coredump;', '', d)}"
+USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'networkd', '--system -d / -M --shell /sbin/nologin systemd-network;', '', d)}"
USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'polkit', '--system --no-create-home --user-group --home-dir ${sysconfdir}/polkit-1 polkitd;', '', d)}"
-USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'resolved', '--system -d / -M --shell /bin/nologin systemd-resolve;', '', d)}"
-USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'timesyncd', '--system -d / -M --shell /bin/nologin systemd-timesync;', '', d)}"
-USERADD_PARAM_${PN}-extra-utils = "--system -d / -M --shell /bin/nologin systemd-bus-proxy"
-USERADD_PARAM_${PN}-journal-gateway = "--system -d / -M --shell /bin/nologin systemd-journal-gateway"
-USERADD_PARAM_${PN}-journal-remote = "--system -d / -M --shell /bin/nologin systemd-journal-remote"
-USERADD_PARAM_${PN}-journal-upload = "--system -d / -M --shell /bin/nologin systemd-journal-upload"
+USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'resolved', '--system -d / -M --shell /sbin/nologin systemd-resolve;', '', d)}"
+USERADD_PARAM_${PN} += "${@bb.utils.contains('PACKAGECONFIG', 'timesyncd', '--system -d / -M --shell /sbin/nologin systemd-timesync;', '', d)}"
+USERADD_PARAM_${PN}-extra-utils = "--system -d / -M --shell /sbin/nologin systemd-bus-proxy"
+USERADD_PARAM_${PN}-journal-gateway = "--system -d / -M --shell /sbin/nologin systemd-journal-gateway"
+USERADD_PARAM_${PN}-journal-remote = "--system -d / -M --shell /sbin/nologin systemd-journal-remote"
+USERADD_PARAM_${PN}-journal-upload = "--system -d / -M --shell /sbin/nologin systemd-journal-upload"
FILES_${PN}-analyze = "${bindir}/systemd-analyze"