C#基于SOCKET通信开发的Telnet模拟工具

来源:互联网 发布:mysql大小写敏感开关 编辑:程序博客网 时间:2024/06/10 21:00
最近在折腾网络方面的通讯协议,每次熟悉协议的时候,总是习惯用telnet来测试,但是在测试的过程中,很纠结的是,有的地方输入不能

出错,一出错就得重新输入,而且还不能像CMD命令一样,可以通过方向键回到之前的输入。在痛苦了多次后,决定做一个类似Telnet功能的

模拟工具,更确切的说是基于SOCKET的网络通信工具,以便更好的进行SMTP/POP3/IMAP的测试。实现在的关键代码如下:

using System;using System.Collections.Generic;using System.ComponentModel;using System.Data;using System.Drawing;using System.Linq;using System.Text;using System.Windows.Forms;using System.Net.Sockets;using UtilSp.ClassLib;using System.Linq.Expressions;using System.Threading;namespace SocketLink{    public partial class FormMain : Form    {        public FormMain()        {            InitializeComponent();        }        private Socket socket_ = null;        private Helper helper_ = new Helper();//In order to automatically update data to UI with binding property.        private int receiveLen_max_ = 0xFFFF;        private Thread receiveThread_ = null;        private Encoding receiveEncoding_ = Encoding.UTF8;        private bool needConvertBase64Received_ = false;        private string lineBreak_ = "\r\n";        private void buttonConnect_Click(object sender, EventArgs e)        {            try            {                string host = textBoxHost.Text;                string port = textBoxPort.Text;                if (string.IsNullOrEmpty(host))                {                    showMessage(Tip.hostEmpty);                    return;                }                if (string.IsNullOrEmpty(port))                {                    showMessage(Tip.portEmpty);                    return;                }                if (!IpPortSp.isPort(port))                {                    MessageBox.Show(Tip.portIllegal);                    return;                }                socket_ = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);                socket_.Connect(host, Convert.ToInt32(port));                if (!socket_.Connected)                {                    showBackInfo(Tip.connectFail);                    return;                }                receiveThread_ = new Thread(receiveCallBack);//Create thread to listen receive from socket.                receiveThread_.IsBackground = true;                receiveThread_.Start();                helper_.connectEnabled_pro = false;                helper_.disconnectEnabled_pro = true;                helper_.sendEnabled_pro = true;                showBackInfo(Tip.connectOK);            }            catch (System.Exception ex)            {                showBackInfo(ex.Message);            }        }        private void showMessage(string message)        {            MessageBox.Show(message);        }        private void showBackInfo(string backInfo, bool isNeedInvoke = false)        {            if (isNeedInvoke)            {                this.Invoke((Action)(() =>                {                    helper_.backInfo_pro += backInfo + "\r\n";                                    }));            }            else            {                helper_.backInfo_pro += backInfo + "\r\n";            }        }        public class Helper : INotifyPropertyChanged //Automatically update UI data class        {            #region backInfo Property            private string backInfo_ = "";            public string backInfo_pro            {                get                {                    return backInfo_;                }                set                {                    if (value == backInfo_)                    {                        return;                    }                    backInfo_ = value;                    NotifyPropertyChanged(() => backInfo_pro);                }            }            #endregion            #region connectEnabled Property            private bool connectEnabled_ = true;            public bool connectEnabled_pro            {                get                {                    return connectEnabled_;                }                set                {                    if (value == connectEnabled_)                    {                        return;                    }                    connectEnabled_ = value;                    NotifyPropertyChanged(() => connectEnabled_pro);                }            }            #endregion            #region backInfo NotifyPropertyChanged            public void NotifyPropertyChanged<T>(Expression<Func<T>> property)            {                if (PropertyChanged == null)                {                    return;                }                var memberExpression = property.Body as MemberExpression;                if (memberExpression == null)                {                    return;                }                PropertyChanged.Invoke(this, new PropertyChangedEventArgs(memberExpression.Member.Name));            }            public event PropertyChangedEventHandler PropertyChanged;            #endregion            #region disconnectEnabled Property            private bool disconnectEnabled_ = false;            public bool disconnectEnabled_pro            {                get                {                    return disconnectEnabled_;                }                set                {                    if (value == disconnectEnabled_)                    {                        return;                    }                    disconnectEnabled_ = value;                    NotifyPropertyChanged(() => disconnectEnabled_pro);                }            }            #endregion            #region sendEnabled Property            private bool sendEnabled_ = false;            public bool sendEnabled_pro            {                get                {                    return sendEnabled_;                }                set                {                    if (value == sendEnabled_)                    {                        return;                    }                    sendEnabled_ = value;                    NotifyPropertyChanged(() => sendEnabled_pro);                }            }            #endregion        }        private void FormMain_Load(object sender, EventArgs e)        {            initializeUI();            binding();        }        private void binding()//Binding property with helper_ and automatically update data.         {            textBoxInfo.DataBindings.Add("Text", helper_, "backInfo_pro");            buttonConnect.DataBindings.Add("Enabled", helper_, "connectEnabled_pro");            buttonDisconnect.DataBindings.Add("Enabled", helper_, "disconnectEnabled_pro");            buttonSend.DataBindings.Add("Enabled", helper_, "sendEnabled_pro");        }        private void initializeUI()        {            comboBoxSendEncoding.SelectedIndex = 2;            comboBoxReceiveEncoding.SelectedIndex = 2;        }        private void buttonDisconnect_Click(object sender, EventArgs e)        {            try            {                if (socket_ == null)                {                    return;                }                socket_.Close();                if (socket_ == null)                {                    this.showBackInfo(Tip.disconnectFail);                }                else                {                    helper_.connectEnabled_pro = true;                    helper_.disconnectEnabled_pro = false;                    helper_.sendEnabled_pro = false;                    this.showBackInfo(Tip.disconnectOK);                }            }            catch (System.Exception ex)            {                this.showBackInfo(ex.Message);            }        }        private void buttonSend_Click(object sender, EventArgs e)        {            try            {                string sendStr = textBoxSendData.Text;                if (string.IsNullOrEmpty(sendStr))                {                    showBackInfo(Tip.sendDataEmpty);                    return;                }                if (!socket_.Connected)                {                    showBackInfo(Tip.notConnect);                    return;                }                showBackInfo(Tip.sending);                string sendEncodingName = comboBoxSendEncoding.Text;                if (string.IsNullOrEmpty(sendEncodingName))                {                    showBackInfo(Tip.sendEncodingEmpty);                    return;                }                string receiveEncodingName = comboBoxReceiveEncoding.Text;                if (string.IsNullOrEmpty(receiveEncodingName))                {                    showBackInfo(Tip.receiveEncodingEmpty);                    return;                }                Encoding sendEncoding = Encoding.GetEncoding(sendEncodingName);                receiveEncoding_ = Encoding.GetEncoding(receiveEncodingName);                sendStr += checkBoxAutoAddLineBreak.Checked ? lineBreak_ : "";//Automaticall add line break.SMTP/POP3/IMAP need.                byte[] sendData = null;                if (checkBoxToBase64.Checked)                {                    sendData = Base64Sp.tobase64Bytes(sendStr, sendEncoding);                }                else                {                    sendData = sendEncoding.GetBytes(sendStr);                }                socket_.Send(sendData);                showBackInfo(Tip.sendCompleted + Tip.receiving);                if (checkBoxAutoClear.Checked)                {                    textBoxSendData.Text = "";                }            }            catch (System.Exception ex)            {                showBackInfo(ex.Message);            }        }        private void receiveCallBack()        {            int receiveTimes_max = 5;            int receiveTimes_accmulate = 0;            while (true)            {                try                {                    if (socket_ == null)                    {                        break;                    }                    byte[] receiveBuffer_ = new byte[receiveLen_max_];                    int receiveLen = socket_.Receive(receiveBuffer_);                    #region Automatically disconnect when receive empty times reach receiveTimes_max                    if (receiveLen <= 0)                    {                        if (receiveTimes_accmulate > receiveTimes_max)                        {                            showBackInfo(Tip.lostConnect, true);                            this.Invoke((Action)(() => { buttonDisconnect_Click(null, EventArgs.Empty); }));                            break;                        }                        Thread.Sleep(1000);                        receiveTimes_accmulate++;                        continue;                    }                    #endregion                    receiveTimes_accmulate = 0;//If received data,times reset 0.                    string receiveStr = receiveEncoding_.GetString(receiveBuffer_, 0, receiveLen);                    if (needConvertBase64Received_)                    {                        receiveStr = Base64Sp.toNormalStr(receiveStr, receiveEncoding_);                    }                    showBackInfo(receiveStr, true);                }                catch (System.Exception ex)                {                    break;                }            }        }        private class Tip        {            public static string base64ToNormalTip = "Convert base64 string that selected in the info to normal string with encode.Then auto copy result to clipboard.";            public static string connectOK = "Connect OK!";            public static string connectFail = "Connect Fail!";            public static string disconnectOK = "Disconnect OK!";            public static string disconnectFail = "Disconnect Fail!";            public static string hostEmpty = "Host is empty!";            public static string notConnect = "Not connect!";            public static string portEmpty = "Port is empty!";            public static string portIllegal = "Port is illegal!";            public static string receiveEncodingEmpty = "Receive encode is empty!";            public static string receiveEncodingTip = "Different protocol need different encoding!";            public static string receiving = "Receiving...";            public static string receiveCompleted = "Receive completed!";            public static string sendDataEmpty = "Send data is empty!";            public static string sendEncodingEmpty = "Send encode is empty!";            public static string sendEncodingTip = "Different protocol need different encoding!";            public static string sending = "Sending...";            public static string sendCompleted = "Send data completed!";            public static string sendDataTip = "You may need to add line break when communicate by SMTP/IMAP/POP3 etc.!";            public static string toBase64Tip = "You may need convert string to base64 when send user name on SMTP.";        }        private void buttonBase64StrToNormalStr_Click(object sender, EventArgs e)        {//Need convert to normal string when received base64 string.            try            {                string base64Str = "";                base64Str = textBoxInfo.SelectedText;                if (string.IsNullOrEmpty(base64Str))                {                    return;                }                string receiveEncodingName = comboBoxReceiveEncoding.Text;                if (string.IsNullOrEmpty(receiveEncodingName))                {                    showBackInfo(Tip.receiveEncodingEmpty);                    return;                }                receiveEncoding_ = Encoding.GetEncoding(receiveEncodingName);                string normalStr = Base64Sp.toNormalStr(base64Str, receiveEncoding_);                Clipboard.SetText(normalStr);                MessageBox.Show(normalStr);            }            catch (System.Exception ex)            {                MessageBox.Show(ex.Message);            }        }        private void textBoxSendData_MouseHover(object sender, EventArgs e)        {            toolTipInfo.Show(Tip.sendDataTip, sender as Control);        }        private void checkBoxToBase64_MouseHover(object sender, EventArgs e)        {            toolTipInfo.Show(Tip.toBase64Tip, sender as Control);        }        private void comboBoxSendEncoding_MouseHover(object sender, EventArgs e)        {            toolTipInfo.Show(Tip.sendEncodingTip, sender as Control);        }        private void comboBoxReceiveEncoding_MouseHover(object sender, EventArgs e)        {            toolTipInfo.Show(Tip.receiveEncodingTip, sender as Control);        }        private void buttonBase64StrToNormalStr_MouseHover(object sender, EventArgs e)        {            toolTipInfo.Show(Tip.base64ToNormalTip, sender as Control);        }    }}


转载请注明出处http://blog.csdn.net/xxdddail/article/details/9471079