UDPRouter

调试UDP包交互时,在网上没有找到一个好的端口转发工具。便自己实现了一个UDP端口转发器。

.net 4.0

using System;
using System.Collections.Generic;
using System.Collections.Concurrent;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Net;

namespace TcpRouter
{
    class Program
    {
        private int listenPort;
        private string ip;
        private int port;
        private ConcurrentDictionary<IPEndPoint, ProxyItem> proxies = new ConcurrentDictionary<IPEndPoint, ProxyItem>();
        private TcpListener listener;
        private log4net.ILog log;

        public Program(int listenPort, string ip, int port)
        {
            // TODO: Complete member initialization
            this.listenPort = listenPort;
            this.ip = ip;
            this.port = port;
        }
        static void Main(string[] args)
        {
            log4net.Config.XmlConfigurator.ConfigureAndWatch(new System.IO.FileInfo(System.AppDomain.CurrentDomain.SetupInformation.ConfigurationFile));


            Console.Write("请输入监听端口:");
            int listenPort = int.Parse(Console.ReadLine());


            Console.Write("请输入转发目标(IP:PORT):");
            string strDest = Console.ReadLine();

            string ip;
            int port;

            {
                string[] items = strDest.Split(':');

                ip = items[0];
                port = int.Parse(items[1]);
            }

            Console.Title = string.Format("TCP:{0}=>{1}", listenPort, strDest);

            Program p = new Program(listenPort, ip, port);
            p.Run();
        }

        private void Run()
        {
            this.log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
            System.AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException);
            IPEndPoint localEP = new IPEndPoint(IPAddress.Any, this.listenPort);
            this.listener = new TcpListener(localEP);
            listener.Start(100);
            listener.BeginAcceptSocket(OnAccepted, listener);

            Console.ReadLine();
        }

        void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
        {
            log.Fatal("UnhandledException", (Exception)e.ExceptionObject);
        }
        public void OnAccepted(IAsyncResult ar)
        {
            TcpListener listener = ar.AsyncState as TcpListener;
            Socket remoteSocket = listener.EndAcceptSocket(ar);
            listener.BeginAcceptSocket(OnAccepted, listener);
            Socket proxy = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            try
            {
                proxy.BeginConnect(this.ip, this.port, arConn =>
                {
                    try
                    {
                        proxy.EndConnect(arConn);

                        this.SetupProxy(new ProxyItem() { Proxy = proxy, RemoteSocket = remoteSocket });

                    }
                    catch (Exception exp)
                    {
                        log.Debug(exp.Message);

                        //断开连接
                        //remoteSocket.BeginDisconnect(false, ardc => {
                        //    remoteSocket.EndDisconnect(ardc);
                        //}, remoteSocket);

                        //改为增加日志
                        byte[] buffer = new byte[1024];
                        remoteSocket.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, arRecv =>
                        {
                            try
                            {
                                int received = remoteSocket.EndReceive(arRecv);

                                this.Print(remoteSocket.RemoteEndPoint.ToString(), "non", buffer, 0, received);
                            }
                            catch (SocketException ex)
                            {
                                log.Debug(ex);
                            }
                            catch (ObjectDisposedException ex)
                            {
                                log.Debug(ex);
                            }


                        }, null);
                    }

 

                }, proxy);
            }
            catch (Exception exp)
            {
                log.Debug(exp);
            }

        }

        private void SetupTransfer(Socket src, Socket des)
        {
            string srcAddress = src.RemoteEndPoint.ToString();
            string desAddress = des.RemoteEndPoint.ToString();

            byte[] buffer = new byte[1024];
            Action<IAsyncResult> action = null;
           
            action = new Action<IAsyncResult>(ar =>
            {
                int received = -1;
                try
                {
                    received = src.EndReceive(ar);
                }
                catch (Exception exp)
                {

                    log.ErrorFormat("src.EndReceive ERROR, srcAddress:{0},{1}", srcAddress, exp.Message);
                    try
                    {
                        des.Disconnect(false);
                        log.Debug("断开连接" + desAddress);

                    }
                    catch{}
                }
             

                if(received > 0)
                {

                    this.Print(srcAddress, desAddress, buffer, 0, received);
                    try
                    {
                        des.BeginSend(buffer, 0, received, SocketFlags.None, arSend =>
                        {
                            try
                            {
                                des.EndSend(arSend);
                            }
                            catch (Exception exp)
                            {
                                log.ErrorFormat("des.EndSend ERROR, desAddress:{0},{1}", desAddress, exp.Message);
                                log.Error(exp);
                                try
                                {
                                    src.Disconnect(false);
                                    log.Debug("断开连接" + srcAddress);
                                }
                                catch { }
                                return;
                            }

                            try
                            {
                                src.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, new AsyncCallback(action), null);
                            }
                            catch (Exception exp)
                            {
                                log.ErrorFormat("src.BeginReceive ERROR, srcAddress:{0},{1}", srcAddress, exp.Message);
                                log.Error(exp);
                                try
                                {
                                    des.Disconnect(false);
                                    log.Debug("断开连接" + desAddress);
                                }
                                catch { }
                                try
                                {
                                    src.Disconnect(false);
                                    log.Debug("断开连接" + srcAddress);
                                }
                                catch { }
                            }


                        }, des);
                    }
                    catch (Exception exp)
                    {
                        log.ErrorFormat("des.BeginSend ERROR, srcAddress:{0},{1}", srcAddress, exp.Message);
                        log.Error(exp);
                        try
                        {
                            des.Disconnect(false);
                            log.Debug("断开连接" + desAddress);
                        }
                        catch { }
                        try
                        {
                            src.Disconnect(false);
                            log.Debug("断开连接" + srcAddress);
                        }
                        catch { }
                    }
                }
                else
                {
                    log.ErrorFormat("主动断开连接, srcAddress:{0},{1}", srcAddress, "没有收到数据");
                    //应该是断开了
                    try
                    {
                        des.Disconnect(false);
                        log.Debug("断开连接" + desAddress);
                    }
                    catch { }
                    try
                    {
                        src.Disconnect(false);
                        log.Debug("断开连接" + srcAddress);
                    }
                    catch { }
                }
               
            });

            try
            {
                src.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, new AsyncCallback(action), null);
            }
            catch (Exception exp)
            {
                log.Debug(exp);
                try
                {
                    des.Disconnect(false);
                    log.Debug("断开连接" + desAddress);
                }
                catch { }
                try
                {
                    src.Disconnect(false);
                    log.Debug("断开连接" + srcAddress);
                }
                catch { }
            }

        }


        private void SetupProxy(ProxyItem proxy)
        {
            var p = proxy;
            SetupTransfer(proxy.RemoteSocket, proxy.Proxy);
            SetupTransfer(proxy.Proxy, proxy.RemoteSocket);
        }


        private void Print(string src, string des, byte[] bytes, int offset , int count)
        {
            string str = string.Format("{0}=>{1}:{2}", src, des, BitConverter.ToString(bytes, offset, count));
            //Console.WriteLine(str);
            log.Debug(str);
        }
    }


    public class ProxyItem
    {

        public Socket RemoteSocket { get; set; }

        public Socket Proxy { get; set; }

    }
}

 

posted @ 2011-12-26 09:32  阿牛  阅读(268)  评论(0编辑  收藏  举报