Skip to content

MemoryError and data race in devpoll selector on Solaris #102494

@kulikjak

Description

@kulikjak

There are currently two big issues with DevPoll selector on Solaris.

Memory Error

If you set ulimit -n unlimited on Solaris and its derivatives (where /dev/poll is available) and import selectors, Python crashes with a MemoryError:

> ulimit -n unlimited
> python3.11 -c "import selectors"
Traceback (most recent call last):
  File "<string>", line 1, in <module>
  File "/usr/lib/python3.11/selectors.py", line 613, in <module>
    elif _can_use('devpoll'):
         ^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.11/selectors.py", line 594, in _can_use
    selector_obj = selector()
                   ^^^^^^^^^^
MemoryError

The issue is that Python uses RLIMIT_NOFILE to allocated that many struct pollfds, and there is no upper limit. Infinity is represented by something close to INT_MAX, and the allocation thus fails.

Data race

There is a potential data race when multiple threads are operating on the same DevpollSelector; specifically when one thread is registering a new file object at the same time another one is polling. The issue is that the same struct pollfd buffer is used for both operations. Since sections around the OS calls have threads enabled, this can result in Python registering fd which just returned from the poll operation (rather than the one given), or vice versa.

Update: I added the second issue, which was not known when I originally filed this, but the attached PR fixes it as well.

Your environment

I tested this on Oracle Solaris with 3.11, 3.9 and 3.7 (where you need a slightly different way to crash it: python3.7 -c "import select; select.devpoll()").

I verified that on SmartOS, it behaves the same way (on SmartOS, you can actually set huge ulimit -n values that break it as well).

Linked PRs

Metadata

Metadata

Assignees

No one assigned

    Labels

    OS-unsupportedstdlibStandard Library Python modules in the Lib/ directorytype-bugAn unexpected behavior, bug, or error
    No fields configured for issues without a type.

    Projects

    Status

    No status

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions