feyris-tan e3b125e29d
Some checks failed
🚀 Pack skyscraper8 / make-zip (push) Failing after 1m49s
minor bug fixes.
2025-10-30 07:58:27 +01:00

653 lines
33 KiB
C#

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using skyscraper5.IO.StreamReader;
using skyscraper5.Skyscraper.IO.RemoteStreamReader;
using skyscraper5.Skyscraper.Net.Sockets;
using skyscraper5.src.Skyscraper.IO.PortableExecutables;
namespace skyscraper5.Skyscraper.IO.CrazycatStreamReader
{
internal class RemoteStreamReaderServer
{
private bool _logRequests;
private int _listenPort;
private IPAddress _listenAddress;
private bool clientConnected;
private IStreamReader localStreamReader;
private Thread clientThread;
private Dictionary<string, string> dllVersionInfo;
public bool IsRunning { get; private set; }
public int ListenPort
{
get => _listenPort;
set
{
if (IsRunning)
throw new InvalidOperationException();
_listenPort = value;
}
}
public IPAddress ListenAddress
{
get => _listenAddress;
set
{
if (IsRunning)
throw new InvalidOperationException();
_listenAddress = value;
}
}
public bool LogRequests
{
get => _logRequests;
set => _logRequests = value;
}
public void Run()
{
if (localStreamReader == null)
{
localStreamReader = LocalStreamReader.GetInstance();
if (!localStreamReader.CheckForDVB())
{
Console.WriteLine("No tuners present, quitting.");
return;
}
}
if (ListenAddress == null)
ListenAddress = IPAddress.Any;
IPEndPoint listenEndPoint = new IPEndPoint(ListenAddress, ListenPort);
TcpListener tcpListener = new TcpListener(listenEndPoint);
tcpListener.Start();
Console.WriteLine("Listening on {0}", tcpListener.LocalEndpoint);
while (true)
{
TcpClient acceptTcpClient = tcpListener.AcceptTcpClient();
if (clientConnected)
{
Console.WriteLine("Rejected connection from {0}. I'm busy.", acceptTcpClient.Client.RemoteEndPoint);
NetworkStream blockoffStream = acceptTcpClient.GetStream();
blockoffStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.SERVER_BUSY_WITH_ANOTHER_CLIENT);
blockoffStream.Flush();
acceptTcpClient.Close();
}
else
{
Console.WriteLine("Accepted connection from {0}", acceptTcpClient.Client.RemoteEndPoint);
clientConnected = true;
clientThread = new Thread(ClientThreadMethod);
clientThread.Name = String.Format("RemoteStreamReader Client @ {0}", acceptTcpClient.Client.RemoteEndPoint);
clientThread.Start(acceptTcpClient);
}
}
}
private void ClientThreadMethod(object o)
{
TcpClient tcpClient = (TcpClient)o;
NetworkStream tcpStream = tcpClient.GetStream();
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.SERVER_READY);
tcpStream.Flush();
bool breakout = false;
while (!breakout)
{
uint opcode;
try
{
opcode = tcpStream.ReadUInt32BE();
if (LogRequests)
Console.WriteLine("Request from {0}: {1}", tcpClient.Client.RemoteEndPoint, (RemoteStreamReaderConstants)opcode);
}
catch (Exception e)
{
Console.WriteLine("Lost connection to {0}: {1}", tcpClient.Client.RemoteEndPoint, e);
clientConnected = false;
return;
}
switch (opcode)
{
case (uint)RemoteStreamReaderConstants.REQUEST_NOOP:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_HOSTNAME:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.WriteUTF8(Environment.MachineName);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_USERNAME:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.WriteUTF8(Environment.UserName);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_DATE_TIME:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.WriteInt64BE(DateTime.Now.Ticks);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_DISPOSE:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.Flush();
breakout = true;
break;
case (uint)RemoteStreamReaderConstants.REQUEST_CHECK_FOR_DVB_EX_EX:
bool checkForDvbExEx = localStreamReader.CheckForDVBExEx((index, name, type) =>
{
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.ENUMERATE_CHECK_FOR_DVB_EX_EX);
tcpStream.WriteInt32BE(index);
tcpStream.WriteUTF8(name);
tcpStream.WriteInt32BE((int)type);
});
if (checkForDvbExEx)
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
else
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_START_DVB_EX:
int readIndex = tcpStream.ReadInt32BE();
bool startDvbExResult = localStreamReader.StartDvbEx(readIndex);
tcpStream.WriteUInt32BE(startDvbExResult
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_STOP_DVB:
bool stopDvbResult = localStreamReader.StopDVB();
tcpStream.WriteUInt32BE(stopDvbResult
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_GET_TUNER_TYPE:
STD_TYPE m = (STD_TYPE)(-1);
bool getTunerTypeResult = localStreamReader.GetTunerType(ref m);
tcpStream.WriteUInt32BE(getTunerTypeResult
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (getTunerTypeResult)
{
tcpStream.WriteInt32BE((int)m);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_GET_CAPS:
Caps caps = localStreamReader.GetCaps();
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.WriteInt32BE((int)caps);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SEND_DISEQC:
uint diseqcType = tcpStream.ReadUInt32BE();
byte recvMe = tcpStream.ReadUInt8();
DiSEqC_Opcode diSEqCOpcode = (DiSEqC_Opcode)recvMe;
bool sendDiSEqC = localStreamReader.SendDiSEqC(diseqcType, diSEqCOpcode);
tcpStream.WriteUInt32BE(sendDiSEqC
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_RF_SCAN:
int rfScanFreq = tcpStream.ReadInt32BE();
int rfScanPol = tcpStream.ReadInt32BE();
int rfScanLof1 = tcpStream.ReadInt32BE();
int rfScanLof2 = tcpStream.ReadInt32BE();
int rfScanLofSw = tcpStream.ReadInt32BE();
double rfScanRfLevel = Double.NaN;
bool rfScan = localStreamReader.RFScan(rfScanFreq, rfScanPol, rfScanLof1, rfScanLof2, rfScanLofSw, out rfScanRfLevel);
tcpStream.WriteUInt32BE(rfScan
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.WriteDouble(rfScanRfLevel);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SET_CHANNEL:
int setChannelFreq = tcpStream.ReadInt32BE();
int setChannelSymbRate = tcpStream.ReadInt32BE();
int setChannelPol = tcpStream.ReadInt32BE();
VITERBIRATE_TYPE setChannelFec = (VITERBIRATE_TYPE)tcpStream.ReadInt32BE();
int setChannelLof1 = tcpStream.ReadInt32BE();
int setChannelLof2 = tcpStream.ReadInt32BE();
int setChannelLofSw = tcpStream.ReadInt32BE();
bool channel = localStreamReader.SetChannel(setChannelFreq, setChannelSymbRate, setChannelPol, setChannelFec, setChannelLof1, setChannelLof2, setChannelLofSw);
tcpStream.WriteUInt32BE(channel
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SIGNAL_INFO:
SearchResult signalInfoSearchResult = default;
bool signalInfo = localStreamReader.SignalInfo(ref signalInfoSearchResult);
tcpStream.WriteUInt32BE(signalInfo
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (signalInfo)
{
int sizeOf = Marshal.SizeOf(typeof(SearchResult));
IntPtr allocHGlobal = Marshal.AllocHGlobal(sizeOf);
Marshal.StructureToPtr(signalInfoSearchResult, allocHGlobal, true);
byte[] bytes = new byte[sizeOf];
Marshal.Copy(allocHGlobal, bytes, 0, sizeOf);
Marshal.FreeHGlobal(allocHGlobal);
tcpStream.Write(bytes, 0, sizeOf);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SET_FILTER:
int setFilterPid = tcpStream.ReadInt32BE();
int setFilterSize = tcpStream.ReadInt32BE();
FilterServer filterServer = new FilterServer();
IntPtr setFilterNumber = default;
bool filter = localStreamReader.SetFilter(setFilterPid, filterServer.DvbCallback, 0x02, setFilterSize, ref setFilterNumber);
tcpStream.WriteUInt32BE(filter
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (filter)
{
if (filterServers == null)
filterServers = new Dictionary<IntPtr, FilterServer>();
filterServers.Add(setFilterNumber, filterServer);
filterServer.ListenIp = ListenAddress;
filterServer.TcpListener = new TcpListener(filterServer.ListenIp, 0);
filterServer.TcpListener.Start();
filterServer.Thread = new Thread(filterServer.Run);
string filterName = String.Format("Filter for PID {0} @{1}", setFilterPid, filterServer.TcpListener.Server.LocalEndPoint);
filterServer.Thread.Name = filterName;
filterServer.Thread.Start();
tcpStream.WriteIntPtr(setFilterNumber);
tcpStream.WriteIPEndPoint((IPEndPoint)filterServer.TcpListener.LocalEndpoint);
Console.WriteLine(filterName);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_DEL_FILTER:
IntPtr delFilterNumber = tcpStream.ReadIntPtr();
bool delFilter = localStreamReader.DelFilter(delFilterNumber);
tcpStream.WriteUInt32BE(delFilter
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if(delFilter)
{
FilterServer server = filterServers[delFilterNumber];
lock (server.clients)
{
server.clients.ForEach(x => x.Close());
}
server.Dispose();
server.Thread.Interrupt();
filterServers.Remove(delFilterNumber);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_BL_SCAN2:
int blscan2FreqStart = tcpStream.ReadInt32BE();
int blscan2FreqStop = tcpStream.ReadInt32BE();
int blscan2Pol = tcpStream.ReadInt32BE();
int blscan2Lof1 = tcpStream.ReadInt32BE();
int blscan2Lof2 = tcpStream.ReadInt32BE();
int blscan2LofSw = tcpStream.ReadInt32BE();
IntPtr blscan2SearchResults = Marshal.AllocHGlobal(65536);
int blscan2TpNum = -1;
BlScanCallback blScanCallback = (ref SearchResult result) =>
{
int sizeOf = Marshal.SizeOf(typeof(SearchResult));
IntPtr allocHGlobal = Marshal.AllocHGlobal(sizeOf);
Marshal.StructureToPtr(result, allocHGlobal, true);
byte[] buffer = new byte[sizeOf];
Marshal.Copy(allocHGlobal, buffer, 0, sizeOf);
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.ENUMERATE_BL_SCAN_2);
tcpStream.Write(buffer, 0, sizeOf);
Marshal.FreeHGlobal(allocHGlobal);
};
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_WILL_TAKE_SOME_TIME);
bool blScan2 = localStreamReader.BLScan2(blscan2FreqStart, blscan2FreqStop, blscan2Pol, blscan2Lof1, blscan2Lof2, blscan2LofSw, blscan2SearchResults, ref blscan2TpNum, blScanCallback);
tcpStream.WriteUInt32BE(blScan2
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (blScan2)
{
tcpStream.WriteInt32BE(blscan2TpNum);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_CHECK_FOR_DVB:
bool checkForDvb = localStreamReader.CheckForDVB();
if (checkForDvb)
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
else
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_GET_MAC:
byte[] buffer = new byte[6];
bool mac = localStreamReader.GetMAC(buffer);
if (mac)
{
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.Write(buffer, 0, 6);
}
else
{
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_FAILED);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_AIR_SCAN:
int freqStart = tcpStream.ReadInt32BE();
int freqEnd = tcpStream.ReadInt32BE();
uint step = tcpStream.ReadUInt32BE();
uint bandwidth = tcpStream.ReadUInt32BE();
int std = tcpStream.ReadInt32BE();
IntPtr airScanSearchResults = Marshal.AllocHGlobal(65536);
int airScanTpNum = -1;
AirScanCallback airScanCallback = (ref SearchResult2 result) =>
{
int sizeOf = Marshal.SizeOf(typeof(SearchResult2));
IntPtr allocHGlobal = Marshal.AllocHGlobal(sizeOf);
Marshal.StructureToPtr(result, allocHGlobal, true);
byte[] buffer = new byte[sizeOf];
Marshal.Copy(allocHGlobal, buffer, 0, sizeOf);
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.ENUMERATE_AIR_SCAN);
tcpStream.Write(buffer, 0, sizeOf);
Marshal.FreeHGlobal(allocHGlobal);
};
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_WILL_TAKE_SOME_TIME);
bool airscan = localStreamReader.AirScan(freqStart, freqEnd, step, bandwidth, std, airScanSearchResults, ref airScanTpNum, airScanCallback);
tcpStream.WriteUInt32BE(airscan
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (airscan)
{
tcpStream.WriteInt32BE(airScanTpNum);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SET_CHANNEL_2:
uint freq = tcpStream.ReadUInt32BE();
uint bandwidth2 = tcpStream.ReadUInt32BE();
bool channel2 = localStreamReader.SetChannel2(freq, bandwidth2);
tcpStream.WriteUInt32BE(channel2
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SIGNAL_INFO_2:
SearchResult2 signalInfoSearchResult2 = default;
bool signalInfo2 = localStreamReader.SignalInfo2(ref signalInfoSearchResult2);
tcpStream.WriteUInt32BE(signalInfo2
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (signalInfo2)
{
int sizeOf = Marshal.SizeOf(typeof(SearchResult2));
IntPtr allocHGlobal = Marshal.AllocHGlobal(sizeOf);
Marshal.StructureToPtr(signalInfoSearchResult2, allocHGlobal, true);
byte[] bytes = new byte[sizeOf];
Marshal.Copy(allocHGlobal, bytes, 0, sizeOf);
Marshal.FreeHGlobal(allocHGlobal);
tcpStream.Write(bytes, 0, sizeOf);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_MIS_SEL:
bool bEnable = tcpStream.ReadBoolean();
byte misFilter = tcpStream.ReadUInt8();
byte misFilterMask = tcpStream.ReadUInt8();
bool misSel = localStreamReader.MISSel(bEnable, misFilter, misFilterMask);
tcpStream.WriteUInt32BE(misSel
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_PLS_SEL:
byte plsMode = tcpStream.ReadUInt8();
uint code = tcpStream.ReadUInt32BE();
bool plsSel = localStreamReader.PLSSel(plsMode, code);
tcpStream.WriteUInt32BE(plsSel
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_BL_SCAN_EX:
freq = tcpStream.ReadUInt32BE();
int freq_range = tcpStream.ReadInt32BE();
int pol = tcpStream.ReadInt32BE();
int lof1 = tcpStream.ReadInt32BE();
int lof2 = tcpStream.ReadInt32BE();
int lofsw = tcpStream.ReadInt32BE();
int minsr = tcpStream.ReadInt32BE();
std = tcpStream.ReadInt32BE();
SearchResult result = new SearchResult();
bool blScanEx = localStreamReader.BLScanEx((int)freq, freq_range, pol, lof1, lof2, lofsw, minsr, (STD_TYPE)std, ref result);
tcpStream.WriteUInt32BE(blScanEx
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (blScanEx)
{
int sizeOfEx = Marshal.SizeOf(typeof(SearchResult));
IntPtr allocHGlobalEx = Marshal.AllocHGlobal(sizeOfEx);
Marshal.StructureToPtr(result, allocHGlobalEx, true);
byte[] bufferEx = new byte[sizeOfEx];
Marshal.Copy(allocHGlobalEx, bufferEx, 0, sizeOfEx);
tcpStream.Write(bufferEx, 0, sizeOfEx);
Marshal.FreeHGlobal(allocHGlobalEx);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_MOD_SEL:
S2Mode s2mode = new S2Mode();
s2mode.frameLen = tcpStream.ReadInt32BE();
s2mode.modcode = (S2MODCODE)tcpStream.ReadInt32BE();
s2mode.pilot = tcpStream.ReadBoolean();
uint num = tcpStream.ReadUInt32BE();
bool modSel = localStreamReader.ModSel(ref s2mode, num);
tcpStream.WriteUInt32BE(modSel
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (modSel)
{
tcpStream.WriteInt32BE(s2mode.frameLen);
tcpStream.WriteInt32BE((int)s2mode.modcode);
tcpStream.WriteBoolean(s2mode.pilot);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_IQ_SCAN:
uint input = tcpStream.ReadUInt32BE();
sbyte[] pIQ;
num = tcpStream.ReadUInt32BE();
pIQ = new sbyte[num * 2];
bool iqScan = localStreamReader.IQScan(input, pIQ, num);
tcpStream.WriteUInt32BE(iqScan
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (iqScan)
{
byte[] pIQunsigned = new byte[num * 2];
for (long i = 0; i < num * 2; i++)
{
pIQunsigned[i] = (byte)pIQ[i];
}
tcpStream.WriteByteArray(pIQunsigned);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_GET_SIGNAL_EX_EX:
bool pPresent = false;
bool pLock = false;
int pRFLevel = int.MinValue;
float pSNR = float.NaN;
float pBER = float.NaN;
bool getSignalExEx = localStreamReader.GetSignalExEx(ref pPresent, ref pLock, ref pRFLevel, ref pSNR, ref pBER);
tcpStream.WriteUInt32BE(getSignalExEx
? (uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL
: (uint)RemoteStreamReaderConstants.COMMAND_FAILED);
if (getSignalExEx)
{
tcpStream.WriteBoolean(pPresent);
tcpStream.WriteBoolean(pPresent);
tcpStream.WriteInt32BE(pRFLevel);
tcpStream.WriteFloat(pSNR);
tcpStream.WriteFloat(pBER);
}
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SKYSCRAPER_ENGINE_NAME:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.WriteUTF8(localStreamReader.GetEngineName());
tcpStream.Flush();
break;
case (uint)RemoteStreamReaderConstants.REQUEST_SKYSCRAPER_ENGINE_VERSION:
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_SUCCESSFUL);
tcpStream.WriteVersion(localStreamReader.GetEngineVersion());
tcpStream.Flush();
break;
default:
Console.WriteLine("Recieved unknown command {0:X8}", opcode);
tcpStream.WriteUInt32BE((uint)RemoteStreamReaderConstants.COMMAND_NOT_UNDERSTOOD);
tcpStream.Flush();
break;
}
}
tcpStream.Close();
tcpClient.Close();
clientConnected = false;
}
private Dictionary<IntPtr, FilterServer> filterServers;
class FilterServer : IDisposable
{
public FilterServer()
{
clients = new List<TcpClientWrapped>();
}
private byte[] buffer;
public void DvbCallback(IntPtr pointer, int length)
{
if (buffer == null)
buffer = new byte[188];
Marshal.Copy(pointer, buffer, 0, 188);
lock (clients)
{
foreach (TcpClientWrapped tcpClient in clients)
{
try
{
tcpClient.DropPacket(buffer, 0, 188);
}
catch (Exception e)
{
if (tcpClient.wrapped.Client != null)
{
Console.WriteLine("Lost filter client: {0}", tcpClient.wrapped.Client.RemoteEndPoint);
}
clients.Remove(tcpClient);
break;
}
}
}
}
public IPAddress ListenIp { get; set; }
public Thread Thread { get; set; }
public TcpListener TcpListener { get; set; }
public List<TcpClientWrapped> clients;
public class TcpClientWrapped : IDisposable
{
public TcpClientWrapped(TcpClient client)
{
this.wrapped = client;
this.bufferedStream = new BufferedStream(wrapped.GetStream(), 96256);
}
internal TcpClient wrapped;
internal BufferedStream bufferedStream;
public void Dispose()
{
wrapped?.Dispose();
bufferedStream?.Dispose();
}
public void Close()
{
try
{
bufferedStream?.Close();
wrapped?.Close();
}
catch (IOException ioe)
{
Console.WriteLine("Failed to properly close TCPClient");
}
}
internal void DropPacket(byte[] buffer, int offset, int length)
{
bufferedStream?.Write(buffer, offset, length);
}
}
public void Run()
{
while (!disposed)
{
try
{
TcpClient acceptTcpClient = TcpListener.AcceptTcpClient();
Console.WriteLine("Accepted Filter client {0}", acceptTcpClient.Client.RemoteEndPoint);
lock (clients)
{
clients.Add(new TcpClientWrapped(acceptTcpClient));
}
}
catch (Exception e)
{
break;
}
}
if (!disposed)
Dispose();
}
private bool disposed;
public void Dispose()
{
TcpListener.Stop();
disposed = true;
}
}
}
}