Firefly1126移植rtmp推流器到RKMedia源码库中

Firefly1126移植rtmp推流器到RKMedia源码库中

1,桌面上新建一个librtmp文件夹,在其中放入srs-librtmp.a和srs-librtmp.h两个文件及libssl.a,libcrypto.a两个文件 ,文件分别来自

/home/kxq/Desktop/srs.oschina/trunk/objs/lib

/home/kxq/Desktop/srs.oschina/trunk/objs/include

/home/kxq/Desktop/srs.oschina/trunk/objs/openssl/lib

2,将librtmp文件夹放入RkMedia文件夹下,文件夹位置

/home/kxq/Desktop/rv1126_rv1109_linux_release_20210306/external/rkmedia/examples

3,新建一个rkmedia_vi_venc_rtmp_test.c文件,在其中编入srs-librtmp.a库,并将srs-librtmp.a文件改名为librtmp.a,使用rtmp推流

首先在同一目录下的cmakelist.txt文件中添加c文件的信息如下 :

#--------------------------
# rkmedia_vi_venc_rtmp_test
#--------------------------
link_directories("/home/kxq/Desktop/rv1126_rv1109_linux_release_20210306/external/rkmedia/examples/librtmp/")
add_executable(rkmedia_vi_venc_rtmp_test rkmedia_vi_venc_rtmp_test.c ${COMMON_SRC})
add_dependencies(rkmedia_vi_venc_rtmp_test easymedia)
target_link_libraries(rkmedia_vi_venc_rtmp_test easymedia 
rtmp -ldl -lstdc++ -lm 
ssl -ldl -lstdc++ -lm 
crypto -ldl -lstdc++ -lm)
target_include_directories(rkmedia_vi_venc_rtmp_test PRIVATE ${CMAKE_SOURCE_DIR}/include)
install(TARGETS rkmedia_vi_venc_rtmp_test RUNTIME DESTINATION "bin")

4,参考rkmedia_vi_venc_rtmp_test.c和srs_h264_raw_publish.c加入rtmp的推流程序,rkmedia_vi_venc_rtmp_test.c文件中主要做了以下改动

首先在头文件中加入rtmp库引用位置

#include "librtmp/srs_librtmp.h"

再加入rtmp推流所用全局变量

static srs_rtmp_t rtmp = NULL;
static int dts,pts = 0;

加入推流代码

void push_rtmp_stream(srs_rtmp_t rtmp_input, MEDIA_BUFFER mb, int dts_input, int pts_input){

char* h264_raw = (char*)RK_MPI_MB_GetPtr(mb);

if(h264_raw != NULL){
        // send out the h264 packet over RTMP
        int ret = srs_h264_write_raw_frames(rtmp_input, h264_raw, RK_MPI_MB_GetSize(mb), dts_input, pts_input);
        //printf("ret = %d\n",ret);
        if (ret != 0) {
            if (srs_h264_is_dvbsp_error(ret)) {
                srs_human_trace("ignore drop video error, code=%d", ret);
            } else if (srs_h264_is_duplicated_sps_error(ret)) {
                srs_human_trace("ignore duplicated sps, code=%d", ret);
            } else if (srs_h264_is_duplicated_pps_error(ret)) {
                srs_human_trace("ignore duplicated pps, code=%d", ret);
            } else {
                srs_human_trace("send h264 raw data failed. ret=%d", ret);
                srs_rtmp_destroy(rtmp);
                return ;
            }
        }
    }

    usleep(10 * 1000);
    
}

将回调函数中改为

void video_packet_cb(MEDIA_BUFFER mb) {
  static RK_S32 packet_cnt = 0;
  double fps_rtmp = 25;
  if (quit)
    return;

  printf("#Get packet-%d, size %zu\n", packet_cnt, RK_MPI_MB_GetSize(mb));

  push_rtmp_stream(rtmp, mb, dts, pts);

  RK_MPI_MB_ReleaseBuffer(mb);

  dts += 1000 / fps_rtmp;
  pts = dts;
  packet_cnt++;
}

在Main函数中加入rtmp握手初始化相关代码

  // init rtsp
  //g_rtsplive = create_rtsp_demo(554);
  //g_rtsp_session = rtsp_new_session(g_rtsplive, "/live/main_stream");
  //init rtmp
  printf("Example for srs-librtmp\n");
  printf("SRS(ossrs) client librtmp library.\n");
  printf("version: %d.%d.%d\n", srs_version_major(), srs_version_minor(), srs_version_revision());
        
  // connect rtmp context
  const char* rtmp_url = "rtmp://公网rtmp服务器IP:端口/live/livestream";
  rtmp = srs_rtmp_create(rtmp_url);
    
  if (srs_rtmp_handshake(rtmp) != 0) {
      srs_human_trace("simple handshake failed.");
      srs_rtmp_destroy(rtmp);
      return 0;
  }
  srs_human_trace("simple handshake success");
    
  if (srs_rtmp_connect_app(rtmp) != 0) {
      srs_human_trace("connect vhost/app failed.");
      srs_rtmp_destroy(rtmp);
      return 0;
  }
  srs_human_trace("connect vhost/app success");
    
  if (srs_rtmp_publish_stream(rtmp) != 0) {
      srs_human_trace("publish stream failed.");
      srs_rtmp_destroy(rtmp);
      return 0;
  }
  srs_human_trace("publish stream success");

在主函数退出时注销rtmp推流服务

srs_rtmp_destroy(rtmp);

5,编译程序指令如下

# SDK根目录,选择环境
source envsetup.sh firefly_rv1126_rv1109
# 重编rkmedia源码
make rkmedia-dirclean && make rkmedia
# rkmedia库/程序打包到文件系统(oem.img)
./build.sh rootfs
# 重新烧写oem.img,若有其他基础包配置更新(如ffmpeg),则需要重烧rootfs.img

或者执行完前两步后,在SDK/buildroot/output/firefly_rv1126_rv1109/oem/usr/bin目录下找到rkmedia_vi_venc_rtmp_test二进制可执行程序,移动到板子某一个目录下,再进行测试。

测试代码

./rkmedia_vi_venc_rtmp_test -w 640 -h 480 -d /dev/video25

拉流代码

vlc rtmp://公网rtmp服务器IP:端口/live/livestream

注:不要用vlc获取rtmp流,在window下下载OBS软件点击媒体源,设置中将本地文件勾选去掉,在输入中输入rtmp://公网rtmp服务器IP:端口/live/livestream,之后点击确认开始拉流。

posted @ 2022-04-14 10:44  Deceiver_Ker  阅读(1120)  评论(0编辑  收藏  举报