naudio / NAudio

Audio and MIDI library for .NET

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Read method of Pcm24BitToSampleProvider ignores the offset parameter

jurihock opened this issue · comments

Seems to be related to #297

int bytesRead = source.Read(sourceBuffer, 0, sourceBytesRequired);

Looks fine to me, the offset is for the output buffer (buffer), not the sourceBuffer, which is a temporary buffer we read into before converting to write into buffer which does use offset

Thanks for reviewing, Mark!

Actually, I have the following problem, where I suspect an offset issue in Pcm24BitToSampleProvider (probably):

using System.Diagnostics;

class Program
{
  static void Main()
  {
    var file = @"D:\voice.wav"; // https://github.com/jurihock/stftPitchShift/blob/main/examples/voice.wav

    // TEST 1: ok
    {
      // read all samples

      var reader = new NAudio.Wave.AudioFileReader(file);
      var totalcount = (int)(reader.Length / (reader.WaveFormat.BitsPerSample / 8));

      var offset = 0;
      var count = totalcount;

      var data = new float[count];
      var result = reader.Read(data, offset, count);

      Debug.Assert(result == count);
    }

    // TEST 2: ok
    {
      // crop right

      var reader = new NAudio.Wave.AudioFileReader(file);
      var totalcount = (int)(reader.Length / (reader.WaveFormat.BitsPerSample / 8));

      var offset = 0;
      var count = totalcount - 42;

      var data = new float[count];
      var result = reader.Read(data, offset, count);

      Debug.Assert(result == count);
    }

    // TEST 3: nok
    {
      // crop left

      var reader = new NAudio.Wave.AudioFileReader(file);
      var totalcount = (int)(reader.Length / (reader.WaveFormat.BitsPerSample / 8));

      var offset = 42;
      var count = totalcount - offset;

      var data = new float[count];
      var result = reader.Read(data, offset, count); // IndexOutOfRangeException in Pcm24BitToSampleProvider.Read()

      Debug.Assert(result == count);
    }

    // TEST 4: implausible
    {
      // crop left, but allocate totalcount

      var reader = new NAudio.Wave.AudioFileReader(file);
      var totalcount = (int)(reader.Length / (reader.WaveFormat.BitsPerSample / 8));

      var offset = 42;
      var count = totalcount - offset;

      var data = new float[totalcount]; // totalcount instead of count to fix IndexOutOfRangeException
      var result = reader.Read(data, offset, count);

      Debug.Assert(result == count);
    }
  }
}

The test case 3 fails with IndexOutOfRangeException, because the data array is supposedly too short. The test case 4 throws no exception in Pcm24BitToSampleProvider.Read(), but now the data array contains unnecessary zeros in the front. That makes no sense to me.

Pcm24BitToSampleProvider

Am I missing something?

Oh, sorry! I have now carefully read through your answer and the read function description. I actually misunderstood how the offset parameter of the Pcm24BitToSampleProvider.Read works. Thanks again!