GSSF callback called thousands of times for audio

107 views Asked by At

I'm using two GSSF filters, one to send BGRA frames and another to send PCM 16bit 48KHz audio samples to directshow graph.

The image filter callback is called at the right frequency, more or less 30ms apart since I'm working in 29.97fps. But for audio, once the graph starts the audio callback is called more than 5000 times.

Video Setup:

BitmapInfoHeader bmi = new BitmapInfoHeader();
bmi.Size = Marshal.SizeOf(typeof(BitmapInfoHeader));
bmi.Width = width; //1920
bmi.Height = height * -1; //1080
bmi.Planes = 1;
bmi.BitCount = (short)bpp; //32
bmi.Compression = 0;
bmi.ImageSize = (bmi.BitCount / 8) * bmi.Width * bmi.Height; //8294400
bmi.XPelsPerMeter = 0;
bmi.YPelsPerMeter = 0;
bmi.ClrUsed = 0;
bmi.ClrImportant = 0;

int hr = ssi.SetMediaTypeFromBitmap(bmi, (long)fps); // (long)(10000000 / 29.97)
DsError.ThrowExceptionForHR(hr);

Audio Setup

WaveFormatEx wfex = new WaveFormatEx();
wfex.wFormatTag = 1; //PCM
wfex.nSamplesPerSec = samplerate; //48000;
wfex.wBitsPerSample = (ushort)bps; //16
wfex.nChannels = (ushort)numChannels; //2
wfex.nAvgBytesPerSec = samplerate * (bps * numChannels / 8); //192000
wfex.nBlockAlign = (ushort)(numChannels * bps / 8); //4
wfex.cbSize = 0;

//Keep Data
bytesPerSample = wfex.nAvgBytesPerSec;
frequency = samplerate;
channels = numChannels;
bits = bps;

AMMediaType amt = new AMMediaType();
amt.majorType = MediaType.Audio;
amt.subType = MediaSubType.PCM;
amt.formatType = FormatType.WaveEx;
amt.temporalCompression = false;
amt.fixedSizeSamples = true;
amt.sampleSize = wfex.nBlockAlign;
amt.formatSize = Marshal.SizeOf(wfex);
amt.formatPtr = Marshal.AllocCoTaskMem(amt.formatSize);
Marshal.StructureToPtr(wfex, amt.formatPtr, false);

int hr = ssa.SetMediaTypeEx(amt, wfex.nAvgBytesPerSec);
DsError.ThrowExceptionForHR(hr);

Tools.FreeAMMediaType(amt);

I'm setting Timestamps like this:

For Video:

// fps is (long)(10000000/29.97)
DsLong rtStart = new DsLong(frameNumber * fps);
DsLong rtStop = new DsLong(rtStart + fps);
int hr = pSample.SetTime(rtStart, rtStop);
frameNumber++;

For Audio:

//size is the number os audio samples written in bytes
//bits = 16
//channles = 2
//frequency = 48000
//timeUnit = 10000000
// lastTime starts from 0
long sampleCount = size * 8 / bits / channels;
long frameLength = timeUnit * sampleCount / frequency;
DsLong rtStart = new DsLong(lastTime);
lastTime = rtStart + frameLength;
DsLong rtStop = new DsLong(lastTime);
int hr = pSample.SetTime(rtStart, rtStop);

I haven't posted the full code because is mostly the same as the example of GSSF. But I can post whatever you feel is necessary.

Anyone has any idea why is this happening?

Thank you

1

There are 1 answers

0
tweellt On BEST ANSWER

I've stopped working on this but I thought I could give it a try again and I found the "problem". If anyone else has this problem, here it goes...

The thing is, like RomanR said, I should throttle the requests, but I couldn't figure out what was going on since I add several request of audio and few of video.

So I kept digging and found out the culprit. Since I was encoding audio in Mpeg Layer II, this paricular codec requests 1152 samples per channel at a time, even you you have 1920 samples to deliver. So I wasn't feeding the samples the right way. I created a sample manager which delivers the right number of samples and times them accordingly.