python / python/cpython

concurrent.interpreters: crash (NULL dereference) when an unpickled AttributeError has a non-string arg

Ouverte
#151,862 0 commentaires 0 réactions 0 personnes assignées Voir sur GitHub

Personne n'a encore pris cette issue.

3.14 3.15 3.16 interpreter-core topic-subinterpreters type-bug
Langage dominant
Python
Étoiles
77.2k
Forks
35.9k
Métriques de merge des PR
Métriques de PR en attente

Description

Python/crossinterp.c's check_missing___main___attr() passes the result of PyUnicode_AsUTF8() straight to strncmp() without a NULL check:

const char *err = PyUnicode_AsUTF8(msgobj);
// Check if it's a missing __main__ attr.
int cmp = strncmp(err, "module '__main__' has no attribute '", 36);

msgobj is args[0] of an AttributeError raised on the receive side of the cross-interpreter pickle fallback, reached when an object is moved between interpreters through a concurrent.interpreters queue or channel and its unpickling in the receiving interpreter fails.

PyUnicode_AsUTF8() returns NULL (and sets an exception) when args[0] is not a str — e.g. AttributeError(42), AttributeError(b'x'), AttributeError(None) — or is a str containing lone surrogates (AttributeError('\ud800')). When err == NULL, strncmp(NULL, ...) dereferences NULL and the interpreter crashes (SIGSEGV).

Reproduction

Put an object into a concurrent.interpreters queue whose unpickling on the receive side raises an AttributeError with a non-string (or surrogate) first argument, then get() it — the receiving interpreter segfaults instead of raising NotShareableError. A self-contained reproduction is added as a regression test (test_get_unpickle_fails_with_bad_attributeerror_arg in Lib/test/test_interpreters/test_queues.py), exercising args 42, b'x', None, and '\ud800'.

Scope

This is the check_missing___main___attr() NULL dereference reached through the queue/channel receive path. It does not by itself make every cross-interpreter unpickle failure safe — Interpreter.call() has a separate crash on its result-preserve path that I will report independently.

Fix

Add a NULL guard immediately after PyUnicode_AsUTF8, matching the correctly-checked sibling helper _copy_string_obj_raw(): on NULL, clear the exception (the function asserts !PyErr_Occurred() on entry), Py_DECREF(msgobj), and return 0 (not a missing-__main__ attribute).

Affected versions

concurrent.interpreters (PEP 734) is public in 3.14+; this reproduces on main and 3.14.

Linked PR

A PR follows.

Linked PRs
  • gh-151863

Guide de contribution

Ouvrir le guide de contribution

Par où commencer

  1. Lisez l'issue en entier, puis le guide de contribution du projet.
  2. Signalez en commentaire que vous la prenez — cela évite que deux personnes fassent le même travail.
  3. Forkez le dépôt et travaillez sur une branche.
  4. Ouvrez une pull request qui référence le numéro de l'issue.

Piste de recherche

L’issue pointe vers Python/crossinterp.c et check_missing___main___attr() ; comparez sa gestion de PyUnicode_AsUTF8() avec celle de l’helper homologue _copy_string_obj_raw(). Exécutez Lib/test/test_interpreters/test_queues.py, en particulier test_get_unpickle_fails_with_bad_attributeerror_arg, et confirmez que les arguments AttributeError malformés listés lèvent NotShareableError sans provoquer de crash. Un PR associé, gh-151863, indique que le travail est déjà en cours.

Rédigé par le modèle d'indexation à partir du texte de l'issue.

Évaluation

Stack technique
c, python
Domaine
compilers
Type d'issue
Bug
Difficulté
2/5
Temps estimé
1-3 heures
Activité
À l'abandon
Clarté
Clairement spécifiée
Accessibilité débutants
25/100

Recevez les nouvelles issues par e-mail

Un résumé court des issues GitHub adaptées aux débutants.