The new framing mode causes the user space regression, because the alsa-lib code does not initialize the reserved space in the params structure when the device is opened. This change adds SNDRV_RAWMIDI_IOCTL_USER_PVERSION like we do for the PCM interface for the protocol acknowledgment.
Unified · Split
| @@ -98,6 +98,7 @@ struct snd_rawmidi_file { · 97 unmodified lines | ||
| 98 | 98 | struct snd_rawmidi *rmidi; |
| 99 | 99 | struct snd_rawmidi_substream *input; |
| 100 | 100 | struct snd_rawmidi_substream *output; |
| 101 | + unsigned int user_pversion; /* supported protocol version */ | |
| 101 | 102 | }; |
| 102 | 103 | |
| 103 | 104 | struct snd_rawmidi_str { |
| @@ -784,6 +784,7 @@ struct snd_rawmidi_status { · 783 unmodified lines | ||
| 784 | 784 | |
| 785 | 785 | #define SNDRV_RAWMIDI_IOCTL_PVERSION _IOR('W', 0x00, int) |
| 786 | 786 | #define SNDRV_RAWMIDI_IOCTL_INFO _IOR('W', 0x01, struct snd_rawmidi_info) |
| 787 | +#define SNDRV_RAWMIDI_IOCTL_USER_PVERSION _IOW('W', 0x02, int) | |
| 787 | 788 | #define SNDRV_RAWMIDI_IOCTL_PARAMS _IOWR('W', 0x10, struct snd_rawmidi_params) |
| 788 | 789 | #define SNDRV_RAWMIDI_IOCTL_STATUS _IOWR('W', 0x20, struct snd_rawmidi_status) |
| 789 | 790 | #define SNDRV_RAWMIDI_IOCTL_DROP _IOW('W', 0x30, int) |
| @@ -873,12 +873,21 @@ static long snd_rawmidi_ioctl(struct file *file, unsigned int cmd, unsigned long · 872 unmodified lines | ||
| 873 | 873 | return -EINVAL; |
| 874 | 874 | } |
| 875 | 875 | } |
| 876 | + case SNDRV_RAWMIDI_IOCTL_USER_PVERSION: | |
| 877 | + if (get_user(rfile->user_pversion, (unsigned int __user *)arg)) | |
| 878 | + return -EFAULT; | |
| 879 | + return 0; | |
| 880 | + | |
| 876 | 881 | case SNDRV_RAWMIDI_IOCTL_PARAMS: |
| 877 | 882 | { |
| 878 | 883 | struct snd_rawmidi_params params; |
| 879 | 884 | |
| 880 | 885 | if (copy_from_user(¶ms, argp, sizeof(struct snd_rawmidi_params))) |
| 881 | 886 | return -EFAULT; |
| 887 | + if (rfile->user_pversion < SNDRV_PROTOCOL_VERSION(2, 0, 2)) { | |
| 888 | + params.mode = 0; | |
| 889 | + memset(params.reserved, 0, sizeof(params.reserved)); | |
| 890 | + } | |
| 882 | 891 | switch (params.stream) { |
| 883 | 892 | case SNDRV_RAWMIDI_STREAM_OUTPUT: |
| 884 | 893 | if (rfile->output == NULL) |