Skip to content

WAVE_FORMAT_EXTENSIBLE decodes on Python 3.12 but raises on 3.10 (the CI version) #13

Description

@thorwhalen

The gap

WAVE_FORMAT_EXTENSIBLE (format tag 0xFFFE) WAV files — which ffmpeg writes routinely, and which any multichannel or >16-bit file tends to use — decode on Python 3.12 and raise on Python 3.10:

python 3.10.13:  decode_wav_bytes(extensible_wav) -> wave.Error: unknown format: 65534
python 3.12.12:  decode_wav_bytes(extensible_wav) -> ([0, 1, -1, 2, -2], 44100)

Same bytes, same recode. CI runs 3.10 only, so this is invisible to the suite.

Cause

Not in recode's own parsing. The chunk walker added in #11 handles these files correctly — it locates the payload at the right offset (verified: _wav_data_chunk returns (68, 10) on both versions). The failure is one line later, in decode_wav_header_bytes, which delegates to stdlib wave:

# 3.10  wave._read_fmt_chunk
if wFormatTag == WAVE_FORMAT_PCM: ...
else: raise Error('unknown format: %r' % (wFormatTag,))

# 3.12  wave._read_fmt_chunk
if wFormatTag != WAVE_FORMAT_PCM and wFormatTag != WAVE_FORMAT_EXTENSIBLE:
    raise Error(...)

stdlib wave gained EXTENSIBLE support in 3.12.

Options

  1. Parse the fmt chunk directly. The walker is already there and fmt is a fixed layout of 16/18/40 bytes. This makes behaviour identical on every supported Python and drops the stdlib wave dependency from the read path — wave is a deprecated-adjacent module and its Wave_read is also why the errors were heterogeneous before Fix #4: locate the WAV data chunk instead of inferring where it must be #11.
  2. Declare EXTENSIBLE out of scope and say so in the docstring.
  3. Raise the supported Python floor to 3.12 (probably not worth it for this alone).

Option 1 is the one that makes recode self-contained on the read path, and the machinery is now mostly in place.

Found by adversarial review while fixing #4.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions