David Watson <bai...@users.sourceforge.net> added the comment: Here is a new version of the patch; I've added some tests which use the RFC 3542 interface (IPv6 advanced API) and am now quite happy with it generally.
As well as Linux, I've tested it on an old (unsupported) FreeBSD 5.3 installation, which required a few changes in the tests and the code, but is probably representative of many socket implementations. Testing on other systems would be appreciated! The main issue was that when truncating ancillary data, FreeBSD seemed to just copy as much into the buffer as would fit and did not adjust the last item's cmsg_len member to reflect the amount of data that was actually present, so the item would appear to extend past the end of the buffer. The last version of the patch detected this and raised RuntimeError, which prevented any truncated receives from succeeding. The new version instead issues a warning and returns as much of the last item as is in the buffer. The warning could perhaps be disabled for systems like this, given that it happens every time ancillary data is truncated, but truncation generally shouldn't happen in a program's normal operation, and on other platforms a bad cmsg_len value might indicate that the returned data is actually incorrect in some way. After some investigation, I've stuck with using CMSG_FIRSTHDR() and CMSG_NXTHDR() to step through the headers when assembling the ancillary data in sendmsg(). The KAME IPv6 userspace utilities at [1] include several programs which send multiple control messages at once, and these always use CMSG_NXTHDR() to advance to the next uninitialized header, while some (but not all) of them zero-fill the buffer beforehand, suggesting they ran into the issue with glibc's macros returning NULL (KAME developed the BSD IPv6 stack, and the zero-filling isn't necessary with the BSD macros). The alternative would be to add CMSG_SPACE(size) to the pointer to get to the next header. Going by the diagram in RFC 3542, that should be equivalent, but if some system defined CMSG_SPACE(len) as, say, CMSG_LEN(len) + 3, instead of (CMSG_LEN(len) + 3) & ~3, it would probably go unnoticed until someone tried to use CMSG_SPACE() that way. So given the KAME example, I think using CMSG_NXTHDR() with a zero-filled buffer is the way to go. [1] http://www.kame.net/dev/cvsweb2.cgi/kame/kame/kame/ ---------- Added file: http://bugs.python.org/file17483/baikie-hwundram-v3.diff _______________________________________ Python tracker <rep...@bugs.python.org> <http://bugs.python.org/issue6560> _______________________________________ _______________________________________________ Python-bugs-list mailing list Unsubscribe: http://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com