为SRS流媒体服务器添加HLS加密功能(附源码)

简介: 为SRS流媒体服务器添加HLS加密功能(附源码)之前测试使用过nginx的HLS加密功能,会使用到一个叫做nginx-rtmp-module的插件,但此插件很久不更新了,网上搜索到一个中国制造的叫做SRS的流媒体服务器,比较活跃,而且据说这个流媒体服务器的性能和功能都强大不少,但遗憾的是没有HLS加密功能。

为SRS流媒体服务器添加HLS加密功能(附源码)

之前测试使用过nginx的HLS加密功能,会使用到一个叫做nginx-rtmp-module的插件,但此插件很久不更新了,网上搜索到一个中国制造的叫做SRS的流媒体服务器,比较活跃,而且据说这个流媒体服务器的性能和功能都强大不少,但遗憾的是没有HLS加密功能。问原作者为什么没有添加这个功能没有回复,所以还是自己动手,丰衣足食吧,花了几个晚上的时间自己参考nginx-rtmp实现了一下。代码放到了github上。

功能介绍

几个新添加的参数配置项

 hls_keys        on;
 hls_fragments_per_key 4;
 hls_key_file     [app]/[stream]-[seq].key;
 hls_key_file_path    ./objs/nginx/html;
 hls_key_url     http://localhost:8080/live/h265.m3u8;
 

分别代表如下含义:

  • hls_keys: 是否开启hls加密,默认关闭。
  • hls_fragments_per_key: 每个key可以加密多少个ts片段,默认值是10。
  • hls_key_file: key文件相对路径的生成模板,包括一个[app]文件夹以及名字[stream]-[seq],后缀为.key,默认值为[app]/[stream]-[seq].key。
  • hls_key_file_path: 可以为key文件的生成指定本地目录,默认为hls_path(存放ts的目录)。
  • hls_key_url: 可以为key指定一个HTTP url。

实现过程中的几个关键点

需要实现的功能点包括一下几个方面:

从配置文件读取配置项

这个仿照srs的实现添加,比较简单。

key和iv的自动生成和保存

在这里每隔hls_fragments_per_key个ts会自动的生成随机的16bytes的key和iv。key会保存在hls_key_file_path路径中,iv会保存在m3u8文件中。

在代码实现中,key和iv在内存中保存了三份。SrsHlsMuxer中保存了一份,用于提供每次new SrsHlsSegment时需要的key和iv。因为每次刷新m3u8(refresh_m3u8)时,都要从头重新生成一次m3u8文件,所以需要为每个SrsHlsSegment对象备份一份iv。最后是传递给writer的key和iv,用于AES128加密。

AES128加密

材料都准备好了,最后的关键问题就是加密。在这里使用了Openssl的加密库,SRS的实现是每次写一个packet(188bytes),而AES128需要加密的raw数据是16的倍数,因此需要在原有SrsFileWriter的实现上加一层缓冲。缓冲到16的倍数后(也就是188*4),加密一次数据,然后写到文件中。具体实现是下面的样子:

srs_error_t SrsEncFileWriter::write(void* buf, size_t count, ssize_t* pnwrite)
{
    
    srs_assert(count == SRS_TS_PACKET_SIZE);
    srs_error_t err = srs_success;

    if(buflength != HLS_AES_ENCRYPT_BLOCK_LENGTH)
    {
        memcpy(tmpbuf+buflength,(char*)buf,SRS_TS_PACKET_SIZE);
        buflength += SRS_TS_PACKET_SIZE;
    }
    if(buflength == HLS_AES_ENCRYPT_BLOCK_LENGTH)
    {
        unsigned char encryptedbuf[HLS_AES_ENCRYPT_BLOCK_LENGTH]; 
        memset(encryptedbuf,0,HLS_AES_ENCRYPT_BLOCK_LENGTH);
        AES_cbc_encrypt((unsigned char *)tmpbuf, (unsigned char *)encryptedbuf, HLS_AES_ENCRYPT_BLOCK_LENGTH, &key, iv, AES_ENCRYPT);
        buflength = 0;
        memset(tmpbuf,0,HLS_AES_ENCRYPT_BLOCK_LENGTH);
        return SrsFileWriter::write(encryptedbuf,HLS_AES_ENCRYPT_BLOCK_LENGTH,pnwrite);
    }
    else
    {
        return err;
    }
 
};

需要注意的是每次close TS文件的FD时需要判断缓冲中有没有数据,如果有的话需要添加填充数据(添加到正好为16的倍数即可),然后加密,写文件,关闭文件:

 int addBytes = 16 - buflength % 16;
 memset(tmpbuf + buflength, addBytes, addBytes);
 unsigned char encryptedbuf[buflength+addBytes];

测试

能够为HLS TS切片正常加密和播放。没有做充分的测试,对SRS了解的还不够深入。如果大家需要这个功能的话,可以尝试着使用一下,遇到问题联系我。

如何使用

首先,在配置文件中添加以下配置项。

http_server {
    enabled         on; 
    listen          8080;
    dir             ./objs/nginx/html;
}
 
vhost __defaultVhost__ {
    hls {
        enabled         on; 
        hls_fragment    10; 
        hls_window      600000;
        hls_path        ./objs/nginx/html;
        hls_m3u8_file   [app]/[stream].m3u8;
        hls_ts_file     [app]/[stream]-[seq].ts;
        hls_keys        on; 
        hls_fragments_per_key 4;
        hls_key_file     [app]/[stream]-[seq].key;
        hls_key_file_path    ./objs/nginx/html;
        hls_key_url       http://localhost:8080/live;
    }   

然后到trunk目录下启动:

./objs/srs -c conf/hls.conf

推送rtmp流的命令:

ffmpeg -re  -i /Users/zexu/Movies/test.mp4 -c copy -f flv rtmp://localhost:1935/live/h265

最后在播放器中播放URL:

http://localhost:8080/live/h265.m3u8

关于配置项要注意的地方

关于hls_key_file_path和hls_key_url,要么都不配置(注释掉即可),这样的话m3u8,ts和key文件都在一个目录下面。要么就都配置,需要自己保证两个地址能够对上。否则会出现key找不到而导致播放失败的问题。


作者: HarlanC

博客地址: http://www.cnblogs.com/harlanc/
个人博客: http://www.harlancn.me/
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出, 原文链接

如果觉的博主写的可以,收到您的赞会是很大的动力,如果您觉的不好,您可以投反对票,但麻烦您留言写下问题在哪里,这样才能共同进步。谢谢!

目录
相关文章
|
3月前
|
存储 缓存 安全
php项目源码加密之Zend Guard Loader加密的代码解密可能性很小-优雅草卓伊凡
php项目源码加密之Zend Guard Loader加密的代码解密可能性很小-优雅草卓伊凡
117 2
|
3月前
|
云安全 弹性计算 安全
阿里云服务器安全功能解析:基础防护与云安全产品参考
在使用云服务器的过程中,云服务器的安全问题是很多用户非常关心的问题。阿里云服务器除了提供基础的防护之外,还提供了一系列安全防护类云产品,以确保用户云服务器的安全。本文将详细介绍阿里云服务器的基础安全防护有哪些,以及阿里云的一些安全防护类云产品,帮助用户更好地理解和使用阿里云服务器的安全功能。
|
10月前
|
Linux PHP 数据安全/隐私保护
2024授权加密系统PHP网站源码
2024授权加密系统PHP网站源码
261 58
|
9月前
|
监控 前端开发 应用服务中间件
小游戏源码开发搭建技术栈和服务器配置流程
近些年不同场景游戏层出不穷,现就小游戏开发技术应用及功能详细剖析!
|
8月前
快速拥有满血全功能DeepSeek,再也不怕服务器繁忙!
官网繁忙不用怕!现在跟我一起通过视频学习阿里云《零门槛、即刻拥有 DeepSeek-R1 满血版》技术解决方案,最快两步三分钟就能拥有 免费!满血版!随时可用!支持联网搜索!带有个人知识库(RAG)!的DeepSeek 模型能力!!!
225 0
快速拥有满血全功能DeepSeek,再也不怕服务器繁忙!
|
10月前
|
弹性计算 运维 监控
云产品评测:云服务诊断 — ECS实例健康状态与诊断功能体验
作为一名运维工程师,我日常管理和维护云资源,确保服务稳定运行。阿里云的云服务诊断功能提供了便捷的方式实时了解和优化ECS实例的健康状态。通过健康状态功能,我能够查看CPU、内存等指标,及时发现并解决性能瓶颈,提升了约30%的工作效率。诊断功能则帮助我快速定位复杂问题,减少了40%的诊断时间,并提供详细的优化建议。尽管功能已很强大,但仍建议进一步细化诊断结果和增加自定义告警选项,以提升使用体验。我非常推荐此工具给其他运维人员。
242 22
|
10月前
|
前端开发 数据安全/隐私保护
全新紫色新UI数码盲盒系统源码/全开源无加密/附教程
全新紫色新UI数码盲盒系统源码/全开源无加密/附教程 前端uniapp+H5 后端FastAdmin框架 可打包成APP多端运行 亲测可用
250 13
|
10月前
|
弹性计算 运维 开发者
关于ECS 健康状态 诊断功能评测
这是一位开发兼运维工程师的观点,认为云资源的健康状态和诊断功能作用有限,因为大多数问题根源在于代码质量,而这些工具无法改善低下的代码质量导致的资源异常。
|
11月前
|
PHP 数据库 数据安全/隐私保护
布谷直播源码部署服务器关于数据库配置的详细说明
布谷直播系统源码搭建部署时数据库配置明细!
|
11月前
|
NoSQL 应用服务中间件 PHP
布谷一对一直播源码服务器环境配置及app功能
一对一直播源码阿里云服务器环境配置及要求

热门文章

最新文章