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);
        }
    }
    

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

  • 相关阅读:
    爱加密亮相第十八届软博会,移动App安全引关注
    android 实现自己定义状态栏通知(Status Notification)
    Android中View绘制流程以及invalidate()等相关方法分析
    设计模式 ( 十八 ) 策略模式Strategy(对象行为型)
    目标检測的图像特征提取之(一)HOG特征
    Vbox 未指定XXX网络名称 找不到网卡问题
    NetBeans工具学习之道:NetBeans IDE Java 高速新手教程
    NETSH WINSOCK RESET这条命令的含义和作用?
    红帽/CentOS ext4无法格式化大分区 补充ext4格式化方式
    android之PackageManager简单介绍
  • 原文地址:https://www.cnblogs.com/doudouyoutang/p/8073019.html
Copyright © 2011-2022 走看看