Как немедленно отправить конкретную порцию данных. Сокет C
Есть сервер и есть клиент по передаче файлов, и там и там буфер для записи/чтения по 1450 байт.
Когда сервер отправляет последние данные файлы, клиент должен записать их в файл, а после, вывести сообщение о том, что загрузка прошла успешно (это сообщение тоже отправляет сервер, так же сервер отправляет еще одно сообщение - о доступных командах (меню)). В общем сервер работает через состояния. Я перечислил 3 из них:
- отправка файла, пока файл не кончился (пока чтение из него по 1450 байт);
- отправка сообщения об успешном завершении (когда последнее чтение было меньше 1450 байт, сервер меняет состояние клиента на 2);
- отправка списка доступных команд (переход сюда, когда 2 было отправлено).
Проблема: сервер объединяет всё и отправляет разом (последние данные файла + сообщение об успехе + список доступных команд). Как мне сделать так, что бы сокет отправлял данные СРАЗУ, не накапливая сообщения в своем буфере?
UPD:
Условный код сервера (sc - client):
send(sc, "asd", 3, 0);
send(sc, "zxc", 3, 0);
Условный код клиента (ss - server):
recv(ss, buf, 1450, 0);
// что-то делаем + чистим буфер
recv(ss, buf, 1450, 0);
// что-то делаем
Первый вызов recv примет сразу "asdzxc", как их наверняка разделить? Что бы на первый recv пришел только asd, а на второй zxc. Может есть какие-то флаги для сокетов и их функций на подобные случаи? Пытался найти ответ в манах socket, send и recv, но ничего подобного там не увидел :(
UPD2:
Тип сокета - SOCK_STREAM
UPD3:
Вопрос решен в комментариях.
Ответы (1 шт):
Для разделения данных на пакеты обычно используются протоколы высокого уровня.
Самый распространенный это структуры TLV. Сервер отправляет тип данных (например один байт), длинну передачи, а затем сами данные.
код клиента будет выглядеть примерно так.
while (1) {
recv(ss, &t, 1, 0);
if (t != 'd') break или continue или process = process_data;
recv(ss, &l, 2, 0);
recv(ss, buf, l, 0);
process(buf, l);
}