[feat] separate rtp send/receive module from ice transport module

This commit is contained in:
dijunkun
2025-01-03 17:34:46 +08:00
parent 7ddcca53e4
commit eef35ff0d4
18 changed files with 384 additions and 218 deletions

View File

@@ -0,0 +1 @@
#include "audio_channel_receive.h"

View File

@@ -0,0 +1,18 @@
/*
* @Author: DI JUNKUN
* @Date: 2025-01-03
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/
#ifndef _AUDIO_CHANNEL_RECEIVE_H_
#define _AUDIO_CHANNEL_RECEIVE_H_
class AudioChannelReceive {
public:
AudioChannelReceive();
~AudioChannelReceive();
public:
};
#endif

View File

@@ -0,0 +1 @@
#include "audio_channel_send.h"

View File

@@ -0,0 +1,18 @@
/*
* @Author: DI JUNKUN
* @Date: 2025-01-03
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/
#ifndef _AUDIO_CHANNEL_SEND_H_
#define _AUDIO_CHANNEL_SEND_H_
class AudioChannelSend {
public:
AudioChannelSend();
~AudioChannelSend();
public:
};
#endif

View File

@@ -0,0 +1 @@
#include "data_channel_receive.h"

View File

@@ -0,0 +1,18 @@
/*
* @Author: DI JUNKUN
* @Date: 2025-01-03
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/
#ifndef _DATA_CHANNEL_RECEIVE_H_
#define _DATA_CHANNEL_RECEIVE_H_
class DataChannelReceive {
public:
DataChannelReceive();
~DataChannelReceive();
public:
};
#endif

View File

@@ -0,0 +1 @@
#include "data_channel_send.h"

View File

@@ -0,0 +1,18 @@
/*
* @Author: DI JUNKUN
* @Date: 2025-01-03
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/
#ifndef _DATA_CHANNEL_SEND_H_
#define _DATA_CHANNEL_SEND_H_
class DataChannelSend {
public:
DataChannelSend();
~DataChannelSend();
public:
};
#endif

View File

@@ -0,0 +1 @@
#include "video_channel_receive.h"

View File

@@ -0,0 +1,18 @@
/*
* @Author: DI JUNKUN
* @Date: 2025-01-03
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/
#ifndef _VIDEO_CHANNEL_RECEIVE_H_
#define _VIDEO_CHANNEL_RECEIVE_H_
class VideoChannelReceive {
public:
VideoChannelReceive();
~VideoChannelReceive();
public:
};
#endif

View File

@@ -0,0 +1,50 @@
#include "video_channel_send.h"
VideoChannelSend::VideoChannelSend() {}
VideoChannelSend::~VideoChannelSend() {}
void VideoChannelSend::Initialize(RtpPacket::PAYLOAD_TYPE negotiated_video_pt) {
video_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_video_pt);
rtp_video_sender_ = std::make_unique<RtpVideoSender>(ice_io_statistics_);
rtp_video_sender_->SetSendDataFunc(
[this](const char *data, size_t size) -> int {
if (!ice_agent_) {
LOG_ERROR("ice_agent_ is nullptr");
return -1;
}
if (state_ != NICE_COMPONENT_STATE_CONNECTED &&
state_ != NICE_COMPONENT_STATE_READY) {
LOG_ERROR("Ice is not connected, state = [{}]",
nice_component_state_to_string(state_));
return -2;
}
ice_io_statistics_->UpdateVideoOutboundBytes((uint32_t)size);
return ice_agent_->Send(data, size);
});
rtp_video_sender_->Start();
}
void VideoChannelSend::Destroy() {
if (rtp_video_sender_) {
rtp_video_sender_->Stop();
}
}
int VideoChannelSend::SendVideo(char *encoded_frame, size_t size) {
std::vector<RtpPacket> packets;
if (rtp_video_sender_) {
if (video_rtp_codec_) {
video_rtp_codec_->Encode(
static_cast<RtpCodec::VideoFrameType>(frame_type),
(uint8_t *)encoded_frame, (uint32_t)size, packets);
}
rtp_video_sender_->Enqueue(packets);
}
return 0;
}

View File

@@ -0,0 +1,29 @@
/*
* @Author: DI JUNKUN
* @Date: 2025-01-03
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/
#ifndef _VIDEO_CHANNEL_SEND_H_
#define _VIDEO_CHANNEL_SEND_H_
#include "rtp_codec.h"
#include "rtp_video_sender.h"
class VideoChannelSend {
public:
VideoChannelSend();
~VideoChannelSend();
public:
void Initialize(RtpPacket::PAYLOAD_TYPE negotiated_video_pt);
void Destroy();
int SendVideo(char *encoded_frame, size_t size);
private:
std::unique_ptr<RtpCodec> video_rtp_codec_ = nullptr;
std::unique_ptr<RtpVideoSender> rtp_video_sender_ = nullptr;
};
#endif

View File

@@ -140,24 +140,24 @@ int PeerConnection::Init(PeerConnectionParams params,
user_id.size(), user_data_); user_id.size(), user_data_);
} else if ("connected" == ice_status) { } else if ("connected" == ice_status) {
// std::string transmission_id = std::string(user_id, user_id_size); // std::string transmission_id = std::string(user_id, user_id_size);
// is_ice_transmission_ready_[user_id] = true; // is_ice_transport_ready_[user_id] = true;
// on_connection_status_(ConnectionStatus::Connected, user_id.data(), // on_connection_status_(ConnectionStatus::Connected, user_id.data(),
// user_id.size(), user_data_); // user_id.size(), user_data_);
// b_force_i_frame_ = true; // b_force_i_frame_ = true;
LOG_INFO("Ice connected"); LOG_INFO("Ice connected");
} else if ("ready" == ice_status) { } else if ("ready" == ice_status) {
is_ice_transmission_ready_[user_id] = true; is_ice_transport_ready_[user_id] = true;
b_force_i_frame_ = true; b_force_i_frame_ = true;
LOG_INFO("Ice ready"); LOG_INFO("Ice ready");
on_connection_status_(ConnectionStatus::Connected, user_id.data(), on_connection_status_(ConnectionStatus::Connected, user_id.data(),
user_id.size(), user_data_); user_id.size(), user_data_);
} else if ("closed" == ice_status) { } else if ("closed" == ice_status) {
is_ice_transmission_ready_[user_id] = false; is_ice_transport_ready_[user_id] = false;
LOG_INFO("Ice closed"); LOG_INFO("Ice closed");
on_connection_status_(ConnectionStatus::Closed, user_id.data(), on_connection_status_(ConnectionStatus::Closed, user_id.data(),
user_id.size(), user_data_); user_id.size(), user_data_);
} else if ("failed" == ice_status) { } else if ("failed" == ice_status) {
is_ice_transmission_ready_[user_id] = false; is_ice_transport_ready_[user_id] = false;
if (offer_peer_ && try_rejoin_with_turn_) { if (offer_peer_ && try_rejoin_with_turn_) {
enable_turn_ = true; enable_turn_ = true;
reliable_ice_ = false; reliable_ice_ = false;
@@ -179,7 +179,7 @@ int PeerConnection::Init(PeerConnectionParams params,
user_id.size(), user_data_); user_id.size(), user_data_);
} }
} else { } else {
is_ice_transmission_ready_[user_id] = false; is_ice_transport_ready_[user_id] = false;
LOG_INFO("Unknown ice state [{}]", ice_status); LOG_INFO("Unknown ice state [{}]", ice_status);
} }
}; };
@@ -298,7 +298,7 @@ int PeerConnection::Leave(const std::string &transmission_id) {
transmission_id); transmission_id);
} }
is_ice_transmission_ready_[user_id_] = false; is_ice_transport_ready_[user_id_] = false;
leave_ = true; leave_ = true;
ReleaseAllIceTransmission(); ReleaseAllIceTransmission();
@@ -306,11 +306,11 @@ int PeerConnection::Leave(const std::string &transmission_id) {
} }
int PeerConnection::ReleaseAllIceTransmission() { int PeerConnection::ReleaseAllIceTransmission() {
for (auto &user_id_it : ice_transmission_list_) { for (auto &user_id_it : ice_transport_list_) {
user_id_it.second->DestroyIceTransmission(); user_id_it.second->DestroyIceTransmission();
} }
ice_transmission_list_.clear(); ice_transport_list_.clear();
is_ice_transmission_ready_.clear(); is_ice_transport_ready_.clear();
return 0; return 0;
} }
@@ -349,12 +349,12 @@ SignalStatus PeerConnection::GetSignalStatus() {
} }
int PeerConnection::SendVideoFrame(const XVideoFrame *video_frame) { int PeerConnection::SendVideoFrame(const XVideoFrame *video_frame) {
if (ice_transmission_list_.empty()) { if (ice_transport_list_.empty()) {
return -1; return -1;
} }
for (auto &ice_trans : ice_transmission_list_) { for (auto &ice_trans : ice_transport_list_) {
if (!is_ice_transmission_ready_[ice_trans.first]) { if (!is_ice_transport_ready_[ice_trans.first]) {
continue; continue;
} }
@@ -365,12 +365,12 @@ int PeerConnection::SendVideoFrame(const XVideoFrame *video_frame) {
} }
int PeerConnection::SendAudioFrame(const char *data, size_t size) { int PeerConnection::SendAudioFrame(const char *data, size_t size) {
if (ice_transmission_list_.empty()) { if (ice_transport_list_.empty()) {
return -1; return -1;
} }
for (auto &ice_trans : ice_transmission_list_) { for (auto &ice_trans : ice_transport_list_) {
if (!is_ice_transmission_ready_[ice_trans.first]) { if (!is_ice_transport_ready_[ice_trans.first]) {
continue; continue;
} }
ice_trans.second->SendAudioFrame(data, size); ice_trans.second->SendAudioFrame(data, size);
@@ -380,8 +380,8 @@ int PeerConnection::SendAudioFrame(const char *data, size_t size) {
} }
int PeerConnection::SendDataFrame(const char *data, size_t size) { int PeerConnection::SendDataFrame(const char *data, size_t size) {
for (auto &ice_trans : ice_transmission_list_) { for (auto &ice_trans : ice_transport_list_) {
if (!is_ice_transmission_ready_[ice_trans.first]) { if (!is_ice_transport_ready_[ice_trans.first]) {
continue; continue;
} }
ice_trans.second->SendDataFrame(data, size); ice_trans.second->SendDataFrame(data, size);
@@ -594,31 +594,30 @@ void PeerConnection::ProcessIceWorkMsg(const IceWorkMsg &msg) {
LOG_INFO("]"); LOG_INFO("]");
for (auto &remote_user_id : user_id_list) { for (auto &remote_user_id : user_id_list) {
ice_transmission_list_[remote_user_id] = ice_transport_list_[remote_user_id] = std::make_unique<IceTransport>(
std::make_unique<IceTransmission>(
true, transmission_id, user_id_, remote_user_id, ws_transport_, true, transmission_id, user_id_, remote_user_id, ws_transport_,
on_ice_status_change_, user_data_); on_ice_status_change_, user_data_);
ice_transmission_list_[remote_user_id]->SetLocalCapabilities( ice_transport_list_[remote_user_id]->SetLocalCapabilities(
hardware_acceleration_, trickle_ice_, reliable_ice_, enable_turn_, hardware_acceleration_, trickle_ice_, reliable_ice_, enable_turn_,
false, video_payload_types_, audio_payload_types_); false, video_payload_types_, audio_payload_types_);
ice_transmission_list_[remote_user_id]->SetOnReceiveVideoFunc( ice_transport_list_[remote_user_id]->SetOnReceiveVideoFunc(
on_receive_video_frame_); on_receive_video_frame_);
ice_transmission_list_[remote_user_id]->SetOnReceiveAudioFunc( ice_transport_list_[remote_user_id]->SetOnReceiveAudioFunc(
on_receive_audio_buffer_); on_receive_audio_buffer_);
ice_transmission_list_[remote_user_id]->SetOnReceiveDataFunc( ice_transport_list_[remote_user_id]->SetOnReceiveDataFunc(
on_receive_data_buffer_); on_receive_data_buffer_);
ice_transmission_list_[remote_user_id]->SetOnReceiveNetStatusReportFunc( ice_transport_list_[remote_user_id]->SetOnReceiveNetStatusReportFunc(
net_status_report_); net_status_report_);
ice_transmission_list_[remote_user_id]->InitIceTransmission( ice_transport_list_[remote_user_id]->InitIceTransmission(
cfg_stun_server_ip_, stun_server_port_, cfg_turn_server_ip_, cfg_stun_server_ip_, stun_server_port_, cfg_turn_server_ip_,
turn_server_port_, cfg_turn_server_username_, turn_server_port_, cfg_turn_server_username_,
cfg_turn_server_password_, cfg_turn_server_password_,
av1_encoding_ ? RtpPacket::AV1 : RtpPacket::H264); av1_encoding_ ? RtpPacket::AV1 : RtpPacket::H264);
ice_transmission_list_[remote_user_id]->JoinTransmission(); ice_transport_list_[remote_user_id]->JoinTransmission();
} }
break; break;
@@ -627,11 +626,11 @@ void PeerConnection::ProcessIceWorkMsg(const IceWorkMsg &msg) {
std::string user_id = msg.user_id; std::string user_id = msg.user_id;
LOG_INFO("Receive notification: user id [{}] leave transmission", LOG_INFO("Receive notification: user id [{}] leave transmission",
user_id); user_id);
auto user_id_it = ice_transmission_list_.find(user_id); auto user_id_it = ice_transport_list_.find(user_id);
if (user_id_it != ice_transmission_list_.end()) { if (user_id_it != ice_transport_list_.end()) {
user_id_it->second->DestroyIceTransmission(); user_id_it->second->DestroyIceTransmission();
ice_transmission_list_.erase(user_id_it); ice_transport_list_.erase(user_id_it);
is_ice_transmission_ready_[user_id] = false; is_ice_transport_ready_[user_id] = false;
LOG_INFO("Terminate transmission to user [{}]", user_id); LOG_INFO("Terminate transmission to user [{}]", user_id);
} }
break; break;
@@ -639,40 +638,37 @@ void PeerConnection::ProcessIceWorkMsg(const IceWorkMsg &msg) {
case IceWorkMsg::Type::Offer: { case IceWorkMsg::Type::Offer: {
std::string transmission_id = msg.transmission_id; std::string transmission_id = msg.transmission_id;
std::string remote_user_id = msg.remote_user_id; std::string remote_user_id = msg.remote_user_id;
if (ice_transmission_list_.end() == if (ice_transport_list_.end() ==
ice_transmission_list_.find(remote_user_id)) { ice_transport_list_.find(remote_user_id)) {
// Enable TURN for answer peer by default // Enable TURN for answer peer by default
ice_transmission_list_[remote_user_id] = ice_transport_list_[remote_user_id] = std::make_unique<IceTransport>(
std::make_unique<IceTransmission>(
false, transmission_id, user_id_, remote_user_id, ws_transport_, false, transmission_id, user_id_, remote_user_id, ws_transport_,
on_ice_status_change_, user_data_); on_ice_status_change_, user_data_);
ice_transmission_list_[remote_user_id]->SetLocalCapabilities( ice_transport_list_[remote_user_id]->SetLocalCapabilities(
hardware_acceleration_, trickle_ice_, reliable_ice_, enable_turn_, hardware_acceleration_, trickle_ice_, reliable_ice_, enable_turn_,
false, video_payload_types_, audio_payload_types_); false, video_payload_types_, audio_payload_types_);
ice_transmission_list_[remote_user_id]->SetOnReceiveVideoFunc( ice_transport_list_[remote_user_id]->SetOnReceiveVideoFunc(
on_receive_video_frame_); on_receive_video_frame_);
ice_transmission_list_[remote_user_id]->SetOnReceiveAudioFunc( ice_transport_list_[remote_user_id]->SetOnReceiveAudioFunc(
on_receive_audio_buffer_); on_receive_audio_buffer_);
ice_transmission_list_[remote_user_id]->SetOnReceiveDataFunc( ice_transport_list_[remote_user_id]->SetOnReceiveDataFunc(
on_receive_data_buffer_); on_receive_data_buffer_);
ice_transmission_list_[remote_user_id]->SetOnReceiveNetStatusReportFunc( ice_transport_list_[remote_user_id]->SetOnReceiveNetStatusReportFunc(
net_status_report_); net_status_report_);
ice_transmission_list_[remote_user_id]->InitIceTransmission( ice_transport_list_[remote_user_id]->InitIceTransmission(
cfg_stun_server_ip_, stun_server_port_, cfg_turn_server_ip_, cfg_stun_server_ip_, stun_server_port_, cfg_turn_server_ip_,
turn_server_port_, cfg_turn_server_username_, turn_server_port_, cfg_turn_server_username_,
cfg_turn_server_password_, cfg_turn_server_password_,
av1_encoding_ ? RtpPacket::AV1 : RtpPacket::H264); av1_encoding_ ? RtpPacket::AV1 : RtpPacket::H264);
ice_transmission_list_[remote_user_id]->SetTransmissionId( ice_transport_list_[remote_user_id]->SetTransmissionId(transmission_id);
transmission_id);
} }
std::string remote_sdp = msg.remote_sdp; std::string remote_sdp = msg.remote_sdp;
int ret = int ret = ice_transport_list_[remote_user_id]->SetRemoteSdp(remote_sdp);
ice_transmission_list_[remote_user_id]->SetRemoteSdp(remote_sdp);
if (0 != ret) { if (0 != ret) {
NegotiationFailed(); NegotiationFailed();
break; break;
@@ -680,19 +676,18 @@ void PeerConnection::ProcessIceWorkMsg(const IceWorkMsg &msg) {
if (trickle_ice_) { if (trickle_ice_) {
sdp_without_cands_ = remote_sdp; sdp_without_cands_ = remote_sdp;
ice_transmission_list_[remote_user_id]->SendAnswer(); ice_transport_list_[remote_user_id]->SendAnswer();
} }
ice_transmission_list_[remote_user_id]->GatherCandidates(); ice_transport_list_[remote_user_id]->GatherCandidates();
break; break;
} }
case IceWorkMsg::Type::Answer: { case IceWorkMsg::Type::Answer: {
std::string remote_user_id = msg.remote_user_id; std::string remote_user_id = msg.remote_user_id;
std::string remote_sdp = msg.remote_sdp; std::string remote_sdp = msg.remote_sdp;
if (ice_transmission_list_.find(remote_user_id) != if (ice_transport_list_.find(remote_user_id) !=
ice_transmission_list_.end()) { ice_transport_list_.end()) {
int ret = int ret = ice_transport_list_[remote_user_id]->SetRemoteSdp(remote_sdp);
ice_transmission_list_[remote_user_id]->SetRemoteSdp(remote_sdp);
if (0 != ret) { if (0 != ret) {
Leave(remote_transmission_id_); Leave(remote_transmission_id_);
break; break;
@@ -700,7 +695,7 @@ void PeerConnection::ProcessIceWorkMsg(const IceWorkMsg &msg) {
if (trickle_ice_) { if (trickle_ice_) {
sdp_without_cands_ = remote_sdp; sdp_without_cands_ = remote_sdp;
ice_transmission_list_[remote_user_id]->GatherCandidates(); ice_transport_list_[remote_user_id]->GatherCandidates();
} }
} }
@@ -714,10 +709,10 @@ void PeerConnection::ProcessIceWorkMsg(const IceWorkMsg &msg) {
// LOG_INFO("[{}] receive new candidate from [{}]:[{}]", user_id_, // LOG_INFO("[{}] receive new candidate from [{}]:[{}]", user_id_,
// remote_user_id, new_candidate); // remote_user_id, new_candidate);
if (ice_transmission_list_.find(remote_user_id) != if (ice_transport_list_.find(remote_user_id) !=
ice_transmission_list_.end()) { ice_transport_list_.end()) {
ice_transmission_list_[remote_user_id]->SetRemoteSdp( ice_transport_list_[remote_user_id]->SetRemoteSdp(sdp_without_cands_ +
sdp_without_cands_ + new_candidate); new_candidate);
} }
break; break;
} }

View File

@@ -13,7 +13,7 @@
#include "audio_decoder.h" #include "audio_decoder.h"
#include "audio_encoder.h" #include "audio_encoder.h"
#include "ice_transmission.h" #include "ice_transport.h"
#include "video_decoder_factory.h" #include "video_decoder_factory.h"
#include "video_encoder_factory.h" #include "video_encoder_factory.h"
#include "ws_client.h" #include "ws_client.h"
@@ -169,9 +169,8 @@ class PeerConnection {
std::string sdp_without_cands_ = ""; std::string sdp_without_cands_ = "";
private: private:
std::map<std::string, std::unique_ptr<IceTransmission>> std::map<std::string, std::unique_ptr<IceTransport>> ice_transport_list_;
ice_transmission_list_; std::map<std::string, bool> is_ice_transport_ready_;
std::map<std::string, bool> is_ice_transmission_ready_;
std::function<void(std::string, const std::string &)> on_ice_status_change_ = std::function<void(std::string, const std::string &)> on_ice_status_change_ =
nullptr; nullptr;

View File

@@ -1,4 +1,4 @@
#include "ice_transmission.h" #include "ice_transport.h"
#include <chrono> #include <chrono>
#include <map> #include <map>
@@ -14,7 +14,7 @@
using nlohmann::json; using nlohmann::json;
IceTransmission::IceTransmission( IceTransport::IceTransport(
bool offer_peer, std::string &transmission_id, std::string &user_id, bool offer_peer, std::string &transmission_id, std::string &user_id,
std::string &remote_user_id, std::shared_ptr<WsClient> ice_ws_transmission, std::string &remote_user_id, std::shared_ptr<WsClient> ice_ws_transmission,
std::function<void(std::string, const std::string &)> on_ice_status_change, std::function<void(std::string, const std::string &)> on_ice_status_change,
@@ -27,7 +27,7 @@ IceTransmission::IceTransmission(
on_ice_status_change_(on_ice_status_change), on_ice_status_change_(on_ice_status_change),
user_data_(user_data) {} user_data_(user_data) {}
IceTransmission::~IceTransmission() { IceTransport::~IceTransport() {
user_data_ = nullptr; user_data_ = nullptr;
video_codec_inited_ = false; video_codec_inited_ = false;
audio_codec_inited_ = false; audio_codec_inited_ = false;
@@ -41,9 +41,11 @@ IceTransmission::~IceTransmission() {
#endif #endif
} }
int IceTransmission::SetLocalCapabilities( int IceTransport::SetLocalCapabilities(bool hardware_acceleration,
bool hardware_acceleration, bool use_trickle_ice, bool use_reliable_ice, bool use_trickle_ice,
bool enable_turn, bool force_turn, std::vector<int> &video_payload_types, bool use_reliable_ice, bool enable_turn,
bool force_turn,
std::vector<int> &video_payload_types,
std::vector<int> &audio_payload_types) { std::vector<int> &audio_payload_types) {
hardware_acceleration_ = hardware_acceleration; hardware_acceleration_ = hardware_acceleration;
use_trickle_ice_ = use_trickle_ice; use_trickle_ice_ = use_trickle_ice;
@@ -56,7 +58,7 @@ int IceTransmission::SetLocalCapabilities(
return 0; return 0;
} }
int IceTransmission::InitIceTransmission( int IceTransport::InitIceTransmission(
std::string &stun_ip, int stun_port, std::string &turn_ip, int turn_port, std::string &stun_ip, int stun_port, std::string &turn_ip, int turn_port,
std::string &turn_username, std::string &turn_password, std::string &turn_username, std::string &turn_password,
RtpPacket::PAYLOAD_TYPE video_codec_payload_type) { RtpPacket::PAYLOAD_TYPE video_codec_payload_type) {
@@ -246,56 +248,50 @@ int IceTransmission::InitIceTransmission(
[]([[maybe_unused]] NiceAgent *agent, [[maybe_unused]] guint stream_id, []([[maybe_unused]] NiceAgent *agent, [[maybe_unused]] guint stream_id,
[[maybe_unused]] guint component_id, NiceComponentState state, [[maybe_unused]] guint component_id, NiceComponentState state,
gpointer user_ptr) { gpointer user_ptr) {
if (user_ptr) { if (auto ice_transport = static_cast<IceTransport *>(user_ptr)) {
IceTransmission *ice_transmission_obj = if (!ice_transport->is_closed_) {
static_cast<IceTransmission *>(user_ptr); LOG_INFO("[{}->{}] state_change: {}", ice_transport->user_id_,
if (!ice_transmission_obj->is_closed_) { ice_transport->remote_user_id_,
LOG_INFO("[{}->{}] state_change: {}",
ice_transmission_obj->user_id_,
ice_transmission_obj->remote_user_id_,
nice_component_state_to_string(state)); nice_component_state_to_string(state));
ice_transmission_obj->state_ = state; ice_transport->state_ = state;
if (state == NICE_COMPONENT_STATE_READY || if (state == NICE_COMPONENT_STATE_READY ||
state == NICE_COMPONENT_STATE_CONNECTED) { state == NICE_COMPONENT_STATE_CONNECTED) {
ice_transmission_obj->ice_io_statistics_->Start(); ice_transport->ice_io_statistics_->Start();
} }
ice_transmission_obj->on_ice_status_change_( ice_transport->on_ice_status_change_(
nice_component_state_to_string(state), nice_component_state_to_string(state),
ice_transmission_obj->remote_user_id_); ice_transport->remote_user_id_);
} }
} }
}, },
[](NiceAgent *agent, guint stream_id, guint component_id, [](NiceAgent *agent, guint stream_id, guint component_id,
gchar *foundation, gpointer user_ptr) { gchar *foundation, gpointer user_ptr) {
if (user_ptr) { if (auto ice_transport = static_cast<IceTransport *>(user_ptr)) {
IceTransmission *ice_transmission_obj = if (ice_transport->use_trickle_ice_) {
static_cast<IceTransmission *>(user_ptr);
if (ice_transmission_obj->use_trickle_ice_) {
GSList *cands = GSList *cands =
nice_agent_get_local_candidates(agent, stream_id, component_id); nice_agent_get_local_candidates(agent, stream_id, component_id);
NiceCandidate *cand; NiceCandidate *cand;
for (GSList *i = cands; i; i = i->next) { for (GSList *i = cands; i; i = i->next) {
cand = (NiceCandidate *)i->data; cand = (NiceCandidate *)i->data;
if (g_strcmp0(cand->foundation, foundation) == 0) { if (g_strcmp0(cand->foundation, foundation) == 0) {
ice_transmission_obj->new_local_candidate_ = ice_transport->new_local_candidate_ =
nice_agent_generate_local_candidate_sdp(agent, cand); nice_agent_generate_local_candidate_sdp(agent, cand);
json message = { json message = {
{"type", "new_candidate"}, {"type", "new_candidate"},
{"transmission_id", ice_transmission_obj->transmission_id_}, {"transmission_id", ice_transport->transmission_id_},
{"user_id", ice_transmission_obj->user_id_}, {"user_id", ice_transport->user_id_},
{"remote_user_id", ice_transmission_obj->remote_user_id_}, {"remote_user_id", ice_transport->remote_user_id_},
{"sdp", ice_transmission_obj->new_local_candidate_}}; {"sdp", ice_transport->new_local_candidate_}};
// LOG_INFO("[{}] Send new candidate to [{}]]:[{}]", // LOG_INFO("[{}] Send new candidate to [{}]]:[{}]",
// ice_transmission_obj->user_id_, // ice_transport->user_id_,
// ice_transmission_obj->remote_user_id_, // ice_transport->remote_user_id_,
// ice_transmission_obj->new_local_candidate_); // ice_transport->new_local_candidate_);
if (ice_transmission_obj->ice_ws_transport_) { if (ice_transport->ice_ws_transport_) {
ice_transmission_obj->ice_ws_transport_->Send(message.dump()); ice_transport->ice_ws_transport_->Send(message.dump());
} }
} }
} }
@@ -307,17 +303,15 @@ int IceTransmission::InitIceTransmission(
[]([[maybe_unused]] NiceAgent *agent, [[maybe_unused]] guint stream_id, []([[maybe_unused]] NiceAgent *agent, [[maybe_unused]] guint stream_id,
gpointer user_ptr) { gpointer user_ptr) {
// non-trickle // non-trickle
if (user_ptr) { if (auto ice_transport = static_cast<IceTransport *>(user_ptr)) {
IceTransmission *ice_transmission_obj = LOG_INFO("[{}->{}] gather_done", ice_transport->user_id_,
static_cast<IceTransmission *>(user_ptr); ice_transport->remote_user_id_);
LOG_INFO("[{}->{}] gather_done", ice_transmission_obj->user_id_,
ice_transmission_obj->remote_user_id_);
if (!ice_transmission_obj->use_trickle_ice_) { if (!ice_transport->use_trickle_ice_) {
if (ice_transmission_obj->offer_peer_) { if (ice_transport->offer_peer_) {
ice_transmission_obj->SendOffer(); ice_transport->SendOffer();
} else { } else {
ice_transmission_obj->SendAnswer(); ice_transport->SendAnswer();
} }
} }
} }
@@ -329,49 +323,43 @@ int IceTransmission::InitIceTransmission(
NiceCandidate *remote = nullptr; NiceCandidate *remote = nullptr;
nice_agent_get_selected_pair(agent, stream_id, component_id, &local, nice_agent_get_selected_pair(agent, stream_id, component_id, &local,
&remote); &remote);
if (user_ptr) { if (auto ice_transport = static_cast<IceTransport *>(user_ptr)) {
IceTransmission *ice_transmission_obj =
static_cast<IceTransmission *>(user_ptr);
if (local->type == NICE_CANDIDATE_TYPE_RELAYED && if (local->type == NICE_CANDIDATE_TYPE_RELAYED &&
remote->type == NICE_CANDIDATE_TYPE_RELAYED) { remote->type == NICE_CANDIDATE_TYPE_RELAYED) {
LOG_INFO("Traversal using relay server"); LOG_INFO("Traversal using relay server");
ice_transmission_obj->traversal_type_ = TraversalType::TRelay; ice_transport->traversal_type_ = TraversalType::TRelay;
} else { } else {
LOG_INFO("Traversal using p2p"); LOG_INFO("Traversal using p2p");
ice_transmission_obj->traversal_type_ = TraversalType::TP2P; ice_transport->traversal_type_ = TraversalType::TP2P;
} }
XNetTrafficStats net_traffic_stats; XNetTrafficStats net_traffic_stats;
memset(&net_traffic_stats, 0, sizeof(net_traffic_stats)); memset(&net_traffic_stats, 0, sizeof(net_traffic_stats));
ice_transmission_obj->on_receive_net_status_report_( ice_transport->on_receive_net_status_report_(
ice_transmission_obj->user_id_.data(), ice_transport->user_id_.data(), ice_transport->user_id_.size(),
ice_transmission_obj->user_id_.size(), TraversalMode(ice_transport->traversal_type_), &net_traffic_stats,
TraversalMode(ice_transmission_obj->traversal_type_), ice_transport->remote_user_id_.data(),
&net_traffic_stats, ice_transmission_obj->remote_user_id_.data(), ice_transport->remote_user_id_.size(), ice_transport->user_data_);
ice_transmission_obj->remote_user_id_.size(),
ice_transmission_obj->user_data_);
} }
}, },
[]([[maybe_unused]] NiceAgent *agent, [[maybe_unused]] guint stream_id, []([[maybe_unused]] NiceAgent *agent, [[maybe_unused]] guint stream_id,
[[maybe_unused]] guint component_id, guint size, gchar *buffer, [[maybe_unused]] guint component_id, guint size, gchar *buffer,
gpointer user_ptr) { gpointer user_ptr) {
if (user_ptr) { if (auto ice_transport = static_cast<IceTransport *>(user_ptr)) {
IceTransmission *ice_transmission_obj = if (ice_transport && !ice_transport->is_closed_) {
static_cast<IceTransmission *>(user_ptr); if (ice_transport->CheckIsRtpPacket(buffer, size)) {
if (ice_transmission_obj && !ice_transmission_obj->is_closed_) { if (ice_transport->CheckIsVideoPacket(buffer, size)) {
if (ice_transmission_obj->CheckIsVideoPacket(buffer, size)) {
RtpPacket packet((uint8_t *)buffer, size); RtpPacket packet((uint8_t *)buffer, size);
ice_transmission_obj->rtp_video_receiver_->InsertRtpPacket( ice_transport->rtp_video_receiver_->InsertRtpPacket(packet);
packet); } else if (ice_transport->CheckIsAudioPacket(buffer, size)) {
} else if (ice_transmission_obj->CheckIsAudioPacket(buffer, size)) {
RtpPacket packet((uint8_t *)buffer, size); RtpPacket packet((uint8_t *)buffer, size);
ice_transmission_obj->rtp_audio_receiver_->InsertRtpPacket( ice_transport->rtp_audio_receiver_->InsertRtpPacket(packet);
packet); } else if (ice_transport->CheckIsDataPacket(buffer, size)) {
} else if (ice_transmission_obj->CheckIsDataPacket(buffer, size)) {
RtpPacket packet((uint8_t *)buffer, size); RtpPacket packet((uint8_t *)buffer, size);
ice_transmission_obj->rtp_data_receiver_->InsertRtpPacket(packet); ice_transport->rtp_data_receiver_->InsertRtpPacket(packet);
} else if (ice_transmission_obj->CheckIsRtcpPacket(buffer, size)) { }
// LOG_ERROR("Rtcp packet [{}]", (uint8_t)(buffer[1])); } else if (ice_transport->CheckIsRtcpPacket(buffer, size)) {
LOG_ERROR("Rtcp packet [{}]", (uint8_t)(buffer[1]));
} else { } else {
LOG_ERROR("Unknown packet"); LOG_ERROR("Unknown packet");
} }
@@ -382,7 +370,7 @@ int IceTransmission::InitIceTransmission(
return 0; return 0;
} }
int IceTransmission::DestroyIceTransmission() { int IceTransport::DestroyIceTransmission() {
LOG_INFO("[{}->{}] Destroy ice transmission", user_id_, remote_user_id_); LOG_INFO("[{}->{}] Destroy ice transmission", user_id_, remote_user_id_);
is_closed_ = true; is_closed_ = true;
@@ -413,14 +401,14 @@ int IceTransmission::DestroyIceTransmission() {
return ice_agent_->DestroyIceAgent(); return ice_agent_->DestroyIceAgent();
} }
int IceTransmission::CreateMediaCodec() { int IceTransport::CreateMediaCodec() {
video_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_video_pt_); video_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_video_pt_);
audio_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_audio_pt_); audio_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_audio_pt_);
data_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_data_pt_); data_rtp_codec_ = std::make_unique<RtpCodec>(negotiated_data_pt_);
return 0; return 0;
} }
int IceTransmission::CreateVideoCodec(RtpPacket::PAYLOAD_TYPE video_pt, int IceTransport::CreateVideoCodec(RtpPacket::PAYLOAD_TYPE video_pt,
bool hardware_acceleration) { bool hardware_acceleration) {
if (video_codec_inited_) { if (video_codec_inited_) {
return 0; return 0;
@@ -493,7 +481,7 @@ int IceTransmission::CreateVideoCodec(RtpPacket::PAYLOAD_TYPE video_pt,
return 0; return 0;
} }
int IceTransmission::CreateAudioCodec() { int IceTransport::CreateAudioCodec() {
if (audio_codec_inited_) { if (audio_codec_inited_) {
return 0; return 0;
} }
@@ -517,13 +505,13 @@ int IceTransmission::CreateAudioCodec() {
return 0; return 0;
} }
int IceTransmission::SetTransmissionId(const std::string &transmission_id) { int IceTransport::SetTransmissionId(const std::string &transmission_id) {
transmission_id_ = transmission_id; transmission_id_ = transmission_id;
return 0; return 0;
} }
int IceTransmission::JoinTransmission() { int IceTransport::JoinTransmission() {
LOG_INFO("[{}] Join transmission", user_id_); LOG_INFO("[{}] Join transmission", user_id_);
if (use_trickle_ice_) { if (use_trickle_ice_) {
@@ -534,7 +522,7 @@ int IceTransmission::JoinTransmission() {
return 0; return 0;
} }
int IceTransmission::GatherCandidates() { int IceTransport::GatherCandidates() {
int ret = ice_agent_->GatherCandidates(); int ret = ice_agent_->GatherCandidates();
if (ret < 0) { if (ret < 0) {
LOG_ERROR("Gather candidates failed"); LOG_ERROR("Gather candidates failed");
@@ -542,7 +530,7 @@ int IceTransmission::GatherCandidates() {
return 0; return 0;
} }
int IceTransmission::SetRemoteSdp(const std::string &remote_sdp) { int IceTransport::SetRemoteSdp(const std::string &remote_sdp) {
std::string media_stream_sdp = GetRemoteCapabilities(remote_sdp); std::string media_stream_sdp = GetRemoteCapabilities(remote_sdp);
if (media_stream_sdp.empty()) { if (media_stream_sdp.empty()) {
LOG_ERROR("Set remote sdp failed due to negotiation failed"); LOG_ERROR("Set remote sdp failed due to negotiation failed");
@@ -556,7 +544,7 @@ int IceTransmission::SetRemoteSdp(const std::string &remote_sdp) {
return 0; return 0;
} }
int IceTransmission::SendOffer() { int IceTransport::SendOffer() {
local_sdp_ = ice_agent_->GenerateLocalSdp(); local_sdp_ = ice_agent_->GenerateLocalSdp();
AppendLocalCapabilitiesToOffer(local_sdp_); AppendLocalCapabilitiesToOffer(local_sdp_);
json message = {{"type", "offer"}, json message = {{"type", "offer"},
@@ -572,7 +560,7 @@ int IceTransmission::SendOffer() {
return 0; return 0;
} }
int IceTransmission::SendAnswer() { int IceTransport::SendAnswer() {
local_sdp_ = ice_agent_->GenerateLocalSdp(); local_sdp_ = ice_agent_->GenerateLocalSdp();
AppendLocalCapabilitiesToAnswer(local_sdp_); AppendLocalCapabilitiesToAnswer(local_sdp_);
json message = {{"type", "answer"}, json message = {{"type", "answer"},
@@ -589,7 +577,7 @@ int IceTransmission::SendAnswer() {
return 0; return 0;
} }
int IceTransmission::AppendLocalCapabilitiesToOffer( int IceTransport::AppendLocalCapabilitiesToOffer(
const std::string &remote_sdp) { const std::string &remote_sdp) {
std::string preferred_video_pt; std::string preferred_video_pt;
std::string to_replace = "ICE/SDP"; std::string to_replace = "ICE/SDP";
@@ -647,7 +635,7 @@ int IceTransmission::AppendLocalCapabilitiesToOffer(
return 0; return 0;
} }
int IceTransmission::AppendLocalCapabilitiesToAnswer( int IceTransport::AppendLocalCapabilitiesToAnswer(
const std::string &remote_sdp) { const std::string &remote_sdp) {
std::string negotiated_video_pt; std::string negotiated_video_pt;
std::string negotiated_audio_pt; std::string negotiated_audio_pt;
@@ -692,8 +680,7 @@ int IceTransmission::AppendLocalCapabilitiesToAnswer(
return 0; return 0;
} }
std::string IceTransmission::GetRemoteCapabilities( std::string IceTransport::GetRemoteCapabilities(const std::string &remote_sdp) {
const std::string &remote_sdp) {
std::string media_stream_sdp; std::string media_stream_sdp;
std::size_t video_start = remote_sdp.find("m=video"); std::size_t video_start = remote_sdp.find("m=video");
std::size_t video_end = remote_sdp.find("m=audio"); std::size_t video_end = remote_sdp.find("m=audio");
@@ -745,7 +732,7 @@ std::string IceTransmission::GetRemoteCapabilities(
return media_stream_sdp; return media_stream_sdp;
} }
bool IceTransmission::NegotiateVideoPayloadType(const std::string &remote_sdp) { bool IceTransport::NegotiateVideoPayloadType(const std::string &remote_sdp) {
std::string remote_video_capabilities; std::string remote_video_capabilities;
std::string local_video_capabilities; std::string local_video_capabilities;
std::string remote_prefered_video_pt; std::string remote_prefered_video_pt;
@@ -817,7 +804,7 @@ bool IceTransmission::NegotiateVideoPayloadType(const std::string &remote_sdp) {
} }
} }
bool IceTransmission::NegotiateAudioPayloadType(const std::string &remote_sdp) { bool IceTransport::NegotiateAudioPayloadType(const std::string &remote_sdp) {
std::string remote_audio_capabilities; std::string remote_audio_capabilities;
std::string remote_prefered_audio_pt; std::string remote_prefered_audio_pt;
@@ -877,7 +864,7 @@ bool IceTransmission::NegotiateAudioPayloadType(const std::string &remote_sdp) {
} }
} }
bool IceTransmission::NegotiateDataPayloadType(const std::string &remote_sdp) { bool IceTransport::NegotiateDataPayloadType(const std::string &remote_sdp) {
std::string remote_data_capabilities; std::string remote_data_capabilities;
std::string remote_prefered_data_pt; std::string remote_prefered_data_pt;
@@ -937,12 +924,11 @@ bool IceTransmission::NegotiateDataPayloadType(const std::string &remote_sdp) {
} }
} }
std::vector<RtpPacket::PAYLOAD_TYPE> std::vector<RtpPacket::PAYLOAD_TYPE> IceTransport::GetNegotiatedCapabilities() {
IceTransmission::GetNegotiatedCapabilities() {
return {negotiated_video_pt_, negotiated_audio_pt_, negotiated_data_pt_}; return {negotiated_video_pt_, negotiated_audio_pt_, negotiated_data_pt_};
} }
int IceTransmission::SendVideoFrame(const XVideoFrame *video_frame) { int IceTransport::SendVideoFrame(const XVideoFrame *video_frame) {
if (state_ != NICE_COMPONENT_STATE_CONNECTED && if (state_ != NICE_COMPONENT_STATE_CONNECTED &&
state_ != NICE_COMPONENT_STATE_READY) { state_ != NICE_COMPONENT_STATE_READY) {
LOG_ERROR("Ice is not connected, state = [{}]", LOG_ERROR("Ice is not connected, state = [{}]",
@@ -960,14 +946,8 @@ int IceTransmission::SendVideoFrame(const XVideoFrame *video_frame) {
video_frame, video_frame,
[this](char *encoded_frame, size_t size, [this](char *encoded_frame, size_t size,
VideoEncoder::VideoFrameType frame_type) -> int { VideoEncoder::VideoFrameType frame_type) -> int {
std::vector<RtpPacket> packets; if (video_channel_send_) {
if (rtp_video_sender_) { video_channel_send_->SendVideo(encoded_frame, size);
if (video_rtp_codec_) {
video_rtp_codec_->Encode(
static_cast<RtpCodec::VideoFrameType>(frame_type),
(uint8_t *)encoded_frame, (uint32_t)size, packets);
}
rtp_video_sender_->Enqueue(packets);
} }
return 0; return 0;
@@ -981,7 +961,7 @@ int IceTransmission::SendVideoFrame(const XVideoFrame *video_frame) {
return 0; return 0;
} }
int IceTransmission::SendAudioFrame(const char *data, size_t size) { int IceTransport::SendAudioFrame(const char *data, size_t size) {
if (state_ != NICE_COMPONENT_STATE_CONNECTED && if (state_ != NICE_COMPONENT_STATE_CONNECTED &&
state_ != NICE_COMPONENT_STATE_READY) { state_ != NICE_COMPONENT_STATE_READY) {
LOG_ERROR("Ice is not connected, state = [{}]", LOG_ERROR("Ice is not connected, state = [{}]",
@@ -1006,7 +986,7 @@ int IceTransmission::SendAudioFrame(const char *data, size_t size) {
return ret; return ret;
} }
int IceTransmission::SendDataFrame(const char *data, size_t size) { int IceTransport::SendDataFrame(const char *data, size_t size) {
if (state_ != NICE_COMPONENT_STATE_CONNECTED && if (state_ != NICE_COMPONENT_STATE_CONNECTED &&
state_ != NICE_COMPONENT_STATE_READY) { state_ != NICE_COMPONENT_STATE_READY) {
LOG_ERROR("Ice is not connected, state = [{}]", LOG_ERROR("Ice is not connected, state = [{}]",
@@ -1026,41 +1006,34 @@ int IceTransmission::SendDataFrame(const char *data, size_t size) {
return 0; return 0;
} }
uint8_t IceTransmission::CheckIsRtcpPacket(const char *buffer, size_t size) { uint8_t IceTransport::CheckIsRtpPacket(const char *buffer, size_t size) {
if (size < 4) { if (size < 2) {
return 0; return 0;
} }
uint8_t v = (buffer[0] >> 6) & 0x03; uint8_t payload_type = buffer[1] & 0x7F;
if (2 != v) { if (payload_type >= 96 && payload_type <= 127) {
return 0; return payload_type;
} } else {
uint8_t pt = buffer[1];
switch (pt) {
case RtcpHeader::PAYLOAD_TYPE::SR: {
return pt;
}
case RtcpHeader::PAYLOAD_TYPE::RR: {
return pt;
}
case RtcpHeader::PAYLOAD_TYPE::SDES: {
return pt;
}
case RtcpHeader::PAYLOAD_TYPE::BYE: {
return pt;
}
case RtcpHeader::PAYLOAD_TYPE::APP: {
return pt;
}
default: {
return 0; return 0;
} }
} }
uint8_t IceTransport::CheckIsRtcpPacket(const char *buffer, size_t size) {
if (size < 2) {
return 0;
} }
uint8_t IceTransmission::CheckIsVideoPacket(const char *buffer, size_t size) { uint8_t payload_type = buffer[1];
if (payload_type >= 192 && payload_type <= 223) {
return payload_type;
;
}
return 0;
}
uint8_t IceTransport::CheckIsVideoPacket(const char *buffer, size_t size) {
if (size < 4) { if (size < 4) {
return 0; return 0;
} }
@@ -1081,7 +1054,7 @@ uint8_t IceTransmission::CheckIsVideoPacket(const char *buffer, size_t size) {
} }
} }
uint8_t IceTransmission::CheckIsAudioPacket(const char *buffer, size_t size) { uint8_t IceTransport::CheckIsAudioPacket(const char *buffer, size_t size) {
if (size < 4) { if (size < 4) {
return 0; return 0;
} }
@@ -1099,7 +1072,7 @@ uint8_t IceTransmission::CheckIsAudioPacket(const char *buffer, size_t size) {
} }
} }
uint8_t IceTransmission::CheckIsDataPacket(const char *buffer, size_t size) { uint8_t IceTransport::CheckIsDataPacket(const char *buffer, size_t size) {
if (size < 4) { if (size < 4) {
return 0; return 0;
} }

View File

@@ -1,17 +1,21 @@
/* /*
* @Author: DI JUNKUN * @Author: DI JUNKUN
* @Date: 2023-11-24 * @Date: 2025-01-03
* Copyright (c) 2023 by DI JUNKUN, All Rights Reserved. * Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
*/ */
#ifndef _ICE_TRANSMISSION_H_ #ifndef _ICE_TRANSPORT_H_
#define _ICE_TRANSMISSION_H_ #define _ICE_TRANSPORT_H_
#include <iostream> #include <iostream>
#include "audio_decoder.h" #include "audio_decoder.h"
#include "audio_encoder.h" #include "audio_encoder.h"
#include "congestion_control.h" // #include "congestion_control.h"
#include "audio_channel_receive.h"
#include "audio_channel_send.h"
#include "data_channel_receive.h"
#include "data_channel_send.h"
#include "ice_agent.h" #include "ice_agent.h"
#include "io_statistics.h" #include "io_statistics.h"
#include "ringbuffer.h" #include "ringbuffer.h"
@@ -23,11 +27,13 @@
#include "rtp_packet.h" #include "rtp_packet.h"
#include "rtp_video_receiver.h" #include "rtp_video_receiver.h"
#include "rtp_video_sender.h" #include "rtp_video_sender.h"
#include "video_channel_receive.h"
#include "video_channel_send.h"
#include "video_decoder_factory.h" #include "video_decoder_factory.h"
#include "video_encoder_factory.h" #include "video_encoder_factory.h"
#include "ws_client.h" #include "ws_client.h"
class IceTransmission { class IceTransport {
public: public:
typedef enum { VIDEO = 96, AUDIO = 97, DATA = 127 } DATA_TYPE; typedef enum { VIDEO = 96, AUDIO = 97, DATA = 127 } DATA_TYPE;
typedef enum { H264 = 96, AV1 = 99 } VIDEO_TYPE; typedef enum { H264 = 96, AV1 = 99 } VIDEO_TYPE;
@@ -40,13 +46,13 @@ class IceTransmission {
enum TraversalType { TP2P = 0, TRelay = 1, TUnknown = 2 }; enum TraversalType { TP2P = 0, TRelay = 1, TUnknown = 2 };
public: public:
IceTransmission(bool offer_peer, std::string &transmission_id, IceTransport(bool offer_peer, std::string &transmission_id,
std::string &user_id, std::string &remote_user_id, std::string &user_id, std::string &remote_user_id,
std::shared_ptr<WsClient> ice_ws_transmission, std::shared_ptr<WsClient> ice_ws_transmission,
std::function<void(std::string, const std::string &)> std::function<void(std::string, const std::string &)>
on_ice_status_change, on_ice_status_change,
void *user_data); void *user_data);
~IceTransmission(); ~IceTransport();
public: public:
int SetLocalCapabilities(bool hardware_acceleration, bool use_trickle_ice, int SetLocalCapabilities(bool hardware_acceleration, bool use_trickle_ice,
@@ -131,6 +137,7 @@ class IceTransmission {
int CreateAudioCodec(); int CreateAudioCodec();
private: private:
uint8_t CheckIsRtpPacket(const char *buffer, size_t size);
uint8_t CheckIsRtcpPacket(const char *buffer, size_t size); uint8_t CheckIsRtcpPacket(const char *buffer, size_t size);
uint8_t CheckIsVideoPacket(const char *buffer, size_t size); uint8_t CheckIsVideoPacket(const char *buffer, size_t size);
uint8_t CheckIsAudioPacket(const char *buffer, size_t size); uint8_t CheckIsAudioPacket(const char *buffer, size_t size);
@@ -164,7 +171,7 @@ class IceTransmission {
std::unique_ptr<IceAgent> ice_agent_ = nullptr; std::unique_ptr<IceAgent> ice_agent_ = nullptr;
bool is_closed_ = false; bool is_closed_ = false;
std::shared_ptr<WsClient> ice_ws_transport_ = nullptr; std::shared_ptr<WsClient> ice_ws_transport_ = nullptr;
CongestionControl *congestion_control_ = nullptr; // CongestionControl *congestion_control_ = nullptr;
std::function<void(const XVideoFrame *, const char *, const size_t, void *)> std::function<void(const XVideoFrame *, const char *, const size_t, void *)>
on_receive_video_ = nullptr; on_receive_video_ = nullptr;
std::function<void(const char *, size_t, const char *, const size_t, void *)> std::function<void(const char *, size_t, const char *, const size_t, void *)>
@@ -181,6 +188,13 @@ class IceTransmission {
on_receive_net_status_report_ = nullptr; on_receive_net_status_report_ = nullptr;
private: private:
std::unique_ptr<VideoChannelSend> video_channel_send_ = nullptr;
std::unique_ptr<VideoChannelReceive> video_channel_receive_ = nullptr;
std::unique_ptr<AudioChannelSend> audio_channel_send_ = nullptr;
std::unique_ptr<AudioChannelReceive> audio_channel_receive_ = nullptr;
std::unique_ptr<DataChannelSend> data_channel_send_ = nullptr;
std::unique_ptr<DataChannelReceive> data_channel_receive_ = nullptr;
std::unique_ptr<RtpCodec> video_rtp_codec_ = nullptr; std::unique_ptr<RtpCodec> video_rtp_codec_ = nullptr;
std::unique_ptr<RtpCodec> audio_rtp_codec_ = nullptr; std::unique_ptr<RtpCodec> audio_rtp_codec_ = nullptr;
std::unique_ptr<RtpCodec> data_rtp_codec_ = nullptr; std::unique_ptr<RtpCodec> data_rtp_codec_ = nullptr;

View File

@@ -192,18 +192,29 @@ target("qos")
add_files("src/qos/*.cpp") add_files("src/qos/*.cpp")
add_includedirs("src/qos", {public = true}) add_includedirs("src/qos", {public = true})
-- target("transport")
-- set_kind("object")
-- add_deps("log", "ws", "ice", "qos", "rtp", "rtcp", "statistics", "media")
-- add_files("src/transport/*.cpp")
-- add_includedirs("src/ws", "src/ice", "src/qos", {public = true})
target("transmission") target("transport")
set_kind("object") set_kind("object")
add_deps("log", "ws", "ice", "qos", "rtp", "rtcp", "statistics", "media") add_deps("log", "ws", "ice", "channel", "rtp", "rtcp", "statistics", "media")
add_files("src/transmission/*.cpp") add_files("src/transport/*.cpp")
add_includedirs("src/ws", "src/ice", "src/qos", {public = true}) add_includedirs("src/ws", "src/ice", "src/channel", {public = true})
target("channel")
set_kind("object")
add_deps("log", "rtp", "rtcp")
add_files("src/channel/*.cpp")
add_includedirs("src/rtp", "src/rtcp", {public = true})
target("pc") target("pc")
set_kind("object") set_kind("object")
add_deps("log", "ws", "ice", "transmission", "inih", "common") add_deps("log", "ws", "ice", "transport", "inih", "common")
add_files("src/pc/*.cpp") add_files("src/pc/*.cpp")
add_includedirs("src/transmission", "src/interface", {public = true}) add_includedirs("src/transport", "src/interface", {public = true})
target("projectx") target("projectx")
set_kind("static") set_kind("static")