привет
Делаю я тут сокет сервер. Для приема/отправки сообщений использую свой протокол, такого типа
int PacketTypeId
int PacketLength
byte[] Data;
код для анализа raw socket data такой
public class BufferParser
{....
private readonly MemoryStream _stream = new MemoryStream(1024);
private readonly byte[] _buffer = new byte[1024];
public void Parse()
{
lock (_stream)
{
int step = 0;
int structLength = -1;
IParserStruct currentStruct = null;
//reset stream Position, After writing it points to the end of stream
_stream.Position = 0;
while (_stream.Position + 8 <= _stream.Length) //8 cause we need at least 8 bytes to start
{
if (step == 0)
{
//read Id - it must be always at first place
_stream.Read(_buffer, 0, 8); //8 bytes for StructId and its Length
int structId = BitConverter.ToInt32(_buffer, 0);
Type currentStructType;
if (!Structs.TryGetValue(structId, out currentStructType))
throw new BufferParserException(string.Format("Structure with ID = {0} is not supported.", structId));
currentStruct = (IParserStruct)Activator.CreateInstance(currentStructType);
//read struct Length
structLength = BitConverter.ToInt32(_buffer, 4);
step = 1;
continue;
}
if (step == 1)
{
if (currentStruct == null || structLength == -1)
throw new BufferParserException("Got to read the structure, but not created.");
if (structLength + _stream.Position <= _stream.Length)
{
_stream.Read(_buffer, 0, structLength);
currentStruct.ReadBytes(_buffer, 0);
//make an additional check to ensure struct was read OK. Not used in this version
//if (!currentStruct.CrcOk())
// throw new BufferParserException("Structure was read, but its CRC is wrong.");
//if is ok, raise the event that structure was read succesfully
StructRead(this, currentStruct);
//go read another structure
step = 0;
}
else
{
break; //nothing to read
}
}
}
if (step == 1)
_stream.Position -= 8;
int shiftBufferLength = (int)(_stream.Length - _stream.Position);
if (shiftBufferLength > 0)
{
_stream.Read(_buffer, 0, shiftBufferLength);
_stream.SetLength(0);
_stream.Seek(0, SeekOrigin.Begin);
_stream.Write(_buffer, 0, shiftBufferLength);
}
else
{
_stream.SetLength(0);
_stream.Seek(0, SeekOrigin.Begin);
}
}
}
у каждого клиента свой BufferParser, на данный момент всё работает нормально, но иногда приходят "плохие" данные и выбрасывается исколючение
BufferParserException, именно из этого и была создана
темаАвтор: Holms
Дата: 25.11.09
, никто не предполагал что такое исключение может быть и оно осталось не обработанным.
Щас всё нормально, но интересно как пишутся протоколы которые бы были устойчивы к непредвиденным данным. Блокировать плохие пока IP клиент не разрешает.
Может не стоить изобретать велосипед и есть что-то готовое уже?
Также искал "high-speed scalable TCP/IP server" ничего путного кроме как примеров чата не нашел. Подскажите что используете вы, трудно верится что все пишут свои велосипеды
Смотрел
ACE но показалось что оно слишком большое, да и учить другую библиотеку как-то не шибко охота
Спасибо
... << RSDN@Home 1.2.0 alpha 4 rev. 1253>>
Здравствуйте, Holms, Вы писали:
H>Может не стоить изобретать велосипед и есть что-то готовое уже?
Есть — это очень мягко говоря.
H>Подскажите что используете вы, трудно верится что все пишут свои велосипеды
Сейчас преимущественно WCF.
Здравствуйте, HowardLovekraft, Вы писали:
HL>Сейчас преимущественно WCF.
нее, только не WCF, пока не WCF, может позже...
... << RSDN@Home 1.2.0 alpha 4 rev. 1253>>
Здравствуйте, Holms, Вы писали:
H>Также искал "high-speed scalable TCP/IP server" ничего путного кроме как примеров чата не нашел. Подскажите что используете вы, трудно верится что все пишут свои велосипеды
H>Смотрел ACE но показалось что оно слишком большое, да и учить другую библиотеку как-то не шибко охота
Ну если смотрел ACE и не обязательно C#/.NET, то одним из популярных "high-speed scalable TCP/IP server" приложений является web-server. Берешь сорцы apache-a (лучше apache v.1, ранние версии) и смотришь ядро. Или юзаешь их
фреймверк.
А вообще, конечно, давно пора забыть этот кошмар и юзать WCF
Здравствуйте, Holms, Вы писали:
H>иногда приходят "плохие" данные и выбрасывается исколючение BufferParserException,<...> , никто не предполагал что такое исключение может быть и оно осталось не обработанным.
А это как это?
Если кто-то вставил его генерацию, значит всё-таки ожидал?
H>Щас всё нормально, но интересно как пишутся протоколы которые бы были устойчивы к непредвиденным данным. Блокировать плохие пока IP клиент не разрешает.
H>Может не стоить изобретать велосипед и есть что-то готовое уже?
А что Вы подразумеваете под "безопасный протокол"? Открыв форточку, нужно быть готовым, что со свежим воздухом в неё могут влететь и мухи, и смог
Открыв порт, Вы никак не можете быть уверены, что к нему будут подключаться только "правильные" клиенты. И сколько бы надстроек между сокетным гнездом и Вашим кодом ни было, проверок Вам не избежать. Эти прослойки могут не пропустить к Вашему коду грубые ошибки, но только Вы сами в состоянии решить, какие данные или их комбинации допустимы в Вашем приложении в данной конкретной ситуации, а потому какого-то волшебства в данном аспекте ожидать не приходится.
Здравствуйте, Holms, Вы писали:
H>пока не WCF, может позже...
Мыши плакали, кололись?..
Из того, что еще есть в FCL — remoting, HttpListener.
Здравствуйте, HowardLovekraft, Вы писали:
HL>Мыши плакали, кололись?..
HL>Из того, что еще есть в FCL — remoting, HttpListener.
ну это становится ясно, начинаю изучать досконально WCF, вроде не такой страшный
... << RSDN@Home 1.2.0 alpha 4 rev. 1253>>