2

I am very new with FFMpeg and I am currently trying to convert audio data from PCM AV_SAMPLE_FMT_S16 format to Mp3 AV_SAMPLE_FMT_FLTP format.

For this I am using the AudioResampleContext from FFMpeg

            av_opt_set_int( audioResampleCtx, "in_sample_fmt",     m_aplayer->aCodecCtx->sample_fmt, 0);
            av_opt_set_int( audioResampleCtx, "in_sample_rate",    m_aplayer->aCodecCtx->sample_rate, 0);
            av_opt_set_int( audioResampleCtx, "in_channels",       m_aplayer->aCodecCtx->channels,0);
            av_opt_set_int( audioResampleCtx, "out_channel_layout", audioCodecCtx->channel_layout, 0);
            av_opt_set_int( audioResampleCtx, "out_sample_fmt",     audioCodecCtx->sample_fmt, 0);
            av_opt_set_int( audioResampleCtx, "out_sample_rate",    audioCodecCtx->sample_rate, 0);
            av_opt_set_int( audioResampleCtx, "out_channels",       audioCodecCtx->channels, 0);

The conversion works well since I can listen to my mp3 file but the problems is that my original file is 60 seconds long and the output mp3 file is just 34 seconds. I can hear that it is very accelerated just like if something speeded up the sound. When looking for information with FFMpeg I see that the bitrate just went from 128kbps to 64 kbps.

EDIT: To complete with more information, I want to compress some raw audio data with mp3 codec and have a output.mp3 output format. The raw audio data sample format is AV_SAMPLE_FMT_S16 and the supported sample format for mp3 codec is FLTP (or S16P). Therefore I am doing a sample format conversion from AV_SAMPLE_FMT_S16 to AV_SAMPLE_FMT_FLTP but it is missing half of the data.

Could anyone help me with this ? I know I'm missing something very simple but I just can't figure what.

EDIT:2 Here is the code that does the resampling (coming fromhttps://github.com/martin-steghoefer/debian-karlyriceditor/blob/master/src/ffmpegvideoencoder.cpp) . The audio source isn't an AVFrame but just an array of bytes :

    // Resample the input into the audioSampleBuffer until we proceed the whole decoded data
    if ( (err = avresample_convert( audioResampleCtx,
                                    NULL,
                                    0,
                                    0,
                                    audioFrame->data,
                                    0,
                                    audioFrame->nb_samples )) < 0 )
    {
        qWarning( "Error resampling decoded audio: %d", err );
        return -1;
    }

    if( avresample_available( audioResampleCtx ) >= audioFrame->nb_samples )
    {
        // Read a frame audio data from the resample fifo
        if ( avresample_read( audioResampleCtx, audioFrame->data, audioFrame->nb_samples ) != audioFrame->nb_samples )
        {
            qWarning( "Error reading resampled audio: %d", err );
            return -1;
        }
        //Init packet, do the encoding and write data to file

Thank you for your help !

Robert Jones
  • 587
  • 7
  • 25
  • You'll have to show more code. For example, there's no such things as "mp3 AV_SAMPLE_FMT_FLTP" - fltp is by definition uncompressed data (in float planar format), so I have no idea what mp3 means. Maybe you meant that you compressed "fltp" into mp3 after conversion, but there's no code so it's hard to say. I'm guessing you converted stereo and missed the second plane (frame->data[1] for right channel), since FLTP is planar (left in data[0]; right in data[1]), as opposed to S16 being packed (both channels in data[0]). – Ronald S. Bultje May 11 '16 at 13:54
  • I added more information in my post. What you are saying about FLTP which is planar is interesting. I just can't find a proper example converting some S16 sample format to planar format like FLTP. Like you said I'm missing one plane (probably the second one) therefore I must miss something during the conversion. Do you have any example of S16 to FLTP sample format conversion ? Thank you for your comment ! – Robert Jones May 11 '16 at 14:49
  • Can you show the code that does the actual resampling? – Ronald S. Bultje May 11 '16 at 21:09
  • 1
    Sure, look at ma 2nd edit. As I said I am compressing with mp3 format but my main goal was to use PCM_S16 sample format. As I said it on this post : http://stackoverflow.com/questions/37134003/ffmpeg-encoding-pcm-16-audio-data-allocation-error, I just can't do it because I'm getting errors. – Robert Jones May 12 '16 at 06:55
  • I meant runnable code. Like, can you share the encoding/resampling/decoding code (split it out from your main application) so I can test/run your code locally and help you debug it. – Ronald S. Bultje May 12 '16 at 15:08
  • @RonaldS.Bultje Unforntunately I can't split this code from the main application, it is very dense, sorry for this. Meanwhile, could you tell me if there is a proper way to convert audio data from S16 format to planar format (like PCM S16 to S16P or FLTP) ? I think this is the problem here... – Robert Jones May 13 '16 at 06:48
  • @RobertJones look at my answer http://stackoverflow.com/a/39274304/902217 – CAMOBAP Sep 01 '16 at 14:29

1 Answers1

0

1) If the audio is played faster, than the sampling rate might be incorrect. Check if the input sample rate for the resampler is the same as in the decoder. AND the output sample rate is the same you use in the encoder.

2) Planar vs non-planar is just a way of saving samples in buffer (check: What is the difference between AV_SAMPLE_FMT_S16P and AV_SAMPLE_FMT_S16?). You shouldn't be missing a plane.

3) As the output is shorter: Remind to flush decoder, resampler, encoder. All of them buffer data. When all data is fed to your processor chain (d-r-e) you need to flush each component and handle the flushed data in the next stage (flush decoder -> resample -> encode; flush resampler -> encode; flush encoder).

Did you find a way to solve your issue by now? I'm struggling with a similar issue. When converting from S16 -> FLTP I get an ffmpeg error: "processor: psymodel.c:576: calc_energy: Assertion `el >= 0' failed."

nice_pink
  • 435
  • 1
  • 3
  • 16
  • Hey dude, did you solve the problem with the psymodel.c:576 calc_energy assertion? I get the same error while I'm trying to use the mp3 encoder. – Dosenbiiir Dec 22 '21 at 19:01
  • If in your resampler you create the frame size you need for the encoder (e.g. mp3 1152 samples), then you shouldn't get the error. Best is you don't do a frame to frame resampling, but instead queue your samples and request frames of the required size which contain the resampled data. – nice_pink Jan 03 '22 at 15:47