std :: cout и printf удаляют символы C ++

0

Я загружаю файл с url с помощью socket.h, и когда я пытаюсь вывести содержимое буфера, я получаю только его части. Вот файл, основной json файл. http://82.80.47.90/WarningMessages/alerts.json

Связанный код -

 size_t MAX_DATA_LENGTH = 50001;
 char bufIn[MAX_DATA_LENGTH];
 dataLength = recv(sockfd, bufIn, MAX_DATA_LENGTH-1, 0);
 bufIn[dataLength] = '\0';
 std::cout  << "client: received data length " <<  dataLength << std::endl << bufIn;

Мой консольный вывод, когда я запускаю его -

HTTP для oref.org.il:

Отправлено. клиент: полученная длина данных 524
HTTP/1.1 200 OK
Cache-Control: max-age = 4 Content-Length: 174 Content-Type: application/json
Последнее изменение: Вт, 15 июл 2014 08:43:22 GMT
Accept-Ranges: байт
ETag: W/"6bad3d68a0cf1: 2d5"
Сервер: Microsoft-IIS/6.0
X-Powered-By: ASP.NET
Дата: Вт, 15 Июл 2014 08:44:45 GMT
Set-Cookie: cookie1 = KI4GAQVLKVW4JFN90R6B9GAANOO8HAYR; Path =/

{

Хотя... Когда я нюхаю пакеты, выход -

{"id": "1405424602778", "title": "", "data": []}

Или:

0000   ff fe 7b 00 20 00 0d 00 0a 00 22 00 69 00 64 00  ..{. .....".i.d.
0010   22 00 20 00 3a 00 20 00 22 00 31 00 34 00 30 00  ". .:. .".1.4.0.
0020   35 00 34 00 32 00 34 00 36 00 30 00 32 00 37 00  5.4.2.4.6.0.2.7.
0030   37 00 38 00 22 00 2c 00 0d 00 0a 00 22 00 74 00  7.8.".,.....".t.
0040   69 00 74 00 6c 00 65 00 22 00 20 00 3a 00 20 00  i.t.l.e.". .:. .
0050   22 00 e4 05 d9 05 e7 05 d5 05 d3 05 20 00 d4 05  "........... ...
0060   e2 05 d5 05 e8 05 e3 05 20 00 d4 05 ea 05 e8 05  ........ .......
0070   e2 05 d4 05 20 00 d1 05 de 05 e8 05 d7 05 d1 05  .... ...........
0080   20 00 22 00 2c 00 0d 00 0a 00 22 00 64 00 61 00   .".,.....".d.a.
0090   74 00 61 00 22 00 20 00 3a 00 20 00 5b 00 5d 00  t.a.". .:. .[.].
00a0   0d 00 0a 00 7d 00 0d 00 0a 00 0d 00 0a 00        ....}.........

Я бы действительно попросил вас помочь. Я пытался изменить кодировку, но кодировка UTF-8, поэтому нет смысла ее менять.
Благодарю!

  • 1
    Кажется, кодировка в вашем дампе - UTF16-LE, а не UTF-8.
  • 0
    @JoachimIsaksson Я от парня, что сайт использует UTF-16, но когда я попытался проверить кодировку с помощью функции PHP, он сказал, что это UTF-8. Я постараюсь преобразовать его с помощью iconv, спасибо
Теги:
networking
encoding

1 ответ

0

Вы отправляете cout const char* в bufIn, так что единственный способ, которым cout может судить, - это найти первый байт NUL: ваши данные не ASCII, поэтому он попадает в байты "ff fe 7b 00" и останавливает его вывод. Если вы хотите избежать того, что вы можете либо принудительно послать NULs терминалу с помощью cout.write(bufIn, dataLength), либо cout.write(bufIn, dataLength) итерацию по данным, напечатающим isprint() -able, и печатать значение \ восьмеричное значение или что угодно другие обозначения, которые вам нравятся.

Кроме того, TCP является протоколом байтового потока, что означает, что любые данные, которые вы пытаетесь прочитать, могут быть доставлены вам в небольших разделах с единственной необходимой детализацией на уровне байтов. Если вы повторно получаете один раз и получаете только часть данных, вы должны снова зацикливаться и возвращаться, пока не получите все, что ожидаете/нуждаетесь (или EOF/disconnect/error). Это ваша задача, чтобы собрать эти данные или каким-либо образом справиться с этим, чтобы удовлетворить ваши потребности. Некоторые функции API позволяют блокировать до тех пор, пока не будет получено определенное количество байтов (или EOF/disconnect/error), но это не нормальное поведение. Прочтите справочную страницу для recv и посмотрите несколько примеров, но кратко:

size_t MAX_DATA_LENGTH = 50001;
char bufIn[MAX_DATA_LENGTH];
size_t position = 0;
size_t dataLength;
while ((dataLength = recv(sockfd, bufIn + position, MAX_DATA_LENGTH-position-1, 0)) > 0)
    position += dataLength;
dataLength = position;
bufIn[dataLength] = '\0';

Не самый чистый код, но это общая идея.

  • 0
    Что ж, используя wireshark и сравнивая с dataLength, я заметил, что получаю только 525 байт, в то время как длина данных, указанных в Wireshark, равна 579. Так что вы предлагаете? Спасибо, может быть, 54 байта являются заголовками или что-то?
  • 0
    @Yohonatan: все, что вам нужно сделать, это продолжать читать, пока больше нечего получить ... какой-то показательный (непроверенный) код, отредактированный в нем, который должен поставить вас на правильный путь.
Показать ещё 2 комментария

Ещё вопросы

Сообщество Overcoder
Наверх
Меню