Author Topic: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem  (Read 353 times)

Falcosoft

  • Guest
Hi,
With the new default WASAPI output mode in v2.4.13 BASS_ChannelGetData(MidiStream, @FFT, BASS_DATA_FFT2048) gets invalid data when low buffer length is set e.g. with
BASS_SetConfig(BASS_CONFIG_BUFFER, 30). In versions before v2.4.13 or in v2.4.13 with BASS_DEVICE_DSOUND flag set the problem does not occur. In Directsound mode the
return value of BASS_ChannelGetData() properly indicates that less than the required number of bytes have been available and no invalid data loaded to FFT buffer. in WASAPI mode regardless how low the buffer length is set BASS_ChannelGetData(MidiStream, @FFT, BASS_DATA_FFT2048) always returns 16384 as result and loads invalid data to FFT buffer. This results in serious visual glitches in my player's spectrum analyzer. Increasing the buffer cures the problem but since this is a real time synth this solution is not optimal.

Thanks in advance.

Ian @ un4seen

  • Administrator
  • Posts: 21017
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #1 on: 25 Jan '18 - 17:40 »
I will look into this tomorrow and then get back to you.

Falcosoft

  • Guest
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #2 on: 25 Jan '18 - 21:28 »
Hi Ian,
Thanks for your answer, I will wait. But I would like to report another problem that is most likely related to to above one. First of all I forgot to mention that I also used a low update period (BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 5). In Directsound mode the frequency of DSP callback functions is directly related to the update period. Lower update period value results in more frequent callback function callings and this frequency does not depend on the playback buffer size set by BASS_SetConfig(BASS_CONFIG_BUFFER, x). But in the new WASAPI mode this is more erratic and does not have a regular pattern. Some buffer settings and low update period values results in that the callbacks are called rarely (as if you have set BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 100) in Directsound mode). An example:
In case of BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 5) and BASS_SetConfig(BASS_CONFIG_BUFFER, 50) the callbacks are called about at every 100 ms. If you set the buffer either bigger or smaller the callbacks are called more frequently. 

Ian @ un4seen

  • Administrator
  • Posts: 21017
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #3 on: 26 Jan '18 - 17:28 »
With the new default WASAPI output mode in v2.4.13 BASS_ChannelGetData(MidiStream, @FFT, BASS_DATA_FFT2048) gets invalid data when low buffer length is set e.g. with
BASS_SetConfig(BASS_CONFIG_BUFFER, 30). In versions before v2.4.13 or in v2.4.13 with BASS_DEVICE_DSOUND flag set the problem does not occur. In Directsound mode the
return value of BASS_ChannelGetData() properly indicates that less than the required number of bytes have been available and no invalid data loaded to FFT buffer. in WASAPI mode regardless how low the buffer length is set BASS_ChannelGetData(MidiStream, @FFT, BASS_DATA_FFT2048) always returns 16384 as result and loads invalid data to FFT buffer. This results in serious visual glitches in my player's spectrum analyzer. Increasing the buffer cures the problem but since this is a real time synth this solution is not optimal.

Here's an update that I think should fix the problem:

   www.un4seen.com/stuff/bass.zip

Let me know if you still see any problem. This update will retain some old data that has left the playback buffer (to cover device latency), which will be available to BASS_ChannelGetData, so it may well be able to process more than the BASS_CONFIG_BUFFER setting would suggest.

But I would like to report another problem that is most likely related to to above one. First of all I forgot to mention that I also used a low update period (BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 5). In Directsound mode the frequency of DSP callback functions is directly related to the update period. Lower update period value results in more frequent callback function callings and this frequency does not depend on the playback buffer size set by BASS_SetConfig(BASS_CONFIG_BUFFER, x). But in the new WASAPI mode this is more erratic and does not have a regular pattern. Some buffer settings and low update period values results in that the callbacks are called rarely (as if you have set BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 100) in Directsound mode). An example:
In case of BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 5) and BASS_SetConfig(BASS_CONFIG_BUFFER, 50) the callbacks are called about at every 100 ms. If you set the buffer either bigger or smaller the callbacks are called more frequently.

I don't seem to be able to reproduce this problem here; the buffer length (BASS_CONFIG_BUFFER) doesn't seem to affect the amount of data requested. Is there another BASS_CONFIG_BUFFER setting that particularly shows the difference when compared to the 50 setting? There will be some fluctuation in the amount of data requested due to the asynchronous nature of the buffering, ie. data it written and read with different periods.

There is actually not much benefit in using an update period below 10ms, as that is the period with which the final mix is generated. If you want minimal latency, it would probably be better to disable the playback buffering (rather than using a very low BASS_CONFIG_UPDATEPERIOD) by setting the BASS_ATTRIB_BUFFER option to 0.

Falcosoft

  • Guest
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #4 on: 26 Jan '18 - 18:39 »
Here's an update that I think should fix the problem:

Thanks Ian, now it's working as expected.

I don't seem to be able to reproduce this problem here; the buffer length (BASS_CONFIG_BUFFER) doesn't seem to affect the amount of data requested. Is there another BASS_CONFIG_BUFFER setting that particularly shows the difference when compared to the 50 setting? There will be some fluctuation in the amount of data requested due to the asynchronous nature of the buffering, ie. data it written and read with different periods.
There is actually not much benefit in using an update period below 10ms, as that is the period with which the final mix is generated. If you want minimal latency, it would probably be better to disable the playback buffering (rather than using a very low BASS_CONFIG_UPDATEPERIOD) by setting the BASS_ATTRIB_BUFFER option to 0.

Actually there is a benefit of using 5 ms update period but it is not latency related. As I said above the benefit is the more frequent callback calls which can be important if you use e.g. Bass_VST and VST instruments. The midi timing is more precise in case of 5 ms update latency since the instrument plugins get the midi data at the callback rate and since Bass_VST does not use the deltaFrames member of VstMidiEvent struct (it's always 0) the precision only depends on the callback frequency.
Anyway I have created a test video that tries to demonstrate the problem. I have set the update period to 10 ms. This way the problem is still can be observed.
Maybe it's important and I have not mentioned that both recording and playback are used at the same time. As you can notice the volume bars are OK at both 40 and 60 ms but at 55 ms it's slow. The numbers in the console are the data length values that the callback function receives and you can somewhat see the more/less frequent calls. This phenomenon does not occur in Directsound mode.
https://youtu.be/lY93CeH5f5s
 

Ian @ un4seen

  • Administrator
  • Posts: 21017
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #5 on: 29 Jan '18 - 14:52 »
Actually there is a benefit of using 5 ms update period but it is not latency related. As I said above the benefit is the more frequent callback calls which can be important if you use e.g. Bass_VST and VST instruments. The midi timing is more precise in case of 5 ms update latency since the instrument plugins get the midi data at the callback rate and since Bass_VST does not use the deltaFrames member of VstMidiEvent struct (it's always 0) the precision only depends on the callback frequency.

Oh yes, that's true.

Anyway I have created a test video that tries to demonstrate the problem. I have set the update period to 10 ms. This way the problem is still can be observed.
Maybe it's important and I have not mentioned that both recording and playback are used at the same time. As you can notice the volume bars are OK at both 40 and 60 ms but at 55 ms it's slow. The numbers in the console are the data length values that the callback function receives and you can somewhat see the more/less frequent calls. This phenomenon does not occur in Directsound mode.
https://youtu.be/lY93CeH5f5s

Are those numbers the "length" parameter received by the STREAMPROC function of a 48000 Hz stereo floating-point stream? If so, the peak value of 12000 bytes is 31.25ms, which is higher than BASS should ever request during playback when BASS_CONFIG_UPDATEPERIOD = 10. It should be limited to 1.5x that, ie. 15ms or 5760 bytes in this case. Perhaps that is the input format, and the output format is something else?

In any case, the amount of data requested from the STREAMPROC function shouldn't really affect the refresh rate of a level meter. For example, with the default 100ms update period, the level reading won't stay the same for 100ms. If there is a problem with the level readings being sluggish, I think it may be due to something else. What do you see if you also monitor the playback position via BASS_ChannelGetPosition at the same time, eg. does it advance smoothly or jump?

Falcosoft

  • Guest
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #6 on: 29 Jan '18 - 18:31 »
Hi,
Quote
Are those numbers the "length" parameter received by the STREAMPROC function of a 48000 Hz stereo floating-point stream?
Yes, exactly.
Quote
If so, the peak value of 12000 bytes is 31.25ms, which is higher than BASS should ever request during playback when BASS_CONFIG_UPDATEPERIOD = 10.
That's my problem :)
Quote
Perhaps that is the input format, and the output format is something else?
No, the input and output format is always set to the same to avoid resampling.
The more important initialization code fragments:
 
Code: [Select]
    BASS_RecordInit(RecDevIndex));
    BASS_Init(PlaybackDevIndex, 44100, Dsound, Handle, nil)) ; //Dsound is either 0 or BASS_DEVICE_DSOUND
...   
    BASS_SetConfig(BASS_CONFIG_UPDATEPERIOD, 10);
    BASS_SetConfig(BASS_CONFIG_BUFFER, Latency );   //Latency is set as can be seen in Video
    BASS_SetConfig(BASS_CONFIG_REC_BUFFER, 1000);
...
    chan := BASS_StreamCreate(freq, 2, flags, STREAMPROC_PUSH, nil);
    rchan := BASS_RecordStart(freq, 2, Makelong(flags, 20), @RecordingCallback, nil); // freq is set as can be seen in the Video
...   
    myHDSP := BASS_ChannelSetDSP(chan, @BassDSP nil, 1); // The volume meter data and the 'lenght' numbers calculated here


Quote
In any case, the amount of data requested from the STREAMPROC function shouldn't really affect the refresh rate of a level meter. For example, with the default 100ms update period, the level reading won't stay the same for 100ms. If there is a problem with the level readings being sluggish, I think it may be due to something else. What do you see if you also monitor the playback position via BASS_ChannelGetPosition at the same time, eg. does it advance smoothly or jump?

The volume bar is just a demonstration. It's actually slowed down to make the difference more obvious. It's not the problem. The problem is the inconsistent/erratic/less frequent callback invocation in WASAPI output mode (that  moreover depends on BASS_CONFIG_BUFFER not just the update period) . I have made another video where the huge difference between Directsound and WASAPI mode can be seen. The checkbox in the video enables the BASS_DEVICE_DSOUND flag in Bass_Init().
https://youtu.be/wKgr-PUOEj0

Thanks in advance.



Ian @ un4seen

  • Administrator
  • Posts: 21017
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #7 on: 30 Jan '18 - 13:27 »
I don't seem to be able to reproduce that here, so I will send you a debug version to get some more info on what's happening there.

Falcosoft

  • Guest
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #8 on: 30 Jan '18 - 16:02 »
OK, I'm waiting for the debug version.

Ian @ un4seen

  • Administrator
  • Posts: 21017
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #9 on: 30 Jan '18 - 16:36 »
The email bounced apparently due to the address (falco1@...) being invalid. I see you used a different email address in your latest post. Should I use that one instead?

Falcosoft

  • Guest
Re: BASS 2.4.13 WASAPI BASS_ChannelGetData FFT problem
« Reply #10 on: 30 Jan '18 - 18:12 »
Hi,
Please send it to the email address I have given in this very post. It's the same one you can also find on http://falcosoft.hu as contact info.
Thanks.