NetworkStream (TcpClient, TcpListener, C#)
От: disuk  
Дата: 25.05.05 06:38
Оценка:
написал я самый примитивный прокси сервер, используя классы TcpListener и TcpClient. В самой программе создал два потока. 1-й со стороны клиента, 2-й, соответственно, для работы с удаленным сервером. Вот кусочек кода:

TcpListener listener = new TcpListener(port_in);
listener.Start();
r_tb.AppendText("Жду входящего запроса на порт "+port_in.ToString() +" ..."+next_l);
TcpClient client = listener.AcceptTcpClient();
r_tb.AppendText(" принял запрос на коннект!"+next_l);
NetworkStream ns_cl = client.GetStream();
    //--------------------------
TcpClient server = new TcpClient(tb_host_out.Text, port_out);
r_tb.AppendText("законнектились на удаленный хост "+tb_host_out.Text +" на порт "+port_out.ToString()+next_l);
NetworkStream ns_sr = server.GetStream();
r_tb.AppendText("начинаю работать ------------------------------"+next_l);
            
while(true)
   {
    if (ns_cl.DataAvailable)
    {
     //есть данные для чтения с клиента
     kolwo_cl_read=ns_cl.Read(buff_cl,0,buff_cl.Length);
     r_tb.AppendText("прочитал от клиента "+kolwo_cl_read.ToString()+" байт"+next_l);
     ns_sr.Write(buff_cl,0,kolwo_cl_read);
    };
    if (ns_sr.DataAvailable) 
    {
     //есть данные для отправки на клиента
     kolwo_sr_read=ns_sr.Read(buff_sr,0,buff_sr.Length);
     r_tb.AppendText("прочитал от сервера "+kolwo_sr_read.ToString()+" байт"+next_l);
     ns_cl.Write(buff_sr,0,kolwo_sr_read);
    };
   };

как видно, сейчас в цикле просто тупо проверяется, есть ли данные в потоках, и, если есть, они с одного потока уходят в другой. В принципе все работает, но из-за непрерывного цикла приложение пожирает все процессорные ресурсы и само "не отвечает". собссно, вопрос:
как мне сделать, чтобы только при пришествии данных в поток, вызываласьь моя функция? может есть какое-нибудь событие, вызывающееся, когда приходят данные в поток?

зы: курил NetworkStream class, ничего не выглядел
зыы: курил фак этой ветки форума — вобще нихрена не понял
Re: NetworkStream (TcpClient, TcpListener, C#)
От: Аноним  
Дата: 25.05.05 14:53
Оценка:
Здравствуйте, disuk, Вы писали:

D>написал я самый примитивный прокси сервер, используя классы TcpListener и TcpClient. В самой программе создал два потока. 1-й со стороны клиента, 2-й, соответственно, для работы с удаленным сервером. Вот кусочек кода:


D>
D>TcpListener listener = new TcpListener(port_in);
D>listener.Start();
D>r_tb.AppendText("Жду входящего запроса на порт "+port_in.ToString() +" ..."+next_l);
D>TcpClient client = listener.AcceptTcpClient();
D>r_tb.AppendText(" принял запрос на коннект!"+next_l);
D>NetworkStream ns_cl = client.GetStream();
D>    //--------------------------
D>TcpClient server = new TcpClient(tb_host_out.Text, port_out);
D>r_tb.AppendText("законнектились на удаленный хост "+tb_host_out.Text +" на порт "+port_out.ToString()+next_l);
D>NetworkStream ns_sr = server.GetStream();
D>r_tb.AppendText("начинаю работать ------------------------------"+next_l);
            
D>while(true)
D>   {
D>    if (ns_cl.DataAvailable)
D>    {
D>     //есть данные для чтения с клиента
D>     kolwo_cl_read=ns_cl.Read(buff_cl,0,buff_cl.Length);
D>     r_tb.AppendText("прочитал от клиента "+kolwo_cl_read.ToString()+" байт"+next_l);
D>     ns_sr.Write(buff_cl,0,kolwo_cl_read);
D>    };
D>    if (ns_sr.DataAvailable) 
D>    {
D>     //есть данные для отправки на клиента
D>     kolwo_sr_read=ns_sr.Read(buff_sr,0,buff_sr.Length);
D>     r_tb.AppendText("прочитал от сервера "+kolwo_sr_read.ToString()+" байт"+next_l);
D>     ns_cl.Write(buff_sr,0,kolwo_sr_read);
D>    };
D>   };

D>

D>как видно, сейчас в цикле просто тупо проверяется, есть ли данные в потоках, и, если есть, они с одного потока уходят в другой. В принципе все работает, но из-за непрерывного цикла приложение пожирает все процессорные ресурсы и само "не отвечает". собссно, вопрос:
D>как мне сделать, чтобы только при пришествии данных в поток, вызываласьь моя функция? может есть какое-нибудь событие, вызывающееся, когда приходят данные в поток?

D>зы: курил NetworkStream class, ничего не выглядел

D>зыы: курил фак этой ветки форума — вобще нихрена не понял

В данном случае корректней воспользоваться асинхронной моделью работы с потоком. См. NetworkStream.BeginRead(Write)
Re[2]: NetworkStream (TcpClient, TcpListener, C#)
От: disuk  
Дата: 26.05.05 09:17
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Здравствуйте, disuk, Вы писали:


D>>написал я самый примитивный прокси сервер, используя классы TcpListener и TcpClient. В самой программе создал два потока. 1-й со стороны клиента, 2-й, соответственно, для работы с удаленным сервером. Вот кусочек кода:

D>>как видно, сейчас в цикле просто тупо проверяется, есть ли данные в потоках, и, если есть, они с одного потока уходят в другой. В принципе все работает, но из-за непрерывного цикла приложение пожирает все процессорные ресурсы и само "не отвечает". собссно, вопрос:
D>>как мне сделать, чтобы только при пришествии данных в поток, вызываласьь моя функция? может есть какое-нибудь событие, вызывающееся, когда приходят данные в поток?

А>В данном случае корректней воспользоваться асинхронной моделью работы с потоком. См. NetworkStream.BeginRead(Write)

так. т.е. запихать в отдельную функцию один лишь вызов beginread со стороны потока клиента, в другую функцию поместить бегинРид со стороны сервера, эти функции тут же завершатся (ибо не будут ждать окончания работы beginread) и где-то создать свои коллбаки, которые будутт вызваться, когда функции beginread сработают?
т.е. тут даже с Thread не нужно ничего наворачивать?
Re[3]: NetworkStream (TcpClient, TcpListener, C#)
От: Nickolay Ch  
Дата: 26.05.05 09:27
Оценка:
Здравствуйте, disuk, Вы писали:

D>Здравствуйте, Аноним, Вы писали:


А>>Здравствуйте, disuk, Вы писали:


D>>>написал я самый примитивный прокси сервер, используя классы TcpListener и TcpClient. В самой программе создал два потока. 1-й со стороны клиента, 2-й, соответственно, для работы с удаленным сервером. Вот кусочек кода:

D>>>как видно, сейчас в цикле просто тупо проверяется, есть ли данные в потоках, и, если есть, они с одного потока уходят в другой. В принципе все работает, но из-за непрерывного цикла приложение пожирает все процессорные ресурсы и само "не отвечает". собссно, вопрос:
D>>>как мне сделать, чтобы только при пришествии данных в поток, вызываласьь моя функция? может есть какое-нибудь событие, вызывающееся, когда приходят данные в поток?

А>>В данном случае корректней воспользоваться асинхронной моделью работы с потоком. См. NetworkStream.BeginRead(Write)

D>так. т.е. запихать в отдельную функцию один лишь вызов beginread со стороны потока клиента, в другую функцию поместить бегинРид со стороны сервера, эти функции тут же завершатся (ибо не будут ждать окончания работы beginread) и где-то создать свои коллбаки, которые будутт вызваться, когда функции beginread сработают?
D>т.е. тут даже с Thread не нужно ничего наворачивать?
Да, тред самому создавать не надо. Коллбек вызовется в новом треде из тредпула. Не забыть тока там(в коллбеке) после завершения операции опять начать следующую асинхронную операцию.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.