1 /**
2   Mirror _setobject.h
3 
4   Set object interface
5   */
6 module deimos.python.setobject;
7 
8 import core.stdc.stdio;
9 import deimos.python.pyport;
10 import deimos.python.object;
11 
12 extern(C):
13 // Python-header-file: Include/setobject.h:
14 
15 version(Python_2_5_Or_Later){
16     /// Availability: >= 2.5
17     enum PySet_MINSIZE = 8;
18 
19     /// Availability: >= 2.5
20     struct setentry {
21         /** cached hash code for the entry key */
22         Py_hash_t hash;
23         /// _
24         PyObject* key;
25     }
26 }
27 
28 /**
29 This data structure is shared by set and frozenset objects.
30 
31  Invariants for frozensets:
32      data is immutable.
33      hash is the hash of the frozenset or -1 if not computed yet.
34  Invariants for sets:
35      hash is -1
36 
37 subclass of PyObject.
38 */
39 
40 version(Python_3_5_Or_Later) {
41     struct PySetObject {
42         mixin PyObject_HEAD;
43 
44         /// Availability: >= 2.5
45         Py_ssize_t fill;
46         /// Availability: >= 2.5
47         Py_ssize_t used;
48 
49         /** The table contains mask + 1 slots, and that's a power of 2.
50          * We store the mask instead of the size because the mask is more
51          * frequently needed.
52          */
53         Py_ssize_t mask;
54 
55         /** table points to smalltable for small tables, else to
56          * additional malloc'ed memory.  table is never NULL!  This rule
57          * saves repeated runtime null-tests.
58          */
59         setentry* table;
60 
61         /// _
62         Py_hash_t hash;
63 
64         /// _
65         Py_ssize_t finger;
66 
67         /// _
68         setentry[PySet_MINSIZE] smalltable;
69 
70         /// _
71         PyObject* weakreflist;
72     }
73 }else version(Python_3_2_Or_Later) {
74     struct PySetObject {
75         mixin PyObject_HEAD;
76 
77         /// Availability: >= 2.5
78         Py_ssize_t fill;
79         /// Availability: >= 2.5
80         Py_ssize_t used;
81 
82         /** The table contains mask + 1 slots, and that's a power of 2.
83          * We store the mask instead of the size because the mask is more
84          * frequently needed.
85          */
86         Py_ssize_t mask;
87 
88         /** table points to smalltable for small tables, else to
89          * additional malloc'ed memory.  table is never NULL!  This rule
90          * saves repeated runtime null-tests.
91          */
92         setentry* table;
93 
94         /// _
95         setentry* function(PySetObject* so, PyObject* key, Py_hash_t hash) lookup;
96         /// _
97         Py_hash_t hash;
98 
99         /// _
100         setentry[PySet_MINSIZE] smalltable;
101         /// _
102         PyObject* weakreflist;
103     }
104 }else version(Python_2_5_Or_Later) {
105     struct PySetObject {
106         mixin PyObject_HEAD;
107 
108         /// Availability: >= 2.5
109         Py_ssize_t fill;
110         /// Availability: >= 2.5
111         Py_ssize_t used;
112 
113         /** The table contains mask + 1 slots, and that's a power of 2.
114          * We store the mask instead of the size because the mask is more
115          * frequently needed.
116          */
117         Py_ssize_t mask;
118 
119         /** table points to smalltable for small tables, else to
120          * additional malloc'ed memory.  table is never NULL!  This rule
121          * saves repeated runtime null-tests.
122          */
123         setentry* table;
124 
125         /// _
126         setentry* function(PySetObject* so, PyObject* key, C_long hash) lookup;
127         /// _
128         setentry[PySet_MINSIZE] smalltable;
129 
130         /** only used by frozenset objects */
131         C_long hash;
132         /** List of weak references */
133         PyObject* weakreflist;
134     }
135 
136 }else {
137     struct PySetObject {
138         mixin PyObject_HEAD;
139 
140         /// Availability: 2.4
141         PyObject* data;
142 
143         /** only used by frozenset objects */
144         C_long hash;
145         /** List of weak references */
146         PyObject* weakreflist;
147     }
148 }
149 
150 /// _
151 mixin(PyAPI_DATA!"PyTypeObject PySet_Type");
152 /// _
153 mixin(PyAPI_DATA!"PyTypeObject PyFrozenSet_Type");
154 /// _
155 mixin(PyAPI_DATA!"PyTypeObject PySetIter_Type");
156 
157 // D translations of C macros:
158 /// _
159 int PyFrozenSet_CheckExact()(PyObject* ob) {
160     return Py_TYPE(ob) == &PyFrozenSet_Type;
161 }
162 /// _
163 int PyAnySet_CheckExact()(PyObject* ob) {
164     return Py_TYPE(ob) == &PySet_Type || Py_TYPE(ob) == &PyFrozenSet_Type;
165 }
166 /// _
167 int PyAnySet_Check()(PyObject* ob) {
168     return (
169          Py_TYPE(ob) == &PySet_Type
170       || Py_TYPE(ob) == &PyFrozenSet_Type
171       || PyType_IsSubtype(Py_TYPE(ob), &PySet_Type)
172       || PyType_IsSubtype(Py_TYPE(ob), &PyFrozenSet_Type)
173     );
174 }
175 version(Python_2_6_Or_Later){
176     /// Availability: >= 2.6
177     bool PySet_Check()(PyObject* ob) {
178         return (Py_TYPE(ob) == &PySet_Type ||
179                 PyType_IsSubtype(Py_TYPE(ob), &PySet_Type));
180     }
181     /// Availability: >= 2.6
182     bool PyFrozenSet_Check()(PyObject* ob) {
183         return (Py_TYPE(ob) == &PyFrozenSet_Type ||
184                 PyType_IsSubtype(Py_TYPE(ob), &PyFrozenSet_Type));
185     }
186 }
187 
188 version(Python_2_5_Or_Later){
189     /// Availability: >= 2.5
190     PyObject* PySet_New(PyObject*);
191     /// Availability: >= 2.5
192     PyObject* PyFrozenSet_New(PyObject*);
193     /// Availability: >= 2.5
194     Py_ssize_t PySet_Size(PyObject* anyset);
195     /// Availability: >= 2.5
196     Py_ssize_t PySet_GET_SIZE()(PyObject* so) {
197         return (cast(PySetObject*)so).used;
198     }
199     /// Availability: >= 2.5
200     int PySet_Clear(PyObject* set);
201     /// Availability: >= 2.5
202     int PySet_Contains(PyObject* anyset, PyObject* key);
203     /// Availability: >= 2.5
204     int PySet_Discard(PyObject* set, PyObject* key);
205     /// Availability: >= 2.5
206     int PySet_Add(PyObject* set, PyObject* key);
207     /// Availability: >= 2.5
208     int _PySet_Next(PyObject* set, Py_ssize_t *pos, PyObject** entry);
209     /// Availability: >= 2.5
210     int _PySet_NextEntry(PyObject* set, Py_ssize_t* pos, PyObject** key, Py_hash_t* hash);
211     /// Availability: >= 2.5
212     PyObject* PySet_Pop(PyObject* set);
213     /// Availability: >= 2.5
214     int _PySet_Update(PyObject* set, PyObject* iterable);
215 }
216 
217 version(Python_3_5_Or_Later) {
218     /// Availability: >= 3.5
219     int PySet_ClearFreeList();
220 }
221 
222 version(Python_3_2_Or_Later) {
223     /// Availability: >= 3.2
224     void _PySet_DebugMallocStats(FILE* out_);
225 }
226