classification
Title: PyType_Ready doesn't ensure that all bases are ready
Type: enhancement Stage: needs patch
Components: Interpreter Core Versions: Python 3.2
process
Status: open Resolution:
Dependencies: Superseder:
Assigned To: Nosy List: amaury.forgeotdarc, belopolsky, benjamin.peterson, rupole
Priority: normal Keywords:

Created on 2008-07-27 15:14 by rupole, last changed 2010-06-10 23:38 by belopolsky.

Messages (7)
msg70322 - (view) Author: Roger Upole (rupole) Date: 2008-07-27 15:14
If a type's tp_base has not been initialized yet, PyType_Ready calls 
itself for tp_base.  However, it doesn't do the same for members of 
tp_bases.  The inheritance determinations assume that all bases are 
ready, in particular that tp_mro is not null.
msg70324 - (view) Author: Benjamin Peterson (benjamin.peterson) * (Python committer) Date: 2008-07-27 15:24
I believe that's because the bases are supposed to be ready at the time
a subclass is created.
msg70376 - (view) Author: Roger Upole (rupole) Date: 2008-07-29 02:55
If that were the case, it wouldn't need to call PyType_Ready for 
tp_base either.  From stepping thru the code, there are several places 
in the interpreter core that PyType_Ready is called for types whose 
tp_base has not been initialized yet.
msg70378 - (view) Author: Amaury Forgeot d'Arc (amaury.forgeotdarc) * (Python committer) Date: 2008-07-29 07:19
PyType_Ready is called for each class in tp_bases.
This is done in typeobject.c::best_base()
Isn't it the case in your program?
msg70380 - (view) Author: Amaury Forgeot d'Arc (amaury.forgeotdarc) * (Python committer) Date: 2008-07-29 08:40
Forget my last remark: it applies to heap types (created with
type_new()) and not to static types.

However, it seems that a non-ready class in tp_bases can happen only
when an extension type inherits from another extension type.
It is good practice to call PyType_Ready() on every type you define
(otherwise tp_methods doesn't work); doesn't this answer the initial
problem?
msg71482 - (view) Author: Roger Upole (rupole) Date: 2008-08-19 20:58
This doesn't address the discrepancy between tp_base and tp_bases.
If multiple bases are used, it's no longer 'good practice', it's an
absolute requirement.  IMO, it should call PyType_Ready for all bases, 
or none of them.

Since the code assumes that all bases have been
initialized, it could at least ASSERT so, rather than crashing deep
within the mro calculations.
msg107502 - (view) Author: Alexander Belopolsky (belopolsky) * (Python committer) Date: 2010-06-10 23:38
My knowledge may be out of date, but I thought multiple inheritance was only supported at the python level.  If this is still the case, then no initialization check is needed. (You cannot get an uninitialized type at python level.)  An extra defensive assert is usually not a bad thing in the code, but in this particular case one would need a loop with checks and it does not seem justified.

-1
History
Date User Action Args
2010-06-10 23:38:45belopolskysetversions: + Python 3.2, - Python 2.6, Python 2.5, Python 2.4
nosy: + belopolsky

messages: + msg107502

type: enhancement
stage: needs patch
2008-08-19 20:58:04rupolesetmessages: + msg71482
2008-07-29 08:40:37amaury.forgeotdarcsetmessages: + msg70380
2008-07-29 07:20:00amaury.forgeotdarcsetnosy: + amaury.forgeotdarc
messages: + msg70378
2008-07-29 02:55:54rupolesetmessages: + msg70376
2008-07-27 15:24:49benjamin.petersonsetnosy: + benjamin.peterson
messages: + msg70324
2008-07-27 15:14:04rupolecreate