mirror of
https://github.com/ossrs/srs.git
synced 2025-03-09 15:49:59 +00:00
fix #204, srs-librtmp drop dupliated sps/pps(sequence header). 2.0.22.
This commit is contained in:
parent
b4269c8d67
commit
2c601a0069
6 changed files with 80 additions and 11 deletions
|
@ -244,6 +244,7 @@ Supported operating systems and hardware:
|
|||
* 2013-10-17, Created.<br/>
|
||||
|
||||
## History
|
||||
* v2.0, 2014-11-15, fix [#204](https://github.com/winlinvip/simple-rtmp-server/issues/204), srs-librtmp drop dupliated sps/pps(sequence header). 2.0.22.
|
||||
* v2.0, 2014-11-15, fix [#203](https://github.com/winlinvip/simple-rtmp-server/issues/203), srs-librtmp drop any video before sps/pps(sequence header). 2.0.21.
|
||||
* v2.0, 2014-11-15, fix [#202](https://github.com/winlinvip/simple-rtmp-server/issues/202), fix memory leak of h.264 raw packet send in srs-librtmp. 2.0.20.
|
||||
* v2.0, 2014-11-13, fix [#200](https://github.com/winlinvip/simple-rtmp-server/issues/200), deadloop when read/write 0 and ETIME. 2.0.16.
|
||||
|
|
|
@ -170,6 +170,10 @@ int main(int argc, char** argv)
|
|||
if (error != 0) {
|
||||
if (srs_h264_is_dvbsp_error(error)) {
|
||||
srs_lib_trace("ignore drop video error, code=%d", error);
|
||||
} else if (srs_h264_is_duplicated_sps_error(error)) {
|
||||
srs_lib_trace("ignore duplicated sps, code=%d", error);
|
||||
} else if (srs_h264_is_duplicated_pps_error(error)) {
|
||||
srs_lib_trace("ignore duplicated pps, code=%d", error);
|
||||
} else {
|
||||
srs_lib_trace("send h264 raw data failed.");
|
||||
goto rtmp_destroy;
|
||||
|
|
|
@ -31,7 +31,7 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|||
// current release version
|
||||
#define VERSION_MAJOR 2
|
||||
#define VERSION_MINOR 0
|
||||
#define VERSION_REVISION 21
|
||||
#define VERSION_REVISION 22
|
||||
// server info.
|
||||
#define RTMP_SIG_SRS_KEY "SRS"
|
||||
#define RTMP_SIG_SRS_ROLE "origin/edge server"
|
||||
|
|
|
@ -187,6 +187,8 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|||
#define ERROR_H264_API_NO_PREFIXED 3041
|
||||
#define ERROR_FLV_INVALID_VIDEO_TAG 3042
|
||||
#define ERROR_H264_DROP_BEFORE_SPS_PPS 3043
|
||||
#define ERROR_H264_DUPLICATED_SPS 3044
|
||||
#define ERROR_H264_DUPLICATED_PPS 3045
|
||||
|
||||
/**
|
||||
* whether the error code is an system control error.
|
||||
|
|
|
@ -79,12 +79,18 @@ struct Context
|
|||
// whether the sps and pps sent,
|
||||
// @see https://github.com/winlinvip/simple-rtmp-server/issues/203
|
||||
bool h264_sps_pps_sent;
|
||||
// only send the ssp and pps when both changed.
|
||||
// @see https://github.com/winlinvip/simple-rtmp-server/issues/204
|
||||
bool h264_sps_changed;
|
||||
bool h264_pps_changed;
|
||||
|
||||
Context() {
|
||||
rtmp = NULL;
|
||||
skt = NULL;
|
||||
stream_id = 0;
|
||||
h264_sps_pps_sent = false;
|
||||
h264_sps_changed = false;
|
||||
h264_pps_changed = false;
|
||||
}
|
||||
virtual ~Context() {
|
||||
srs_freep(rtmp);
|
||||
|
@ -1127,8 +1133,8 @@ int __srs_write_h264_sps_pps(Context* context, u_int32_t dts, u_int32_t pts)
|
|||
{
|
||||
int ret = ERROR_SUCCESS;
|
||||
|
||||
// when pps or sps not ready, ignore.
|
||||
if (context->h264_pps.empty() || context->h264_sps.empty()) {
|
||||
// only send when both sps and pps changed.
|
||||
if (!context->h264_sps_changed || !context->h264_pps_changed) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -1207,8 +1213,8 @@ int __srs_write_h264_sps_pps(Context* context, u_int32_t dts, u_int32_t pts)
|
|||
}
|
||||
|
||||
// reset sps and pps.
|
||||
context->h264_pps = "";
|
||||
context->h264_sps = "";
|
||||
context->h264_sps_changed = false;
|
||||
context->h264_pps_changed = false;
|
||||
context->h264_sps_pps_sent = true;
|
||||
|
||||
// TODO: FIXME: for more profile.
|
||||
|
@ -1307,13 +1313,26 @@ int __srs_write_h264_raw_frame(Context* context,
|
|||
return ret;
|
||||
}
|
||||
|
||||
context->h264_sps = "";
|
||||
context->h264_sps.append(frame, frame_size);
|
||||
std::string sps;
|
||||
sps.append(frame, frame_size);
|
||||
|
||||
if (context->h264_sps == sps) {
|
||||
return ERROR_H264_DUPLICATED_SPS;
|
||||
}
|
||||
context->h264_sps_changed = true;
|
||||
context->h264_sps = sps;
|
||||
|
||||
return __srs_write_h264_sps_pps(context, dts, pts);
|
||||
} else if (nal_unit_type == 8) {
|
||||
context->h264_pps = "";
|
||||
context->h264_pps.append(frame, frame_size);
|
||||
|
||||
std::string pps;
|
||||
pps.append(frame, frame_size);
|
||||
|
||||
if (context->h264_pps == pps) {
|
||||
return ERROR_H264_DUPLICATED_PPS;
|
||||
}
|
||||
context->h264_pps_changed = true;
|
||||
context->h264_pps = pps;
|
||||
|
||||
return __srs_write_h264_sps_pps(context, dts, pts);
|
||||
} else {
|
||||
|
@ -1341,6 +1360,11 @@ int srs_h264_write_raw_frames(srs_rtmp_t rtmp,
|
|||
return ret;
|
||||
}
|
||||
|
||||
// use the last error
|
||||
// @see https://github.com/winlinvip/simple-rtmp-server/issues/203
|
||||
// @see https://github.com/winlinvip/simple-rtmp-server/issues/204
|
||||
int error_code_return = ret;
|
||||
|
||||
// send each frame.
|
||||
while (!context->h264_raw_stream.empty()) {
|
||||
// each frame must prefixed by annexb format.
|
||||
|
@ -1363,12 +1387,24 @@ int srs_h264_write_raw_frames(srs_rtmp_t rtmp,
|
|||
|
||||
// send out the frame.
|
||||
char* frame = context->h264_raw_stream.data() + start;
|
||||
|
||||
// it may be return error, but we must process all packets.
|
||||
if ((ret = __srs_write_h264_raw_frame(context, frame, size, dts, pts)) != ERROR_SUCCESS) {
|
||||
error_code_return = ret;
|
||||
|
||||
// ignore known error, process all packets.
|
||||
if (srs_h264_is_dvbsp_error(ret)
|
||||
|| srs_h264_is_duplicated_sps_error(ret)
|
||||
|| srs_h264_is_duplicated_pps_error(ret)
|
||||
) {
|
||||
continue;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
return error_code_return;
|
||||
}
|
||||
|
||||
srs_h264_bool srs_h264_is_dvbsp_error(int error_code)
|
||||
|
@ -1376,6 +1412,16 @@ srs_h264_bool srs_h264_is_dvbsp_error(int error_code)
|
|||
return error_code == ERROR_H264_DROP_BEFORE_SPS_PPS;
|
||||
}
|
||||
|
||||
srs_h264_bool srs_h264_is_duplicated_sps_error(int error_code)
|
||||
{
|
||||
return error_code == ERROR_H264_DUPLICATED_SPS;
|
||||
}
|
||||
|
||||
srs_h264_bool srs_h264_is_duplicated_pps_error(int error_code)
|
||||
{
|
||||
return error_code == ERROR_H264_DUPLICATED_PPS;
|
||||
}
|
||||
|
||||
int srs_h264_startswith_annexb(char* h264_raw_data, int h264_raw_size, int* pnb_start_code)
|
||||
{
|
||||
SrsStream stream;
|
||||
|
|
|
@ -445,7 +445,9 @@ typedef int srs_h264_bool;
|
|||
* @see https://github.com/winlinvip/simple-rtmp-server/issues/66
|
||||
*
|
||||
* @return 0, success; otherswise, failed.
|
||||
* for dvbsp error, check by srs_h264_is_dvbsp_error(error_code).
|
||||
* for dvbsp error, @see srs_h264_is_dvbsp_error().
|
||||
* for duplictated sps error, @see srs_h264_is_duplicated_sps_error().
|
||||
* for duplictated pps error, @see srs_h264_is_duplicated_pps_error().
|
||||
*/
|
||||
/**
|
||||
For the example file:
|
||||
|
@ -491,6 +493,20 @@ extern int srs_h264_write_raw_frames(srs_rtmp_t rtmp,
|
|||
*/
|
||||
extern srs_h264_bool srs_h264_is_dvbsp_error(int error_code);
|
||||
/**
|
||||
* whether error_code is duplicated sps error.
|
||||
*
|
||||
* @see https://github.com/winlinvip/simple-rtmp-server/issues/204
|
||||
* @example /trunk/research/librtmp/srs_h264_raw_publish.c
|
||||
*/
|
||||
extern srs_h264_bool srs_h264_is_duplicated_sps_error(int error_code);
|
||||
/**
|
||||
* whether error_code is duplicated pps error.
|
||||
*
|
||||
* @see https://github.com/winlinvip/simple-rtmp-server/issues/204
|
||||
* @example /trunk/research/librtmp/srs_h264_raw_publish.c
|
||||
*/
|
||||
extern srs_h264_bool srs_h264_is_duplicated_pps_error(int error_code);
|
||||
/**
|
||||
* whether h264 raw data starts with the annexb,
|
||||
* which bytes sequence matches N[00] 00 00 01, where N>=0.
|
||||
* @param h264_raw_data the input h264 raw data, a encoded h.264 I/P/B frame data.
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue