在竞争状态下使用线程读取UDP端口上的数据 [英] read data on UDP port using thread in race condition

查看:151
本文介绍了在竞争状态下使用线程读取UDP端口上的数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在读取一个UDP客户端端口上以字节为单位的数据,该端口由另一台服务器广播.
我创建了一个带有睡眠时间的单线程,当数据传入速度很慢时它可以工作,但是当数据传入增加时,它的内存使用量就会增加,并以未知错误终止.

我希望在这样的线程上获得帮助,例如,在完成一项工作后再转到下一项工作时,线程应该以这种方式进行管理,这不仅取决于睡眠时间,还可以使我的线程顺利运行.
谢谢.

I am reading data in bytes on one UDP client port which is broadcast by other server.
I have created a single thread with sleep time it works when data incoming is slow but when data incoming incresaes then its memory use go high and terminate with unknown error.

I want help on this like thread should manage in such a manner after completion of one job come to next job not only depend on sleep time, so my threading could run smoothly.

Thanks.

 public partial class FormUDP : Form
    {
        UdpClient listener = new UdpClient(9871);
        IPEndPoint groupEP = new IPEndPoint(IPAddress.Any, 0);

        bool ProcessStatus; //process
        Thread _UDPthread; //Thread

     private void btn_rcve_Click(object sender, EventArgs e)
       {
           ThreadStart _process = new ThreadStart(receivemessages);
           _UDPthread = new Thread(_process);
           ProcessStatus = true;
           _UDPthread.Start();

       }


private void receivemessages()
       {
           MessageBox.Show("start");
           while (ProcessStatus)
           {
               try
               {
                   if (listener.Available > 0)
                   {
                       byte[] buffer = listener.Receive(ref groupEP);
                       ///**Start convert **//
                       TBCastMessageHeader bcastHeader = new TBCastMessageHeader();
                       IntPtr bcastHeaderPtr;
                       bcastHeaderPtr = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(TBCastMessageHeader)));
                       Marshal.Copy(buffer, 0, bcastHeaderPtr, buffer.Length);
                       bcastHeader = (TBCastMessageHeader)(Marshal.PtrToStructure(bcastHeaderPtr, typeof(TBCastMessageHeader)));  


                  try
                      {
                          switch (bcastHeader.MessageCode)
                          {
                           case 10:
                                     // convert byte to structure and insert into sql database
                                   break;
                          }
                        }
                      catch (Exception ex)
                        { }
                        finally { Marshal.FreeHGlobal(bcastHeaderPtr); C.Collect();}
               if (ProcessStatus)
                {
                    Thread.Sleep(new TimeSpan(0, 0, 0, 0, 5)); // 5 miliseconds
                }
 
        }

// Structure defined
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi, Pack = 0x1)]
    public struct TBCastMessageHeader
    {
        public ushort MessageCode;
        public uint TimeStamp;
        public ushort MessageLength;
        public sbyte NumberOfDecimals;
        public ushort Reserved;
    }


 }

推荐答案

使用睡眠时间毫无意义.对于您的情况,您应该从一开始就创建一个线程(不要单击),并使用线程同步原语(例如,System.Threading.EventWaitHandle)使它保持休眠状态(实际上,在唤醒状态下,不使用任何CPU时间).更高级的用法是使用通用阻塞队列,每个元素代表一个线程的任务",请参阅我的技巧/窍门文章:如何将ref参数传递给线程 [ Control.Invoke()与Control.BeginInvoke() [ ^ ]
Treeview Scanner和MD5的问题 [来自同一端口号的多个客户端 [如何获取keydown事件在vb.net中的不同线程上操作 [
Using sleep time is pointless. In your case, you should create a thread from the very beginning (not by click) and keep it sleeping (actually, in wait state not using any CPU time until awaken) using thread synchronization primitives, like System.Threading.EventWaitHandle. More advanced use would be using a generic blocking queue with elements each representing a "task" for a thread, see my Tips/Trick article: Simple Blocking Queue for Thread Communication and Inter-thread Invocation[^].
Best way to create a thread is using wrapper, here is how: How to pass ref parameter to the thread[^].

For a general design schema, see my Answers to similar Questions:

Control.Invoke() vs. Control.BeginInvoke()[^]
Problem with Treeview Scanner And MD5[^]
Multple clients from same port Number[^] (this one is for TCP, but many recommendations are still valid for your case)
How to get a keydown event to operate on a different thread in vb.net[^]

—SA


这篇关于在竞争状态下使用线程读取UDP端口上的数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆