Здравствуйте,
надо переписать на с# linux демон, который ранее работал через xinetd в режиме socket_type = stream, wait = no (то есть под каждое входящее tcp соединение с данными xinetd пишет в stdin, демон в while определяет тип сообщения и пишет ответ в stdout)
клиентское приложение внешнее, исходников нет, есть только исходники демона-сервера, работать через снифер приходится
и есть возможность записать нормально работающий поток, потом попытаться повторить , рабочий поток выглядит так:
1) клиент: [SYN] Seq=0 Win=65535 Len=0 MSS=1460 WS=1
2) сервер: [SYN, ACK] Seq=0 Ack=1 Win=5840 Len=0 MSS=1380 WS=7
3) клиент: [ACK] Seq=1 Ack=1 Win=65536 Len=0
то есть нормально устанавливается соединение и затем циклично идут пакеты с данными
4) клиент: [PSH, ACK] Seq=1 Ack=1 Win=65536 Len=40
5) сервер: [ACK] Seq=1 Ack=41 Win=5888 Len=0
6) сервер: [PSH, ACK] Seq=1 Ack=41 Win=5888 Len=44
7) клиент: [ACK] Seq=41 Ack=45 Win=65492 Len=0
8) клиент: [PSH, ACK] Seq=41 Ack=45 Win=65492 Len=40
9) сервер: [PSH, ACK] Seq=45 Ack=81 Win=5888 Len=44
... и так далее, идет диалог без разрывов связи Seq и Ack увеличиваются
в моем случае, в С# версии сервера другая картина:
1) клиент [SYN] Seq=0 Win=65535 Len=0 MSS=1460
2) сервер [SYN, ACK] Seq=0 Ack=1 Win=8192 Len=0 MSS=1460
3) клиент [ACK] Seq=1 Ack=1 Win=65535 Len=0
4) клиент [FIN, ACK] Seq=1 Ack=1 Win=65535 Len=0 —
то есть клиент почему-то разрывает соединение, вся разница в пакетах рукопожатия, то что в рабочей версии есть WS, а в моей нет
затем снова начинается рукопожатие, но в следующий раз уже мой сервер посылает Fin, и так чередуется — то клиент, то сервер ресетят соединение,
сообщения с данными доходят и клиент их получает, но через раз)) — в этом проблема, между ними каждый раз заново устанавливается новое соединение
собственно коммуникация осуществляется сообщениями, на которые надо отвечать мгновенно без наполнения буфера,
но это вроде работает — клиент делает запрос с PSH и сервер ему отвечает с PSH
в чем может быть причина такого поведения?, вероятно сокеты не так запускаю, подскажите пожалуйста что поправить:
IPEndPoint localEndPoint = new IPEndPoint(ipAddress, port);
listener = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
listener.Bind(localEndPoint);
listener.Listen(200);
while (true)
{
Socket clientSocket = listener.Accept();
byte[] buffer = new byte[BUF_SIZE];
int k = clientSocket.Receive(buffer);
Int16 type = BitConverter.ToInt16(buffer, 2);
//сообщения разных типов, в зависимости от типа потом case отвечает по сlientSocket
switch (type)
{
case 0x0010:
...
case 0x0011:
sendBuf = new byte[Reply11];
Init(sendBuf);
try
{
clientSocket.Send(sendBuf, sendBuf.Length, 0);
clientSocket.Shutdown(SocketShutdown.Both);
clientSocket.Close();
}
catch (Exception e)
{
Console.WriteLine(e.ToString());
}
}
}
собственно вопросов два : первый наверно нубский 1) в моем случае clientSocket я закрываю, но судя по снифу рабочего процесса, его keepAlive как-то сделать надо, чтобы многократно на нем делать recv() и send() (или keepAlive на уровне listener сохраняется и для каждого нового сообщения надо создавать новый clientSocket и затем его закрывать?), и 2) почему в C# версии сервера клиент первым посылает Fin ?, ведь если на нем keepAlive какой-то, а у меня -нет, я должен первым Fin послать ?