c# Socket Udp通讯示例源码

读卡器介绍: https://item.taobao.com/item.htm?spm=a1z10.5-c.w4002-17663462238.15.55615b43otkNYI&id=22173428704https://item.taobao.com/item.htm?spm=a1z10.5-c.w4002-17663462238.15.55615b43otkNYI&id=22173428704 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Collections;
using System.Collections.Specialized;

namespace ConsoleApp
{
    class Program
    {
        private static Socket newsock;
        private static EndPoint Remote;
        private static string localIp;

        static void Main(string[] args)
        {
            ArrayList AllIp = new ArrayList();
            string name = Dns.GetHostName();            
            IPAddress[] ipadrlist = Dns.GetHostAddresses(name);
            foreach (IPAddress ipa in ipadrlist)
            {
                if (ipa.AddressFamily == AddressFamily.InterNetwork)
                    localIp = ipa.ToString();
                    if (checkip(localIp))
                    {
                        AllIp.Add(localIp);
                        Console.WriteLine("IPv4地址:"+localIp);
                    } 
            }
            localIp = AllIp[0].ToString();  //如有多个网卡可选任意一个            
            ReceviceData();
        }

        private static bool checkip(string ipstr)   //判断IP是否合法
        {    
            IPAddress ip;
            if (IPAddress.TryParse(ipstr, out ip))
            { return true; }
            else { return false; }
        }

        static void ReceviceData()
        {                   
            IPEndPoint ipep = new IPEndPoint(IPAddress.Parse(localIp), 39169);
            newsock = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);            
            newsock.Bind(ipep);
            Console.WriteLine("绑定地址:" + localIp+":39169\n");
            //发送信息
            byte[] sendbuf = new byte[1];
            sendbuf[0] = 0xa6; //搜寻所有连线的读卡器命令
                               
            IPEndPoint ipep1 = new IPEndPoint(IPAddress.Broadcast, 39169);
            Remote = (EndPoint)(ipep1);
            newsock.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.Broadcast, 1);//设为广播式发送
            newsock.SendTo(sendbuf, 1, SocketFlags.None, Remote);
            Console.WriteLine("SendTo:"+ (Convert.ToString(Remote)+"                      ").Substring(0,21)  + " Data:A6");

            Thread thread = new Thread(new ThreadStart(GetData));
            thread.Start();
        }

        static void GetData()
        {
            try
            {
                byte[] buf = new byte[1024];
                byte[] sendbuf = new byte[255];
                byte[] revbufheadbak = new byte[20];
                while (true)
                {
                    if (newsock == null || newsock.Available < 1)
                    {
                        Thread.Sleep(20);
                        continue;
                    }

                    //接受UDP数据包
                    int recv = newsock.ReceiveFrom(buf, ref Remote);
                    string RemoteIP = Convert.ToString(Remote).Split(':')[0];                 //sock来源IP
                    int RemotePort = Convert.ToInt32(Convert.ToString(Remote).Split(':')[1]); //Sock来源端口

                    string recestr = "FromIP:" + (Convert.ToString(Remote) + "                      ").Substring(0, 21) + " Data:";       //将接收到的数据显示
                    for (int i = 0; i < recv; i++)
                    {
                        recestr = recestr + buf[i].ToString("X2") + " ";
                    }
                    Console.WriteLine(recestr);

                    if (recv>8){
                        if (buf[0] == revbufheadbak[0] && buf[1] == revbufheadbak[1] && buf[2] == revbufheadbak[2] && buf[3] == revbufheadbak[3] && buf[4] == revbufheadbak[4] && buf[5] == revbufheadbak[5] && buf[6] == revbufheadbak[6] && buf[7] == revbufheadbak[7] && buf[8] == revbufheadbak[8])
                        {
                            DisableSendAge(buf, RemoteIP, RemotePort);  //是重复接收的数据包,回应确认接收,不做处理
                            return;
                        } else {
                            for (int i=0;i<9;i++){
                                revbufheadbak[i] = buf[i];  //将当前接收到的数据前9个字节保存,用于再次接收到数据时比对
                            }
                        }
                    }

                    switch (buf[0])
                    {
                        case 0xf2://读卡器响应服务器的搜索指令、上电开机时上传信息
                             Console.WriteLine("数据解析:读卡器上电开机、响应搜索指令的返回信息");
                             Console.WriteLine("功能码:" + buf[0].ToString("X2"));
                             Console.WriteLine("读卡器IP:"+buf[1].ToString("D") + "." + buf[2].ToString("D") + "." + buf[3].ToString("D") + "." + buf[4].ToString("D"));
                             Console.WriteLine("读卡器掩码:"+buf[5].ToString("D") + "." + buf[6].ToString("D") + "." + buf[7].ToString("D") + "." + buf[8].ToString("D"));
                             Console.WriteLine("通讯端口:" + (buf[9] + buf[10] * 256).ToString("D"));
                             Console.WriteLine("机号:" + (buf[11] + buf[12] * 256).ToString("D"));
                             Console.WriteLine("网关:" + buf[13].ToString("D") + "." + buf[14].ToString("D") + "." + buf[15].ToString("D") + "." + buf[16].ToString("D"));
                             Console.WriteLine("网关MAC:" + buf[17].ToString("X2") + "-" + buf[18].ToString("X2") + "-" + buf[19].ToString("X2") + "-" + buf[20].ToString("X2") + "-" + buf[21].ToString("X2") + "-" + buf[22].ToString("X2"));
                             Console.WriteLine("目标服务器IP:" + buf[23].ToString("D") + "." + buf[24].ToString("D") + "." + buf[25].ToString("D") + "." + buf[26].ToString("D"));
                             Console.WriteLine("服务器MAC:" + buf[27].ToString("X2") + "-" + buf[28].ToString("X2") + "-" + buf[29].ToString("X2") + "-" + buf[30].ToString("X2") + "-" + buf[31].ToString("X2") + "-" + buf[32].ToString("X2"));
                             Console.WriteLine("网络标识:" + buf[33].ToString("X2"));
                             Console.WriteLine("响声标识:" + buf[34].ToString("X2"));
                             Console.WriteLine("通讯模块号:" + buf[35].ToString("D") + "-" + buf[36].ToString("D") + "-" + buf[37].ToString("D") + "-" + buf[38].ToString("D"));
                             if (recv > 38)
                             {
                                 string SerialNum = "";
                                 for (int i = 38; i < recv; i++)
                                 {
                                     SerialNum = SerialNum + buf[i].ToString("X2");
                                 }
                                 Console.WriteLine("唯一设备标识:" + SerialNum + "\n");
                             }
                             break;
                        case 0xf3://读卡器发送的心跳数据包

                             break;
                        case 0xf8://

                             break;
                        case 0xc1://IC只读卡号返回   
                             DisableSendAge(buf, RemoteIP, RemotePort); //确定接收到数据包,否则读卡器会发三次
                             Console.WriteLine("数据解析:接收到的信息是IC只读卡号数据包");
                             Console.WriteLine("功能码:" + buf[0].ToString("X2"));
                             Console.WriteLine("读卡器IP:"+buf[1].ToString("D") + "." + buf[2].ToString("D") + "." + buf[3].ToString("D") + "." + buf[4].ToString("D"));
                             Console.WriteLine("机号:" + (buf[5] + buf[6] * 256).ToString("D"));
                             Console.WriteLine("包序号:" + (buf[7] + buf[8] * 256).ToString("D"));
                             Console.WriteLine("16进制卡号:" + buf[10].ToString("X2") + buf[11].ToString("X2") + buf[12].ToString("X2") + buf[13].ToString("X2"));
                             uint cardhao = (uint)(buf[13] * 256 * 256 * 256 + buf[12] * 256 * 256 + buf[11] * 256 + buf[10]);
                             string cardnum = cardhao.ToString("D10");
                             Console.WriteLine("换算成10进制卡号:" + cardnum);
                             if (recv > 14)
                             {
                                 string SerialNum = "";
                                 for (int i = 14; i < recv; i++)
                                 {
                                     SerialNum = SerialNum + buf[i].ToString("X2");
                                 }
                                 Console.WriteLine("唯一设备标识:" + SerialNum+"\n");
                             }

                             //此处可加入业务对数据库的查、增、删、改

                             SendDispBeep(cardnum, RemoteIP, RemotePort);
                             break;
                        case 0xc2://接收到IC读卡器的按键信息
                        case 0xd2://接收到ID读卡器的按键信息
                             break;
                        case 0xc3://IC全扇区读写器主动读取扇区信息返回
                             break;
                        case 0xc5://IC全扇区读写器指定区号、密码读扇区内容返回
                             break;
                        case 0xcd://IC全扇区读写器指定区号、密码写卡及更改密码返回
                             break;
                        case 0xcf://接收到IC卡离开读卡器的信息
                        case 0xdf://接收到ID卡离开读卡器的信息
                             break;
                        case 0xd1://ID读卡器读卡后返回
                             DisableSendAge(buf, RemoteIP, RemotePort); //确定接收到数据包,否则读卡器会发三次
                             Console.WriteLine("数据解析:接收到的信息是IC只读卡号数据包");
                             Console.WriteLine("功能码:" + buf[0].ToString("X2"));
                             Console.WriteLine("读卡器IP:"+buf[1].ToString("D") + "." + buf[2].ToString("D") + "." + buf[3].ToString("D") + "." + buf[4].ToString("D"));
                             Console.WriteLine("机号:" + (buf[5] + buf[6] * 256).ToString("D"));
                             Console.WriteLine("包序号:" + (buf[7] + buf[8] * 256).ToString("D"));
                             Console.WriteLine("16进制卡号:" + buf[9].ToString("X2") + buf[10].ToString("X2") + buf[11].ToString("X2") + buf[12].ToString("X2"));
                             cardhao = (uint)(buf[12] * 256 * 256 * 256 + buf[11] * 256 * 256 + buf[10] * 256 + buf[9]);
                             cardnum = cardhao.ToString("D10");
                             Console.WriteLine("换算成10进制卡号:" + cardnum);
                             if (recv > 14)
                             {
                                 string SerialNum = "";
                                 for (int i = 14; i < recv; i++)
                                 {
                                     SerialNum = SerialNum + buf[i].ToString("X2");
                                 }
                                 Console.WriteLine("唯一设备标识:" + SerialNum+"\n");
                             }

                             //此处可加入业务对数据库的查、增、删、改

                             SendDispBeep(cardnum, RemoteIP, RemotePort);
                             break;
                        default:
                            break;
                    }                    
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);
            }
        }
        
        static void DisableSendAge(byte[] buf, string RemortIpStr, int RemortPortInt)
        {   //回应已接收到数据包,否则读卡器会连发三次
            buf[0] = 0x69;
            IPEndPoint client = new IPEndPoint(IPAddress.Parse(RemortIpStr), RemortPortInt);
            newsock.SendTo(buf, 9, SocketFlags.None, client);
            string SendInf = "SendTo:" + (Convert.ToString(client) + "                      ").Substring(0, 21) + " Data:";
            for (int i = 0; i < 9; i++)
            {
                SendInf = SendInf + buf[i].ToString("X2")+" ";
            }
            Console.WriteLine(SendInf);
        }

        static void SendDispBeep(string cardnum, string RemortIpStr, int RemortPortInt)
        {   //向读卡器发送显示文字及蜂鸣响声
            string DispInf = "卡号:" + cardnum + "  " + DateTime.Now.ToString("yyyy-MM-dd hh:mm:ss")+"            ";//发送的显示文字
            byte[] strlsansi = System.Text.Encoding.GetEncoding(936).GetBytes(DispInf);//显示文字转换为Ansi
            byte[] Sendbyte=new byte[39];
            Sendbyte[0] = 0x5a;  //指令码
            Sendbyte[1] = 0x00;  //机号低位
            Sendbyte[2] = 0x00;  //机号高位,如果高低位都为0表示任意机号
            Sendbyte[3] = 0x02;  //蜂鸣响声代码,共12种不代响声代码
            Sendbyte[4] = 0x14;  //显示时长
            for (int i = 0; i < 34; i++)
            {
                Sendbyte[i+5]=strlsansi[i];
            }

            IPEndPoint client = new IPEndPoint(IPAddress.Parse(RemortIpStr), RemortPortInt);
            newsock.SendTo(Sendbyte, 39, SocketFlags.None, client);
            string SendInf = "SendTo:" + (Convert.ToString(client) + "                      ").Substring(0, 21) + " Data:";
            for (int i = 0; i < 39; i++)
            {
                SendInf = SendInf + Sendbyte[i].ToString("X2") + " ";
            }
            Console.WriteLine(SendInf+"\n");
        }
    }
}

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

津津有味道

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值