Commit 9ed01da70161d3650e6e5bb557a565c7b2ba9f9e

Frank Praznik 2021-03-02T09:47:47

audio: pipewire: Constify and clarify period size calculations Constify the min/max period variables, use a #define for the base clock rate used in the calculations and note that changing the upper limit can have dire side effects as it's a hard limit in Pipewire.

diff --git a/src/audio/pipewire/SDL_pipewire.c b/src/audio/pipewire/SDL_pipewire.c
index 9d26650..1f298da 100644
--- a/src/audio/pipewire/SDL_pipewire.c
+++ b/src/audio/pipewire/SDL_pipewire.c
@@ -34,9 +34,13 @@
 /*
  * These seem to be sane limits as Pipewire
  * uses them in several of it's own modules.
+ *
+ * NOTE: 8192 is a hard upper limit in Pipewire and
+ * increasing this value can lead to buffer overflows.
  */
-#define PW_MIN_SAMPLES 32   /* About 0.67ms at 48kHz */
-#define PW_MAX_SAMPLES 8192 /* About 170.6ms at 48kHz */
+#define PW_MIN_SAMPLES     32   /* About 0.67ms at 48kHz */
+#define PW_MAX_SAMPLES     8192 /* About 170.6ms at 48kHz */
+#define PW_BASE_CLOCK_RATE 48000
 
 #define PW_POD_BUFFER_LENGTH         1024
 #define PW_THREAD_NAME_BUFFER_LENGTH 128
@@ -1009,10 +1013,13 @@ PIPEWIRE_OpenDevice(_THIS, void *handle, const char *devname, int iscapture)
     struct pw_properties *       props;
     const char *                 stream_name, *stream_role;
     const Uint32                 node_id = this->handle == NULL ? PW_ID_ANY : PW_HANDLE_TO_ID(this->handle);
-    int                          min_period, adjusted_samples;
     enum pw_stream_state         state;
     int                          res;
 
+    /* Clamp the period size to sane values */
+    const int min_period       = PW_MIN_SAMPLES * SPA_MAX(this->spec.freq / PW_BASE_CLOCK_RATE, 1);
+    const int adjusted_samples = SPA_CLAMP(this->spec.samples, min_period, PW_MAX_SAMPLES);
+
     /* Get the hints for the stream name and role */
     stream_name = SDL_GetHint(SDL_HINT_AUDIO_DEVICE_STREAM_NAME);
     if (!stream_name || *stream_name == '\0') {
@@ -1035,10 +1042,6 @@ PIPEWIRE_OpenDevice(_THIS, void *handle, const char *devname, int iscapture)
         return SDL_SetError("Pipewire: Failed to set audio format parameters");
     }
 
-    /* Clamp the sample count to sane values */
-    min_period       = PW_MIN_SAMPLES * SPA_MAX(this->spec.freq / 48000, 1);
-    adjusted_samples = SPA_CLAMP(this->spec.samples, min_period, PW_MAX_SAMPLES);
-
     if ((this->hidden = priv = SDL_calloc(1, sizeof(struct SDL_PrivateAudioData))) == NULL) {
         return SDL_OutOfMemory();
     }