Connecting a socket in timeout mode to a server with full listen backlog raises BlockingIOError
Personne n'a encore pris cette issue.
- Langage dominant
- Python
- Étoiles
- 77.2k
- Forks
- 36k
- Métriques de merge des PR
- Métriques de PR en attente
Description
Bug report
Bug description:
I'm working on a Debian bookworm system. Please consider this executable script ms:
#!/usr/bin/python3 -i
from pathlib import Path
import socket
SOCK = 'stream.sock'
s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
Path(SOCK).unlink(missing_ok=True)
s.bind(SOCK)
s.listen(0)
and this one mc:
#!/usr/bin/python3
import socket
SOCK = 'stream.sock'
s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
s.settimeout(3)
s.connect(SOCK)
Let's start ./ms, and once it reaches the Python prompt, run ./mc twice in another terminal:
$ ./mc
$ ./mc
Traceback (most recent call last):
File "/home/wferi/block/./mc", line 8, in <module>
s.connect(SOCK)
BlockingIOError: [Errno 11] Resource temporarily unavailable
The first[^1] invocation runs to completion all right, but all succeeding ones immediately fail with BlockingIOError, as if the connecting socket was in non-blocking mode, not in timeout mode. I understand that the documentation[^2] notes
at the operating system level, sockets in timeout mode are internally set in non-blocking mode
so that must be where this comes from, but such an implementation detail shouldn't leak out of the abstraction, as the documentation also states that
A socket object can be in one of three modes: blocking, non-blocking, or timeout.
and
exception BlockingIOError: Raised when an operation would block on an object (e.g. socket) set for non-blocking operation. [^3]
[^1]: In general the first backlog+1, but I set the listen backlog to 0 in the code of ms above.
[^2]: https://docs.python.org/3/library/socket.html#socket-timeouts
[^3]: https://docs.python.org/3/library/exceptions.html
CPython versions tested on:
3.11
Operating systems tested on:
Linux
Linked PRs
- gh-134688
Guide de contribution
Ouvrir le guide de contribution
Par où commencer
- Lisez l'issue en entier, puis le guide de contribution du projet.
- Signalez en commentaire que vous la prenez — cela évite que deux personnes fassent le même travail.
- Forkez le dépôt et travaillez sur une branche.
- Ouvrez une pull request qui référence le numéro de l'issue.
Piste de recherche
Reproduisez le comportement avec les scripts ms et mc de l’issue, en utilisant un socket Unix avec listen(0) et des connexions temporisées répétées. Lisez la documentation liée sur les timeouts et les exceptions des sockets, puis examinez l’implémentation pertinente des sockets de CPython ainsi que la PR liée gh-134688. Le travail est considéré comme terminé lorsque l’abstraction de timeout documentée est préservée lorsque la file d’attente d’écoute est pleine, avec une couverture de régression pour le cas reproduit.
Rédigé par le modèle d'indexation à partir du texte de l'issue.
Évaluation
- Stack technique
- python
- Domaine
- networking
- Type d'issue
- Bug
- Difficulté
- 4/5
- Temps estimé
- 3-5 jours
- Activité
- À l'abandon
- Clarté
- Clairement spécifiée
- Accessibilité débutants
- 35/100