blob: b1f11b3e695bb32c2de2b8390ce62c8037357117 [file] [log] [blame]
Guido van Rossum2bc13791999-03-24 19:06:42 +00001/* Dictionary object implementation using a hash table */
Guido van Rossum9bfef441993-03-29 10:43:31 +00002
Raymond Hettinger930427b2003-05-03 06:51:59 +00003/* The distribution includes a separate file, Objects/dictnotes.txt,
Tim Peters60b29962006-01-01 01:19:23 +00004 describing explorations into dictionary design and optimization.
Raymond Hettinger930427b2003-05-03 06:51:59 +00005 It covers typical dictionary use patterns, the parameters for
6 tuning dictionaries, and several ideas for possible optimizations.
7*/
8
Victor Stinner742da042016-09-07 17:40:12 -07009/* PyDictKeysObject
10
11This implements the dictionary's hashtable.
12
Raymond Hettingerb12785d2016-10-22 09:58:14 -070013As of Python 3.6, this is compact and ordered. Basic idea is described here:
14* https://mail.python.org/pipermail/python-dev/2012-December/123028.html
15* https://morepypy.blogspot.com/2015/01/faster-more-memory-efficient-and-more.html
Victor Stinner742da042016-09-07 17:40:12 -070016
17layout:
18
19+---------------+
20| dk_refcnt |
21| dk_size |
22| dk_lookup |
23| dk_usable |
24| dk_nentries |
25+---------------+
26| dk_indices |
27| |
28+---------------+
29| dk_entries |
30| |
31+---------------+
32
33dk_indices is actual hashtable. It holds index in entries, or DKIX_EMPTY(-1)
34or DKIX_DUMMY(-2).
35Size of indices is dk_size. Type of each index in indices is vary on dk_size:
36
37* int8 for dk_size <= 128
38* int16 for 256 <= dk_size <= 2**15
39* int32 for 2**16 <= dk_size <= 2**31
40* int64 for 2**32 <= dk_size
41
dalgarno359143c2019-09-10 10:45:07 +010042dk_entries is array of PyDictKeyEntry. Its size is USABLE_FRACTION(dk_size).
Victor Stinner742da042016-09-07 17:40:12 -070043DK_ENTRIES(dk) can be used to get pointer to entries.
44
45NOTE: Since negative value is used for DKIX_EMPTY and DKIX_DUMMY, type of
46dk_indices entry is signed integer and int16 is used for table which
47dk_size == 256.
48*/
49
Benjamin Peterson7d95e402012-04-23 11:24:50 -040050
51/*
Benjamin Peterson7d95e402012-04-23 11:24:50 -040052The DictObject can be in one of two forms.
Victor Stinner742da042016-09-07 17:40:12 -070053
Benjamin Peterson7d95e402012-04-23 11:24:50 -040054Either:
55 A combined table:
56 ma_values == NULL, dk_refcnt == 1.
57 Values are stored in the me_value field of the PyDictKeysObject.
Benjamin Peterson7d95e402012-04-23 11:24:50 -040058Or:
59 A split table:
60 ma_values != NULL, dk_refcnt >= 1
61 Values are stored in the ma_values array.
Victor Stinner742da042016-09-07 17:40:12 -070062 Only string (unicode) keys are allowed.
63 All dicts sharing same key must have same insertion order.
Benjamin Peterson7d95e402012-04-23 11:24:50 -040064
Victor Stinner742da042016-09-07 17:40:12 -070065There are four kinds of slots in the table (slot is index, and
66DK_ENTRIES(keys)[index] if index >= 0):
67
681. Unused. index == DKIX_EMPTY
69 Does not hold an active (key, value) pair now and never did. Unused can
70 transition to Active upon key insertion. This is each slot's initial state.
71
722. Active. index >= 0, me_key != NULL and me_value != NULL
73 Holds an active (key, value) pair. Active can transition to Dummy or
74 Pending upon key deletion (for combined and split tables respectively).
75 This is the only case in which me_value != NULL.
76
773. Dummy. index == DKIX_DUMMY (combined only)
78 Previously held an active (key, value) pair, but that was deleted and an
79 active pair has not yet overwritten the slot. Dummy can transition to
80 Active upon key insertion. Dummy slots cannot be made Unused again
81 else the probe sequence in case of collision would have no way to know
82 they were once active.
83
844. Pending. index >= 0, key != NULL, and value == NULL (split only)
85 Not yet inserted in split-table.
Benjamin Peterson7d95e402012-04-23 11:24:50 -040086*/
87
Victor Stinner742da042016-09-07 17:40:12 -070088/*
89Preserving insertion order
Benjamin Peterson7d95e402012-04-23 11:24:50 -040090
Victor Stinner742da042016-09-07 17:40:12 -070091It's simple for combined table. Since dk_entries is mostly append only, we can
92get insertion order by just iterating dk_entries.
93
94One exception is .popitem(). It removes last item in dk_entries and decrement
95dk_nentries to achieve amortized O(1). Since there are DKIX_DUMMY remains in
96dk_indices, we can't increment dk_usable even though dk_nentries is
97decremented.
98
99In split table, inserting into pending entry is allowed only for dk_entries[ix]
100where ix == mp->ma_used. Inserting into other index and deleting item cause
101converting the dict to the combined table.
102*/
103
104/* PyDict_MINSIZE is the starting size for any new dict.
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400105 * 8 allows dicts with no more than 5 active entries; experiments suggested
106 * this suffices for the majority of dicts (consisting mostly of usually-small
107 * dicts created to pass keyword arguments).
108 * Making this 8, rather than 4 reduces the number of resizes for most
109 * dictionaries, without any significant extra memory use.
110 */
Victor Stinner742da042016-09-07 17:40:12 -0700111#define PyDict_MINSIZE 8
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400112
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000113#include "Python.h"
Victor Stinnere5014be2020-04-14 17:52:15 +0200114#include "pycore_gc.h" // _PyObject_GC_IS_TRACKED()
Victor Stinner59d3dce2020-06-02 14:03:25 +0200115#include "pycore_object.h" // _PyObject_GC_TRACK()
116#include "pycore_pyerrors.h" // _PyErr_Fetch()
Victor Stinnere5014be2020-04-14 17:52:15 +0200117#include "pycore_pystate.h" // _PyThreadState_GET()
Eric Snow96c6af92015-05-29 22:21:39 -0600118#include "dict-common.h"
Victor Stinnere5014be2020-04-14 17:52:15 +0200119#include "stringlib/eq.h" // unicode_eq()
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000120
Larry Hastings61272b72014-01-07 12:41:53 -0800121/*[clinic input]
Larry Hastingsc2047262014-01-25 20:43:29 -0800122class dict "PyDictObject *" "&PyDict_Type"
Larry Hastings61272b72014-01-07 12:41:53 -0800123[clinic start generated code]*/
Larry Hastings581ee362014-01-28 05:00:08 -0800124/*[clinic end generated code: output=da39a3ee5e6b4b0d input=f157a5a0ce9589d6]*/
Larry Hastings44e2eaa2013-11-23 15:37:55 -0800125
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400126
127/*
128To ensure the lookup algorithm terminates, there must be at least one Unused
129slot (NULL key) in the table.
130To avoid slowing down lookups on a near-full table, we resize the table when
131it's USABLE_FRACTION (currently two-thirds) full.
132*/
Guido van Rossum16e93a81997-01-28 00:00:11 +0000133
Tim Peterseb28ef22001-06-02 05:27:19 +0000134#define PERTURB_SHIFT 5
135
Guido van Rossum16e93a81997-01-28 00:00:11 +0000136/*
Tim Peterseb28ef22001-06-02 05:27:19 +0000137Major subtleties ahead: Most hash schemes depend on having a "good" hash
138function, in the sense of simulating randomness. Python doesn't: its most
R David Murray537ad7a2016-07-10 12:33:18 -0400139important hash functions (for ints) are very regular in common
Tim Peterseb28ef22001-06-02 05:27:19 +0000140cases:
Tim Peters15d49292001-05-27 07:39:22 +0000141
R David Murray537ad7a2016-07-10 12:33:18 -0400142 >>>[hash(i) for i in range(4)]
Guido van Rossumdc5f6b22006-08-24 21:29:26 +0000143 [0, 1, 2, 3]
Tim Peters15d49292001-05-27 07:39:22 +0000144
Tim Peterseb28ef22001-06-02 05:27:19 +0000145This isn't necessarily bad! To the contrary, in a table of size 2**i, taking
146the low-order i bits as the initial table index is extremely fast, and there
R David Murray537ad7a2016-07-10 12:33:18 -0400147are no collisions at all for dicts indexed by a contiguous range of ints. So
148this gives better-than-random behavior in common cases, and that's very
149desirable.
Tim Peters15d49292001-05-27 07:39:22 +0000150
Tim Peterseb28ef22001-06-02 05:27:19 +0000151OTOH, when collisions occur, the tendency to fill contiguous slices of the
152hash table makes a good collision resolution strategy crucial. Taking only
153the last i bits of the hash code is also vulnerable: for example, consider
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000154the list [i << 16 for i in range(20000)] as a set of keys. Since ints are
Guido van Rossumdc5f6b22006-08-24 21:29:26 +0000155their own hash codes, and this fits in a dict of size 2**15, the last 15 bits
156 of every hash code are all 0: they *all* map to the same table index.
Tim Peters15d49292001-05-27 07:39:22 +0000157
Tim Peterseb28ef22001-06-02 05:27:19 +0000158But catering to unusual cases should not slow the usual ones, so we just take
159the last i bits anyway. It's up to collision resolution to do the rest. If
160we *usually* find the key we're looking for on the first try (and, it turns
161out, we usually do -- the table load factor is kept under 2/3, so the odds
162are solidly in our favor), then it makes best sense to keep the initial index
163computation dirt cheap.
Tim Peters15d49292001-05-27 07:39:22 +0000164
Tim Peterseb28ef22001-06-02 05:27:19 +0000165The first half of collision resolution is to visit table indices via this
166recurrence:
Tim Peters15d49292001-05-27 07:39:22 +0000167
Tim Peterseb28ef22001-06-02 05:27:19 +0000168 j = ((5*j) + 1) mod 2**i
Tim Peters15d49292001-05-27 07:39:22 +0000169
Tim Peterseb28ef22001-06-02 05:27:19 +0000170For any initial j in range(2**i), repeating that 2**i times generates each
171int in range(2**i) exactly once (see any text on random-number generation for
172proof). By itself, this doesn't help much: like linear probing (setting
173j += 1, or j -= 1, on each loop trip), it scans the table entries in a fixed
174order. This would be bad, except that's not the only thing we do, and it's
175actually *good* in the common cases where hash keys are consecutive. In an
176example that's really too small to make this entirely clear, for a table of
177size 2**3 the order of indices is:
Tim Peters15d49292001-05-27 07:39:22 +0000178
Tim Peterseb28ef22001-06-02 05:27:19 +0000179 0 -> 1 -> 6 -> 7 -> 4 -> 5 -> 2 -> 3 -> 0 [and here it's repeating]
180
181If two things come in at index 5, the first place we look after is index 2,
182not 6, so if another comes in at index 6 the collision at 5 didn't hurt it.
183Linear probing is deadly in this case because there the fixed probe order
184is the *same* as the order consecutive keys are likely to arrive. But it's
185extremely unlikely hash codes will follow a 5*j+1 recurrence by accident,
186and certain that consecutive hash codes do not.
187
188The other half of the strategy is to get the other bits of the hash code
189into play. This is done by initializing a (unsigned) vrbl "perturb" to the
190full hash code, and changing the recurrence to:
191
Tim Peterseb28ef22001-06-02 05:27:19 +0000192 perturb >>= PERTURB_SHIFT;
INADA Naoki267941c2016-10-06 15:19:07 +0900193 j = (5*j) + 1 + perturb;
Tim Peterseb28ef22001-06-02 05:27:19 +0000194 use j % 2**i as the next table index;
195
196Now the probe sequence depends (eventually) on every bit in the hash code,
197and the pseudo-scrambling property of recurring on 5*j+1 is more valuable,
198because it quickly magnifies small differences in the bits that didn't affect
199the initial index. Note that because perturb is unsigned, if the recurrence
200is executed often enough perturb eventually becomes and remains 0. At that
201point (very rarely reached) the recurrence is on (just) 5*j+1 again, and
202that's certain to find an empty slot eventually (since it generates every int
203in range(2**i), and we make sure there's always at least one empty slot).
204
205Selecting a good value for PERTURB_SHIFT is a balancing act. You want it
206small so that the high bits of the hash code continue to affect the probe
207sequence across iterations; but you want it large so that in really bad cases
208the high-order hash bits have an effect on early iterations. 5 was "the
209best" in minimizing total collisions across experiments Tim Peters ran (on
210both normal and pathological cases), but 4 and 6 weren't significantly worse.
211
Guido van Rossumdc5f6b22006-08-24 21:29:26 +0000212Historical: Reimer Behrends contributed the idea of using a polynomial-based
Tim Peterseb28ef22001-06-02 05:27:19 +0000213approach, using repeated multiplication by x in GF(2**n) where an irreducible
214polynomial for each table size was chosen such that x was a primitive root.
215Christian Tismer later extended that to use division by x instead, as an
216efficient way to get the high bits of the hash code into play. This scheme
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000217also gave excellent collision statistics, but was more expensive: two
218if-tests were required inside the loop; computing "the next" index took about
219the same number of operations but without as much potential parallelism
220(e.g., computing 5*j can go on at the same time as computing 1+perturb in the
221above, and then shifting perturb can be done while the table index is being
222masked); and the PyDictObject struct required a member to hold the table's
223polynomial. In Tim's experiments the current scheme ran faster, produced
224equally good collision statistics, needed less code & used less memory.
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000225
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000226*/
Tim Petersdea48ec2001-05-22 20:40:22 +0000227
Fred Drake1bff34a2000-08-31 19:31:38 +0000228/* forward declarations */
Victor Stinner742da042016-09-07 17:40:12 -0700229static Py_ssize_t lookdict(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900230 Py_hash_t hash, PyObject **value_addr);
Victor Stinner742da042016-09-07 17:40:12 -0700231static Py_ssize_t lookdict_unicode(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900232 Py_hash_t hash, PyObject **value_addr);
Victor Stinner742da042016-09-07 17:40:12 -0700233static Py_ssize_t
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400234lookdict_unicode_nodummy(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900235 Py_hash_t hash, PyObject **value_addr);
Victor Stinner742da042016-09-07 17:40:12 -0700236static Py_ssize_t lookdict_split(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900237 Py_hash_t hash, PyObject **value_addr);
Fred Drake1bff34a2000-08-31 19:31:38 +0000238
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400239static int dictresize(PyDictObject *mp, Py_ssize_t minused);
Tim Petersdea48ec2001-05-22 20:40:22 +0000240
INADA Naoki2aaf98c2018-09-26 12:59:00 +0900241static PyObject* dict_iter(PyDictObject *dict);
242
Benjamin Peterson3c569292016-09-08 13:16:41 -0700243/*Global counter used to set ma_version_tag field of dictionary.
Victor Stinner3b6a6b42016-09-08 12:51:24 -0700244 * It is incremented each time that a dictionary is created and each
245 * time that a dictionary is modified. */
246static uint64_t pydict_global_version = 0;
247
248#define DICT_NEXT_VERSION() (++pydict_global_version)
249
Serhiy Storchaka1009bf12015-04-03 23:53:51 +0300250#include "clinic/dictobject.c.h"
251
Victor Stinner522691c2020-06-23 16:40:40 +0200252
253static struct _Py_dict_state *
254get_dict_state(void)
255{
256 PyInterpreterState *interp = _PyInterpreterState_GET();
257 return &interp->dict_state;
258}
259
260
Victor Stinnerae00a5a2020-04-29 02:29:20 +0200261void
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200262_PyDict_ClearFreeList(PyThreadState *tstate)
Christian Heimes77c02eb2008-02-09 02:18:51 +0000263{
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200264 struct _Py_dict_state *state = &tstate->interp->dict_state;
265 while (state->numfree) {
266 PyDictObject *op = state->free_list[--state->numfree];
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000267 assert(PyDict_CheckExact(op));
268 PyObject_GC_Del(op);
269 }
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200270 while (state->keys_numfree) {
271 PyObject_FREE(state->keys_free_list[--state->keys_numfree]);
Victor Stinner742da042016-09-07 17:40:12 -0700272 }
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200273}
274
275
276void
277_PyDict_Fini(PyThreadState *tstate)
278{
279 _PyDict_ClearFreeList(tstate);
280#ifdef Py_DEBUG
Victor Stinner522691c2020-06-23 16:40:40 +0200281 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200282 state->numfree = -1;
283 state->keys_numfree = -1;
Victor Stinnerb4b53862020-05-05 19:55:29 +0200284#endif
Antoine Pitrou9a812cb2011-11-15 00:00:12 +0100285}
286
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200287
David Malcolm49526f42012-06-22 14:55:41 -0400288/* Print summary info about the state of the optimized allocator */
289void
290_PyDict_DebugMallocStats(FILE *out)
291{
Victor Stinner522691c2020-06-23 16:40:40 +0200292 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200293 _PyDebugAllocatorStats(out, "free PyDictObject",
294 state->numfree, sizeof(PyDictObject));
David Malcolm49526f42012-06-22 14:55:41 -0400295}
296
297
Victor Stinner742da042016-09-07 17:40:12 -0700298#define DK_SIZE(dk) ((dk)->dk_size)
299#if SIZEOF_VOID_P > 4
Victor Stinner58f7c5a2016-09-08 11:37:36 -0700300#define DK_IXSIZE(dk) \
301 (DK_SIZE(dk) <= 0xff ? \
302 1 : DK_SIZE(dk) <= 0xffff ? \
303 2 : DK_SIZE(dk) <= 0xffffffff ? \
Benjamin Peterson3c569292016-09-08 13:16:41 -0700304 4 : sizeof(int64_t))
Victor Stinner742da042016-09-07 17:40:12 -0700305#else
Victor Stinner58f7c5a2016-09-08 11:37:36 -0700306#define DK_IXSIZE(dk) \
307 (DK_SIZE(dk) <= 0xff ? \
308 1 : DK_SIZE(dk) <= 0xffff ? \
Benjamin Peterson3c569292016-09-08 13:16:41 -0700309 2 : sizeof(int32_t))
Victor Stinner742da042016-09-07 17:40:12 -0700310#endif
Victor Stinner58f7c5a2016-09-08 11:37:36 -0700311#define DK_ENTRIES(dk) \
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700312 ((PyDictKeyEntry*)(&((int8_t*)((dk)->dk_indices))[DK_SIZE(dk) * DK_IXSIZE(dk)]))
Victor Stinner742da042016-09-07 17:40:12 -0700313
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400314#define DK_MASK(dk) (((dk)->dk_size)-1)
315#define IS_POWER_OF_2(x) (((x) & (x-1)) == 0)
316
INADA Naokia7576492018-11-14 18:39:27 +0900317static void free_keys_object(PyDictKeysObject *keys);
318
319static inline void
320dictkeys_incref(PyDictKeysObject *dk)
321{
Victor Stinner49932fe2020-02-03 17:55:05 +0100322#ifdef Py_REF_DEBUG
323 _Py_RefTotal++;
324#endif
INADA Naokia7576492018-11-14 18:39:27 +0900325 dk->dk_refcnt++;
326}
327
328static inline void
329dictkeys_decref(PyDictKeysObject *dk)
330{
331 assert(dk->dk_refcnt > 0);
Victor Stinner49932fe2020-02-03 17:55:05 +0100332#ifdef Py_REF_DEBUG
333 _Py_RefTotal--;
334#endif
INADA Naokia7576492018-11-14 18:39:27 +0900335 if (--dk->dk_refcnt == 0) {
336 free_keys_object(dk);
337 }
338}
339
Victor Stinner742da042016-09-07 17:40:12 -0700340/* lookup indices. returns DKIX_EMPTY, DKIX_DUMMY, or ix >=0 */
Benjamin Peterson73222252016-09-08 09:58:47 -0700341static inline Py_ssize_t
Andy Lester62d21c92020-03-25 23:13:01 -0500342dictkeys_get_index(const PyDictKeysObject *keys, Py_ssize_t i)
Victor Stinner742da042016-09-07 17:40:12 -0700343{
344 Py_ssize_t s = DK_SIZE(keys);
Victor Stinner71211e32016-09-08 10:52:46 -0700345 Py_ssize_t ix;
346
Victor Stinner742da042016-09-07 17:40:12 -0700347 if (s <= 0xff) {
Andy Lester62d21c92020-03-25 23:13:01 -0500348 const int8_t *indices = (const int8_t*)(keys->dk_indices);
Victor Stinner208857e2016-09-08 11:35:46 -0700349 ix = indices[i];
Victor Stinner742da042016-09-07 17:40:12 -0700350 }
351 else if (s <= 0xffff) {
Andy Lester62d21c92020-03-25 23:13:01 -0500352 const int16_t *indices = (const int16_t*)(keys->dk_indices);
Victor Stinner208857e2016-09-08 11:35:46 -0700353 ix = indices[i];
Victor Stinner742da042016-09-07 17:40:12 -0700354 }
Benjamin Peterson3c569292016-09-08 13:16:41 -0700355#if SIZEOF_VOID_P > 4
Serhiy Storchaka473e0e42016-09-10 21:34:43 +0300356 else if (s > 0xffffffff) {
Andy Lester62d21c92020-03-25 23:13:01 -0500357 const int64_t *indices = (const int64_t*)(keys->dk_indices);
Victor Stinner208857e2016-09-08 11:35:46 -0700358 ix = indices[i];
Victor Stinner742da042016-09-07 17:40:12 -0700359 }
Benjamin Peterson3c569292016-09-08 13:16:41 -0700360#endif
Serhiy Storchaka473e0e42016-09-10 21:34:43 +0300361 else {
Andy Lester62d21c92020-03-25 23:13:01 -0500362 const int32_t *indices = (const int32_t*)(keys->dk_indices);
Serhiy Storchaka473e0e42016-09-10 21:34:43 +0300363 ix = indices[i];
364 }
Victor Stinner71211e32016-09-08 10:52:46 -0700365 assert(ix >= DKIX_DUMMY);
366 return ix;
Victor Stinner742da042016-09-07 17:40:12 -0700367}
368
369/* write to indices. */
Benjamin Peterson73222252016-09-08 09:58:47 -0700370static inline void
INADA Naokia7576492018-11-14 18:39:27 +0900371dictkeys_set_index(PyDictKeysObject *keys, Py_ssize_t i, Py_ssize_t ix)
Victor Stinner742da042016-09-07 17:40:12 -0700372{
373 Py_ssize_t s = DK_SIZE(keys);
Victor Stinner71211e32016-09-08 10:52:46 -0700374
375 assert(ix >= DKIX_DUMMY);
376
Victor Stinner742da042016-09-07 17:40:12 -0700377 if (s <= 0xff) {
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700378 int8_t *indices = (int8_t*)(keys->dk_indices);
Victor Stinner71211e32016-09-08 10:52:46 -0700379 assert(ix <= 0x7f);
Victor Stinner208857e2016-09-08 11:35:46 -0700380 indices[i] = (char)ix;
Victor Stinner742da042016-09-07 17:40:12 -0700381 }
382 else if (s <= 0xffff) {
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700383 int16_t *indices = (int16_t*)(keys->dk_indices);
Victor Stinner71211e32016-09-08 10:52:46 -0700384 assert(ix <= 0x7fff);
Victor Stinner208857e2016-09-08 11:35:46 -0700385 indices[i] = (int16_t)ix;
Victor Stinner742da042016-09-07 17:40:12 -0700386 }
Benjamin Peterson3c569292016-09-08 13:16:41 -0700387#if SIZEOF_VOID_P > 4
Serhiy Storchaka473e0e42016-09-10 21:34:43 +0300388 else if (s > 0xffffffff) {
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700389 int64_t *indices = (int64_t*)(keys->dk_indices);
Victor Stinner208857e2016-09-08 11:35:46 -0700390 indices[i] = ix;
Victor Stinner742da042016-09-07 17:40:12 -0700391 }
Benjamin Peterson3c569292016-09-08 13:16:41 -0700392#endif
Serhiy Storchaka473e0e42016-09-10 21:34:43 +0300393 else {
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700394 int32_t *indices = (int32_t*)(keys->dk_indices);
Serhiy Storchaka473e0e42016-09-10 21:34:43 +0300395 assert(ix <= 0x7fffffff);
396 indices[i] = (int32_t)ix;
397 }
Victor Stinner742da042016-09-07 17:40:12 -0700398}
399
400
Antoine Pitroua504a7a2012-06-24 21:03:45 +0200401/* USABLE_FRACTION is the maximum dictionary load.
Victor Stinner742da042016-09-07 17:40:12 -0700402 * Increasing this ratio makes dictionaries more dense resulting in more
403 * collisions. Decreasing it improves sparseness at the expense of spreading
404 * indices over more cache lines and at the cost of total memory consumed.
Antoine Pitroua504a7a2012-06-24 21:03:45 +0200405 *
406 * USABLE_FRACTION must obey the following:
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400407 * (0 < USABLE_FRACTION(n) < n) for all n >= 2
408 *
Victor Stinner742da042016-09-07 17:40:12 -0700409 * USABLE_FRACTION should be quick to calculate.
410 * Fractions around 1/2 to 2/3 seem to work well in practice.
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400411 */
Victor Stinner742da042016-09-07 17:40:12 -0700412#define USABLE_FRACTION(n) (((n) << 1)/3)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400413
Victor Stinner742da042016-09-07 17:40:12 -0700414/* ESTIMATE_SIZE is reverse function of USABLE_FRACTION.
415 * This can be used to reserve enough size to insert n entries without
416 * resizing.
417 */
INADA Naoki92c50ee2016-11-22 00:57:02 +0900418#define ESTIMATE_SIZE(n) (((n)*3+1) >> 1)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400419
Victor Stinner742da042016-09-07 17:40:12 -0700420/* Alternative fraction that is otherwise close enough to 2n/3 to make
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400421 * little difference. 8 * 2/3 == 8 * 5/8 == 5. 16 * 2/3 == 16 * 5/8 == 10.
422 * 32 * 2/3 = 21, 32 * 5/8 = 20.
423 * Its advantage is that it is faster to compute on machines with slow division.
424 * #define USABLE_FRACTION(n) (((n) >> 1) + ((n) >> 2) - ((n) >> 3))
Victor Stinner742da042016-09-07 17:40:12 -0700425 */
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400426
Victor Stinnera9f61a52013-07-16 22:17:26 +0200427/* GROWTH_RATE. Growth rate upon hitting maximum load.
INADA Naoki5fbc5112018-04-17 15:53:34 +0900428 * Currently set to used*3.
Victor Stinnera9f61a52013-07-16 22:17:26 +0200429 * This means that dicts double in size when growing without deletions,
Raymond Hettinger36f74aa2013-05-17 03:01:13 -0700430 * but have more head room when the number of deletions is on a par with the
INADA Naoki5fbc5112018-04-17 15:53:34 +0900431 * number of insertions. See also bpo-17563 and bpo-33205.
432 *
Raymond Hettinger36f74aa2013-05-17 03:01:13 -0700433 * GROWTH_RATE was set to used*4 up to version 3.2.
434 * GROWTH_RATE was set to used*2 in version 3.3.0
INADA Naoki5fbc5112018-04-17 15:53:34 +0900435 * GROWTH_RATE was set to used*2 + capacity/2 in 3.4.0-3.6.0.
Antoine Pitroua504a7a2012-06-24 21:03:45 +0200436 */
INADA Naoki5fbc5112018-04-17 15:53:34 +0900437#define GROWTH_RATE(d) ((d)->ma_used*3)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400438
439#define ENSURE_ALLOWS_DELETIONS(d) \
440 if ((d)->ma_keys->dk_lookup == lookdict_unicode_nodummy) { \
441 (d)->ma_keys->dk_lookup = lookdict_unicode; \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000442 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400443
444/* This immutable, empty PyDictKeysObject is used for PyDict_Clear()
445 * (which cannot fail and thus can do no allocation).
446 */
447static PyDictKeysObject empty_keys_struct = {
Serhiy Storchaka97932e42016-09-26 23:01:23 +0300448 1, /* dk_refcnt */
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400449 1, /* dk_size */
450 lookdict_split, /* dk_lookup */
451 0, /* dk_usable (immutable) */
Victor Stinner742da042016-09-07 17:40:12 -0700452 0, /* dk_nentries */
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700453 {DKIX_EMPTY, DKIX_EMPTY, DKIX_EMPTY, DKIX_EMPTY,
454 DKIX_EMPTY, DKIX_EMPTY, DKIX_EMPTY, DKIX_EMPTY}, /* dk_indices */
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400455};
456
457static PyObject *empty_values[1] = { NULL };
458
459#define Py_EMPTY_KEYS &empty_keys_struct
460
Victor Stinner611b0fa2016-09-14 15:02:01 +0200461/* Uncomment to check the dict content in _PyDict_CheckConsistency() */
462/* #define DEBUG_PYDICT */
463
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200464#ifdef DEBUG_PYDICT
465# define ASSERT_CONSISTENT(op) assert(_PyDict_CheckConsistency((PyObject *)(op), 1))
466#else
467# define ASSERT_CONSISTENT(op) assert(_PyDict_CheckConsistency((PyObject *)(op), 0))
468#endif
Victor Stinner611b0fa2016-09-14 15:02:01 +0200469
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200470
471int
472_PyDict_CheckConsistency(PyObject *op, int check_content)
Victor Stinner611b0fa2016-09-14 15:02:01 +0200473{
Victor Stinner68762572019-10-07 18:42:01 +0200474#define CHECK(expr) \
475 do { if (!(expr)) { _PyObject_ASSERT_FAILED_MSG(op, Py_STRINGIFY(expr)); } } while (0)
476
477 assert(op != NULL);
478 CHECK(PyDict_Check(op));
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200479 PyDictObject *mp = (PyDictObject *)op;
Victor Stinner50fe3f82018-10-26 18:47:15 +0200480
Victor Stinner611b0fa2016-09-14 15:02:01 +0200481 PyDictKeysObject *keys = mp->ma_keys;
482 int splitted = _PyDict_HasSplitTable(mp);
483 Py_ssize_t usable = USABLE_FRACTION(keys->dk_size);
Victor Stinner611b0fa2016-09-14 15:02:01 +0200484
Victor Stinner68762572019-10-07 18:42:01 +0200485 CHECK(0 <= mp->ma_used && mp->ma_used <= usable);
486 CHECK(IS_POWER_OF_2(keys->dk_size));
487 CHECK(0 <= keys->dk_usable && keys->dk_usable <= usable);
488 CHECK(0 <= keys->dk_nentries && keys->dk_nentries <= usable);
489 CHECK(keys->dk_usable + keys->dk_nentries <= usable);
Victor Stinner611b0fa2016-09-14 15:02:01 +0200490
491 if (!splitted) {
492 /* combined table */
Victor Stinner68762572019-10-07 18:42:01 +0200493 CHECK(keys->dk_refcnt == 1);
Victor Stinner611b0fa2016-09-14 15:02:01 +0200494 }
495
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200496 if (check_content) {
497 PyDictKeyEntry *entries = DK_ENTRIES(keys);
498 Py_ssize_t i;
Victor Stinner611b0fa2016-09-14 15:02:01 +0200499
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200500 for (i=0; i < keys->dk_size; i++) {
501 Py_ssize_t ix = dictkeys_get_index(keys, i);
Victor Stinner68762572019-10-07 18:42:01 +0200502 CHECK(DKIX_DUMMY <= ix && ix <= usable);
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200503 }
Victor Stinner611b0fa2016-09-14 15:02:01 +0200504
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200505 for (i=0; i < usable; i++) {
506 PyDictKeyEntry *entry = &entries[i];
507 PyObject *key = entry->me_key;
508
509 if (key != NULL) {
510 if (PyUnicode_CheckExact(key)) {
511 Py_hash_t hash = ((PyASCIIObject *)key)->hash;
Victor Stinner68762572019-10-07 18:42:01 +0200512 CHECK(hash != -1);
513 CHECK(entry->me_hash == hash);
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200514 }
515 else {
516 /* test_dict fails if PyObject_Hash() is called again */
Victor Stinner68762572019-10-07 18:42:01 +0200517 CHECK(entry->me_hash != -1);
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200518 }
519 if (!splitted) {
Victor Stinner68762572019-10-07 18:42:01 +0200520 CHECK(entry->me_value != NULL);
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200521 }
Victor Stinner611b0fa2016-09-14 15:02:01 +0200522 }
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200523
524 if (splitted) {
Victor Stinner68762572019-10-07 18:42:01 +0200525 CHECK(entry->me_value == NULL);
Victor Stinner611b0fa2016-09-14 15:02:01 +0200526 }
527 }
528
529 if (splitted) {
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200530 /* splitted table */
531 for (i=0; i < mp->ma_used; i++) {
Victor Stinner68762572019-10-07 18:42:01 +0200532 CHECK(mp->ma_values[i] != NULL);
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200533 }
Victor Stinner611b0fa2016-09-14 15:02:01 +0200534 }
535 }
Victor Stinner611b0fa2016-09-14 15:02:01 +0200536 return 1;
Victor Stinner68762572019-10-07 18:42:01 +0200537
538#undef CHECK
Victor Stinner611b0fa2016-09-14 15:02:01 +0200539}
Victor Stinner611b0fa2016-09-14 15:02:01 +0200540
541
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200542static PyDictKeysObject*
543new_keys_object(Py_ssize_t size)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400544{
545 PyDictKeysObject *dk;
Victor Stinner742da042016-09-07 17:40:12 -0700546 Py_ssize_t es, usable;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400547
Victor Stinner742da042016-09-07 17:40:12 -0700548 assert(size >= PyDict_MINSIZE);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400549 assert(IS_POWER_OF_2(size));
Victor Stinner742da042016-09-07 17:40:12 -0700550
551 usable = USABLE_FRACTION(size);
552 if (size <= 0xff) {
553 es = 1;
554 }
555 else if (size <= 0xffff) {
556 es = 2;
557 }
558#if SIZEOF_VOID_P > 4
559 else if (size <= 0xffffffff) {
560 es = 4;
561 }
562#endif
563 else {
564 es = sizeof(Py_ssize_t);
565 }
566
Victor Stinner522691c2020-06-23 16:40:40 +0200567 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200568#ifdef Py_DEBUG
569 // new_keys_object() must not be called after _PyDict_Fini()
570 assert(state->keys_numfree != -1);
571#endif
572 if (size == PyDict_MINSIZE && state->keys_numfree > 0) {
573 dk = state->keys_free_list[--state->keys_numfree];
Victor Stinner742da042016-09-07 17:40:12 -0700574 }
Victor Stinnerb4b53862020-05-05 19:55:29 +0200575 else
Victor Stinnerb4b53862020-05-05 19:55:29 +0200576 {
Victor Stinner98ee9d52016-09-08 09:33:56 -0700577 dk = PyObject_MALLOC(sizeof(PyDictKeysObject)
Victor Stinner98ee9d52016-09-08 09:33:56 -0700578 + es * size
579 + sizeof(PyDictKeyEntry) * usable);
Victor Stinner742da042016-09-07 17:40:12 -0700580 if (dk == NULL) {
581 PyErr_NoMemory();
582 return NULL;
583 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400584 }
Victor Stinner49932fe2020-02-03 17:55:05 +0100585#ifdef Py_REF_DEBUG
586 _Py_RefTotal++;
587#endif
INADA Naokia7576492018-11-14 18:39:27 +0900588 dk->dk_refcnt = 1;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400589 dk->dk_size = size;
Victor Stinner742da042016-09-07 17:40:12 -0700590 dk->dk_usable = usable;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400591 dk->dk_lookup = lookdict_unicode_nodummy;
Victor Stinner742da042016-09-07 17:40:12 -0700592 dk->dk_nentries = 0;
Gregory P. Smith397f1b22018-04-19 22:41:19 -0700593 memset(&dk->dk_indices[0], 0xff, es * size);
Victor Stinner742da042016-09-07 17:40:12 -0700594 memset(DK_ENTRIES(dk), 0, sizeof(PyDictKeyEntry) * usable);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400595 return dk;
596}
597
598static void
599free_keys_object(PyDictKeysObject *keys)
600{
Victor Stinner742da042016-09-07 17:40:12 -0700601 PyDictKeyEntry *entries = DK_ENTRIES(keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400602 Py_ssize_t i, n;
Victor Stinner742da042016-09-07 17:40:12 -0700603 for (i = 0, n = keys->dk_nentries; i < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400604 Py_XDECREF(entries[i].me_key);
605 Py_XDECREF(entries[i].me_value);
606 }
Victor Stinner522691c2020-06-23 16:40:40 +0200607 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200608#ifdef Py_DEBUG
609 // free_keys_object() must not be called after _PyDict_Fini()
610 assert(state->keys_numfree != -1);
611#endif
612 if (keys->dk_size == PyDict_MINSIZE && state->keys_numfree < PyDict_MAXFREELIST) {
613 state->keys_free_list[state->keys_numfree++] = keys;
Victor Stinner742da042016-09-07 17:40:12 -0700614 return;
615 }
Raymond Hettingerce5179f2016-01-31 08:56:21 -0800616 PyObject_FREE(keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400617}
618
619#define new_values(size) PyMem_NEW(PyObject *, size)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400620#define free_values(values) PyMem_FREE(values)
621
622/* Consumes a reference to the keys object */
623static PyObject *
624new_dict(PyDictKeysObject *keys, PyObject **values)
625{
626 PyDictObject *mp;
Victor Stinnerc9b7f512013-07-08 22:19:20 +0200627 assert(keys != NULL);
Victor Stinner522691c2020-06-23 16:40:40 +0200628 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200629#ifdef Py_DEBUG
630 // new_dict() must not be called after _PyDict_Fini()
631 assert(state->numfree != -1);
632#endif
633 if (state->numfree) {
634 mp = state->free_list[--state->numfree];
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000635 assert (mp != NULL);
Dong-hee Na1b55b652020-02-17 19:09:15 +0900636 assert (Py_IS_TYPE(mp, &PyDict_Type));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000637 _Py_NewReference((PyObject *)mp);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000638 }
Victor Stinnerb4e85ca2020-06-23 11:33:18 +0200639 else {
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400640 mp = PyObject_GC_New(PyDictObject, &PyDict_Type);
641 if (mp == NULL) {
INADA Naokia7576492018-11-14 18:39:27 +0900642 dictkeys_decref(keys);
Zackery Spytz3d07c1e2019-03-23 20:23:29 -0600643 if (values != empty_values) {
644 free_values(values);
645 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400646 return NULL;
647 }
648 }
649 mp->ma_keys = keys;
650 mp->ma_values = values;
651 mp->ma_used = 0;
Victor Stinner3b6a6b42016-09-08 12:51:24 -0700652 mp->ma_version_tag = DICT_NEXT_VERSION();
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200653 ASSERT_CONSISTENT(mp);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000654 return (PyObject *)mp;
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000655}
656
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400657/* Consumes a reference to the keys object */
658static PyObject *
659new_dict_with_shared_keys(PyDictKeysObject *keys)
660{
661 PyObject **values;
662 Py_ssize_t i, size;
663
Victor Stinner742da042016-09-07 17:40:12 -0700664 size = USABLE_FRACTION(DK_SIZE(keys));
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400665 values = new_values(size);
666 if (values == NULL) {
INADA Naokia7576492018-11-14 18:39:27 +0900667 dictkeys_decref(keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400668 return PyErr_NoMemory();
669 }
670 for (i = 0; i < size; i++) {
671 values[i] = NULL;
672 }
673 return new_dict(keys, values);
674}
675
Yury Selivanovb0a7a032018-01-22 11:54:41 -0500676
677static PyObject *
678clone_combined_dict(PyDictObject *orig)
679{
680 assert(PyDict_CheckExact(orig));
681 assert(orig->ma_values == NULL);
682 assert(orig->ma_keys->dk_refcnt == 1);
683
684 Py_ssize_t keys_size = _PyDict_KeysSize(orig->ma_keys);
685 PyDictKeysObject *keys = PyObject_Malloc(keys_size);
686 if (keys == NULL) {
687 PyErr_NoMemory();
688 return NULL;
689 }
690
691 memcpy(keys, orig->ma_keys, keys_size);
692
693 /* After copying key/value pairs, we need to incref all
694 keys and values and they are about to be co-owned by a
695 new dict object. */
696 PyDictKeyEntry *ep0 = DK_ENTRIES(keys);
697 Py_ssize_t n = keys->dk_nentries;
698 for (Py_ssize_t i = 0; i < n; i++) {
699 PyDictKeyEntry *entry = &ep0[i];
700 PyObject *value = entry->me_value;
701 if (value != NULL) {
702 Py_INCREF(value);
703 Py_INCREF(entry->me_key);
704 }
705 }
706
707 PyDictObject *new = (PyDictObject *)new_dict(keys, NULL);
708 if (new == NULL) {
709 /* In case of an error, `new_dict()` takes care of
710 cleaning up `keys`. */
711 return NULL;
712 }
713 new->ma_used = orig->ma_used;
Victor Stinner0fc91ee2019-04-12 21:51:34 +0200714 ASSERT_CONSISTENT(new);
Yury Selivanovb0a7a032018-01-22 11:54:41 -0500715 if (_PyObject_GC_IS_TRACKED(orig)) {
716 /* Maintain tracking. */
717 _PyObject_GC_TRACK(new);
718 }
Yury Selivanov0b752282018-07-06 12:20:07 -0400719
720 /* Since we copied the keys table we now have an extra reference
Victor Stinner49932fe2020-02-03 17:55:05 +0100721 in the system. Manually call increment _Py_RefTotal to signal that
INADA Naokia7576492018-11-14 18:39:27 +0900722 we have it now; calling dictkeys_incref would be an error as
Yury Selivanov0b752282018-07-06 12:20:07 -0400723 keys->dk_refcnt is already set to 1 (after memcpy). */
Victor Stinner49932fe2020-02-03 17:55:05 +0100724#ifdef Py_REF_DEBUG
725 _Py_RefTotal++;
726#endif
Yury Selivanov0b752282018-07-06 12:20:07 -0400727
Yury Selivanovb0a7a032018-01-22 11:54:41 -0500728 return (PyObject *)new;
729}
730
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400731PyObject *
732PyDict_New(void)
733{
Inada Naokif2a18672019-03-12 17:25:44 +0900734 dictkeys_incref(Py_EMPTY_KEYS);
735 return new_dict(Py_EMPTY_KEYS, empty_values);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400736}
737
Victor Stinner742da042016-09-07 17:40:12 -0700738/* Search index of hash table from offset of entry table */
739static Py_ssize_t
740lookdict_index(PyDictKeysObject *k, Py_hash_t hash, Py_ssize_t index)
741{
Victor Stinner742da042016-09-07 17:40:12 -0700742 size_t mask = DK_MASK(k);
INADA Naoki073ae482017-06-23 15:22:50 +0900743 size_t perturb = (size_t)hash;
744 size_t i = (size_t)hash & mask;
Victor Stinner742da042016-09-07 17:40:12 -0700745
INADA Naoki073ae482017-06-23 15:22:50 +0900746 for (;;) {
INADA Naokia7576492018-11-14 18:39:27 +0900747 Py_ssize_t ix = dictkeys_get_index(k, i);
Victor Stinner742da042016-09-07 17:40:12 -0700748 if (ix == index) {
749 return i;
750 }
751 if (ix == DKIX_EMPTY) {
752 return DKIX_EMPTY;
753 }
INADA Naoki073ae482017-06-23 15:22:50 +0900754 perturb >>= PERTURB_SHIFT;
755 i = mask & (i*5 + perturb + 1);
Victor Stinner742da042016-09-07 17:40:12 -0700756 }
Barry Warsawb2e57942017-09-14 18:13:16 -0700757 Py_UNREACHABLE();
Victor Stinner742da042016-09-07 17:40:12 -0700758}
759
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000760/*
761The basic lookup function used by all operations.
Guido van Rossum16e93a81997-01-28 00:00:11 +0000762This is based on Algorithm D from Knuth Vol. 3, Sec. 6.4.
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000763Open addressing is preferred over chaining since the link overhead for
764chaining would be substantial (100% with typical malloc overhead).
765
Tim Peterseb28ef22001-06-02 05:27:19 +0000766The initial probe index is computed as hash mod the table size. Subsequent
767probe indices are computed as explained earlier.
Guido van Rossum2bc13791999-03-24 19:06:42 +0000768
769All arithmetic on hash should ignore overflow.
Guido van Rossum16e93a81997-01-28 00:00:11 +0000770
Guido van Rossumdc5f6b22006-08-24 21:29:26 +0000771The details in this version are due to Tim Peters, building on many past
Tim Peterseb28ef22001-06-02 05:27:19 +0000772contributions by Reimer Behrends, Jyrki Alakuijala, Vladimir Marangozov and
Guido van Rossumdc5f6b22006-08-24 21:29:26 +0000773Christian Tismer.
Fred Drake1bff34a2000-08-31 19:31:38 +0000774
Victor Stinner742da042016-09-07 17:40:12 -0700775lookdict() is general-purpose, and may return DKIX_ERROR if (and only if) a
Victor Stinnera4348cc2016-09-08 12:01:25 -0700776comparison raises an exception.
Guido van Rossum89d8c602007-09-18 17:26:56 +0000777lookdict_unicode() below is specialized to string keys, comparison of which can
INADA Naoki1b8df102017-02-20 22:48:10 +0900778never raise an exception; that function can never return DKIX_ERROR when key
779is string. Otherwise, it falls back to lookdict().
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400780lookdict_unicode_nodummy is further specialized for string keys that cannot be
781the <dummy> value.
INADA Naoki778928b2017-08-03 23:45:15 +0900782For both, when the key isn't found a DKIX_EMPTY is returned.
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000783*/
Victor Stinnerc7a8f672016-11-15 15:13:40 +0100784static Py_ssize_t _Py_HOT_FUNCTION
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400785lookdict(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900786 Py_hash_t hash, PyObject **value_addr)
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000787{
INADA Naoki778928b2017-08-03 23:45:15 +0900788 size_t i, mask, perturb;
Victor Stinner742da042016-09-07 17:40:12 -0700789 PyDictKeysObject *dk;
INADA Naoki778928b2017-08-03 23:45:15 +0900790 PyDictKeyEntry *ep0;
Tim Peterseb28ef22001-06-02 05:27:19 +0000791
Antoine Pitrou9a234902012-05-13 20:48:01 +0200792top:
Victor Stinner742da042016-09-07 17:40:12 -0700793 dk = mp->ma_keys;
Victor Stinner742da042016-09-07 17:40:12 -0700794 ep0 = DK_ENTRIES(dk);
INADA Naoki778928b2017-08-03 23:45:15 +0900795 mask = DK_MASK(dk);
796 perturb = hash;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000797 i = (size_t)hash & mask;
Victor Stinner742da042016-09-07 17:40:12 -0700798
INADA Naoki778928b2017-08-03 23:45:15 +0900799 for (;;) {
INADA Naokia7576492018-11-14 18:39:27 +0900800 Py_ssize_t ix = dictkeys_get_index(dk, i);
Victor Stinner742da042016-09-07 17:40:12 -0700801 if (ix == DKIX_EMPTY) {
Victor Stinner742da042016-09-07 17:40:12 -0700802 *value_addr = NULL;
803 return ix;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400804 }
INADA Naoki778928b2017-08-03 23:45:15 +0900805 if (ix >= 0) {
806 PyDictKeyEntry *ep = &ep0[ix];
807 assert(ep->me_key != NULL);
808 if (ep->me_key == key) {
809 *value_addr = ep->me_value;
810 return ix;
Victor Stinner742da042016-09-07 17:40:12 -0700811 }
INADA Naoki778928b2017-08-03 23:45:15 +0900812 if (ep->me_hash == hash) {
813 PyObject *startkey = ep->me_key;
814 Py_INCREF(startkey);
815 int cmp = PyObject_RichCompareBool(startkey, key, Py_EQ);
816 Py_DECREF(startkey);
817 if (cmp < 0) {
818 *value_addr = NULL;
819 return DKIX_ERROR;
820 }
821 if (dk == mp->ma_keys && ep->me_key == startkey) {
822 if (cmp > 0) {
823 *value_addr = ep->me_value;
824 return ix;
Victor Stinner742da042016-09-07 17:40:12 -0700825 }
INADA Naoki778928b2017-08-03 23:45:15 +0900826 }
827 else {
828 /* The dict was mutated, restart */
829 goto top;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400830 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000831 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000832 }
INADA Naoki778928b2017-08-03 23:45:15 +0900833 perturb >>= PERTURB_SHIFT;
834 i = (i*5 + perturb + 1) & mask;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000835 }
Barry Warsawb2e57942017-09-14 18:13:16 -0700836 Py_UNREACHABLE();
Guido van Rossum4b1302b1993-03-27 18:11:32 +0000837}
838
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400839/* Specialized version for string-only keys */
Victor Stinnerc7a8f672016-11-15 15:13:40 +0100840static Py_ssize_t _Py_HOT_FUNCTION
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400841lookdict_unicode(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900842 Py_hash_t hash, PyObject **value_addr)
Fred Drake1bff34a2000-08-31 19:31:38 +0000843{
Victor Stinner742da042016-09-07 17:40:12 -0700844 assert(mp->ma_values == NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000845 /* Make sure this function doesn't have to handle non-unicode keys,
846 including subclasses of str; e.g., one reason to subclass
847 unicodes is to override __eq__, and for speed we don't cater to
848 that here. */
849 if (!PyUnicode_CheckExact(key)) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400850 mp->ma_keys->dk_lookup = lookdict;
INADA Naoki778928b2017-08-03 23:45:15 +0900851 return lookdict(mp, key, hash, value_addr);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000852 }
Tim Peters15d49292001-05-27 07:39:22 +0000853
INADA Naoki778928b2017-08-03 23:45:15 +0900854 PyDictKeyEntry *ep0 = DK_ENTRIES(mp->ma_keys);
855 size_t mask = DK_MASK(mp->ma_keys);
856 size_t perturb = (size_t)hash;
857 size_t i = (size_t)hash & mask;
858
859 for (;;) {
INADA Naokia7576492018-11-14 18:39:27 +0900860 Py_ssize_t ix = dictkeys_get_index(mp->ma_keys, i);
Victor Stinner742da042016-09-07 17:40:12 -0700861 if (ix == DKIX_EMPTY) {
Victor Stinner742da042016-09-07 17:40:12 -0700862 *value_addr = NULL;
863 return DKIX_EMPTY;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400864 }
INADA Naoki778928b2017-08-03 23:45:15 +0900865 if (ix >= 0) {
866 PyDictKeyEntry *ep = &ep0[ix];
867 assert(ep->me_key != NULL);
868 assert(PyUnicode_CheckExact(ep->me_key));
869 if (ep->me_key == key ||
870 (ep->me_hash == hash && unicode_eq(ep->me_key, key))) {
871 *value_addr = ep->me_value;
872 return ix;
Victor Stinner742da042016-09-07 17:40:12 -0700873 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400874 }
INADA Naoki778928b2017-08-03 23:45:15 +0900875 perturb >>= PERTURB_SHIFT;
876 i = mask & (i*5 + perturb + 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000877 }
Barry Warsawb2e57942017-09-14 18:13:16 -0700878 Py_UNREACHABLE();
Fred Drake1bff34a2000-08-31 19:31:38 +0000879}
880
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400881/* Faster version of lookdict_unicode when it is known that no <dummy> keys
882 * will be present. */
Victor Stinnerc7a8f672016-11-15 15:13:40 +0100883static Py_ssize_t _Py_HOT_FUNCTION
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400884lookdict_unicode_nodummy(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900885 Py_hash_t hash, PyObject **value_addr)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400886{
Victor Stinner742da042016-09-07 17:40:12 -0700887 assert(mp->ma_values == NULL);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400888 /* Make sure this function doesn't have to handle non-unicode keys,
889 including subclasses of str; e.g., one reason to subclass
890 unicodes is to override __eq__, and for speed we don't cater to
891 that here. */
892 if (!PyUnicode_CheckExact(key)) {
893 mp->ma_keys->dk_lookup = lookdict;
INADA Naoki778928b2017-08-03 23:45:15 +0900894 return lookdict(mp, key, hash, value_addr);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400895 }
INADA Naoki778928b2017-08-03 23:45:15 +0900896
897 PyDictKeyEntry *ep0 = DK_ENTRIES(mp->ma_keys);
898 size_t mask = DK_MASK(mp->ma_keys);
899 size_t perturb = (size_t)hash;
900 size_t i = (size_t)hash & mask;
901
902 for (;;) {
INADA Naokia7576492018-11-14 18:39:27 +0900903 Py_ssize_t ix = dictkeys_get_index(mp->ma_keys, i);
Victor Stinner742da042016-09-07 17:40:12 -0700904 assert (ix != DKIX_DUMMY);
905 if (ix == DKIX_EMPTY) {
Victor Stinner742da042016-09-07 17:40:12 -0700906 *value_addr = NULL;
907 return DKIX_EMPTY;
908 }
INADA Naoki778928b2017-08-03 23:45:15 +0900909 PyDictKeyEntry *ep = &ep0[ix];
910 assert(ep->me_key != NULL);
911 assert(PyUnicode_CheckExact(ep->me_key));
Victor Stinner742da042016-09-07 17:40:12 -0700912 if (ep->me_key == key ||
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400913 (ep->me_hash == hash && unicode_eq(ep->me_key, key))) {
INADA Naokiba609772016-12-07 20:41:42 +0900914 *value_addr = ep->me_value;
Victor Stinner742da042016-09-07 17:40:12 -0700915 return ix;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400916 }
INADA Naoki778928b2017-08-03 23:45:15 +0900917 perturb >>= PERTURB_SHIFT;
918 i = mask & (i*5 + perturb + 1);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400919 }
Barry Warsawb2e57942017-09-14 18:13:16 -0700920 Py_UNREACHABLE();
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400921}
922
923/* Version of lookdict for split tables.
924 * All split tables and only split tables use this lookup function.
925 * Split tables only contain unicode keys and no dummy keys,
926 * so algorithm is the same as lookdict_unicode_nodummy.
927 */
Victor Stinnerc7a8f672016-11-15 15:13:40 +0100928static Py_ssize_t _Py_HOT_FUNCTION
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400929lookdict_split(PyDictObject *mp, PyObject *key,
INADA Naoki778928b2017-08-03 23:45:15 +0900930 Py_hash_t hash, PyObject **value_addr)
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400931{
Victor Stinner742da042016-09-07 17:40:12 -0700932 /* mp must split table */
933 assert(mp->ma_values != NULL);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400934 if (!PyUnicode_CheckExact(key)) {
INADA Naoki778928b2017-08-03 23:45:15 +0900935 Py_ssize_t ix = lookdict(mp, key, hash, value_addr);
Victor Stinner742da042016-09-07 17:40:12 -0700936 if (ix >= 0) {
INADA Naokiba609772016-12-07 20:41:42 +0900937 *value_addr = mp->ma_values[ix];
Victor Stinner742da042016-09-07 17:40:12 -0700938 }
939 return ix;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400940 }
Victor Stinner742da042016-09-07 17:40:12 -0700941
INADA Naoki778928b2017-08-03 23:45:15 +0900942 PyDictKeyEntry *ep0 = DK_ENTRIES(mp->ma_keys);
943 size_t mask = DK_MASK(mp->ma_keys);
944 size_t perturb = (size_t)hash;
945 size_t i = (size_t)hash & mask;
946
947 for (;;) {
INADA Naokia7576492018-11-14 18:39:27 +0900948 Py_ssize_t ix = dictkeys_get_index(mp->ma_keys, i);
INADA Naoki778928b2017-08-03 23:45:15 +0900949 assert (ix != DKIX_DUMMY);
Victor Stinner742da042016-09-07 17:40:12 -0700950 if (ix == DKIX_EMPTY) {
Victor Stinner742da042016-09-07 17:40:12 -0700951 *value_addr = NULL;
952 return DKIX_EMPTY;
953 }
INADA Naoki778928b2017-08-03 23:45:15 +0900954 PyDictKeyEntry *ep = &ep0[ix];
955 assert(ep->me_key != NULL);
956 assert(PyUnicode_CheckExact(ep->me_key));
Victor Stinner742da042016-09-07 17:40:12 -0700957 if (ep->me_key == key ||
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400958 (ep->me_hash == hash && unicode_eq(ep->me_key, key))) {
INADA Naokiba609772016-12-07 20:41:42 +0900959 *value_addr = mp->ma_values[ix];
Victor Stinner742da042016-09-07 17:40:12 -0700960 return ix;
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400961 }
INADA Naoki778928b2017-08-03 23:45:15 +0900962 perturb >>= PERTURB_SHIFT;
963 i = mask & (i*5 + perturb + 1);
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400964 }
Barry Warsawb2e57942017-09-14 18:13:16 -0700965 Py_UNREACHABLE();
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400966}
967
Benjamin Petersonfb886362010-04-24 18:21:17 +0000968int
969_PyDict_HasOnlyStringKeys(PyObject *dict)
970{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000971 Py_ssize_t pos = 0;
972 PyObject *key, *value;
Benjamin Petersonf6096542010-11-17 22:33:12 +0000973 assert(PyDict_Check(dict));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000974 /* Shortcut */
Benjamin Peterson7d95e402012-04-23 11:24:50 -0400975 if (((PyDictObject *)dict)->ma_keys->dk_lookup != lookdict)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000976 return 1;
977 while (PyDict_Next(dict, &pos, &key, &value))
978 if (!PyUnicode_Check(key))
979 return 0;
980 return 1;
Benjamin Petersonfb886362010-04-24 18:21:17 +0000981}
982
Antoine Pitrou3a652b12009-03-23 18:52:06 +0000983#define MAINTAIN_TRACKING(mp, key, value) \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000984 do { \
985 if (!_PyObject_GC_IS_TRACKED(mp)) { \
986 if (_PyObject_GC_MAY_BE_TRACKED(key) || \
987 _PyObject_GC_MAY_BE_TRACKED(value)) { \
988 _PyObject_GC_TRACK(mp); \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000989 } \
990 } \
991 } while(0)
Antoine Pitrou3a652b12009-03-23 18:52:06 +0000992
993void
994_PyDict_MaybeUntrack(PyObject *op)
995{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000996 PyDictObject *mp;
997 PyObject *value;
Victor Stinner742da042016-09-07 17:40:12 -0700998 Py_ssize_t i, numentries;
999 PyDictKeyEntry *ep0;
Antoine Pitrou3a652b12009-03-23 18:52:06 +00001000
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001001 if (!PyDict_CheckExact(op) || !_PyObject_GC_IS_TRACKED(op))
1002 return;
1003
1004 mp = (PyDictObject *) op;
Victor Stinner742da042016-09-07 17:40:12 -07001005 ep0 = DK_ENTRIES(mp->ma_keys);
1006 numentries = mp->ma_keys->dk_nentries;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001007 if (_PyDict_HasSplitTable(mp)) {
Victor Stinner742da042016-09-07 17:40:12 -07001008 for (i = 0; i < numentries; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001009 if ((value = mp->ma_values[i]) == NULL)
1010 continue;
1011 if (_PyObject_GC_MAY_BE_TRACKED(value)) {
Victor Stinner742da042016-09-07 17:40:12 -07001012 assert(!_PyObject_GC_MAY_BE_TRACKED(ep0[i].me_key));
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001013 return;
1014 }
1015 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001016 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001017 else {
Victor Stinner742da042016-09-07 17:40:12 -07001018 for (i = 0; i < numentries; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001019 if ((value = ep0[i].me_value) == NULL)
1020 continue;
1021 if (_PyObject_GC_MAY_BE_TRACKED(value) ||
1022 _PyObject_GC_MAY_BE_TRACKED(ep0[i].me_key))
1023 return;
1024 }
1025 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001026 _PyObject_GC_UNTRACK(op);
Antoine Pitrou3a652b12009-03-23 18:52:06 +00001027}
1028
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001029/* Internal function to find slot for an item from its hash
Victor Stinner3c336c52016-09-12 14:17:40 +02001030 when it is known that the key is not present in the dict.
1031
1032 The dict must be combined. */
INADA Naokiba609772016-12-07 20:41:42 +09001033static Py_ssize_t
INADA Naoki778928b2017-08-03 23:45:15 +09001034find_empty_slot(PyDictKeysObject *keys, Py_hash_t hash)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001035{
INADA Naoki778928b2017-08-03 23:45:15 +09001036 assert(keys != NULL);
Tim Peters6d6c1a32001-08-02 04:15:00 +00001037
INADA Naoki778928b2017-08-03 23:45:15 +09001038 const size_t mask = DK_MASK(keys);
1039 size_t i = hash & mask;
INADA Naokia7576492018-11-14 18:39:27 +09001040 Py_ssize_t ix = dictkeys_get_index(keys, i);
INADA Naoki778928b2017-08-03 23:45:15 +09001041 for (size_t perturb = hash; ix >= 0;) {
INADA Naoki267941c2016-10-06 15:19:07 +09001042 perturb >>= PERTURB_SHIFT;
INADA Naoki778928b2017-08-03 23:45:15 +09001043 i = (i*5 + perturb + 1) & mask;
INADA Naokia7576492018-11-14 18:39:27 +09001044 ix = dictkeys_get_index(keys, i);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001045 }
INADA Naoki778928b2017-08-03 23:45:15 +09001046 return i;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001047}
1048
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001049static int
1050insertion_resize(PyDictObject *mp)
1051{
Raymond Hettinger36f74aa2013-05-17 03:01:13 -07001052 return dictresize(mp, GROWTH_RATE(mp));
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001053}
Antoine Pitroue965d972012-02-27 00:45:12 +01001054
1055/*
1056Internal routine to insert a new item into the table.
1057Used both by the internal resize routine and by the public insert routine.
Antoine Pitroue965d972012-02-27 00:45:12 +01001058Returns -1 if an error occurred, or 0 on success.
1059*/
1060static int
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001061insertdict(PyDictObject *mp, PyObject *key, Py_hash_t hash, PyObject *value)
Antoine Pitroue965d972012-02-27 00:45:12 +01001062{
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001063 PyObject *old_value;
INADA Naokiba609772016-12-07 20:41:42 +09001064 PyDictKeyEntry *ep;
Antoine Pitroue965d972012-02-27 00:45:12 +01001065
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001066 Py_INCREF(key);
1067 Py_INCREF(value);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001068 if (mp->ma_values != NULL && !PyUnicode_CheckExact(key)) {
1069 if (insertion_resize(mp) < 0)
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001070 goto Fail;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001071 }
1072
INADA Naoki778928b2017-08-03 23:45:15 +09001073 Py_ssize_t ix = mp->ma_keys->dk_lookup(mp, key, hash, &old_value);
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001074 if (ix == DKIX_ERROR)
1075 goto Fail;
Victor Stinner742da042016-09-07 17:40:12 -07001076
Antoine Pitroud6967322014-10-18 00:35:00 +02001077 assert(PyUnicode_CheckExact(key) || mp->ma_keys->dk_lookup == lookdict);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001078 MAINTAIN_TRACKING(mp, key, value);
Victor Stinner742da042016-09-07 17:40:12 -07001079
1080 /* When insertion order is different from shared key, we can't share
1081 * the key anymore. Convert this instance to combine table.
1082 */
1083 if (_PyDict_HasSplitTable(mp) &&
INADA Naokiba609772016-12-07 20:41:42 +09001084 ((ix >= 0 && old_value == NULL && mp->ma_used != ix) ||
Victor Stinner742da042016-09-07 17:40:12 -07001085 (ix == DKIX_EMPTY && mp->ma_used != mp->ma_keys->dk_nentries))) {
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001086 if (insertion_resize(mp) < 0)
1087 goto Fail;
Victor Stinner742da042016-09-07 17:40:12 -07001088 ix = DKIX_EMPTY;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001089 }
Victor Stinner742da042016-09-07 17:40:12 -07001090
1091 if (ix == DKIX_EMPTY) {
1092 /* Insert into new slot. */
INADA Naokiba609772016-12-07 20:41:42 +09001093 assert(old_value == NULL);
Victor Stinner742da042016-09-07 17:40:12 -07001094 if (mp->ma_keys->dk_usable <= 0) {
1095 /* Need to resize. */
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001096 if (insertion_resize(mp) < 0)
1097 goto Fail;
Victor Stinner742da042016-09-07 17:40:12 -07001098 }
INADA Naoki778928b2017-08-03 23:45:15 +09001099 Py_ssize_t hashpos = find_empty_slot(mp->ma_keys, hash);
INADA Naokiba609772016-12-07 20:41:42 +09001100 ep = &DK_ENTRIES(mp->ma_keys)[mp->ma_keys->dk_nentries];
INADA Naokia7576492018-11-14 18:39:27 +09001101 dictkeys_set_index(mp->ma_keys, hashpos, mp->ma_keys->dk_nentries);
Victor Stinner742da042016-09-07 17:40:12 -07001102 ep->me_key = key;
1103 ep->me_hash = hash;
1104 if (mp->ma_values) {
1105 assert (mp->ma_values[mp->ma_keys->dk_nentries] == NULL);
1106 mp->ma_values[mp->ma_keys->dk_nentries] = value;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001107 }
1108 else {
Victor Stinner742da042016-09-07 17:40:12 -07001109 ep->me_value = value;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001110 }
1111 mp->ma_used++;
Victor Stinner3b6a6b42016-09-08 12:51:24 -07001112 mp->ma_version_tag = DICT_NEXT_VERSION();
Victor Stinner742da042016-09-07 17:40:12 -07001113 mp->ma_keys->dk_usable--;
1114 mp->ma_keys->dk_nentries++;
1115 assert(mp->ma_keys->dk_usable >= 0);
Victor Stinner0fc91ee2019-04-12 21:51:34 +02001116 ASSERT_CONSISTENT(mp);
Victor Stinner742da042016-09-07 17:40:12 -07001117 return 0;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001118 }
Victor Stinner742da042016-09-07 17:40:12 -07001119
Inada Naoki91234a12019-06-03 21:30:58 +09001120 if (old_value != value) {
1121 if (_PyDict_HasSplitTable(mp)) {
1122 mp->ma_values[ix] = value;
1123 if (old_value == NULL) {
1124 /* pending state */
1125 assert(ix == mp->ma_used);
1126 mp->ma_used++;
1127 }
INADA Naokiba609772016-12-07 20:41:42 +09001128 }
Inada Naoki91234a12019-06-03 21:30:58 +09001129 else {
1130 assert(old_value != NULL);
1131 DK_ENTRIES(mp->ma_keys)[ix].me_value = value;
1132 }
1133 mp->ma_version_tag = DICT_NEXT_VERSION();
INADA Naokiba609772016-12-07 20:41:42 +09001134 }
INADA Naokiba609772016-12-07 20:41:42 +09001135 Py_XDECREF(old_value); /* which **CAN** re-enter (see issue #22653) */
Victor Stinner0fc91ee2019-04-12 21:51:34 +02001136 ASSERT_CONSISTENT(mp);
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001137 Py_DECREF(key);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001138 return 0;
Serhiy Storchaka753bca32017-05-20 12:30:02 +03001139
1140Fail:
1141 Py_DECREF(value);
1142 Py_DECREF(key);
1143 return -1;
Antoine Pitroue965d972012-02-27 00:45:12 +01001144}
1145
Inada Naoki2ddc7f62019-03-18 20:38:33 +09001146// Same to insertdict but specialized for ma_keys = Py_EMPTY_KEYS.
1147static int
1148insert_to_emptydict(PyDictObject *mp, PyObject *key, Py_hash_t hash,
1149 PyObject *value)
1150{
1151 assert(mp->ma_keys == Py_EMPTY_KEYS);
1152
1153 PyDictKeysObject *newkeys = new_keys_object(PyDict_MINSIZE);
1154 if (newkeys == NULL) {
1155 return -1;
1156 }
1157 if (!PyUnicode_CheckExact(key)) {
1158 newkeys->dk_lookup = lookdict;
1159 }
1160 dictkeys_decref(Py_EMPTY_KEYS);
1161 mp->ma_keys = newkeys;
1162 mp->ma_values = NULL;
1163
1164 Py_INCREF(key);
1165 Py_INCREF(value);
1166 MAINTAIN_TRACKING(mp, key, value);
1167
1168 size_t hashpos = (size_t)hash & (PyDict_MINSIZE-1);
Dong-hee Nac39d1dd2019-10-11 17:43:11 +09001169 PyDictKeyEntry *ep = DK_ENTRIES(mp->ma_keys);
Inada Naoki2ddc7f62019-03-18 20:38:33 +09001170 dictkeys_set_index(mp->ma_keys, hashpos, 0);
1171 ep->me_key = key;
1172 ep->me_hash = hash;
1173 ep->me_value = value;
1174 mp->ma_used++;
1175 mp->ma_version_tag = DICT_NEXT_VERSION();
1176 mp->ma_keys->dk_usable--;
1177 mp->ma_keys->dk_nentries++;
1178 return 0;
1179}
1180
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001181/*
luzpaza5293b42017-11-05 07:37:50 -06001182Internal routine used by dictresize() to build a hashtable of entries.
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001183*/
1184static void
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001185build_indices(PyDictKeysObject *keys, PyDictKeyEntry *ep, Py_ssize_t n)
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001186{
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001187 size_t mask = (size_t)DK_SIZE(keys) - 1;
1188 for (Py_ssize_t ix = 0; ix != n; ix++, ep++) {
1189 Py_hash_t hash = ep->me_hash;
1190 size_t i = hash & mask;
INADA Naokia7576492018-11-14 18:39:27 +09001191 for (size_t perturb = hash; dictkeys_get_index(keys, i) != DKIX_EMPTY;) {
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001192 perturb >>= PERTURB_SHIFT;
INADA Naoki870c2862017-06-24 09:03:19 +09001193 i = mask & (i*5 + perturb + 1);
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001194 }
INADA Naokia7576492018-11-14 18:39:27 +09001195 dictkeys_set_index(keys, i, ix);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001196 }
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001197}
1198
1199/*
1200Restructure the table by allocating a new table and reinserting all
1201items again. When entries have been deleted, the new table may
1202actually be smaller than the old one.
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001203If a table is split (its keys and hashes are shared, its values are not),
1204then the values are temporarily copied into the table, it is resized as
1205a combined table, then the me_value slots in the old table are NULLed out.
1206After resizing a table is always combined,
1207but can be resplit by make_keys_shared().
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001208*/
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001209static int
Victor Stinner3d3f2642016-12-15 17:21:23 +01001210dictresize(PyDictObject *mp, Py_ssize_t minsize)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001211{
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001212 Py_ssize_t newsize, numentries;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001213 PyDictKeysObject *oldkeys;
1214 PyObject **oldvalues;
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001215 PyDictKeyEntry *oldentries, *newentries;
Tim Peters91a364d2001-05-19 07:04:38 +00001216
Victor Stinner742da042016-09-07 17:40:12 -07001217 /* Find the smallest table size > minused. */
1218 for (newsize = PyDict_MINSIZE;
Victor Stinner3d3f2642016-12-15 17:21:23 +01001219 newsize < minsize && newsize > 0;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001220 newsize <<= 1)
1221 ;
1222 if (newsize <= 0) {
1223 PyErr_NoMemory();
1224 return -1;
1225 }
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001226
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001227 oldkeys = mp->ma_keys;
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001228
1229 /* NOTE: Current odict checks mp->ma_keys to detect resize happen.
1230 * So we can't reuse oldkeys even if oldkeys->dk_size == newsize.
1231 * TODO: Try reusing oldkeys when reimplement odict.
1232 */
1233
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001234 /* Allocate a new table. */
1235 mp->ma_keys = new_keys_object(newsize);
1236 if (mp->ma_keys == NULL) {
1237 mp->ma_keys = oldkeys;
1238 return -1;
1239 }
Victor Stinner3d3f2642016-12-15 17:21:23 +01001240 // New table must be large enough.
1241 assert(mp->ma_keys->dk_usable >= mp->ma_used);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001242 if (oldkeys->dk_lookup == lookdict)
1243 mp->ma_keys->dk_lookup = lookdict;
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001244
1245 numentries = mp->ma_used;
1246 oldentries = DK_ENTRIES(oldkeys);
1247 newentries = DK_ENTRIES(mp->ma_keys);
1248 oldvalues = mp->ma_values;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001249 if (oldvalues != NULL) {
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001250 /* Convert split table into new combined table.
1251 * We must incref keys; we can transfer values.
1252 * Note that values of split table is always dense.
1253 */
1254 for (Py_ssize_t i = 0; i < numentries; i++) {
1255 assert(oldvalues[i] != NULL);
1256 PyDictKeyEntry *ep = &oldentries[i];
1257 PyObject *key = ep->me_key;
1258 Py_INCREF(key);
1259 newentries[i].me_key = key;
1260 newentries[i].me_hash = ep->me_hash;
1261 newentries[i].me_value = oldvalues[i];
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001262 }
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001263
INADA Naokia7576492018-11-14 18:39:27 +09001264 dictkeys_decref(oldkeys);
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001265 mp->ma_values = NULL;
Victor Stinner742da042016-09-07 17:40:12 -07001266 if (oldvalues != empty_values) {
1267 free_values(oldvalues);
1268 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001269 }
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001270 else { // combined table.
1271 if (oldkeys->dk_nentries == numentries) {
1272 memcpy(newentries, oldentries, numentries * sizeof(PyDictKeyEntry));
1273 }
1274 else {
1275 PyDictKeyEntry *ep = oldentries;
1276 for (Py_ssize_t i = 0; i < numentries; i++) {
1277 while (ep->me_value == NULL)
1278 ep++;
1279 newentries[i] = *ep++;
1280 }
1281 }
1282
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001283 assert(oldkeys->dk_lookup != lookdict_split);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001284 assert(oldkeys->dk_refcnt == 1);
Victor Stinner49932fe2020-02-03 17:55:05 +01001285#ifdef Py_REF_DEBUG
1286 _Py_RefTotal--;
1287#endif
Victor Stinner522691c2020-06-23 16:40:40 +02001288 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +02001289#ifdef Py_DEBUG
1290 // dictresize() must not be called after _PyDict_Fini()
1291 assert(state->keys_numfree != -1);
Victor Stinnerb4b53862020-05-05 19:55:29 +02001292#endif
Victor Stinnerb4e85ca2020-06-23 11:33:18 +02001293 if (oldkeys->dk_size == PyDict_MINSIZE &&
1294 state->keys_numfree < PyDict_MAXFREELIST)
Victor Stinnerb4b53862020-05-05 19:55:29 +02001295 {
Victor Stinnerb4e85ca2020-06-23 11:33:18 +02001296 state->keys_free_list[state->keys_numfree++] = oldkeys;
1297 }
1298 else {
INADA Naokia7576492018-11-14 18:39:27 +09001299 PyObject_FREE(oldkeys);
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001300 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001301 }
Serhiy Storchakae26e20d2016-10-29 10:50:00 +03001302
1303 build_indices(mp->ma_keys, newentries, numentries);
1304 mp->ma_keys->dk_usable -= numentries;
1305 mp->ma_keys->dk_nentries = numentries;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001306 return 0;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001307}
1308
Benjamin Peterson15ee8212012-04-24 14:44:18 -04001309/* Returns NULL if unable to split table.
1310 * A NULL return does not necessarily indicate an error */
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001311static PyDictKeysObject *
1312make_keys_shared(PyObject *op)
1313{
1314 Py_ssize_t i;
1315 Py_ssize_t size;
1316 PyDictObject *mp = (PyDictObject *)op;
1317
Benjamin Peterson15ee8212012-04-24 14:44:18 -04001318 if (!PyDict_CheckExact(op))
1319 return NULL;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001320 if (!_PyDict_HasSplitTable(mp)) {
1321 PyDictKeyEntry *ep0;
1322 PyObject **values;
1323 assert(mp->ma_keys->dk_refcnt == 1);
1324 if (mp->ma_keys->dk_lookup == lookdict) {
1325 return NULL;
1326 }
1327 else if (mp->ma_keys->dk_lookup == lookdict_unicode) {
1328 /* Remove dummy keys */
1329 if (dictresize(mp, DK_SIZE(mp->ma_keys)))
1330 return NULL;
1331 }
1332 assert(mp->ma_keys->dk_lookup == lookdict_unicode_nodummy);
1333 /* Copy values into a new array */
Victor Stinner742da042016-09-07 17:40:12 -07001334 ep0 = DK_ENTRIES(mp->ma_keys);
1335 size = USABLE_FRACTION(DK_SIZE(mp->ma_keys));
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001336 values = new_values(size);
1337 if (values == NULL) {
1338 PyErr_SetString(PyExc_MemoryError,
1339 "Not enough memory to allocate new values array");
1340 return NULL;
1341 }
1342 for (i = 0; i < size; i++) {
1343 values[i] = ep0[i].me_value;
1344 ep0[i].me_value = NULL;
1345 }
1346 mp->ma_keys->dk_lookup = lookdict_split;
1347 mp->ma_values = values;
1348 }
INADA Naokia7576492018-11-14 18:39:27 +09001349 dictkeys_incref(mp->ma_keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001350 return mp->ma_keys;
1351}
Christian Heimes99170a52007-12-19 02:07:34 +00001352
1353PyObject *
1354_PyDict_NewPresized(Py_ssize_t minused)
1355{
INADA Naoki92c50ee2016-11-22 00:57:02 +09001356 const Py_ssize_t max_presize = 128 * 1024;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001357 Py_ssize_t newsize;
1358 PyDictKeysObject *new_keys;
INADA Naoki92c50ee2016-11-22 00:57:02 +09001359
Inada Naoki2ddc7f62019-03-18 20:38:33 +09001360 if (minused <= USABLE_FRACTION(PyDict_MINSIZE)) {
Inada Naokif2a18672019-03-12 17:25:44 +09001361 return PyDict_New();
1362 }
INADA Naoki92c50ee2016-11-22 00:57:02 +09001363 /* There are no strict guarantee that returned dict can contain minused
1364 * items without resize. So we create medium size dict instead of very
1365 * large dict or MemoryError.
1366 */
1367 if (minused > USABLE_FRACTION(max_presize)) {
1368 newsize = max_presize;
1369 }
1370 else {
1371 Py_ssize_t minsize = ESTIMATE_SIZE(minused);
Inada Naoki2ddc7f62019-03-18 20:38:33 +09001372 newsize = PyDict_MINSIZE*2;
INADA Naoki92c50ee2016-11-22 00:57:02 +09001373 while (newsize < minsize) {
1374 newsize <<= 1;
1375 }
1376 }
1377 assert(IS_POWER_OF_2(newsize));
1378
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001379 new_keys = new_keys_object(newsize);
1380 if (new_keys == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001381 return NULL;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001382 return new_dict(new_keys, NULL);
Christian Heimes99170a52007-12-19 02:07:34 +00001383}
1384
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001385/* Note that, for historical reasons, PyDict_GetItem() suppresses all errors
1386 * that may occur (originally dicts supported only string keys, and exceptions
1387 * weren't possible). So, while the original intent was that a NULL return
Thomas Wouters0e3f5912006-08-11 14:57:12 +00001388 * meant the key wasn't present, in reality it can mean that, or that an error
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001389 * (suppressed) occurred while computing the key's hash, or that some error
1390 * (suppressed) occurred when comparing keys in the dict's internal probe
1391 * sequence. A nasty example of the latter is when a Python-coded comparison
1392 * function hits a stack-depth error, which can cause this to return NULL
1393 * even if the key is present.
1394 */
Guido van Rossumc0b618a1997-05-02 03:12:38 +00001395PyObject *
Tim Peters1f5871e2000-07-04 17:44:48 +00001396PyDict_GetItem(PyObject *op, PyObject *key)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001397{
Victor Stinner59d3dce2020-06-02 14:03:25 +02001398 if (!PyDict_Check(op)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001399 return NULL;
Victor Stinner59d3dce2020-06-02 14:03:25 +02001400 }
1401 PyDictObject *mp = (PyDictObject *)op;
1402
1403 Py_hash_t hash;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001404 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001405 (hash = ((PyASCIIObject *) key)->hash) == -1)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001406 {
1407 hash = PyObject_Hash(key);
1408 if (hash == -1) {
1409 PyErr_Clear();
1410 return NULL;
1411 }
1412 }
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001413
Victor Stinner59d3dce2020-06-02 14:03:25 +02001414 PyThreadState *tstate = _PyThreadState_GET();
1415#ifdef Py_DEBUG
1416 // bpo-40839: Before Python 3.10, it was possible to call PyDict_GetItem()
1417 // with the GIL released.
1418 _Py_EnsureTstateNotNULL(tstate);
1419#endif
1420
1421 /* Preserve the existing exception */
1422 PyObject *exc_type, *exc_value, *exc_tb;
1423 PyObject *value;
1424 Py_ssize_t ix;
1425
1426 _PyErr_Fetch(tstate, &exc_type, &exc_value, &exc_tb);
1427 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
1428
1429 /* Ignore any exception raised by the lookup */
1430 _PyErr_Restore(tstate, exc_type, exc_value, exc_tb);
1431
1432 if (ix < 0) {
1433 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001434 }
INADA Naokiba609772016-12-07 20:41:42 +09001435 return value;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001436}
1437
Serhiy Storchakaf0b311b2016-11-06 13:18:24 +02001438/* Same as PyDict_GetItemWithError() but with hash supplied by caller.
1439 This returns NULL *with* an exception set if an exception occurred.
1440 It returns NULL *without* an exception set if the key wasn't present.
1441*/
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001442PyObject *
1443_PyDict_GetItem_KnownHash(PyObject *op, PyObject *key, Py_hash_t hash)
1444{
Victor Stinner742da042016-09-07 17:40:12 -07001445 Py_ssize_t ix;
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001446 PyDictObject *mp = (PyDictObject *)op;
INADA Naokiba609772016-12-07 20:41:42 +09001447 PyObject *value;
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001448
Serhiy Storchakaf0b311b2016-11-06 13:18:24 +02001449 if (!PyDict_Check(op)) {
1450 PyErr_BadInternalCall();
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001451 return NULL;
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001452 }
Serhiy Storchakaf0b311b2016-11-06 13:18:24 +02001453
INADA Naoki778928b2017-08-03 23:45:15 +09001454 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Serhiy Storchakaf0b311b2016-11-06 13:18:24 +02001455 if (ix < 0) {
1456 return NULL;
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001457 }
INADA Naokiba609772016-12-07 20:41:42 +09001458 return value;
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001459}
1460
Guido van Rossum47b9ff62006-08-24 00:41:19 +00001461/* Variant of PyDict_GetItem() that doesn't suppress exceptions.
1462 This returns NULL *with* an exception set if an exception occurred.
1463 It returns NULL *without* an exception set if the key wasn't present.
1464*/
1465PyObject *
1466PyDict_GetItemWithError(PyObject *op, PyObject *key)
1467{
Victor Stinner742da042016-09-07 17:40:12 -07001468 Py_ssize_t ix;
Benjamin Peterson8f67d082010-10-17 20:54:53 +00001469 Py_hash_t hash;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001470 PyDictObject*mp = (PyDictObject *)op;
INADA Naokiba609772016-12-07 20:41:42 +09001471 PyObject *value;
Guido van Rossum47b9ff62006-08-24 00:41:19 +00001472
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001473 if (!PyDict_Check(op)) {
1474 PyErr_BadInternalCall();
1475 return NULL;
1476 }
1477 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001478 (hash = ((PyASCIIObject *) key)->hash) == -1)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001479 {
1480 hash = PyObject_Hash(key);
1481 if (hash == -1) {
1482 return NULL;
1483 }
1484 }
Guido van Rossum47b9ff62006-08-24 00:41:19 +00001485
INADA Naoki778928b2017-08-03 23:45:15 +09001486 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07001487 if (ix < 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001488 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09001489 return value;
Guido van Rossum47b9ff62006-08-24 00:41:19 +00001490}
1491
Brett Cannonfd074152012-04-14 14:10:13 -04001492PyObject *
1493_PyDict_GetItemIdWithError(PyObject *dp, struct _Py_Identifier *key)
1494{
1495 PyObject *kv;
1496 kv = _PyUnicode_FromId(key); /* borrowed */
1497 if (kv == NULL)
1498 return NULL;
scoder6067d4b2020-05-11 06:04:31 +02001499 Py_hash_t hash = ((PyASCIIObject *) kv)->hash;
1500 assert (hash != -1); /* interned strings have their hash value initialised */
1501 return _PyDict_GetItem_KnownHash(dp, kv, hash);
Brett Cannonfd074152012-04-14 14:10:13 -04001502}
1503
Serhiy Storchakaa24107b2019-02-25 17:59:46 +02001504PyObject *
1505_PyDict_GetItemStringWithError(PyObject *v, const char *key)
1506{
1507 PyObject *kv, *rv;
1508 kv = PyUnicode_FromString(key);
1509 if (kv == NULL) {
1510 return NULL;
1511 }
1512 rv = PyDict_GetItemWithError(v, kv);
1513 Py_DECREF(kv);
1514 return rv;
1515}
1516
Victor Stinnerb4efc962015-11-20 09:24:02 +01001517/* Fast version of global value lookup (LOAD_GLOBAL).
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001518 * Lookup in globals, then builtins.
Victor Stinnerb4efc962015-11-20 09:24:02 +01001519 *
1520 * Raise an exception and return NULL if an error occurred (ex: computing the
1521 * key hash failed, key comparison failed, ...). Return NULL if the key doesn't
1522 * exist. Return the value if the key exists.
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001523 */
1524PyObject *
1525_PyDict_LoadGlobal(PyDictObject *globals, PyDictObject *builtins, PyObject *key)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001526{
Victor Stinner742da042016-09-07 17:40:12 -07001527 Py_ssize_t ix;
Victor Stinnerb4efc962015-11-20 09:24:02 +01001528 Py_hash_t hash;
INADA Naokiba609772016-12-07 20:41:42 +09001529 PyObject *value;
Victor Stinnerb4efc962015-11-20 09:24:02 +01001530
1531 if (!PyUnicode_CheckExact(key) ||
1532 (hash = ((PyASCIIObject *) key)->hash) == -1)
1533 {
1534 hash = PyObject_Hash(key);
1535 if (hash == -1)
1536 return NULL;
Antoine Pitroue965d972012-02-27 00:45:12 +01001537 }
Victor Stinnerb4efc962015-11-20 09:24:02 +01001538
1539 /* namespace 1: globals */
INADA Naoki778928b2017-08-03 23:45:15 +09001540 ix = globals->ma_keys->dk_lookup(globals, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07001541 if (ix == DKIX_ERROR)
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001542 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09001543 if (ix != DKIX_EMPTY && value != NULL)
1544 return value;
Victor Stinnerb4efc962015-11-20 09:24:02 +01001545
1546 /* namespace 2: builtins */
INADA Naoki778928b2017-08-03 23:45:15 +09001547 ix = builtins->ma_keys->dk_lookup(builtins, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07001548 if (ix < 0)
Victor Stinnerb4efc962015-11-20 09:24:02 +01001549 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09001550 return value;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001551}
1552
Antoine Pitroue965d972012-02-27 00:45:12 +01001553/* CAUTION: PyDict_SetItem() must guarantee that it won't resize the
1554 * dictionary if it's merely replacing the value for an existing key.
1555 * This means that it's safe to loop over a dictionary with PyDict_Next()
1556 * and occasionally replace a value -- but you can't insert new keys or
1557 * remove them.
1558 */
1559int
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001560PyDict_SetItem(PyObject *op, PyObject *key, PyObject *value)
Antoine Pitroue965d972012-02-27 00:45:12 +01001561{
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001562 PyDictObject *mp;
1563 Py_hash_t hash;
Antoine Pitroue965d972012-02-27 00:45:12 +01001564 if (!PyDict_Check(op)) {
1565 PyErr_BadInternalCall();
1566 return -1;
1567 }
1568 assert(key);
1569 assert(value);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001570 mp = (PyDictObject *)op;
1571 if (!PyUnicode_CheckExact(key) ||
1572 (hash = ((PyASCIIObject *) key)->hash) == -1)
1573 {
Antoine Pitroue965d972012-02-27 00:45:12 +01001574 hash = PyObject_Hash(key);
1575 if (hash == -1)
1576 return -1;
1577 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001578
Inada Naoki2ddc7f62019-03-18 20:38:33 +09001579 if (mp->ma_keys == Py_EMPTY_KEYS) {
1580 return insert_to_emptydict(mp, key, hash, value);
1581 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001582 /* insertdict() handles any resizing that might be necessary */
1583 return insertdict(mp, key, hash, value);
Antoine Pitroue965d972012-02-27 00:45:12 +01001584}
1585
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001586int
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001587_PyDict_SetItem_KnownHash(PyObject *op, PyObject *key, PyObject *value,
1588 Py_hash_t hash)
1589{
1590 PyDictObject *mp;
1591
1592 if (!PyDict_Check(op)) {
1593 PyErr_BadInternalCall();
1594 return -1;
1595 }
1596 assert(key);
1597 assert(value);
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001598 assert(hash != -1);
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001599 mp = (PyDictObject *)op;
1600
Inada Naoki2ddc7f62019-03-18 20:38:33 +09001601 if (mp->ma_keys == Py_EMPTY_KEYS) {
1602 return insert_to_emptydict(mp, key, hash, value);
1603 }
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001604 /* insertdict() handles any resizing that might be necessary */
1605 return insertdict(mp, key, hash, value);
1606}
1607
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001608static int
INADA Naoki778928b2017-08-03 23:45:15 +09001609delitem_common(PyDictObject *mp, Py_hash_t hash, Py_ssize_t ix,
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001610 PyObject *old_value)
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001611{
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001612 PyObject *old_key;
Antoine Pitroud741ed42016-12-27 14:23:43 +01001613 PyDictKeyEntry *ep;
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001614
INADA Naoki778928b2017-08-03 23:45:15 +09001615 Py_ssize_t hashpos = lookdict_index(mp->ma_keys, hash, ix);
1616 assert(hashpos >= 0);
1617
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001618 mp->ma_used--;
Antoine Pitroud741ed42016-12-27 14:23:43 +01001619 mp->ma_version_tag = DICT_NEXT_VERSION();
1620 ep = &DK_ENTRIES(mp->ma_keys)[ix];
INADA Naokia7576492018-11-14 18:39:27 +09001621 dictkeys_set_index(mp->ma_keys, hashpos, DKIX_DUMMY);
Antoine Pitroud741ed42016-12-27 14:23:43 +01001622 ENSURE_ALLOWS_DELETIONS(mp);
1623 old_key = ep->me_key;
1624 ep->me_key = NULL;
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001625 ep->me_value = NULL;
Antoine Pitroud741ed42016-12-27 14:23:43 +01001626 Py_DECREF(old_key);
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001627 Py_DECREF(old_value);
Antoine Pitroud741ed42016-12-27 14:23:43 +01001628
Victor Stinner0fc91ee2019-04-12 21:51:34 +02001629 ASSERT_CONSISTENT(mp);
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001630 return 0;
1631}
1632
Raymond Hettinger4b74fba2014-05-03 16:32:11 -07001633int
Tim Peters1f5871e2000-07-04 17:44:48 +00001634PyDict_DelItem(PyObject *op, PyObject *key)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001635{
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001636 Py_hash_t hash;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001637 assert(key);
1638 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001639 (hash = ((PyASCIIObject *) key)->hash) == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001640 hash = PyObject_Hash(key);
1641 if (hash == -1)
1642 return -1;
1643 }
Victor Stinner742da042016-09-07 17:40:12 -07001644
1645 return _PyDict_DelItem_KnownHash(op, key, hash);
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001646}
1647
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001648int
1649_PyDict_DelItem_KnownHash(PyObject *op, PyObject *key, Py_hash_t hash)
1650{
INADA Naoki778928b2017-08-03 23:45:15 +09001651 Py_ssize_t ix;
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001652 PyDictObject *mp;
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001653 PyObject *old_value;
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001654
1655 if (!PyDict_Check(op)) {
1656 PyErr_BadInternalCall();
1657 return -1;
1658 }
1659 assert(key);
1660 assert(hash != -1);
1661 mp = (PyDictObject *)op;
INADA Naoki778928b2017-08-03 23:45:15 +09001662 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &old_value);
Victor Stinner742da042016-09-07 17:40:12 -07001663 if (ix == DKIX_ERROR)
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001664 return -1;
INADA Naokiba609772016-12-07 20:41:42 +09001665 if (ix == DKIX_EMPTY || old_value == NULL) {
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001666 _PyErr_SetKeyError(key);
1667 return -1;
1668 }
Victor Stinner78601a32016-09-09 19:28:36 -07001669
1670 // Split table doesn't allow deletion. Combine it.
1671 if (_PyDict_HasSplitTable(mp)) {
1672 if (dictresize(mp, DK_SIZE(mp->ma_keys))) {
1673 return -1;
1674 }
INADA Naoki778928b2017-08-03 23:45:15 +09001675 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &old_value);
Victor Stinner78601a32016-09-09 19:28:36 -07001676 assert(ix >= 0);
1677 }
1678
INADA Naoki778928b2017-08-03 23:45:15 +09001679 return delitem_common(mp, hash, ix, old_value);
Serhiy Storchakab9d98d52015-10-02 12:47:11 +03001680}
1681
Antoine Pitroud741ed42016-12-27 14:23:43 +01001682/* This function promises that the predicate -> deletion sequence is atomic
1683 * (i.e. protected by the GIL), assuming the predicate itself doesn't
1684 * release the GIL.
1685 */
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001686int
1687_PyDict_DelItemIf(PyObject *op, PyObject *key,
1688 int (*predicate)(PyObject *value))
1689{
Antoine Pitroud741ed42016-12-27 14:23:43 +01001690 Py_ssize_t hashpos, ix;
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001691 PyDictObject *mp;
1692 Py_hash_t hash;
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001693 PyObject *old_value;
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001694 int res;
1695
1696 if (!PyDict_Check(op)) {
1697 PyErr_BadInternalCall();
1698 return -1;
1699 }
1700 assert(key);
1701 hash = PyObject_Hash(key);
1702 if (hash == -1)
1703 return -1;
1704 mp = (PyDictObject *)op;
INADA Naoki778928b2017-08-03 23:45:15 +09001705 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &old_value);
Antoine Pitroud741ed42016-12-27 14:23:43 +01001706 if (ix == DKIX_ERROR)
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001707 return -1;
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001708 if (ix == DKIX_EMPTY || old_value == NULL) {
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001709 _PyErr_SetKeyError(key);
1710 return -1;
1711 }
Antoine Pitroud741ed42016-12-27 14:23:43 +01001712
1713 // Split table doesn't allow deletion. Combine it.
1714 if (_PyDict_HasSplitTable(mp)) {
1715 if (dictresize(mp, DK_SIZE(mp->ma_keys))) {
1716 return -1;
1717 }
INADA Naoki778928b2017-08-03 23:45:15 +09001718 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &old_value);
Antoine Pitroud741ed42016-12-27 14:23:43 +01001719 assert(ix >= 0);
1720 }
1721
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001722 res = predicate(old_value);
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001723 if (res == -1)
1724 return -1;
INADA Naoki778928b2017-08-03 23:45:15 +09001725
1726 hashpos = lookdict_index(mp->ma_keys, hash, ix);
1727 assert(hashpos >= 0);
1728
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001729 if (res > 0)
Antoine Pitrouc06ae202016-12-27 14:34:54 +01001730 return delitem_common(mp, hashpos, ix, old_value);
Antoine Pitroue10ca3a2016-12-27 14:19:20 +01001731 else
1732 return 0;
1733}
1734
1735
Guido van Rossum25831651993-05-19 14:50:45 +00001736void
Tim Peters1f5871e2000-07-04 17:44:48 +00001737PyDict_Clear(PyObject *op)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001738{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001739 PyDictObject *mp;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001740 PyDictKeysObject *oldkeys;
1741 PyObject **oldvalues;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001742 Py_ssize_t i, n;
Tim Petersdea48ec2001-05-22 20:40:22 +00001743
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001744 if (!PyDict_Check(op))
1745 return;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001746 mp = ((PyDictObject *)op);
1747 oldkeys = mp->ma_keys;
1748 oldvalues = mp->ma_values;
1749 if (oldvalues == empty_values)
1750 return;
1751 /* Empty the dict... */
INADA Naokia7576492018-11-14 18:39:27 +09001752 dictkeys_incref(Py_EMPTY_KEYS);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001753 mp->ma_keys = Py_EMPTY_KEYS;
1754 mp->ma_values = empty_values;
1755 mp->ma_used = 0;
Victor Stinner3b6a6b42016-09-08 12:51:24 -07001756 mp->ma_version_tag = DICT_NEXT_VERSION();
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001757 /* ...then clear the keys and values */
1758 if (oldvalues != NULL) {
Victor Stinner742da042016-09-07 17:40:12 -07001759 n = oldkeys->dk_nentries;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001760 for (i = 0; i < n; i++)
1761 Py_CLEAR(oldvalues[i]);
1762 free_values(oldvalues);
INADA Naokia7576492018-11-14 18:39:27 +09001763 dictkeys_decref(oldkeys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001764 }
1765 else {
1766 assert(oldkeys->dk_refcnt == 1);
INADA Naokia7576492018-11-14 18:39:27 +09001767 dictkeys_decref(oldkeys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001768 }
Victor Stinner0fc91ee2019-04-12 21:51:34 +02001769 ASSERT_CONSISTENT(mp);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001770}
1771
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001772/* Internal version of PyDict_Next that returns a hash value in addition
1773 * to the key and value.
1774 * Return 1 on success, return 0 when the reached the end of the dictionary
1775 * (or if op is not a dictionary)
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001776 */
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001777int
1778_PyDict_Next(PyObject *op, Py_ssize_t *ppos, PyObject **pkey,
1779 PyObject **pvalue, Py_hash_t *phash)
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001780{
INADA Naokica2d8be2016-11-04 16:59:10 +09001781 Py_ssize_t i;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001782 PyDictObject *mp;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001783 PyDictKeyEntry *entry_ptr;
1784 PyObject *value;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001785
1786 if (!PyDict_Check(op))
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001787 return 0;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001788 mp = (PyDictObject *)op;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001789 i = *ppos;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001790 if (mp->ma_values) {
INADA Naokica2d8be2016-11-04 16:59:10 +09001791 if (i < 0 || i >= mp->ma_used)
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001792 return 0;
INADA Naokica2d8be2016-11-04 16:59:10 +09001793 /* values of split table is always dense */
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001794 entry_ptr = &DK_ENTRIES(mp->ma_keys)[i];
INADA Naokica2d8be2016-11-04 16:59:10 +09001795 value = mp->ma_values[i];
1796 assert(value != NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001797 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001798 else {
INADA Naokica2d8be2016-11-04 16:59:10 +09001799 Py_ssize_t n = mp->ma_keys->dk_nentries;
1800 if (i < 0 || i >= n)
1801 return 0;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001802 entry_ptr = &DK_ENTRIES(mp->ma_keys)[i];
1803 while (i < n && entry_ptr->me_value == NULL) {
1804 entry_ptr++;
1805 i++;
Victor Stinner742da042016-09-07 17:40:12 -07001806 }
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001807 if (i >= n)
1808 return 0;
1809 value = entry_ptr->me_value;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001810 }
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001811 *ppos = i+1;
1812 if (pkey)
1813 *pkey = entry_ptr->me_key;
1814 if (phash)
1815 *phash = entry_ptr->me_hash;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04001816 if (pvalue)
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001817 *pvalue = value;
1818 return 1;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001819}
1820
Tim Peters080c88b2003-02-15 03:01:11 +00001821/*
1822 * Iterate over a dict. Use like so:
1823 *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001824 * Py_ssize_t i;
Tim Peters080c88b2003-02-15 03:01:11 +00001825 * PyObject *key, *value;
1826 * i = 0; # important! i should not otherwise be changed by you
Neal Norwitz07323012003-02-15 14:45:12 +00001827 * while (PyDict_Next(yourdict, &i, &key, &value)) {
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001828 * Refer to borrowed references in key and value.
Tim Peters080c88b2003-02-15 03:01:11 +00001829 * }
1830 *
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001831 * Return 1 on success, return 0 when the reached the end of the dictionary
1832 * (or if op is not a dictionary)
1833 *
Tim Peters080c88b2003-02-15 03:01:11 +00001834 * CAUTION: In general, it isn't safe to use PyDict_Next in a loop that
Tim Peters67830702001-03-21 19:23:56 +00001835 * mutates the dict. One exception: it is safe if the loop merely changes
1836 * the values associated with the keys (but doesn't insert new keys or
1837 * delete keys), via PyDict_SetItem().
1838 */
Guido van Rossum25831651993-05-19 14:50:45 +00001839int
Martin v. Löwis18e16552006-02-15 17:27:45 +00001840PyDict_Next(PyObject *op, Py_ssize_t *ppos, PyObject **pkey, PyObject **pvalue)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00001841{
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03001842 return _PyDict_Next(op, ppos, pkey, pvalue, NULL);
Thomas Wouterscf297e42007-02-23 15:07:44 +00001843}
1844
Eric Snow96c6af92015-05-29 22:21:39 -06001845/* Internal version of dict.pop(). */
1846PyObject *
Serhiy Storchaka42e1ea92017-01-12 19:12:21 +02001847_PyDict_Pop_KnownHash(PyObject *dict, PyObject *key, Py_hash_t hash, PyObject *deflt)
Eric Snow96c6af92015-05-29 22:21:39 -06001848{
Victor Stinner742da042016-09-07 17:40:12 -07001849 Py_ssize_t ix, hashpos;
Eric Snow96c6af92015-05-29 22:21:39 -06001850 PyObject *old_value, *old_key;
1851 PyDictKeyEntry *ep;
Yury Selivanov684ef2c2016-10-28 19:01:21 -04001852 PyDictObject *mp;
1853
1854 assert(PyDict_Check(dict));
1855 mp = (PyDictObject *)dict;
Eric Snow96c6af92015-05-29 22:21:39 -06001856
1857 if (mp->ma_used == 0) {
1858 if (deflt) {
1859 Py_INCREF(deflt);
1860 return deflt;
1861 }
1862 _PyErr_SetKeyError(key);
1863 return NULL;
1864 }
INADA Naoki778928b2017-08-03 23:45:15 +09001865 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &old_value);
Victor Stinner742da042016-09-07 17:40:12 -07001866 if (ix == DKIX_ERROR)
Eric Snow96c6af92015-05-29 22:21:39 -06001867 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09001868 if (ix == DKIX_EMPTY || old_value == NULL) {
Eric Snow96c6af92015-05-29 22:21:39 -06001869 if (deflt) {
1870 Py_INCREF(deflt);
1871 return deflt;
1872 }
1873 _PyErr_SetKeyError(key);
1874 return NULL;
1875 }
Victor Stinner3b6a6b42016-09-08 12:51:24 -07001876
Victor Stinner78601a32016-09-09 19:28:36 -07001877 // Split table doesn't allow deletion. Combine it.
1878 if (_PyDict_HasSplitTable(mp)) {
1879 if (dictresize(mp, DK_SIZE(mp->ma_keys))) {
1880 return NULL;
1881 }
INADA Naoki778928b2017-08-03 23:45:15 +09001882 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &old_value);
Victor Stinner78601a32016-09-09 19:28:36 -07001883 assert(ix >= 0);
1884 }
1885
INADA Naoki778928b2017-08-03 23:45:15 +09001886 hashpos = lookdict_index(mp->ma_keys, hash, ix);
1887 assert(hashpos >= 0);
Victor Stinner78601a32016-09-09 19:28:36 -07001888 assert(old_value != NULL);
Eric Snow96c6af92015-05-29 22:21:39 -06001889 mp->ma_used--;
Victor Stinner3b6a6b42016-09-08 12:51:24 -07001890 mp->ma_version_tag = DICT_NEXT_VERSION();
INADA Naokia7576492018-11-14 18:39:27 +09001891 dictkeys_set_index(mp->ma_keys, hashpos, DKIX_DUMMY);
Victor Stinner78601a32016-09-09 19:28:36 -07001892 ep = &DK_ENTRIES(mp->ma_keys)[ix];
1893 ENSURE_ALLOWS_DELETIONS(mp);
1894 old_key = ep->me_key;
1895 ep->me_key = NULL;
INADA Naokiba609772016-12-07 20:41:42 +09001896 ep->me_value = NULL;
Victor Stinner78601a32016-09-09 19:28:36 -07001897 Py_DECREF(old_key);
Victor Stinner611b0fa2016-09-14 15:02:01 +02001898
Victor Stinner0fc91ee2019-04-12 21:51:34 +02001899 ASSERT_CONSISTENT(mp);
Eric Snow96c6af92015-05-29 22:21:39 -06001900 return old_value;
1901}
1902
Serhiy Storchaka67796522017-01-12 18:34:33 +02001903PyObject *
Serhiy Storchaka42e1ea92017-01-12 19:12:21 +02001904_PyDict_Pop(PyObject *dict, PyObject *key, PyObject *deflt)
Serhiy Storchaka67796522017-01-12 18:34:33 +02001905{
1906 Py_hash_t hash;
1907
Serhiy Storchaka42e1ea92017-01-12 19:12:21 +02001908 if (((PyDictObject *)dict)->ma_used == 0) {
Serhiy Storchaka67796522017-01-12 18:34:33 +02001909 if (deflt) {
1910 Py_INCREF(deflt);
1911 return deflt;
1912 }
1913 _PyErr_SetKeyError(key);
1914 return NULL;
1915 }
1916 if (!PyUnicode_CheckExact(key) ||
1917 (hash = ((PyASCIIObject *) key)->hash) == -1) {
1918 hash = PyObject_Hash(key);
1919 if (hash == -1)
1920 return NULL;
1921 }
Serhiy Storchaka42e1ea92017-01-12 19:12:21 +02001922 return _PyDict_Pop_KnownHash(dict, key, hash, deflt);
Serhiy Storchaka67796522017-01-12 18:34:33 +02001923}
1924
Eric Snow96c6af92015-05-29 22:21:39 -06001925/* Internal version of dict.from_keys(). It is subclass-friendly. */
1926PyObject *
1927_PyDict_FromKeys(PyObject *cls, PyObject *iterable, PyObject *value)
1928{
1929 PyObject *it; /* iter(iterable) */
1930 PyObject *key;
1931 PyObject *d;
1932 int status;
1933
Victor Stinnera5ed5f02016-12-06 18:45:50 +01001934 d = _PyObject_CallNoArg(cls);
Eric Snow96c6af92015-05-29 22:21:39 -06001935 if (d == NULL)
1936 return NULL;
1937
1938 if (PyDict_CheckExact(d) && ((PyDictObject *)d)->ma_used == 0) {
1939 if (PyDict_CheckExact(iterable)) {
1940 PyDictObject *mp = (PyDictObject *)d;
1941 PyObject *oldvalue;
1942 Py_ssize_t pos = 0;
1943 PyObject *key;
1944 Py_hash_t hash;
1945
Serhiy Storchakac61ac162017-03-21 08:52:38 +02001946 if (dictresize(mp, ESTIMATE_SIZE(PyDict_GET_SIZE(iterable)))) {
Eric Snow96c6af92015-05-29 22:21:39 -06001947 Py_DECREF(d);
1948 return NULL;
1949 }
1950
1951 while (_PyDict_Next(iterable, &pos, &key, &oldvalue, &hash)) {
1952 if (insertdict(mp, key, hash, value)) {
1953 Py_DECREF(d);
1954 return NULL;
1955 }
1956 }
1957 return d;
1958 }
1959 if (PyAnySet_CheckExact(iterable)) {
1960 PyDictObject *mp = (PyDictObject *)d;
1961 Py_ssize_t pos = 0;
1962 PyObject *key;
1963 Py_hash_t hash;
1964
Victor Stinner742da042016-09-07 17:40:12 -07001965 if (dictresize(mp, ESTIMATE_SIZE(PySet_GET_SIZE(iterable)))) {
Eric Snow96c6af92015-05-29 22:21:39 -06001966 Py_DECREF(d);
1967 return NULL;
1968 }
1969
1970 while (_PySet_NextEntry(iterable, &pos, &key, &hash)) {
1971 if (insertdict(mp, key, hash, value)) {
1972 Py_DECREF(d);
1973 return NULL;
1974 }
1975 }
1976 return d;
1977 }
1978 }
1979
1980 it = PyObject_GetIter(iterable);
1981 if (it == NULL){
1982 Py_DECREF(d);
1983 return NULL;
1984 }
1985
1986 if (PyDict_CheckExact(d)) {
1987 while ((key = PyIter_Next(it)) != NULL) {
1988 status = PyDict_SetItem(d, key, value);
1989 Py_DECREF(key);
1990 if (status < 0)
1991 goto Fail;
1992 }
1993 } else {
1994 while ((key = PyIter_Next(it)) != NULL) {
1995 status = PyObject_SetItem(d, key, value);
1996 Py_DECREF(key);
1997 if (status < 0)
1998 goto Fail;
1999 }
2000 }
2001
2002 if (PyErr_Occurred())
2003 goto Fail;
2004 Py_DECREF(it);
2005 return d;
2006
2007Fail:
2008 Py_DECREF(it);
2009 Py_DECREF(d);
2010 return NULL;
2011}
2012
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002013/* Methods */
2014
2015static void
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002016dict_dealloc(PyDictObject *mp)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002017{
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002018 PyObject **values = mp->ma_values;
2019 PyDictKeysObject *keys = mp->ma_keys;
2020 Py_ssize_t i, n;
INADA Naokia6296d32017-08-24 14:55:17 +09002021
2022 /* bpo-31095: UnTrack is needed before calling any callbacks */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002023 PyObject_GC_UnTrack(mp);
Jeroen Demeyer351c6742019-05-10 19:21:11 +02002024 Py_TRASHCAN_BEGIN(mp, dict_dealloc)
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002025 if (values != NULL) {
2026 if (values != empty_values) {
Victor Stinner742da042016-09-07 17:40:12 -07002027 for (i = 0, n = mp->ma_keys->dk_nentries; i < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002028 Py_XDECREF(values[i]);
2029 }
2030 free_values(values);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002031 }
INADA Naokia7576492018-11-14 18:39:27 +09002032 dictkeys_decref(keys);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002033 }
Victor Stinnerac2a4fe2013-07-16 22:19:00 +02002034 else if (keys != NULL) {
Antoine Pitrou2d169b22012-05-12 23:43:44 +02002035 assert(keys->dk_refcnt == 1);
INADA Naokia7576492018-11-14 18:39:27 +09002036 dictkeys_decref(keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002037 }
Victor Stinner522691c2020-06-23 16:40:40 +02002038 struct _Py_dict_state *state = get_dict_state();
Victor Stinnerb4e85ca2020-06-23 11:33:18 +02002039#ifdef Py_DEBUG
2040 // new_dict() must not be called after _PyDict_Fini()
2041 assert(state->numfree != -1);
Victor Stinnerb4b53862020-05-05 19:55:29 +02002042#endif
Victor Stinnerb4e85ca2020-06-23 11:33:18 +02002043 if (state->numfree < PyDict_MAXFREELIST && Py_IS_TYPE(mp, &PyDict_Type)) {
2044 state->free_list[state->numfree++] = mp;
2045 }
2046 else {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002047 Py_TYPE(mp)->tp_free((PyObject *)mp);
Victor Stinnerb4b53862020-05-05 19:55:29 +02002048 }
Jeroen Demeyer351c6742019-05-10 19:21:11 +02002049 Py_TRASHCAN_END
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002050}
2051
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002052
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002053static PyObject *
Guido van Rossum8ce8a782007-11-01 19:42:39 +00002054dict_repr(PyDictObject *mp)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002055{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002056 Py_ssize_t i;
Victor Stinnerf91929b2013-11-19 13:07:38 +01002057 PyObject *key = NULL, *value = NULL;
2058 _PyUnicodeWriter writer;
2059 int first;
Guido van Rossum255443b1998-04-10 22:47:14 +00002060
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002061 i = Py_ReprEnter((PyObject *)mp);
2062 if (i != 0) {
2063 return i > 0 ? PyUnicode_FromString("{...}") : NULL;
2064 }
Guido van Rossum255443b1998-04-10 22:47:14 +00002065
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002066 if (mp->ma_used == 0) {
Victor Stinnerf91929b2013-11-19 13:07:38 +01002067 Py_ReprLeave((PyObject *)mp);
2068 return PyUnicode_FromString("{}");
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002069 }
Tim Petersa7259592001-06-16 05:11:17 +00002070
Victor Stinnerf91929b2013-11-19 13:07:38 +01002071 _PyUnicodeWriter_Init(&writer);
2072 writer.overallocate = 1;
2073 /* "{" + "1: 2" + ", 3: 4" * (len - 1) + "}" */
2074 writer.min_length = 1 + 4 + (2 + 4) * (mp->ma_used - 1) + 1;
Tim Petersa7259592001-06-16 05:11:17 +00002075
Victor Stinnerf91929b2013-11-19 13:07:38 +01002076 if (_PyUnicodeWriter_WriteChar(&writer, '{') < 0)
2077 goto error;
Tim Petersa7259592001-06-16 05:11:17 +00002078
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002079 /* Do repr() on each key+value pair, and insert ": " between them.
2080 Note that repr may mutate the dict. */
2081 i = 0;
Victor Stinnerf91929b2013-11-19 13:07:38 +01002082 first = 1;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002083 while (PyDict_Next((PyObject *)mp, &i, &key, &value)) {
Victor Stinnerf91929b2013-11-19 13:07:38 +01002084 PyObject *s;
2085 int res;
2086
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002087 /* Prevent repr from deleting key or value during key format. */
2088 Py_INCREF(key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002089 Py_INCREF(value);
Victor Stinnerf97dfd72013-07-18 01:00:45 +02002090
Victor Stinnerf91929b2013-11-19 13:07:38 +01002091 if (!first) {
2092 if (_PyUnicodeWriter_WriteASCIIString(&writer, ", ", 2) < 0)
2093 goto error;
2094 }
2095 first = 0;
2096
2097 s = PyObject_Repr(key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002098 if (s == NULL)
Victor Stinnerf91929b2013-11-19 13:07:38 +01002099 goto error;
2100 res = _PyUnicodeWriter_WriteStr(&writer, s);
2101 Py_DECREF(s);
2102 if (res < 0)
2103 goto error;
2104
2105 if (_PyUnicodeWriter_WriteASCIIString(&writer, ": ", 2) < 0)
2106 goto error;
2107
2108 s = PyObject_Repr(value);
2109 if (s == NULL)
2110 goto error;
2111 res = _PyUnicodeWriter_WriteStr(&writer, s);
2112 Py_DECREF(s);
2113 if (res < 0)
2114 goto error;
2115
2116 Py_CLEAR(key);
2117 Py_CLEAR(value);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002118 }
Tim Petersa7259592001-06-16 05:11:17 +00002119
Victor Stinnerf91929b2013-11-19 13:07:38 +01002120 writer.overallocate = 0;
2121 if (_PyUnicodeWriter_WriteChar(&writer, '}') < 0)
2122 goto error;
Tim Petersa7259592001-06-16 05:11:17 +00002123
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002124 Py_ReprLeave((PyObject *)mp);
Victor Stinnerf91929b2013-11-19 13:07:38 +01002125
2126 return _PyUnicodeWriter_Finish(&writer);
2127
2128error:
2129 Py_ReprLeave((PyObject *)mp);
2130 _PyUnicodeWriter_Dealloc(&writer);
2131 Py_XDECREF(key);
2132 Py_XDECREF(value);
2133 return NULL;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002134}
2135
Martin v. Löwis18e16552006-02-15 17:27:45 +00002136static Py_ssize_t
Guido van Rossum8ce8a782007-11-01 19:42:39 +00002137dict_length(PyDictObject *mp)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002138{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002139 return mp->ma_used;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002140}
2141
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002142static PyObject *
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002143dict_subscript(PyDictObject *mp, PyObject *key)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002144{
Victor Stinner742da042016-09-07 17:40:12 -07002145 Py_ssize_t ix;
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002146 Py_hash_t hash;
INADA Naokiba609772016-12-07 20:41:42 +09002147 PyObject *value;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002148
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002149 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002150 (hash = ((PyASCIIObject *) key)->hash) == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002151 hash = PyObject_Hash(key);
2152 if (hash == -1)
2153 return NULL;
2154 }
INADA Naoki778928b2017-08-03 23:45:15 +09002155 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07002156 if (ix == DKIX_ERROR)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002157 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09002158 if (ix == DKIX_EMPTY || value == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002159 if (!PyDict_CheckExact(mp)) {
2160 /* Look up __missing__ method if we're a subclass. */
2161 PyObject *missing, *res;
Benjamin Petersonce798522012-01-22 11:24:29 -05002162 _Py_IDENTIFIER(__missing__);
2163 missing = _PyObject_LookupSpecial((PyObject *)mp, &PyId___missing__);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002164 if (missing != NULL) {
Petr Viktorinffd97532020-02-11 17:46:57 +01002165 res = PyObject_CallOneArg(missing, key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002166 Py_DECREF(missing);
2167 return res;
2168 }
2169 else if (PyErr_Occurred())
2170 return NULL;
2171 }
Raymond Hettinger69492da2013-09-02 15:59:26 -07002172 _PyErr_SetKeyError(key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002173 return NULL;
2174 }
INADA Naokiba609772016-12-07 20:41:42 +09002175 Py_INCREF(value);
2176 return value;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002177}
2178
2179static int
Guido van Rossum8ce8a782007-11-01 19:42:39 +00002180dict_ass_sub(PyDictObject *mp, PyObject *v, PyObject *w)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002181{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002182 if (w == NULL)
2183 return PyDict_DelItem((PyObject *)mp, v);
2184 else
2185 return PyDict_SetItem((PyObject *)mp, v, w);
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002186}
2187
Guido van Rossuma9e7a811997-05-13 21:02:11 +00002188static PyMappingMethods dict_as_mapping = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002189 (lenfunc)dict_length, /*mp_length*/
2190 (binaryfunc)dict_subscript, /*mp_subscript*/
2191 (objobjargproc)dict_ass_sub, /*mp_ass_subscript*/
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002192};
2193
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002194static PyObject *
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002195dict_keys(PyDictObject *mp)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002196{
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002197 PyObject *v;
2198 Py_ssize_t i, j;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002199 PyDictKeyEntry *ep;
Cheryl Sabellaf66e3362019-04-05 06:08:43 -04002200 Py_ssize_t n, offset;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002201 PyObject **value_ptr;
Guido van Rossuma4dd0112001-04-15 22:16:26 +00002202
Guido van Rossuma4dd0112001-04-15 22:16:26 +00002203 again:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002204 n = mp->ma_used;
2205 v = PyList_New(n);
2206 if (v == NULL)
2207 return NULL;
2208 if (n != mp->ma_used) {
2209 /* Durnit. The allocations caused the dict to resize.
2210 * Just start over, this shouldn't normally happen.
2211 */
2212 Py_DECREF(v);
2213 goto again;
2214 }
Victor Stinner742da042016-09-07 17:40:12 -07002215 ep = DK_ENTRIES(mp->ma_keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002216 if (mp->ma_values) {
2217 value_ptr = mp->ma_values;
2218 offset = sizeof(PyObject *);
2219 }
2220 else {
2221 value_ptr = &ep[0].me_value;
2222 offset = sizeof(PyDictKeyEntry);
2223 }
Cheryl Sabellaf66e3362019-04-05 06:08:43 -04002224 for (i = 0, j = 0; j < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002225 if (*value_ptr != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002226 PyObject *key = ep[i].me_key;
2227 Py_INCREF(key);
2228 PyList_SET_ITEM(v, j, key);
2229 j++;
2230 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002231 value_ptr = (PyObject **)(((char *)value_ptr) + offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002232 }
2233 assert(j == n);
2234 return v;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002235}
2236
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002237static PyObject *
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002238dict_values(PyDictObject *mp)
Guido van Rossum25831651993-05-19 14:50:45 +00002239{
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002240 PyObject *v;
2241 Py_ssize_t i, j;
Benjamin Petersonf0acae22016-09-08 09:50:08 -07002242 PyDictKeyEntry *ep;
Cheryl Sabellaf66e3362019-04-05 06:08:43 -04002243 Py_ssize_t n, offset;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002244 PyObject **value_ptr;
Guido van Rossuma4dd0112001-04-15 22:16:26 +00002245
Guido van Rossuma4dd0112001-04-15 22:16:26 +00002246 again:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002247 n = mp->ma_used;
2248 v = PyList_New(n);
2249 if (v == NULL)
2250 return NULL;
2251 if (n != mp->ma_used) {
2252 /* Durnit. The allocations caused the dict to resize.
2253 * Just start over, this shouldn't normally happen.
2254 */
2255 Py_DECREF(v);
2256 goto again;
2257 }
Benjamin Petersonf0acae22016-09-08 09:50:08 -07002258 ep = DK_ENTRIES(mp->ma_keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002259 if (mp->ma_values) {
2260 value_ptr = mp->ma_values;
2261 offset = sizeof(PyObject *);
2262 }
2263 else {
Benjamin Petersonf0acae22016-09-08 09:50:08 -07002264 value_ptr = &ep[0].me_value;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002265 offset = sizeof(PyDictKeyEntry);
2266 }
Cheryl Sabellaf66e3362019-04-05 06:08:43 -04002267 for (i = 0, j = 0; j < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002268 PyObject *value = *value_ptr;
2269 value_ptr = (PyObject **)(((char *)value_ptr) + offset);
2270 if (value != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002271 Py_INCREF(value);
2272 PyList_SET_ITEM(v, j, value);
2273 j++;
2274 }
2275 }
2276 assert(j == n);
2277 return v;
Guido van Rossum25831651993-05-19 14:50:45 +00002278}
2279
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002280static PyObject *
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002281dict_items(PyDictObject *mp)
Guido van Rossum25831651993-05-19 14:50:45 +00002282{
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002283 PyObject *v;
2284 Py_ssize_t i, j, n;
Cheryl Sabellaf66e3362019-04-05 06:08:43 -04002285 Py_ssize_t offset;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002286 PyObject *item, *key;
2287 PyDictKeyEntry *ep;
2288 PyObject **value_ptr;
Guido van Rossuma4dd0112001-04-15 22:16:26 +00002289
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002290 /* Preallocate the list of tuples, to avoid allocations during
2291 * the loop over the items, which could trigger GC, which
2292 * could resize the dict. :-(
2293 */
Guido van Rossuma4dd0112001-04-15 22:16:26 +00002294 again:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002295 n = mp->ma_used;
2296 v = PyList_New(n);
2297 if (v == NULL)
2298 return NULL;
2299 for (i = 0; i < n; i++) {
2300 item = PyTuple_New(2);
2301 if (item == NULL) {
2302 Py_DECREF(v);
2303 return NULL;
2304 }
2305 PyList_SET_ITEM(v, i, item);
2306 }
2307 if (n != mp->ma_used) {
2308 /* Durnit. The allocations caused the dict to resize.
2309 * Just start over, this shouldn't normally happen.
2310 */
2311 Py_DECREF(v);
2312 goto again;
2313 }
2314 /* Nothing we do below makes any function calls. */
Victor Stinner742da042016-09-07 17:40:12 -07002315 ep = DK_ENTRIES(mp->ma_keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002316 if (mp->ma_values) {
2317 value_ptr = mp->ma_values;
2318 offset = sizeof(PyObject *);
2319 }
2320 else {
2321 value_ptr = &ep[0].me_value;
2322 offset = sizeof(PyDictKeyEntry);
2323 }
Cheryl Sabellaf66e3362019-04-05 06:08:43 -04002324 for (i = 0, j = 0; j < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002325 PyObject *value = *value_ptr;
2326 value_ptr = (PyObject **)(((char *)value_ptr) + offset);
2327 if (value != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002328 key = ep[i].me_key;
2329 item = PyList_GET_ITEM(v, j);
2330 Py_INCREF(key);
2331 PyTuple_SET_ITEM(item, 0, key);
2332 Py_INCREF(value);
2333 PyTuple_SET_ITEM(item, 1, value);
2334 j++;
2335 }
2336 }
2337 assert(j == n);
2338 return v;
Guido van Rossum25831651993-05-19 14:50:45 +00002339}
2340
Larry Hastings5c661892014-01-24 06:17:25 -08002341/*[clinic input]
2342@classmethod
2343dict.fromkeys
Larry Hastings5c661892014-01-24 06:17:25 -08002344 iterable: object
2345 value: object=None
2346 /
2347
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02002348Create a new dictionary with keys from iterable and values set to value.
Larry Hastings5c661892014-01-24 06:17:25 -08002349[clinic start generated code]*/
2350
Larry Hastings5c661892014-01-24 06:17:25 -08002351static PyObject *
2352dict_fromkeys_impl(PyTypeObject *type, PyObject *iterable, PyObject *value)
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02002353/*[clinic end generated code: output=8fb98e4b10384999 input=382ba4855d0f74c3]*/
Larry Hastings5c661892014-01-24 06:17:25 -08002354{
Eric Snow96c6af92015-05-29 22:21:39 -06002355 return _PyDict_FromKeys((PyObject *)type, iterable, value);
Raymond Hettingere33d3df2002-11-27 07:29:33 +00002356}
2357
Brandt Buchereb8ac572020-02-24 19:47:34 -08002358/* Single-arg dict update; used by dict_update_common and operators. */
2359static int
2360dict_update_arg(PyObject *self, PyObject *arg)
2361{
2362 if (PyDict_CheckExact(arg)) {
2363 return PyDict_Merge(self, arg, 1);
2364 }
2365 _Py_IDENTIFIER(keys);
2366 PyObject *func;
2367 if (_PyObject_LookupAttrId(arg, &PyId_keys, &func) < 0) {
2368 return -1;
2369 }
2370 if (func != NULL) {
2371 Py_DECREF(func);
2372 return PyDict_Merge(self, arg, 1);
2373 }
2374 return PyDict_MergeFromSeq2(self, arg, 1);
2375}
2376
Raymond Hettinger31017ae2004-03-04 08:25:44 +00002377static int
Victor Stinner742da042016-09-07 17:40:12 -07002378dict_update_common(PyObject *self, PyObject *args, PyObject *kwds,
2379 const char *methname)
Guido van Rossume3f5b9c1997-05-28 19:15:28 +00002380{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002381 PyObject *arg = NULL;
2382 int result = 0;
Raymond Hettinger31017ae2004-03-04 08:25:44 +00002383
Serhiy Storchaka60c3d352017-11-11 16:19:56 +02002384 if (!PyArg_UnpackTuple(args, methname, 0, 1, &arg)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002385 result = -1;
Serhiy Storchaka60c3d352017-11-11 16:19:56 +02002386 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002387 else if (arg != NULL) {
Brandt Buchereb8ac572020-02-24 19:47:34 -08002388 result = dict_update_arg(self, arg);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002389 }
Serhiy Storchaka60c3d352017-11-11 16:19:56 +02002390
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002391 if (result == 0 && kwds != NULL) {
2392 if (PyArg_ValidateKeywordArguments(kwds))
2393 result = PyDict_Merge(self, kwds, 1);
2394 else
2395 result = -1;
2396 }
2397 return result;
Raymond Hettinger31017ae2004-03-04 08:25:44 +00002398}
2399
Victor Stinner91f0d4a2017-01-19 12:45:06 +01002400/* Note: dict.update() uses the METH_VARARGS|METH_KEYWORDS calling convention.
Serhiy Storchaka6969eaf2017-07-03 21:20:15 +03002401 Using METH_FASTCALL|METH_KEYWORDS would make dict.update(**dict2) calls
2402 slower, see the issue #29312. */
Raymond Hettinger31017ae2004-03-04 08:25:44 +00002403static PyObject *
2404dict_update(PyObject *self, PyObject *args, PyObject *kwds)
2405{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002406 if (dict_update_common(self, args, kwds, "update") != -1)
2407 Py_RETURN_NONE;
2408 return NULL;
Tim Peters6d6c1a32001-08-02 04:15:00 +00002409}
2410
Guido van Rossum05ac6de2001-08-10 20:28:28 +00002411/* Update unconditionally replaces existing items.
2412 Merge has a 3rd argument 'override'; if set, it acts like Update,
Tim Peters1fc240e2001-10-26 05:06:50 +00002413 otherwise it leaves existing items unchanged.
2414
2415 PyDict_{Update,Merge} update/merge from a mapping object.
2416
Tim Petersf582b822001-12-11 18:51:08 +00002417 PyDict_MergeFromSeq2 updates/merges from any iterable object
Tim Peters1fc240e2001-10-26 05:06:50 +00002418 producing iterable objects of length 2.
2419*/
2420
Tim Petersf582b822001-12-11 18:51:08 +00002421int
Tim Peters1fc240e2001-10-26 05:06:50 +00002422PyDict_MergeFromSeq2(PyObject *d, PyObject *seq2, int override)
2423{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002424 PyObject *it; /* iter(seq2) */
2425 Py_ssize_t i; /* index into seq2 of current element */
2426 PyObject *item; /* seq2[i] */
2427 PyObject *fast; /* item as a 2-tuple or 2-list */
Tim Peters1fc240e2001-10-26 05:06:50 +00002428
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002429 assert(d != NULL);
2430 assert(PyDict_Check(d));
2431 assert(seq2 != NULL);
Tim Peters1fc240e2001-10-26 05:06:50 +00002432
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002433 it = PyObject_GetIter(seq2);
2434 if (it == NULL)
2435 return -1;
Tim Peters1fc240e2001-10-26 05:06:50 +00002436
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002437 for (i = 0; ; ++i) {
2438 PyObject *key, *value;
2439 Py_ssize_t n;
Tim Peters1fc240e2001-10-26 05:06:50 +00002440
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002441 fast = NULL;
2442 item = PyIter_Next(it);
2443 if (item == NULL) {
2444 if (PyErr_Occurred())
2445 goto Fail;
2446 break;
2447 }
Tim Peters1fc240e2001-10-26 05:06:50 +00002448
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002449 /* Convert item to sequence, and verify length 2. */
2450 fast = PySequence_Fast(item, "");
2451 if (fast == NULL) {
2452 if (PyErr_ExceptionMatches(PyExc_TypeError))
2453 PyErr_Format(PyExc_TypeError,
2454 "cannot convert dictionary update "
2455 "sequence element #%zd to a sequence",
2456 i);
2457 goto Fail;
2458 }
2459 n = PySequence_Fast_GET_SIZE(fast);
2460 if (n != 2) {
2461 PyErr_Format(PyExc_ValueError,
2462 "dictionary update sequence element #%zd "
2463 "has length %zd; 2 is required",
2464 i, n);
2465 goto Fail;
2466 }
Tim Peters1fc240e2001-10-26 05:06:50 +00002467
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002468 /* Update/merge with this (key, value) pair. */
2469 key = PySequence_Fast_GET_ITEM(fast, 0);
2470 value = PySequence_Fast_GET_ITEM(fast, 1);
Serhiy Storchaka753bca32017-05-20 12:30:02 +03002471 Py_INCREF(key);
2472 Py_INCREF(value);
Serhiy Storchakaa24107b2019-02-25 17:59:46 +02002473 if (override) {
2474 if (PyDict_SetItem(d, key, value) < 0) {
Serhiy Storchaka753bca32017-05-20 12:30:02 +03002475 Py_DECREF(key);
2476 Py_DECREF(value);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002477 goto Fail;
Serhiy Storchaka753bca32017-05-20 12:30:02 +03002478 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002479 }
Serhiy Storchakaa24107b2019-02-25 17:59:46 +02002480 else if (PyDict_GetItemWithError(d, key) == NULL) {
2481 if (PyErr_Occurred() || PyDict_SetItem(d, key, value) < 0) {
2482 Py_DECREF(key);
2483 Py_DECREF(value);
2484 goto Fail;
2485 }
2486 }
2487
Serhiy Storchaka753bca32017-05-20 12:30:02 +03002488 Py_DECREF(key);
2489 Py_DECREF(value);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002490 Py_DECREF(fast);
2491 Py_DECREF(item);
2492 }
Tim Peters1fc240e2001-10-26 05:06:50 +00002493
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002494 i = 0;
Victor Stinner0fc91ee2019-04-12 21:51:34 +02002495 ASSERT_CONSISTENT(d);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002496 goto Return;
Tim Peters1fc240e2001-10-26 05:06:50 +00002497Fail:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002498 Py_XDECREF(item);
2499 Py_XDECREF(fast);
2500 i = -1;
Tim Peters1fc240e2001-10-26 05:06:50 +00002501Return:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002502 Py_DECREF(it);
2503 return Py_SAFE_DOWNCAST(i, Py_ssize_t, int);
Tim Peters1fc240e2001-10-26 05:06:50 +00002504}
2505
doko@ubuntu.comc96df682016-10-11 08:04:02 +02002506static int
Serhiy Storchakae036ef82016-10-02 11:06:43 +03002507dict_merge(PyObject *a, PyObject *b, int override)
Guido van Rossum05ac6de2001-08-10 20:28:28 +00002508{
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02002509 PyDictObject *mp, *other;
2510 Py_ssize_t i, n;
Victor Stinner742da042016-09-07 17:40:12 -07002511 PyDictKeyEntry *entry, *ep0;
Tim Peters6d6c1a32001-08-02 04:15:00 +00002512
Serhiy Storchakae036ef82016-10-02 11:06:43 +03002513 assert(0 <= override && override <= 2);
2514
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002515 /* We accept for the argument either a concrete dictionary object,
2516 * or an abstract "mapping" object. For the former, we can do
2517 * things quite efficiently. For the latter, we only require that
2518 * PyMapping_Keys() and PyObject_GetItem() be supported.
2519 */
2520 if (a == NULL || !PyDict_Check(a) || b == NULL) {
2521 PyErr_BadInternalCall();
2522 return -1;
2523 }
2524 mp = (PyDictObject*)a;
INADA Naoki2aaf98c2018-09-26 12:59:00 +09002525 if (PyDict_Check(b) && (Py_TYPE(b)->tp_iter == (getiterfunc)dict_iter)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002526 other = (PyDictObject*)b;
2527 if (other == mp || other->ma_used == 0)
2528 /* a.update(a) or a.update({}); nothing to do */
2529 return 0;
2530 if (mp->ma_used == 0)
2531 /* Since the target dict is empty, PyDict_GetItem()
2532 * always returns NULL. Setting override to 1
2533 * skips the unnecessary test.
2534 */
2535 override = 1;
2536 /* Do one big resize at the start, rather than
2537 * incrementally resizing as we insert new items. Expect
2538 * that there will be no (or few) overlapping keys.
2539 */
INADA Naokib1152be2016-10-27 19:26:50 +09002540 if (USABLE_FRACTION(mp->ma_keys->dk_size) < other->ma_used) {
2541 if (dictresize(mp, ESTIMATE_SIZE(mp->ma_used + other->ma_used))) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002542 return -1;
INADA Naokib1152be2016-10-27 19:26:50 +09002543 }
2544 }
Victor Stinner742da042016-09-07 17:40:12 -07002545 ep0 = DK_ENTRIES(other->ma_keys);
2546 for (i = 0, n = other->ma_keys->dk_nentries; i < n; i++) {
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002547 PyObject *key, *value;
2548 Py_hash_t hash;
Victor Stinner742da042016-09-07 17:40:12 -07002549 entry = &ep0[i];
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002550 key = entry->me_key;
2551 hash = entry->me_hash;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002552 if (other->ma_values)
2553 value = other->ma_values[i];
2554 else
2555 value = entry->me_value;
2556
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002557 if (value != NULL) {
2558 int err = 0;
2559 Py_INCREF(key);
2560 Py_INCREF(value);
Serhiy Storchakaf0b311b2016-11-06 13:18:24 +02002561 if (override == 1)
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002562 err = insertdict(mp, key, hash, value);
Serhiy Storchakaf0b311b2016-11-06 13:18:24 +02002563 else if (_PyDict_GetItem_KnownHash(a, key, hash) == NULL) {
2564 if (PyErr_Occurred()) {
2565 Py_DECREF(value);
2566 Py_DECREF(key);
2567 return -1;
2568 }
2569 err = insertdict(mp, key, hash, value);
2570 }
Serhiy Storchakae036ef82016-10-02 11:06:43 +03002571 else if (override != 0) {
2572 _PyErr_SetKeyError(key);
2573 Py_DECREF(value);
2574 Py_DECREF(key);
2575 return -1;
2576 }
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002577 Py_DECREF(value);
2578 Py_DECREF(key);
2579 if (err != 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002580 return -1;
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002581
Victor Stinner742da042016-09-07 17:40:12 -07002582 if (n != other->ma_keys->dk_nentries) {
Benjamin Petersona82f77f2015-07-04 19:55:16 -05002583 PyErr_SetString(PyExc_RuntimeError,
2584 "dict mutated during update");
2585 return -1;
2586 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002587 }
2588 }
2589 }
2590 else {
2591 /* Do it the generic, slower way */
2592 PyObject *keys = PyMapping_Keys(b);
2593 PyObject *iter;
2594 PyObject *key, *value;
2595 int status;
Barry Warsaw66a0d1d2001-06-26 20:08:32 +00002596
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002597 if (keys == NULL)
2598 /* Docstring says this is equivalent to E.keys() so
2599 * if E doesn't have a .keys() method we want
2600 * AttributeError to percolate up. Might as well
2601 * do the same for any other error.
2602 */
2603 return -1;
Barry Warsaw66a0d1d2001-06-26 20:08:32 +00002604
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002605 iter = PyObject_GetIter(keys);
2606 Py_DECREF(keys);
2607 if (iter == NULL)
2608 return -1;
Barry Warsaw66a0d1d2001-06-26 20:08:32 +00002609
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002610 for (key = PyIter_Next(iter); key; key = PyIter_Next(iter)) {
Serhiy Storchakaa24107b2019-02-25 17:59:46 +02002611 if (override != 1) {
2612 if (PyDict_GetItemWithError(a, key) != NULL) {
2613 if (override != 0) {
2614 _PyErr_SetKeyError(key);
2615 Py_DECREF(key);
2616 Py_DECREF(iter);
2617 return -1;
2618 }
2619 Py_DECREF(key);
2620 continue;
2621 }
2622 else if (PyErr_Occurred()) {
Serhiy Storchakae036ef82016-10-02 11:06:43 +03002623 Py_DECREF(key);
2624 Py_DECREF(iter);
2625 return -1;
2626 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002627 }
2628 value = PyObject_GetItem(b, key);
2629 if (value == NULL) {
2630 Py_DECREF(iter);
2631 Py_DECREF(key);
2632 return -1;
2633 }
2634 status = PyDict_SetItem(a, key, value);
2635 Py_DECREF(key);
2636 Py_DECREF(value);
2637 if (status < 0) {
2638 Py_DECREF(iter);
2639 return -1;
2640 }
2641 }
2642 Py_DECREF(iter);
2643 if (PyErr_Occurred())
2644 /* Iterator completed, via error */
2645 return -1;
2646 }
Victor Stinner0fc91ee2019-04-12 21:51:34 +02002647 ASSERT_CONSISTENT(a);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002648 return 0;
Guido van Rossume3f5b9c1997-05-28 19:15:28 +00002649}
2650
Serhiy Storchakae036ef82016-10-02 11:06:43 +03002651int
2652PyDict_Update(PyObject *a, PyObject *b)
2653{
2654 return dict_merge(a, b, 1);
2655}
2656
2657int
2658PyDict_Merge(PyObject *a, PyObject *b, int override)
2659{
2660 /* XXX Deprecate override not in (0, 1). */
2661 return dict_merge(a, b, override != 0);
2662}
2663
2664int
2665_PyDict_MergeEx(PyObject *a, PyObject *b, int override)
2666{
2667 return dict_merge(a, b, override);
2668}
2669
Guido van Rossume3f5b9c1997-05-28 19:15:28 +00002670static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05302671dict_copy(PyDictObject *mp, PyObject *Py_UNUSED(ignored))
Guido van Rossume3f5b9c1997-05-28 19:15:28 +00002672{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002673 return PyDict_Copy((PyObject*)mp);
Jeremy Hyltona12c7a72000-03-30 22:27:31 +00002674}
2675
2676PyObject *
Tim Peters1f5871e2000-07-04 17:44:48 +00002677PyDict_Copy(PyObject *o)
Jeremy Hyltona12c7a72000-03-30 22:27:31 +00002678{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002679 PyObject *copy;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002680 PyDictObject *mp;
2681 Py_ssize_t i, n;
Jeremy Hyltona12c7a72000-03-30 22:27:31 +00002682
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002683 if (o == NULL || !PyDict_Check(o)) {
2684 PyErr_BadInternalCall();
2685 return NULL;
2686 }
Yury Selivanovb0a7a032018-01-22 11:54:41 -05002687
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002688 mp = (PyDictObject *)o;
Yury Selivanovb0a7a032018-01-22 11:54:41 -05002689 if (mp->ma_used == 0) {
2690 /* The dict is empty; just return a new dict. */
2691 return PyDict_New();
2692 }
2693
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002694 if (_PyDict_HasSplitTable(mp)) {
2695 PyDictObject *split_copy;
Victor Stinner742da042016-09-07 17:40:12 -07002696 Py_ssize_t size = USABLE_FRACTION(DK_SIZE(mp->ma_keys));
2697 PyObject **newvalues;
2698 newvalues = new_values(size);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002699 if (newvalues == NULL)
2700 return PyErr_NoMemory();
2701 split_copy = PyObject_GC_New(PyDictObject, &PyDict_Type);
2702 if (split_copy == NULL) {
2703 free_values(newvalues);
2704 return NULL;
2705 }
2706 split_copy->ma_values = newvalues;
2707 split_copy->ma_keys = mp->ma_keys;
2708 split_copy->ma_used = mp->ma_used;
INADA Naokid1c82c52018-04-03 11:43:53 +09002709 split_copy->ma_version_tag = DICT_NEXT_VERSION();
INADA Naokia7576492018-11-14 18:39:27 +09002710 dictkeys_incref(mp->ma_keys);
Victor Stinner742da042016-09-07 17:40:12 -07002711 for (i = 0, n = size; i < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002712 PyObject *value = mp->ma_values[i];
2713 Py_XINCREF(value);
2714 split_copy->ma_values[i] = value;
2715 }
Benjamin Peterson7ce67e42012-04-24 10:32:57 -04002716 if (_PyObject_GC_IS_TRACKED(mp))
2717 _PyObject_GC_TRACK(split_copy);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002718 return (PyObject *)split_copy;
2719 }
Yury Selivanovb0a7a032018-01-22 11:54:41 -05002720
2721 if (PyDict_CheckExact(mp) && mp->ma_values == NULL &&
2722 (mp->ma_used >= (mp->ma_keys->dk_nentries * 2) / 3))
2723 {
2724 /* Use fast-copy if:
2725
2726 (1) 'mp' is an instance of a subclassed dict; and
2727
2728 (2) 'mp' is not a split-dict; and
2729
2730 (3) if 'mp' is non-compact ('del' operation does not resize dicts),
2731 do fast-copy only if it has at most 1/3 non-used keys.
2732
Ville Skyttä61f82e02018-04-20 23:08:45 +03002733 The last condition (3) is important to guard against a pathological
Yury Selivanovb0a7a032018-01-22 11:54:41 -05002734 case when a large dict is almost emptied with multiple del/pop
2735 operations and copied after that. In cases like this, we defer to
2736 PyDict_Merge, which produces a compacted copy.
2737 */
2738 return clone_combined_dict(mp);
2739 }
2740
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002741 copy = PyDict_New();
2742 if (copy == NULL)
2743 return NULL;
2744 if (PyDict_Merge(copy, o, 1) == 0)
2745 return copy;
2746 Py_DECREF(copy);
2747 return NULL;
Guido van Rossume3f5b9c1997-05-28 19:15:28 +00002748}
2749
Martin v. Löwis18e16552006-02-15 17:27:45 +00002750Py_ssize_t
Tim Peters1f5871e2000-07-04 17:44:48 +00002751PyDict_Size(PyObject *mp)
Guido van Rossum4199fac1993-11-05 10:18:44 +00002752{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002753 if (mp == NULL || !PyDict_Check(mp)) {
2754 PyErr_BadInternalCall();
2755 return -1;
2756 }
2757 return ((PyDictObject *)mp)->ma_used;
Guido van Rossum4199fac1993-11-05 10:18:44 +00002758}
2759
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002760PyObject *
Tim Peters1f5871e2000-07-04 17:44:48 +00002761PyDict_Keys(PyObject *mp)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002762{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002763 if (mp == NULL || !PyDict_Check(mp)) {
2764 PyErr_BadInternalCall();
2765 return NULL;
2766 }
2767 return dict_keys((PyDictObject *)mp);
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002768}
2769
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002770PyObject *
Tim Peters1f5871e2000-07-04 17:44:48 +00002771PyDict_Values(PyObject *mp)
Guido van Rossum25831651993-05-19 14:50:45 +00002772{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002773 if (mp == NULL || !PyDict_Check(mp)) {
2774 PyErr_BadInternalCall();
2775 return NULL;
2776 }
2777 return dict_values((PyDictObject *)mp);
Guido van Rossum25831651993-05-19 14:50:45 +00002778}
2779
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002780PyObject *
Tim Peters1f5871e2000-07-04 17:44:48 +00002781PyDict_Items(PyObject *mp)
Guido van Rossum25831651993-05-19 14:50:45 +00002782{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002783 if (mp == NULL || !PyDict_Check(mp)) {
2784 PyErr_BadInternalCall();
2785 return NULL;
2786 }
2787 return dict_items((PyDictObject *)mp);
Guido van Rossum25831651993-05-19 14:50:45 +00002788}
2789
Tim Peterse63415e2001-05-08 04:38:29 +00002790/* Return 1 if dicts equal, 0 if not, -1 if error.
2791 * Gets out as soon as any difference is detected.
2792 * Uses only Py_EQ comparison.
2793 */
2794static int
Guido van Rossum8ce8a782007-11-01 19:42:39 +00002795dict_equal(PyDictObject *a, PyDictObject *b)
Tim Peterse63415e2001-05-08 04:38:29 +00002796{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002797 Py_ssize_t i;
Tim Peterse63415e2001-05-08 04:38:29 +00002798
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002799 if (a->ma_used != b->ma_used)
2800 /* can't be equal if # of entries differ */
2801 return 0;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002802 /* Same # of entries -- check all of 'em. Exit early on any diff. */
Victor Stinner742da042016-09-07 17:40:12 -07002803 for (i = 0; i < a->ma_keys->dk_nentries; i++) {
2804 PyDictKeyEntry *ep = &DK_ENTRIES(a->ma_keys)[i];
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002805 PyObject *aval;
2806 if (a->ma_values)
2807 aval = a->ma_values[i];
2808 else
2809 aval = ep->me_value;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002810 if (aval != NULL) {
2811 int cmp;
2812 PyObject *bval;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002813 PyObject *key = ep->me_key;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002814 /* temporarily bump aval's refcount to ensure it stays
2815 alive until we're done with it */
2816 Py_INCREF(aval);
2817 /* ditto for key */
2818 Py_INCREF(key);
Antoine Pitrou0e9958b2012-12-02 19:10:07 +01002819 /* reuse the known hash value */
INADA Naoki778928b2017-08-03 23:45:15 +09002820 b->ma_keys->dk_lookup(b, key, ep->me_hash, &bval);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002821 if (bval == NULL) {
Serhiy Storchaka753bca32017-05-20 12:30:02 +03002822 Py_DECREF(key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002823 Py_DECREF(aval);
2824 if (PyErr_Occurred())
2825 return -1;
2826 return 0;
2827 }
Dong-hee Na2d5bf562019-12-31 10:04:22 +09002828 Py_INCREF(bval);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002829 cmp = PyObject_RichCompareBool(aval, bval, Py_EQ);
Serhiy Storchaka753bca32017-05-20 12:30:02 +03002830 Py_DECREF(key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002831 Py_DECREF(aval);
Dong-hee Na2d5bf562019-12-31 10:04:22 +09002832 Py_DECREF(bval);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002833 if (cmp <= 0) /* error or not equal */
2834 return cmp;
2835 }
2836 }
2837 return 1;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002838}
Tim Peterse63415e2001-05-08 04:38:29 +00002839
2840static PyObject *
2841dict_richcompare(PyObject *v, PyObject *w, int op)
2842{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002843 int cmp;
2844 PyObject *res;
Tim Peterse63415e2001-05-08 04:38:29 +00002845
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002846 if (!PyDict_Check(v) || !PyDict_Check(w)) {
2847 res = Py_NotImplemented;
2848 }
2849 else if (op == Py_EQ || op == Py_NE) {
2850 cmp = dict_equal((PyDictObject *)v, (PyDictObject *)w);
2851 if (cmp < 0)
2852 return NULL;
2853 res = (cmp == (op == Py_EQ)) ? Py_True : Py_False;
2854 }
2855 else
2856 res = Py_NotImplemented;
2857 Py_INCREF(res);
2858 return res;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002859}
Tim Peterse63415e2001-05-08 04:38:29 +00002860
Larry Hastings61272b72014-01-07 12:41:53 -08002861/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002862
2863@coexist
2864dict.__contains__
2865
2866 key: object
2867 /
2868
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02002869True if the dictionary has the specified key, else False.
Larry Hastings61272b72014-01-07 12:41:53 -08002870[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002871
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002872static PyObject *
Larry Hastingsc2047262014-01-25 20:43:29 -08002873dict___contains__(PyDictObject *self, PyObject *key)
Serhiy Storchaka19d25972017-02-04 08:05:07 +02002874/*[clinic end generated code: output=a3d03db709ed6e6b input=fe1cb42ad831e820]*/
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002875{
Larry Hastingsc2047262014-01-25 20:43:29 -08002876 register PyDictObject *mp = self;
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002877 Py_hash_t hash;
Victor Stinner742da042016-09-07 17:40:12 -07002878 Py_ssize_t ix;
INADA Naokiba609772016-12-07 20:41:42 +09002879 PyObject *value;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002880
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002881 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002882 (hash = ((PyASCIIObject *) key)->hash) == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002883 hash = PyObject_Hash(key);
2884 if (hash == -1)
2885 return NULL;
2886 }
INADA Naoki778928b2017-08-03 23:45:15 +09002887 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07002888 if (ix == DKIX_ERROR)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002889 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09002890 if (ix == DKIX_EMPTY || value == NULL)
Victor Stinner742da042016-09-07 17:40:12 -07002891 Py_RETURN_FALSE;
2892 Py_RETURN_TRUE;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00002893}
2894
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01002895/*[clinic input]
2896dict.get
2897
2898 key: object
Serhiy Storchaka48088ee2017-01-19 19:00:30 +02002899 default: object = None
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01002900 /
2901
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02002902Return the value for key if key is in the dictionary, else default.
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01002903[clinic start generated code]*/
2904
Guido van Rossumc0b618a1997-05-02 03:12:38 +00002905static PyObject *
Serhiy Storchaka48088ee2017-01-19 19:00:30 +02002906dict_get_impl(PyDictObject *self, PyObject *key, PyObject *default_value)
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02002907/*[clinic end generated code: output=bba707729dee05bf input=279ddb5790b6b107]*/
Barry Warsawc38c5da1997-10-06 17:49:20 +00002908{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002909 PyObject *val = NULL;
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002910 Py_hash_t hash;
Victor Stinner742da042016-09-07 17:40:12 -07002911 Py_ssize_t ix;
Barry Warsawc38c5da1997-10-06 17:49:20 +00002912
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002913 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002914 (hash = ((PyASCIIObject *) key)->hash) == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002915 hash = PyObject_Hash(key);
2916 if (hash == -1)
2917 return NULL;
2918 }
INADA Naoki778928b2017-08-03 23:45:15 +09002919 ix = (self->ma_keys->dk_lookup) (self, key, hash, &val);
Victor Stinner742da042016-09-07 17:40:12 -07002920 if (ix == DKIX_ERROR)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002921 return NULL;
INADA Naokiba609772016-12-07 20:41:42 +09002922 if (ix == DKIX_EMPTY || val == NULL) {
Serhiy Storchaka48088ee2017-01-19 19:00:30 +02002923 val = default_value;
INADA Naokiba609772016-12-07 20:41:42 +09002924 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002925 Py_INCREF(val);
2926 return val;
Barry Warsawc38c5da1997-10-06 17:49:20 +00002927}
2928
Benjamin Peterson00e98862013-03-07 22:16:29 -05002929PyObject *
2930PyDict_SetDefault(PyObject *d, PyObject *key, PyObject *defaultobj)
Guido van Rossum164452c2000-08-08 16:12:54 +00002931{
Benjamin Peterson00e98862013-03-07 22:16:29 -05002932 PyDictObject *mp = (PyDictObject *)d;
INADA Naoki93f26f72016-11-02 18:45:16 +09002933 PyObject *value;
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002934 Py_hash_t hash;
Guido van Rossum164452c2000-08-08 16:12:54 +00002935
Benjamin Peterson00e98862013-03-07 22:16:29 -05002936 if (!PyDict_Check(d)) {
2937 PyErr_BadInternalCall();
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002938 return NULL;
Benjamin Peterson00e98862013-03-07 22:16:29 -05002939 }
INADA Naoki93f26f72016-11-02 18:45:16 +09002940
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002941 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002942 (hash = ((PyASCIIObject *) key)->hash) == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002943 hash = PyObject_Hash(key);
2944 if (hash == -1)
2945 return NULL;
2946 }
Inada Naoki2ddc7f62019-03-18 20:38:33 +09002947 if (mp->ma_keys == Py_EMPTY_KEYS) {
2948 if (insert_to_emptydict(mp, key, hash, defaultobj) < 0) {
2949 return NULL;
2950 }
2951 return defaultobj;
2952 }
INADA Naoki93f26f72016-11-02 18:45:16 +09002953
2954 if (mp->ma_values != NULL && !PyUnicode_CheckExact(key)) {
2955 if (insertion_resize(mp) < 0)
2956 return NULL;
2957 }
2958
INADA Naoki778928b2017-08-03 23:45:15 +09002959 Py_ssize_t ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07002960 if (ix == DKIX_ERROR)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002961 return NULL;
INADA Naoki93f26f72016-11-02 18:45:16 +09002962
2963 if (_PyDict_HasSplitTable(mp) &&
INADA Naokiba609772016-12-07 20:41:42 +09002964 ((ix >= 0 && value == NULL && mp->ma_used != ix) ||
INADA Naoki93f26f72016-11-02 18:45:16 +09002965 (ix == DKIX_EMPTY && mp->ma_used != mp->ma_keys->dk_nentries))) {
2966 if (insertion_resize(mp) < 0) {
2967 return NULL;
2968 }
INADA Naoki93f26f72016-11-02 18:45:16 +09002969 ix = DKIX_EMPTY;
2970 }
2971
2972 if (ix == DKIX_EMPTY) {
2973 PyDictKeyEntry *ep, *ep0;
2974 value = defaultobj;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002975 if (mp->ma_keys->dk_usable <= 0) {
Victor Stinner3c336c52016-09-12 14:17:40 +02002976 if (insertion_resize(mp) < 0) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002977 return NULL;
Victor Stinner3c336c52016-09-12 14:17:40 +02002978 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002979 }
INADA Naoki778928b2017-08-03 23:45:15 +09002980 Py_ssize_t hashpos = find_empty_slot(mp->ma_keys, hash);
INADA Naoki93f26f72016-11-02 18:45:16 +09002981 ep0 = DK_ENTRIES(mp->ma_keys);
2982 ep = &ep0[mp->ma_keys->dk_nentries];
INADA Naokia7576492018-11-14 18:39:27 +09002983 dictkeys_set_index(mp->ma_keys, hashpos, mp->ma_keys->dk_nentries);
Benjamin Petersonb1efa532013-03-04 09:47:50 -05002984 Py_INCREF(key);
INADA Naoki93f26f72016-11-02 18:45:16 +09002985 Py_INCREF(value);
2986 MAINTAIN_TRACKING(mp, key, value);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002987 ep->me_key = key;
2988 ep->me_hash = hash;
INADA Naokiba609772016-12-07 20:41:42 +09002989 if (_PyDict_HasSplitTable(mp)) {
INADA Naoki93f26f72016-11-02 18:45:16 +09002990 assert(mp->ma_values[mp->ma_keys->dk_nentries] == NULL);
2991 mp->ma_values[mp->ma_keys->dk_nentries] = value;
Victor Stinner742da042016-09-07 17:40:12 -07002992 }
2993 else {
INADA Naoki93f26f72016-11-02 18:45:16 +09002994 ep->me_value = value;
Victor Stinner742da042016-09-07 17:40:12 -07002995 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04002996 mp->ma_used++;
Victor Stinner3b6a6b42016-09-08 12:51:24 -07002997 mp->ma_version_tag = DICT_NEXT_VERSION();
INADA Naoki93f26f72016-11-02 18:45:16 +09002998 mp->ma_keys->dk_usable--;
2999 mp->ma_keys->dk_nentries++;
3000 assert(mp->ma_keys->dk_usable >= 0);
3001 }
INADA Naokiba609772016-12-07 20:41:42 +09003002 else if (value == NULL) {
INADA Naoki93f26f72016-11-02 18:45:16 +09003003 value = defaultobj;
3004 assert(_PyDict_HasSplitTable(mp));
3005 assert(ix == mp->ma_used);
3006 Py_INCREF(value);
3007 MAINTAIN_TRACKING(mp, key, value);
INADA Naokiba609772016-12-07 20:41:42 +09003008 mp->ma_values[ix] = value;
INADA Naoki93f26f72016-11-02 18:45:16 +09003009 mp->ma_used++;
3010 mp->ma_version_tag = DICT_NEXT_VERSION();
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003011 }
INADA Naoki93f26f72016-11-02 18:45:16 +09003012
Victor Stinner0fc91ee2019-04-12 21:51:34 +02003013 ASSERT_CONSISTENT(mp);
INADA Naoki93f26f72016-11-02 18:45:16 +09003014 return value;
Guido van Rossum164452c2000-08-08 16:12:54 +00003015}
3016
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01003017/*[clinic input]
3018dict.setdefault
3019
3020 key: object
Serhiy Storchaka48088ee2017-01-19 19:00:30 +02003021 default: object = None
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01003022 /
3023
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02003024Insert key with a value of default if key is not in the dictionary.
3025
3026Return the value for key if key is in the dictionary, else default.
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01003027[clinic start generated code]*/
3028
Benjamin Peterson00e98862013-03-07 22:16:29 -05003029static PyObject *
Serhiy Storchaka48088ee2017-01-19 19:00:30 +02003030dict_setdefault_impl(PyDictObject *self, PyObject *key,
3031 PyObject *default_value)
Serhiy Storchaka78d9e582017-01-25 00:30:04 +02003032/*[clinic end generated code: output=f8c1101ebf69e220 input=0f063756e815fd9d]*/
Benjamin Peterson00e98862013-03-07 22:16:29 -05003033{
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01003034 PyObject *val;
Benjamin Peterson00e98862013-03-07 22:16:29 -05003035
Serhiy Storchaka48088ee2017-01-19 19:00:30 +02003036 val = PyDict_SetDefault((PyObject *)self, key, default_value);
Benjamin Peterson00e98862013-03-07 22:16:29 -05003037 Py_XINCREF(val);
3038 return val;
3039}
Guido van Rossum164452c2000-08-08 16:12:54 +00003040
3041static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303042dict_clear(PyDictObject *mp, PyObject *Py_UNUSED(ignored))
Guido van Rossumfb8f1ca1997-03-21 21:55:12 +00003043{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003044 PyDict_Clear((PyObject *)mp);
3045 Py_RETURN_NONE;
Guido van Rossumfb8f1ca1997-03-21 21:55:12 +00003046}
3047
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003048/*[clinic input]
3049dict.pop
3050
3051 key: object
3052 default: object = NULL
3053 /
3054
Serhiy Storchaka279f4462019-09-14 12:24:05 +03003055D.pop(k[,d]) -> v, remove specified key and return the corresponding value.
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003056
3057If key is not found, default is returned if given, otherwise KeyError is raised
3058[clinic start generated code]*/
3059
Guido van Rossumba6ab842000-12-12 22:02:18 +00003060static PyObject *
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003061dict_pop_impl(PyDictObject *self, PyObject *key, PyObject *default_value)
Serhiy Storchaka279f4462019-09-14 12:24:05 +03003062/*[clinic end generated code: output=3abb47b89f24c21c input=eeebec7812190348]*/
Guido van Rossume027d982002-04-12 15:11:59 +00003063{
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003064 return _PyDict_Pop((PyObject*)self, key, default_value);
Guido van Rossume027d982002-04-12 15:11:59 +00003065}
3066
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003067/*[clinic input]
3068dict.popitem
3069
3070Remove and return a (key, value) pair as a 2-tuple.
3071
3072Pairs are returned in LIFO (last-in, first-out) order.
3073Raises KeyError if the dict is empty.
3074[clinic start generated code]*/
3075
Guido van Rossume027d982002-04-12 15:11:59 +00003076static PyObject *
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003077dict_popitem_impl(PyDictObject *self)
3078/*[clinic end generated code: output=e65fcb04420d230d input=1c38a49f21f64941]*/
Guido van Rossumba6ab842000-12-12 22:02:18 +00003079{
Victor Stinner742da042016-09-07 17:40:12 -07003080 Py_ssize_t i, j;
3081 PyDictKeyEntry *ep0, *ep;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003082 PyObject *res;
Guido van Rossumba6ab842000-12-12 22:02:18 +00003083
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003084 /* Allocate the result tuple before checking the size. Believe it
3085 * or not, this allocation could trigger a garbage collection which
3086 * could empty the dict, so if we checked the size first and that
3087 * happened, the result would be an infinite loop (searching for an
3088 * entry that no longer exists). Note that the usual popitem()
3089 * idiom is "while d: k, v = d.popitem()". so needing to throw the
3090 * tuple away if the dict *is* empty isn't a significant
3091 * inefficiency -- possible, but unlikely in practice.
3092 */
3093 res = PyTuple_New(2);
3094 if (res == NULL)
3095 return NULL;
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003096 if (self->ma_used == 0) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003097 Py_DECREF(res);
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003098 PyErr_SetString(PyExc_KeyError, "popitem(): dictionary is empty");
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003099 return NULL;
3100 }
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003101 /* Convert split table to combined table */
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003102 if (self->ma_keys->dk_lookup == lookdict_split) {
3103 if (dictresize(self, DK_SIZE(self->ma_keys))) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003104 Py_DECREF(res);
3105 return NULL;
3106 }
3107 }
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003108 ENSURE_ALLOWS_DELETIONS(self);
Victor Stinner742da042016-09-07 17:40:12 -07003109
3110 /* Pop last item */
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003111 ep0 = DK_ENTRIES(self->ma_keys);
3112 i = self->ma_keys->dk_nentries - 1;
Victor Stinner742da042016-09-07 17:40:12 -07003113 while (i >= 0 && ep0[i].me_value == NULL) {
3114 i--;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003115 }
Victor Stinner742da042016-09-07 17:40:12 -07003116 assert(i >= 0);
3117
3118 ep = &ep0[i];
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003119 j = lookdict_index(self->ma_keys, ep->me_hash, i);
Victor Stinner742da042016-09-07 17:40:12 -07003120 assert(j >= 0);
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003121 assert(dictkeys_get_index(self->ma_keys, j) == i);
3122 dictkeys_set_index(self->ma_keys, j, DKIX_DUMMY);
Victor Stinner742da042016-09-07 17:40:12 -07003123
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003124 PyTuple_SET_ITEM(res, 0, ep->me_key);
3125 PyTuple_SET_ITEM(res, 1, ep->me_value);
Victor Stinner742da042016-09-07 17:40:12 -07003126 ep->me_key = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003127 ep->me_value = NULL;
Victor Stinner742da042016-09-07 17:40:12 -07003128 /* We can't dk_usable++ since there is DKIX_DUMMY in indices */
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003129 self->ma_keys->dk_nentries = i;
3130 self->ma_used--;
3131 self->ma_version_tag = DICT_NEXT_VERSION();
Victor Stinner0fc91ee2019-04-12 21:51:34 +02003132 ASSERT_CONSISTENT(self);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003133 return res;
Guido van Rossumba6ab842000-12-12 22:02:18 +00003134}
3135
Jeremy Hylton8caad492000-06-23 14:18:11 +00003136static int
3137dict_traverse(PyObject *op, visitproc visit, void *arg)
3138{
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003139 PyDictObject *mp = (PyDictObject *)op;
Benjamin Peterson55f44522016-09-05 12:12:59 -07003140 PyDictKeysObject *keys = mp->ma_keys;
Serhiy Storchaka46825d22016-09-26 21:29:34 +03003141 PyDictKeyEntry *entries = DK_ENTRIES(keys);
Victor Stinner742da042016-09-07 17:40:12 -07003142 Py_ssize_t i, n = keys->dk_nentries;
3143
Benjamin Peterson55f44522016-09-05 12:12:59 -07003144 if (keys->dk_lookup == lookdict) {
3145 for (i = 0; i < n; i++) {
3146 if (entries[i].me_value != NULL) {
3147 Py_VISIT(entries[i].me_value);
3148 Py_VISIT(entries[i].me_key);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003149 }
3150 }
Victor Stinner742da042016-09-07 17:40:12 -07003151 }
3152 else {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003153 if (mp->ma_values != NULL) {
Benjamin Peterson55f44522016-09-05 12:12:59 -07003154 for (i = 0; i < n; i++) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003155 Py_VISIT(mp->ma_values[i]);
3156 }
3157 }
3158 else {
Benjamin Peterson55f44522016-09-05 12:12:59 -07003159 for (i = 0; i < n; i++) {
3160 Py_VISIT(entries[i].me_value);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003161 }
3162 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003163 }
3164 return 0;
Jeremy Hylton8caad492000-06-23 14:18:11 +00003165}
3166
3167static int
3168dict_tp_clear(PyObject *op)
3169{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003170 PyDict_Clear(op);
3171 return 0;
Jeremy Hylton8caad492000-06-23 14:18:11 +00003172}
3173
Guido van Rossum8ce8a782007-11-01 19:42:39 +00003174static PyObject *dictiter_new(PyDictObject *, PyTypeObject *);
Guido van Rossum09e563a2001-05-01 12:10:21 +00003175
Serhiy Storchaka0ce7a3a2015-12-22 08:16:18 +02003176Py_ssize_t
Eric Snow96c6af92015-05-29 22:21:39 -06003177_PyDict_SizeOf(PyDictObject *mp)
Martin v. Löwis00709aa2008-06-04 14:18:43 +00003178{
Victor Stinner742da042016-09-07 17:40:12 -07003179 Py_ssize_t size, usable, res;
Martin v. Löwis00709aa2008-06-04 14:18:43 +00003180
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003181 size = DK_SIZE(mp->ma_keys);
Victor Stinner742da042016-09-07 17:40:12 -07003182 usable = USABLE_FRACTION(size);
3183
Serhiy Storchaka5c4064e2015-12-19 20:05:25 +02003184 res = _PyObject_SIZE(Py_TYPE(mp));
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003185 if (mp->ma_values)
Victor Stinner742da042016-09-07 17:40:12 -07003186 res += usable * sizeof(PyObject*);
Martin v. Loewis4f2f3b62012-04-24 19:13:57 +02003187 /* If the dictionary is split, the keys portion is accounted-for
3188 in the type object. */
3189 if (mp->ma_keys->dk_refcnt == 1)
Victor Stinner98ee9d52016-09-08 09:33:56 -07003190 res += (sizeof(PyDictKeysObject)
Victor Stinner98ee9d52016-09-08 09:33:56 -07003191 + DK_IXSIZE(mp->ma_keys) * size
3192 + sizeof(PyDictKeyEntry) * usable);
Serhiy Storchaka0ce7a3a2015-12-22 08:16:18 +02003193 return res;
Martin v. Loewis4f2f3b62012-04-24 19:13:57 +02003194}
3195
3196Py_ssize_t
3197_PyDict_KeysSize(PyDictKeysObject *keys)
3198{
Victor Stinner98ee9d52016-09-08 09:33:56 -07003199 return (sizeof(PyDictKeysObject)
Victor Stinner98ee9d52016-09-08 09:33:56 -07003200 + DK_IXSIZE(keys) * DK_SIZE(keys)
3201 + USABLE_FRACTION(DK_SIZE(keys)) * sizeof(PyDictKeyEntry));
Martin v. Löwis00709aa2008-06-04 14:18:43 +00003202}
3203
doko@ubuntu.com17210f52016-01-14 14:04:59 +01003204static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303205dict_sizeof(PyDictObject *mp, PyObject *Py_UNUSED(ignored))
Serhiy Storchaka0ce7a3a2015-12-22 08:16:18 +02003206{
3207 return PyLong_FromSsize_t(_PyDict_SizeOf(mp));
3208}
3209
Brandt Buchereb8ac572020-02-24 19:47:34 -08003210static PyObject *
3211dict_or(PyObject *self, PyObject *other)
3212{
3213 if (!PyDict_Check(self) || !PyDict_Check(other)) {
3214 Py_RETURN_NOTIMPLEMENTED;
3215 }
3216 PyObject *new = PyDict_Copy(self);
3217 if (new == NULL) {
3218 return NULL;
3219 }
3220 if (dict_update_arg(new, other)) {
3221 Py_DECREF(new);
3222 return NULL;
3223 }
3224 return new;
3225}
3226
3227static PyObject *
3228dict_ior(PyObject *self, PyObject *other)
3229{
3230 if (dict_update_arg(self, other)) {
3231 return NULL;
3232 }
3233 Py_INCREF(self);
3234 return self;
3235}
3236
Raymond Hettinger8f5cdaa2003-12-13 11:26:12 +00003237PyDoc_STRVAR(getitem__doc__, "x.__getitem__(y) <==> x[y]");
3238
Martin v. Löwis00709aa2008-06-04 14:18:43 +00003239PyDoc_STRVAR(sizeof__doc__,
3240"D.__sizeof__() -> size of D in memory, in bytes");
3241
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00003242PyDoc_STRVAR(update__doc__,
Brett Cannonf2754162013-05-11 14:46:48 -04003243"D.update([E, ]**F) -> None. Update D from dict/iterable E and F.\n\
3244If E is present and has a .keys() method, then does: for k in E: D[k] = E[k]\n\
3245If E is present and lacks a .keys() method, then does: for k, v in E: D[k] = v\n\
3246In either case, this is followed by: for k in F: D[k] = F[k]");
Tim Petersf7f88b12000-12-13 23:18:45 +00003247
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00003248PyDoc_STRVAR(clear__doc__,
3249"D.clear() -> None. Remove all items from D.");
Tim Petersf7f88b12000-12-13 23:18:45 +00003250
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00003251PyDoc_STRVAR(copy__doc__,
3252"D.copy() -> a shallow copy of D");
Tim Petersf7f88b12000-12-13 23:18:45 +00003253
Guido van Rossumb90c8482007-02-10 01:11:45 +00003254/* Forward */
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303255static PyObject *dictkeys_new(PyObject *, PyObject *);
3256static PyObject *dictitems_new(PyObject *, PyObject *);
3257static PyObject *dictvalues_new(PyObject *, PyObject *);
Guido van Rossumb90c8482007-02-10 01:11:45 +00003258
Guido van Rossum45c85d12007-07-27 16:31:40 +00003259PyDoc_STRVAR(keys__doc__,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003260 "D.keys() -> a set-like object providing a view on D's keys");
Guido van Rossum45c85d12007-07-27 16:31:40 +00003261PyDoc_STRVAR(items__doc__,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003262 "D.items() -> a set-like object providing a view on D's items");
Guido van Rossum45c85d12007-07-27 16:31:40 +00003263PyDoc_STRVAR(values__doc__,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003264 "D.values() -> an object providing a view on D's values");
Guido van Rossumb90c8482007-02-10 01:11:45 +00003265
Guido van Rossumc0b618a1997-05-02 03:12:38 +00003266static PyMethodDef mapp_methods[] = {
Larry Hastings31826802013-10-19 00:09:25 -07003267 DICT___CONTAINS___METHODDEF
Serhiy Storchaka62be7422018-11-27 13:27:31 +02003268 {"__getitem__", (PyCFunction)(void(*)(void))dict_subscript, METH_O | METH_COEXIST,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003269 getitem__doc__},
Serhiy Storchaka62be7422018-11-27 13:27:31 +02003270 {"__sizeof__", (PyCFunction)(void(*)(void))dict_sizeof, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003271 sizeof__doc__},
Victor Stinner7dc6a5f2017-01-19 12:37:13 +01003272 DICT_GET_METHODDEF
3273 DICT_SETDEFAULT_METHODDEF
Inada Naoki9e4f2f32019-04-12 16:11:28 +09003274 DICT_POP_METHODDEF
3275 DICT_POPITEM_METHODDEF
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303276 {"keys", dictkeys_new, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003277 keys__doc__},
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303278 {"items", dictitems_new, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003279 items__doc__},
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303280 {"values", dictvalues_new, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003281 values__doc__},
Serhiy Storchaka62be7422018-11-27 13:27:31 +02003282 {"update", (PyCFunction)(void(*)(void))dict_update, METH_VARARGS | METH_KEYWORDS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003283 update__doc__},
Larry Hastings5c661892014-01-24 06:17:25 -08003284 DICT_FROMKEYS_METHODDEF
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003285 {"clear", (PyCFunction)dict_clear, METH_NOARGS,
3286 clear__doc__},
3287 {"copy", (PyCFunction)dict_copy, METH_NOARGS,
3288 copy__doc__},
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003289 DICT___REVERSED___METHODDEF
Guido van Rossum48b069a2020-04-07 09:50:06 -07003290 {"__class_getitem__", (PyCFunction)Py_GenericAlias, METH_O|METH_CLASS, PyDoc_STR("See PEP 585")},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003291 {NULL, NULL} /* sentinel */
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003292};
3293
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00003294/* Return 1 if `key` is in dict `op`, 0 if not, and -1 on error. */
Raymond Hettingerbc0f2ab2003-11-25 21:12:14 +00003295int
3296PyDict_Contains(PyObject *op, PyObject *key)
Guido van Rossum0dbb4fb2001-04-20 16:50:40 +00003297{
Benjamin Peterson8f67d082010-10-17 20:54:53 +00003298 Py_hash_t hash;
Victor Stinner742da042016-09-07 17:40:12 -07003299 Py_ssize_t ix;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003300 PyDictObject *mp = (PyDictObject *)op;
INADA Naokiba609772016-12-07 20:41:42 +09003301 PyObject *value;
Guido van Rossum0dbb4fb2001-04-20 16:50:40 +00003302
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003303 if (!PyUnicode_CheckExact(key) ||
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02003304 (hash = ((PyASCIIObject *) key)->hash) == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003305 hash = PyObject_Hash(key);
3306 if (hash == -1)
3307 return -1;
3308 }
INADA Naoki778928b2017-08-03 23:45:15 +09003309 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07003310 if (ix == DKIX_ERROR)
3311 return -1;
INADA Naokiba609772016-12-07 20:41:42 +09003312 return (ix != DKIX_EMPTY && value != NULL);
Guido van Rossum0dbb4fb2001-04-20 16:50:40 +00003313}
3314
Thomas Wouterscf297e42007-02-23 15:07:44 +00003315/* Internal version of PyDict_Contains used when the hash value is already known */
3316int
Benjamin Peterson8f67d082010-10-17 20:54:53 +00003317_PyDict_Contains(PyObject *op, PyObject *key, Py_hash_t hash)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003318{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003319 PyDictObject *mp = (PyDictObject *)op;
INADA Naokiba609772016-12-07 20:41:42 +09003320 PyObject *value;
Victor Stinner742da042016-09-07 17:40:12 -07003321 Py_ssize_t ix;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003322
INADA Naoki778928b2017-08-03 23:45:15 +09003323 ix = (mp->ma_keys->dk_lookup)(mp, key, hash, &value);
Victor Stinner742da042016-09-07 17:40:12 -07003324 if (ix == DKIX_ERROR)
3325 return -1;
INADA Naokiba609772016-12-07 20:41:42 +09003326 return (ix != DKIX_EMPTY && value != NULL);
Thomas Wouterscf297e42007-02-23 15:07:44 +00003327}
3328
Guido van Rossum0dbb4fb2001-04-20 16:50:40 +00003329/* Hack to implement "key in dict" */
3330static PySequenceMethods dict_as_sequence = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003331 0, /* sq_length */
3332 0, /* sq_concat */
3333 0, /* sq_repeat */
3334 0, /* sq_item */
3335 0, /* sq_slice */
3336 0, /* sq_ass_item */
3337 0, /* sq_ass_slice */
3338 PyDict_Contains, /* sq_contains */
3339 0, /* sq_inplace_concat */
3340 0, /* sq_inplace_repeat */
Guido van Rossum0dbb4fb2001-04-20 16:50:40 +00003341};
3342
Brandt Buchereb8ac572020-02-24 19:47:34 -08003343static PyNumberMethods dict_as_number = {
3344 .nb_or = dict_or,
3345 .nb_inplace_or = dict_ior,
3346};
3347
Guido van Rossum09e563a2001-05-01 12:10:21 +00003348static PyObject *
Tim Peters6d6c1a32001-08-02 04:15:00 +00003349dict_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
3350{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003351 PyObject *self;
Victor Stinnera9f61a52013-07-16 22:17:26 +02003352 PyDictObject *d;
Tim Peters6d6c1a32001-08-02 04:15:00 +00003353
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003354 assert(type != NULL && type->tp_alloc != NULL);
3355 self = type->tp_alloc(type, 0);
Victor Stinnera9f61a52013-07-16 22:17:26 +02003356 if (self == NULL)
3357 return NULL;
Victor Stinnera9f61a52013-07-16 22:17:26 +02003358 d = (PyDictObject *)self;
Victor Stinnerac2a4fe2013-07-16 22:19:00 +02003359
Victor Stinnera9f61a52013-07-16 22:17:26 +02003360 /* The object has been implicitly tracked by tp_alloc */
3361 if (type == &PyDict_Type)
3362 _PyObject_GC_UNTRACK(d);
Victor Stinnerac2a4fe2013-07-16 22:19:00 +02003363
3364 d->ma_used = 0;
Victor Stinner3b6a6b42016-09-08 12:51:24 -07003365 d->ma_version_tag = DICT_NEXT_VERSION();
Victor Stinner742da042016-09-07 17:40:12 -07003366 d->ma_keys = new_keys_object(PyDict_MINSIZE);
Victor Stinnerac2a4fe2013-07-16 22:19:00 +02003367 if (d->ma_keys == NULL) {
3368 Py_DECREF(self);
3369 return NULL;
3370 }
Victor Stinner0fc91ee2019-04-12 21:51:34 +02003371 ASSERT_CONSISTENT(d);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003372 return self;
Tim Peters6d6c1a32001-08-02 04:15:00 +00003373}
3374
Tim Peters25786c02001-09-02 08:22:48 +00003375static int
3376dict_init(PyObject *self, PyObject *args, PyObject *kwds)
3377{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003378 return dict_update_common(self, args, kwds, "dict");
Tim Peters25786c02001-09-02 08:22:48 +00003379}
3380
Tim Peters6d6c1a32001-08-02 04:15:00 +00003381static PyObject *
Dong-hee Nae27916b2020-04-02 09:55:43 +09003382dict_vectorcall(PyObject *type, PyObject * const*args,
3383 size_t nargsf, PyObject *kwnames)
3384{
3385 assert(PyType_Check(type));
3386 Py_ssize_t nargs = PyVectorcall_NARGS(nargsf);
3387 if (!_PyArg_CheckPositional("dict", nargs, 0, 1)) {
3388 return NULL;
3389 }
3390
3391 PyObject *self = dict_new((PyTypeObject *)type, NULL, NULL);
3392 if (self == NULL) {
3393 return NULL;
3394 }
3395 if (nargs == 1) {
3396 if (dict_update_arg(self, args[0]) < 0) {
3397 Py_DECREF(self);
3398 return NULL;
3399 }
3400 args++;
3401 }
3402 if (kwnames != NULL) {
3403 for (Py_ssize_t i = 0; i < PyTuple_GET_SIZE(kwnames); i++) {
3404 if (PyDict_SetItem(self, PyTuple_GET_ITEM(kwnames, i), args[i]) < 0) {
3405 Py_DECREF(self);
3406 return NULL;
3407 }
3408 }
3409 }
3410 return self;
3411}
3412
3413static PyObject *
Guido van Rossum8ce8a782007-11-01 19:42:39 +00003414dict_iter(PyDictObject *dict)
Guido van Rossum09e563a2001-05-01 12:10:21 +00003415{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003416 return dictiter_new(dict, &PyDictIterKey_Type);
Guido van Rossum09e563a2001-05-01 12:10:21 +00003417}
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003418
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00003419PyDoc_STRVAR(dictionary_doc,
Ezio Melotti7f807b72010-03-01 04:08:34 +00003420"dict() -> new empty dictionary\n"
Tim Petersa427a2b2001-10-29 22:25:45 +00003421"dict(mapping) -> new dictionary initialized from a mapping object's\n"
Ezio Melotti7f807b72010-03-01 04:08:34 +00003422" (key, value) pairs\n"
3423"dict(iterable) -> new dictionary initialized as if via:\n"
Tim Peters4d859532001-10-27 18:27:48 +00003424" d = {}\n"
Ezio Melotti7f807b72010-03-01 04:08:34 +00003425" for k, v in iterable:\n"
Just van Rossuma797d812002-11-23 09:45:04 +00003426" d[k] = v\n"
3427"dict(**kwargs) -> new dictionary initialized with the name=value pairs\n"
3428" in the keyword argument list. For example: dict(one=1, two=2)");
Tim Peters25786c02001-09-02 08:22:48 +00003429
Guido van Rossumc0b618a1997-05-02 03:12:38 +00003430PyTypeObject PyDict_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003431 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3432 "dict",
3433 sizeof(PyDictObject),
3434 0,
3435 (destructor)dict_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003436 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003437 0, /* tp_getattr */
3438 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003439 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003440 (reprfunc)dict_repr, /* tp_repr */
Brandt Buchereb8ac572020-02-24 19:47:34 -08003441 &dict_as_number, /* tp_as_number */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003442 &dict_as_sequence, /* tp_as_sequence */
3443 &dict_as_mapping, /* tp_as_mapping */
Georg Brandl00da4e02010-10-18 07:32:48 +00003444 PyObject_HashNotImplemented, /* tp_hash */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003445 0, /* tp_call */
3446 0, /* tp_str */
3447 PyObject_GenericGetAttr, /* tp_getattro */
3448 0, /* tp_setattro */
3449 0, /* tp_as_buffer */
3450 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC |
3451 Py_TPFLAGS_BASETYPE | Py_TPFLAGS_DICT_SUBCLASS, /* tp_flags */
3452 dictionary_doc, /* tp_doc */
3453 dict_traverse, /* tp_traverse */
3454 dict_tp_clear, /* tp_clear */
3455 dict_richcompare, /* tp_richcompare */
3456 0, /* tp_weaklistoffset */
3457 (getiterfunc)dict_iter, /* tp_iter */
3458 0, /* tp_iternext */
3459 mapp_methods, /* tp_methods */
3460 0, /* tp_members */
3461 0, /* tp_getset */
3462 0, /* tp_base */
3463 0, /* tp_dict */
3464 0, /* tp_descr_get */
3465 0, /* tp_descr_set */
3466 0, /* tp_dictoffset */
3467 dict_init, /* tp_init */
3468 PyType_GenericAlloc, /* tp_alloc */
3469 dict_new, /* tp_new */
3470 PyObject_GC_Del, /* tp_free */
Dong-hee Nae27916b2020-04-02 09:55:43 +09003471 .tp_vectorcall = dict_vectorcall,
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003472};
3473
Victor Stinner3c1e4812012-03-26 22:10:51 +02003474PyObject *
3475_PyDict_GetItemId(PyObject *dp, struct _Py_Identifier *key)
3476{
3477 PyObject *kv;
3478 kv = _PyUnicode_FromId(key); /* borrowed */
Victor Stinner5b3b1002013-07-22 23:50:57 +02003479 if (kv == NULL) {
3480 PyErr_Clear();
Victor Stinner3c1e4812012-03-26 22:10:51 +02003481 return NULL;
Victor Stinner5b3b1002013-07-22 23:50:57 +02003482 }
Victor Stinner3c1e4812012-03-26 22:10:51 +02003483 return PyDict_GetItem(dp, kv);
3484}
3485
Guido van Rossum3cca2451997-05-16 14:23:33 +00003486/* For backward compatibility with old dictionary interface */
3487
Guido van Rossumc0b618a1997-05-02 03:12:38 +00003488PyObject *
Martin v. Löwis32b4a1b2002-12-11 13:21:12 +00003489PyDict_GetItemString(PyObject *v, const char *key)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003490{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003491 PyObject *kv, *rv;
3492 kv = PyUnicode_FromString(key);
Victor Stinnerfdcbab92013-07-16 22:16:05 +02003493 if (kv == NULL) {
3494 PyErr_Clear();
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003495 return NULL;
Victor Stinnerfdcbab92013-07-16 22:16:05 +02003496 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003497 rv = PyDict_GetItem(v, kv);
3498 Py_DECREF(kv);
3499 return rv;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003500}
3501
3502int
Victor Stinner3c1e4812012-03-26 22:10:51 +02003503_PyDict_SetItemId(PyObject *v, struct _Py_Identifier *key, PyObject *item)
3504{
3505 PyObject *kv;
3506 kv = _PyUnicode_FromId(key); /* borrowed */
3507 if (kv == NULL)
3508 return -1;
3509 return PyDict_SetItem(v, kv, item);
3510}
3511
3512int
Martin v. Löwis32b4a1b2002-12-11 13:21:12 +00003513PyDict_SetItemString(PyObject *v, const char *key, PyObject *item)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003514{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003515 PyObject *kv;
3516 int err;
3517 kv = PyUnicode_FromString(key);
3518 if (kv == NULL)
3519 return -1;
3520 PyUnicode_InternInPlace(&kv); /* XXX Should we really? */
3521 err = PyDict_SetItem(v, kv, item);
3522 Py_DECREF(kv);
3523 return err;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003524}
3525
3526int
Victor Stinner5fd2e5a2013-11-06 18:58:22 +01003527_PyDict_DelItemId(PyObject *v, _Py_Identifier *key)
3528{
3529 PyObject *kv = _PyUnicode_FromId(key); /* borrowed */
3530 if (kv == NULL)
3531 return -1;
3532 return PyDict_DelItem(v, kv);
3533}
3534
3535int
Martin v. Löwis32b4a1b2002-12-11 13:21:12 +00003536PyDict_DelItemString(PyObject *v, const char *key)
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003537{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003538 PyObject *kv;
3539 int err;
3540 kv = PyUnicode_FromString(key);
3541 if (kv == NULL)
3542 return -1;
3543 err = PyDict_DelItem(v, kv);
3544 Py_DECREF(kv);
3545 return err;
Guido van Rossum4b1302b1993-03-27 18:11:32 +00003546}
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003547
Raymond Hettinger019a1482004-03-18 02:41:19 +00003548/* Dictionary iterator types */
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003549
3550typedef struct {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003551 PyObject_HEAD
3552 PyDictObject *di_dict; /* Set to NULL when iterator is exhausted */
3553 Py_ssize_t di_used;
3554 Py_ssize_t di_pos;
3555 PyObject* di_result; /* reusable result tuple for iteritems */
3556 Py_ssize_t len;
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003557} dictiterobject;
3558
3559static PyObject *
Guido van Rossum8ce8a782007-11-01 19:42:39 +00003560dictiter_new(PyDictObject *dict, PyTypeObject *itertype)
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003561{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003562 dictiterobject *di;
3563 di = PyObject_GC_New(dictiterobject, itertype);
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003564 if (di == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003565 return NULL;
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003566 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003567 Py_INCREF(dict);
3568 di->di_dict = dict;
3569 di->di_used = dict->ma_used;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003570 di->len = dict->ma_used;
Dong-hee Na24dc2f82019-10-20 05:01:08 +09003571 if (itertype == &PyDictRevIterKey_Type ||
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003572 itertype == &PyDictRevIterItem_Type ||
Dong-hee Na24dc2f82019-10-20 05:01:08 +09003573 itertype == &PyDictRevIterValue_Type) {
3574 if (dict->ma_values) {
3575 di->di_pos = dict->ma_used - 1;
3576 }
3577 else {
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003578 di->di_pos = dict->ma_keys->dk_nentries - 1;
Dong-hee Na24dc2f82019-10-20 05:01:08 +09003579 }
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003580 }
3581 else {
3582 di->di_pos = 0;
3583 }
3584 if (itertype == &PyDictIterItem_Type ||
3585 itertype == &PyDictRevIterItem_Type) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003586 di->di_result = PyTuple_Pack(2, Py_None, Py_None);
3587 if (di->di_result == NULL) {
3588 Py_DECREF(di);
3589 return NULL;
3590 }
3591 }
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003592 else {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003593 di->di_result = NULL;
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003594 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003595 _PyObject_GC_TRACK(di);
3596 return (PyObject *)di;
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003597}
3598
3599static void
3600dictiter_dealloc(dictiterobject *di)
3601{
INADA Naokia6296d32017-08-24 14:55:17 +09003602 /* bpo-31095: UnTrack is needed before calling any callbacks */
3603 _PyObject_GC_UNTRACK(di);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003604 Py_XDECREF(di->di_dict);
3605 Py_XDECREF(di->di_result);
3606 PyObject_GC_Del(di);
Antoine Pitrou7ddda782009-01-01 15:35:33 +00003607}
3608
3609static int
3610dictiter_traverse(dictiterobject *di, visitproc visit, void *arg)
3611{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003612 Py_VISIT(di->di_dict);
3613 Py_VISIT(di->di_result);
3614 return 0;
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003615}
3616
Raymond Hettinger6b27cda2005-09-24 21:23:05 +00003617static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303618dictiter_len(dictiterobject *di, PyObject *Py_UNUSED(ignored))
Raymond Hettinger0ce6dc82004-03-18 08:38:00 +00003619{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003620 Py_ssize_t len = 0;
3621 if (di->di_dict != NULL && di->di_used == di->di_dict->ma_used)
3622 len = di->len;
3623 return PyLong_FromSize_t(len);
Raymond Hettinger0ce6dc82004-03-18 08:38:00 +00003624}
3625
Guido van Rossumb90c8482007-02-10 01:11:45 +00003626PyDoc_STRVAR(length_hint_doc,
3627 "Private method returning an estimate of len(list(it)).");
Raymond Hettinger6b27cda2005-09-24 21:23:05 +00003628
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003629static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05303630dictiter_reduce(dictiterobject *di, PyObject *Py_UNUSED(ignored));
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003631
3632PyDoc_STRVAR(reduce_doc, "Return state information for pickling.");
3633
Raymond Hettinger6b27cda2005-09-24 21:23:05 +00003634static PyMethodDef dictiter_methods[] = {
Serhiy Storchaka62be7422018-11-27 13:27:31 +02003635 {"__length_hint__", (PyCFunction)(void(*)(void))dictiter_len, METH_NOARGS,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003636 length_hint_doc},
Serhiy Storchaka62be7422018-11-27 13:27:31 +02003637 {"__reduce__", (PyCFunction)(void(*)(void))dictiter_reduce, METH_NOARGS,
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003638 reduce_doc},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003639 {NULL, NULL} /* sentinel */
Raymond Hettinger0ce6dc82004-03-18 08:38:00 +00003640};
3641
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003642static PyObject*
3643dictiter_iternextkey(dictiterobject *di)
Guido van Rossum213c7a62001-04-23 14:08:49 +00003644{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003645 PyObject *key;
INADA Naokica2d8be2016-11-04 16:59:10 +09003646 Py_ssize_t i;
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02003647 PyDictKeysObject *k;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003648 PyDictObject *d = di->di_dict;
Guido van Rossum213c7a62001-04-23 14:08:49 +00003649
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003650 if (d == NULL)
3651 return NULL;
3652 assert (PyDict_Check(d));
Guido van Rossum2147df72002-07-16 20:30:22 +00003653
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003654 if (di->di_used != d->ma_used) {
3655 PyErr_SetString(PyExc_RuntimeError,
3656 "dictionary changed size during iteration");
3657 di->di_used = -1; /* Make this state sticky */
3658 return NULL;
3659 }
Guido van Rossum2147df72002-07-16 20:30:22 +00003660
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003661 i = di->di_pos;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003662 k = d->ma_keys;
INADA Naokica2d8be2016-11-04 16:59:10 +09003663 assert(i >= 0);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003664 if (d->ma_values) {
INADA Naokica2d8be2016-11-04 16:59:10 +09003665 if (i >= d->ma_used)
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003666 goto fail;
3667 key = DK_ENTRIES(k)[i].me_key;
INADA Naokica2d8be2016-11-04 16:59:10 +09003668 assert(d->ma_values[i] != NULL);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003669 }
3670 else {
INADA Naokica2d8be2016-11-04 16:59:10 +09003671 Py_ssize_t n = k->dk_nentries;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003672 PyDictKeyEntry *entry_ptr = &DK_ENTRIES(k)[i];
3673 while (i < n && entry_ptr->me_value == NULL) {
3674 entry_ptr++;
3675 i++;
3676 }
3677 if (i >= n)
3678 goto fail;
3679 key = entry_ptr->me_key;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003680 }
Thomas Perl796cc6e2019-03-28 07:03:25 +01003681 // We found an element (key), but did not expect it
3682 if (di->len == 0) {
3683 PyErr_SetString(PyExc_RuntimeError,
3684 "dictionary keys changed during iteration");
3685 goto fail;
3686 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003687 di->di_pos = i+1;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003688 di->len--;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003689 Py_INCREF(key);
3690 return key;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003691
3692fail:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003693 di->di_dict = NULL;
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +03003694 Py_DECREF(d);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003695 return NULL;
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003696}
3697
Raymond Hettinger019a1482004-03-18 02:41:19 +00003698PyTypeObject PyDictIterKey_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003699 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3700 "dict_keyiterator", /* tp_name */
3701 sizeof(dictiterobject), /* tp_basicsize */
3702 0, /* tp_itemsize */
3703 /* methods */
3704 (destructor)dictiter_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003705 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003706 0, /* tp_getattr */
3707 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003708 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003709 0, /* tp_repr */
3710 0, /* tp_as_number */
3711 0, /* tp_as_sequence */
3712 0, /* tp_as_mapping */
3713 0, /* tp_hash */
3714 0, /* tp_call */
3715 0, /* tp_str */
3716 PyObject_GenericGetAttr, /* tp_getattro */
3717 0, /* tp_setattro */
3718 0, /* tp_as_buffer */
3719 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */
3720 0, /* tp_doc */
3721 (traverseproc)dictiter_traverse, /* tp_traverse */
3722 0, /* tp_clear */
3723 0, /* tp_richcompare */
3724 0, /* tp_weaklistoffset */
3725 PyObject_SelfIter, /* tp_iter */
3726 (iternextfunc)dictiter_iternextkey, /* tp_iternext */
3727 dictiter_methods, /* tp_methods */
3728 0,
Raymond Hettinger019a1482004-03-18 02:41:19 +00003729};
3730
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003731static PyObject *
3732dictiter_iternextvalue(dictiterobject *di)
Raymond Hettinger019a1482004-03-18 02:41:19 +00003733{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003734 PyObject *value;
INADA Naokica2d8be2016-11-04 16:59:10 +09003735 Py_ssize_t i;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003736 PyDictObject *d = di->di_dict;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003737
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003738 if (d == NULL)
3739 return NULL;
3740 assert (PyDict_Check(d));
Raymond Hettinger019a1482004-03-18 02:41:19 +00003741
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003742 if (di->di_used != d->ma_used) {
3743 PyErr_SetString(PyExc_RuntimeError,
3744 "dictionary changed size during iteration");
3745 di->di_used = -1; /* Make this state sticky */
3746 return NULL;
3747 }
Raymond Hettinger019a1482004-03-18 02:41:19 +00003748
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003749 i = di->di_pos;
INADA Naokica2d8be2016-11-04 16:59:10 +09003750 assert(i >= 0);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003751 if (d->ma_values) {
INADA Naokica2d8be2016-11-04 16:59:10 +09003752 if (i >= d->ma_used)
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003753 goto fail;
INADA Naokica2d8be2016-11-04 16:59:10 +09003754 value = d->ma_values[i];
3755 assert(value != NULL);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003756 }
3757 else {
INADA Naokica2d8be2016-11-04 16:59:10 +09003758 Py_ssize_t n = d->ma_keys->dk_nentries;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003759 PyDictKeyEntry *entry_ptr = &DK_ENTRIES(d->ma_keys)[i];
3760 while (i < n && entry_ptr->me_value == NULL) {
3761 entry_ptr++;
3762 i++;
3763 }
3764 if (i >= n)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003765 goto fail;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003766 value = entry_ptr->me_value;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003767 }
Thomas Perlb8311cf2019-04-02 11:30:10 +02003768 // We found an element, but did not expect it
3769 if (di->len == 0) {
3770 PyErr_SetString(PyExc_RuntimeError,
3771 "dictionary keys changed during iteration");
3772 goto fail;
3773 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003774 di->di_pos = i+1;
3775 di->len--;
3776 Py_INCREF(value);
3777 return value;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003778
3779fail:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003780 di->di_dict = NULL;
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +03003781 Py_DECREF(d);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003782 return NULL;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003783}
3784
3785PyTypeObject PyDictIterValue_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003786 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3787 "dict_valueiterator", /* tp_name */
3788 sizeof(dictiterobject), /* tp_basicsize */
3789 0, /* tp_itemsize */
3790 /* methods */
3791 (destructor)dictiter_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003792 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003793 0, /* tp_getattr */
3794 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003795 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003796 0, /* tp_repr */
3797 0, /* tp_as_number */
3798 0, /* tp_as_sequence */
3799 0, /* tp_as_mapping */
3800 0, /* tp_hash */
3801 0, /* tp_call */
3802 0, /* tp_str */
3803 PyObject_GenericGetAttr, /* tp_getattro */
3804 0, /* tp_setattro */
3805 0, /* tp_as_buffer */
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003806 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003807 0, /* tp_doc */
3808 (traverseproc)dictiter_traverse, /* tp_traverse */
3809 0, /* tp_clear */
3810 0, /* tp_richcompare */
3811 0, /* tp_weaklistoffset */
3812 PyObject_SelfIter, /* tp_iter */
3813 (iternextfunc)dictiter_iternextvalue, /* tp_iternext */
3814 dictiter_methods, /* tp_methods */
3815 0,
Raymond Hettinger019a1482004-03-18 02:41:19 +00003816};
3817
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003818static PyObject *
3819dictiter_iternextitem(dictiterobject *di)
Raymond Hettinger019a1482004-03-18 02:41:19 +00003820{
Serhiy Storchaka753bca32017-05-20 12:30:02 +03003821 PyObject *key, *value, *result;
INADA Naokica2d8be2016-11-04 16:59:10 +09003822 Py_ssize_t i;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003823 PyDictObject *d = di->di_dict;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003824
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003825 if (d == NULL)
3826 return NULL;
3827 assert (PyDict_Check(d));
Raymond Hettinger019a1482004-03-18 02:41:19 +00003828
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003829 if (di->di_used != d->ma_used) {
3830 PyErr_SetString(PyExc_RuntimeError,
3831 "dictionary changed size during iteration");
3832 di->di_used = -1; /* Make this state sticky */
3833 return NULL;
3834 }
Raymond Hettinger019a1482004-03-18 02:41:19 +00003835
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003836 i = di->di_pos;
INADA Naokica2d8be2016-11-04 16:59:10 +09003837 assert(i >= 0);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003838 if (d->ma_values) {
INADA Naokica2d8be2016-11-04 16:59:10 +09003839 if (i >= d->ma_used)
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003840 goto fail;
3841 key = DK_ENTRIES(d->ma_keys)[i].me_key;
INADA Naokica2d8be2016-11-04 16:59:10 +09003842 value = d->ma_values[i];
3843 assert(value != NULL);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003844 }
3845 else {
INADA Naokica2d8be2016-11-04 16:59:10 +09003846 Py_ssize_t n = d->ma_keys->dk_nentries;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003847 PyDictKeyEntry *entry_ptr = &DK_ENTRIES(d->ma_keys)[i];
3848 while (i < n && entry_ptr->me_value == NULL) {
3849 entry_ptr++;
3850 i++;
3851 }
3852 if (i >= n)
3853 goto fail;
3854 key = entry_ptr->me_key;
3855 value = entry_ptr->me_value;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04003856 }
Thomas Perlb8311cf2019-04-02 11:30:10 +02003857 // We found an element, but did not expect it
3858 if (di->len == 0) {
3859 PyErr_SetString(PyExc_RuntimeError,
3860 "dictionary keys changed during iteration");
3861 goto fail;
3862 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003863 di->di_pos = i+1;
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003864 di->len--;
Serhiy Storchaka753bca32017-05-20 12:30:02 +03003865 Py_INCREF(key);
3866 Py_INCREF(value);
3867 result = di->di_result;
3868 if (Py_REFCNT(result) == 1) {
3869 PyObject *oldkey = PyTuple_GET_ITEM(result, 0);
3870 PyObject *oldvalue = PyTuple_GET_ITEM(result, 1);
3871 PyTuple_SET_ITEM(result, 0, key); /* steals reference */
3872 PyTuple_SET_ITEM(result, 1, value); /* steals reference */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003873 Py_INCREF(result);
Serhiy Storchaka753bca32017-05-20 12:30:02 +03003874 Py_DECREF(oldkey);
3875 Py_DECREF(oldvalue);
Serhiy Storchaka49f5cdd2016-10-09 23:08:05 +03003876 }
3877 else {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003878 result = PyTuple_New(2);
3879 if (result == NULL)
3880 return NULL;
Serhiy Storchaka753bca32017-05-20 12:30:02 +03003881 PyTuple_SET_ITEM(result, 0, key); /* steals reference */
3882 PyTuple_SET_ITEM(result, 1, value); /* steals reference */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003883 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003884 return result;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003885
3886fail:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003887 di->di_dict = NULL;
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +03003888 Py_DECREF(d);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003889 return NULL;
Raymond Hettinger019a1482004-03-18 02:41:19 +00003890}
3891
3892PyTypeObject PyDictIterItem_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003893 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3894 "dict_itemiterator", /* tp_name */
3895 sizeof(dictiterobject), /* tp_basicsize */
3896 0, /* tp_itemsize */
3897 /* methods */
3898 (destructor)dictiter_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003899 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003900 0, /* tp_getattr */
3901 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02003902 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003903 0, /* tp_repr */
3904 0, /* tp_as_number */
3905 0, /* tp_as_sequence */
3906 0, /* tp_as_mapping */
3907 0, /* tp_hash */
3908 0, /* tp_call */
3909 0, /* tp_str */
3910 PyObject_GenericGetAttr, /* tp_getattro */
3911 0, /* tp_setattro */
3912 0, /* tp_as_buffer */
3913 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */
3914 0, /* tp_doc */
3915 (traverseproc)dictiter_traverse, /* tp_traverse */
3916 0, /* tp_clear */
3917 0, /* tp_richcompare */
3918 0, /* tp_weaklistoffset */
3919 PyObject_SelfIter, /* tp_iter */
3920 (iternextfunc)dictiter_iternextitem, /* tp_iternext */
3921 dictiter_methods, /* tp_methods */
3922 0,
Guido van Rossum59d1d2b2001-04-20 19:13:02 +00003923};
Guido van Rossumb90c8482007-02-10 01:11:45 +00003924
3925
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003926/* dictreviter */
3927
3928static PyObject *
3929dictreviter_iternext(dictiterobject *di)
3930{
3931 PyDictObject *d = di->di_dict;
3932
3933 if (d == NULL) {
3934 return NULL;
3935 }
3936 assert (PyDict_Check(d));
3937
3938 if (di->di_used != d->ma_used) {
3939 PyErr_SetString(PyExc_RuntimeError,
3940 "dictionary changed size during iteration");
3941 di->di_used = -1; /* Make this state sticky */
3942 return NULL;
3943 }
3944
3945 Py_ssize_t i = di->di_pos;
3946 PyDictKeysObject *k = d->ma_keys;
3947 PyObject *key, *value, *result;
3948
Serhiy Storchaka2e3d8732019-10-23 14:48:08 +03003949 if (i < 0) {
3950 goto fail;
3951 }
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003952 if (d->ma_values) {
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003953 key = DK_ENTRIES(k)[i].me_key;
3954 value = d->ma_values[i];
3955 assert (value != NULL);
3956 }
3957 else {
3958 PyDictKeyEntry *entry_ptr = &DK_ENTRIES(k)[i];
Serhiy Storchaka2e3d8732019-10-23 14:48:08 +03003959 while (entry_ptr->me_value == NULL) {
3960 if (--i < 0) {
3961 goto fail;
3962 }
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003963 entry_ptr--;
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003964 }
3965 key = entry_ptr->me_key;
3966 value = entry_ptr->me_value;
3967 }
3968 di->di_pos = i-1;
3969 di->len--;
3970
Dong-hee Na1b55b652020-02-17 19:09:15 +09003971 if (Py_IS_TYPE(di, &PyDictRevIterKey_Type)) {
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003972 Py_INCREF(key);
3973 return key;
3974 }
Dong-hee Na1b55b652020-02-17 19:09:15 +09003975 else if (Py_IS_TYPE(di, &PyDictRevIterValue_Type)) {
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003976 Py_INCREF(value);
3977 return value;
3978 }
Dong-hee Na1b55b652020-02-17 19:09:15 +09003979 else if (Py_IS_TYPE(di, &PyDictRevIterItem_Type)) {
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01003980 Py_INCREF(key);
3981 Py_INCREF(value);
3982 result = di->di_result;
3983 if (Py_REFCNT(result) == 1) {
3984 PyObject *oldkey = PyTuple_GET_ITEM(result, 0);
3985 PyObject *oldvalue = PyTuple_GET_ITEM(result, 1);
3986 PyTuple_SET_ITEM(result, 0, key); /* steals reference */
3987 PyTuple_SET_ITEM(result, 1, value); /* steals reference */
3988 Py_INCREF(result);
3989 Py_DECREF(oldkey);
3990 Py_DECREF(oldvalue);
3991 }
3992 else {
3993 result = PyTuple_New(2);
3994 if (result == NULL) {
3995 return NULL;
3996 }
3997 PyTuple_SET_ITEM(result, 0, key); /* steals reference */
3998 PyTuple_SET_ITEM(result, 1, value); /* steals reference */
3999 }
4000 return result;
4001 }
4002 else {
4003 Py_UNREACHABLE();
4004 }
4005
4006fail:
4007 di->di_dict = NULL;
4008 Py_DECREF(d);
4009 return NULL;
4010}
4011
4012PyTypeObject PyDictRevIterKey_Type = {
4013 PyVarObject_HEAD_INIT(&PyType_Type, 0)
4014 "dict_reversekeyiterator",
4015 sizeof(dictiterobject),
4016 .tp_dealloc = (destructor)dictiter_dealloc,
4017 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,
4018 .tp_traverse = (traverseproc)dictiter_traverse,
4019 .tp_iter = PyObject_SelfIter,
4020 .tp_iternext = (iternextfunc)dictreviter_iternext,
4021 .tp_methods = dictiter_methods
4022};
4023
4024
4025/*[clinic input]
4026dict.__reversed__
4027
4028Return a reverse iterator over the dict keys.
4029[clinic start generated code]*/
4030
4031static PyObject *
4032dict___reversed___impl(PyDictObject *self)
4033/*[clinic end generated code: output=e674483336d1ed51 input=23210ef3477d8c4d]*/
4034{
4035 assert (PyDict_Check(self));
4036 return dictiter_new(self, &PyDictRevIterKey_Type);
4037}
4038
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00004039static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05304040dictiter_reduce(dictiterobject *di, PyObject *Py_UNUSED(ignored))
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00004041{
Serhiy Storchakabb86bf42018-12-11 08:28:18 +02004042 _Py_IDENTIFIER(iter);
Sergey Fedoseev63958442018-10-20 05:43:33 +05004043 /* copy the iterator state */
4044 dictiterobject tmp = *di;
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00004045 Py_XINCREF(tmp.di_dict);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004046
Sergey Fedoseev63958442018-10-20 05:43:33 +05004047 PyObject *list = PySequence_List((PyObject*)&tmp);
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00004048 Py_XDECREF(tmp.di_dict);
Sergey Fedoseev63958442018-10-20 05:43:33 +05004049 if (list == NULL) {
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00004050 return NULL;
4051 }
Serhiy Storchakabb86bf42018-12-11 08:28:18 +02004052 return Py_BuildValue("N(N)", _PyEval_GetBuiltinId(&PyId_iter), list);
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00004053}
4054
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004055PyTypeObject PyDictRevIterItem_Type = {
4056 PyVarObject_HEAD_INIT(&PyType_Type, 0)
4057 "dict_reverseitemiterator",
4058 sizeof(dictiterobject),
4059 .tp_dealloc = (destructor)dictiter_dealloc,
4060 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,
4061 .tp_traverse = (traverseproc)dictiter_traverse,
4062 .tp_iter = PyObject_SelfIter,
4063 .tp_iternext = (iternextfunc)dictreviter_iternext,
4064 .tp_methods = dictiter_methods
4065};
4066
4067PyTypeObject PyDictRevIterValue_Type = {
4068 PyVarObject_HEAD_INIT(&PyType_Type, 0)
4069 "dict_reversevalueiterator",
4070 sizeof(dictiterobject),
4071 .tp_dealloc = (destructor)dictiter_dealloc,
4072 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,
4073 .tp_traverse = (traverseproc)dictiter_traverse,
4074 .tp_iter = PyObject_SelfIter,
4075 .tp_iternext = (iternextfunc)dictreviter_iternext,
4076 .tp_methods = dictiter_methods
4077};
4078
Guido van Rossum3ac67412007-02-10 18:55:06 +00004079/***********************************************/
Guido van Rossumb90c8482007-02-10 01:11:45 +00004080/* View objects for keys(), items(), values(). */
Guido van Rossum3ac67412007-02-10 18:55:06 +00004081/***********************************************/
4082
Guido van Rossumb90c8482007-02-10 01:11:45 +00004083/* The instance lay-out is the same for all three; but the type differs. */
4084
Guido van Rossumb90c8482007-02-10 01:11:45 +00004085static void
Eric Snow96c6af92015-05-29 22:21:39 -06004086dictview_dealloc(_PyDictViewObject *dv)
Guido van Rossumb90c8482007-02-10 01:11:45 +00004087{
INADA Naokia6296d32017-08-24 14:55:17 +09004088 /* bpo-31095: UnTrack is needed before calling any callbacks */
4089 _PyObject_GC_UNTRACK(dv);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004090 Py_XDECREF(dv->dv_dict);
4091 PyObject_GC_Del(dv);
Antoine Pitrou7ddda782009-01-01 15:35:33 +00004092}
4093
4094static int
Eric Snow96c6af92015-05-29 22:21:39 -06004095dictview_traverse(_PyDictViewObject *dv, visitproc visit, void *arg)
Antoine Pitrou7ddda782009-01-01 15:35:33 +00004096{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004097 Py_VISIT(dv->dv_dict);
4098 return 0;
Guido van Rossumb90c8482007-02-10 01:11:45 +00004099}
4100
Guido van Rossum83825ac2007-02-10 04:54:19 +00004101static Py_ssize_t
Eric Snow96c6af92015-05-29 22:21:39 -06004102dictview_len(_PyDictViewObject *dv)
Guido van Rossumb90c8482007-02-10 01:11:45 +00004103{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004104 Py_ssize_t len = 0;
4105 if (dv->dv_dict != NULL)
4106 len = dv->dv_dict->ma_used;
4107 return len;
Guido van Rossumb90c8482007-02-10 01:11:45 +00004108}
4109
Eric Snow96c6af92015-05-29 22:21:39 -06004110PyObject *
4111_PyDictView_New(PyObject *dict, PyTypeObject *type)
Guido van Rossumb90c8482007-02-10 01:11:45 +00004112{
Eric Snow96c6af92015-05-29 22:21:39 -06004113 _PyDictViewObject *dv;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004114 if (dict == NULL) {
4115 PyErr_BadInternalCall();
4116 return NULL;
4117 }
4118 if (!PyDict_Check(dict)) {
4119 /* XXX Get rid of this restriction later */
4120 PyErr_Format(PyExc_TypeError,
4121 "%s() requires a dict argument, not '%s'",
Victor Stinner58ac7002020-02-07 03:04:21 +01004122 type->tp_name, Py_TYPE(dict)->tp_name);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004123 return NULL;
4124 }
Eric Snow96c6af92015-05-29 22:21:39 -06004125 dv = PyObject_GC_New(_PyDictViewObject, type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004126 if (dv == NULL)
4127 return NULL;
4128 Py_INCREF(dict);
4129 dv->dv_dict = (PyDictObject *)dict;
4130 _PyObject_GC_TRACK(dv);
4131 return (PyObject *)dv;
Guido van Rossumb90c8482007-02-10 01:11:45 +00004132}
4133
Dennis Sweeney3ee0e482020-06-12 13:19:25 -04004134static PyObject *
Pablo Galindo10c3b212020-06-15 02:05:20 +01004135dictview_mapping(PyObject *view, void *Py_UNUSED(ignored)) {
Dennis Sweeney3ee0e482020-06-12 13:19:25 -04004136 assert(view != NULL);
4137 assert(PyDictKeys_Check(view)
4138 || PyDictValues_Check(view)
4139 || PyDictItems_Check(view));
4140 PyObject *mapping = (PyObject *)((_PyDictViewObject *)view)->dv_dict;
4141 return PyDictProxy_New(mapping);
4142}
4143
4144static PyGetSetDef dictview_getset[] = {
Pablo Galindo10c3b212020-06-15 02:05:20 +01004145 {"mapping", dictview_mapping, (setter)NULL,
Dennis Sweeney3ee0e482020-06-12 13:19:25 -04004146 "dictionary that this view refers to", NULL},
4147 {0}
4148};
4149
Neal Norwitze36f2ba2007-02-26 23:12:28 +00004150/* TODO(guido): The views objects are not complete:
4151
4152 * support more set operations
4153 * support arbitrary mappings?
4154 - either these should be static or exported in dictobject.h
4155 - if public then they should probably be in builtins
4156*/
4157
Guido van Rossumaac530c2007-08-24 22:33:45 +00004158/* Return 1 if self is a subset of other, iterating over self;
4159 0 if not; -1 if an error occurred. */
Guido van Rossumd9214d12007-02-12 02:23:40 +00004160static int
4161all_contained_in(PyObject *self, PyObject *other)
4162{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004163 PyObject *iter = PyObject_GetIter(self);
4164 int ok = 1;
Guido van Rossumd9214d12007-02-12 02:23:40 +00004165
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004166 if (iter == NULL)
4167 return -1;
4168 for (;;) {
4169 PyObject *next = PyIter_Next(iter);
4170 if (next == NULL) {
4171 if (PyErr_Occurred())
4172 ok = -1;
4173 break;
4174 }
4175 ok = PySequence_Contains(other, next);
4176 Py_DECREF(next);
4177 if (ok <= 0)
4178 break;
4179 }
4180 Py_DECREF(iter);
4181 return ok;
Guido van Rossumd9214d12007-02-12 02:23:40 +00004182}
4183
4184static PyObject *
4185dictview_richcompare(PyObject *self, PyObject *other, int op)
4186{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004187 Py_ssize_t len_self, len_other;
4188 int ok;
4189 PyObject *result;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004190
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004191 assert(self != NULL);
4192 assert(PyDictViewSet_Check(self));
4193 assert(other != NULL);
Guido van Rossumd9214d12007-02-12 02:23:40 +00004194
Brian Curtindfc80e32011-08-10 20:28:54 -05004195 if (!PyAnySet_Check(other) && !PyDictViewSet_Check(other))
4196 Py_RETURN_NOTIMPLEMENTED;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004197
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004198 len_self = PyObject_Size(self);
4199 if (len_self < 0)
4200 return NULL;
4201 len_other = PyObject_Size(other);
4202 if (len_other < 0)
4203 return NULL;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004204
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004205 ok = 0;
4206 switch(op) {
Guido van Rossumaac530c2007-08-24 22:33:45 +00004207
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004208 case Py_NE:
4209 case Py_EQ:
4210 if (len_self == len_other)
4211 ok = all_contained_in(self, other);
4212 if (op == Py_NE && ok >= 0)
4213 ok = !ok;
4214 break;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004215
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004216 case Py_LT:
4217 if (len_self < len_other)
4218 ok = all_contained_in(self, other);
4219 break;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004220
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004221 case Py_LE:
4222 if (len_self <= len_other)
4223 ok = all_contained_in(self, other);
4224 break;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004225
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004226 case Py_GT:
4227 if (len_self > len_other)
4228 ok = all_contained_in(other, self);
4229 break;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004230
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004231 case Py_GE:
4232 if (len_self >= len_other)
4233 ok = all_contained_in(other, self);
4234 break;
Guido van Rossumaac530c2007-08-24 22:33:45 +00004235
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004236 }
4237 if (ok < 0)
4238 return NULL;
4239 result = ok ? Py_True : Py_False;
4240 Py_INCREF(result);
4241 return result;
Guido van Rossumd9214d12007-02-12 02:23:40 +00004242}
4243
Raymond Hettingerb0d56af2009-03-03 10:52:49 +00004244static PyObject *
Eric Snow96c6af92015-05-29 22:21:39 -06004245dictview_repr(_PyDictViewObject *dv)
Raymond Hettingerb0d56af2009-03-03 10:52:49 +00004246{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004247 PyObject *seq;
bennorthd7773d92018-01-26 15:46:01 +00004248 PyObject *result = NULL;
4249 Py_ssize_t rc;
Raymond Hettingerb0d56af2009-03-03 10:52:49 +00004250
bennorthd7773d92018-01-26 15:46:01 +00004251 rc = Py_ReprEnter((PyObject *)dv);
4252 if (rc != 0) {
4253 return rc > 0 ? PyUnicode_FromString("...") : NULL;
4254 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004255 seq = PySequence_List((PyObject *)dv);
bennorthd7773d92018-01-26 15:46:01 +00004256 if (seq == NULL) {
4257 goto Done;
4258 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004259 result = PyUnicode_FromFormat("%s(%R)", Py_TYPE(dv)->tp_name, seq);
4260 Py_DECREF(seq);
bennorthd7773d92018-01-26 15:46:01 +00004261
4262Done:
4263 Py_ReprLeave((PyObject *)dv);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004264 return result;
Raymond Hettingerb0d56af2009-03-03 10:52:49 +00004265}
4266
Guido van Rossum3ac67412007-02-10 18:55:06 +00004267/*** dict_keys ***/
Guido van Rossumb90c8482007-02-10 01:11:45 +00004268
4269static PyObject *
Eric Snow96c6af92015-05-29 22:21:39 -06004270dictkeys_iter(_PyDictViewObject *dv)
Guido van Rossumb90c8482007-02-10 01:11:45 +00004271{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004272 if (dv->dv_dict == NULL) {
4273 Py_RETURN_NONE;
4274 }
4275 return dictiter_new(dv->dv_dict, &PyDictIterKey_Type);
Guido van Rossum3ac67412007-02-10 18:55:06 +00004276}
4277
4278static int
Eric Snow96c6af92015-05-29 22:21:39 -06004279dictkeys_contains(_PyDictViewObject *dv, PyObject *obj)
Guido van Rossum3ac67412007-02-10 18:55:06 +00004280{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004281 if (dv->dv_dict == NULL)
4282 return 0;
4283 return PyDict_Contains((PyObject *)dv->dv_dict, obj);
Guido van Rossumb90c8482007-02-10 01:11:45 +00004284}
4285
Guido van Rossum83825ac2007-02-10 04:54:19 +00004286static PySequenceMethods dictkeys_as_sequence = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004287 (lenfunc)dictview_len, /* sq_length */
4288 0, /* sq_concat */
4289 0, /* sq_repeat */
4290 0, /* sq_item */
4291 0, /* sq_slice */
4292 0, /* sq_ass_item */
4293 0, /* sq_ass_slice */
4294 (objobjproc)dictkeys_contains, /* sq_contains */
Guido van Rossum83825ac2007-02-10 04:54:19 +00004295};
4296
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004297// Create an set object from dictviews object.
4298// Returns a new reference.
4299// This utility function is used by set operations.
Guido van Rossum523259b2007-08-24 23:41:22 +00004300static PyObject*
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004301dictviews_to_set(PyObject *self)
Guido van Rossum523259b2007-08-24 23:41:22 +00004302{
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004303 PyObject *left = self;
4304 if (PyDictKeys_Check(self)) {
4305 // PySet_New() has fast path for the dict object.
4306 PyObject *dict = (PyObject *)((_PyDictViewObject *)self)->dv_dict;
4307 if (PyDict_CheckExact(dict)) {
4308 left = dict;
4309 }
4310 }
4311 return PySet_New(left);
4312}
Martin v. Löwisafe55bb2011-10-09 10:38:36 +02004313
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004314static PyObject*
4315dictviews_sub(PyObject *self, PyObject *other)
4316{
4317 PyObject *result = dictviews_to_set(self);
4318 if (result == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004319 return NULL;
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004320 }
Guido van Rossum523259b2007-08-24 23:41:22 +00004321
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004322 _Py_IDENTIFIER(difference_update);
4323 PyObject *tmp = _PyObject_CallMethodIdOneArg(
4324 result, &PyId_difference_update, other);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004325 if (tmp == NULL) {
4326 Py_DECREF(result);
4327 return NULL;
4328 }
Guido van Rossum523259b2007-08-24 23:41:22 +00004329
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004330 Py_DECREF(tmp);
4331 return result;
Guido van Rossum523259b2007-08-24 23:41:22 +00004332}
4333
Forest Gregg998cf1f2019-08-26 02:17:43 -05004334static int
4335dictitems_contains(_PyDictViewObject *dv, PyObject *obj);
4336
4337PyObject *
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04004338_PyDictView_Intersect(PyObject* self, PyObject *other)
Guido van Rossum523259b2007-08-24 23:41:22 +00004339{
Forest Gregg998cf1f2019-08-26 02:17:43 -05004340 PyObject *result;
4341 PyObject *it;
4342 PyObject *key;
4343 Py_ssize_t len_self;
4344 int rv;
4345 int (*dict_contains)(_PyDictViewObject *, PyObject *);
Martin v. Löwisafe55bb2011-10-09 10:38:36 +02004346
Forest Gregg998cf1f2019-08-26 02:17:43 -05004347 /* Python interpreter swaps parameters when dict view
4348 is on right side of & */
4349 if (!PyDictViewSet_Check(self)) {
4350 PyObject *tmp = other;
4351 other = self;
4352 self = tmp;
4353 }
4354
4355 len_self = dictview_len((_PyDictViewObject *)self);
4356
4357 /* if other is a set and self is smaller than other,
4358 reuse set intersection logic */
Dong-hee Na1b55b652020-02-17 19:09:15 +09004359 if (Py_IS_TYPE(other, &PySet_Type) && len_self <= PyObject_Size(other)) {
Forest Gregg998cf1f2019-08-26 02:17:43 -05004360 _Py_IDENTIFIER(intersection);
4361 return _PyObject_CallMethodIdObjArgs(other, &PyId_intersection, self, NULL);
4362 }
4363
4364 /* if other is another dict view, and it is bigger than self,
4365 swap them */
4366 if (PyDictViewSet_Check(other)) {
4367 Py_ssize_t len_other = dictview_len((_PyDictViewObject *)other);
4368 if (len_other > len_self) {
4369 PyObject *tmp = other;
4370 other = self;
4371 self = tmp;
4372 }
4373 }
4374
4375 /* at this point, two things should be true
4376 1. self is a dictview
4377 2. if other is a dictview then it is smaller than self */
4378 result = PySet_New(NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004379 if (result == NULL)
4380 return NULL;
Guido van Rossum523259b2007-08-24 23:41:22 +00004381
Forest Gregg998cf1f2019-08-26 02:17:43 -05004382 it = PyObject_GetIter(other);
Zackery Spytzb16e3822019-10-13 05:49:05 -06004383 if (it == NULL) {
4384 Py_DECREF(result);
4385 return NULL;
4386 }
Forest Gregg998cf1f2019-08-26 02:17:43 -05004387
Forest Gregg998cf1f2019-08-26 02:17:43 -05004388 if (PyDictKeys_Check(self)) {
4389 dict_contains = dictkeys_contains;
4390 }
4391 /* else PyDictItems_Check(self) */
4392 else {
4393 dict_contains = dictitems_contains;
4394 }
4395
4396 while ((key = PyIter_Next(it)) != NULL) {
4397 rv = dict_contains((_PyDictViewObject *)self, key);
4398 if (rv < 0) {
4399 goto error;
4400 }
4401 if (rv) {
4402 if (PySet_Add(result, key)) {
4403 goto error;
4404 }
4405 }
4406 Py_DECREF(key);
4407 }
4408 Py_DECREF(it);
4409 if (PyErr_Occurred()) {
4410 Py_DECREF(result);
4411 return NULL;
4412 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004413 return result;
Forest Gregg998cf1f2019-08-26 02:17:43 -05004414
4415error:
4416 Py_DECREF(it);
4417 Py_DECREF(result);
4418 Py_DECREF(key);
4419 return NULL;
Guido van Rossum523259b2007-08-24 23:41:22 +00004420}
4421
4422static PyObject*
4423dictviews_or(PyObject* self, PyObject *other)
4424{
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004425 PyObject *result = dictviews_to_set(self);
4426 if (result == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004427 return NULL;
4428 }
Guido van Rossum523259b2007-08-24 23:41:22 +00004429
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004430 if (_PySet_Update(result, other) < 0) {
4431 Py_DECREF(result);
4432 return NULL;
4433 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004434 return result;
Guido van Rossum523259b2007-08-24 23:41:22 +00004435}
4436
Dennis Sweeney07d81122020-06-10 01:56:56 -04004437static PyObject *
4438dictitems_xor(PyObject *self, PyObject *other)
4439{
4440 assert(PyDictItems_Check(self));
4441 assert(PyDictItems_Check(other));
4442 PyObject *d1 = (PyObject *)((_PyDictViewObject *)self)->dv_dict;
4443 PyObject *d2 = (PyObject *)((_PyDictViewObject *)other)->dv_dict;
4444
4445 PyObject *temp_dict = PyDict_Copy(d1);
4446 if (temp_dict == NULL) {
4447 return NULL;
4448 }
4449 PyObject *result_set = PySet_New(NULL);
4450 if (result_set == NULL) {
4451 Py_CLEAR(temp_dict);
4452 return NULL;
4453 }
4454
4455 PyObject *key = NULL, *val1 = NULL, *val2 = NULL;
4456 Py_ssize_t pos = 0;
4457 Py_hash_t hash;
4458
4459 while (_PyDict_Next(d2, &pos, &key, &val2, &hash)) {
4460 Py_INCREF(key);
4461 Py_INCREF(val2);
4462 val1 = _PyDict_GetItem_KnownHash(temp_dict, key, hash);
4463
4464 int to_delete;
4465 if (val1 == NULL) {
4466 if (PyErr_Occurred()) {
4467 goto error;
4468 }
4469 to_delete = 0;
4470 }
4471 else {
4472 Py_INCREF(val1);
4473 to_delete = PyObject_RichCompareBool(val1, val2, Py_EQ);
4474 if (to_delete < 0) {
4475 goto error;
4476 }
4477 }
4478
4479 if (to_delete) {
4480 if (_PyDict_DelItem_KnownHash(temp_dict, key, hash) < 0) {
4481 goto error;
4482 }
4483 }
4484 else {
4485 PyObject *pair = PyTuple_Pack(2, key, val2);
4486 if (pair == NULL) {
4487 goto error;
4488 }
4489 if (PySet_Add(result_set, pair) < 0) {
4490 Py_DECREF(pair);
4491 goto error;
4492 }
4493 Py_DECREF(pair);
4494 }
4495 Py_DECREF(key);
4496 Py_XDECREF(val1);
4497 Py_DECREF(val2);
4498 }
4499 key = val1 = val2 = NULL;
4500
4501 _Py_IDENTIFIER(items);
4502 PyObject *remaining_pairs = _PyObject_CallMethodIdNoArgs(temp_dict,
4503 &PyId_items);
4504 if (remaining_pairs == NULL) {
4505 goto error;
4506 }
4507 if (_PySet_Update(result_set, remaining_pairs) < 0) {
4508 Py_DECREF(remaining_pairs);
4509 goto error;
4510 }
4511 Py_DECREF(temp_dict);
4512 Py_DECREF(remaining_pairs);
4513 return result_set;
4514
4515error:
4516 Py_XDECREF(temp_dict);
4517 Py_XDECREF(result_set);
4518 Py_XDECREF(key);
4519 Py_XDECREF(val1);
4520 Py_XDECREF(val2);
4521 return NULL;
4522}
4523
Guido van Rossum523259b2007-08-24 23:41:22 +00004524static PyObject*
4525dictviews_xor(PyObject* self, PyObject *other)
4526{
Dennis Sweeney07d81122020-06-10 01:56:56 -04004527 if (PyDictItems_Check(self) && PyDictItems_Check(other)) {
4528 return dictitems_xor(self, other);
4529 }
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004530 PyObject *result = dictviews_to_set(self);
4531 if (result == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004532 return NULL;
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004533 }
Guido van Rossum523259b2007-08-24 23:41:22 +00004534
Inada Naoki6cbc84f2019-11-08 00:59:04 +09004535 _Py_IDENTIFIER(symmetric_difference_update);
4536 PyObject *tmp = _PyObject_CallMethodIdOneArg(
4537 result, &PyId_symmetric_difference_update, other);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004538 if (tmp == NULL) {
4539 Py_DECREF(result);
4540 return NULL;
4541 }
Guido van Rossum523259b2007-08-24 23:41:22 +00004542
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004543 Py_DECREF(tmp);
4544 return result;
Guido van Rossum523259b2007-08-24 23:41:22 +00004545}
4546
4547static PyNumberMethods dictviews_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004548 0, /*nb_add*/
4549 (binaryfunc)dictviews_sub, /*nb_subtract*/
4550 0, /*nb_multiply*/
4551 0, /*nb_remainder*/
4552 0, /*nb_divmod*/
4553 0, /*nb_power*/
4554 0, /*nb_negative*/
4555 0, /*nb_positive*/
4556 0, /*nb_absolute*/
4557 0, /*nb_bool*/
4558 0, /*nb_invert*/
4559 0, /*nb_lshift*/
4560 0, /*nb_rshift*/
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04004561 (binaryfunc)_PyDictView_Intersect, /*nb_and*/
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004562 (binaryfunc)dictviews_xor, /*nb_xor*/
4563 (binaryfunc)dictviews_or, /*nb_or*/
Guido van Rossum523259b2007-08-24 23:41:22 +00004564};
4565
Daniel Stutzbach045b3ba2010-09-02 15:06:06 +00004566static PyObject*
4567dictviews_isdisjoint(PyObject *self, PyObject *other)
4568{
4569 PyObject *it;
4570 PyObject *item = NULL;
4571
4572 if (self == other) {
Eric Snow96c6af92015-05-29 22:21:39 -06004573 if (dictview_len((_PyDictViewObject *)self) == 0)
Daniel Stutzbach045b3ba2010-09-02 15:06:06 +00004574 Py_RETURN_TRUE;
4575 else
4576 Py_RETURN_FALSE;
4577 }
4578
4579 /* Iterate over the shorter object (only if other is a set,
4580 * because PySequence_Contains may be expensive otherwise): */
4581 if (PyAnySet_Check(other) || PyDictViewSet_Check(other)) {
Eric Snow96c6af92015-05-29 22:21:39 -06004582 Py_ssize_t len_self = dictview_len((_PyDictViewObject *)self);
Daniel Stutzbach045b3ba2010-09-02 15:06:06 +00004583 Py_ssize_t len_other = PyObject_Size(other);
4584 if (len_other == -1)
4585 return NULL;
4586
4587 if ((len_other > len_self)) {
4588 PyObject *tmp = other;
4589 other = self;
4590 self = tmp;
4591 }
4592 }
4593
4594 it = PyObject_GetIter(other);
4595 if (it == NULL)
4596 return NULL;
4597
4598 while ((item = PyIter_Next(it)) != NULL) {
4599 int contains = PySequence_Contains(self, item);
4600 Py_DECREF(item);
4601 if (contains == -1) {
4602 Py_DECREF(it);
4603 return NULL;
4604 }
4605
4606 if (contains) {
4607 Py_DECREF(it);
4608 Py_RETURN_FALSE;
4609 }
4610 }
4611 Py_DECREF(it);
4612 if (PyErr_Occurred())
4613 return NULL; /* PyIter_Next raised an exception. */
4614 Py_RETURN_TRUE;
4615}
4616
4617PyDoc_STRVAR(isdisjoint_doc,
4618"Return True if the view and the given iterable have a null intersection.");
4619
Serhiy Storchaka81524022018-11-27 13:05:02 +02004620static PyObject* dictkeys_reversed(_PyDictViewObject *dv, PyObject *Py_UNUSED(ignored));
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004621
4622PyDoc_STRVAR(reversed_keys_doc,
4623"Return a reverse iterator over the dict keys.");
4624
Guido van Rossumb90c8482007-02-10 01:11:45 +00004625static PyMethodDef dictkeys_methods[] = {
Daniel Stutzbach045b3ba2010-09-02 15:06:06 +00004626 {"isdisjoint", (PyCFunction)dictviews_isdisjoint, METH_O,
4627 isdisjoint_doc},
Serhiy Storchaka62be7422018-11-27 13:27:31 +02004628 {"__reversed__", (PyCFunction)(void(*)(void))dictkeys_reversed, METH_NOARGS,
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004629 reversed_keys_doc},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004630 {NULL, NULL} /* sentinel */
Guido van Rossumb90c8482007-02-10 01:11:45 +00004631};
4632
4633PyTypeObject PyDictKeys_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004634 PyVarObject_HEAD_INIT(&PyType_Type, 0)
4635 "dict_keys", /* tp_name */
Eric Snow96c6af92015-05-29 22:21:39 -06004636 sizeof(_PyDictViewObject), /* tp_basicsize */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004637 0, /* tp_itemsize */
4638 /* methods */
4639 (destructor)dictview_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02004640 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004641 0, /* tp_getattr */
4642 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02004643 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004644 (reprfunc)dictview_repr, /* tp_repr */
4645 &dictviews_as_number, /* tp_as_number */
4646 &dictkeys_as_sequence, /* tp_as_sequence */
4647 0, /* tp_as_mapping */
4648 0, /* tp_hash */
4649 0, /* tp_call */
4650 0, /* tp_str */
4651 PyObject_GenericGetAttr, /* tp_getattro */
4652 0, /* tp_setattro */
4653 0, /* tp_as_buffer */
4654 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */
4655 0, /* tp_doc */
4656 (traverseproc)dictview_traverse, /* tp_traverse */
4657 0, /* tp_clear */
4658 dictview_richcompare, /* tp_richcompare */
4659 0, /* tp_weaklistoffset */
4660 (getiterfunc)dictkeys_iter, /* tp_iter */
4661 0, /* tp_iternext */
4662 dictkeys_methods, /* tp_methods */
Dennis Sweeney3ee0e482020-06-12 13:19:25 -04004663 .tp_getset = dictview_getset,
Guido van Rossumb90c8482007-02-10 01:11:45 +00004664};
4665
4666static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05304667dictkeys_new(PyObject *dict, PyObject *Py_UNUSED(ignored))
Guido van Rossumb90c8482007-02-10 01:11:45 +00004668{
Eric Snow96c6af92015-05-29 22:21:39 -06004669 return _PyDictView_New(dict, &PyDictKeys_Type);
Guido van Rossumb90c8482007-02-10 01:11:45 +00004670}
4671
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004672static PyObject *
Serhiy Storchaka81524022018-11-27 13:05:02 +02004673dictkeys_reversed(_PyDictViewObject *dv, PyObject *Py_UNUSED(ignored))
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004674{
4675 if (dv->dv_dict == NULL) {
4676 Py_RETURN_NONE;
4677 }
4678 return dictiter_new(dv->dv_dict, &PyDictRevIterKey_Type);
4679}
4680
Guido van Rossum3ac67412007-02-10 18:55:06 +00004681/*** dict_items ***/
Guido van Rossumb90c8482007-02-10 01:11:45 +00004682
4683static PyObject *
Eric Snow96c6af92015-05-29 22:21:39 -06004684dictitems_iter(_PyDictViewObject *dv)
Guido van Rossumb90c8482007-02-10 01:11:45 +00004685{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004686 if (dv->dv_dict == NULL) {
4687 Py_RETURN_NONE;
4688 }
4689 return dictiter_new(dv->dv_dict, &PyDictIterItem_Type);
Guido van Rossum3ac67412007-02-10 18:55:06 +00004690}
4691
4692static int
Eric Snow96c6af92015-05-29 22:21:39 -06004693dictitems_contains(_PyDictViewObject *dv, PyObject *obj)
Guido van Rossum3ac67412007-02-10 18:55:06 +00004694{
Serhiy Storchaka753bca32017-05-20 12:30:02 +03004695 int result;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004696 PyObject *key, *value, *found;
4697 if (dv->dv_dict == NULL)
4698 return 0;
4699 if (!PyTuple_Check(obj) || PyTuple_GET_SIZE(obj) != 2)
4700 return 0;
4701 key = PyTuple_GET_ITEM(obj, 0);
4702 value = PyTuple_GET_ITEM(obj, 1);
Raymond Hettinger6692f012016-09-18 21:46:08 -07004703 found = PyDict_GetItemWithError((PyObject *)dv->dv_dict, key);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004704 if (found == NULL) {
4705 if (PyErr_Occurred())
4706 return -1;
4707 return 0;
4708 }
Serhiy Storchaka753bca32017-05-20 12:30:02 +03004709 Py_INCREF(found);
Serhiy Storchaka18b711c2019-08-04 14:12:48 +03004710 result = PyObject_RichCompareBool(found, value, Py_EQ);
Serhiy Storchaka753bca32017-05-20 12:30:02 +03004711 Py_DECREF(found);
4712 return result;
Guido van Rossumb90c8482007-02-10 01:11:45 +00004713}
4714
Guido van Rossum83825ac2007-02-10 04:54:19 +00004715static PySequenceMethods dictitems_as_sequence = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004716 (lenfunc)dictview_len, /* sq_length */
4717 0, /* sq_concat */
4718 0, /* sq_repeat */
4719 0, /* sq_item */
4720 0, /* sq_slice */
4721 0, /* sq_ass_item */
4722 0, /* sq_ass_slice */
4723 (objobjproc)dictitems_contains, /* sq_contains */
Guido van Rossum83825ac2007-02-10 04:54:19 +00004724};
4725
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004726static PyObject* dictitems_reversed(_PyDictViewObject *dv);
4727
4728PyDoc_STRVAR(reversed_items_doc,
4729"Return a reverse iterator over the dict items.");
4730
Guido van Rossumb90c8482007-02-10 01:11:45 +00004731static PyMethodDef dictitems_methods[] = {
Daniel Stutzbach045b3ba2010-09-02 15:06:06 +00004732 {"isdisjoint", (PyCFunction)dictviews_isdisjoint, METH_O,
4733 isdisjoint_doc},
Serhiy Storchaka62be7422018-11-27 13:27:31 +02004734 {"__reversed__", (PyCFunction)(void(*)(void))dictitems_reversed, METH_NOARGS,
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004735 reversed_items_doc},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004736 {NULL, NULL} /* sentinel */
Guido van Rossumb90c8482007-02-10 01:11:45 +00004737};
4738
4739PyTypeObject PyDictItems_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004740 PyVarObject_HEAD_INIT(&PyType_Type, 0)
4741 "dict_items", /* tp_name */
Eric Snow96c6af92015-05-29 22:21:39 -06004742 sizeof(_PyDictViewObject), /* tp_basicsize */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004743 0, /* tp_itemsize */
4744 /* methods */
4745 (destructor)dictview_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02004746 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004747 0, /* tp_getattr */
4748 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02004749 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004750 (reprfunc)dictview_repr, /* tp_repr */
4751 &dictviews_as_number, /* tp_as_number */
4752 &dictitems_as_sequence, /* tp_as_sequence */
4753 0, /* tp_as_mapping */
4754 0, /* tp_hash */
4755 0, /* tp_call */
4756 0, /* tp_str */
4757 PyObject_GenericGetAttr, /* tp_getattro */
4758 0, /* tp_setattro */
4759 0, /* tp_as_buffer */
4760 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */
4761 0, /* tp_doc */
4762 (traverseproc)dictview_traverse, /* tp_traverse */
4763 0, /* tp_clear */
4764 dictview_richcompare, /* tp_richcompare */
4765 0, /* tp_weaklistoffset */
4766 (getiterfunc)dictitems_iter, /* tp_iter */
4767 0, /* tp_iternext */
4768 dictitems_methods, /* tp_methods */
Dennis Sweeney3ee0e482020-06-12 13:19:25 -04004769 .tp_getset = dictview_getset,
Guido van Rossumb90c8482007-02-10 01:11:45 +00004770};
4771
4772static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05304773dictitems_new(PyObject *dict, PyObject *Py_UNUSED(ignored))
Guido van Rossumb90c8482007-02-10 01:11:45 +00004774{
Eric Snow96c6af92015-05-29 22:21:39 -06004775 return _PyDictView_New(dict, &PyDictItems_Type);
Guido van Rossumb90c8482007-02-10 01:11:45 +00004776}
4777
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004778static PyObject *
4779dictitems_reversed(_PyDictViewObject *dv)
4780{
4781 if (dv->dv_dict == NULL) {
4782 Py_RETURN_NONE;
4783 }
4784 return dictiter_new(dv->dv_dict, &PyDictRevIterItem_Type);
4785}
4786
Guido van Rossum3ac67412007-02-10 18:55:06 +00004787/*** dict_values ***/
Guido van Rossumb90c8482007-02-10 01:11:45 +00004788
4789static PyObject *
Eric Snow96c6af92015-05-29 22:21:39 -06004790dictvalues_iter(_PyDictViewObject *dv)
Guido van Rossumb90c8482007-02-10 01:11:45 +00004791{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004792 if (dv->dv_dict == NULL) {
4793 Py_RETURN_NONE;
4794 }
4795 return dictiter_new(dv->dv_dict, &PyDictIterValue_Type);
Guido van Rossumb90c8482007-02-10 01:11:45 +00004796}
4797
Guido van Rossum83825ac2007-02-10 04:54:19 +00004798static PySequenceMethods dictvalues_as_sequence = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004799 (lenfunc)dictview_len, /* sq_length */
4800 0, /* sq_concat */
4801 0, /* sq_repeat */
4802 0, /* sq_item */
4803 0, /* sq_slice */
4804 0, /* sq_ass_item */
4805 0, /* sq_ass_slice */
4806 (objobjproc)0, /* sq_contains */
Guido van Rossum83825ac2007-02-10 04:54:19 +00004807};
4808
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004809static PyObject* dictvalues_reversed(_PyDictViewObject *dv);
4810
4811PyDoc_STRVAR(reversed_values_doc,
4812"Return a reverse iterator over the dict values.");
4813
Guido van Rossumb90c8482007-02-10 01:11:45 +00004814static PyMethodDef dictvalues_methods[] = {
Serhiy Storchaka62be7422018-11-27 13:27:31 +02004815 {"__reversed__", (PyCFunction)(void(*)(void))dictvalues_reversed, METH_NOARGS,
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004816 reversed_values_doc},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004817 {NULL, NULL} /* sentinel */
Guido van Rossumb90c8482007-02-10 01:11:45 +00004818};
4819
4820PyTypeObject PyDictValues_Type = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004821 PyVarObject_HEAD_INIT(&PyType_Type, 0)
4822 "dict_values", /* tp_name */
Eric Snow96c6af92015-05-29 22:21:39 -06004823 sizeof(_PyDictViewObject), /* tp_basicsize */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004824 0, /* tp_itemsize */
4825 /* methods */
4826 (destructor)dictview_dealloc, /* tp_dealloc */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02004827 0, /* tp_vectorcall_offset */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004828 0, /* tp_getattr */
4829 0, /* tp_setattr */
Jeroen Demeyer530f5062019-05-31 04:13:39 +02004830 0, /* tp_as_async */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004831 (reprfunc)dictview_repr, /* tp_repr */
4832 0, /* tp_as_number */
4833 &dictvalues_as_sequence, /* tp_as_sequence */
4834 0, /* tp_as_mapping */
4835 0, /* tp_hash */
4836 0, /* tp_call */
4837 0, /* tp_str */
4838 PyObject_GenericGetAttr, /* tp_getattro */
4839 0, /* tp_setattro */
4840 0, /* tp_as_buffer */
4841 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */
4842 0, /* tp_doc */
4843 (traverseproc)dictview_traverse, /* tp_traverse */
4844 0, /* tp_clear */
4845 0, /* tp_richcompare */
4846 0, /* tp_weaklistoffset */
4847 (getiterfunc)dictvalues_iter, /* tp_iter */
4848 0, /* tp_iternext */
4849 dictvalues_methods, /* tp_methods */
Dennis Sweeney3ee0e482020-06-12 13:19:25 -04004850 .tp_getset = dictview_getset,
Guido van Rossumb90c8482007-02-10 01:11:45 +00004851};
4852
4853static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05304854dictvalues_new(PyObject *dict, PyObject *Py_UNUSED(ignored))
Guido van Rossumb90c8482007-02-10 01:11:45 +00004855{
Eric Snow96c6af92015-05-29 22:21:39 -06004856 return _PyDictView_New(dict, &PyDictValues_Type);
Guido van Rossumb90c8482007-02-10 01:11:45 +00004857}
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004858
Rémi Lapeyre6531bf62018-11-06 01:38:54 +01004859static PyObject *
4860dictvalues_reversed(_PyDictViewObject *dv)
4861{
4862 if (dv->dv_dict == NULL) {
4863 Py_RETURN_NONE;
4864 }
4865 return dictiter_new(dv->dv_dict, &PyDictRevIterValue_Type);
4866}
4867
4868
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004869/* Returns NULL if cannot allocate a new PyDictKeysObject,
4870 but does not set an error */
4871PyDictKeysObject *
4872_PyDict_NewKeysForClass(void)
4873{
Victor Stinner742da042016-09-07 17:40:12 -07004874 PyDictKeysObject *keys = new_keys_object(PyDict_MINSIZE);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004875 if (keys == NULL)
4876 PyErr_Clear();
4877 else
4878 keys->dk_lookup = lookdict_split;
4879 return keys;
4880}
4881
4882#define CACHED_KEYS(tp) (((PyHeapTypeObject*)tp)->ht_cached_keys)
4883
4884PyObject *
4885PyObject_GenericGetDict(PyObject *obj, void *context)
4886{
4887 PyObject *dict, **dictptr = _PyObject_GetDictPtr(obj);
4888 if (dictptr == NULL) {
4889 PyErr_SetString(PyExc_AttributeError,
4890 "This object has no __dict__");
4891 return NULL;
4892 }
4893 dict = *dictptr;
4894 if (dict == NULL) {
4895 PyTypeObject *tp = Py_TYPE(obj);
4896 if ((tp->tp_flags & Py_TPFLAGS_HEAPTYPE) && CACHED_KEYS(tp)) {
INADA Naokia7576492018-11-14 18:39:27 +09004897 dictkeys_incref(CACHED_KEYS(tp));
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004898 *dictptr = dict = new_dict_with_shared_keys(CACHED_KEYS(tp));
4899 }
4900 else {
4901 *dictptr = dict = PyDict_New();
4902 }
4903 }
4904 Py_XINCREF(dict);
4905 return dict;
4906}
4907
4908int
4909_PyObjectDict_SetItem(PyTypeObject *tp, PyObject **dictptr,
Victor Stinner742da042016-09-07 17:40:12 -07004910 PyObject *key, PyObject *value)
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004911{
4912 PyObject *dict;
4913 int res;
4914 PyDictKeysObject *cached;
4915
4916 assert(dictptr != NULL);
4917 if ((tp->tp_flags & Py_TPFLAGS_HEAPTYPE) && (cached = CACHED_KEYS(tp))) {
4918 assert(dictptr != NULL);
4919 dict = *dictptr;
4920 if (dict == NULL) {
INADA Naokia7576492018-11-14 18:39:27 +09004921 dictkeys_incref(cached);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004922 dict = new_dict_with_shared_keys(cached);
4923 if (dict == NULL)
4924 return -1;
4925 *dictptr = dict;
4926 }
4927 if (value == NULL) {
4928 res = PyDict_DelItem(dict, key);
INADA Naoki2294f3a2017-02-12 13:51:30 +09004929 // Since key sharing dict doesn't allow deletion, PyDict_DelItem()
4930 // always converts dict to combined form.
4931 if ((cached = CACHED_KEYS(tp)) != NULL) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004932 CACHED_KEYS(tp) = NULL;
INADA Naokia7576492018-11-14 18:39:27 +09004933 dictkeys_decref(cached);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004934 }
Victor Stinner3d3f2642016-12-15 17:21:23 +01004935 }
4936 else {
INADA Naoki2294f3a2017-02-12 13:51:30 +09004937 int was_shared = (cached == ((PyDictObject *)dict)->ma_keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004938 res = PyDict_SetItem(dict, key, value);
INADA Naoki2294f3a2017-02-12 13:51:30 +09004939 if (was_shared &&
4940 (cached = CACHED_KEYS(tp)) != NULL &&
4941 cached != ((PyDictObject *)dict)->ma_keys) {
Victor Stinner3d3f2642016-12-15 17:21:23 +01004942 /* PyDict_SetItem() may call dictresize and convert split table
4943 * into combined table. In such case, convert it to split
4944 * table again and update type's shared key only when this is
4945 * the only dict sharing key with the type.
4946 *
4947 * This is to allow using shared key in class like this:
4948 *
4949 * class C:
4950 * def __init__(self):
4951 * # one dict resize happens
4952 * self.a, self.b, self.c = 1, 2, 3
4953 * self.d, self.e, self.f = 4, 5, 6
4954 * a = C()
4955 */
Benjamin Peterson15ee8212012-04-24 14:44:18 -04004956 if (cached->dk_refcnt == 1) {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004957 CACHED_KEYS(tp) = make_keys_shared(dict);
Victor Stinner742da042016-09-07 17:40:12 -07004958 }
4959 else {
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004960 CACHED_KEYS(tp) = NULL;
4961 }
INADA Naokia7576492018-11-14 18:39:27 +09004962 dictkeys_decref(cached);
Benjamin Peterson15ee8212012-04-24 14:44:18 -04004963 if (CACHED_KEYS(tp) == NULL && PyErr_Occurred())
4964 return -1;
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004965 }
4966 }
4967 } else {
4968 dict = *dictptr;
4969 if (dict == NULL) {
4970 dict = PyDict_New();
4971 if (dict == NULL)
4972 return -1;
4973 *dictptr = dict;
4974 }
4975 if (value == NULL) {
4976 res = PyDict_DelItem(dict, key);
4977 } else {
4978 res = PyDict_SetItem(dict, key, value);
4979 }
4980 }
4981 return res;
4982}
4983
4984void
4985_PyDictKeys_DecRef(PyDictKeysObject *keys)
4986{
INADA Naokia7576492018-11-14 18:39:27 +09004987 dictkeys_decref(keys);
Benjamin Peterson7d95e402012-04-23 11:24:50 -04004988}