pub mod report;
use crate::{FromPacket, MutablePacket, Packet, PacketSize};
use pnet_macros_support::packet::PrimitiveValues;
use report::{
MutableReceiverReportPacket,
MutableSenderReportPacket,
ReceiverReport,
ReceiverReportPacket,
SenderReport,
SenderReportPacket,
};
#[derive(Clone, Debug, Eq, PartialEq)]
#[non_exhaustive]
pub enum Rtcp {
SenderReport(SenderReport),
ReceiverReport(ReceiverReport),
KnownType(RtcpType),
}
#[derive(Debug, PartialEq)]
#[non_exhaustive]
pub enum RtcpPacket<'a> {
SenderReport(SenderReportPacket<'a>),
ReceiverReport(ReceiverReportPacket<'a>),
KnownType(RtcpType),
}
impl RtcpPacket<'_> {
#[must_use]
pub fn new(pkt: &[u8]) -> Option<RtcpPacket<'_>> {
RtcpType::from_packet(pkt).and_then(|rtcp_id| rtcp_id.decode(pkt))
}
}
impl<'a> Packet for RtcpPacket<'a> {
fn packet(&self) -> &[u8] {
match self {
Self::SenderReport(s) => s.packet(),
Self::ReceiverReport(s) => s.packet(),
Self::KnownType(_) => &[],
}
}
fn payload(&self) -> &[u8] {
match self {
Self::SenderReport(s) => s.payload(),
Self::ReceiverReport(s) => s.payload(),
Self::KnownType(_) => &[],
}
}
}
impl<'a> FromPacket for RtcpPacket<'a> {
type T = Rtcp;
fn from_packet(&self) -> Self::T {
match self {
Self::SenderReport(s) => Rtcp::SenderReport(s.from_packet()),
Self::ReceiverReport(s) => Rtcp::ReceiverReport(s.from_packet()),
Self::KnownType(t) => Rtcp::KnownType(*t),
}
}
}
impl<'a> PacketSize for RtcpPacket<'a> {
fn packet_size(&self) -> usize {
match self {
Self::SenderReport(s) => s.packet_size(),
Self::ReceiverReport(s) => s.packet_size(),
Self::KnownType(_) => 0,
}
}
}
#[derive(Debug, PartialEq)]
#[non_exhaustive]
pub enum MutableRtcpPacket<'a> {
SenderReport(MutableSenderReportPacket<'a>),
ReceiverReport(MutableReceiverReportPacket<'a>),
KnownType(RtcpType),
}
impl MutableRtcpPacket<'_> {
pub fn new(pkt: &mut [u8]) -> Option<MutableRtcpPacket<'_>> {
RtcpType::from_packet(pkt).and_then(move |rtcp_id| rtcp_id.decode_mut(pkt))
}
}
impl<'a> Packet for MutableRtcpPacket<'a> {
fn packet(&self) -> &[u8] {
match self {
Self::SenderReport(s) => s.packet(),
Self::ReceiverReport(s) => s.packet(),
Self::KnownType(_) => &[],
}
}
fn payload(&self) -> &[u8] {
match self {
Self::SenderReport(s) => s.payload(),
Self::ReceiverReport(s) => s.payload(),
Self::KnownType(_) => &[],
}
}
}
impl<'a> MutablePacket for MutableRtcpPacket<'a> {
fn packet_mut(&mut self) -> &mut [u8] {
match self {
Self::SenderReport(s) => s.packet_mut(),
Self::ReceiverReport(s) => s.packet_mut(),
Self::KnownType(_) => &mut [],
}
}
fn payload_mut(&mut self) -> &mut [u8] {
match self {
Self::SenderReport(s) => s.payload_mut(),
Self::ReceiverReport(s) => s.payload_mut(),
Self::KnownType(_) => &mut [],
}
}
}
impl<'a> FromPacket for MutableRtcpPacket<'a> {
type T = Rtcp;
fn from_packet(&self) -> Self::T {
match self {
Self::SenderReport(s) => Rtcp::SenderReport(s.from_packet()),
Self::ReceiverReport(s) => Rtcp::ReceiverReport(s.from_packet()),
Self::KnownType(t) => Rtcp::KnownType(*t),
}
}
}
impl<'a> PacketSize for MutableRtcpPacket<'a> {
fn packet_size(&self) -> usize {
match self {
Self::SenderReport(s) => s.packet_size(),
Self::ReceiverReport(s) => s.packet_size(),
Self::KnownType(_) => 0,
}
}
}
#[derive(Copy, Clone, Debug, Eq, Hash, PartialEq)]
#[non_exhaustive]
pub enum RtcpType {
SmpteMap,
JitterReport,
SenderReport,
ReceiverReport,
SourceDescription,
Goodbye,
ApplicationDefined,
TransportFeedback,
PayloadFeedback,
ExtendedReport,
Avb,
ReceiverSummary,
PortMapping,
Idms,
ReportingGroupSources,
SplicingNotification,
Reserved(u8),
Unassigned(u8),
}
impl<'a> RtcpType {
#[must_use]
pub fn new(val: u8) -> Self {
match val {
194 => Self::SmpteMap,
195 => Self::JitterReport,
200 => Self::SenderReport,
201 => Self::ReceiverReport,
202 => Self::SourceDescription,
203 => Self::Goodbye,
204 => Self::ApplicationDefined,
205 => Self::TransportFeedback,
206 => Self::PayloadFeedback,
207 => Self::ExtendedReport,
208 => Self::Avb,
209 => Self::ReceiverSummary,
210 => Self::PortMapping,
211 => Self::Idms,
212 => Self::ReportingGroupSources,
213 => Self::SplicingNotification,
0 | 192 | 193 | 255 => Self::Reserved(val),
_ => Self::Unassigned(val),
}
}
#[must_use]
pub fn decode(&self, pkt: &'a [u8]) -> Option<RtcpPacket<'a>> {
match self {
Self::SenderReport => SenderReportPacket::new(pkt).map(RtcpPacket::SenderReport),
Self::ReceiverReport => ReceiverReportPacket::new(pkt).map(RtcpPacket::ReceiverReport),
a => Some(RtcpPacket::KnownType(*a)),
}
}
pub fn decode_mut(&self, pkt: &'a mut [u8]) -> Option<MutableRtcpPacket<'a>> {
match self {
Self::SenderReport =>
MutableSenderReportPacket::new(pkt).map(MutableRtcpPacket::SenderReport),
Self::ReceiverReport =>
MutableReceiverReportPacket::new(pkt).map(MutableRtcpPacket::ReceiverReport),
a => Some(MutableRtcpPacket::KnownType(*a)),
}
}
pub fn from_packet(pkt: &[u8]) -> Option<Self> {
pkt.get(1).copied().map(Self::new)
}
}
impl PrimitiveValues for RtcpType {
type T = (u8,);
fn to_primitive_values(&self) -> Self::T {
match self {
Self::SmpteMap => (194,),
Self::JitterReport => (195,),
Self::SenderReport => (200,),
Self::ReceiverReport => (201,),
Self::SourceDescription => (202,),
Self::Goodbye => (203,),
Self::ApplicationDefined => (204,),
Self::TransportFeedback => (205,),
Self::PayloadFeedback => (206,),
Self::ExtendedReport => (207,),
Self::Avb => (208,),
Self::ReceiverSummary => (209,),
Self::PortMapping => (210,),
Self::Idms => (211,),
Self::ReportingGroupSources => (212,),
Self::SplicingNotification => (213,),
Self::Reserved(val) | Self::Unassigned(val) => (*val,),
}
}
}