首页 > 代码库 > C# RFID windows 服务 网络协议方式

C# RFID windows 服务 网络协议方式

上篇话说是串口方式操作RFID设备。 下面介绍网络协议方式。 设备支持断线重连。 那我们的服务也不能差了不是。 所以这个服务类也是支持的哦。 

不解释上代码:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
namespace Rfid
{
    /// <summary>
    /// 获取Vip数据
    /// </summary>
    /// <param name="vip"></param>
    public delegate void GetVipEventHandle(object obj, MarkArgs vip);
 
    /// <summary>
    /// 识别标签
    /// </summary>
    /// <param name="idMark"></param>
    public delegate void IdentificationMarksEventHandle(object obj, MarkArgs idMark);
 
 
    /// <summary>
    /// 写标签
    /// </summary>
    public delegate void WriteMarksEventHandle(object obj, MarkArgs writeMark);
 
 
 
    public class RfidSocket
    {
        public event GetVipEventHandle GetVip;
 
        public event IdentificationMarksEventHandle IdentificationMarks;
 
        public event WriteMarksEventHandle WriteMarks;
 
        /// <summary>
        /// 识别标签协议
        /// </summary>
        public readonly byte[] MReadMarks = new byte[5] { 0xA0, 0x03, 0x82, 0x00, 0xDB };
 
        /// <summary>
        /// 接受失败协议
        /// </summary>
        public readonly byte[] MErrorHeader = new byte[3] { 0xE4, 0x04, 0x82 };
 
        /// <summary>
        /// 接受成功协议
        /// </summary>
        public readonly byte[] MSucessHeader = new byte[3] { 0xE0, 0x10, 0x82 };
 
        /// <summary>
        /// Vip数据长度
        /// </summary>
        public const int MDataLength = 12;
 
        /// <summary>
        /// 发送读取协议证
        /// </summary>
        public System.Windows.Forms.Timer MTimer = new System.Windows.Forms.Timer();
 
        /// <summary>
        /// 链接状态
        /// </summary>
        public bool Connected = false;
 
        /// <summary>
        /// Vip编号
        /// </summary>
        public string VipId = string.Empty;
 
        /// <summary>
        /// 全局锁
        /// </summary>
        public object MLock = new object();
 
        /// <summary>
        /// Socket通讯
        /// </summary>
        public SocketClient Client = new SocketClient();
 
        /// <summary>
        /// 连接错误次数
        /// </summary>
        public int MConnectErrorCount = 0;
 
        public string Ip { get; set; }
        public int Port { get; set; }
        public int ErrorCount { get; set; }
        public RfidSocket(string ip, int port, int errorCount)
        {
            this.Ip = ip;
            this.Port = port;
            this.ErrorCount = errorCount;
 
        }
 
        void client_OnDisconnected(object sender)
        {
            Client.mOnConnected -= client_mOnConnected;
            Client.mOnError -= client_mOnError;
            Client.OnDataIn -= client_OnDataIn;
            Client.OnDisconnected -= client_OnDisconnected;
        }
 
        void client_OnDataIn(object sender, byte[] data)
        {
            try
            {
                GC.Collect();
                GC.WaitForFullGCComplete();
                GC.Collect();
 
                //当前不考虑数据协议失败情况
                Monitor.Enter(MLock);
 
                //判断消息头
                if (data.Length > 3)
                {
                    IdentificationTag(data);
 
                    WriteTag(data);
                }
 
                ReaderTag(data);
            }
            finally
            {
                Monitor.Exit(MLock);
            }
        }
 
        /// 识别标签协
        private void IdentificationTag(byte[] data)
        {
            //识别标签协议成功
            if (data[0] == 0xE0 && data[1] == 0x10 && data[2] == 0x82)
            {
                //解析标签成功
                if (data.Length >= 18)
                {
                    var vipByte = new byte[4];
                    Array.Copy(data, 13, vipByte, 0, vipByte.Length);
                    var vipId = ((vipByte[0]) + (vipByte[1] << 8) + (vipByte[2] << 16) + (vipByte[3] << 32)).ToString();
                    if (IdentificationMarks != null)
                    {
                        var markArgs = new MarkArgs(vipId, string.Empty, true);
                        IdentificationMarks(this, markArgs);
                    }
                }
            }
            else if (data[0] == 0xE4 && data[1] == 0x04 && data[2] == 0x82)
            {
                if (IdentificationMarks != null)
                {
                    var markArgs = new MarkArgs(string.Empty, string.Empty, false);
                    IdentificationMarks(this, markArgs);
                }
            }
        }
 
        /// 快写标签
        private void WriteTag(byte[] data)
        {
            if (data[0] == 0xE0 && data[1] == 0x04 && data[2] == 0x9C)
            {
                if (data.Length >= 6)
                {
                    if (data[4] == 0x0)
                    {
                        //写标签成功
                        if (WriteMarks != null)
                        {
                            var markArgs = new MarkArgs(string.Empty, string.Empty, true);
                            WriteMarks(this, markArgs);
                        }
                    }
                    else
                    {
                        //写标签失败
                        if (WriteMarks != null)
                        {
                            var markArgs = new MarkArgs(string.Empty, string.Empty, false);
                            WriteMarks(this, markArgs);
                        }
                    }
                }
            }
        }
 
        /// 定时模式读取标签
        private void ReaderTag(byte[] data)
        {
            if (data.Length >= 17)
            {
                if (data[0] == 0x00 && data[1] == 0x00 && data[16] == 0xFF)
                {
                    var bytCheck = new byte[15];
                    Array.Copy(data, 0, bytCheck, 0, 15);
                    var checkSum = EPCSDKHelper.CheckSum(bytCheck) & 0xFF;//校验和
                    if (data[15] == checkSum)
                    {
                        var vipByte = new byte[4];
                        Array.Copy(bytCheck, 10, vipByte, 0, 4);
                        var vipId = ((vipByte[0]) + (vipByte[1] << 8) + (vipByte[2] << 16) + (vipByte[3] << 32)).ToString();
                        this.VipId = vipId;
                        if (GetVip != null)
                        {
                            var markArgs = new MarkArgs(this.VipId, string.Empty, true);
                            GetVip(this, markArgs);
                        }
                    }
                }
            }
        }
 
        private void client_mOnError(object sender, SocketException error)
        {
            if (!Client.ConnectFlag)
            {
                ReConnect();
            }
        }
 
        private void client_mOnConnected(object sender)
        {
            MConnectErrorCount = 0;
        }
 
        private void ReConnect()
        {
            if (Client != null)
            {
                Client.mOnConnected -= client_mOnConnected;
                Client.mOnError -= client_mOnError;
                Client.OnDataIn -= client_OnDataIn;
                Client.OnDisconnected -= client_OnDisconnected;
            }
            Client = new SocketClient();
            Client.Connect(this.Ip, this.Port);
            Client.mOnConnected += client_mOnConnected;
            Client.mOnError += client_mOnError;
            Client.OnDataIn += client_OnDataIn;
            Client.OnDisconnected += client_OnDisconnected;
        }
 
        private void mTimer_Tick(object sender, EventArgs e)
        {
            try
            {
                MTimer.Enabled = false;
                if (Client.ConnectFlag)
                {
                    Client.Send(TagProtocol.MIdentificationMarks);
                }
                else
                {
                    MConnectErrorCount++;
                    if (MConnectErrorCount > this.ErrorCount)
                    {
                        ReConnect();
                    }
                }
            }
            finally
            {
                MTimer.Enabled = true;
            }
        }
 
        public void Start()
        {
            Client = new SocketClient();
            Client.Connect(this.Ip, this.Port);
            Client.mOnConnected += client_mOnConnected;
            Client.mOnError += client_mOnError;
            Client.OnDataIn += client_OnDataIn;
            Client.OnDisconnected += client_OnDisconnected;
 
            MTimer.Interval = 1000;
            MTimer.Enabled = true;
            MTimer.Tick += mTimer_Tick;
        }
 
        public void ClearVipId()
        {
            try
            {
                Monitor.Enter(MLock);
                this.VipId = string.Empty;
            }
            finally
            {
                Monitor.Exit(MLock);
            }
        }
 
        public void WriteMark(int mark)
        {
            if (mark < 0 && mark > 0xffffffff)
            {
                throw new Exception("超出写标签范围!");
            }
            var markByte = mark.ToString("x").PadLeft(8, ‘0‘);
            var byt = new byte[4];
            for (var i = 0; i < markByte.Length; i = i + 2)
            {
                byt[i / 2] = (byte)Convert.ToInt32(markByte[i].ToString() + markByte[i + 1].ToString(), 16);
            }
            var writeMarkData = http://www.mamicode.com/new byte[10];
            Array.Copy(TagProtocol.MWriteMark, 0, writeMarkData, 0, TagProtocol.MWriteMark.Length);
            Array.Copy(byt, 0, writeMarkData, TagProtocol.MWriteMark.Length, byt.Length);
            //写校验和
            writeMarkData[9] = (byte)(EPCSDKHelper.CheckSum(writeMarkData) & 0xFF);
            Client.Send(writeMarkData);
 
            GC.Collect();
            GC.WaitForFullGCComplete();
            GC.Collect();
        }
    }

  上面介绍了网络通讯的设备类当然也少不了Socket通讯类。 不然没法通许不是

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
namespace Rfid
{
    public delegate void ClientErrorEvent(object sender, SocketException error);
    public delegate void ClientOnDataInHandler(object sender, byte[] data);
    public delegate void ClientEvent(object sender);
 
    public class SocketClient
    {
        public event ClientEvent mOnConnected = null;
        public event ClientEvent OnDisconnected = null;
        public event ClientOnDataInHandler OnDataIn = null;
        public event ClientErrorEvent mOnError = null;
        private Socket cli = null;
        private byte[] databuffer;
        private int buffersize = 64 * 1024;
 
        public bool ConnectFlag
        {
            get
            {
                if (cli == null)
                {
                    return false;
                }
 
                return cli.Connected;
            }
        }
        private void RaiseDisconnectedEvent()
        {
            if (null != OnDisconnected) OnDisconnected(this);
        }
        private void RaiseErrorEvent(SocketException error)
        {
            if (null != mOnError) mOnError(this, error);
        }
        private void HandleConnectionData(IAsyncResult parameter)
        {
            Socket remote = (Socket)parameter.AsyncState;
 
            int read = remote.EndReceive(parameter);
            if (0 == read)
            {
                RaiseDisconnectedEvent();
            }
            else
            {
                byte[] received = new byte[read];
                Array.Copy(databuffer, 0, received, 0, read);
                if (null != OnDataIn) OnDataIn(this, received);
                StartWaitingForData(remote);
            }
        }
        private void HandleIncomingData(IAsyncResult parameter)
        {
            try
            {
                HandleConnectionData(parameter);
            }
            catch (ObjectDisposedException)
            {
                RaiseDisconnectedEvent();
            }
            catch (SocketException x)
            {
                if (x.ErrorCode == 10054)
                {
                    RaiseDisconnectedEvent();
                }
                RaiseErrorEvent(x);
            }
        }
        private void StartWaitingForData(Socket soc)
        {
            soc.BeginReceive(databuffer,
                0,
                buffersize,
                SocketFlags.None,
                new AsyncCallback(HandleIncomingData),
                soc);
        }
 
        private void HandleSendFinished(IAsyncResult parameter)
        {
            Socket socket = (Socket)parameter.AsyncState;
            socket.EndSend(parameter);
        }
        public SocketClient()
        {
            databuffer = new byte[buffersize];
        }
        private void Connected(IAsyncResult iar)
        {
            Socket socket = (Socket)iar.AsyncState;
            try
            {
                socket.EndConnect(iar);
            }
            catch (SocketException x)
            {
                RaiseErrorEvent(x);
                return;
            }
            catch (ArgumentException)
            {
                return;
            }
            catch (Exception e)
            {
                LogInfo.Error("Connected:" + e.Message);
                LogInfo.Error(e.StackTrace);
                return;
            }
            if (null != mOnConnected) mOnConnected(this);
            StartWaitingForData(socket);
        }
        public void Connect(string ip, int port)
        {
            cli = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            IPEndPoint iep = new IPEndPoint(IPAddress.Parse(ip), port);
            try
            {
                cli.BeginConnect(iep, new AsyncCallback(Connected), cli);
            }
            catch (SocketException er)
            {
                LogInfo.Error("与服务器无法建立连接!错误编号:" + er.ErrorCode + " 错误消息:" + er.Message);
            }
        }
        public void Close()
        {
            cli.Shutdown(SocketShutdown.Both);
            cli.Close();
        }
 
        public void Send(byte[] buffer)
        {
            try
            {
                cli.BeginSend(buffer,
                    0,
                    buffer.Length,
                    SocketFlags.None,
                    new AsyncCallback(HandleSendFinished),
                    cli);
            }
            catch (ObjectDisposedException)
            {
                RaiseDisconnectedEvent();
            }
            catch (SocketException x)
            {
                RaiseErrorEvent(x);
            }
        }
    }

  看到这些你有没有什么想说的。 提出你的想法。其实搞和硬件通讯还是很有趣的。下篇我将介绍一下让我恶心的不能再恶心的东进的电话卡模块。他的SDK简直无法用言语表达了(我只能说祝福了)。 对于RFID的SDK简单明了想要搞个程序还是很容易的。