[issue8882] socketmodule.c`getsockaddrarg() should not check the length of sun_path

Edward Pilatowicz report at bugs.python.org
Thu Jun 3 03:27:50 CEST 2010


New submission from Edward Pilatowicz <edward.pilatowicz at oracle.com>:

recently i was writing some python code that attempted to bind a unix
domain socket to a long filesystem path.  this code was failing and
telling me that the path name was too long.  tracing python i saw that
it wasn't event issuing a system call for my bind() request.  eventually
i tracked down the problem to socketmodule.c`getsockaddrarg():

http://svn.python.org/view/python/trunk/Modules/socketmodule.c?view=markup

there we see that getsockaddrarg() checks to verify that the specified
path is less than "sizeof addr->sun_path", where addr is a struct
sockaddr_un.  this seems incorrect to me.

on most systems sockaddr_un.sun_path is defined as a small character
array.  this limit is an ancient bit of unix legacy and most modern
systems do not actually limit domain socket names to a path as short as
sun_path.  on solaris the real limit is MAXPATHLEN, there by allowing
unix domain sockets to be bound to any filesystem path.

the posix specification also says that users of the sockaddr_un 
structure should not make any assumptions about the maximum supported
length of sun_path.

from:
    http://www.opengroup.org/onlinepubs/009695399/basedefs/sys/un.h.html

we have:
    char        sun_path[]    socket pathname
    ...

    The size of sun_path has intentionally been left undefined. This is
    because different implementations use different sizes. For example,
    4.3 BSD uses a size of 108, and 4.4 BSD uses a size of 104. Since
    most implementations originate from BSD versions, the size is
    typically in the range 92 to 108.

    Applications should not assume a particular length for sun_path or
    assume that it can hold {_POSIX_PATH_MAX} characters (255).

hence, it seems to me that python should not actually be doing any size
checks on the path passed to getsockaddrarg().  instead is should
dynamically allocate a sockaddr_un large enough to hold whatever string
was pass in.  this structure can then be passed on to system calls which
can they check if the specified path is of a supported length.  (if you
look at the posix definitions for bind() and connect() you'll see that 
they both can return ENAMETOOLONG if the passed in pathname is too 
large.)

----------
components: None
messages: 106929
nosy: Edward.Pilatowicz
priority: normal
severity: normal
status: open
title: socketmodule.c`getsockaddrarg() should not check the length of sun_path
type: behavior
versions: Python 2.6

_______________________________________
Python tracker <report at bugs.python.org>
<http://bugs.python.org/issue8882>
_______________________________________


More information about the Python-bugs-list mailing list