The staged virtio-snd capture path needs to sample stop_threshold from
completion context to distinguish free-running capture from bounded
capture. Software parameters can update this field while capture runs.

Mark the runtime stop-threshold assignments with WRITE_ONCE and the proc
status read with READ_ONCE. This pairs the assignments with the driver's
READ_ONCE policy sampling in the following patch.

These annotations do not provide a transaction for the entire sw_params
update. The driver serializes its cached policy and accounting with its
own substream lock.

Assisted-by: LLM
Signed-off-by: Joonho Lee <[email protected]>

---
diff --git a/sound/core/oss/pcm_oss.c b/sound/core/oss/pcm_oss.c
--- a/sound/core/oss/pcm_oss.c
+++ b/sound/core/oss/pcm_oss.c
@@ -2958,7 +2958,7 @@
               runtime->oss.mmap_bytes);
 #endif
        /* In mmap mode we never stop */
-       runtime->stop_threshold = runtime->boundary;
+       WRITE_ONCE(runtime->stop_threshold, runtime->boundary);
 
        return 0;
 }
diff --git a/sound/core/pcm.c b/sound/core/pcm.c
--- a/sound/core/pcm.c
+++ b/sound/core/pcm.c
@@ -422,7 +422,8 @@
        snd_iprintf(buffer, "period_step: %u\n", runtime->period_step);
        snd_iprintf(buffer, "avail_min: %lu\n", runtime->control->avail_min);
        snd_iprintf(buffer, "start_threshold: %lu\n", runtime->start_threshold);
-       snd_iprintf(buffer, "stop_threshold: %lu\n", runtime->stop_threshold);
+       snd_iprintf(buffer, "stop_threshold: %lu\n",
+                   READ_ONCE(runtime->stop_threshold));
        snd_iprintf(buffer, "silence_threshold: %lu\n", 
runtime->silence_threshold);
        snd_iprintf(buffer, "silence_size: %lu\n", runtime->silence_size);
        snd_iprintf(buffer, "boundary: %lu\n", runtime->boundary);
diff --git a/sound/core/pcm_native.c b/sound/core/pcm_native.c
--- a/sound/core/pcm_native.c
+++ b/sound/core/pcm_native.c
@@ -871,7 +871,7 @@
        runtime->period_step = 1;
        runtime->control->avail_min = runtime->period_size;
        runtime->start_threshold = 1;
-       runtime->stop_threshold = runtime->buffer_size;
+       WRITE_ONCE(runtime->stop_threshold, runtime->buffer_size);
        runtime->silence_threshold = 0;
        runtime->silence_size = 0;
        runtime->boundary = runtime->buffer_size;
@@ -1062,7 +1062,8 @@
                runtime->period_step = params->period_step;
                runtime->control->avail_min = params->avail_min;
                runtime->start_threshold = params->start_threshold;
-               runtime->stop_threshold = params->stop_threshold;
+               /* Drivers may sample the stop policy from completion context. 
*/
+               WRITE_ONCE(runtime->stop_threshold, params->stop_threshold);
                runtime->silence_threshold = params->silence_threshold;
                runtime->silence_size = params->silence_size;
                params->boundary = runtime->boundary;


Reply via email to