Skip to content

Workaround mishandled nested classes in Python and cPickle #5986

@nthiery

Description

@nthiery

With the python code below::
class A:
class B:
pass
Python 2.6 erroneously set the B.name to "B" instead of "A.B".

Furthermore, upon pickling (here in save_global)
and unpickling (in load_global) a class
with name "A.B" in a module mod, the standard
cPickle module searches for "A.B" in mod.dict
instead of looking up "A" and then "B" in the result.

This patch works around this by a patch to cPickle.c (in fact a copy of it in the Sage source tree; see #5985) which fixes the name for B to its appropriate value A.B, and inserts 'A.B' = A.B in
mod.dict (hacky, but seems to work) the first time A.B is pickled,
and fixes load_global to implement a proper lookup upon unpickling.

It also ensures that sage/interfaces/sage0.py uses loads/dumps from
sage_object rather than calling directly cPickle.loads/dumps
(+1 by cwitty on this change)

Python source experts are more than welcome to rework/rewrite this patch!

Depends on #5483 and #5985

CC: @sagetrac-sage-combinat @sagetrac-cwitty

Component: misc

Keywords: nested classes

Author: Craig Citro, Nicolas M. Thiéry

Reviewer: Robert Bradshaw

Merged: sage-4.2.alpha0

Issue created by migration from https://trac.sagemath.org/ticket/5986

Metadata

Metadata

Assignees

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions