blob: 7dbaa890e714d8cbcb53c4cf7151da74296dad14 [file] [log] [blame]
Eric Snow96c6af92015-05-29 22:21:39 -06001/* Ordered Dictionary object implementation.
2
3This implementation is necessarily explicitly equivalent to the pure Python
4OrderedDict class in Lib/collections/__init__.py. The strategy there
5involves using a doubly-linked-list to capture the order. We keep to that
6strategy, using a lower-level linked-list.
7
8About the Linked-List
9=====================
10
11For the linked list we use a basic doubly-linked-list. Using a circularly-
12linked-list does have some benefits, but they don't apply so much here
13since OrderedDict is focused on the ends of the list (for the most part).
14Furthermore, there are some features of generic linked-lists that we simply
15don't need for OrderedDict. Thus a simple custom implementation meets our
16needs. Alternatives to our simple approach include the QCIRCLE_*
17macros from BSD's queue.h, and the linux's list.h.
18
19Getting O(1) Node Lookup
20------------------------
21
22One invariant of Python's OrderedDict is that it preserves time complexity
23of dict's methods, particularly the O(1) operations. Simply adding a
24linked-list on top of dict is not sufficient here; operations for nodes in
25the middle of the linked-list implicitly require finding the node first.
26With a simple linked-list like we're using, that is an O(n) operation.
27Consequently, methods like __delitem__() would change from O(1) to O(n),
28which is unacceptable.
29
30In order to preserve O(1) performance for node removal (finding nodes), we
31must do better than just looping through the linked-list. Here are options
32we've considered:
33
341. use a second dict to map keys to nodes (a la the pure Python version).
352. keep a simple hash table mirroring the order of dict's, mapping each key
36 to the corresponding node in the linked-list.
373. use a version of shared keys (split dict) that allows non-unicode keys.
384. have the value stored for each key be a (value, node) pair, and adjust
39 __getitem__(), get(), etc. accordingly.
40
41The approach with the least performance impact (time and space) is #2,
42mirroring the key order of dict's dk_enties with an array of node pointers.
43While lookdict() and friends (dk_lookup) don't give us the index into the
44array, we make use of pointer arithmetic to get that index. An alternative
45would be to refactor lookdict() to provide the index, explicitly exposing
46the implementation detail. We could even just use a custom lookup function
47for OrderedDict that facilitates our need. However, both approaches are
48significantly more complicated than just using pointer arithmetic.
49
50The catch with mirroring the hash table ordering is that we have to keep
51the ordering in sync through any dict resizes. However, that order only
52matters during node lookup. We can simply defer any potential resizing
53until we need to do a lookup.
54
55Linked-List Nodes
56-----------------
57
58The current implementation stores a pointer to the associated key only.
59One alternative would be to store a pointer to the PyDictKeyEntry instead.
60This would save one pointer de-reference per item, which is nice during
61calls to values() and items(). However, it adds unnecessary overhead
62otherwise, so we stick with just the key.
63
64Linked-List API
65---------------
66
67As noted, the linked-list implemented here does not have all the bells and
68whistles. However, we recognize that the implementation may need to
69change to accommodate performance improvements or extra functionality. To
70that end, We use a simple API to interact with the linked-list. Here's a
71summary of the methods/macros:
72
73Node info:
74
75* _odictnode_KEY(node)
76* _odictnode_VALUE(od, node)
77* _odictnode_PREV(node)
78* _odictnode_NEXT(node)
79
80Linked-List info:
81
82* _odict_FIRST(od)
83* _odict_LAST(od)
84* _odict_EMPTY(od)
85* _odict_FOREACH(od, node) - used in place of `for (node=...)`
86
87For adding nodes:
88
89* _odict_add_head(od, node)
90* _odict_add_tail(od, node)
91* _odict_add_new_node(od, key)
92
93For removing nodes:
94
95* _odict_pop_node(od, node, key)
96* _odict_clear_node(od, node)
97* _odict_clear_nodes(od, clear_each)
98
99Others:
100
101* _odict_initialize(od)
102* _odict_find_node(od, key)
103* _odict_keys_equal(od1, od2)
104
105Used, but specific to the linked-list implementation:
106
107* _odict_free_fast_nodes(od)
108
109And here's a look at how the linked-list relates to the OrderedDict API:
110
111============ === === ==== ==== ==== === ==== ===== ==== ==== === ==== === ===
112method key val prev next mem 1st last empty iter find add rmv clr keq
113============ === === ==== ==== ==== === ==== ===== ==== ==== === ==== === ===
114__del__ ~ X
115__delitem__ free ~ node
116__eq__ ~ X
117__iter__ X X
118__new__ X X
119__reduce__ X ~ X
120__repr__ X X X
121__reversed__ X X
122__setitem__ key
123__sizeof__ size X
124clear ~ ~ X
125copy X X X
126items X X X
127keys X X
128move_to_end X X X ~ h/t key
129pop free key
130popitem X X free X X node
131setdefault ~ ? ~
132values X X
133============ === === ==== ==== ==== === ==== ===== ==== ==== === ==== === ===
134
135__delitem__ is the only method that directly relies on finding an arbitrary
136node in the linked-list. Everything else is iteration or relates to the
137ends of the linked-list.
138
139Situation that Endangers Consistency
140------------------------------------
141Using a raw linked-list for OrderedDict exposes a key situation that can
142cause problems. If a node is stored in a variable, there is a chance that
143the node may have been deallocated before the variable gets used, thus
144potentially leading to a segmentation fault. A key place where this shows
145up is during iteration through the linked list (via _odict_FOREACH or
146otherwise).
147
148A number of solutions are available to resolve this situation:
149
150* defer looking up the node until as late as possible and certainly after
151 any code that could possibly result in a deletion;
152* if the node is needed both before and after a point where the node might
153 be removed, do a check before using the node at the "after" location to
154 see if the node is still valid;
155* like the last one, but simply pull the node again to ensure it's right;
156* keep the key in the variable instead of the node and then look up the
157 node using the key at the point where the node is needed (this is what
158 we do for the iterators).
159
160Another related problem, preserving consistent ordering during iteration,
161is described below. That one is not exclusive to using linked-lists.
162
163
164Challenges from Subclassing dict
165================================
166
167OrderedDict subclasses dict, which is an unusual relationship between two
168builtin types (other than the base object type). Doing so results in
169some complication and deserves further explanation. There are two things
170to consider here. First, in what circumstances or with what adjustments
171can OrderedDict be used as a drop-in replacement for dict (at the C level)?
172Second, how can the OrderedDict implementation leverage the dict
173implementation effectively without introducing unnecessary coupling or
174inefficiencies?
175
176This second point is reflected here and in the implementation, so the
177further focus is on the first point. It is worth noting that for
178overridden methods, the dict implementation is deferred to as much as
179possible. Furthermore, coupling is limited to as little as is reasonable.
180
181Concrete API Compatibility
182--------------------------
183
184Use of the concrete C-API for dict (PyDict_*) with OrderedDict is
185problematic. (See http://bugs.python.org/issue10977.) The concrete API
186has a number of hard-coded assumptions tied to the dict implementation.
187This is, in part, due to performance reasons, which is understandable
188given the part dict plays in Python.
189
190Any attempt to replace dict with OrderedDict for any role in the
191interpreter (e.g. **kwds) faces a challenge. Such any effort must
192recognize that the instances in affected locations currently interact with
193the concrete API.
194
195Here are some ways to address this challenge:
196
1971. Change the relevant usage of the concrete API in CPython and add
198 PyDict_CheckExact() calls to each of the concrete API funcions.
1992. Adjust the relevant concrete API functions to explicitly accommodate
200 OrderedDict.
2013. As with #1, add the checks, but improve the abstract API with smart fast
202 paths for dict and OrderedDict, and refactor CPython to use the abstract
203 API. Improvements to the abstract API would be valuable regardless.
204
205Adding the checks to the concrete API would help make any interpreter
206switch to OrderedDict less painful for extension modules. However, this
207won't work. The equivalent C API call to `dict.__setitem__(obj, k, v)`
208is 'PyDict_SetItem(obj, k, v)`. This illustrates how subclasses in C call
209the base class's methods, since there is no equivalent of super() in the
210C API. Calling into Python for parent class API would work, but some
211extension modules already rely on this feature of the concrete API.
212
213For reference, here is a breakdown of some of the dict concrete API:
214
215========================== ============= =======================
216concrete API uses abstract API
217========================== ============= =======================
218PyDict_Check PyMapping_Check
219(PyDict_CheckExact) -
220(PyDict_New) -
221(PyDictProxy_New) -
222PyDict_Clear -
223PyDict_Contains PySequence_Contains
224PyDict_Copy -
225PyDict_SetItem PyObject_SetItem
226PyDict_SetItemString PyMapping_SetItemString
227PyDict_DelItem PyMapping_DelItem
228PyDict_DelItemString PyMapping_DelItemString
229PyDict_GetItem -
230PyDict_GetItemWithError PyObject_GetItem
231_PyDict_GetItemIdWithError -
232PyDict_GetItemString PyMapping_GetItemString
233PyDict_Items PyMapping_Items
234PyDict_Keys PyMapping_Keys
235PyDict_Values PyMapping_Values
236PyDict_Size PyMapping_Size
237 PyMapping_Length
238PyDict_Next PyIter_Next
239_PyDict_Next -
240PyDict_Merge -
241PyDict_Update -
242PyDict_MergeFromSeq2 -
243PyDict_ClearFreeList -
244- PyMapping_HasKeyString
245- PyMapping_HasKey
246========================== ============= =======================
247
248
249The dict Interface Relative to OrderedDict
250==========================================
251
252Since OrderedDict subclasses dict, understanding the various methods and
253attributes of dict is important for implementing OrderedDict.
254
255Relevant Type Slots
256-------------------
257
258================= ================ =================== ================
259slot attribute object dict
260================= ================ =================== ================
261tp_dealloc - object_dealloc dict_dealloc
262tp_repr __repr__ object_repr dict_repr
263sq_contains __contains__ - dict_contains
264mp_length __len__ - dict_length
265mp_subscript __getitem__ - dict_subscript
266mp_ass_subscript __setitem__ - dict_ass_sub
267 __delitem__
268tp_hash __hash__ _Py_HashPointer ..._HashNotImpl
269tp_str __str__ object_str -
270tp_getattro __getattribute__ ..._GenericGetAttr (repeated)
271 __getattr__
272tp_setattro __setattr__ ..._GenericSetAttr (disabled)
273tp_doc __doc__ (literal) dictionary_doc
274tp_traverse - - dict_traverse
275tp_clear - - dict_tp_clear
276tp_richcompare __eq__ object_richcompare dict_richcompare
277 __ne__
278tp_weaklistoffset (__weakref__) - -
279tp_iter __iter__ - dict_iter
280tp_dictoffset (__dict__) - -
281tp_init __init__ object_init dict_init
282tp_alloc - PyType_GenericAlloc (repeated)
283tp_new __new__ object_new dict_new
284tp_free - PyObject_Del PyObject_GC_Del
285================= ================ =================== ================
286
287Relevant Methods
288----------------
289
290================ =================== ===============
291method object dict
292================ =================== ===============
293__reduce__ object_reduce -
294__sizeof__ object_sizeof dict_sizeof
295clear - dict_clear
296copy - dict_copy
297fromkeys - dict_fromkeys
298get - dict_get
299items - dictitems_new
300keys - dictkeys_new
301pop - dict_pop
302popitem - dict_popitem
303setdefault - dict_setdefault
304update - dict_update
305values - dictvalues_new
306================ =================== ===============
307
308
309Pure Python OrderedDict
310=======================
311
312As already noted, compatibility with the pure Python OrderedDict
313implementation is a key goal of this C implementation. To further that
314goal, here's a summary of how OrderedDict-specific methods are implemented
315in collections/__init__.py. Also provided is an indication of which
316methods directly mutate or iterate the object, as well as any relationship
317with the underlying linked-list.
318
319============= ============== == ================ === === ====
320method impl used ll uses inq mut iter
321============= ============== == ================ === === ====
322__contains__ dict - - X
323__delitem__ OrderedDict Y dict.__delitem__ X
324__eq__ OrderedDict N OrderedDict ~
325 dict.__eq__
326 __iter__
327__getitem__ dict - - X
328__iter__ OrderedDict Y - X
329__init__ OrderedDict N update
330__len__ dict - - X
331__ne__ MutableMapping - __eq__ ~
332__reduce__ OrderedDict N OrderedDict ~
333 __iter__
334 __getitem__
335__repr__ OrderedDict N __class__ ~
336 items
337__reversed__ OrderedDict Y - X
338__setitem__ OrderedDict Y __contains__ X
339 dict.__setitem__
340__sizeof__ OrderedDict Y __len__ ~
341 __dict__
342clear OrderedDict Y dict.clear X
343copy OrderedDict N __class__
344 __init__
345fromkeys OrderedDict N __setitem__
346get dict - - ~
347items MutableMapping - ItemsView X
348keys MutableMapping - KeysView X
349move_to_end OrderedDict Y - X
350pop OrderedDict N __contains__ X
351 __getitem__
352 __delitem__
353popitem OrderedDict Y dict.pop X
354setdefault OrderedDict N __contains__ ~
355 __getitem__
356 __setitem__
357update MutableMapping - __setitem__ ~
358values MutableMapping - ValuesView X
359============= ============== == ================ === === ====
360
361__reversed__ and move_to_end are both exclusive to OrderedDict.
362
363
364C OrderedDict Implementation
365============================
366
367================= ================
368slot impl
369================= ================
370tp_dealloc odict_dealloc
371tp_repr odict_repr
372mp_ass_subscript odict_ass_sub
373tp_doc odict_doc
374tp_traverse odict_traverse
375tp_clear odict_tp_clear
376tp_richcompare odict_richcompare
377tp_weaklistoffset (offset)
378tp_iter odict_iter
379tp_dictoffset (offset)
380tp_init odict_init
381tp_alloc (repeated)
382tp_new odict_new
383================= ================
384
385================= ================
386method impl
387================= ================
388__reduce__ odict_reduce
389__sizeof__ odict_sizeof
390clear odict_clear
391copy odict_copy
392fromkeys odict_fromkeys
393items odictitems_new
394keys odictkeys_new
395pop odict_pop
396popitem odict_popitem
397setdefault odict_setdefault
398update odict_update
399values odictvalues_new
400================= ================
401
402Inherited unchanged from object/dict:
403
404================ ==========================
405method type field
406================ ==========================
407- tp_free
408__contains__ tp_as_sequence.sq_contains
409__getattr__ tp_getattro
410__getattribute__ tp_getattro
411__getitem__ tp_as_mapping.mp_subscript
412__hash__ tp_hash
413__len__ tp_as_mapping.mp_length
414__setattr__ tp_setattro
415__str__ tp_str
416get -
417================ ==========================
418
419
420Other Challenges
421================
422
423Preserving Ordering During Iteration
424------------------------------------
425During iteration through an OrderedDict, it is possible that items could
426get added, removed, or reordered. For a linked-list implementation, as
427with some other implementations, that situation may lead to undefined
428behavior. The documentation for dict mentions this in the `iter()` section
429of http://docs.python.org/3.4/library/stdtypes.html#dictionary-view-objects.
430In this implementation we follow dict's lead (as does the pure Python
431implementation) for __iter__(), keys(), values(), and items().
432
433For internal iteration (using _odict_FOREACH or not), there is still the
434risk that not all nodes that we expect to be seen in the loop actually get
435seen. Thus, we are careful in each of those places to ensure that they
436are. This comes, of course, at a small price at each location. The
437solutions are much the same as those detailed in the `Situation that
438Endangers Consistency` section above.
439
440
441Potential Optimizations
442=======================
443
444* Allocate the nodes as a block via od_fast_nodes instead of individually.
445 - Set node->key to NULL to indicate the node is not-in-use.
446 - Add _odict_EXISTS()?
447 - How to maintain consistency across resizes? Existing node pointers
448 would be invalidate after a resize, which is particularly problematic
449 for the iterators.
450* Use a more stream-lined implementation of update() and, likely indirectly,
451 __init__().
452
453*/
454
455/* TODO
456
457sooner:
458- reentrancy (make sure everything is at a thread-safe state when calling
459 into Python). I've already checked this multiple times, but want to
460 make one more pass.
461- add unit tests for reentrancy?
462
463later:
464- make the dict views support the full set API (the pure Python impl does)
465- implement a fuller MutableMapping API in C?
466- move the MutableMapping implementation to abstract.c?
467- optimize mutablemapping_update
468- use PyObject_MALLOC (small object allocator) for odict nodes?
469- support subclasses better (e.g. in odict_richcompare)
470
471*/
472
473#include "Python.h"
474#include "structmember.h"
475#include "dict-common.h"
476#include <stddef.h>
477
478
479typedef struct _odictnode _ODictNode;
480
481/* PyODictObject */
482struct _odictobject {
Eric Snow4fabf022015-06-04 00:09:56 -0600483 PyDictObject od_dict; /* the underlying dict */
484 _ODictNode *od_first; /* first node in the linked list, if any */
485 _ODictNode *od_last; /* last node in the linked list, if any */
Eric Snow8c7f9552015-08-07 17:45:12 -0600486 /* od_fast_nodes and od_resize_sentinel are managed by _odict_resize()
487 * Note that we rely on implementation details of dict for both. */
488 _ODictNode **od_fast_nodes; /* hash table that mirrors the dict table */
489 Py_uintptr_t od_resize_sentinel; /* changes if odict should be resized */
490
Eric Snow4fabf022015-06-04 00:09:56 -0600491 size_t od_state; /* incremented whenever the LL changes */
492 PyObject *od_inst_dict; /* OrderedDict().__dict__ */
493 PyObject *od_weakreflist; /* holds weakrefs to the odict */
Eric Snow96c6af92015-05-29 22:21:39 -0600494};
495
496
497/* ----------------------------------------------
498 * odict keys (a simple doubly-linked list)
499 */
500
501struct _odictnode {
502 PyObject *key;
Eric Snow4c729182015-06-03 10:50:37 -0600503 Py_hash_t hash;
Eric Snow96c6af92015-05-29 22:21:39 -0600504 _ODictNode *next;
505 _ODictNode *prev;
506};
507
508#define _odictnode_KEY(node) \
509 (node->key)
Eric Snow4c729182015-06-03 10:50:37 -0600510#define _odictnode_HASH(node) \
511 (node->hash)
Eric Snow96c6af92015-05-29 22:21:39 -0600512/* borrowed reference */
513#define _odictnode_VALUE(node, od) \
Eric Snowa762af72015-06-01 22:59:08 -0600514 PyODict_GetItemWithError((PyObject *)od, _odictnode_KEY(node))
Eric Snow96c6af92015-05-29 22:21:39 -0600515#define _odictnode_PREV(node) (node->prev)
516#define _odictnode_NEXT(node) (node->next)
517
518#define _odict_FIRST(od) (((PyODictObject *)od)->od_first)
519#define _odict_LAST(od) (((PyODictObject *)od)->od_last)
520#define _odict_EMPTY(od) (_odict_FIRST(od) == NULL)
521#define _odict_FOREACH(od, node) \
522 for (node = _odict_FIRST(od); node != NULL; node = _odictnode_NEXT(node))
523
Eric Snow8c7f9552015-08-07 17:45:12 -0600524#define _odict_FAST_SIZE(od) ((PyDictObject *)od)->ma_keys->dk_size
Eric Snow96c6af92015-05-29 22:21:39 -0600525
Eric Snow96c6af92015-05-29 22:21:39 -0600526static void
527_odict_free_fast_nodes(PyODictObject *od) {
528 if (od->od_fast_nodes) {
529 PyMem_FREE(od->od_fast_nodes);
530 }
531}
532
Eric Snow4c729182015-06-03 10:50:37 -0600533/* Return the index into the hash table, regardless of a valid node. */
534static Py_ssize_t
535_odict_get_index_hash(PyODictObject *od, PyObject *key, Py_hash_t hash)
536{
537 PyObject **value_addr = NULL;
538 PyDictKeyEntry *ep;
539 PyDictKeysObject *keys = ((PyDictObject *)od)->ma_keys;
540
541 ep = (keys->dk_lookup)((PyDictObject *)od, key, hash, &value_addr);
542 if (ep == NULL)
543 return -1;
544 /* We use pointer arithmetic to get the entry's index into the table. */
545 return ep - keys->dk_entries;
546}
547
548/* Replace od->od_fast_nodes with a new table matching the size of dict's. */
Eric Snow96c6af92015-05-29 22:21:39 -0600549static int
550_odict_resize(PyODictObject *od) {
Eric Snow4c729182015-06-03 10:50:37 -0600551 Py_ssize_t size, i;
Eric Snow96c6af92015-05-29 22:21:39 -0600552 _ODictNode **fast_nodes, *node;
553
554 /* Initialize a new "fast nodes" table. */
555 size = ((PyDictObject *)od)->ma_keys->dk_size;
556 fast_nodes = PyMem_NEW(_ODictNode *, size);
557 if (fast_nodes == NULL) {
558 PyErr_NoMemory();
559 return -1;
560 }
561 for (i = 0; i < size; i++)
562 fast_nodes[i] = NULL;
563
564 /* Copy the current nodes into the table. */
Eric Snow96c6af92015-05-29 22:21:39 -0600565 _odict_FOREACH(od, node) {
Eric Snow4c729182015-06-03 10:50:37 -0600566 i = _odict_get_index_hash(od, _odictnode_KEY(node),
567 _odictnode_HASH(node));
Eric Snow96c6af92015-05-29 22:21:39 -0600568 if (i < 0) {
Eric Snow96c6af92015-05-29 22:21:39 -0600569 PyMem_FREE(fast_nodes);
570 return -1;
571 }
572 fast_nodes[i] = node;
573 }
Eric Snow96c6af92015-05-29 22:21:39 -0600574
575 /* Replace the old fast nodes table. */
576 _odict_free_fast_nodes(od);
577 od->od_fast_nodes = fast_nodes;
Eric Snow8c7f9552015-08-07 17:45:12 -0600578 od->od_resize_sentinel = (Py_uintptr_t)(((PyDictObject *)od)->ma_keys);
Eric Snow96c6af92015-05-29 22:21:39 -0600579 return 0;
580}
581
582/* Return the index into the hash table, regardless of a valid node. */
583static Py_ssize_t
584_odict_get_index(PyODictObject *od, PyObject *key)
585{
586 Py_hash_t hash;
Eric Snow4c729182015-06-03 10:50:37 -0600587 PyDictKeysObject *keys;
Eric Snow96c6af92015-05-29 22:21:39 -0600588
589 assert(key != NULL);
Eric Snow4c729182015-06-03 10:50:37 -0600590 hash = PyObject_Hash(key);
591 if (hash == -1)
Eric Snow96c6af92015-05-29 22:21:39 -0600592 return -1;
Eric Snow4c729182015-06-03 10:50:37 -0600593 keys = ((PyDictObject *)od)->ma_keys;
594
595 /* Ensure od_fast_nodes and dk_entries are in sync. */
Eric Snow8c7f9552015-08-07 17:45:12 -0600596 if (od->od_resize_sentinel != (Py_uintptr_t)keys) {
Eric Snow4c729182015-06-03 10:50:37 -0600597 int resize_res = _odict_resize(od);
598 if (resize_res < 0)
599 return -1;
600 }
601
602 return _odict_get_index_hash(od, key, hash);
Eric Snow96c6af92015-05-29 22:21:39 -0600603}
604
605static int
606_odict_initialize(PyODictObject *od)
607{
Eric Snow4fabf022015-06-04 00:09:56 -0600608 od->od_state = 0;
Eric Snow96c6af92015-05-29 22:21:39 -0600609 _odict_FIRST(od) = NULL;
610 _odict_LAST(od) = NULL;
611 return _odict_resize((PyODictObject *)od);
612}
613
614/* Returns NULL if there was some error or the key was not found. */
615static _ODictNode *
616_odict_find_node(PyODictObject *od, PyObject *key)
617{
618 Py_ssize_t index;
619
620 if (_odict_EMPTY(od))
621 return NULL;
622 index = _odict_get_index(od, key);
623 if (index < 0)
624 return NULL;
625 return od->od_fast_nodes[index];
626}
627
628static void
629_odict_add_head(PyODictObject *od, _ODictNode *node)
630{
631 if (_odict_FIRST(od) == NULL) {
632 _odictnode_PREV(node) = NULL;
633 _odictnode_NEXT(node) = NULL;
634 _odict_FIRST(od) = node;
635 _odict_LAST(od) = node;
636 }
637 else {
638 _odictnode_PREV(node) = NULL;
639 _odictnode_NEXT(node) = _odict_FIRST(od);
640 _odict_FIRST(od) = node;
641 _odictnode_PREV(_odict_FIRST(od)) = node;
642 }
Eric Snow4fabf022015-06-04 00:09:56 -0600643 od->od_state++;
Eric Snow96c6af92015-05-29 22:21:39 -0600644}
645
646static void
647_odict_add_tail(PyODictObject *od, _ODictNode *node)
648{
649 if (_odict_LAST(od) == NULL) {
650 _odictnode_PREV(node) = NULL;
651 _odictnode_NEXT(node) = NULL;
652 _odict_FIRST(od) = node;
653 _odict_LAST(od) = node;
654 }
655 else {
656 _odictnode_PREV(node) = _odict_LAST(od);
657 _odictnode_NEXT(node) = NULL;
658 _odictnode_NEXT(_odict_LAST(od)) = node;
659 _odict_LAST(od) = node;
660 }
Eric Snow8c7f9552015-08-07 17:45:12 -0600661
Eric Snow4fabf022015-06-04 00:09:56 -0600662 od->od_state++;
Eric Snow96c6af92015-05-29 22:21:39 -0600663}
664
665/* adds the node to the end of the list */
666static int
667_odict_add_new_node(PyODictObject *od, PyObject *key)
668{
Eric Snow4c729182015-06-03 10:50:37 -0600669 Py_hash_t hash;
Eric Snow96c6af92015-05-29 22:21:39 -0600670 Py_ssize_t i;
671 _ODictNode *node;
672
673 Py_INCREF(key);
Eric Snow4c729182015-06-03 10:50:37 -0600674 hash = PyObject_Hash(key);
675 if (hash == -1)
676 return -1;
677
Eric Snow96c6af92015-05-29 22:21:39 -0600678 i = _odict_get_index(od, key);
679 if (i < 0) {
680 if (!PyErr_Occurred())
681 PyErr_SetObject(PyExc_KeyError, key);
682 Py_DECREF(key);
683 return -1;
684 }
685 else if (od->od_fast_nodes[i] != NULL) {
686 /* We already have a node for the key so there's no need to add one. */
687 Py_DECREF(key);
688 return 0;
689 }
690
691 /* must not be added yet */
692 node = (_ODictNode *)PyMem_MALLOC(sizeof(_ODictNode));
693 if (node == NULL) {
694 Py_DECREF(key);
695 PyErr_NoMemory();
696 return -1;
697 }
698
699 _odictnode_KEY(node) = key;
Eric Snow4c729182015-06-03 10:50:37 -0600700 _odictnode_HASH(node) = hash;
Eric Snow96c6af92015-05-29 22:21:39 -0600701 _odict_add_tail(od, node);
702 od->od_fast_nodes[i] = node;
703 return 0;
704}
705
706/* Putting the decref after the free causes problems. */
707#define _odictnode_DEALLOC(node) \
708 do { \
709 Py_DECREF(_odictnode_KEY(node)); \
710 PyMem_FREE((void *)node); \
711 } while (0)
712
713/* Repeated calls on the same node are no-ops. */
714static void
715_odict_remove_node(PyODictObject *od, _ODictNode *node)
716{
717 if (_odict_FIRST(od) == node)
718 _odict_FIRST(od) = _odictnode_NEXT(node);
719 else if (_odictnode_PREV(node) != NULL)
720 _odictnode_NEXT(_odictnode_PREV(node)) = _odictnode_NEXT(node);
721
722 if (_odict_LAST(od) == node)
723 _odict_LAST(od) = _odictnode_PREV(node);
724 else if (_odictnode_NEXT(node) != NULL)
725 _odictnode_PREV(_odictnode_NEXT(node)) = _odictnode_PREV(node);
726
727 _odictnode_PREV(node) = NULL;
728 _odictnode_NEXT(node) = NULL;
Eric Snow4fabf022015-06-04 00:09:56 -0600729 od->od_state++;
Eric Snow96c6af92015-05-29 22:21:39 -0600730}
731
732static _ODictNode *
733_odict_pop_node(PyODictObject *od, _ODictNode *node, PyObject *key)
734{
735 if (node == NULL) {
736 node = _odict_find_node(od, key);
737 if (node == NULL)
738 return NULL;
739 }
740 _odict_remove_node(od, node);
741 return node;
742}
743
744/* If someone calls PyDict_DelItem() directly on an OrderedDict, we'll
745 get all sorts of problems here. In PyODict_DelItem we make sure to
746 call _odict_clear_node first.
747
748 This matters in the case of colliding keys. Suppose we add 3 keys:
749 [A, B, C], where the hash of C collides with A and the next possible
750 index in the hash table is occupied by B. If we remove B then for C
751 the dict's looknode func will give us the old index of B instead of
752 the index we got before deleting B. However, the node for C in
753 od_fast_nodes is still at the old dict index of C. Thus to be sure
754 things don't get out of sync, we clear the node in od_fast_nodes
755 *before* calling PyDict_DelItem.
756
757 The same must be done for any other OrderedDict operations where
758 we modify od_fast_nodes.
759*/
760static int
761_odict_clear_node(PyODictObject *od, _ODictNode *node, PyObject *key)
762{
763 Py_ssize_t i;
764
765 assert(key != NULL);
766 if (_odict_EMPTY(od)) {
767 /* Let later code decide if this is a KeyError. */
768 return 0;
769 }
770
771 i = _odict_get_index(od, key);
772 if (i < 0)
773 return PyErr_Occurred() ? -1 : 0;
774
775 if (node == NULL)
776 node = od->od_fast_nodes[i];
777 assert(node == od->od_fast_nodes[i]);
778 if (node == NULL) {
779 /* Let later code decide if this is a KeyError. */
780 return 0;
781 }
782
783 // Now clear the node.
784 od->od_fast_nodes[i] = NULL;
785 _odict_remove_node(od, node);
786 _odictnode_DEALLOC(node);
787 return 0;
788}
789
790static void
791_odict_clear_nodes(PyODictObject *od)
792{
793 _ODictNode *node, *next;
794
795 if (!_odict_EMPTY(od)) {
796 node = _odict_FIRST(od);
797 while (node != NULL) {
798 next = _odictnode_NEXT(node);
799 _odictnode_DEALLOC(node);
800 node = next;
801 }
802 _odict_FIRST(od) = NULL;
803 _odict_LAST(od) = NULL;
804 }
805
806 _odict_free_fast_nodes(od);
807 od->od_fast_nodes = NULL;
808}
809
810/* There isn't any memory management of nodes past this point. */
811#undef _odictnode_DEALLOC
812
813static int
814_odict_keys_equal(PyODictObject *a, PyODictObject *b)
815{
816 _ODictNode *node_a, *node_b;
817
818 node_a = _odict_FIRST(a);
819 node_b = _odict_FIRST(b);
820 while (1) {
821 if (node_a == NULL && node_b == NULL)
822 /* success: hit the end of each at the same time */
823 return 1;
824 else if (node_a == NULL || node_b == NULL)
825 /* unequal length */
826 return 0;
827 else {
828 int res = PyObject_RichCompareBool(
829 (PyObject *)_odictnode_KEY(node_a),
830 (PyObject *)_odictnode_KEY(node_b),
831 Py_EQ);
832 if (res < 0)
833 return res;
834 else if (res == 0)
835 return 0;
836
837 /* otherwise it must match, so move on to the next one */
838 node_a = _odictnode_NEXT(node_a);
839 node_b = _odictnode_NEXT(node_b);
840 }
841 }
842}
843
844
845/* ----------------------------------------------
846 * OrderedDict mapping methods
847 */
848
849/* mp_ass_subscript: __setitem__() and __delitem__() */
850
851static int
852odict_mp_ass_sub(PyODictObject *od, PyObject *v, PyObject *w)
853{
854 if (w == NULL)
855 return PyODict_DelItem((PyObject *)od, v);
856 else
857 return PyODict_SetItem((PyObject *)od, v, w);
858}
859
860/* tp_as_mapping */
861
862static PyMappingMethods odict_as_mapping = {
863 0, /*mp_length*/
864 0, /*mp_subscript*/
865 (objobjargproc)odict_mp_ass_sub, /*mp_ass_subscript*/
866};
867
868
869/* ----------------------------------------------
870 * OrderedDict methods
871 */
872
873/* __delitem__() */
874
875PyDoc_STRVAR(odict_delitem__doc__, "od.__delitem__(y) <==> del od[y]");
876
877/* __eq__() */
878
879PyDoc_STRVAR(odict_eq__doc__,
880"od.__eq__(y) <==> od==y. Comparison to another OD is order-sensitive \n\
881 while comparison to a regular mapping is order-insensitive.\n\
882 ");
883
884/* forward */
885static PyObject * odict_richcompare(PyObject *v, PyObject *w, int op);
886
887static PyObject *
888odict_eq(PyObject *a, PyObject *b)
889{
890 return odict_richcompare(a, b, Py_EQ);
891}
892
893/* __init__() */
894
895PyDoc_STRVAR(odict_init__doc__,
896"Initialize an ordered dictionary. The signature is the same as\n\
897 regular dictionaries, but keyword arguments are not recommended because\n\
898 their insertion order is arbitrary.\n\
899\n\
900 ");
901
902/* forward */
903static int odict_init(PyObject *self, PyObject *args, PyObject *kwds);
904
905/* __iter__() */
906
907PyDoc_STRVAR(odict_iter__doc__, "od.__iter__() <==> iter(od)");
908
909static PyObject * odict_iter(PyODictObject *self); /* forward */
910
911/* __ne__() */
912
913/* Mapping.__ne__() does not have a docstring. */
914PyDoc_STRVAR(odict_ne__doc__, "");
915
916static PyObject *
917odict_ne(PyObject *a, PyObject *b)
918{
919 return odict_richcompare(a, b, Py_NE);
920}
921
922/* __repr__() */
923
924PyDoc_STRVAR(odict_repr__doc__, "od.__repr__() <==> repr(od)");
925
926static PyObject * odict_repr(PyODictObject *self); /* forward */
927
928/* __setitem__() */
929
930PyDoc_STRVAR(odict_setitem__doc__, "od.__setitem__(i, y) <==> od[i]=y");
931
932/* fromkeys() */
933
934PyDoc_STRVAR(odict_fromkeys__doc__,
935"OD.fromkeys(S[, v]) -> New ordered dictionary with keys from S.\n\
936 If not specified, the value defaults to None.\n\
937\n\
938 ");
939
940static PyObject *
Eric Snowac02ef32015-06-02 20:42:14 -0600941odict_fromkeys(PyObject *cls, PyObject *args, PyObject *kwargs)
Eric Snow96c6af92015-05-29 22:21:39 -0600942{
Eric Snowac02ef32015-06-02 20:42:14 -0600943 static char *kwlist[] = {"iterable", "value", 0};
Eric Snow96c6af92015-05-29 22:21:39 -0600944 PyObject *seq;
945 PyObject *value = Py_None;
Eric Snowac02ef32015-06-02 20:42:14 -0600946
947 /* both borrowed */
948 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|O:fromkeys", kwlist,
949 &seq, &value)) {
Eric Snow96c6af92015-05-29 22:21:39 -0600950 return NULL;
Eric Snowac02ef32015-06-02 20:42:14 -0600951 }
Eric Snow96c6af92015-05-29 22:21:39 -0600952 return _PyDict_FromKeys(cls, seq, value);
953}
954
955/* __sizeof__() */
956
957/* OrderedDict.__sizeof__() does not have a docstring. */
958PyDoc_STRVAR(odict_sizeof__doc__, "");
959
960static PyObject *
961odict_sizeof(PyODictObject *od)
962{
963 PyObject *pylong;
Eric Snowc5e59602015-05-30 11:28:56 -0600964 Py_ssize_t res, temp;
Eric Snow96c6af92015-05-29 22:21:39 -0600965
966 pylong = _PyDict_SizeOf((PyDictObject *)od);
967 if (pylong == NULL)
968 return NULL;
969 res = PyLong_AsSsize_t(pylong);
970 Py_DECREF(pylong);
971 if (res == -1 && PyErr_Occurred())
972 return NULL;
973
974 res += sizeof(PyODictObject) - sizeof(PyDictObject);
975
976 /* instance dict */
977 pylong = _PyDict_SizeOf((PyDictObject *)od->od_inst_dict);
978 if (pylong == NULL)
979 return NULL;
Eric Snowc5e59602015-05-30 11:28:56 -0600980 temp = PyLong_AsSsize_t(pylong);
Eric Snow96c6af92015-05-29 22:21:39 -0600981 Py_DECREF(pylong);
Eric Snowc5e59602015-05-30 11:28:56 -0600982 if (temp == -1 && PyErr_Occurred())
Eric Snow96c6af92015-05-29 22:21:39 -0600983 return NULL;
Eric Snowc5e59602015-05-30 11:28:56 -0600984 res += temp;
Eric Snow96c6af92015-05-29 22:21:39 -0600985
Eric Snow8c7f9552015-08-07 17:45:12 -0600986 res += sizeof(_ODictNode) * _odict_FAST_SIZE(od); /* od_fast_nodes */
Eric Snow96c6af92015-05-29 22:21:39 -0600987 if (!_odict_EMPTY(od)) {
988 res += sizeof(_ODictNode) * PyODict_SIZE(od); /* linked-list */
989 }
990 return PyLong_FromSsize_t(res);
991}
992
993/* __reduce__() */
994
995PyDoc_STRVAR(odict_reduce__doc__, "Return state information for pickling");
996
997static PyObject *
998odict_reduce(register PyODictObject *od)
999{
1000 _Py_IDENTIFIER(__dict__);
1001 _Py_IDENTIFIER(__class__);
1002 PyObject *vars = NULL, *ns = NULL, *result = NULL, *cls = NULL;
1003 PyObject *items_iter = NULL, *items = NULL, *args = NULL;
1004
1005 /* capture any instance state */
1006 vars = _PyObject_GetAttrId((PyObject *)od, &PyId___dict__);
Eric Snowc5e59602015-05-30 11:28:56 -06001007 if (vars == NULL)
1008 goto Done;
1009 else {
Eric Snow96c6af92015-05-29 22:21:39 -06001010 PyObject *empty, *od_vars, *iterator, *key;
Eric Snowc5e59602015-05-30 11:28:56 -06001011 int ns_len;
Eric Snow96c6af92015-05-29 22:21:39 -06001012
1013 /* od.__dict__ isn't necessarily a dict... */
1014 ns = PyObject_CallMethod((PyObject *)vars, "copy", NULL);
1015 if (ns == NULL)
1016 goto Done;
1017 empty = PyODict_New();
1018 if (empty == NULL)
1019 goto Done;
1020 od_vars = _PyObject_GetAttrId((PyObject *)empty, &PyId___dict__);
1021 Py_DECREF(empty);
1022 if (od_vars == NULL)
1023 goto Done;
1024 iterator = PyObject_GetIter(od_vars);
1025 Py_DECREF(od_vars);
1026 if (iterator == NULL)
1027 goto Done;
1028
1029 while ( (key = PyIter_Next(iterator)) ) {
1030 if (PyMapping_HasKey(ns, key) && PyMapping_DelItem(ns, key) != 0) {
1031 Py_DECREF(iterator);
1032 Py_DECREF(key);
1033 goto Done;
1034 }
1035 Py_DECREF(key);
1036 }
1037 Py_DECREF(iterator);
1038 if (PyErr_Occurred())
1039 goto Done;
1040
Eric Snowc5e59602015-05-30 11:28:56 -06001041 ns_len = PyObject_Length(ns);
1042 if (ns_len == -1)
1043 goto Done;
1044 if (!ns_len) {
Eric Snow96c6af92015-05-29 22:21:39 -06001045 /* nothing novel to pickle in od.__dict__ */
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001046 Py_CLEAR(ns);
Eric Snow96c6af92015-05-29 22:21:39 -06001047 }
1048 }
1049
1050 /* build the result */
1051 cls = _PyObject_GetAttrId((PyObject *)od, &PyId___class__);
1052 if (cls == NULL)
1053 goto Done;
1054
1055 args = PyTuple_New(0);
1056 if (args == NULL)
1057 goto Done;
1058
1059 items = PyObject_CallMethod((PyObject *)od, "items", NULL);
1060 if (items == NULL)
1061 goto Done;
1062
1063 items_iter = PyObject_GetIter(items);
1064 if (items_iter == NULL)
1065 goto Done;
1066
1067 result = PyTuple_Pack(5, cls, args, ns ? ns : Py_None, Py_None, items_iter);
1068
1069Done:
1070 Py_XDECREF(vars);
1071 Py_XDECREF(ns);
1072 Py_XDECREF(cls);
1073 Py_XDECREF(args);
1074 Py_XDECREF(items);
1075 Py_XDECREF(items_iter);
1076
1077 return result;
1078}
1079
1080/* setdefault() */
1081
1082PyDoc_STRVAR(odict_setdefault__doc__,
1083 "od.setdefault(k[,d]) -> od.get(k,d), also set od[k]=d if k not in od");
1084
1085/* Skips __missing__() calls. */
1086static PyObject *
Eric Snowac02ef32015-06-02 20:42:14 -06001087odict_setdefault(register PyODictObject *od, PyObject *args, PyObject *kwargs)
Eric Snow96c6af92015-05-29 22:21:39 -06001088{
Eric Snowac02ef32015-06-02 20:42:14 -06001089 static char *kwlist[] = {"key", "default", 0};
Eric Snow96c6af92015-05-29 22:21:39 -06001090 PyObject *key, *result = NULL;
1091 PyObject *failobj = Py_None;
1092
1093 /* both borrowed */
Eric Snowac02ef32015-06-02 20:42:14 -06001094 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|O:setdefault", kwlist,
1095 &key, &failobj)) {
Eric Snow96c6af92015-05-29 22:21:39 -06001096 return NULL;
Eric Snowac02ef32015-06-02 20:42:14 -06001097 }
Eric Snow96c6af92015-05-29 22:21:39 -06001098
1099 if (PyODict_CheckExact(od)) {
Eric Snowd1719752015-06-01 23:12:13 -06001100 result = PyODict_GetItemWithError(od, key); /* borrowed */
1101 if (result == NULL) {
1102 if (PyErr_Occurred())
1103 return NULL;
1104 assert(_odict_find_node(od, key) == NULL);
1105 if (PyODict_SetItem((PyObject *)od, key, failobj) >= 0) {
Eric Snow96c6af92015-05-29 22:21:39 -06001106 result = failobj;
1107 Py_INCREF(failobj);
1108 }
1109 }
1110 else {
Eric Snowd1719752015-06-01 23:12:13 -06001111 Py_INCREF(result);
Eric Snow96c6af92015-05-29 22:21:39 -06001112 }
1113 }
1114 else {
1115 int exists = PySequence_Contains((PyObject *)od, key);
1116 if (exists < 0) {
Eric Snowd1719752015-06-01 23:12:13 -06001117 return NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001118 }
1119 else if (exists) {
1120 result = PyObject_GetItem((PyObject *)od, key);
1121 }
1122 else if (PyObject_SetItem((PyObject *)od, key, failobj) >= 0) {
1123 result = failobj;
1124 Py_INCREF(failobj);
1125 }
1126 }
1127
Eric Snow96c6af92015-05-29 22:21:39 -06001128 return result;
1129}
1130
1131/* pop() */
1132
1133PyDoc_STRVAR(odict_pop__doc__,
1134"od.pop(k[,d]) -> v, remove specified key and return the corresponding\n\
1135 value. If key is not found, d is returned if given, otherwise KeyError\n\
1136 is raised.\n\
1137\n\
1138 ");
1139
1140/* forward */
1141static PyObject * _odict_popkey(PyObject *, PyObject *, PyObject *);
1142
1143/* Skips __missing__() calls. */
1144static PyObject *
Eric Snowac02ef32015-06-02 20:42:14 -06001145odict_pop(PyObject *od, PyObject *args, PyObject *kwargs)
Eric Snow96c6af92015-05-29 22:21:39 -06001146{
Eric Snowac02ef32015-06-02 20:42:14 -06001147 static char *kwlist[] = {"key", "default", 0};
Eric Snow96c6af92015-05-29 22:21:39 -06001148 PyObject *key, *failobj = NULL;
1149
Eric Snowac02ef32015-06-02 20:42:14 -06001150 /* borrowed */
1151 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|O:pop", kwlist,
1152 &key, &failobj)) {
Eric Snow96c6af92015-05-29 22:21:39 -06001153 return NULL;
1154 }
1155
1156 return _odict_popkey(od, key, failobj);
1157}
1158
1159static PyObject *
1160_odict_popkey(PyObject *od, PyObject *key, PyObject *failobj)
1161{
1162 _ODictNode *node;
1163 PyObject *value = NULL;
1164
Eric Snow96c6af92015-05-29 22:21:39 -06001165 /* Pop the node first to avoid a possible dict resize (due to
1166 eval loop reentrancy) and complications due to hash collision
1167 resolution. */
1168 node = _odict_find_node((PyODictObject *)od, key);
1169 if (node == NULL) {
1170 if (PyErr_Occurred())
Eric Snowd1719752015-06-01 23:12:13 -06001171 return NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001172 }
1173 else {
1174 int res = _odict_clear_node((PyODictObject *)od, node, key);
1175 if (res < 0) {
Eric Snowd1719752015-06-01 23:12:13 -06001176 return NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001177 }
1178 }
1179
1180 /* Now delete the value from the dict. */
1181 if (PyODict_CheckExact(od)) {
1182 if (node != NULL) {
1183 /* We could do PyDict_GetItem() and PyDict_DelItem() directly... */
1184 value = _PyDict_Pop((PyDictObject *)od, key, failobj);
1185 }
1186 }
1187 else {
1188 int exists = PySequence_Contains(od, key);
1189 if (exists < 0)
Eric Snowd1719752015-06-01 23:12:13 -06001190 return NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001191 if (exists) {
1192 value = PyObject_GetItem(od, key);
1193 if (value != NULL) {
1194 if (PyObject_DelItem(od, key) == -1) {
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001195 Py_CLEAR(value);
Eric Snow96c6af92015-05-29 22:21:39 -06001196 }
1197 }
1198 }
1199 }
1200
1201 /* Apply the fallback value, if necessary. */
1202 if (value == NULL && !PyErr_Occurred()) {
1203 if (failobj) {
1204 value = failobj;
1205 Py_INCREF(failobj);
1206 }
1207 else {
1208 PyErr_SetObject(PyExc_KeyError, key);
1209 }
1210 }
1211
Eric Snow96c6af92015-05-29 22:21:39 -06001212 return value;
1213}
1214
1215/* popitem() */
1216
1217PyDoc_STRVAR(odict_popitem__doc__,
1218"od.popitem() -> (k, v), return and remove a (key, value) pair.\n\
1219 Pairs are returned in LIFO order if last is true or FIFO order if false.\n\
1220\n\
1221 ");
1222
1223static PyObject *
Eric Snowac02ef32015-06-02 20:42:14 -06001224odict_popitem(PyObject *od, PyObject *args, PyObject *kwargs)
Eric Snow96c6af92015-05-29 22:21:39 -06001225{
Eric Snowac02ef32015-06-02 20:42:14 -06001226 static char *kwlist[] = {"last", 0};
Eric Snow96c6af92015-05-29 22:21:39 -06001227 PyObject *key, *value, *item = NULL, *last = NULL;
1228 _ODictNode *node;
Eric Snowac02ef32015-06-02 20:42:14 -06001229 int pos = -1;
Eric Snow96c6af92015-05-29 22:21:39 -06001230
1231 if (_odict_EMPTY((PyODictObject *)od)) {
1232 PyErr_SetString(PyExc_KeyError, "dictionary is empty");
1233 return NULL;
1234 }
1235
1236 /* pull the item */
1237
Eric Snowac02ef32015-06-02 20:42:14 -06001238 /* borrowed */
1239 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|O:popitem", kwlist,
1240 &last)) {
Eric Snow96c6af92015-05-29 22:21:39 -06001241 return NULL;
Eric Snowac02ef32015-06-02 20:42:14 -06001242 }
Eric Snow96c6af92015-05-29 22:21:39 -06001243
Eric Snowac02ef32015-06-02 20:42:14 -06001244 if (last != NULL) {
1245 int is_true;
1246 is_true = PyObject_IsTrue(last);
1247 if (is_true == -1)
1248 return NULL;
1249 pos = is_true ? -1 : 0;
1250 }
1251 if (pos == 0)
Eric Snow96c6af92015-05-29 22:21:39 -06001252 node = _odict_FIRST((PyODictObject *)od);
Eric Snowac02ef32015-06-02 20:42:14 -06001253 else
1254 node = _odict_LAST((PyODictObject *)od);
Eric Snow96c6af92015-05-29 22:21:39 -06001255
1256 key = _odictnode_KEY(node);
Eric Snowd1719752015-06-01 23:12:13 -06001257 Py_INCREF(key);
Eric Snow96c6af92015-05-29 22:21:39 -06001258 value = _odict_popkey(od, key, NULL);
1259 if (value == NULL)
1260 return NULL;
1261 item = PyTuple_Pack(2, key, value);
Eric Snowd1719752015-06-01 23:12:13 -06001262 Py_DECREF(key);
Eric Snow96c6af92015-05-29 22:21:39 -06001263 Py_DECREF(value);
1264 return item;
1265}
1266
1267/* keys() */
1268
1269/* MutableMapping.keys() does not have a docstring. */
1270PyDoc_STRVAR(odict_keys__doc__, "");
1271
1272static PyObject * odictkeys_new(PyObject *od); /* forward */
1273
1274/* values() */
1275
1276/* MutableMapping.values() does not have a docstring. */
1277PyDoc_STRVAR(odict_values__doc__, "");
1278
1279static PyObject * odictvalues_new(PyObject *od); /* forward */
1280
1281/* items() */
1282
1283/* MutableMapping.items() does not have a docstring. */
1284PyDoc_STRVAR(odict_items__doc__, "");
1285
1286static PyObject * odictitems_new(PyObject *od); /* forward */
1287
1288/* update() */
1289
1290/* MutableMapping.update() does not have a docstring. */
1291PyDoc_STRVAR(odict_update__doc__, "");
1292
1293/* forward */
1294static PyObject * mutablemapping_update(PyObject *, PyObject *, PyObject *);
1295
1296#define odict_update mutablemapping_update
1297
1298/* clear() */
1299
1300PyDoc_STRVAR(odict_clear__doc__,
1301 "od.clear() -> None. Remove all items from od.");
1302
1303static PyObject *
1304odict_clear(register PyODictObject *od)
1305{
1306 PyDict_Clear((PyObject *)od);
1307 _odict_clear_nodes(od);
1308 _odict_FIRST(od) = NULL;
1309 _odict_LAST(od) = NULL;
1310 if (_odict_resize(od) < 0)
1311 return NULL;
1312 Py_RETURN_NONE;
1313}
1314
1315/* copy() */
1316
1317PyDoc_STRVAR(odict_copy__doc__, "od.copy() -> a shallow copy of od");
1318
1319static PyObject *
1320odict_copy(register PyODictObject *od)
1321{
1322 _ODictNode *node;
1323 PyObject *od_copy;
1324
1325 if (PyODict_CheckExact(od))
1326 od_copy = PyODict_New();
1327 else
1328 od_copy = PyObject_CallFunctionObjArgs((PyObject *)Py_TYPE(od), NULL);
1329 if (od_copy == NULL)
1330 return NULL;
1331
1332 if (PyODict_CheckExact(od)) {
1333 _odict_FOREACH(od, node) {
Eric Snowa762af72015-06-01 22:59:08 -06001334 PyObject *key = _odictnode_KEY(node);
1335 PyObject *value = _odictnode_VALUE(node, od);
1336 if (value == NULL) {
1337 if (!PyErr_Occurred())
1338 PyErr_SetObject(PyExc_KeyError, key);
1339 goto fail;
1340 }
1341 if (PyODict_SetItem((PyObject *)od_copy, key, value) != 0)
Eric Snow96c6af92015-05-29 22:21:39 -06001342 goto fail;
1343 }
1344 }
1345 else {
1346 _odict_FOREACH(od, node) {
1347 int res;
1348 PyObject *value = PyObject_GetItem((PyObject *)od,
1349 _odictnode_KEY(node));
1350 if (value == NULL)
1351 goto fail;
1352 res = PyObject_SetItem((PyObject *)od_copy,
1353 _odictnode_KEY(node), value);
1354 Py_DECREF(value);
1355 if (res != 0)
1356 goto fail;
1357 }
1358 }
1359 return od_copy;
1360
1361fail:
1362 Py_DECREF(od_copy);
1363 return NULL;
1364}
1365
1366/* __reversed__() */
1367
1368PyDoc_STRVAR(odict_reversed__doc__, "od.__reversed__() <==> reversed(od)");
1369
1370#define _odict_ITER_REVERSED 1
1371#define _odict_ITER_KEYS 2
1372#define _odict_ITER_VALUES 4
1373
1374/* forward */
1375static PyObject * odictiter_new(PyODictObject *, int);
1376
1377static PyObject *
1378odict_reversed(PyODictObject *od)
1379{
Eric Snow96c6af92015-05-29 22:21:39 -06001380 return odictiter_new(od, _odict_ITER_KEYS|_odict_ITER_REVERSED);
1381}
1382
1383/* move_to_end() */
1384
1385PyDoc_STRVAR(odict_move_to_end__doc__,
1386"Move an existing element to the end (or beginning if last==False).\n\
1387\n\
1388 Raises KeyError if the element does not exist.\n\
1389 When last=True, acts like a fast version of self[key]=self.pop(key).\n\
1390\n\
1391 ");
1392
1393static PyObject *
Eric Snowac02ef32015-06-02 20:42:14 -06001394odict_move_to_end(PyODictObject *od, PyObject *args, PyObject *kwargs)
Eric Snow96c6af92015-05-29 22:21:39 -06001395{
Eric Snowac02ef32015-06-02 20:42:14 -06001396 static char *kwlist[] = {"key", "last", 0};
Eric Snow96c6af92015-05-29 22:21:39 -06001397 PyObject *key, *last = NULL;
1398 Py_ssize_t pos = -1;
1399
1400 /* both borrowed */
Eric Snowac02ef32015-06-02 20:42:14 -06001401 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|O:move_to_end", kwlist,
1402 &key, &last)) {
Eric Snow96c6af92015-05-29 22:21:39 -06001403 return NULL;
Eric Snowac02ef32015-06-02 20:42:14 -06001404 }
Eric Snow96c6af92015-05-29 22:21:39 -06001405 if (_odict_EMPTY(od)) {
1406 PyErr_SetObject(PyExc_KeyError, key);
Eric Snow96c6af92015-05-29 22:21:39 -06001407 return NULL;
1408 }
1409 if (last != NULL) {
Eric Snowc5e59602015-05-30 11:28:56 -06001410 int is_true;
Eric Snowc5e59602015-05-30 11:28:56 -06001411 is_true = PyObject_IsTrue(last);
Eric Snowc5e59602015-05-30 11:28:56 -06001412 if (is_true == -1)
1413 return NULL;
1414 pos = is_true ? -1 : 0;
Eric Snow96c6af92015-05-29 22:21:39 -06001415 }
1416 if (pos == 0) {
1417 /* Only move if not already the first one. */
1418 PyObject *first_key = _odictnode_KEY(_odict_FIRST(od));
Eric Snowc5e59602015-05-30 11:28:56 -06001419 int not_equal = PyObject_RichCompareBool(key, first_key, Py_NE);
1420 if (not_equal == -1)
1421 return NULL;
1422 if (not_equal) {
Eric Snow96c6af92015-05-29 22:21:39 -06001423 _ODictNode *node = _odict_pop_node(od, NULL, key);
1424 if (node != NULL) {
1425 _odict_add_head(od, node);
1426 }
1427 else {
1428 if (!PyErr_Occurred())
1429 PyErr_SetObject(PyExc_KeyError, key);
Eric Snow96c6af92015-05-29 22:21:39 -06001430 return NULL;
1431 }
1432 }
1433 }
1434 else if (pos == -1) {
1435 /* Only move if not already the last one. */
1436 PyObject *last_key = _odictnode_KEY(_odict_LAST(od));
Eric Snowc5e59602015-05-30 11:28:56 -06001437 int not_equal = PyObject_RichCompareBool(key, last_key, Py_NE);
1438 if (not_equal == -1)
1439 return NULL;
1440 if (not_equal) {
Eric Snow96c6af92015-05-29 22:21:39 -06001441 _ODictNode *node = _odict_pop_node(od, NULL, key);
1442 if (node != NULL) {
1443 _odict_add_tail(od, node);
1444 }
1445 else {
1446 if (!PyErr_Occurred())
1447 PyErr_SetObject(PyExc_KeyError, key);
Eric Snow96c6af92015-05-29 22:21:39 -06001448 return NULL;
1449 }
1450 }
1451 }
Eric Snow96c6af92015-05-29 22:21:39 -06001452 Py_RETURN_NONE;
1453}
1454
1455
1456/* tp_methods */
1457
1458static PyMethodDef odict_methods[] = {
1459
1460 /* explicitly defined so we can align docstrings with
1461 * collections.OrderedDict */
1462 {"__delitem__", (PyCFunction)odict_mp_ass_sub, METH_NOARGS,
1463 odict_delitem__doc__},
1464 {"__eq__", (PyCFunction)odict_eq, METH_NOARGS,
1465 odict_eq__doc__},
1466 {"__init__", (PyCFunction)odict_init, METH_NOARGS,
1467 odict_init__doc__},
1468 {"__iter__", (PyCFunction)odict_iter, METH_NOARGS,
1469 odict_iter__doc__},
1470 {"__ne__", (PyCFunction)odict_ne, METH_NOARGS,
1471 odict_ne__doc__},
1472 {"__repr__", (PyCFunction)odict_repr, METH_NOARGS,
1473 odict_repr__doc__},
1474 {"__setitem__", (PyCFunction)odict_mp_ass_sub, METH_NOARGS,
1475 odict_setitem__doc__},
Eric Snowac02ef32015-06-02 20:42:14 -06001476 {"fromkeys", (PyCFunction)odict_fromkeys,
1477 METH_VARARGS | METH_KEYWORDS | METH_CLASS, odict_fromkeys__doc__},
Eric Snow96c6af92015-05-29 22:21:39 -06001478
1479 /* overridden dict methods */
1480 {"__sizeof__", (PyCFunction)odict_sizeof, METH_NOARGS,
1481 odict_sizeof__doc__},
1482 {"__reduce__", (PyCFunction)odict_reduce, METH_NOARGS,
1483 odict_reduce__doc__},
Eric Snowac02ef32015-06-02 20:42:14 -06001484 {"setdefault", (PyCFunction)odict_setdefault,
1485 METH_VARARGS | METH_KEYWORDS, odict_setdefault__doc__},
1486 {"pop", (PyCFunction)odict_pop,
1487 METH_VARARGS | METH_KEYWORDS, odict_pop__doc__},
1488 {"popitem", (PyCFunction)odict_popitem,
1489 METH_VARARGS | METH_KEYWORDS, odict_popitem__doc__},
Eric Snow96c6af92015-05-29 22:21:39 -06001490 {"keys", (PyCFunction)odictkeys_new, METH_NOARGS,
1491 odict_keys__doc__},
1492 {"values", (PyCFunction)odictvalues_new, METH_NOARGS,
1493 odict_values__doc__},
1494 {"items", (PyCFunction)odictitems_new, METH_NOARGS,
1495 odict_items__doc__},
1496 {"update", (PyCFunction)odict_update, METH_VARARGS | METH_KEYWORDS,
1497 odict_update__doc__},
1498 {"clear", (PyCFunction)odict_clear, METH_NOARGS,
1499 odict_clear__doc__},
1500 {"copy", (PyCFunction)odict_copy, METH_NOARGS,
1501 odict_copy__doc__},
1502
1503 /* new methods */
1504 {"__reversed__", (PyCFunction)odict_reversed, METH_NOARGS,
1505 odict_reversed__doc__},
Eric Snowac02ef32015-06-02 20:42:14 -06001506 {"move_to_end", (PyCFunction)odict_move_to_end,
1507 METH_VARARGS | METH_KEYWORDS, odict_move_to_end__doc__},
Eric Snow96c6af92015-05-29 22:21:39 -06001508
1509 {NULL, NULL} /* sentinel */
1510};
1511
1512
1513/* ----------------------------------------------
1514 * OrderedDict members
1515 */
1516
1517/* tp_members */
1518
1519static PyMemberDef odict_members[] = {
1520 {"__dict__", T_OBJECT, offsetof(PyODictObject, od_inst_dict), READONLY},
1521 {0}
1522};
1523
1524
1525/* ----------------------------------------------
1526 * OrderedDict type slot methods
1527 */
1528
1529/* tp_dealloc */
1530
1531static void
1532odict_dealloc(PyODictObject *self)
1533{
1534 PyObject_GC_UnTrack(self);
1535 Py_TRASHCAN_SAFE_BEGIN(self);
1536 Py_XDECREF(self->od_inst_dict);
1537 if (self->od_weakreflist != NULL)
1538 PyObject_ClearWeakRefs((PyObject *)self);
1539
1540 _odict_clear_nodes(self);
1541 Py_TRASHCAN_SAFE_END(self);
1542
1543 /* must be last */
1544 PyDict_Type.tp_dealloc((PyObject *)self);
1545};
1546
1547/* tp_repr */
1548
1549static PyObject *
1550odict_repr(PyODictObject *self)
1551{
1552 int i;
1553 const char *formatstr;
1554 _Py_IDENTIFIER(__class__);
1555 _Py_IDENTIFIER(__name__);
1556 Py_ssize_t count = -1;
1557 PyObject *pieces = NULL, *result = NULL, *cls = NULL;
1558 PyObject *classname = NULL, *format = NULL, *args = NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001559
1560 i = Py_ReprEnter((PyObject *)self);
1561 if (i != 0) {
1562 return i > 0 ? PyUnicode_FromString("...") : NULL;
1563 }
1564
1565 if (PyODict_SIZE(self) == 0) {
1566 /* "OrderedDict()" */
1567 goto Finish;
1568 }
1569
1570 if (PyODict_CheckExact(self)) {
Eric Snowa762af72015-06-01 22:59:08 -06001571 _ODictNode *node;
Eric Snow96c6af92015-05-29 22:21:39 -06001572 pieces = PyList_New(PyODict_SIZE(self));
1573 if (pieces == NULL)
1574 goto Done;
1575
1576 _odict_FOREACH(self, node) {
Eric Snowa762af72015-06-01 22:59:08 -06001577 PyObject *pair;
1578 PyObject *key = _odictnode_KEY(node);
1579 PyObject *value = _odictnode_VALUE(node, self);
1580 if (value == NULL) {
1581 if (!PyErr_Occurred())
1582 PyErr_SetObject(PyExc_KeyError, key);
Eric Snowdb4061c2015-06-03 11:09:48 -06001583 goto Done;
Eric Snowa762af72015-06-01 22:59:08 -06001584 }
1585 pair = PyTuple_Pack(2, key, value);
Eric Snow96c6af92015-05-29 22:21:39 -06001586 if (pair == NULL)
1587 goto Done;
1588
1589 PyList_SET_ITEM(pieces, ++count, pair); /* steals reference */
1590 }
1591 }
1592 else {
1593 PyObject *items = PyObject_CallMethod((PyObject *)self, "items", NULL);
1594 if (items == NULL)
1595 goto Done;
1596 pieces = PySequence_List(items);
1597 Py_DECREF(items);
1598 if(pieces == NULL)
1599 goto Done;
1600 }
1601
1602Finish:
1603 cls = _PyObject_GetAttrId((PyObject *)self, &PyId___class__);
1604 if (cls == NULL)
1605 goto Done;
1606 classname = _PyObject_GetAttrId(cls, &PyId___name__);
1607 if (classname == NULL)
1608 goto Done;
1609
1610 if (pieces == NULL) {
1611 formatstr = "%s()";
1612 args = PyTuple_Pack(1, classname);
1613 }
1614 else {
1615 formatstr = "%s(%r)";
1616 args = PyTuple_Pack(2, classname, pieces);
1617 }
1618 if (args == NULL)
1619 goto Done;
1620
1621 format = PyUnicode_InternFromString(formatstr);
1622 if (format == NULL)
1623 goto Done;
1624
1625 result = PyUnicode_Format(format, args);
1626Done:
1627 Py_XDECREF(pieces);
1628 Py_XDECREF(cls);
1629 Py_XDECREF(classname);
1630 Py_XDECREF(format);
1631 Py_XDECREF(args);
1632 Py_ReprLeave((PyObject *)self);
1633 return result;
1634};
1635
1636/* tp_doc */
1637
1638PyDoc_STRVAR(odict_doc,
1639 "Dictionary that remembers insertion order");
1640
1641/* tp_traverse */
1642
1643static int
1644odict_traverse(PyODictObject *od, visitproc visit, void *arg)
1645{
1646 Py_VISIT(od->od_inst_dict);
1647 Py_VISIT(od->od_weakreflist);
1648 return PyDict_Type.tp_traverse((PyObject *)od, visit, arg);
1649}
1650
1651/* tp_clear */
1652
1653static int
1654odict_tp_clear(PyODictObject *od)
1655{
1656 PyObject *res;
1657 Py_CLEAR(od->od_inst_dict);
1658 Py_CLEAR(od->od_weakreflist);
1659 res = odict_clear(od);
1660 if (res == NULL)
1661 return -1;
1662 Py_DECREF(res);
1663 return 0;
1664}
1665
1666/* tp_richcompare */
1667
1668static PyObject *
1669odict_richcompare(PyObject *v, PyObject *w, int op)
1670{
1671 if (!PyODict_Check(v) || !PyDict_Check(w)) {
1672 Py_RETURN_NOTIMPLEMENTED;
1673 }
1674
1675 if (op == Py_EQ || op == Py_NE) {
1676 PyObject *res, *cmp;
1677 int eq;
1678
1679 cmp = PyDict_Type.tp_richcompare(v, w, op);
1680 if (cmp == NULL)
1681 return NULL;
1682 if (!PyODict_Check(w))
1683 return cmp;
1684 if (op == Py_EQ && cmp == Py_False)
1685 return cmp;
1686 if (op == Py_NE && cmp == Py_True)
1687 return cmp;
1688 Py_DECREF(cmp);
1689
1690 /* Try comparing odict keys. */
1691 eq = _odict_keys_equal((PyODictObject *)v, (PyODictObject *)w);
1692 if (eq < 0)
1693 return NULL;
1694
1695 res = (eq == (op == Py_EQ)) ? Py_True : Py_False;
1696 Py_INCREF(res);
1697 return res;
1698 } else {
1699 Py_RETURN_NOTIMPLEMENTED;
1700 }
1701};
1702
1703/* tp_iter */
1704
1705static PyObject *
1706odict_iter(PyODictObject *od)
1707{
1708 return odictiter_new(od, _odict_ITER_KEYS);
1709};
1710
1711/* tp_init */
1712
1713static int
1714odict_init(PyObject *self, PyObject *args, PyObject *kwds)
1715{
1716 PyObject *res;
1717 Py_ssize_t len = PyObject_Length(args);
1718
1719 if (len == -1)
1720 return -1;
1721 if (len > 1) {
1722 char *msg = "expected at most 1 arguments, got %d";
1723 PyErr_Format(PyExc_TypeError, msg, len);
1724 return -1;
1725 }
1726
1727 /* __init__() triggering update() is just the way things are! */
1728 res = odict_update(self, args, kwds);
1729 if (res == NULL) {
1730 return -1;
1731 } else {
1732 Py_DECREF(res);
1733 return 0;
1734 }
1735};
1736
1737/* tp_new */
1738
1739static PyObject *
1740odict_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1741{
1742 PyObject *od = PyDict_Type.tp_new(type, args, kwds);
1743 if (od != NULL) {
Eric Snow96c6af92015-05-29 22:21:39 -06001744 if (_odict_initialize((PyODictObject *)od) < 0)
1745 return NULL;
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001746 ((PyODictObject *)od)->od_inst_dict = PyDict_New();
1747 ((PyODictObject *)od)->od_weakreflist = NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001748 }
1749 return od;
1750}
1751
1752/* PyODict_Type */
1753
1754PyTypeObject PyODict_Type = {
1755 PyVarObject_HEAD_INIT(&PyType_Type, 0)
1756 "collections.OrderedDict", /* tp_name */
1757 sizeof(PyODictObject), /* tp_basicsize */
1758 0, /* tp_itemsize */
1759 (destructor)odict_dealloc, /* tp_dealloc */
1760 0, /* tp_print */
1761 0, /* tp_getattr */
1762 0, /* tp_setattr */
1763 0, /* tp_reserved */
1764 (reprfunc)odict_repr, /* tp_repr */
1765 0, /* tp_as_number */
1766 0, /* tp_as_sequence */
1767 &odict_as_mapping, /* tp_as_mapping */
1768 0, /* tp_hash */
1769 0, /* tp_call */
1770 0, /* tp_str */
1771 0, /* tp_getattro */
1772 0, /* tp_setattro */
1773 0, /* tp_as_buffer */
1774 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC,/* tp_flags */
1775 odict_doc, /* tp_doc */
1776 (traverseproc)odict_traverse, /* tp_traverse */
1777 (inquiry)odict_tp_clear, /* tp_clear */
1778 (richcmpfunc)odict_richcompare, /* tp_richcompare */
1779 offsetof(PyODictObject, od_weakreflist), /* tp_weaklistoffset */
1780 (getiterfunc)odict_iter, /* tp_iter */
1781 0, /* tp_iternext */
1782 odict_methods, /* tp_methods */
1783 odict_members, /* tp_members */
1784 0, /* tp_getset */
1785 &PyDict_Type, /* tp_base */
1786 0, /* tp_dict */
1787 0, /* tp_descr_get */
1788 0, /* tp_descr_set */
1789 offsetof(PyODictObject, od_inst_dict), /* tp_dictoffset */
1790 (initproc)odict_init, /* tp_init */
1791 PyType_GenericAlloc, /* tp_alloc */
1792 (newfunc)odict_new, /* tp_new */
1793 0, /* tp_free */
1794};
1795
1796
1797/* ----------------------------------------------
1798 * the public OrderedDict API
1799 */
1800
1801PyObject *
1802PyODict_New(void) {
1803 return odict_new(&PyODict_Type, NULL, NULL);
1804};
1805
1806int
1807PyODict_SetItem(PyObject *od, PyObject *key, PyObject *value) {
1808 int res = PyDict_SetItem(od, key, value);
1809 if (res == 0) {
1810 res = _odict_add_new_node((PyODictObject *)od, key);
Eric Snowc5e59602015-05-30 11:28:56 -06001811 /* XXX Revert setting the value on the dict? */
Eric Snow96c6af92015-05-29 22:21:39 -06001812 }
1813 return res;
1814};
1815
1816int
1817PyODict_DelItem(PyObject *od, PyObject *key) {
1818 int res = _odict_clear_node((PyODictObject *)od, NULL, key);
1819 if (res < 0)
1820 return -1;
1821 return PyDict_DelItem(od, key);
1822};
1823
1824
1825/* -------------------------------------------
1826 * The OrderedDict views (keys/values/items)
1827 */
1828
1829typedef struct {
1830 PyObject_HEAD
1831 int kind;
1832 PyODictObject *di_odict;
Eric Snowb952ab42015-06-01 23:35:13 -06001833 Py_ssize_t di_size;
Eric Snow4fabf022015-06-04 00:09:56 -06001834 size_t di_state;
Eric Snow96c6af92015-05-29 22:21:39 -06001835 PyObject *di_current;
1836 PyObject *di_result; /* reusable result tuple for iteritems */
1837} odictiterobject;
1838
1839static void
1840odictiter_dealloc(odictiterobject *di)
1841{
1842 _PyObject_GC_UNTRACK(di);
Eric Snowa762af72015-06-01 22:59:08 -06001843 Py_XDECREF(di->di_odict);
Eric Snow96c6af92015-05-29 22:21:39 -06001844 Py_XDECREF(di->di_current);
1845 if (di->kind & (_odict_ITER_KEYS | _odict_ITER_VALUES)) {
1846 Py_DECREF(di->di_result);
1847 }
1848 PyObject_GC_Del(di);
1849}
1850
1851static int
1852odictiter_traverse(odictiterobject *di, visitproc visit, void *arg)
1853{
1854 Py_VISIT(di->di_odict);
1855 Py_VISIT(di->di_current); /* A key could be any type, not just str. */
1856 Py_VISIT(di->di_result);
1857 return 0;
1858}
1859
Eric Snowa762af72015-06-01 22:59:08 -06001860/* In order to protect against modifications during iteration, we track
1861 * the current key instead of the current node. */
Eric Snow96c6af92015-05-29 22:21:39 -06001862static PyObject *
1863odictiter_nextkey(odictiterobject *di)
1864{
Eric Snowa762af72015-06-01 22:59:08 -06001865 PyObject *key = NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001866 _ODictNode *node;
1867 int reversed = di->kind & _odict_ITER_REVERSED;
1868
Eric Snowa762af72015-06-01 22:59:08 -06001869 if (di->di_odict == NULL)
Eric Snow96c6af92015-05-29 22:21:39 -06001870 return NULL;
Eric Snowa762af72015-06-01 22:59:08 -06001871 if (di->di_current == NULL)
1872 goto done; /* We're already done. */
1873
Eric Snowb952ab42015-06-01 23:35:13 -06001874 /* Check for unsupported changes. */
Eric Snow4fabf022015-06-04 00:09:56 -06001875 if (di->di_odict->od_state != di->di_state) {
1876 PyErr_SetString(PyExc_RuntimeError,
1877 "OrderedDict mutated during iteration");
1878 goto done;
1879 }
Eric Snowb952ab42015-06-01 23:35:13 -06001880 if (di->di_size != PyODict_SIZE(di->di_odict)) {
1881 PyErr_SetString(PyExc_RuntimeError,
1882 "OrderedDict changed size during iteration");
1883 di->di_size = -1; /* Make this state sticky */
1884 return NULL;
1885 }
1886
Eric Snowa762af72015-06-01 22:59:08 -06001887 /* Get the key. */
Eric Snow96c6af92015-05-29 22:21:39 -06001888 node = _odict_find_node(di->di_odict, di->di_current);
1889 if (node == NULL) {
1890 /* Must have been deleted. */
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001891 Py_CLEAR(di->di_current);
Eric Snow96c6af92015-05-29 22:21:39 -06001892 return NULL;
1893 }
1894 key = di->di_current;
1895
1896 /* Advance to the next key. */
1897 node = reversed ? _odictnode_PREV(node) : _odictnode_NEXT(node);
1898 if (node == NULL) {
1899 /* Reached the end. */
1900 di->di_current = NULL;
1901 }
1902 else {
1903 di->di_current = _odictnode_KEY(node);
1904 Py_INCREF(di->di_current);
1905 }
1906
1907 return key;
Eric Snowa762af72015-06-01 22:59:08 -06001908
1909done:
1910 Py_CLEAR(di->di_odict);
1911 return key;
Eric Snow96c6af92015-05-29 22:21:39 -06001912}
1913
1914static PyObject *
1915odictiter_iternext(odictiterobject *di)
1916{
1917 PyObject *value;
1918 PyObject *key = odictiter_nextkey(di); /* new reference */
1919
1920 if (key == NULL)
1921 return NULL;
1922
1923 /* Handle the keys case. */
1924 if (! (di->kind & _odict_ITER_VALUES)) {
1925 return key;
1926 }
1927
1928 /* Handle the items case. */
1929 if (di->kind & _odict_ITER_KEYS) {
1930 PyObject *result = di->di_result;
1931
1932 value = PyODict_GetItem((PyObject *)di->di_odict, key); /* borrowed */
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001933 if (value == NULL) {
Eric Snowa762af72015-06-01 22:59:08 -06001934 if (!PyErr_Occurred())
1935 PyErr_SetObject(PyExc_KeyError, key);
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001936 Py_DECREF(key);
Eric Snowa762af72015-06-01 22:59:08 -06001937 goto done;
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001938 }
1939 Py_INCREF(value);
Eric Snow96c6af92015-05-29 22:21:39 -06001940
1941 if (result->ob_refcnt == 1) {
1942 /* not in use so we can reuse it
1943 * (the common case during iteration) */
1944 Py_INCREF(result);
1945 Py_DECREF(PyTuple_GET_ITEM(result, 0)); /* borrowed */
1946 Py_DECREF(PyTuple_GET_ITEM(result, 1)); /* borrowed */
1947 }
1948 else {
1949 result = PyTuple_New(2);
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001950 if (result == NULL) {
1951 Py_DECREF(key);
1952 Py_DECREF(value);
Eric Snowa762af72015-06-01 22:59:08 -06001953 goto done;
Eric Snowe3dfa9e2015-05-30 12:51:15 -06001954 }
Eric Snow96c6af92015-05-29 22:21:39 -06001955 }
1956
Eric Snow96c6af92015-05-29 22:21:39 -06001957 PyTuple_SET_ITEM(result, 0, key); /* steals reference */
1958 PyTuple_SET_ITEM(result, 1, value); /* steals reference */
1959
1960 return result;
1961 }
1962 /* Handle the values case. */
1963 else {
1964 value = PyODict_GetItem((PyObject *)di->di_odict, key);
Eric Snow96c6af92015-05-29 22:21:39 -06001965 Py_DECREF(key);
Eric Snowa762af72015-06-01 22:59:08 -06001966 if (value == NULL) {
1967 if (!PyErr_Occurred())
1968 PyErr_SetObject(PyExc_KeyError, key);
1969 goto done;
1970 }
1971 Py_INCREF(value);
Eric Snow96c6af92015-05-29 22:21:39 -06001972 return value;
1973 }
Eric Snowa762af72015-06-01 22:59:08 -06001974
1975done:
1976 Py_CLEAR(di->di_current);
1977 Py_CLEAR(di->di_odict);
1978 return NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06001979}
1980
1981/* No need for tp_clear because odictiterobject is not mutable. */
1982
1983PyDoc_STRVAR(reduce_doc, "Return state information for pickling");
1984
1985static PyObject *
1986odictiter_reduce(odictiterobject *di)
1987{
Eric Snowc5e59602015-05-30 11:28:56 -06001988 PyObject *list, *iter;
Eric Snow96c6af92015-05-29 22:21:39 -06001989
1990 list = PyList_New(0);
1991 if (!list)
1992 return NULL;
1993
1994 /* iterate the temporary into a list */
1995 for(;;) {
1996 PyObject *element = odictiter_iternext(di);
1997 if (element) {
1998 if (PyList_Append(list, element)) {
1999 Py_DECREF(element);
2000 Py_DECREF(list);
2001 return NULL;
2002 }
2003 Py_DECREF(element);
2004 }
2005 else {
2006 /* done iterating? */
2007 break;
2008 }
2009 }
2010 if (PyErr_Occurred()) {
2011 Py_DECREF(list);
2012 return NULL;
2013 }
Eric Snowc5e59602015-05-30 11:28:56 -06002014 iter = _PyObject_GetBuiltin("iter");
2015 if (iter == NULL) {
2016 Py_DECREF(list);
2017 return NULL;
2018 }
2019 return Py_BuildValue("N(N)", iter, list);
Eric Snow96c6af92015-05-29 22:21:39 -06002020}
2021
2022static PyMethodDef odictiter_methods[] = {
2023 {"__reduce__", (PyCFunction)odictiter_reduce, METH_NOARGS, reduce_doc},
2024 {NULL, NULL} /* sentinel */
2025};
2026
2027PyTypeObject PyODictIter_Type = {
2028 PyVarObject_HEAD_INIT(&PyType_Type, 0)
2029 "odict_iterator", /* tp_name */
2030 sizeof(odictiterobject), /* tp_basicsize */
2031 0, /* tp_itemsize */
2032 /* methods */
2033 (destructor)odictiter_dealloc, /* tp_dealloc */
2034 0, /* tp_print */
2035 0, /* tp_getattr */
2036 0, /* tp_setattr */
2037 0, /* tp_reserved */
2038 0, /* tp_repr */
2039 0, /* tp_as_number */
2040 0, /* tp_as_sequence */
2041 0, /* tp_as_mapping */
2042 0, /* tp_hash */
2043 0, /* tp_call */
2044 0, /* tp_str */
2045 PyObject_GenericGetAttr, /* tp_getattro */
2046 0, /* tp_setattro */
2047 0, /* tp_as_buffer */
2048 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
2049 0, /* tp_doc */
2050 (traverseproc)odictiter_traverse, /* tp_traverse */
2051 0, /* tp_clear */
2052 0, /* tp_richcompare */
2053 0, /* tp_weaklistoffset */
2054 PyObject_SelfIter, /* tp_iter */
2055 (iternextfunc)odictiter_iternext, /* tp_iternext */
2056 odictiter_methods, /* tp_methods */
2057 0,
2058};
2059
2060static PyObject *
2061odictiter_new(PyODictObject *od, int kind)
2062{
2063 odictiterobject *di;
2064 _ODictNode *node;
2065 int reversed = kind & _odict_ITER_REVERSED;
2066
2067 di = PyObject_GC_New(odictiterobject, &PyODictIter_Type);
2068 if (di == NULL)
2069 return NULL;
2070
2071 if (kind & (_odict_ITER_KEYS | _odict_ITER_VALUES)){
2072 di->di_result = PyTuple_Pack(2, Py_None, Py_None);
2073 if (di->di_result == NULL) {
2074 Py_DECREF(di);
2075 return NULL;
2076 }
2077 }
2078 else
2079 di->di_result = NULL;
2080
2081 di->kind = kind;
2082 node = reversed ? _odict_LAST(od) : _odict_FIRST(od);
2083 di->di_current = node ? _odictnode_KEY(node) : NULL;
2084 Py_XINCREF(di->di_current);
Eric Snowb952ab42015-06-01 23:35:13 -06002085 di->di_size = PyODict_SIZE(od);
Eric Snow4fabf022015-06-04 00:09:56 -06002086 di->di_state = od->od_state;
Eric Snow96c6af92015-05-29 22:21:39 -06002087 di->di_odict = od;
2088 Py_INCREF(od);
2089
2090 _PyObject_GC_TRACK(di);
2091 return (PyObject *)di;
2092}
2093
2094/* keys() */
2095
2096static PyObject *
2097odictkeys_iter(_PyDictViewObject *dv)
2098{
2099 if (dv->dv_dict == NULL) {
2100 Py_RETURN_NONE;
2101 }
2102 return odictiter_new((PyODictObject *)dv->dv_dict,
2103 _odict_ITER_KEYS);
2104}
2105
2106static PyObject *
2107odictkeys_reversed(_PyDictViewObject *dv)
2108{
2109 if (dv->dv_dict == NULL) {
2110 Py_RETURN_NONE;
2111 }
2112 return odictiter_new((PyODictObject *)dv->dv_dict,
2113 _odict_ITER_KEYS|_odict_ITER_REVERSED);
2114}
2115
2116static PyMethodDef odictkeys_methods[] = {
2117 {"__reversed__", (PyCFunction)odictkeys_reversed, METH_NOARGS, NULL},
2118 {NULL, NULL} /* sentinel */
2119};
2120
2121PyTypeObject PyODictKeys_Type = {
2122 PyVarObject_HEAD_INIT(&PyType_Type, 0)
2123 "odict_keys", /* tp_name */
2124 0, /* tp_basicsize */
2125 0, /* tp_itemsize */
2126 0, /* tp_dealloc */
2127 0, /* tp_print */
2128 0, /* tp_getattr */
2129 0, /* tp_setattr */
2130 0, /* tp_reserved */
2131 0, /* tp_repr */
2132 0, /* tp_as_number */
2133 0, /* tp_as_sequence */
2134 0, /* tp_as_mapping */
2135 0, /* tp_hash */
2136 0, /* tp_call */
2137 0, /* tp_str */
2138 0, /* tp_getattro */
2139 0, /* tp_setattro */
2140 0, /* tp_as_buffer */
2141 0, /* tp_flags */
2142 0, /* tp_doc */
2143 0, /* tp_traverse */
2144 0, /* tp_clear */
2145 0, /* tp_richcompare */
2146 0, /* tp_weaklistoffset */
2147 (getiterfunc)odictkeys_iter, /* tp_iter */
2148 0, /* tp_iternext */
2149 odictkeys_methods, /* tp_methods */
2150 0, /* tp_members */
2151 0, /* tp_getset */
2152 &PyDictKeys_Type, /* tp_base */
2153};
2154
2155static PyObject *
2156odictkeys_new(PyObject *od)
2157{
2158 return _PyDictView_New(od, &PyODictKeys_Type);
2159}
2160
2161/* items() */
2162
2163static PyObject *
2164odictitems_iter(_PyDictViewObject *dv)
2165{
2166 if (dv->dv_dict == NULL) {
2167 Py_RETURN_NONE;
2168 }
2169 return odictiter_new((PyODictObject *)dv->dv_dict,
2170 _odict_ITER_KEYS|_odict_ITER_VALUES);
2171}
2172
2173static PyObject *
2174odictitems_reversed(_PyDictViewObject *dv)
2175{
2176 if (dv->dv_dict == NULL) {
2177 Py_RETURN_NONE;
2178 }
2179 return odictiter_new((PyODictObject *)dv->dv_dict,
2180 _odict_ITER_KEYS|_odict_ITER_VALUES|_odict_ITER_REVERSED);
2181}
2182
2183static PyMethodDef odictitems_methods[] = {
2184 {"__reversed__", (PyCFunction)odictitems_reversed, METH_NOARGS, NULL},
2185 {NULL, NULL} /* sentinel */
2186};
2187
2188PyTypeObject PyODictItems_Type = {
2189 PyVarObject_HEAD_INIT(&PyType_Type, 0)
2190 "odict_items", /* tp_name */
2191 0, /* tp_basicsize */
2192 0, /* tp_itemsize */
2193 0, /* tp_dealloc */
2194 0, /* tp_print */
2195 0, /* tp_getattr */
2196 0, /* tp_setattr */
2197 0, /* tp_reserved */
2198 0, /* tp_repr */
2199 0, /* tp_as_number */
2200 0, /* tp_as_sequence */
2201 0, /* tp_as_mapping */
2202 0, /* tp_hash */
2203 0, /* tp_call */
2204 0, /* tp_str */
2205 0, /* tp_getattro */
2206 0, /* tp_setattro */
2207 0, /* tp_as_buffer */
2208 0, /* tp_flags */
2209 0, /* tp_doc */
2210 0, /* tp_traverse */
2211 0, /* tp_clear */
2212 0, /* tp_richcompare */
2213 0, /* tp_weaklistoffset */
2214 (getiterfunc)odictitems_iter, /* tp_iter */
2215 0, /* tp_iternext */
2216 odictitems_methods, /* tp_methods */
2217 0, /* tp_members */
2218 0, /* tp_getset */
2219 &PyDictItems_Type, /* tp_base */
2220};
2221
2222static PyObject *
2223odictitems_new(PyObject *od)
2224{
2225 return _PyDictView_New(od, &PyODictItems_Type);
2226}
2227
2228/* values() */
2229
2230static PyObject *
2231odictvalues_iter(_PyDictViewObject *dv)
2232{
2233 if (dv->dv_dict == NULL) {
2234 Py_RETURN_NONE;
2235 }
2236 return odictiter_new((PyODictObject *)dv->dv_dict,
2237 _odict_ITER_VALUES);
2238}
2239
2240static PyObject *
2241odictvalues_reversed(_PyDictViewObject *dv)
2242{
2243 if (dv->dv_dict == NULL) {
2244 Py_RETURN_NONE;
2245 }
2246 return odictiter_new((PyODictObject *)dv->dv_dict,
2247 _odict_ITER_VALUES|_odict_ITER_REVERSED);
2248}
2249
2250static PyMethodDef odictvalues_methods[] = {
2251 {"__reversed__", (PyCFunction)odictvalues_reversed, METH_NOARGS, NULL},
2252 {NULL, NULL} /* sentinel */
2253};
2254
2255PyTypeObject PyODictValues_Type = {
2256 PyVarObject_HEAD_INIT(&PyType_Type, 0)
2257 "odict_values", /* tp_name */
2258 0, /* tp_basicsize */
2259 0, /* tp_itemsize */
2260 0, /* tp_dealloc */
2261 0, /* tp_print */
2262 0, /* tp_getattr */
2263 0, /* tp_setattr */
2264 0, /* tp_reserved */
2265 0, /* tp_repr */
2266 0, /* tp_as_number */
2267 0, /* tp_as_sequence */
2268 0, /* tp_as_mapping */
2269 0, /* tp_hash */
2270 0, /* tp_call */
2271 0, /* tp_str */
2272 0, /* tp_getattro */
2273 0, /* tp_setattro */
2274 0, /* tp_as_buffer */
2275 0, /* tp_flags */
2276 0, /* tp_doc */
2277 0, /* tp_traverse */
2278 0, /* tp_clear */
2279 0, /* tp_richcompare */
2280 0, /* tp_weaklistoffset */
2281 (getiterfunc)odictvalues_iter, /* tp_iter */
2282 0, /* tp_iternext */
2283 odictvalues_methods, /* tp_methods */
2284 0, /* tp_members */
2285 0, /* tp_getset */
2286 &PyDictValues_Type, /* tp_base */
2287};
2288
2289static PyObject *
2290odictvalues_new(PyObject *od)
2291{
2292 return _PyDictView_New(od, &PyODictValues_Type);
2293}
2294
2295
2296/* ----------------------------------------------
2297 MutableMappping implementations
2298
2299Mapping:
2300
2301============ ===========
2302method uses
2303============ ===========
2304__contains__ __getitem__
2305__eq__ items
2306__getitem__ +
2307__iter__ +
2308__len__ +
2309__ne__ __eq__
2310get __getitem__
2311items ItemsView
2312keys KeysView
2313values ValuesView
2314============ ===========
2315
2316ItemsView uses __len__, __iter__, and __getitem__.
2317KeysView uses __len__, __iter__, and __contains__.
2318ValuesView uses __len__, __iter__, and __getitem__.
2319
2320MutableMapping:
2321
2322============ ===========
2323method uses
2324============ ===========
2325__delitem__ +
2326__setitem__ +
2327clear popitem
2328pop __getitem__
2329 __delitem__
2330popitem __iter__
2331 _getitem__
2332 __delitem__
2333setdefault __getitem__
2334 __setitem__
2335update __setitem__
2336============ ===========
2337*/
2338
2339static int
2340mutablemapping_add_pairs(PyObject *self, PyObject *pairs)
2341{
2342 PyObject *pair, *iterator, *unexpected;
2343 int res = 0;
2344
2345 iterator = PyObject_GetIter(pairs);
2346 if (iterator == NULL)
2347 return -1;
2348 PyErr_Clear();
2349
2350 while ((pair = PyIter_Next(iterator)) != NULL) {
2351 /* could be more efficient (see UNPACK_SEQUENCE in ceval.c) */
Eric Snowc5e59602015-05-30 11:28:56 -06002352 PyObject *key = NULL, *value = NULL;
Eric Snow96c6af92015-05-29 22:21:39 -06002353 PyObject *pair_iterator = PyObject_GetIter(pair);
Eric Snowc5e59602015-05-30 11:28:56 -06002354 if (pair_iterator == NULL)
2355 goto Done;
Eric Snow96c6af92015-05-29 22:21:39 -06002356
2357 key = PyIter_Next(pair_iterator);
2358 if (key == NULL) {
2359 if (!PyErr_Occurred())
2360 PyErr_SetString(PyExc_ValueError,
2361 "need more than 0 values to unpack");
2362 goto Done;
2363 }
2364
2365 value = PyIter_Next(pair_iterator);
2366 if (value == NULL) {
2367 if (!PyErr_Occurred())
2368 PyErr_SetString(PyExc_ValueError,
2369 "need more than 1 value to unpack");
2370 goto Done;
2371 }
2372
2373 unexpected = PyIter_Next(pair_iterator);
2374 if (unexpected != NULL) {
2375 Py_DECREF(unexpected);
2376 PyErr_SetString(PyExc_ValueError,
2377 "too many values to unpack (expected 2)");
2378 goto Done;
2379 }
2380 else if (PyErr_Occurred())
2381 goto Done;
2382
2383 res = PyObject_SetItem(self, key, value);
2384
2385Done:
2386 Py_DECREF(pair);
Eric Snowc5e59602015-05-30 11:28:56 -06002387 Py_XDECREF(pair_iterator);
Eric Snow96c6af92015-05-29 22:21:39 -06002388 Py_XDECREF(key);
2389 Py_XDECREF(value);
2390 if (PyErr_Occurred())
2391 break;
2392 }
2393 Py_DECREF(iterator);
2394
2395 if (res < 0 || PyErr_Occurred() != NULL)
2396 return -1;
2397 else
2398 return 0;
2399}
2400
2401static PyObject *
2402mutablemapping_update(PyObject *self, PyObject *args, PyObject *kwargs)
2403{
2404 int res = 0;
2405 Py_ssize_t len = (args != NULL) ? PyObject_Size(args) : 0;
2406
2407 /* first handle args, if any */
Eric Snowc5e59602015-05-30 11:28:56 -06002408 if (len < 0) /* PyObject_Size raised an exception. */
Eric Snow96c6af92015-05-29 22:21:39 -06002409 return NULL;
Benjamin Peterson99e96f22015-06-06 23:20:32 -05002410
2411 if (len > 1) {
Eric Snow96c6af92015-05-29 22:21:39 -06002412 char *msg = "update() takes at most 1 positional argument (%d given)";
2413 PyErr_Format(PyExc_TypeError, msg, len);
2414 return NULL;
2415 }
Eric Snow96c6af92015-05-29 22:21:39 -06002416
Benjamin Peterson0718de92015-06-07 00:00:42 -05002417 if (len == 1) {
2418 PyObject *other = PyTuple_GET_ITEM(args, 0); /* borrowed reference */
2419 if (other == NULL)
2420 return NULL;
2421 Py_INCREF(other);
2422 if (PyObject_HasAttrString(other, "items")) { /* never fails */
2423 PyObject *items = PyMapping_Items(other);
2424 Py_DECREF(other);
2425 if (items == NULL)
2426 return NULL;
2427 res = mutablemapping_add_pairs(self, items);
2428 Py_DECREF(items);
2429 if (res == -1)
2430 return NULL;
2431 }
2432 else if (PyObject_HasAttrString(other, "keys")) { /* never fails */
2433 PyObject *keys, *iterator, *key;
2434 keys = PyObject_CallMethod(other, "keys", NULL);
2435 if (keys == NULL) {
2436 Py_DECREF(other);
2437 return NULL;
2438 }
2439 iterator = PyObject_GetIter(keys);
2440 Py_DECREF(keys);
2441 if (iterator == NULL) {
2442 Py_DECREF(other);
2443 return NULL;
2444 }
2445 while (res == 0 && (key = PyIter_Next(iterator))) {
2446 PyObject *value = PyObject_GetItem(other, key);
2447 if (value != NULL) {
2448 res = PyObject_SetItem(self, key, value);
2449 Py_DECREF(value);
2450 }
2451 else {
2452 res = -1;
2453 }
2454 Py_DECREF(key);
2455 }
2456 Py_DECREF(other);
2457 Py_DECREF(iterator);
2458 if (res != 0 || PyErr_Occurred())
2459 return NULL;
2460 }
2461 else {
2462 res = mutablemapping_add_pairs(self, other);
2463 Py_DECREF(other);
2464 if (res != 0)
2465 return NULL;
2466 }
2467 }
2468
2469 /* now handle kwargs */
2470 len = (kwargs != NULL) ? PyObject_Size(kwargs) : 0;
2471 if (len < 0) /* PyObject_Size raised an exception. */
Eric Snow96c6af92015-05-29 22:21:39 -06002472 return NULL;
Benjamin Peterson0718de92015-06-07 00:00:42 -05002473 if (len > 0) {
2474 PyObject *items;
2475 if (!PyMapping_Check(kwargs)) {
2476 PyErr_SetString(PyExc_TypeError, "expected mapping for kwargs");
2477 return NULL;
2478 }
2479 items = PyMapping_Items(kwargs);
Eric Snow96c6af92015-05-29 22:21:39 -06002480 if (items == NULL)
2481 return NULL;
2482 res = mutablemapping_add_pairs(self, items);
2483 Py_DECREF(items);
2484 if (res == -1)
2485 return NULL;
2486 }
Eric Snow96c6af92015-05-29 22:21:39 -06002487
2488 Py_RETURN_NONE;
2489}