|
-1 / 5 / 0
Регистрация: 22.11.2016
Сообщений: 68
|
|
Хочу изучить TCP/IP на самом глубоком уровне. Что "внутри" библиотеки ws2_32.dll (winsock)?22.11.2016, 02:28. Показов 10479. Ответов 48
Метки нет (Все метки)
Предисловие (можно не читать если не интересно)
Разрабатываю клиент-серверную архитектуру, от которой требуется высочайшая стабильность при любых проблемах с интернетом на клиенте - чтобы клиент работал на всех Windows от XP до 8.1, и x86 и x64, и при критически низкой скорости интернета, и при пропаданиях подключения в любое время и при любой продолжительности. Соединение должно быть открыто постоянно 24/7 (пока не будет обрыва - тогда оно восстанавливается, причем данные никогда не теряются) Казалось бы, TCP должен из коробки многое уметь, но я видел то что: - стандартный winsockовскийKeepAlive работает не всегда, сервер был Win XP x64, одна и та же клиентская программа на C# успешно работала если клиент взять Win 8.1 x64 и не работала если взять Win 7 x86, насколько помню - во втором случае просто не отправлялись пакеты Keep-Alive, а вдруг у меня еще и другие ОС будут, скажем линукс, разве там KeepAlive совместим? сомнения сомнения, вот и решил отказаться от него и делать свою реализацию то есть Heartbeat - чексумма почему-то не проверяется ни в UDP ни в TCP, ну по крайней мере я вижу то что если отправлять достаточно большой буфер данных, и если уже при отправке на 2 секунды вынуть LAN-кабель (после чего вернуть назад), то пакет с "дыркой" из 0x0 байтов как ни в чем не бывало доходит до принимающего сокета и обрабатывается им, и никаких Exception нигде нету Я уже частично выработал общий алгоритм: 1)Connect. Он повторяется сколь угодно раз до тех пор пока не перестанет бросать Exception 2)Write обязательно вызывается только один раз для одного сообщения (для одного byte[]) 2.1)в этот отправляемый byte[] нужно перед данными еще записать кастомную чексумму (ну раз стандартная не проверяется), и записать размер пакета в байтах чтобы сервер знал сколько выделить памяти для чтения пакета, и в самом начале еще фиксированное число байт для идентификации (потому что не успел я на рабочем сервере запустить очередную версию своей системы для теста, как посыпались пакеты от каких-то неадекватных ботов, что сломало сервер) 3)на сервере Read, у которого обязательно обработка Exception в случае если соединение пропадет уже к моменту вызова Read 3.1)а на случай "дырок" (см. выше) данные нужно читать в цикле, маленькими буферами байт по 10, получая сколько байт по факту считано и тем самым отсеивая "дырки" (это вроде бы получилось сделать) 3.2)затем данные сверяются с чексуммой, если не совпадает то пакет нужно перезапросить то есть в этом случае принимающая и передающая стороны меняются местами 3.2.1)и вообще в любом случае принимающая сторона должна давать ответ об успехе или неудаче (неудача=перезапрос) 4)учесть, что пакет перезапрашивающий данные тоже может дойти не верным, так что все перечисленное к нему тоже применяется, тогда его тоже перезапросить надо, и так до бесконечности пока проблема не исчезнет Я надеюсь, что хоть этого-то хватит для идеально стабильной работы системы. Все это буду пошагово тестировать с помощью тротлинга (программ, которые замедляют скорость интернета) и с помощью ручного и программного обрыва соединения. Но надежды это хорошо, а я бы хотел иметь знания, достоверно изучить тему до уровня Tx/Rx которые в сетевом кабеле, увидеть все своими глазами, это и в будущем пригодится, с железом вроде различных микроконтроллеров (и даже "заказных" микросхем типа черных "капель"!) придется иметь тесные отношения. И вот вопросы: 1) что "внутри" ws2_32.dll? насколько знаю, в Windows есть сетевой драйвер - это служба, он напрямую работает с Tx/Rx (или как-то через BIOS? UEFI?), а с другой стороны есть ws2_32, который работает с драйвером. по каком "протоколу", каким способом ws2_32 связан с драйвером? это случайно не ZwOpenFile (часто применяемый для связи с драйверами)? 2) возможно ли работать с этим драйвером напрямую без ws2_32? не пугайтесь - этого не будет в продакшн, просто исследование 3) возможно ли спуститься еще глубже драйвера и напрямую работать с Tx/Rx/BIOS/UEFI? опять же в продакшне этого не будет, тем более это уже даже не user-mode, а нечто близкое к нулевому кольцу, вопрос только в том - насколько сложно, сколько вообще времени займет это исследование? Внимание! P.S. Вопрос не по сетям в целом, а только по ОС Windows, я понимаю то что можно и линукс (андроид) сюда подключить, но если я буду одновременно две ОС исследовать, то мне уж точно никакого времени не хватит
0
|
|
| 22.11.2016, 02:28 | |
|
Ответы с готовыми решениями:
48
Сформировать N-уровневый вложенный список, элементом которого на самом глубоком уровне является число N
точка входа в процедуру inet_pton не найдена в библиотеке dll ws2_32.dll |
|
-1 / 5 / 0
Регистрация: 22.11.2016
Сообщений: 68
|
|||||||||||||
| 11.12.2016, 13:12 [ТС] | |||||||||||||
|
Убежденный,
![]() Могут перемешаться сами буфера, в смысле прийти в разном порядке. То есть если я сделаю так:
Но они вроде и без потоков могут перемешаться. Поэтому я вообще не буду делать так. На каждый "пакет" моего протокола будет всего один send, то есть вот так у меня будет:
Теперь насчет recv, здесь конечно сложнее, ибо не зная размер "пакета" я не могу весь "пакет" считать одним вызовом recv, поэтому будет путаница, но и она решается с помощью алгоритма конечного автомата хоть и говнокод это будет. Но recv у меня, скорее всего, и не будут в разных потоках.
Но по-моему такой алгоритм уже есть в ОС, только надо правильно его настроить, думаю что вот у меня на клиенте он правильно настроен, а на сервере нет. В общем, завтра буду смотреть
0
|
|||||||||||||
|
Ушел с форума
|
||||||
| 11.12.2016, 13:18 | ||||||
|
одновременно, то система не даст тебе никаких гарантий на счет порядка данных. т.е. каждая следующая операция вызывается строго после того, как отработала предыдущая, данные никогда перемешаны не будут. Такая конструкция полностью безопасна (надо только добавить проверку возвращаемого значения у каждого send). Как, по-твоему, они определяют конец одного HTTP-сообщения и начало другого? Правильно, там стейт-машина с парсингом протокола.
0
|
||||||
|
-1 / 5 / 0
Регистрация: 22.11.2016
Сообщений: 68
|
|||||||||||||
| 11.12.2016, 13:35 [ТС] | |||||||||||||
|
Убежденный,
Я отправлю 2 буфера в разных потоках (специально взял очень малый размер чтобы каждый отправлялся 1 сегментом)
Или байты в заголовках TCP-сегментов тоже могут перемешаться? Слушай, я в принципе могу извратиться и сделать на клиенте всего 2 потока - в одном while read, в другом write, и в этом втором будут и heartbeatы и команды и все остальные write. И тоже самое на сервере - на каждый клиент один сокет и два потока. Но это усложняет и без того сложную задачу, поэтому не вводи меня в заблуждение, пожалуйста. А то с таким же успехом у тебя окажется, что и printf (вывод в консоль) нельзя вызывать сразу в нескольких потоках, и т.п.
На это забей. Этого просто не будет. Read для 1 сокета будет в 1 потоке и на сервере и на клиенте.
0
|
|||||||||||||
|
Ушел с форума
|
|||||
| 11.12.2016, 14:45 | |||||
|
должны пройти еще много промежуточных уровней - WinSock Providers, msafd, afd.sys, tcpip.sys и т.д. Вот что сказано по поводу функции send в MSDN:
0
|
|||||
|
-1 / 5 / 0
Регистрация: 22.11.2016
Сообщений: 68
|
||
| 11.12.2016, 14:56 [ТС] | ||
|
Убежденный,
И что в итоге принимается другой стороной? Вот я у себя не наблюдал такого, чтобы аж порядок байт в одном сегменте перемешивался при многопоточности. Наверно, у меня этого нет. Так какие условия должны измениться (ОС, железо...), чтобы это было? На эти вопросы ты, очевидно, не ответишь. Придется пока решать остальные проблемы, а там видно будет, может код даже проще для восприятия станет благодаря отказу от многопоточных send. В любом случае проведу испытания.
0
|
||
|
Ушел с форума
|
||||
| 11.12.2016, 15:22 | ||||
|
Компоненты сетевого стека, которые расположены ниже send, могут передавать этот буфер хоть по одному байту по сети. То есть, в каждом сегменте может быть хоть по одному байту данных и это не будет каким-то нарушением спецификации TCP. Пока твои данные в send будут проходить многочисленные уровни сетевого стека, они уже там, еще до превращения в сегменты, могут быть раздроблены на произвольное количество частей. В результате на принимающей стороне ты получишь "перемешанные" данные. Вот почему в TCP так важно соблюдать строгую очередность по отношению к send-send или recv-recv. Ну напиши тест. Например, где несколько потоков в параллель, без задержек, в цикле "бомбят" один и тот же сокет функциями send. А сервер читает данные и смотрит, были ли нарушения в последовательности данных. Я вот однажды уже приводил похожий тест, который доказывает, что фрагментация TCP-потока возможна и в локальных сетях, и даже на localhost: TCP протокол отправка данных на сервер Я думаю, результаты такого теста будут интересны очень многим и многие скажут спасибо.
0
|
||||
|
-1 / 5 / 0
Регистрация: 22.11.2016
Сообщений: 68
|
|||||
| 11.12.2016, 15:31 [ТС] | |||||
|
Убежденный,
А какие еще тесты можно провести подобные? То есть с потоками и с проблемой путаницы. Например, с файлами на диске есть ли такое, если я с каждым вызовом WriteFile буду писать новую строчку в файл, то перепутаются только строчки, или и символы в них?
Добавлено через 2 минуты
0
|
|||||
|
Ушел с форума
|
|||||
| 11.12.2016, 15:58 | |||||
|
Уверен на 100%, что они всегда ставят блокировку на параллельный доступ к буферам с данными? выполнены строго последовательно, то даже в этом случае нет гарантий, что они попадут на физическое устройство именно в таком порядке. Современные дисковые контроллеры могут переупорядочивать обращения к разным секторам. И, например, если будет power failure, то при включении компьютера может оказаться, что более поздние данные успели записаться, а более ранние - нет ![]() Это, кстати, большая головная боль разработчиков баз данных и прочих систем, к которым предъявляются соответствующие требования в плане надежности и других гарантий (ACID и т.п.). Так что прямых аналогий с диском, наверное, провести нельзя. почему так и этак. Всегда полезно знать, как устроена система изнутри, чтобы наиболее эффективно управлять ей снаружи. От темы отписался.
0
|
|||||
|
-1 / 5 / 0
Регистрация: 22.11.2016
Сообщений: 68
|
|||||||||
| 11.12.2016, 16:01 [ТС] | |||||||||
|
Убежденный,
(помнишь, ты говорил, что в этом нет смысла т.к. не бывает "дырок" и в общем-то достаточно штатной чексуммы TCP, но многопоточность-то мы тогда не брали во внимание) , то мало не покажется. Не по теме:
А вот этот поможет, или там тоже байты путаются? :)
А насчет вопросов по алгоритму данной системы - я их вообще везде задаю, что-то новое узнаю почти от каждого, но конкретно по алгоритмам может дать справку только тот, кто именно писал подобную систему.
0
|
|||||||||
| 11.12.2016, 16:01 | |
|
Помогаю со студенческими работами здесь
49
Проверка данных внутри библиотеки dll Как изучить WinSock Подключение библиотеки импорта Ws2_32.lib Хук на ws2_32.dll Сокеты через Ws2_32.dll Искать еще темы с ответами Или воспользуйтесь поиском по форуму: |
|
Новые блоги и статьи
|
|||
|
Отчёт о спецтехнике находящейся в ремонте
Maks 20.04.2026
Отчёт из решения ниже размещен в конфигурации КА2.
Задача: отобразить спецтехнику, которая на данный момент находится в ремонте.
Есть нетиповой документ "Заявка на ремонт спецтехники" который. . .
|
Памятка для бота и "визитка" для читателей "Semantic Universe Layer (Слой семантической вселенной)"
Hrethgir 19.04.2026
Сгенерировано для краткого описания по случаю сборки и компиляции скелета серверного приложения. И пусть после этого скажут, что статьи сгенерированные AI - туфта и не интересно. И это не реклама -. . .
|
Запрет удаления строк ТЧ документа при определенном условии
Maks 19.04.2026
Алгоритм из решения ниже реализован на примере нетипового документа "Аккумуляторы", разработанного в конфигурации КА2. У данного документа есть ТЧ, в которой в зависимости от прав доступа. . .
|
Модель заражения группы наркоманов
alhaos 17.04.2026
Условия задачи сформулированы тут
Суть:
- Группа наркоманов из 10 человек.
- Только один инфицирован ВИЧ.
- Колются одной иглой.
- Колются раз в день.
- Колются последовательно через. . .
|
|
Мысли в слух. Про "навсегда".
kumehtar 16.04.2026
Подумалось тут, что наверное очень глупо использовать во всяких своих установках понятие "навсегда". Это очень сильное понятие, и я только начинаю понимать край его смысла, не смотря на то что давно. . .
|
My Business CRM
MaGz GoLd 16.04.2026
Всем привет, недавно возникла потребность создать CRM, для личных нужд. Собственно программа предоставляет из себя базу данных клиентов, в которой можно фиксировать звонки, стадии сделки, а также. . .
|
Знаешь почему 90% людей редко бывают счастливыми?
kumehtar 14.04.2026
Потому что они ждут. Ждут выходных, ждут отпуска, ждут удачного момента. . .
а удачный момент так и не приходит.
|
Фиксация колонок в отчете СКД
Maks 14.04.2026
Фиксация колонок в СКД отчета типа Таблица.
Задача: зафиксировать три левых колонки в отчете.
Процедура ПриКомпоновкеРезультата(ДокументРезультат, ДанныеРасшифровки, СтандартнаяОбработка)
/ / . . .
|