zoukankan      html  css  js  c++  java
  • PCM转AAC返回1768846202 错误解决

    1、参考FFMPEG

      https://github.com/chrisballinger/FFmpeg-iOS-Encoder/blob/master/FFmpegEncoder/AACEncoder.m

      输出的AAC按照下面的设置的时候

    - (void) setupEncoderFromSampleBuffer:(CMSampleBufferRef)sampleBuffer {
        AudioStreamBasicDescription inAudioStreamBasicDescription = *CMAudioFormatDescriptionGetStreamBasicDescription((CMAudioFormatDescriptionRef)CMSampleBufferGetFormatDescription(sampleBuffer));
        
        AudioStreamBasicDescription outAudioStreamBasicDescription = {0}; // Always initialize the fields of a new audio stream basic description structure to zero, as shown here: ...
        outAudioStreamBasicDescription.mSampleRate = inAudioStreamBasicDescription.mSampleRate; // The number of frames per second of the data in the stream, when the stream is played at normal speed. For compressed formats, this field indicates the number of frames per second of equivalent decompressed data. The mSampleRate field must be nonzero, except when this structure is used in a listing of supported formats (see “kAudioStreamAnyRate”).
        outAudioStreamBasicDescription.mFormatID = kAudioFormatMPEG4AAC; // kAudioFormatMPEG4AAC_HE does not work. Can't find `AudioClassDescription`. `mFormatFlags` is set to 0.
        outAudioStreamBasicDescription.mFormatFlags = kMPEG4Object_AAC_LC; // Format-specific flags to specify details of the format. Set to 0 to indicate no format flags. See “Audio Data Format Identifiers” for the flags that apply to each format.
        outAudioStreamBasicDescription.mBytesPerPacket = 0; // The number of bytes in a packet of audio data. To indicate variable packet size, set this field to 0. For a format that uses variable packet size, specify the size of each packet using an AudioStreamPacketDescription structure.
        outAudioStreamBasicDescription.mFramesPerPacket = 1024; // The number of frames in a packet of audio data. For uncompressed audio, the value is 1. For variable bit-rate formats, the value is a larger fixed number, such as 1024 for AAC. For formats with a variable number of frames per packet, such as Ogg Vorbis, set this field to 0.
        outAudioStreamBasicDescription.mBytesPerFrame = 0; // The number of bytes from the start of one frame to the start of the next frame in an audio buffer. Set this field to 0 for compressed formats. ...
        outAudioStreamBasicDescription.mChannelsPerFrame = 1; // The number of channels in each frame of audio data. This value must be nonzero.
        outAudioStreamBasicDescription.mBitsPerChannel = 0; // ... Set this field to 0 for compressed formats.
        outAudioStreamBasicDescription.mReserved = 0; // Pads the structure out to force an even 8-byte alignment. Must be set to 0.
        AudioClassDescription *description = [self
                                              getAudioClassDescriptionWithType:kAudioFormatMPEG4AAC
                                              fromManufacturer:kAppleSoftwareAudioCodecManufacturer];
    
        OSStatus status = AudioConverterNewSpecific(&inAudioStreamBasicDescription, &outAudioStreamBasicDescription, 1, description, &_audioConverter);
        if (status != 0) {
            NSLog(@"setup converter: %d", (int)status);
        }
    }
    

      在真正转码的时候

      一直返回 Error Domain=NSOSStatusErrorDomain Code=1768846202 "(null)"错误

       status = AudioConverterFillComplexBuffer(_audioConverter, inInputDataProc, (__bridge void *)(self), &ioOutputDataPacketSize, &outAudioBufferList, outPacketDescription);
            //NSLog(@"ioOutputDataPacketSize: %d", (unsigned int)ioOutputDataPacketSize);
            NSData *data = nil;
            if (status == 0) {
                NSData *rawAAC = [NSData dataWithBytes:outAudioBufferList.mBuffers[0].mData length:outAudioBufferList.mBuffers[0].mDataByteSize];
                NSData *adtsHeader = [self adtsDataForPacketLength:rawAAC.length];
                NSMutableData *fullData = [NSMutableData dataWithData:adtsHeader];
                [fullData appendData:rawAAC];
                data = fullData;
            } else {
                error = [NSError errorWithDomain:NSOSStatusErrorDomain code:status userInfo:nil];
            }
    

      1768846202 对应的错误码是  'insz' ,意思是输入的缓冲区数据大小不对

      经过仔细检查,是因为输入的声道数错误

      

    - (void) setupEncoderFromSampleBuffer:(CMSampleBufferRef)sampleBuffer {
        AudioStreamBasicDescription inAudioStreamBasicDescription = *CMAudioFormatDescriptionGetStreamBasicDescription((CMAudioFormatDescriptionRef)CMSampleBufferGetFormatDescription(sampleBuffer));
        
        AudioStreamBasicDescription outAudioStreamBasicDescription = {0}; // 初始化输出流的结构体描述为0. 很重要。
        outAudioStreamBasicDescription.mSampleRate = inAudioStreamBasicDescription.mSampleRate; // 音频流,在正常播放情况下的帧率。如果是压缩的格式,这个属性表示解压缩后的帧率。帧率不能为0。
        outAudioStreamBasicDescription.mFormatID = kAudioFormatMPEG4AAC; // 设置编码格式
        outAudioStreamBasicDescription.mFormatFlags = kMPEG4Object_AAC_LC; // 无损编码 ,0表示没有
        outAudioStreamBasicDescription.mBytesPerPacket = 0; // 每一个packet的音频数据大小。如果的动态大小,设置为0。动态大小的格式,需要用AudioStreamPacketDescription 来确定每个packet的大小。
        outAudioStreamBasicDescription.mFramesPerPacket = 1024; // 每个packet的帧数。如果是未压缩的音频数据,值是1。动态码率格式,这个值是一个较大的固定数字,比如说AAC的1024。如果是动态大小帧数(比如Ogg格式)设置为0。
    //    outAudioStreamBasicDescription.mBytesPerFrame = 0; //  每帧的大小。每一帧的起始点到下一帧的起始点。如果是压缩格式,设置为0 。
        outAudioStreamBasicDescription.mChannelsPerFrame =  inAudioStreamBasicDescription.mChannelsPerFrame; // 声道数
    //    outAudioStreamBasicDescription.mBitsPerChannel = 0; // 压缩格式设置为0
    //    outAudioStreamBasicDescription.mReserved = 0; // 8字节对齐,填0.
        AudioClassDescription *description = [self
                                              getAudioClassDescriptionWithType:kAudioFormatMPEG4AAC
                                              fromManufacturer:'appl']; //软编
        
        OSStatus status = AudioConverterNewSpecific(&inAudioStreamBasicDescription,
                                                    &outAudioStreamBasicDescription,
                                                    1,
                                                    description,
                                                    &_audioConverter); // 创建转换器
        if (status != 0) {
            NSLog(@"setup converter: %d", (int)status);
        }
    }
    

      修改成上面的参数可以解决问题

  • 相关阅读:
    So easy Webservice 2.WebService介绍
    So easy Webservice 1.Socket建设web服务
    eclipse 实用快捷键
    Memory Layout of C Programs
    C程序员必须知道的内存知识【英】
    闭包,懂不懂由你,反正我是懂了
    什么是闭包,我的理解
    浅析Java中的访问权限控制
    Java访问控制
    Java修饰符public,private,protected及默认的区别
  • 原文地址:https://www.cnblogs.com/doudouyoutang/p/8073019.html
Copyright © 2011-2022 走看看