在Linux环境下为FFmpeg集成LC3音频编码器(liblc3)需要以下步骤。LC3是新一代低复杂度音频编解码器,广泛应用于蓝牙LE Audio等场景:
1. 环境准备
# 安装基础编译工具
sudo apt update
sudo apt install build-essential git cmake ninja-build nasm pkg-config
# 安装FFmpeg依赖
sudo apt install libssl-dev zlib1g-dev
2. 编译安装liblc3
2.1 获取源码
git clone https://github.com/google/liblc3.git
cd liblc3
2.2 编译安装
mkdir build && cd build
cmake -GNinja -DCMAKE_BUILD_TYPE=Release ..
ninja
sudo ninja install
2.3 验证安装
# 检查头文件和库
ls /usr/local/include/lc3.h
ls /usr/local/lib/liblc3.so
3. 修改FFmpeg源码
3.1 获取FFmpeg源码
git clone https://git.ffmpeg.org/ffmpeg.git ffmpeg
cd ffmpeg
3.2 添加LC3编码器支持
在libavcodec/Makefile中添加:
OBJS-$(CONFIG_LC3_ENCODER) += lc3enc.o
3.3 创建编码器文件
新建libavcodec/lc3enc.c:
#include <lc3.h>
#include "libavutil/opt.h"
#include "avcodec.h"
#include "internal.h"
typedef struct LC3EncContext {
AVClass *class;
lc3_encoder_t encoder;
int frame_ms; // 帧时长(毫秒)
int bitrate; // 目标比特率
} LC3EncContext;
static av_cold int lc3_encode_init(AVCodecContext *avctx)
{
LC3EncContext *s = avctx->priv_data;
int dt_us = s->frame_ms * 1000;
int sr_hz = avctx->sample_rate;
// 创建LC3编码器实例
s->encoder = lc3_encoder_create(dt_us, sr_hz, 0);
if (!s->encoder) {
av_log(avctx, AV_LOG_ERROR, "Failed to create LC3 encoder\n");
return AVERROR(ENOMEM);
}
// 设置输出参数
avctx->frame_size = (sr_hz * s->frame_ms) / 1000;
avctx->bit_rate = s->bitrate;
return 0;
}
static int lc3_encode_frame(AVCodecContext *avctx, AVPacket *avpkt,
const AVFrame *frame, int *got_packet)
{
LC3EncContext *s = avctx->priv_data;
int ret, frame_bytes;
// 计算输出帧大小
frame_bytes = lc3_encoder_get_frame_bytes(s->encoder);
// 分配输出包
if ((ret = ff_alloc_packet2(avctx, avpkt, frame_bytes, 0))
return ret;
// 执行编码
const int16_t *pcm = (const int16_t *)frame->data[0];
lc3_encoder_encode(s->encoder, pcm, avpkt->data);
avpkt->size = frame_bytes;
*got_packet = 1;
return 0;
}
static av_cold int lc3_encode_close(AVCodecContext *avctx)
{
LC3EncContext *s = avctx->priv_data;
if (s->encoder) lc3_encoder_destroy(s->encoder);
return 0;
}
#define OFFSET(x) offsetof(LC3EncContext, x)
static const AVOption options[] = {
{ "frame_ms", "Frame duration (ms)", OFFSET(frame_ms), AV_OPT_TYPE_INT, {.i64=10}, 5, 20, AV_OPT_FLAG_ENCODING_PARAM },
{ "bitrate", "Target bitrate", OFFSET(bitrate), AV_OPT_TYPE_INT, {.i64=160000}, 24000, 960000, AV_OPT_FLAG_ENCODING_PARAM },
{ NULL }
};
static const AVClass lc3_enc_class = {
.class_name = "LC3 Encoder",
.item_name = av_default_item_name,
.option = options,
.version = LIBAVUTIL_VERSION_INT,
};
AVCodec ff_lc3_encoder = {
.name = "lc3",
.long_name = NULL_IF_CONFIG_SMALL("LC3 (Low Complexity Communication Codec)"),
.type = AVMEDIA_TYPE_AUDIO,
.id = AV_CODEC_ID_LC3,
.priv_data_size = sizeof(LC3EncContext),
.init = lc3_encode_init,
.encode2 = lc3_encode_frame,
.close = lc3_encode_close,
.capabilities = AV_CODEC_CAP_DR1,
.sample_fmts = (const enum AVSampleFormat[]){ AV_SAMPLE_FMT_S16, AV_SAMPLE_FMT_NONE },
.priv_class = &lc3_enc_class,
};
3.4 注册编码器
在libavcodec/allcodecs.c中添加:
extern AVCodec ff_lc3_encoder;
// 在音频编码器部分添加
if (CONFIG_LC3_ENCODER) REGISTER_ENCODER(LC3, lc3);
3.5 添加Codec ID
在libavcodec/codec_id.h的enum AVCodecID中添加:
AV_CODEC_ID_LC3,
4. 配置与编译FFmpeg
4.1 配置编译选项
./configure \
--extra-cflags="-I/usr/local/include" \
--extra-ldflags="-L/usr/local/lib" \
--enable-libshaderc \
--enable-lc3 \
--enable-gpl
4.2 编译安装
make -j$(nproc)
sudo make install
5. 验证集成
5.1 检查编码器
ffmpeg -encoders | grep lc3
# 应输出: A..... lc3 LC3 (Low Complexity Communication Codec)
ffmpeg -h encoder=lc3
5.2 测试编码
# 转换PCM文件为LC3
ffmpeg -f s16le -ar 48000 -ac 1 -i input.pcm -c:a lc3 -b:a 160k output.lc3
# 播放测试
ffplay -f lc3 -ar 48000 -ac 1 output.lc3
6. 调试与问题解决
常见问题:
-
链接错误:
export LD_LIBRARY_PATH=/usr/local/lib:$LD_LIBRARY_PATH -
API不匹配:
检查liblc3版本,最新API参考:// 新版本API示例 lc3_encoder_t enc = lc3_setup_encoder(LC3_DT_10MS, 48000, NULL); -
采样格式支持:
LC3目前仅支持S16格式,如需浮点支持需添加转换:// 在lc3enc.c的encode_frame中添加 if (frame->format != AV_SAMPLE_FMT_S16) { // 使用swresample转换格式 }
7. 高级功能扩展
添加参数支持:
// 在options数组中新增
{ "complexity", "Encoding complexity", OFFSET(complexity), AV_OPT_TYPE_INT, {.i64=3}, 0, 10, ... }
支持多声道:
// 初始化时创建多实例
s->encoders = av_malloc_array(avctx->channels, sizeof(lc3_encoder_t));
for (int ch = 0; ch < avctx->channels; ch++) {
s->encoders[ch] = lc3_encoder_create(...);
}
技术要点总结
- 帧长处理:LC3支持5/7.5/10ms帧长,需与采样率匹配
- 比特率范围:单声道24-320kbps,立体声48-640kbps
- 延迟控制:总延迟 = 帧长 + 编码延迟(典型2.5ms)
- 实时性优化:
// 禁用内存分配 avctx->internal->allocate_progress = 0;
完整实现参考:FFmpeg LC3补丁示例 (需查找最新补丁)
注意:LC3标准仍在演进中,建议跟踪liblc3的GitHub仓库获取最新API变更。

被折叠的 条评论
为什么被折叠?



