diff options
Diffstat (limited to 'src/corelib')
-rw-r--r-- | src/corelib/tools/qmap.h | 20 |
1 files changed, 20 insertions, 0 deletions
diff --git a/src/corelib/tools/qmap.h b/src/corelib/tools/qmap.h index df0ae46..5696ba6 100644 --- a/src/corelib/tools/qmap.h +++ b/src/corelib/tools/qmap.h @@ -125,6 +125,10 @@ template <class Key, class T> struct QMapNode { Key key; T value; + +private: + // never access these members through this structure. + // see below QMapData::Node *backward; QMapData::Node *forward[1]; }; @@ -134,6 +138,22 @@ struct QMapPayloadNode { Key key; T value; + +private: + // QMap::e is a pointer to QMapData::Node, which matches the member + // below. However, the memory allocation node in QMapData::node_create + // allocates sizeof(QMapPayloNode) and incorrectly calculates the offset + // of 'backward' below. If the alignment of QMapPayloadNode is larger + // than the alignment of a pointer, the 'backward' member is aligned to + // the end of this structure, not to 'value' above, and will occupy the + // tail-padding area. + // + // e.g., on a 32-bit archictecture with Key = int and + // sizeof(T) = alignof(T) = 8 + // 0 4 8 12 16 20 24 byte + // | key | PAD | value |backward| PAD | correct layout + // | key | PAD | value | |backward| how it's actually used + // |<----- value of QMap::payload() = 20 ----->| QMapData::Node *backward; }; |