Joh*_*nck 35

由于其他常量类似于INADDR_LOOPBACK主机字节顺序,我提交此系列中的所有常量应该已htonl应用于它们,包括INADDR_ANY.

(注意:我在@Mat编辑时写了这个答案;他的答案现在也说最好是保持一致并且总是使用htonl.)

合理

如果您这样编写代码,则对代码的未来维护者构成危害:

if (some_condition)
    sa.s_addr = htonl(INADDR_LOOPBACK);
else
    sa.s_addr = INADDR_ANY;
Run Code Online (Sandbox Code Playgroud)

如果我正在审查这段代码,我会立即质疑为什么其中一个常量已htonl应用而另一个未应用.而且我会将其报告为一个错误,无论我是否碰巧拥有INADDR_ANY始终为0 的"内部知识",因此将其转换为无操作.

您编写的代码不仅仅是关于具有正确的运行时行为,还应该在可能的情况下显而易见,并且容易相信它是正确的.出于这个原因,你不应该剥离htonl周围INADDR_ANY.不使用htonl我可以看到的三个原因是:

  1. 它可能冒犯有经验的套接字程序员使用,htonl因为他们知道它什么都不做(因为他们知道心脏的常数值).
  2. 它需要较少的输入以省略它.
  3. 虚假的"性能"优化(显然无关紧要).

  • 我完全同意,像你这样的"有经验的套接字程序员"在没有`htonl`的情况下阅读代码不会有任何问题.我认为,那些了解C但不具备套接字API专业知识的人会发现,如果代码保持一致,就更容易维护代码.我同意不同意你的断言,即编写对新手不友好的代码会更好. (6认同)
  • 你之前说"你显然没有真正完成任何套接字接口编程",现在你抱怨我在你的大方向上进行讽刺性的刺戳.你可能会惊讶地发现我在C中使用套接字做了很多工作(但仍然发现这里的原始问题很有趣!). (6认同)
  • 我将编辑我的答案,以反映不使用htonl的第三个原因是它不会冒犯greybeards. (2认同)
  • 关于GCC的Re#3,至少编译器能够通过`htonl`和朋友进行常量折叠,因此对性能没有影响. (2认同)

Mat*_*Mat 18

INADDR_ANY是IPV4中的"任何地址".该地址0.0.0.0以点分表示,因此0x000000在任何字节序的十六进制中.通过它htonl没有任何影响.

现在,如果您想了解其他宏常量,请查看INADDR_LOOPBACK它是否在您的平台上定义.有可能是这样的宏:

#define INADDR_LOOPBACK     0x7f000001  /* 127.0.0.1   */
Run Code Online (Sandbox Code Playgroud)

(来自linux/in.h,等效定义winsock.h).

因此INADDR_LOOPBACK,有htonl必要.

为了保持一致性,因此可以更好地htonl在所有情况下使用.

  • @John:这都是订单.它是零.所有位都为零.它也不会从零改变 - 它在IP RFC中定义. (2认同)

R..*_*R.. 8

无论是正确的,因为有义INADDR_ANYhtonl被弃用,导致复杂的,丑陋的代码仅适用于IPv4.切换到getaddrinfo用于满足所有套接字地址创建需求:

struct addrinfo *ai, hints = { .ai_flags = AI_PASSIVE|AI_ADDRCONFIG };
getaddrinfo(0, "1234", &hints, &ai);
Run Code Online (Sandbox Code Playgroud)

替换"1234"为您的端口号或服务名称.