Отправка массива произвольной длины через сокет.Порядок байтов - PullRequest
3 голосов
/ 25 марта 2010

Я сейчас борюсь с программированием сокетов и столкнулся с проблемой, которую не знаю, как решить переносимым способом. Задача проста: мне нужно отправить массив из 16 байтов по сети, получить его в клиентском приложении и проанализировать его. Я знаю, что есть такие функции, как htonl, htons и так далее, которые можно использовать с uint16 и uint32. Но что мне делать с кусками данных, которые больше этого?

Спасибо.

Ответы [ 4 ]

3 голосов
/ 25 марта 2010

Endianness - это свойство многобайтовых переменных, таких как 16-битные и 32-битные целые числа. Это связано с тем, идет ли первым старший или младший байт. Если клиентское приложение обрабатывает массив как отдельные байты, ему не нужно беспокоиться о порядке байтов, поскольку порядок битов в байтах одинаков.

3 голосов
/ 25 марта 2010

Вы говорите, массив из 16 байтов.Это не очень помогает.Порядковый номер имеет значение только для вещей размером больше байта.

Если это действительно необработанные байты, просто отправьте их, вы получите их точно так же

Если это действительно структура, которую вы хотите отправить

 struct msg
 {
     int foo;
     int bar;
 .....

Затем вам нужно проработать буфер, извлекая нужные значения.

При отправке вы должны собрать пакет в стандартный порядок

 int off = 0;
 *(int*)&buff[off] = htonl(foo);
 off += sizeof(int);
 *(int*)&buff[off] = htonl(bar);
 ...

, когдавы получаете

 int foo = ntohl((int)buff[off]);
 off += sizeof(int);
 int bar = ntohl((int)buff[off]);
 ....

РЕДАКТИРОВАТЬ: я вижу, что вы хотите отправить IPv6-адрес, они всегда в сетевом порядке байтов - так что вы можете просто передать его в сыром виде.

1 голос
/ 25 марта 2010

Сами байты больше не имеют порядкового номера в том смысле, что любой отдельный байт, передаваемый компьютером, будет иметь одинаковое значение в другом принимающем компьютере. Порядковый номер в наши дни имеет отношение только к многобайтовым типам данных, таким как целые.

В вашем конкретном случае все сводится к знанию того, что получатель сделает с вашими 16 байтами. Если он будет обрабатывать каждую из 16 записей в массиве как дискретные однобайтовые значения, вы можете просто отправить их, не беспокоясь о порядке байтов. Если, с другой стороны, получатель будет обрабатывать ваш 16-байтовый массив как четыре 32-битных целых числа, то перед отправкой вам нужно будет пропустить каждое целое число через hton ().

Это помогает?

1 голос
/ 25 марта 2010

htons, htonl и т. Д. Предназначены для работы с одним элементом данных (например, int), который больше одного байта. Массив байтов, каждый из которых используется как отдельный элемент данных (например, строка), вообще не нужно переводить между порядком байтов хоста и сети.

...