[bind10-dev] Solaris doesn't honor IPV6_USE_MIN_MTU?

JINMEI Tatuya / 神明達哉 jinmei at isc.org
Wed Feb 29 14:48:05 UTC 2012


At Wed, 29 Feb 2012 08:23:32 +1100,
Mark Andrews <marka at isc.org> wrote:

> What we should do is log a bug report with Oracle after making sure
> that the test machine is up to date on its patches.

Right.  It would be nice if someone can confirm that using the test
program (or some other similar way).  uname -a on our test machine
says:
SunOS sol-10.lab.isc.org 5.10 Generic_118833-33 sun4u sparc SUNW,Sun-Fire-V240

> Since this is detectable at runtime I would just log that setsockopt
> IPV6_USE_MIN_MTU is broken and that you are limiting the EDNS UDP
> response then set a maximum EDNS UDP size to be 1280 less headers
> on the socket.

Yes, that (= reducing the response size) is what I proposed in the
previous message.

> When Oracle fix the bug it will be self correcting.  BTW has anyone
> tested if setting IPV6_USE_MIN_MTU in sendmsg is also broken.

On Solaris?  I just did it, and confirmed it's also broken.  A revised
test program is copied below.  It worked as expected on, e.g, a
FreeBSD 8.2 box, but didn't for the Solaris test machine.

---
JINMEI, Tatuya

#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>

#include <netdb.h>
#include <cassert>
#include <iostream>

using namespace std;

int
main(int argc, char* argv[]) {
    if (argc < 2) {
        cerr << "specify an IPv6 address in command line" << endl;
        return (1);
    }

    struct addrinfo hints, *res;

    memset(&hints, 0, sizeof(hints));
    hints.ai_family = AF_INET6;
    hints.ai_socktype = SOCK_DGRAM;
    hints.ai_protocol = IPPROTO_UDP;
    hints.ai_flags = AI_NUMERICHOST | AI_NUMERICSERV;
    const int error =  getaddrinfo(argv[1], "53535", &hints, &res);
    assert(error == 0);

    const int s = socket(res->ai_family, res->ai_socktype, res->ai_protocol);
    assert(s != -1);

    int on = 1;
#if 0
    assert(setsockopt(s, IPPROTO_IPV6, IPV6_USE_MIN_MTU, &on, sizeof(on))
           == 0);
    socklen_t optlen = sizeof(on);
    assert(getsockopt(s, IPPROTO_IPV6, IPV6_USE_MIN_MTU, &on, &optlen) == 0);
    cout << "IPV6_USE_MIN_MTU: " << on << endl;
#endif

    on = 1;
    char buf[1500];
    struct msghdr msghdr;
    struct iovec iov;
    iov.iov_base = buf;
    iov.iov_len = sizeof(buf);
    msghdr.msg_name = res->ai_addr;
    msghdr.msg_namelen = res->ai_addrlen;
    msghdr.msg_iov = &iov;
    msghdr.msg_iovlen = 1;
    msghdr.msg_flags = 0;
    msghdr.msg_controllen = CMSG_SPACE(sizeof(on));
    msghdr.msg_control = malloc(msghdr.msg_controllen);
    assert(msghdr.msg_control != NULL);

    struct cmsghdr* cmsg = CMSG_FIRSTHDR(&msghdr);
    cmsg->cmsg_len = CMSG_LEN(sizeof(int));
    cmsg->cmsg_level = IPPROTO_IPV6;
    cmsg->cmsg_type = IPV6_USE_MIN_MTU;
    cmsg->cmsg_len = CMSG_LEN(sizeof(on));
    memcpy(CMSG_DATA(cmsg), &on, sizeof(on));

    assert(sendmsg(s, &msghdr, 0) == sizeof(buf));

    return (0);
}


More information about the bind10-dev mailing list