skyscraper8/skyscraper8/ThreemediaOtt/ThreemediaOttHandler.cs
feyris-tan 124bc001aa
All checks were successful
🚀 Pack skyscraper8 / make-zip (push) Successful in 1m14s
Began parsing Threemedia OTT fragments.
2026-06-28 12:37:47 +02:00

124 lines
3.0 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;
using log4net;
using skyscraper5.Ietf.Rfc768;
using skyscraper5.Ietf.Rfc971;
using skyscraper5.Skyscraper.Plugins;
using skyscraper5.Skyscraper.Scraper;
using skyscraper8.Ietf.FLUTE;
namespace skyscraper8.ThreemediaOtt
{
[SkyscraperPlugin]
internal class ThreemediaOttHandler : ISkyscraperMpePlugin
{
private static readonly IPAddress THREEMDIA_DESTINATION_IP = IPAddress.Parse("224.1.2.1");
private static readonly ILog logger = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType.Name);
public void ConnectToStorage(object[] connector)
{
throw new NotImplementedException();
}
private SkyscraperContext context;
public void SetContext(DateTime? currentTime, object skyscraperContext)
{
if (context != null)
{
context = skyscraperContext as SkyscraperContext;
}
}
public bool CanHandlePacket(InternetHeader internetHeader, byte[] ipv4Packet)
{
if (!internetHeader.IsDestinationMulticast)
return false;
if (!internetHeader.DestinationAddress.Equals(THREEMDIA_DESTINATION_IP))
return false;
if (internetHeader.Protocol != 17)
return false;
if (ipv4Packet[2] != 0x04)
return false;
if (ipv4Packet[3] != 0x61)
return false;
if (ipv4Packet[8] != 0x10)
return false;
return true;
}
private Dictionary<ushort, ThreemediaSession> sessions;
public void HandlePacket(InternetHeader internetHeader, byte[] ipv4Packet)
{
UserDatagram udpPacket = new UserDatagram(ipv4Packet);
LctFrame lctFrame = new LctFrame(udpPacket.Payload, false);
if (lctFrame.CloseSessionFlag)
{
AssembleSegment(udpPacket.DestinationPort);
return;
}
else
{
IngestPacket(udpPacket.DestinationPort, lctFrame);
return;
}
}
private void IngestPacket(ushort udpPacketDestinationPort, LctFrame lctFrame)
{
if (sessions == null)
sessions = new Dictionary<ushort, ThreemediaSession>();
ThreemediaSession selectedSession = null;
if (sessions.ContainsKey(udpPacketDestinationPort))
{
selectedSession = sessions[udpPacketDestinationPort];
}
else
{
selectedSession = new ThreemediaSession();
sessions[udpPacketDestinationPort] = selectedSession;
}
selectedSession.IngestPacket(lctFrame);
}
private void AssembleSegment(ushort destinationPort)
{
if (sessions == null)
return;
if (!sessions.ContainsKey(destinationPort))
{
return;
}
ThreemediaSession selectedSession = sessions[destinationPort];
if (!selectedSession.IsComplete())
{
logger.WarnFormat(String.Format("The session on Port {0} is incomplete and can not be recovered.", destinationPort));
selectedSession.Dispose();
return;
}
ThreemediaSessionStream stream = selectedSession.CreateStream();
FileStream fs = File.OpenWrite("test.bin");
stream.CopyTo(fs);
fs.Flush(true);
fs.Close();
}
public bool StopProcessingAfterThis()
{
return true;
}
}
}