LINUX.ORG.RU

[Qt][QTCPSocket] почему фрагментируется?

 


0

1

Я пересылаю сообщения при помощи QTCPServer и QTCPSocket - все идет, но если размер пакета превышает какое-то значение - происходит фрагментация пакета...

Вопрос, разве Qt не для того на свете есть чтобы я мог посылать мегабайтные QByteArray через сокет и получать сигналы от QTCPSocket именно таких же размеров? Безо всяких непредсказуемых разделений на пакеты?

Чтоб я делаю не так раз через QTCPSocket у меня пакеты разбиваются на мелкие части? Как настроить, что применить, как обойти проблему?

Проблема проста и очевидна - тупо бьются пакеты на части и всё. Даже те что до 64 Кб и то разбиваются иногда на 20-30 Кб... мистика... что делать, help! :)

★★★★★

Последнее исправление: I-Love-Microsoft (всего исправлений: 1)

IP-пакеты могут быть разделены на части произвольным образом и соединены вместе по пути. Главное, что порядок данных сохраняется.

Можно же передавать сначала длину данных, потом сами эти данные, а на другом хосте добавлять всё в один буфер, пока не накопится эта длина. Чтобы было «удобнее», можно даже класс для этого написать.

gentoo_root ★★★★★
()

Даже те что до 64 Кб и то разбиваются иногда на 20-30 Кб

А на канальном уровне фреймы вообще по 1500 байт, а то и меньше. Ну и что дальше?

xscrew ★★
()

мистика... что делать, help! :)

man ethernet, ip, tcp, osi

bk_ ★★
()

man 7 tcp

в TCP нет пакетов, это потоко-ориентированный протокол.

что делать

использовать UDP, реализовывать свой протокол поверх TCP с поддержкой пакетов.

Vinick ★★
()

В sctp ( http://ru.wikipedia.org/wiki/SCTP#.D0.A4.D0.BE.D1.80.D0.BC.D0.B8.D1.80.D0.BE.... ) Есть то что тебе надо.

В tcp же тебе надо для своего протокла делать так: отправлять 8 байт длину сообщения а потом сообщение. Так делают все. Других вариантов просто нет для tcp. Либо, если надо послать данные неизвестной длинны то надо в потоке данных использовать разделитель и ескейпить его среди данных.

Раз у тебя возникают подобные вопросы, посмотри, может тебе надо использовать более высокоуровневый протокол, например, http.

mmarkk
()

разве Qt не для того на свете есть чтобы я мог посылать мегабайтные QByteArray >через сокет и получать сигналы от QTCPSocket именно таких же размеров?

нет.

nanoolinux ★★★★
()
Ответ на: комментарий от mmarkk

В tcp же тебе надо для своего протокла делать так: отправлять 8 байт длину сообщения а потом сообщение

а почему именно 8 байт? 8 байт это гарантированная длина пакета, которая не будет фрагментирована или как? мне удобнее 4 байт для длины слать, вроде ерунда, но я на всякий случай спрошу :)

вот тут нашел как раз тему на 100% объясняющая то что мне надо, читаю «It's a common problem; I'll list a few solutions for you:»

I-Love-Microsoft ★★★★★
() автор топика
Ответ на: комментарий от I-Love-Microsoft

ну если ты экономишь байты - то можно и вобще один послать, если твои каг-бе пакеты укладываются в эту длину.... но как ты знаешь, 640 килобайт хватит всем, поэтому лучше сразу зарезервировать 8 байт - их точно хватит :) Да и к тому же щас все переходят на 64-битные платформы. а там 8 байт - родной размер.

мне удобнее 4 байт для длины слать

ты ещё, поди, про сетевой порядок байтов не знаешь...и, видимо, про кроссплатформенность не слыхал. (всмысле, про различие sizeof на разных плфтормах). Иначе про удобство у тебя не возникло бы вопросов.

либо, если экономить надо, а длины могут быть непредсказуемые, то можно использовать упаковку типа как в NTFS (сначала, идёт три бита в которых хранится число от 1 до 8, которое описывает сколько байтов занимает идущее далее число, в котором хранится длина фрагмента), но ты ведь не будешь заниматься подобной хернёй? больше потеряешь CPU на обработке трафика.

mmarkk
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.