From 0075779d38be8e5af13f1c5e207cc06c1244cc1c Mon Sep 17 00:00:00 2001 From: winlin Date: Sat, 8 Nov 2014 10:28:59 +0800 Subject: [PATCH] for bug #66, refine the api to send h264 frames. --- trunk/research/librtmp/srs_h264_raw_publish.c | 8 +++- trunk/src/libs/srs_librtmp.cpp | 10 ++-- trunk/src/libs/srs_librtmp.hpp | 46 +++++++++++++++---- 3 files changed, 50 insertions(+), 14 deletions(-) diff --git a/trunk/research/librtmp/srs_h264_raw_publish.c b/trunk/research/librtmp/srs_h264_raw_publish.c index dc633df96..c51b930a4 100644 --- a/trunk/research/librtmp/srs_h264_raw_publish.c +++ b/trunk/research/librtmp/srs_h264_raw_publish.c @@ -50,9 +50,13 @@ int read_h264_frame(char* data, int size, char** pp, int fps, srs_trace("h264 raw data invalid."); return -1; } + + // @see srs_write_h264_raw_frames + // each frame prefixed h.264 annexb header, by N[00] 00 00 01, where N>=0, + // for instance, frame = header(00 00 00 01) + payload(67 42 80 29 95 A0 14 01 6E 40) + *frame = p; p += pnb_start_code; - *frame = p; for (;p < data + size; p++) { if (srs_h264_startswith_annexb(p, size - (p - data), &pnb_start_code)) { break; @@ -162,7 +166,7 @@ int main(int argc, char** argv) } // send out the h264 packet over RTMP - if (srs_write_h264_raw_frame(rtmp, data, size, dts, pts) != 0) { + if (srs_write_h264_raw_frames(rtmp, data, size, dts, pts) != 0) { srs_trace("send h264 raw data failed."); goto rtmp_destroy; } diff --git a/trunk/src/libs/srs_librtmp.cpp b/trunk/src/libs/srs_librtmp.cpp index 187536246..e0bb223e7 100644 --- a/trunk/src/libs/srs_librtmp.cpp +++ b/trunk/src/libs/srs_librtmp.cpp @@ -996,21 +996,23 @@ char* srs_amf0_human_print(srs_amf0_t amf0, char** pdata, int* psize) return any->human_print(pdata, psize); } -int srs_write_h264_raw_frame(srs_rtmp_t rtmp, char* frame, int frame_size, u_int32_t dts, u_int32_t pts) +int srs_write_h264_raw_frames(srs_rtmp_t rtmp, char* frames, int frames_size, u_int32_t dts, u_int32_t pts) { int ret = ERROR_SUCCESS; - srs_assert(frame_size > 1); + srs_assert(frames_size > 1); srs_assert(rtmp != NULL); Context* context = (Context*)rtmp; - // 5bits, 7.3.1 NAL unit syntax, + /*// 5bits, 7.3.1 NAL unit syntax, // H.264-AVC-ISO_IEC_14496-10.pdf, page 44. // 7: SPS, 8: PPS, 5: I Frame, 1: P Frame u_int8_t nal_unit_type = (char)frame[0] & 0x1f; - /*// the timestamp in rtmp message header is dts. + // the RTMP packet header + + // the timestamp in rtmp message header is dts. u_int32_t timestamp = dts; // for h264 in RTMP video payload, there is 5bytes header: diff --git a/trunk/src/libs/srs_librtmp.hpp b/trunk/src/libs/srs_librtmp.hpp index 10758dd67..bb07e3bb0 100644 --- a/trunk/src/libs/srs_librtmp.hpp +++ b/trunk/src/libs/srs_librtmp.hpp @@ -338,21 +338,51 @@ extern char* srs_amf0_human_print(srs_amf0_t amf0, char** pdata, int* psize); *************************************************************/ /** * write h.264 raw frame over RTMP to rtmp server. -* @param frame the input h264 raw data, an encoded h.264 I/P/B frame data. -* the frame without h.264 annexb header, by N[00] 00 00 01, where N>=0, -* for instance, header(00 00 00 01) + frame(67 42 80 29 95 A0 14 01 6E 40) -* @paam frame_size the size of h264 raw data. -* assert frame_size > 1, at least has 1 bytes header. +* @param frames the input h264 raw data, encoded h.264 I/P/B frames data. +* frames can be one or more than one frame, +* each frame prefixed h.264 annexb header, by N[00] 00 00 01, where N>=0, +* for instance, frame = header(00 00 00 01) + payload(67 42 80 29 95 A0 14 01 6E 40) +* @paam frames_size the size of h264 raw data. +* assert frames_size > 1, at least has 1 bytes header. * @param dts the dts of h.264 raw data. * @param pts the pts of h.264 raw data. * -* @remark, user should free the frame. +* @remark, user should free the frames. * @remark, the tbn of dts/pts is 1/1000 for RTMP, that is, in ms. * * @return 0, success; otherswise, failed. */ -extern int srs_write_h264_raw_frame(srs_rtmp_t rtmp, - char* frame, int frame_size, u_int32_t dts, u_int32_t pts +/** +For the example file: + http://winlinvip.github.io/srs.release/3rdparty/720p.h264.raw +The data sequence is: + // SPS + 000000016742802995A014016E40 + // PPS + 0000000168CE3880 + // IFrame + 0000000165B8041014C038008B0D0D3A071..... + // PFrame + 0000000141E02041F8CDDC562BBDEFAD2F..... +User can send the SPS+PPS, then each frame: + // SPS+PPS + srs_write_h264_raw_frame('000000016742802995A014016E400000000168CE3880', size, dts, pts) + // IFrame + srs_write_h264_raw_frame('0000000165B8041014C038008B0D0D3A071......', size, dts, pts) + // PFrame + srs_write_h264_raw_frame('0000000141E02041F8CDDC562BBDEFAD2F......', size, dts, pts) +User also can send one by one: + // SPS + srs_write_h264_raw_frame('000000016742802995A014016E4', size, dts, pts) + // PPS + srs_write_h264_raw_frame('00000000168CE3880', size, dts, pts) + // IFrame + srs_write_h264_raw_frame('0000000165B8041014C038008B0D0D3A071......', size, dts, pts) + // PFrame + srs_write_h264_raw_frame('0000000141E02041F8CDDC562BBDEFAD2F......', size, dts, pts) +*/ +extern int srs_write_h264_raw_frames(srs_rtmp_t rtmp, + char* frames, int frames_size, u_int32_t dts, u_int32_t pts ); /** * whether h264 raw data starts with the annexb,