peerdetector.cs

来自「破解的飞信源代码」· CS 代码 · 共 420 行 · 第 1/2 页

CS
420
字号
namespace Imps.Client.Core.P2P.ICE
{
    using Imps.Client.Core;
    using Imps.Client.Utils;
    using System;
    using System.Collections.Generic;
    using System.Diagnostics;
    using System.Net;
    using System.Net.NetworkInformation;
    using System.Net.Sockets;
    using System.Runtime.CompilerServices;
    using System.Security.Cryptography;
    using System.Threading;

    public class PeerDetector : IDisposable
    {
        private const int BufferSize = 0x100;
        private readonly Thread detectThread;
        private readonly ICryptoTransform encryptor;
        private const int GuidLength = 0x10;
        private const int Int32TypeSize = 4;
        private const int IPAddressTypeSize = 4;
        private const int KeyOffset = 1;
        private readonly Stopwatch lastSendTime = new Stopwatch();
        private const int LongTypeSize = 8;
        private const string mcastAddress = "225.102.116.110";
        private readonly Dictionary<Socket, byte[]> mcastEelements;
        private static readonly IPEndPoint mcastEndPoint = new IPEndPoint(IPAddress.Parse("225.102.116.110"), 0x2af8);
        private const int mcastPort = 0x2af8;
        private const int SelectTimeout = 0x1e8480;
        public const int SendRegMessageInterval = 0x7530;
        private readonly long sid;
        private bool stop;
        private readonly Socket tcpListener;
        private readonly int tcpPort;

        public event EventHandler<PeerAcceptedEventArgs> PeerAccepted;

        public event EventHandler<PeerFoundEventArgs> PeerFound;

        public PeerDetector(Socket listener, long sid)
        {
            this.tcpListener = listener;
            this.stop = false;
            this.mcastEelements = new Dictionary<Socket, byte[]>();
            this.detectThread = new Thread(new ThreadStart(this.DetectProc));
            long num = sid;
            this.sid = sid;
            this.tcpPort = ((IPEndPoint) listener.LocalEndPoint).Port;
            byte[] sidArray = BitConverter.GetBytes(num);
            this.encryptor = CreateEncryptor(sidArray);
        }

        private void CloseAllMCastSockets()
        {
            lock (this.mcastEelements)
            {
                Dictionary<Socket, byte[]>.KeyCollection.Enumerator enumerator = this.mcastEelements.get_Keys().GetEnumerator();
                try
                {
                    while (enumerator.MoveNext())
                    {
                        Socket socket = enumerator.get_Current();
                        try
                        {
                            socket.Close();
                            continue;
                        }
                        catch
                        {
                            continue;
                        }
                    }
                }
                finally
                {
                    enumerator.Dispose();
                }
                this.mcastEelements.Clear();
            }
        }

        private byte[] ComputeRegData(IPAddress address, int port)
        {
            byte[] src = BitConverter.GetBytes(this.sid);
            byte[] addressBytes = address.GetAddressBytes();
            byte[] bytes = BitConverter.GetBytes(port);
            byte[] dst = new byte[addressBytes.Length + bytes.Length];
            Buffer.BlockCopy(addressBytes, 0, dst, 0, addressBytes.Length);
            Buffer.BlockCopy(bytes, 0, dst, addressBytes.Length, bytes.Length);
            byte[] buffer5 = this.encryptor.TransformFinalBlock(dst, 0, dst.Length);
            byte[] buffer6 = new byte[buffer5.Length + src.Length];
            Buffer.BlockCopy(src, 0, buffer6, 0, src.Length);
            Buffer.BlockCopy(buffer5, 0, buffer6, src.Length, buffer5.Length);
            return buffer6;
        }

        private static ICryptoTransform CreateDecryptor(byte[] sidArray)
        {
            using (SymmetricAlgorithm sa = DES.Create())
            {
                byte[] a = sidArray;
                sa.IV = a;
                GenerateKey(sa, a);
                return sa.CreateDecryptor();
            }
        }

        private static ICryptoTransform CreateEncryptor(byte[] sidArray)
        {
            using (SymmetricAlgorithm sa = DES.Create())
            {
                byte[] a = sidArray;
                sa.IV = a;
                GenerateKey(sa, a);
                return sa.CreateEncryptor();
            }
        }

        private static Peer Decrypt(byte[] msg, int length)
        {
            byte[] src;
            byte[] dst = new byte[8];
            Buffer.BlockCopy(msg, 0, dst, 0, dst.Length);
            using (ICryptoTransform transform = CreateDecryptor(dst))
            {
                src = transform.TransformFinalBlock(msg, 8, length - 8);
            }
            if ((src == null) || (src[0] == 0))
            {
                return null;
            }
            byte[] buffer3 = new byte[4];
            Buffer.BlockCopy(src, 0, buffer3, 0, buffer3.Length);
            Peer peer = new Peer(BitConverter.ToInt64(msg, 0));
            peer.AddUsableEndPoint(new IPEndPoint(new IPAddress(buffer3), BitConverter.ToInt32(src, 4)));
            peer.Mode = TransportMode.P2PV3;
            return peer;
        }

        private void DetectProc()
        {
            List<Socket> checkRead;
            byte[] buffer = new byte[0x100];
            lock (this.mcastEelements)
            {
                checkRead = new List<Socket>(this.mcastEelements.get_Keys());
            }
            checkRead.Add(this.tcpListener);
            while (!this.stop)
            {
                try
                {
                    Socket.Select(checkRead, null, null, 0x1e8480);
                    this.ProcessReadySockets(buffer, checkRead);
                    this.SendRegMessage();
                    checkRead.Clear();
                    lock (this.mcastEelements)
                    {
                        checkRead.AddRange(this.mcastEelements.get_Keys());
                    }
                    checkRead.Add(this.tcpListener);
                    continue;
                }
                catch (Exception exception)
                {
                    ClientLogger.WriteGeneral("DetectProc内部循环出错", exception.ToString(), 10);
                    continue;
                }
            }
        }

        public void Dispose()
        {
            this.Unregister();
        }

        private void DoAccept()
        {
            Socket tranSock = null;
            try
            {
                tranSock = this.tcpListener.Accept();
                Stopwatch stopwatch = Stopwatch.StartNew();
                byte[] buffer = new byte[0x10];
                int offset = 0;
                while (stopwatch.get_ElapsedMilliseconds() < 0x3e8)
                {
                    if (tranSock.Poll(0x2710, SelectMode.SelectRead))
                    {
                        offset += tranSock.Receive(buffer, offset, buffer.Length - offset, SocketFlags.None);
                        if (offset == 0x10)
                        {
                            this.FirePeerAccepted(new PeerAcceptedEventArgs(tranSock, new Guid(buffer)));
                            return;
                        }
                    }
                }
            }
            catch (Exception exception)
            {
                ClientLogger.WriteGeneral("DoAccept failed.", exception.ToString(), 10);
            }
            try
            {
                if (tranSock != null)
                {
                    tranSock.Close();
                }
            }

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?