From f76de62f7d48a25d5f67357ae7b2f487904a5fcc Mon Sep 17 00:00:00 2001 From: Guido van Rossum Date: Thu, 18 Oct 2001 15:49:21 +0000 Subject: [PATCH] Fix SF bug #472234: type(obj) calls type->tp_init (Roeland Rengelink) The fix is a band-aid: type_call() now makes the same exception for a single-argument call to type() as type_new() was already making. --- Lib/test/test_descr.py | 12 ++++++++++++ Misc/ACKS | 1 + Objects/typeobject.c | 7 +++++++ 3 files changed, 20 insertions(+) diff --git a/Lib/test/test_descr.py b/Lib/test/test_descr.py index c9235c8b0e5..962c1cc7a04 100644 --- a/Lib/test/test_descr.py +++ b/Lib/test/test_descr.py @@ -716,6 +716,18 @@ def _get_x(self): return "D" + self.__super._get_x() vereq(D().x, "DCBA") + # Make sure type(x) doesn't call x.__class__.__init__ + class T(type): + counter = 0 + def __init__(self, *args): + T.counter += 1 + class C: + __metaclass__ = T + vereq(T.counter, 1) + a = C() + vereq(type(a), C) + vereq(T.counter, 1) + def pymods(): if verbose: print "Testing Python subclass of module..." log = [] diff --git a/Misc/ACKS b/Misc/ACKS index 0ae72c34d4e..e7400e9e51a 100644 --- a/Misc/ACKS +++ b/Misc/ACKS @@ -337,6 +337,7 @@ Sean Reifschneider Michael P. Reilly Bernhard Reiter Steven Reiz +Roeland Rengelink Jan Pieter Riegel Armin Rigo Nicholas Riley diff --git a/Objects/typeobject.c b/Objects/typeobject.c index c37e54f900f..66eecec6d16 100644 --- a/Objects/typeobject.c +++ b/Objects/typeobject.c @@ -147,6 +147,13 @@ type_call(PyTypeObject *type, PyObject *args, PyObject *kwds) obj = type->tp_new(type, args, kwds); if (obj != NULL) { + /* Ugly exception: when the call was type(something), + don't call tp_init on the result. */ + if (type == &PyType_Type && + PyTuple_Check(args) && PyTuple_GET_SIZE(args) == 1 && + (kwds == NULL || + (PyDict_Check(kwds) && PyDict_Size(kwds) == 0))) + return obj; type = obj->ob_type; if (type->tp_init != NULL && type->tp_init(obj, args, kwds) < 0) {