Поведение QTcpSocket::waitForBytesWritten?

Меня немного смущает поведение QTcpSocket::waitForBytesWritten()...

До какого момента эта функция блокируется?

  • Пока данные не будут записаны во внутренний буфер ОС для передачи по TCP?
  • Пока данные не будут физически преобразованы в TCP-пакеты и отправлены?
  • Пока не будут переданы все данные и удаленный клиент не подтвердит получение всех пакетов?

Я просмотрел документацию, но она показалась мне не очень ясной.


person Nathan Osman    schedule 11.01.2011    source источник


Ответы (1)


Вообще говоря, операционные системы предоставляют простые API только для первого вопроса - поскольку Qt является переносимым API, лучше всего полагаться на него только в отношении передачи в буфер ОС. Если вам нужно фактическое подтверждение получения, лучше всего, чтобы оно было отправлено удаленным приложением — в конце концов, данные могут быть подтверждены удаленным приложением, но никогда не считываются из буфера чтения удаленной ОС.

Если вам нужно, чтобы удаленная сторона не блокировала вас навсегда, вместо этого следует дождаться QIODevice::bytesWritten подайте сигнал и вернитесь в цикл событий, чтобы выполнить другую работу, или просто установите соответствующий тайм-аут. В общем, удаленная сторона всегда может заблокировать вас на каком-то уровне, т. е. она может отказаться от подтверждения, заполнив ваш локальный буфер ОС, и в этот момент записи не будут передаваться из Qt в ОС; независимо от того, на каком уровне находится waitForBytesWritten(), его всегда можно заблокировать.

Таким образом, bytesWritten и waitForBytesWritten() следует использовать только для дросселирования источника данных, т. е. если вы попали в замкнутый цикл, передавая 1 Гб данных в сокет одновременно, вы можете в конечном итоге буферизовать их в процессе и заканчивается память. Запуская дополнительные операции чтения/записи с помощью сигнала bytesWritten, вы можете избежать этой проблемы.

person bdonlan    schedule 11.01.2011
comment
Мне не нужно подтверждение получения. Чего я действительно хочу, так это избежать ситуации, когда клиент может задержать приложение, ожидая отправки ACK. - person Nathan Osman; 11.01.2011