Obtain packet timestamp through ioctl call on socket file descriptor

China☆狼群 提交于 2019-12-21 12:12:15

问题


I'm working on a system running embedded linux. I'm trying to obtain the packet timestamp from a stream I'm receiving on a socket.

After creating the socket, I do the following:

if (fd != -1) {
    int enabled = 1;
    setsockopt(fd, SOL_SOCKET, SO_TIMESTAMP, &enabled, sizeof(enabled);
}

After that I bind the socket, the socket is of type SOCK_STREAM. I successfully receive data on the socket, by calling the function recv(fd, buf, size, 0). Now in order to obtain the timestamp of the received data, I'm currently trying the following:

ret = recv(fd, buf, size, 0);
if (ret > 0) {
    struct timeval tv_ioctl;
    tv_ioctl.tv_sec = 0;
    tv_ioctl.tv_usec = 0;
    int error = ioctl(fd, SO_TIMESTAMP, &tv_ioctl);
    printf("%ld.%ld - error = %d", (long int)tv_ioctl.tv_sec, 
            (long int)tv_ioctl.tv_usec, error);
}

The output of the printf statement is always the following:

0.0 error = -1

The error = -1 indicates that the ioctl call has failed. I've performed a test with getsockopt to check if the SO_TIMESTAMP option is set, getsockopt returns 0 for the option SO_TIMESTAMP so it seems correctly set. I'm a bit lost here, how can I further investigate why the ioctl call seems to be failing?


回答1:


The ioctl to retrieve the most recent timestamp on the socket is SIOCGSTAMP; SO_TIMESTAMP is a socket option, not an ioctl. Your code should read:

int error = ioctl(fd, SIOCGSTAMP, &tv_ioctl);
                      ^^^^^^^^^^

The alternate method to retrieve timestamps is to change recv to recvmmsg and extract the timestamp from the ancillary data. This is more efficient as it involves fewer system calls (Socket reading and timestamps); the ioctl is simpler, though.

Note that SIOCGSTAMP and SO_TIMESTAMP are mutually exclusive - if you're going to use SIOCGSTAMP you should disable SO_TIMESTAMP (with enabled = 0). This is because SO_TIMESTAMP directs the kernel to make the timestamp available via recvmmsg ancillary data instead of via SIOCGSTAMP.



来源:https://stackoverflow.com/questions/36041740/obtain-packet-timestamp-through-ioctl-call-on-socket-file-descriptor

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!