From 9d3e19c192b97b4c4c0abcafdbf1edb1e56cee88 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Wed, 7 Oct 2026 19:25:19 +0200 Subject: [PATCH] ALSA: seq: Fix missing direction and ump_group handling in 32bit compat ioctl I forgot to cover the two new fields, direction and ump_group, in struct snd_seq_port_info for the 32bit compat ioctls of SNDRV_SEQ_IOCTL_GET_PORT_INFO & co, which ended up with the garbage copies in those fields. Add the handling of those two fields in the compat layer. Also, avoid over-copying the 64bit snd_seq_port_info but only the first part (before the field kernel); this avoids the copy of kernel-space garbage value in the reserved field. Fixes: ff166a9d19fa ("ALSA: seq: Add port direction to snd_seq_port_info") Reported-by: Sashiko Signed-off-by: Takashi Iwai Link: https://patch.msgid.link/20261007172533.14667-2-tiwai@suse.de --- sound/core/seq/seq_compat.c | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/sound/core/seq/seq_compat.c b/sound/core/seq/seq_compat.c index 80110501da6f..57aaa39afb9d 100644 --- a/sound/core/seq/seq_compat.c +++ b/sound/core/seq/seq_compat.c @@ -25,7 +25,9 @@ struct snd_seq_port_info32 { u32 kernel; /* reserved for kernel use (must be NULL) */ u32 flags; /* misc. conditioning */ unsigned char time_queue; /* queue # for timestamping */ - char reserved[59]; /* for future use */ + unsigned char direction; /* port usage direction (r/w/bidir) */ + unsigned char ump_group; /* 0 = UMP EP (no conversion), 1-16 = UMP group number */ + char reserved[57]; /* for future use */ }; static int snd_seq_call_port_info_ioctl(struct snd_seq_client *client, unsigned int cmd, @@ -40,7 +42,9 @@ static int snd_seq_call_port_info_ioctl(struct snd_seq_client *client, unsigned if (copy_from_user(data, data32, sizeof(*data32)) || get_user(data->flags, &data32->flags) || - get_user(data->time_queue, &data32->time_queue)) + get_user(data->time_queue, &data32->time_queue) || + get_user(data->direction, &data32->direction) || + get_user(data->ump_group, &data32->ump_group)) return -EFAULT; data->kernel = NULL; @@ -50,9 +54,12 @@ static int snd_seq_call_port_info_ioctl(struct snd_seq_client *client, unsigned if (err < 0) return err; - if (copy_to_user(data32, data, sizeof(*data32)) || + if (copy_to_user(data32, data, + offsetof(struct snd_seq_port_info32, kernel)) || put_user(data->flags, &data32->flags) || - put_user(data->time_queue, &data32->time_queue)) + put_user(data->time_queue, &data32->time_queue) || + put_user(data->direction, &data32->direction) || + put_user(data->ump_group, &data32->ump_group)) return -EFAULT; return err;