private void Receive(){
Socket client; // сокет для обмена данными.
Listener = new TcpListener(LocalPort);
Listener.Start(); // начали слушать
Console.WriteLine("Waiting connections [" + Convert.ToString(LocalPort) + "]...");
try{
client = Listener.AcceptSocket();
} catch {
return;
}
string data;
byte[] cldata = new byte[1024]; // буфер данных
int size = 0;
while (true)
{
try
{
size = client.Receive(cldata); // попытка чтения данных
}
catch
{
}
try
{
if (size > 0)
{
data = Encoding.ASCII.GetString(cldata).TrimEnd('\0');
Console.WriteLine("<" + data);
if (data == "CLOSE") // если CLOSE – вырубимся
{
ClientSock.Send(Encoding.ASCII.GetBytes("Closing the server..."));
ClientSock.Close();
Listener.Stop();
Console.WriteLine("Server closed. Reason: client wish! Type EXIT to quit the application.");
ServThread.Abort();
return;
}
else
{
client.Send(Encoding.ASCII.GetBytes("Your data: " + data));
}
Array.Clear(cldata, 0, 1024);
}
}
catch(Exception e)
{
Console.WriteLine(e.Message);
client.Sockt.Close(); // ну эт если какая хрень..
// Listener.Stop();
// Console.WriteLine("Server closing. Reason: client offline. Type EXIT to quit the application.");
// ServThread.Abort();
}
}
}
size = client.Receive(cldata); // size равен размерности массива cldata, а не количеству принятых байт. Как получить количество принятых байт?
Здравствуйте, vovanmain, Вы писали:
V>size = client.Receive(cldata); // size равен размерности массива cldata, а не количеству принятых байт. Как получить количество принятых байт?
Чтобы получить, нужно на сервере привязать к отправляемым данным общий размер отправляемых данных (ну допустим в первых байтах данных у нас будет этот размер, вот в такой семантике: [FILESIZE=1024442]). На клиенте нужно выделить размер файла и запомнить его где-нибудь, а затем принимать байты данных до тех пор пока принятый (выделенный размер из первой порции байтов с сервера) размер не станет больше полученного объема данных.
Пример такой обработки (при условии что мы выделили из первой порции байтов общий размер отправляемых данных с сервера на клиент):
private void ReceiveFile(Socket sender, byte[] receivedByte, RichTextBox log)
{
this.ReceiveFileSize(sender, receivedByte, log);
int totalBytesReceivedSize = 0;
// пока принятые данные не станут больше или равны принятому размеру данных
while (!(totalBytesReceivedSize > this.fileSize))
{
this.AddingReceivedDataToLog(sender, receivedByte, log);
totalBytesReceivedSize += this.bufferSize;
}
}
За подробностями реализации, можно обратиться к следующей теме:
здесьАвтор: Xobotik
Дата: 25.03.10
Код конечно не айс, но работает как надо. Пол часа посидеть разобраться и будет все и у вас работать.
Здравствуйте, vovanmain, Вы писали:
V>V>private void Receive(){
V> Socket client; // сокет для обмена данными.
V> Listener = new TcpListener(LocalPort);
V> Listener.Start(); // начали слушать
V> Console.WriteLine("Waiting connections [" + Convert.ToString(LocalPort) + "]...");
V> try{
V> client = Listener.AcceptSocket();
V> } catch {
V> return;
V> }
V> string data;
V> byte[] cldata = new byte[1024]; // буфер данных
V> int size = 0;
V> while (true)
V> {
V> try
V> {
V> size = client.Receive(cldata); // попытка чтения данных
V> }
V> catch
V> {
V> }
V> try
V> {
V> if (size > 0)
V> {
V> data = Encoding.ASCII.GetString(cldata).TrimEnd('\0');
V> Console.WriteLine("<" + data);
V> if (data == "CLOSE") // если CLOSE – вырубимся
V> {
V> ClientSock.Send(Encoding.ASCII.GetBytes("Closing the server..."));
V> ClientSock.Close();
V> Listener.Stop();
V> Console.WriteLine("Server closed. Reason: client wish! Type EXIT to quit the application.");
V> ServThread.Abort();
V> return;
V> }
V> else
V> {
V> client.Send(Encoding.ASCII.GetBytes("Your data: " + data));
V> }
V> Array.Clear(cldata, 0, 1024);
V> }
V> }
V> catch(Exception e)
V> {
V> Console.WriteLine(e.Message);
V> client.Sockt.Close(); // ну эт если какая хрень..
V> // Listener.Stop();
V> // Console.WriteLine("Server closing. Reason: client offline. Type EXIT to quit the application.");
V> // ServThread.Abort();
V> }
V> }
V>}
V>
V>size = client.Receive(cldata); // size равен размерности массива cldata, а не количеству принятых байт. Как получить количество принятых байт?
вцелом согласен, можно проще
public static byte[] BlockedReceive(Socket socket)
{
var buffer = new byte[Intlen];
socket.Receive(buffer, 0, Intlen, SocketFlags.None);
var length = BitConverter.ToInt32(buffer, 0);
if (0 == length)
{
buffer = null;
return null;
}
buffer = new byte[length];
var offset = 0;
while (offset != length)
offset += socket.Receive(buffer, offset, length - offset, SocketFlags.None);
return buffer;
}
тут особенность в том, что первый int в потоке, длина последующего массива байт (сериализованного обьекта например)
Intlen = sizeof(Int32);
код тоже не идеальный но сам смысл понятен думаю ))