一:加密模块:
在webrtc中,通过开源的libSRTP进行RTP的数据加密;
webrtc为了方便,进行的封装;
实现了加密,解密;
src\pc\srtpsession.h;
// Class that wraps a libSRTP session.
class SrtpSession
SrtpTransport::SendRtpPacket
二:加密逻辑:
BaseChannel::BaseChannel(rtc::Thread* worker_thread,
rtc::Thread* network_thread,
rtc::Thread* signaling_thread,
std::unique_ptr
const std::string& content_name,
bool rtcp_mux_required,
bool srtp_required)
: worker_thread_(worker_thread),
network_thread_(network_thread),
signaling_thread_(signaling_thread),
content_name_(content_name),
rtcp_mux_required_(rtcp_mux_required),
unencrypted_rtp_transport_(
rtc::MakeUnique
srtp_required_(srtp_required),//是否启用srtp加密;
media_channel_(std::move(media_channel)) {
RTC_DCHECK_RUN_ON(worker_thread_);
rtp_transport_ = unencrypted_rtp_transport_.get(); //赋值;
ConnectToRtpTransport();
......
}
srtp_required: srtp加密是否启用;
//EnableSdes_n:这个函数仅启用Srtp;
void BaseChannel::EnableSdes_n() {
if (sdes_transport_) {
return;
}
// DtlsSrtpTransport and SrtpTransport shouldn't be enabled at the same
// time.
RTC_DCHECK(!dtls_srtp_transport_);
RTC_DCHECK(unencrypted_rtp_transport_);
sdes_transport_ = rtc::MakeUnique
std::move(unencrypted_rtp_transport_)); //创建srtp transport,未加密的transport作为构造参数;
sdes_transport_接收到未加密的数据,加密,然后输出;
#if defined(ENABLE_EXTERNAL_AUTH)
sdes_transport_->EnableExternalAuth();
#endif
SetRtpTransport(sdes_transport_.get());
RTC_LOG(LS_INFO) << "Wrapping RtpTransport in SrtpTransport.";
}
和上面的函数一样,EnableDtlsSrtp_n:这个启用 Dtls + Srtp;
void BaseChannel::EnableDtlsSrtp_n()
{
// DtlsSrtpTransport and SrtpTransport shouldn't be enabled at the same
// time.
}
两个设置函数:
void SetTransports(DtlsTransportInternal* rtp_dtls_transport,
DtlsTransportInternal* rtcp_dtls_transport); //设置加密transport;
void SetTransports(rtc::PacketTransportInternal* rtp_packet_transport,
rtc::PacketTransportInternal* rtcp_packet_transport); //设置一般transport;
看一个源码:
void BaseChannel::SetTransports(DtlsTransportInternal* rtp_dtls_transport,
DtlsTransportInternal* rtcp_dtls_transport) {
network_thread_->Invoke
RTC_FROM_HERE,
Bind(&BaseChannel::SetTransports_n, this, rtp_dtls_transport,
rtcp_dtls_transport, rtp_dtls_transport, rtcp_dtls_transport));
}
void BaseChannel::SetTransports(
rtc::PacketTransportInternal* rtp_packet_transport,
rtc::PacketTransportInternal* rtcp_packet_transport) {
network_thread_->Invoke
RTC_FROM_HERE, Bind(&BaseChannel::SetTransports_n, this, nullptr, nullptr, //不加密的话,这两个参数设置为空,看SetTransports_n函数;
rtp_packet_transport, rtcp_packet_transport));
}
void BaseChannel::SetTransports_n(
DtlsTransportInternal* rtp_dtls_transport, //非加密,为空;
DtlsTransportInternal* rtcp_dtls_transport, //非加密,为空;
rtc::PacketTransportInternal* rtp_packet_transport,
rtc::PacketTransportInternal* rtcp_packet_transport) {
RTC_DCHECK(network_thread_->IsCurrent());
// Validate some assertions about the input.
RTC_DCHECK(rtp_packet_transport);
RTC_DCHECK_EQ(NeedsRtcpTransport(), rtcp_packet_transport != nullptr);
if (rtp_dtls_transport || rtcp_dtls_transport) {
// DTLS/non-DTLS pointers should be to the same object.
RTC_DCHECK(rtp_dtls_transport == rtp_packet_transport);
RTC_DCHECK(rtcp_dtls_transport == rtcp_packet_transport);
// Can't go from non-DTLS to DTLS.
RTC_DCHECK(!rtp_transport_->rtp_packet_transport() || rtp_dtls_transport_);
} else {
// Can't go from DTLS to non-DTLS.
RTC_DCHECK(!rtp_dtls_transport_);
}
// Transport names should be the same.
if (rtp_dtls_transport && rtcp_dtls_transport) {
RTC_DCHECK(rtp_dtls_transport->transport_name() ==
rtcp_dtls_transport->transport_name());
}
if (rtp_packet_transport == rtp_transport_->rtp_packet_transport()) {
// Nothing to do if transport isn't changing.
return;
}
std::string debug_name;
if (rtp_dtls_transport) {
transport_name_ = rtp_dtls_transport->transport_name();
debug_name = transport_name_;
} else {
debug_name = rtp_packet_transport->transport_name();
}
// If this BaseChannel doesn't require RTCP mux and we haven't fully
// negotiated RTCP mux, we need an RTCP transport.
if (rtcp_packet_transport) {
RTC_LOG(LS_INFO) << "Setting RTCP Transport for " << content_name()
<< " on " << debug_name << " transport "
<< rtcp_packet_transport;
SetTransport_n(/*rtcp=*/true, rtcp_dtls_transport, rtcp_packet_transport);
}
RTC_LOG(LS_INFO) << "Setting RTP Transport for " << content_name() << " on "
<< debug_name << " transport " << rtp_packet_transport;
SetTransport_n(/*rtcp=*/false, rtp_dtls_transport, rtp_packet_transport);
// Set DtlsTransport/PacketTransport for RTP-level transport.
if ((rtp_dtls_transport_ || rtcp_dtls_transport_) && dtls_srtp_transport_) {
// When setting the transport with non-null |dtls_srtp_transport_|, we are
// using DTLS-SRTP. This could happen for bundling. If the
// |dtls_srtp_transport| is null, we cannot tell if it doing DTLS-SRTP or
// SDES until the description is set. So don't call |EnableDtlsSrtp_n| here.
dtls_srtp_transport_->SetDtlsTransports(rtp_dtls_transport,
rtcp_dtls_transport);
} else {
rtp_transport_->SetRtpPacketTransport(rtp_packet_transport);
rtp_transport_->SetRtcpPacketTransport(rtcp_packet_transport);
}
// Update aggregate writable/ready-to-send state between RTP and RTCP upon
// setting new transport channels.
UpdateWritableState_n();
}
void BaseChannel::SetTransports_n: 根据参数设置最后应用的transport;