summaryrefslogtreecommitdiff
path: root/sound/firewire
diff options
context:
space:
mode:
authorTakashi Sakamoto <o-takashi@sakamocchi.jp>2023-02-02 22:37:08 +0900
committerTakashi Iwai <tiwai@suse.de>2023-02-04 09:35:17 +0100
commit0d9eb7ed958a71296c6829869f6304ddfdca64df (patch)
tree4d0edf9c83d12e2636af697b0ba85863f06a1daa /sound/firewire
parentd045bceff5a904bd79d71dede9f927c00ce4906f (diff)
ALSA: fireface: add field for the number of messages copied to user space
Current structure includes no field to express the number of messages copied to user space, thus user space application needs to information out of the structure to parse the content of structure. This commit adds a field to express the number of messages copied to user space since It is more preferable to use self-contained structure. Kees Cook proposed an idea of annotation for bound of flexible arrays in his future improvement for flexible-length array in kernel. The additional field for message count is suitable to the idea as well. Reference: https://people.kernel.org/kees/bounded-flexible-arrays-in-c Signed-off-by: Takashi Sakamoto <o-takashi@sakamocchi.jp> Link: https://lore.kernel.org/r/20230202133708.163936-1-o-takashi@sakamocchi.jp Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'sound/firewire')
-rw-r--r--sound/firewire/fireface/ff-protocol-former.c28
1 files changed, 16 insertions, 12 deletions
diff --git a/sound/firewire/fireface/ff-protocol-former.c b/sound/firewire/fireface/ff-protocol-former.c
index fa41de978756..efd59e9d9935 100644
--- a/sound/firewire/fireface/ff-protocol-former.c
+++ b/sound/firewire/fireface/ff-protocol-former.c
@@ -677,23 +677,19 @@ static void ff400_handle_msg(struct snd_ff *ff, unsigned int offset, const __le3
static long ff400_copy_msg_to_user(struct snd_ff *ff, char __user *buf, long count)
{
+ struct snd_firewire_event_ff400_message ev = {
+ .type = SNDRV_FIREWIRE_EVENT_FF400_MESSAGE,
+ .message_count = 0,
+ };
struct ff400_msg_parser *parser = ff->msg_parser;
- u32 type = SNDRV_FIREWIRE_EVENT_FF400_MESSAGE;
long consumed = 0;
- int ret = 0;
+ long ret = 0;
- if (count < 8)
+ if (count < sizeof(ev) || parser->pull_pos == parser->push_pos)
return 0;
- spin_unlock_irq(&ff->lock);
- if (copy_to_user(buf, &type, sizeof(type)))
- ret = -EFAULT;
- spin_lock_irq(&ff->lock);
- if (ret)
- return ret;
-
- count -= sizeof(type);
- consumed += sizeof(type);
+ count -= sizeof(ev);
+ consumed += sizeof(ev);
while (count >= sizeof(*parser->msgs) && parser->pull_pos != parser->push_pos) {
spin_unlock_irq(&ff->lock);
@@ -707,10 +703,18 @@ static long ff400_copy_msg_to_user(struct snd_ff *ff, char __user *buf, long cou
++parser->pull_pos;
if (parser->pull_pos >= FF400_QUEUE_SIZE)
parser->pull_pos = 0;
+ ++ev.message_count;
count -= sizeof(*parser->msgs);
consumed += sizeof(*parser->msgs);
}
+ spin_unlock_irq(&ff->lock);
+ if (copy_to_user(buf, &ev, sizeof(ev)))
+ ret = -EFAULT;
+ spin_lock_irq(&ff->lock);
+ if (ret)
+ return ret;
+
return consumed;
}