I am working on a quite complex C program, designed to run under Linux, which is relying a lot on ancillary data coming from sockets.
I am actually experiencing a strange behaviour, which seem to occur, by the way, on my program only (other sample codes, like this one, are working properly). I'm using ancillary data by defining:
struct msghdr mhdr;
struct iovec iov;
struct cmsghdr *cmsg = NULL;
struct sockaddr_ll addrll;
socklen_t addrllLen=sizeof(addrll);
unsigned char packet[PACKET_SIZE_MAX];
char ctrlBuf[CMSG_SPACE(sizeof(struct scm_timestamping))]; // For example, in order to retrieve timestamps
Then, by setting:
memset(&mhdr,0,sizeof(mhdr));
iov.iov_base=packet;
iov.iov_len=sizeof(packet);
mhdr.msg_name=&(addrll); // This is a raw socket
mhdr.msg_namelen=addrllLen; // This is a raw socket
mhdr.msg_control=ctrlBuf;
mhdr.msg_controllen=sizeof(ctrlBuf);
mhdr.msg_iov=&iov;
mhdr.msg_iovlen=1;
mhdr.msg_flags=0;
I then send and receive data using sendto()
and recvmsg()
, after setting some socket options to retrieve useful ancillary data (such as software or hardware timestamps, by setting SO_TIMESTAMPING
). I was able to verify that these options are actually supported by the sockets I am opening.
The issue sometimes comes up when I try to extract the ancillary data, using a code like the following one, which is, for instance, extracting a struct scm_timestamping
with transmit/receive timestamps:
for(cmsg=CMSG_FIRSTHDR(&mhdr);cmsg!=NULL;cmsg=CMSG_NXTHDR(&mhdr, cmsg)) {
if(cmsg->cmsg_level==SOL_SOCKET && cmsg->cmsg_type==SO_TIMESTAMPING) {
hw_ts=*((struct scm_timestamping *)CMSG_DATA(cmsg));
}
}
Sometimes, CMSG_FIRSTHDR(&mhdr)
returns a null pointer and the returned mhdr.msg_controllen
is 0
, in such a way that I cannot extract any timestamp.
Other times, on the same PC and using the same NIC, everything is perfectly fine.
So, my question is: in which cases can the returned mhdr.msg_controllen
be 0
, in general? Can this be due to a problem in the definition of the struct msghdr
? Or is this due to some sort of kernel problem?