【问题标题】:How to accelerate writing to tcp socket?如何加速写入 tcp 套接字?
【发布时间】:2018-02-03 03:31:33
【问题描述】:

我正在开发一个 Web 服务器,它返回微小的 JSON(大约 200 字节)。业务逻辑大约花费 2-3 微秒,但写入套接字大约花费 25 微秒。我将write 用于单个缓冲区,writev 用于多个缓冲区。

我已经通过启用 TCP_NODELAY 禁用了 Nagle 算法。有没有其他加速写作的方法?

监听套接字选项:

......
if (listen(sfd, SOMAXCONN) == -1) { ... }

int val = true;
if (setsockopt(sfd, IPPROTO_TCP, TCP_NODELAY, &val, sizeof(val)) == -1) { ... }
if (setsockopt(sfd, IPPROTO_TCP, TCP_DEFER_ACCEPT, &val, sizeof(val)) == -1) { ... }
if (setsockopt(sfd, IPPROTO_TCP, TCP_QUICKACK, &val, sizeof(val)) == -1) { ... }

auto flags = fcntl(sfd, F_GETFL, 0);
if (flags == -1) { ... }
flags |= O_NONBLOCK;
if (fcntl(sfd, F_SETFL, flags) == -1) { ... }
......

接受的套接字选项:

......
int infd = accept(sfd, &in_addr, &in_len);
if (infd == -1) { ... }

auto flags = fcntl(infd, F_GETFL, 0);
if (flags == -1) { ... }
flags |= O_NONBLOCK;
if (fcntl(infd, F_SETFL, flags) == -1) { ... }

int val = true;
if (setsockopt(infd, IPPROTO_TCP, TCP_NODELAY, &val, sizeof(val)) == -1) { ... }
......

提前谢谢你!

【问题讨论】:

  • 这真的有问题吗?这是您应用程序中的 主要瓶颈吗?还不够“好”吗?
  • 使用异步写入,man aio(7)
  • Nagle 不会加速“写作”。它加速了部分数据包的发送。但这在这里有什么关系呢?要么你有很多很多这样的 200 字节数据包(然后 Nagle 无关紧要),要么你只有几个(Nagle 现在很重要,但 25 微秒不再重要)。我不认为aio 是解决方案。无论如何,它通常与缓冲输出无关,但它也只会将 25 us 移动到另一个线程。
  • 据我所知,禁用 Nagle 算法会强制立即发送数据包而无需等待下一部分数据。

标签: c++ sockets tcp


【解决方案1】:

Nagle 算法可能会有所帮助,但它仅在您的瓶颈是往返传输本身时才有帮助。假设您的“写入时间”仅基于数据包 TX 时间(例如:从写入套接字到数据离开适配器的时间),禁用此算法不会解决您的解决方案。基于 TCP 连接的固有流性质,可能没有可靠的解决方法...如果时间真的那么关键,请考虑使用 UDP,尤其是因为您的数据包很小。如果 TCP 是必需品,可能会考虑使用不同的套接字库。不过老实说,你的时机对我来说似乎并没有那么可怕。

【讨论】:

    猜你喜欢
    • 2013-05-25
    • 2015-08-04
    • 1970-01-01
    • 1970-01-01
    • 2016-08-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多