rtmp拉流的兼容性改进 (#1595)

* 修复play指令的bug

* 修改MSG_AGGREGATE的时间戳处理逻辑

这里参考了ffmpeg的方式来计算时间戳.

* add bom
This commit is contained in:
alexliyu7352 2022-04-28 14:13:09 +08:00 committed by GitHub
parent c31d44d680
commit c1d2adebae
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 12 additions and 3 deletions

View File

@ -214,7 +214,7 @@ inline void RtmpPlayer::send_createStream() {
inline void RtmpPlayer::send_play() { inline void RtmpPlayer::send_play() {
AMFEncoder enc; AMFEncoder enc;
enc << "play" << ++_send_req_id << nullptr << _stream_id << (double) _stream_index; enc << "play" << ++_send_req_id << nullptr << _stream_id << "-2000";
sendRequest(MSG_CMD, enc.data()); sendRequest(MSG_CMD, enc.data());
auto fun = [](AMFValue &val) { auto fun = [](AMFValue &val) {
//TraceL << "play onStatus"; //TraceL << "play onStatus";
@ -297,7 +297,8 @@ void RtmpPlayer::onCmd_onStatus(AMFDecoder &dec) {
auto level = val["level"]; auto level = val["level"];
auto code = val["code"].as_string(); auto code = val["code"].as_string();
if (level.type() == AMF_STRING) { if (level.type() == AMF_STRING) {
if (level.as_string() != "status") { // warning 不应该断开
if (level.as_string() != "status" && level.as_string() != "warning") {
throw std::runtime_error(StrPrinter << "onStatus 失败:" << level.as_string() << " " << code << endl); throw std::runtime_error(StrPrinter << "onStatus 失败:" << level.as_string() << " " << code << endl);
} }
} }

View File

@ -766,6 +766,9 @@ void RtmpProtocol::handle_chunk(RtmpPacket::Ptr packet) {
case MSG_AGGREGATE: { case MSG_AGGREGATE: {
auto ptr = (uint8_t *) chunk_data.buffer.data(); auto ptr = (uint8_t *) chunk_data.buffer.data();
auto ptr_tail = ptr + chunk_data.buffer.size(); auto ptr_tail = ptr + chunk_data.buffer.size();
uint32_t latest_ts, timestamp;
timestamp = chunk_data.time_stamp;
bool first_message = true;
while (ptr + 8 + 3 < ptr_tail) { while (ptr + 8 + 3 < ptr_tail) {
auto type = *ptr; auto type = *ptr;
ptr += 1; ptr += 1;
@ -781,12 +784,17 @@ void RtmpProtocol::handle_chunk(RtmpPacket::Ptr packet) {
if (ptr + size > ptr_tail) { if (ptr + size > ptr_tail) {
break; break;
} }
if (!first_message) {
timestamp += ts - latest_ts;
}
first_message = false;
latest_ts = ts;
auto sub_packet_ptr = RtmpPacket::create(); auto sub_packet_ptr = RtmpPacket::create();
auto &sub_packet = *sub_packet_ptr; auto &sub_packet = *sub_packet_ptr;
sub_packet.buffer.assign((char *)ptr, size); sub_packet.buffer.assign((char *)ptr, size);
sub_packet.type_id = type; sub_packet.type_id = type;
sub_packet.body_size = size; sub_packet.body_size = size;
sub_packet.time_stamp = ts; sub_packet.time_stamp = timestamp;
sub_packet.stream_index = chunk_data.stream_index; sub_packet.stream_index = chunk_data.stream_index;
sub_packet.chunk_id = chunk_data.chunk_id; sub_packet.chunk_id = chunk_data.chunk_id;
handle_chunk(std::move(sub_packet_ptr)); handle_chunk(std::move(sub_packet_ptr));