【发布时间】:2015-04-02 18:45:19
【问题描述】:
是否可以通过Linux系统上的非特权套接字获取接收到的ICMP消息的内容?
我很想知道是否可以使用 UDP DGRAM 套接字、TCP STREAM 套接字和/或 ICMP DGRAM 套接字。
TCP套接字
我知道AF_INET, SOCK_STREAM,IPPROTO_TCP 套接字可以通过ENETUNREACH、ETIMEDOUT 等返回值获得关于connect() 结果的反馈。我想要的是实际的整个 ICMP 消息(整个数据包),除了 sudo 和 setuid(没有 raw 套接字)之外的任何方式(创建另一个套接字,...)。
UDP套接字
我知道您可以将IP_RECVERRIP_PROTO-level 选项设置为AF_INET, SOCK_DGRAM,IPPROTO_UDP 套接字,但不能设置为STREAM 套接字。此选项允许调用 recvmsg() 并设置 MSG_ERRQUEUE 标志以接收包含 ICMP 错误的 sock_extended_err 结构。它是默认工作还是我必须指定我想通过哪个ICMP 消息(即:通过ICMP_FILTER 套接字选项)?
ICMP套接字
我也知道,自 ~2010 年以来,Linux 系统允许 AF_INET,SOCK_DGRAM,IPPROTO_ICMP 套接字发送一些 ICMP 消息用于 ping 目的(我不关心发送 ICMP)并接收一些(哪个类型/代码我不知道)。但是貌似默认没有开启,需要root权限才能激活,这是被禁止的。是否可以使用这些来接收ICMP 消息,以及哪些消息?
- 其他信息
我确切地说我是针对 Linux 内核 >=2.6.x 和 IPv4 提出这个问题的。我想要检索的ICMP 消息是最重要的 ttl-expired 和如果可能dest/port/host/network-unreach。我不能以 root 或 setuid root 身份运行该程序,因此禁止使用 RAW 套接字。我不需要检索封装ICMP 消息的IP 层。
【问题讨论】:
-
这不是 100% 重复,但非常接近 stackoverflow.com/questions/11914568/…。
-
ICMP 的级别低于 UDP 和 TCP,所以不,您不能将 UDP 或 TCP 用于 ICMP。
-
@JoachimPileborg 是在不同的抽象层次,但不代表不能在两者之间传递信息(udp stack to application)。
-
@user590028 谢谢,这应该适用于第 2 点。
标签: c sockets networking network-programming icmp