1 /* BitSet implementation */
2
3 #define PY_SSIZE_T_CLEAN
4 #include <Python.h>
5
6 #include "structmember.h"
7 #include "longintrepr.h"
8
9 #include "../include/guppy.h"
10 #include "../heapy/heapdef.h"
11 #include "sets_internal.h"
12
13 /* Docstrings */
14
15 char bitset_doc[] =
16
17
18 "The class BitSet is the base class for all bitset classes.\n"
19 "\n"
20 "A bitset is a set of 'bits'. Bits are integers, in a range that is\n"
21 "typically [-2**31 .. 2**31-1] or the range of the builtin Python int\n"
22 "type. The implementation of bitsets is such that it handles dense sets\n"
23 "the most efficiently while sparse sets are handled reasonably well.\n"
24 "\n"
25 "Bitsets can be either mutable or immutable. Mutable bitsets have\n"
26 "various operations to add and remove bits in-place. Immutable bitsets\n"
27 "have hashing so they can be used as keys in dicts. Both kinds of\n"
28 "bitsets have several operations in common. Sometimes an operand can be\n"
29 "either a bitset or a 'convertible', which means it is one of the\n"
30 "following kinds.\n"
31 "\n"
32 "iterable\n"
33 " An iterable argument is convertible to a bitset if each object yielded\n"
34 " is an integer in the range of an int.\n"
35 "\n"
36 "int\n"
37 " A positive argument, x, of one of these types will be converted\n"
38 " to a bitset with the same bits as the binary representation of x.\n"
39 "\n"
40 " A negative argument will be converted to a complemented bitset,\n"
41 " equivalent to the following expression:\n"
42 "\n"
43 " ~immbitset(~x)\n"
44 "\n"
45 " This corresponds to the bits in the 2-complement binary representation\n"
46 " of x, except that the result conceptually has all negative bits set.\n"
47 " The difference shows (only) when shifting a complemented bitset.\n"
48 "\n"
49 "The following operations are common for mutable and immutable bitsets.\n"
50 "\n"
51 "------------------------------------------\n"
52 "Standard binary operations.\n"
53 "\n"
54 "In the usual case the left argument is some kind of bitset, and the\n"
55 "right argument is a bitset or a 'convertible' as defined above. The\n"
56 "return value is then an immutable bitset.\n"
57 "\n"
58 "x & y -> Intersection: the set of\n"
59 " bits that are in both x and y.\n"
60 "\n"
61 "x | y -> Union: the set of\n"
62 " bits that are in either x or y.\n"
63 "\n"
64 "x ^ y -> Symmetric difference: the set of\n"
65 " bits that are in exactly one of x and y.\n"
66 "\n"
67 "x - y -> Difference: the set of\n"
68 " bits that are in x but not in y.\n"
69 "\n"
70 "If the right argument is a bitset but not the left argument, the\n"
71 "result will be an immutable bitset if only the left argument is a\n"
72 "convertible that does not define the same operation; otherwise the\n"
73 "result is what is returned by the operation of the left argument or a\n"
74 "TypeError will be raised. The following table gives the result for the\n"
75 "different kinds of arguments.\n"
76 "\n"
77 " Left argument Right argument Result\n"
78 " - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n"
79 " bitset bitset immutable bitset\n"
80 " bitset convertible immutable bitset\n"
81 " bitset other TypeError\n"
82 "\n"
83 " defining the same op bitset handled by left argument\n"
84 " convertible bitset immutable bitset\n"
85 " other bitset TypeError\n"
86 "\n"
87 "\n"
88 "\n"
89 "------------------------------------------\n"
90 "In-place binary operations.\n"
91 "\n"
92 "The left argument must be a bitset.\n"
93 "If it is mutable, it is updated in place and returned.\n"
94 "If it is immutable, the result is a new immutable bitset.\n"
95 "The right argument is a bitset or a convertible.\n"
96 "\n"
97 "x &= y -> Intersection\n"
98 "\n"
99 "x |= y -> Union\n"
100 "\n"
101 "x ^= y -> Symmetric difference\n"
102 "\n"
103 "x -= y -> Difference\n"
104 "\n"
105 "------------------------------------------\n"
106 "Complement operation.\n"
107 "\n"
108 "~x -> immutable bitset\n"
109 "\n"
110 "Return the complement of x. This is a bitset that, conceptually,\n"
111 "contains all bits in the universe except the ones in x.\n"
112 "\n"
113 "[ Subtle\n"
114 "\n"
115 " If x is not already complemented, ~x will return a special\n"
116 " complemented kind of set. This can be used like other bitsets except\n"
117 " for two operations that are not supported: it is not possible to\n"
118 " iterate over, or take the length of a complemented bitset. If x is a\n"
119 " complemented bitset, ~x returns a non-complemented bitset.\n"
120 "\n"
121 " Mutable bitsets may become complemented in-place if given a\n"
122 " complemented argument to a suitable in-place operation. This is\n"
123 " represented by a flag. Immutable complemented bitsets are represented\n"
124 " by a special type, but this is to be considered an implementation\n"
125 " detail, it could as well be using a flag. ]\n"
126 "\n"
127 "------------------------------------------\n"
128 "Shift operation.\n"
129 "\n"
130 "x << y -> immutable bitset\n"
131 "\n"
132 "Return the set of bits of x, with the integer y added to each one.\n"
133 "Raise OverflowError if some bit would exceed the range of an int. \n"
134 "\n"
135 "[ Subtle\n"
136 "\n"
137 " For non-complemented x and positive y, the result is what one would\n"
138 " expect if x was a number in binary representation. But when x is\n"
139 " complemented, the result will equal\n"
140 "\n"
141 " ~((~x) << y)\n"
142 "\n"
143 " which is different from what one would expect from binary number\n"
144 " shifting, since 1's are shifted in from the right.\n"
145 "\n"
146 " The operation allows both positive or negative y values, unlike the\n"
147 " shift for integer objects. For negative y's, the operation will shift\n"
148 " bits to the right but not quite in the same way as a binary integer\n"
149 " right-shift operation would do it, because the low bits will not\n"
150 " disappear but be shifted towards negative bits. ]\n"
151 "\n"
152 "------------------------------------------\n"
153 "Inclusion test.\n"
154 "\n"
155 "The left argument is an integer in the range of an int.\n"
156 "The right argument is a bitset.\n"
157 "\n"
158 "x in y -> bool\n"
159 " True if x is an element of y, False otherwise.\n"
160 "\n"
161 "------------------------------------------\n"
162 "Relational operations.\n"
163 "\n"
164 "These return a boolean value.\n"
165 "The left argument is a bitset.\n"
166 "The right argument is a bitset.\n"
167 "If the right argument is another type, TypeError will be raised.\n"
168 "(This restriction may be reconsidered in the future.)\n"
169 "\n"
170 "x == y -> Equal:\n"
171 " x and y contain the same bits.\n"
172 "\n"
173 "x != y -> Not equal:\n"
174 " x and y do not contain the same bits.\n"
175 "\n"
176 "x <= y -> Subset, non-strict:\n"
177 " all bits in x are also in y.\n"
178 "\n"
179 "x < y -> Subset, strict:\n"
180 " all bits in x are also in y,\n"
181 " and y contains some bits not in x.\n"
182 "\n"
183 "x >= y -> Superset, non-strict:\n"
184 " all bits in y are also in x.\n"
185 "\n"
186 "x > y -> Superset, strict:\n"
187 " all bits in y are also in x,\n"
188 " and x contains some bit not in y.\n"
189 "\n"
190 "------------------------------------------\n"
191 "Iteration.\n"
192 "\n"
193 "iter(x) -> iterator\n"
194 "\n"
195 "The iterator yields the bits of x.\n"
196 "\n"
197 "Raises TypeError if x is complemented.\n"
198 "\n"
199 "[The order is implementation dependent.]\n"
200 "\n"
201 "------------------------------------------\n"
202 "Length.\n"
203 "\n"
204 "len(x) -> int\n"
205 "\n"
206 "Return the number of bits in x.\n"
207 "\n"
208 "Raises TypeError if x is complemented.\n"
209 "\n"
210 "------------------------------------------\n"
211 "Truth-value testing.\n"
212 "\n"
213 "bool(x) -> bool\n"
214 "\n"
215 "Return True if x is not empty, False otherwise.\n"
216 "\n"
217 "------------------------------------------\n"
218 "Conversions.\n"
219 "\n"
220 "int(x) -> int\n"
221 "\n"
222 "Return an integer having the same binary representation as the bits of\n"
223 "x, or raise an exception if the bitset can not be represented in the\n"
224 "choosen type. When no exception is raised, the bitset x can be exactly\n"
225 "recreated and the following invariants will hold.\n"
226 "\n"
227 " immbitset(int(x)) == x\n"
228 "\n"
229 "The exception OverflowError will be raised if it is found that x can\n"
230 "not be represented. Note that for a sparse bitset with high bit\n"
231 "numbers, int(x) may create a very big object since it allocates\n"
232 "storage for all the low bits up to the highest bit number set, unlike\n"
233 "bitsets that use a sparse representation. Creating such big objects\n"
234 "may run out of storage which may raise a MemoryError or cause some\n"
235 "other malfunction depending on the system.\n"
236 "\n"
237 "------------------------------------------\n"
238 "Mutable copy\n"
239 "\n"
240 "S.mutcopy() -> mutable bitset\n"
241 "\n"
242 "Return a mutable copy of S.\n"
243 ;
244
245
246 static char ImmBitSet_doc[] =
247 "ImmBitSet() -> empty immutable bitset\n"
248 "ImmBitSet(bitset) -> immutable bitset with bitset's bits\n"
249 "ImmBitSet(iterable) -> immutable bitset with iterable's bits (int items)\n"
250 "ImmBitSet(integer) -> immutable bitset with integer's bits (binary 2-complement)\n"
251 "\n"
252 "The result can only be non-complemented; TypeError is raised\n"
253 "otherwise. (The function immbitset() can be used to create both\n"
254 "complemented and non-complemented bitsets.)\n"
255 "\n"
256 "An immutable bitset provides the operations common for all bitsets as\n"
257 "described for the BitSet base class. It also defines the following:\n"
258 "\n"
259 "hash(x) -> int\n"
260 "\n"
261 "Return a hash value based on the bit numbers of the elements.\n"
262 ;
263
264 static char cplbitset_doc[] =
265
266 "CplBitSet(x:ImmBitSet) -> complemented immutable bitset.\n"
267 "\n"
268 "If the argument is an instance of ImmBitSet, this is the same as ~x,\n"
269 "otherwise TypeError is raised.\n"
270 "\n"
271 "A complemented immutable bitset provides the same operations as\n"
272 "non-complemented immutable bitsets, except for len() and iter().\n"
273 ;
274
275 static char mutbitset_doc[] =
276 "MutBitSet() -> new empty mutable bitset\n"
277 "MutBitSet(bitset) -> new mutable bitset with bitset's bits\n"
278 "MutBitSet(iterable) -> new mutable bitset with iterable's bits (int items)\n"
279 "MutBitSet(integer) -> new mutable bitset with integer's bits (binary 2-complement)\n"
280 "\n"
281 "A mutable bitset has operations common for all bitsets as described\n"
282 "for the BitSet base class. It also defines the following methods:\n"
283 "\n"
284 " add, append, clear, discard, pop, remove, tac, tas\n"
285 ;
286
287 static char add_doc[] =
288 "S.add(e)\n"
289 "\n"
290 "Add e to S; no effect if e was already in S\n"
291 ;
292
293 static char append_doc[] =
294 "S.append(e)\n"
295 "\n"
296 "Add e to S, or raise ValueError if e was already in S.";
297
298 static char discard_doc[] =
299 "S.discard(e)\n"
300 "\n"
301 "Remove e from S; no effect if e was not in S.";
302
303 static char pop_doc[] =
304 "S.pop([index]) -> int\n"
305 "\n"
306 "Remove and return a bit, or raise ValueError if there is no bit to pop.\n"
307 "\n"
308 "The index must be -1 (default) to pop the highest bit or 0 to pop the\n"
309 "lowest bit; otherwise IndexError will be raised.";
310
311 static char remove_doc[] =
312 "S.remove(e)\n"
313 "\n"
314 "Remove e from S, or raise ValueError if e was not in S.";
315
316 static char clear_doc[] =
317 "S.clear()\n"
318 "\n"
319 "Remove all elements from S, and compact its storage.";
320
321
322 static char tasbit_doc[] =
323 "S.tas(e) -> bool\n"
324 "\n"
325 "Test and Set.\n"
326 "If e is in S return True,\n"
327 "else add e to S and return False.";
328
329 static char tacbit_doc[] =
330 "S.tac(e) -> bool\n"
331 "\n"
332 "Test and Clear.\n"
333 "If e is in S, remove e from S and return True,\n"
334 "else return False.";
335
336 static char mutable_copy_doc[] =
337 "S.mutcopy() -> mutable bitset\n"
338 "\n"
339 "Return a mutable copy of S.\n"
340 ;
341
342 static char bitsingle_doc[] =
343 "immbit(bit) -> immutable bitset\n"
344 "\n"
345 "Return an immutable bitset containing the single bit specified.\n"
346 "The bit must be an integer in the range of an int.";
347
348 static char bitrange_doc[] =
349 "immbitrange([start,] stop[, step]) -> immutable bitset\n"
350 "\n"
351 "Return an immutable bitset containing an arithmetic progression of integers.\n"
352 "immbitrange(i, j) equals immbitset([i, i+1, i+2, ..., j-1]).\n"
353 "Start defaults to 0. If step is given, it specifies a positive increment.\n"
354 "For example, immbitrange(3) equals immbitset([0, 1, 2]).";
355
356 static char bitform_doc[] =
357 "_bs(flags, data) -> some kind of bitset\n"
358 "\n"
359 "Internal function used to form a bitset when unpickling.\n"
360 "It is designed to be 'safe' with any data but may give strange results\n"
361 "if given something else than what x.__reduce__() generated.";
362
363 /* Forward declarations */
364
365 static void anybitset_classify(PyObject *v, int *vt);
366 static PyObject *anybitset_convert(PyObject *v, int *vt);
367
368 static PyObject *immbitset_complement(NyImmBitSetObject *v);
369
370
371 static PyObject *mutbitset_as_immbitset_and_cpl(NyMutBitSetObject *v, int cpl);
372 static PyObject *mutbitset_as_immbitset_and_del(NyMutBitSetObject *v);
373 static NyImmBitSetObject *mutbitset_as_noncomplemented_immbitset_subtype(
374 NyMutBitSetObject *v, PyTypeObject *type);
375 static NyBitField *mutbitset_findpos_ins(NyMutBitSetObject *v, NyBit pos);
376 static NyBitField *mutbitset_findpos(NyMutBitSetObject *v, NyBit pos);
377 static NySetField *mutbitset_getrange_mut(NyMutBitSetObject *v, NySetField **shi);
378 static int mutbitset_iop_iterable(NyMutBitSetObject *ms, int op, PyObject *v);
379 static NyMutBitSetObject *mutbitset_new_from_arg(PyObject *arg);
380 static int mutbitset_reset(NyMutBitSetObject *v, NyImmBitSetObject *set);
381
382 static NySetField *root_ins1(NyMutBitSetObject *v, NySetField *sf, NyBit pos);
383 static NyImmBitSetObject *immbitset_realloc(NyImmBitSetObject *self, NyBit size);
384
385
386 static int mutbitset_ior_field(NyMutBitSetObject *v, NyBitField *w);
387
388 static int mutbitset_iop_PyLongObject(NyMutBitSetObject *ms, int op, PyObject *v);
389
390 static PyObject *NyBitSet_FormMethod;
391
392 static NyImmBitSetObject * cplbitset_cpl(NyCplBitSetObject*v);
393
394 NyImmBitSetObject *sf_slice(NySetField *ss, NySetField *se, NyBit ilow, NyBit ihigh);
395
396 /* NyBitSet_Type -- Base type with no operations, just a doc string */
397
398 PyTypeObject NyBitSet_Type = {
399 PyVarObject_HEAD_INIT(NULL, 0)
400 .tp_name = "guppy.sets.setsc.BitSet",
401 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
402 .tp_doc = bitset_doc,
403 };
404
405
406 /* */
407
408 #if PY_MAJOR_VERSION >= 3 && PY_MINOR_VERSION >= 9
409 # ifndef Py_TRACE_REFS
410 # define _Py_ForgetReference(op) do {} while (0)
411 # define _Py_DEC_REFTOTAL do {} while (0)
412 # endif
413 #endif
414
415 #define NOSET 0
416 #define BITSET 1
417 #define CPLSET 2
418 #define MUTSET 3
419
420 #define NyForm_CPL 1
421 #define NyForm_MUT 2
422
423 /* Predefined no-bits and all-bits sets */
424
425 NyImmBitSetObject _NyImmBitSet_EmptyStruct = {
426 PyVarObject_HEAD_INIT(NULL, 0)
427 };
428
429 NyCplBitSetObject _NyImmBitSet_OmegaStruct = {
430 PyObject_HEAD_INIT(NULL)
431 &_NyImmBitSet_EmptyStruct /* ob_val */
432 };
433
434 /* Counting bits for len() is optimized by looking up lengths of
435 bit segments. The segment size is defined by this shift. Larger
436 values than 8, eg 16, can make len() some 30% faster at some tests,
437 but use exponentially more table space. 11 can be a compromise.
438 Experimental data can be found in notes per 5/6 -03.
439 */
440
441 #define LEN_TAB_SHIFT 8 /* 8 is a memory/cache conservation setting. */
442
443 #define LEN_TAB_SIZE (1<<LEN_TAB_SHIFT)
444
445 static int len_tab[LEN_TAB_SIZE]; /* helper for len() */
446
447 static int n_immbitset, n_cplbitset, n_mutbitset;
448
449 /* Check if an object looks like it can return an iterator
450 via PyObject_GetIter, except that no iterator is created and checked.
451 This is to be able to more cleanly return NotImplemented when
452 doing mixed-type operations, separating not having an iterator
453 from errors like returning an invalid iterator.
454 */
455
456 static int
NyIterable_Check(PyObject * o)457 NyIterable_Check(PyObject *o)
458 {
459 PyTypeObject *t = Py_TYPE(o);
460 return t->tp_iter || PySequence_Check(o);
461 }
462
463 static NyBit
bitno_modiv(NyBit bitno,NyBit * div)464 bitno_modiv(NyBit bitno, NyBit *div) {
465 /* We need divmod a'la Python: using algo from intobject.c */
466 NyBit xdivy = bitno / NyBits_N;
467 NyBit xmody = bitno - xdivy * NyBits_N;
468 /* If the signs of x and y differ, and the remainder is non-0,
469 * C89 doesn't define whether xdivy is now the floor or the
470 * ceiling of the infinitely precise quotient. We want the floor,
471 * and we have it iff the remainder's sign matches y's.
472 */
473 if (xmody < 0) /* i.e. and signs differ */ {
474 xmody += NyBits_N;
475 --xdivy;
476 assert(xmody && ((NyBits_N ^ xmody) >= 0));
477 }
478 *div = xdivy;
479 return xmody;
480 }
481
482
483
484 static void
bitno_to_field(NyBit bitno,NyBitField * f)485 bitno_to_field(NyBit bitno, NyBitField *f) {
486 f->bits = ONE_LONG<<bitno_modiv(bitno, &f->pos);
487 }
488
489 /* Find the first (lowest) or last (highest) bit set
490
491 Only to be used when some bit is set.
492
493 Hardcoded for 64 or 32 bit fields
494
495 */
496
497 static int
bits_first(NyBits bits)498 bits_first(NyBits bits)
499 {
500 int i = 0;
501 assert(bits);
502
503 #if (NyBits_N==64)
504 if (!(bits & 0xffffffff)) {
505 i += 32;
506 bits = bits >> 32;
507 }
508 #elif (NyBits_N==32)
509 /* Nothing */
510 #else
511 #error "Unsupported NyBits_N"
512 #endif
513 if (!(bits & 0xffff)) {
514 i += 16;
515 bits = bits >> 16;
516 }
517 if (!(bits & 0xff)) {
518 i += 8;
519 bits = bits >> 8;
520 }
521 if (!(bits & 0xf)) {
522 i += 4;
523 bits = bits >> 4;
524 }
525 if (!(bits & 0x3)) {
526 i += 2;
527 bits = bits >> 2;
528 }
529 if (!(bits & 0x1)) {
530 i += 1;
531 bits = bits >> 1;
532 }
533 assert(bits & 0x1);
534 return i;
535 }
536
537 static int
bits_last(NyBits bits)538 bits_last(NyBits bits)
539 {
540 int i = NyBits_N-1;
541 assert(bits);
542 #if (NyBits_N==64)
543 if (!(bits & 0xffffffff00000000)) {
544 i -= 32;
545 bits = bits << 32;
546 }
547 if (!(bits & 0xffff000000000000)) {
548 i -= 16;
549 bits = bits << 16;
550 }
551 if (!(bits & 0xff00000000000000)) {
552 i -= 8;
553 bits = bits << 8;
554 }
555 if (!(bits & 0xf000000000000000)) {
556 i -= 4;
557 bits = bits << 4;
558 }
559 if (!(bits & 0xc000000000000000)) {
560 i -= 2;
561 bits = bits << 2;
562 }
563 if (!(bits & 0x8000000000000000)) {
564 i -= 1;
565 }
566 #elif (NyBits_N==32)
567 if (!(bits & 0xffff0000)) {
568 i -= 16;
569 bits = bits << 16;
570 }
571 if (!(bits & 0xff000000)) {
572 i -= 8;
573 bits = bits << 8;
574 }
575 if (!(bits & 0xf0000000)) {
576 i -= 4;
577 bits = bits << 4;
578 }
579 if (!(bits & 0xc0000000)) {
580 i -= 2;
581 bits = bits << 2;
582 }
583 if (!(bits & 0x80000000)) {
584 i -= 1;
585 }
586 #else
587 #error "Unsupported NyBits_N"
588 #endif
589 return i;
590 }
591
592 static int
bits_length(NyBits bits)593 bits_length(NyBits bits) {
594 int n = 0;
595 while (bits) {
596 n += len_tab[bits & (LEN_TAB_SIZE-1)];
597 bits >>= LEN_TAB_SHIFT;
598 }
599 return n;
600
601 }
602
603 static NyBit
field_first(NyBitField * f)604 field_first(NyBitField *f)
605 {
606 return bits_first(f->bits) + f->pos * NyBits_N;
607 }
608
609 static NyBit
field_last(NyBitField * f)610 field_last(NyBitField *f)
611 {
612 return bits_last(f->bits) + f->pos * NyBits_N;
613 }
614
615 /* Quoting listobject.c */
616
617 static NyBit
roundupsize(NyBit n)618 roundupsize(NyBit n)
619 {
620 size_t nbits = 0;
621 size_t n2 = (size_t)n >> 5;
622
623 /* Round up:
624 * If n < 256, to a multiple of 8.
625 * If n < 2048, to a multiple of 64.
626 * If n < 16384, to a multiple of 512.
627 * If n < 131072, to a multiple of 4096.
628 * If n < 1048576, to a multiple of 32768.
629 * If n < 8388608, to a multiple of 262144.
630 * If n < 67108864, to a multiple of 2097152.
631 * If n < 536870912, to a multiple of 16777216.
632 * ...
633 * If n < 2**(5+3*i), to a multiple of 2**(3*i).
634 *
635 * This over-allocates proportional to the list size, making room
636 * for additional growth. The over-allocation is mild, but is
637 * enough to give linear-time amortized behavior over a long
638 * sequence of appends() in the presence of a poorly-performing
639 * system realloc() (which is a reality, e.g., across all flavors
640 * of Windows, with Win9x behavior being particularly bad -- and
641 * we've still got address space fragmentation problems on Win9x
642 * even with this scheme, although it requires much longer lists to
643 * provoke them than it used to).
644 */
645 do {
646 n2 >>= 3;
647 nbits += 3;
648 } while (n2);
649 return ((n >> nbits) + 1) << nbits;
650 }
651
652 static NyBit
bitno_from_object(PyObject * arg)653 bitno_from_object(PyObject *arg)
654 {
655 /* Get a bit number from a Python object.
656 This is somewhat restrictive, but it is easier to explain,
657 and nicer to later change to less restrictive but the other way around. */
658 if (PyLong_Check(arg)) {
659 return PyLong_AsSsize_t(arg); // xxx should really use Py_ssize_t or something..
660 } else {
661 PyErr_SetString(PyExc_TypeError, "bitno_from_object: an int was expected");
662 return -1;
663 }
664 }
665
666 NyImmBitSetObject *
NyImmBitSet_SubtypeNew(PyTypeObject * type,NyBit size)667 NyImmBitSet_SubtypeNew(PyTypeObject *type, NyBit size)
668 {
669 if (!size && type == &NyImmBitSet_Type) {
670 Py_INCREF(NyImmBitSet_Empty);
671 return NyImmBitSet_Empty;
672 } else {
673 NyImmBitSetObject *r = (void *)type->tp_alloc(type, size);
674 if (r) {
675 /* Mark length as not-calculated */
676 r->ob_length = -1;
677 /* Note: the other fields are cleared by tp_alloc. */
678 n_immbitset++;
679 }
680 return r;
681 }
682 }
683
684
685 NyImmBitSetObject *
NyImmBitSet_New(NyBit size)686 NyImmBitSet_New(NyBit size)
687 {
688 return NyImmBitSet_SubtypeNew(&NyImmBitSet_Type, size);
689 }
690
691
692 static NyImmBitSetObject *
NyImmBitSet_SubtypeFromIterable(PyTypeObject * type,PyObject * v)693 NyImmBitSet_SubtypeFromIterable(PyTypeObject *type, PyObject *v)
694 {
695 NyMutBitSetObject *ms;
696 NyImmBitSetObject *ret;
697 ms = NyMutBitSet_New();
698 if (!ms) return 0;
699 if (mutbitset_iop_iterable(ms, NyBits_OR, v) == -1) {
700 Py_DECREF(ms);
701 return 0;
702 }
703 ret = mutbitset_as_noncomplemented_immbitset_subtype(ms, type);
704 Py_DECREF(ms);
705 return ret;
706 }
707
708 static NyImmBitSetObject *
NyImmBitSet_FromIterable(PyObject * v)709 NyImmBitSet_FromIterable(PyObject *v)
710 {
711 return NyImmBitSet_SubtypeFromIterable(&NyImmBitSet_Type, v);
712 }
713
714
715 NyImmBitSetObject *
NyImmBitSet_SubtypeNewArg(PyTypeObject * type,PyObject * v)716 NyImmBitSet_SubtypeNewArg(PyTypeObject *type, PyObject *v)
717 {
718 int vt;
719 NyMutBitSetObject *ms;
720 NyImmBitSetObject *ret;
721 if (!v) {
722 return NyImmBitSet_SubtypeNew(type, 0);
723 }
724 anybitset_classify(v, &vt);
725 if (vt == BITSET) {
726 NyImmBitSetObject *bs = (NyImmBitSetObject *)v;
727 NyImmBitSetObject *ret = NyImmBitSet_SubtypeNew(type, Py_SIZE(bs));
728 memcpy(ret->ob_field, bs->ob_field, sizeof(NyBitField) * Py_SIZE(bs));
729 return ret;
730 }
731 if (vt == MUTSET) {
732 ms = (NyMutBitSetObject *)v;
733 Py_INCREF(ms);
734 } else {
735 ms = mutbitset_new_from_arg(v);
736 }
737 if (!ms)
738 return 0;
739 if (ms->cpl) {
740 PyErr_SetString(PyExc_TypeError, "ImmBitSet.__new__ : complemented arg not supported");
741 Py_DECREF(ms);
742 return 0;
743 }
744 ret = mutbitset_as_noncomplemented_immbitset_subtype(ms, type);
745 Py_DECREF(ms);
746 return ret;
747 }
748
749
750
751
752 static NyImmBitSetObject *
NyImmBitSet_Singleton(PyObject * arg)753 NyImmBitSet_Singleton(PyObject *arg)
754 {
755 NyBit bit = bitno_from_object(arg);
756 if (bit == -1 && PyErr_Occurred())
757 return NULL;
758 else {
759 NyImmBitSetObject *p = NyImmBitSet_New(1);
760 if (p) {
761 bitno_to_field(bit, &p->ob_field[0]);
762 }
763 return p;
764 }
765 }
766
767
768 static PyObject *
NyImmBitSet_FromPyLongObject(PyObject * v)769 NyImmBitSet_FromPyLongObject(PyObject *v)
770 {
771 NyMutBitSetObject *ms = NyMutBitSet_New();
772 if (!ms) return 0;
773 if (mutbitset_iop_PyLongObject(ms, NyBits_OR, v) == -1) {
774 Py_DECREF(ms);
775 return 0;
776 }
777 return mutbitset_as_immbitset_and_del(ms);
778 }
779
780 static int
mutbitset_initset(NyMutBitSetObject * v,NyImmBitSetObject * set)781 mutbitset_initset(NyMutBitSetObject *v, NyImmBitSetObject *set)
782 {
783 /* Requires state to be as after mutset_clear() */
784
785 NySetField *sf = root_ins1(v, &v->fst_root.ob_field[0], NyPos_MIN);
786 if (!sf)
787 return -1;
788 if (set) {
789 sf->set = set;
790 Py_INCREF(set);
791 sf->lo = set->ob_field;
792 sf->hi = set->ob_field + Py_SIZE(set);
793 } else {
794 sf->set = immbitset_realloc(0, 1);
795 sf->lo = sf->hi = sf->set->ob_field;
796 if (!sf->set)
797 return -1;
798 }
799 return 0;
800 }
801
802 NyMutBitSetObject *
NyMutBitSet_SubtypeNew(PyTypeObject * type,NyImmBitSetObject * set,NyUnionObject * root)803 NyMutBitSet_SubtypeNew(PyTypeObject *type, NyImmBitSetObject *set, NyUnionObject *root)
804 {
805 NyMutBitSetObject *v = (NyMutBitSetObject *)type->tp_alloc(type, 0);
806 if (v) {
807 v->cur_field = 0;
808 v->cpl = 0;
809 v->splitting_size = 500/*1000*/;
810
811 #if PY_MAJOR_VERSION >= 3 && PY_MINOR_VERSION >= 9
812 Py_SET_REFCNT(&v->fst_root, 1);
813 Py_SET_SIZE(&v->fst_root, 0);
814 #else
815 Py_REFCNT(&v->fst_root) = 1;
816 Py_SIZE(&v->fst_root) = 0;
817 #endif
818
819 v->fst_root.cur_size = 0;
820 if (!root) {
821 v->root = &v->fst_root;
822 if (mutbitset_initset(v, set) == -1) {
823 Py_DECREF(v);
824 return 0;
825 }
826 } else {
827 assert(!set);
828 v->root = root;
829 Py_INCREF(root);
830 }
831 n_mutbitset++;
832 }
833 return v;
834 }
835
836 NyMutBitSetObject *
NyMutBitSet_New(void)837 NyMutBitSet_New(void)
838 {
839 return NyMutBitSet_SubtypeNew(&NyMutBitSet_Type, 0, 0);
840 }
841
842 static void
fp_move(NyBitField * dst,NyBitField * src,NyBit n)843 fp_move(NyBitField *dst, NyBitField *src, NyBit n) {
844 memmove(dst, src, n * sizeof(NyBitField));
845 }
846
847 static void
sfp_move(NySetField * dst,NySetField * src,NyBit n)848 sfp_move(NySetField *dst, NySetField *src, NyBit n) {
849 memmove(dst, src, n * sizeof(NySetField));
850 }
851
852 static NyBitField *
bitfield_binsearch(NyBitField * lo,NyBitField * hi,NyBit pos)853 bitfield_binsearch(NyBitField *lo, NyBitField *hi, NyBit pos)
854 {
855 for (;;) {
856 NyBitField *cur = lo + (hi - lo) / 2;
857 if (cur == lo) {
858 if (lo < hi && lo->pos >= pos)
859 return lo;
860 else
861 return hi;
862 }
863 else if (cur->pos == pos)
864 return cur;
865 else if (cur->pos < pos)
866 lo = cur;
867 else
868 hi = cur;
869 }
870 }
871
872 static NySetField *
setfield_binsearch(NySetField * lo,NySetField * hi,NyBit pos)873 setfield_binsearch(NySetField *lo, NySetField *hi, NyBit pos)
874 {
875 for (;;) {
876 NySetField *cur = lo + (hi - lo) / 2;
877 if (cur == lo)
878 return lo;
879 else if (cur->pos == pos)
880 return cur;
881 else if (cur->pos < pos)
882 lo = cur;
883 else
884 hi = cur;
885 }
886 }
887
888 static void
union_dealloc(NyUnionObject * v)889 union_dealloc(NyUnionObject *v)
890 {
891 NyBit i;
892 for (i = 0; i < v->cur_size; i++)
893 Py_XDECREF(v->ob_field[i].set);
894 PyObject_Del(v);
895 }
896
897 static NyUnionObject *
union_realloc(NyUnionObject * self,NyBit size)898 union_realloc(NyUnionObject *self, NyBit size)
899 {
900 /* Changes the allocated size to make room for up-rounded size items */
901 size = roundupsize(size);
902 if (!self)
903 return PyObject_NewVar(NyUnionObject, &NyUnion_Type, size);
904 else {
905 NyUnionObject *ret;
906 assert(Py_REFCNT(self) == 1);
907 _Py_ForgetReference((PyObject *)self);
908 _Py_DEC_REFTOTAL;
909 ret = PyObject_Realloc(self,
910 Py_TYPE(self)->tp_basicsize + Py_TYPE(self)->tp_itemsize * size);
911 ret = (void *) PyObject_InitVar((void *)ret, Py_TYPE(ret), size);
912 return ret;
913 }
914 }
915
916 static NySetField *
root_ins1(NyMutBitSetObject * v,NySetField * sf,NyBit pos)917 root_ins1(NyMutBitSetObject *v, NySetField *sf, NyBit pos)
918 {
919 NyUnionObject *bs = v->root;
920 NyBit where = sf - &bs->ob_field[0];
921 NyBit cur_size = bs->cur_size;
922 if (cur_size >= Py_SIZE(bs)) {
923 if (bs == &v->fst_root) {
924 if (cur_size >= NyUnion_MINSIZE) {
925 assert(cur_size == NyUnion_MINSIZE);
926 bs = union_realloc(0, cur_size + 1);
927 if (!bs) return 0;
928 sfp_move(&bs->ob_field[0], &v->fst_root.ob_field[0], cur_size);
929 } else {
930 Py_SIZE(bs) = cur_size + 1;
931 }
932 } else {
933 bs = union_realloc(bs, cur_size + 1);
934 if (!bs) return 0;
935 }
936 assert(cur_size < Py_SIZE(bs));
937 v->root = bs;
938 sf = &bs->ob_field[where];
939 }
940 assert(where <= cur_size);
941 if (where < cur_size) {
942 assert(sf + 1 + cur_size - where <= &bs->ob_field[Py_SIZE(bs)]);
943 sfp_move(sf+1, sf, cur_size - where);
944 }
945 bs->cur_size = cur_size + 1;
946 sf->pos = pos;
947 sf->set = 0;
948 return sf;
949 }
950
951 static NyImmBitSetObject *
immbitset_realloc(NyImmBitSetObject * self,NyBit size)952 immbitset_realloc(NyImmBitSetObject *self, NyBit size)
953 {
954 NyImmBitSetObject *ret;
955 /* Changes the allocated size to make room for up-rounded size items
956 Allocates a new object if self == 0,
957 */
958 NyBit upsize = roundupsize(size);
959 if (!self) {
960 ret = NyImmBitSet_New(upsize);
961 return ret;
962 } else {
963 assert(Py_REFCNT(self) == 1);
964 _Py_ForgetReference((PyObject *)self);
965 _Py_DEC_REFTOTAL;
966 ret = PyObject_Realloc(self,
967 Py_TYPE(self)->tp_basicsize + Py_TYPE(self)->tp_itemsize * upsize);
968 ret = (void *) PyObject_InitVar((void *)ret, Py_TYPE(ret), upsize);
969 return ret;
970 }
971 }
972
973 static NyBitField *
sf_getrange(NySetField * v,NyBitField ** shi)974 sf_getrange(NySetField *v, NyBitField **shi)
975 {
976 *shi = v->hi;
977 return v->lo;
978 }
979
980
981 static NyBitField *
sf_getrange_mut(NySetField * sf,NyBitField ** shi)982 sf_getrange_mut(NySetField *sf, NyBitField **shi)
983 {
984 if (Py_REFCNT(sf->set) > 1) {
985 NyImmBitSetObject *oset = sf->set;
986 NyBit lo = sf->lo - oset->ob_field;
987 NyBit hi = sf->hi - oset->ob_field;
988 NyImmBitSetObject *set = NyImmBitSet_New(Py_SIZE(oset)?Py_SIZE(oset):8);
989 if (!set)
990 return 0;
991 fp_move(set->ob_field, oset->ob_field, Py_SIZE(oset));
992 sf->lo = set->ob_field + lo;
993 sf->hi = set->ob_field + hi;
994 sf->set = set;
995 Py_DECREF(oset);
996 }
997 *shi = sf->hi;
998 return sf->lo;
999 }
1000
1001 static int
sf_realloc(NySetField * v,NyBit size)1002 sf_realloc(NySetField *v, NyBit size)
1003 {
1004 if (!v->set) {
1005 v->set = immbitset_realloc(0, size);
1006 if (!v->set)
1007 return -1;
1008 v->lo = v->hi = v->set->ob_field + Py_SIZE(v->set)/2;
1009 } else {
1010 NyBitField *ofield = &v->set->ob_field[0];
1011 NyImmBitSetObject *bs = immbitset_realloc(v->set, size);
1012 if (!bs)
1013 return -1;
1014 v->lo = &bs->ob_field[0] + (v->lo - ofield);
1015 v->hi = &bs->ob_field[0] + (v->hi - ofield);
1016 v->set = bs;
1017 assert(bs->ob_field <= v->hi && v->hi <= bs->ob_field+Py_SIZE(bs));
1018 assert(bs->ob_field <= v->lo && v->lo < bs->ob_field+Py_SIZE(bs));
1019 }
1020 return 0;
1021 }
1022
1023 static NyBitField *
sf_ins1(NySetField * sf,NyBitField * f,NyBit pos)1024 sf_ins1(NySetField *sf, NyBitField *f, NyBit pos)
1025 {
1026 NyBitField *lo_tot = sf->set->ob_field;
1027 NyBitField *hi_tot = sf->set->ob_field + Py_SIZE(sf->set);
1028 NyBit lo_size = f - sf->lo;
1029 NyBit hi_size = sf->hi - f;
1030 NyBit tot_size = sf->hi - sf->lo;
1031
1032 if (hi_size <= lo_size && sf->hi < hi_tot) goto MOVE_HI;
1033 if (lo_size <= hi_size && sf->lo > lo_tot) goto MOVE_LO;
1034 if (hi_size <= lo_size * 3 && sf->hi < hi_tot) goto MOVE_HI;
1035 if (lo_size <= hi_size * 3 && sf->lo > lo_tot) goto MOVE_LO;
1036
1037 if (tot_size * 8 < Py_SIZE(sf->set) * 7) {
1038 /* Not extremely filled. May pay to center it. */
1039 NyBit move = ((hi_tot - sf->hi) - (sf->lo - lo_tot)) / 2;
1040 fp_move(sf->lo + move, sf->lo, tot_size);
1041 f += move;
1042 sf->lo += move;
1043 sf->hi += move;
1044 if (hi_size <= lo_size && sf->hi < hi_tot) goto MOVE_HI;
1045 if (lo_size <= hi_size && sf->lo > lo_tot) goto MOVE_LO;
1046 assert(0);
1047 }
1048
1049 if (sf_realloc(sf, sf->hi + 1 - lo_tot) == -1)
1050 return 0;
1051 f = sf->lo + lo_size;
1052
1053 hi_tot = sf->set->ob_field + Py_SIZE(sf->set);
1054 lo_tot = sf->set->ob_field;
1055 {
1056 NyBit move = ((hi_tot - sf->hi) - (sf->lo - lo_tot)) / 2;
1057 fp_move(sf->lo + move, sf->lo, tot_size);
1058 f += move;
1059 sf->lo += move;
1060 sf->hi += move;
1061 if (hi_size <= lo_size && sf->hi < hi_tot) goto MOVE_HI;
1062 if (lo_size <= hi_size && sf->lo > lo_tot) goto MOVE_LO;
1063 assert(0);
1064
1065 }
1066
1067 MOVE_HI:
1068 fp_move(f + 1, f, hi_size);
1069 sf->hi++;
1070 return f;
1071
1072 MOVE_LO:
1073 fp_move(sf->lo - 1, sf->lo, lo_size);
1074 sf->lo--;
1075 return f - 1;
1076 }
1077
1078 static NyBitField *
mutbitset_split_ins1(NyMutBitSetObject * v,NySetField * sf,NyBitField * f,NyBit pos)1079 mutbitset_split_ins1(NyMutBitSetObject *v, NySetField *sf, NyBitField *f, NyBit pos) {
1080 NyBit sfpos = sf - v->root->ob_field;
1081 NyBit a_size = f - sf->lo;
1082 NyBit b_size = sf->hi - f;
1083 NySetField *nsf = root_ins1(v, sf+1, pos);
1084 assert(a_size >= 0);
1085 assert(b_size >= 0);
1086 if (!nsf)
1087 return 0;
1088 sf = v->root->ob_field + sfpos;
1089 if (sf_realloc(nsf, b_size) == -1)
1090 return 0;
1091 nsf->lo = nsf->set->ob_field + (Py_SIZE(nsf->set) - b_size) / 2;
1092 nsf->hi = nsf->lo + b_size;
1093 fp_move(nsf->lo, f, b_size);
1094 nsf->pos = nsf->lo->pos;
1095 sf->hi = f;
1096 if (sf_realloc(sf, f + 1 - sf->set->ob_field) == -1)
1097 return 0;
1098 f = sf->lo + a_size;
1099 sf->hi = f + 1;
1100 assert(sf->hi <= sf->set->ob_field+Py_SIZE(sf->set));
1101 return f;
1102 }
1103
1104 static NyBitField *
mutbitset_ins1(NyMutBitSetObject * v,NySetField * sf,NyBitField * f,NyBit pos)1105 mutbitset_ins1(NyMutBitSetObject *v, NySetField *sf, NyBitField *f, NyBit pos)
1106 {
1107 if (f - sf->lo > v->splitting_size &&
1108 sf->hi - f > v->splitting_size)
1109 f = mutbitset_split_ins1(v, sf, f, pos);
1110 else
1111 f = sf_ins1(sf, f, pos);
1112 if (f) {
1113 f->pos = pos;
1114 f->bits = 0;
1115 }
1116 return f;
1117 }
1118
1119 static NyBitField *
mutbitset_findpos(NyMutBitSetObject * v,NyBit pos)1120 mutbitset_findpos(NyMutBitSetObject *v, NyBit pos)
1121 {
1122 NyBitField *f = v->cur_field;
1123 NySetField *sf;
1124 if (f && f->pos == pos)
1125 return f;
1126 {
1127 NyUnionObject *root = v->root;
1128 NySetField *lo = &root->ob_field[0];
1129 NySetField *hi = &root->ob_field[root->cur_size];
1130 sf = setfield_binsearch(lo, hi, pos);
1131 assert(lo <= sf && sf < hi);
1132 assert(lo->pos <= pos);
1133 assert(sf >= lo);
1134 }
1135 {
1136 f = bitfield_binsearch(sf->lo, sf->hi, pos);
1137 if (!(f < sf->hi && f->pos == pos))
1138 f = 0;
1139 return f;
1140 }
1141 }
1142
1143
1144 static NyBitField *
mutbitset_findpos_mut(NyMutBitSetObject * v,NyBit pos)1145 mutbitset_findpos_mut(NyMutBitSetObject *v, NyBit pos)
1146 {
1147 NyBitField *f = v->cur_field;
1148 NyUnionObject *root;
1149 NySetField *sf;
1150 if (f && f->pos == pos)
1151 return f;
1152 root = v->root;
1153 {
1154 NySetField *lo = &root->ob_field[0];
1155 NySetField *hi = &root->ob_field[root->cur_size];
1156 sf = setfield_binsearch(lo, hi, pos);
1157 assert(lo <= sf && sf < hi);
1158 assert(lo->pos <= pos);
1159 assert(sf >= lo);
1160 }
1161 {
1162 f = bitfield_binsearch(sf->lo, sf->hi, pos);
1163 if (!(f < sf->hi && f->pos == pos))
1164 /* Not found so we are not going to update. */
1165 f = 0;
1166 else {
1167 if (Py_REFCNT(root) > 1 || Py_REFCNT(sf->set) > 1) {
1168 /* It was found but some struct needs to be copied.
1169 Just research in ins mode. */
1170 f = mutbitset_findpos_ins(v, pos);
1171 }
1172 }
1173 }
1174 return f;
1175 }
1176
1177
1178 static NyBitField *
mutbitset_findpos_ins(NyMutBitSetObject * v,NyBit pos)1179 mutbitset_findpos_ins(NyMutBitSetObject *v, NyBit pos)
1180 {
1181 int ins = 1;
1182 NySetField *sf;
1183 NyBitField *f = v->cur_field;
1184 if (f && f->pos == pos)
1185 return f;
1186 {
1187 NySetField *lo, *hi;
1188 hi = 0; /* Avoid warning */
1189 lo = mutbitset_getrange_mut(v, &hi);
1190 sf = setfield_binsearch(lo, hi, pos);
1191 assert(lo <= sf && sf < hi);
1192 assert(lo->pos <= pos);
1193 assert(sf >= lo);
1194 }
1195 {
1196 NyBitField *lo, *hi;
1197 lo = sf_getrange_mut(sf, &hi);
1198 (void)lo;
1199 f = bitfield_binsearch(sf->lo, sf->hi, pos);
1200 if (ins) {
1201 if (!(f < sf->hi && f->pos == pos))
1202 f = mutbitset_ins1(v, sf, f, pos);
1203 v->cur_field = f;
1204 } else {
1205 if (!(f < sf->hi && f->pos == pos))
1206 f = 0;
1207 }
1208 return f;
1209 }
1210 }
1211
1212 static NySetField *
union_getrange(NyUnionObject * v,NySetField ** shi)1213 union_getrange(NyUnionObject *v, NySetField **shi)
1214 {
1215 *shi = &v->ob_field[v->cur_size];
1216 return &v->ob_field[0];
1217 }
1218
1219
1220 static NySetField *
mutbitset_getrange(NyMutBitSetObject * v,NySetField ** shi)1221 mutbitset_getrange(NyMutBitSetObject *v, NySetField **shi)
1222 {
1223 return union_getrange(v->root, shi);
1224 }
1225
1226 static NySetField *
mutbitset_getrange_mut(NyMutBitSetObject * v,NySetField ** shi)1227 mutbitset_getrange_mut(NyMutBitSetObject *v, NySetField **shi)
1228 {
1229 NyUnionObject *root = v->root;
1230 if (Py_REFCNT(root) > 1) {
1231 NyUnionObject *nroot = PyObject_NewVar(NyUnionObject, &NyUnion_Type, Py_SIZE(root));
1232 NyBit i;
1233 if (!nroot)
1234 return 0;
1235 nroot->cur_size = root->cur_size;
1236 sfp_move(nroot->ob_field, root->ob_field, root->cur_size);
1237 for (i = 0; i < nroot->cur_size; i++) {
1238 Py_INCREF(nroot->ob_field[i].set);
1239 }
1240 v->root = nroot;
1241 /* assert(!v->cur_field); */ /* See note Oct 20 2004
1242 - it may not be 0 in all cases */
1243
1244 v->cur_field = 0; /* see notes per 5/6-03, when it was thought
1245 that it should be 0 already but just in case */
1246 Py_DECREF(root);
1247 root = nroot;
1248 }
1249 return union_getrange(root, shi);
1250 }
1251
1252 static NyImmBitSetObject *
mutbitset_as_noncomplemented_immbitset_subtype(NyMutBitSetObject * v,PyTypeObject * type)1253 mutbitset_as_noncomplemented_immbitset_subtype(NyMutBitSetObject *v, PyTypeObject *type)
1254 {
1255 NyBit j;
1256 NyBit size = 0;
1257 NyImmBitSetObject *bs;
1258 NySetField *slo, *shi, *s;
1259 NyBitField *fhi, *flo, *f;
1260 flo = fhi = 0; /* Just avoid a spurios undefined-warning */
1261 slo = mutbitset_getrange(v, &shi);
1262 for (s = slo; s < shi; s++) {
1263 flo = sf_getrange(s, &fhi);
1264 for (f = flo; f < fhi; f++) {
1265 if (f->bits)
1266 size++;
1267 }
1268 }
1269 if ((type == &NyImmBitSet_Type &&
1270 shi - slo == 1 &&
1271 fhi - flo == size &&
1272 Py_SIZE(slo->set) == size)) {
1273 bs = slo->set;
1274 Py_INCREF(bs);
1275 v->cur_field = 0;
1276 } else {
1277 bs = NyImmBitSet_SubtypeNew(type, size);
1278 if (!bs) return 0;
1279 j = 0;
1280 for (s = slo; s < shi; s++) {
1281 flo = sf_getrange(s, &fhi);
1282 for (f = flo; f < fhi; f++) {
1283 if (f->bits)
1284 bs->ob_field[j++] = *f;
1285 }
1286 }
1287 assert(j == size);
1288 }
1289 return bs;
1290 }
1291
1292 static NyImmBitSetObject *
mutbitset_as_noncomplemented_immbitset(NyMutBitSetObject * v)1293 mutbitset_as_noncomplemented_immbitset(NyMutBitSetObject *v)
1294 {
1295 return mutbitset_as_noncomplemented_immbitset_subtype(v, &NyImmBitSet_Type);
1296 }
1297
1298
1299 static PyObject *
mutbitset_as_immbitset_and_cpl(NyMutBitSetObject * v,int cpl)1300 mutbitset_as_immbitset_and_cpl(NyMutBitSetObject *v, int cpl)
1301 {
1302 NyImmBitSetObject *bs = mutbitset_as_noncomplemented_immbitset(v);
1303 PyObject *ret;
1304 if (!bs)
1305 return 0;
1306 if ((v->cpl != 0) != (cpl != 0)) {
1307 ret = immbitset_complement(bs);
1308 Py_DECREF(bs);
1309 } else
1310 ret = (PyObject *)bs;
1311 return ret;
1312 }
1313
1314 PyObject *
NyMutBitSet_AsImmBitSet(NyMutBitSetObject * v)1315 NyMutBitSet_AsImmBitSet(NyMutBitSetObject *v)
1316 {
1317 return mutbitset_as_immbitset_and_cpl(v, 0);
1318 }
1319
1320 static PyObject *
mutbitset_as_immbitset_and_del(NyMutBitSetObject * v)1321 mutbitset_as_immbitset_and_del(NyMutBitSetObject *v)
1322 {
1323 PyObject *bs = NyMutBitSet_AsImmBitSet(v);
1324 Py_DECREF(v);
1325 return bs;
1326 }
1327
1328
1329 int
NyMutBitSet_hasbit(NyMutBitSetObject * v,NyBit bit)1330 NyMutBitSet_hasbit(NyMutBitSetObject *v, NyBit bit)
1331 {
1332 NyBitField f, *fp;
1333 bitno_to_field(bit, &f);
1334 fp = mutbitset_findpos(v, f.pos);
1335 if (!fp)
1336 return 0;
1337 return (fp->bits & f.bits) != 0;
1338 }
1339 static int
mutbitset_contains(NyMutBitSetObject * v,PyObject * w)1340 mutbitset_contains(NyMutBitSetObject *v, PyObject *w)
1341 {
1342 NyBit bit = bitno_from_object(w);
1343 if (bit == -1 && PyErr_Occurred())
1344 return -1;
1345 return NyMutBitSet_hasbit(v, bit);
1346 }
1347
1348 static int
mutbitset_clear(NyMutBitSetObject * v)1349 mutbitset_clear(NyMutBitSetObject *v)
1350 {
1351 if (v->root != &v->fst_root) {
1352 Py_DECREF(v->root);
1353 } else {
1354 NyBit i;
1355 for (i = 0; i < v->root->cur_size; i++)
1356 Py_DECREF(v->root->ob_field[i].set);
1357 }
1358 v->cur_field = 0;
1359 v->root = &v->fst_root;
1360 Py_SIZE(&v->fst_root) = 0;
1361 v->fst_root.cur_size = 0;
1362 return 0;
1363 }
1364
1365
1366 static void
mutbitset_dealloc(NyMutBitSetObject * v)1367 mutbitset_dealloc(NyMutBitSetObject *v)
1368 {
1369 mutbitset_clear(v);
1370 Py_TYPE(v)->tp_free((PyObject *)v);
1371 n_mutbitset--;
1372 }
1373
1374 static void
mutbitset_set_hi(NyMutBitSetObject * v,NySetField * sf,NyBitField * f)1375 mutbitset_set_hi(NyMutBitSetObject *v, NySetField *sf, NyBitField *f)
1376 {
1377 sf->hi = f;
1378 v->cur_field = 0;
1379 }
1380
1381 static void
mutbitset_set_lo(NyMutBitSetObject * v,NySetField * sf,NyBitField * f)1382 mutbitset_set_lo(NyMutBitSetObject *v, NySetField *sf, NyBitField *f)
1383 {
1384 sf->lo = f;
1385 v->cur_field = 0;
1386 }
1387
1388 static PyObject *
mutbitset_complement(NyMutBitSetObject * v)1389 mutbitset_complement(NyMutBitSetObject *v)
1390 {
1391 return mutbitset_as_immbitset_and_cpl(v, 1);
1392 }
1393
1394 static PyObject *
mutbitset_int(NyMutBitSetObject * v)1395 mutbitset_int(NyMutBitSetObject *v)
1396 {
1397 PyObject *w = NyMutBitSet_AsImmBitSet(v);
1398 PyObject *x;
1399 if (!w) return 0;
1400 x = PyNumber_Long(w);
1401 Py_DECREF(w);
1402 return x;
1403 }
1404
1405 static int
mutbitset_ior_field(NyMutBitSetObject * v,NyBitField * w)1406 mutbitset_ior_field(NyMutBitSetObject *v, NyBitField *w)
1407 {
1408 NyBitField *f;
1409 if (w->bits) {
1410 f = mutbitset_findpos_ins(v, w->pos);
1411 if (!f) return -1;
1412 f->bits |= w->bits;
1413 }
1414 return 0;
1415 }
1416
1417 static int
mutbitset_ior_fields(NyMutBitSetObject * v,NyBitField * w,NyBit n)1418 mutbitset_ior_fields(NyMutBitSetObject *v, NyBitField *w, NyBit n)
1419 {
1420 for (; n--;)
1421 if (mutbitset_ior_field(v, w++))
1422 return -1;
1423 return 0;
1424 }
1425
1426 static int
mutbitset_iop_field(NyMutBitSetObject * v,int op,NyBitField * w)1427 mutbitset_iop_field(NyMutBitSetObject *v, int op, NyBitField *w)
1428 {
1429 NyBitField *f;
1430 switch(op) {
1431 case NyBits_OR:
1432 return mutbitset_ior_field(v, w);
1433 case NyBits_XOR:
1434 if (w->bits) {
1435 f = mutbitset_findpos_ins(v, w->pos);
1436 if (!f) return -1;
1437 f->bits ^= w->bits;
1438 }
1439 break;
1440 case NyBits_SUB:
1441 if (w->bits) {
1442 f = mutbitset_findpos_mut(v, w->pos);
1443 if (!f) return 0;
1444 f->bits &= ~ w->bits;
1445 }
1446 break;
1447 default:
1448 PyErr_SetString(PyExc_ValueError,
1449 "Invalid mutbitset_iop_field() operation");
1450 return -1;
1451 }
1452 return 0;
1453 }
1454
1455 /* cpl_conv_left
1456
1457 Convert left inversion
1458
1459 ~a & b == == a SUBR b
1460 ~a | b == ~(a & ~ b) == ~(a SUB b)
1461 ~a ^ b == == ~(a ^ b)
1462 ~a SUB b == ~a & ~b == ~(a | b)
1463 ~a SUBR b == ~(~a) & b == a & b
1464
1465 */
1466
1467
1468 int
cpl_conv_left(int * cplp,int op)1469 cpl_conv_left(int *cplp, int op)
1470 {
1471 if (*cplp) {
1472 switch(op) {
1473 case NyBits_AND: op = NyBits_SUBR; *cplp = 0; break;
1474 case NyBits_OR: op = NyBits_SUB; break;
1475 case NyBits_XOR: break;
1476 case NyBits_SUB: op = NyBits_OR; break;
1477 case NyBits_SUBR: op = NyBits_AND; *cplp = 0; break;
1478 default: assert(0);
1479 }
1480 }
1481 return op;
1482 }
1483
1484 /* cpl_conv_right
1485
1486 Convert right inversion
1487
1488 a & ~b == == a SUB b
1489 a | ~b == ~(~a & b) == ~(a SUBR b)
1490 a ^ ~b == == ~(a ^ b)
1491 a SUB ~b == a & ~(~b) == a & b
1492 a SUBR ~b == ~a & ~b == ~(a | b)
1493
1494 */
1495
1496 int
cpl_conv_right(int op,int * cplp)1497 cpl_conv_right(int op, int *cplp)
1498 {
1499 if (*cplp) {
1500 switch(op) {
1501 case NyBits_AND: op = NyBits_SUB; *cplp = 0; break;
1502 case NyBits_OR: op = NyBits_SUBR; break;
1503 case NyBits_XOR: break;
1504 case NyBits_SUB: op = NyBits_AND; *cplp = 0; break;
1505 case NyBits_SUBR: op = NyBits_OR; break;
1506 default: assert(0);
1507 }
1508 }
1509 return op;
1510 }
1511
1512 static int
mutbitset_iop_convert(NyMutBitSetObject * v,int op)1513 mutbitset_iop_convert(NyMutBitSetObject *v, int op)
1514 {
1515 return cpl_conv_left(&v->cpl, op);
1516 }
1517
1518 static int
mutbitset_iop_fields(NyMutBitSetObject * v,int op,NyBitField * w,NyBit n)1519 mutbitset_iop_fields(NyMutBitSetObject *v, int op, NyBitField *w, NyBit n)
1520 {
1521 NySetField *s, *end_s;
1522 NyBitField *f, *end_w, *end_f;
1523 end_s = 0; /* avoid warning */
1524 op = mutbitset_iop_convert(v, op);
1525 switch(op) {
1526 case NyBits_OR:
1527 case NyBits_XOR:
1528 case NyBits_SUB:
1529 while (n > 0) {
1530 if (mutbitset_iop_field(v, op, w) == -1)
1531 return -1;
1532 n--;
1533 w++;
1534 }
1535 break;
1536 case NyBits_AND:
1537 end_w = w + n;
1538 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
1539 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
1540 while (w < end_w && f->pos > w->pos)
1541 w++;
1542 if (w < end_w && w->pos == f->pos) {
1543 f->bits &= w->bits;
1544 w++;
1545 } else {
1546 f->bits = 0;
1547 }
1548 }
1549 break;
1550 case NyBits_SUBR: {
1551 NyBit i;
1552 for (i = 0; i < n; i++) {
1553 if (w[i].bits) {
1554 if (!mutbitset_findpos_ins(v, w[i].pos))
1555 return -1;
1556 }
1557 }
1558 end_w = w + n;
1559 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
1560 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
1561 while (w < end_w && f->pos > w->pos)
1562 w++;
1563 if (w < end_w && w->pos == f->pos) {
1564 f->bits = ~f->bits & w->bits;
1565 w++;
1566 } else {
1567 f->bits = 0;
1568 }
1569 }
1570 }
1571 break;
1572 default:
1573 PyErr_SetString(PyExc_ValueError,
1574 "Invalid mutbitset_iop_fields() operation");
1575 return -1;
1576 }
1577 return 0;
1578 }
1579
1580 static int
mutbitset_iop_bitno(NyMutBitSetObject * v,int op,NyBit bitno)1581 mutbitset_iop_bitno(NyMutBitSetObject *v, int op, NyBit bitno)
1582 {
1583 NyBitField f;
1584 bitno_to_field(bitno, &f);
1585 return mutbitset_iop_fields(v, op, &f, 1);
1586 }
1587
1588 static int
mutbitset_iop_bits(NyMutBitSetObject * v,int op,NyBit pos,NyBits * bits,NyBit n)1589 mutbitset_iop_bits(NyMutBitSetObject *v, int op, NyBit pos, NyBits *bits, NyBit n)
1590 {
1591 NySetField *s, *end_s;
1592 NyBitField *f, *end_f;
1593 end_s = 0; /* avoid warning */
1594 op = mutbitset_iop_convert(v, op);
1595 switch(op) {
1596 case NyBits_OR:
1597 case NyBits_XOR:
1598 case NyBits_SUB:
1599 while (n > 0) {
1600 NyBitField f;
1601 f.pos = pos;
1602 f.bits = *bits++;
1603 if (mutbitset_iop_field(v, op, &f) == -1)
1604 return -1;
1605 n--;
1606 pos++;
1607 }
1608 break;
1609 case NyBits_AND: {
1610 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
1611 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
1612 while (n > 0 && f->pos > pos) {
1613 n--;
1614 pos++;
1615 bits++;
1616 }
1617 if (n > 0 && f->pos == pos) {
1618 f->bits &= *bits++;
1619 n--;
1620 pos++;
1621 } else {
1622 f->bits = 0;
1623 }
1624 }
1625 }
1626 break;
1627 case NyBits_SUBR: {
1628 int i;
1629 for (i = 0; i < n; i++) {
1630 if (bits[i]) {
1631 if (!mutbitset_findpos_ins(v, pos + i))
1632 return -1;
1633 }
1634 }
1635 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
1636 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
1637 while (n > 0 && f->pos > pos) {
1638 n--;
1639 pos++;
1640 bits++;
1641 }
1642 if (n > 0 && f->pos == pos) {
1643 f->bits = ~f->bits & *bits++;
1644 n--;
1645 pos++;
1646 } else {
1647 f->bits = 0;
1648 }
1649 }
1650 }
1651 break;
1652 default:
1653 PyErr_SetString(PyExc_ValueError,
1654 "Invalid mutbitset_iop_bits() operation");
1655 return -1;
1656 }
1657 return 0;
1658 }
1659
1660
1661 static int
mutbitset_iop_immbitset(NyMutBitSetObject * v,int op,NyImmBitSetObject * w)1662 mutbitset_iop_immbitset(NyMutBitSetObject *v, int op, NyImmBitSetObject *w)
1663 {
1664 return mutbitset_iop_fields(v, op, w->ob_field, Py_SIZE(w));
1665 }
1666
1667 static int
mutbitset_reset(NyMutBitSetObject * v,NyImmBitSetObject * set)1668 mutbitset_reset(NyMutBitSetObject *v, NyImmBitSetObject *set)
1669 {
1670 mutbitset_clear(v);
1671 return mutbitset_initset(v, set);
1672 }
1673
NyMutBitSet_clear(NyMutBitSetObject * v)1674 int NyMutBitSet_clear(NyMutBitSetObject *v)
1675 {
1676 return mutbitset_reset(v, 0);
1677 }
1678
1679
1680 static int
mutbitset_iop_complement(NyMutBitSetObject * v)1681 mutbitset_iop_complement(NyMutBitSetObject *v)
1682 {
1683 v->cpl = !v->cpl;
1684 return 0;
1685 }
1686
1687 static int
mutbitset_iop_cplbitset(NyMutBitSetObject * v,int op,NyCplBitSetObject * w)1688 mutbitset_iop_cplbitset(NyMutBitSetObject *v, int op, NyCplBitSetObject *w)
1689 {
1690 int cpl = 1;
1691 int r;
1692 op = cpl_conv_right(op, &cpl);
1693 r = mutbitset_iop_immbitset(v, op, cplbitset_cpl(w));
1694 if (!r && cpl)
1695 r = mutbitset_iop_complement(v);
1696 return r;
1697 }
1698
1699 static int
mutbitset_iop_mutset(NyMutBitSetObject * v,int op,NyMutBitSetObject * w)1700 mutbitset_iop_mutset(NyMutBitSetObject *v, int op, NyMutBitSetObject *w)
1701 {
1702 int cpl = w->cpl;
1703 NySetField *s, *end_s;
1704 NyBitField *f, *end_f, *wf;
1705 end_s = 0; /* avoid warning */
1706 op = cpl_conv_right(op, &cpl);
1707 op = mutbitset_iop_convert(v, op);
1708 if (v == w) {
1709 /* Special caseing this because:
1710 - may be problems updating the same we iterate on
1711 - the special case may likely be faster
1712 - an obvious opportunity to clear out redundant storage when eg doing ms ^= ms
1713 */
1714 switch (op) {
1715 case NyBits_OR:
1716 case NyBits_AND:
1717 break;
1718 case NyBits_SUB:
1719 case NyBits_SUBR:
1720 case NyBits_XOR:
1721 if (mutbitset_reset(v, 0) == -1)
1722 return -1;
1723 break;
1724 default:
1725 PyErr_SetString(PyExc_ValueError,
1726 "Invalid mutbitset_iop_fields() operation");
1727 return -1;
1728 }
1729 } else
1730 switch(op) {
1731 case NyBits_OR:
1732 case NyBits_XOR:
1733 case NyBits_SUB:
1734 for (s = mutbitset_getrange(w, &end_s); s < end_s; s++)
1735 for (f = sf_getrange(s, &end_f); f < end_f; f++)
1736 if (mutbitset_iop_field(v, op, f) == -1)
1737 return -1;
1738 break;
1739 case NyBits_AND:
1740 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
1741 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
1742 wf = mutbitset_findpos(w, f->pos);
1743 if (wf)
1744 f->bits &= wf->bits;
1745 else
1746 f->bits = 0;
1747 }
1748 break;
1749 case NyBits_SUBR:
1750 for (s = mutbitset_getrange(w, &end_s); s < end_s; s++)
1751 for (f = sf_getrange(s, &end_f); f < end_f; f++)
1752 if (!mutbitset_findpos_ins(v, f->pos))
1753 return -1;
1754 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
1755 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
1756 wf = mutbitset_findpos(w, f->pos);
1757 if (wf)
1758 f->bits = ~f->bits & wf->bits;
1759 else
1760 f->bits = 0;
1761 }
1762 break;
1763 default:
1764 PyErr_SetString(PyExc_ValueError,
1765 "Invalid mutbitset_iop_fields() operation");
1766 return -1;
1767 }
1768 if (cpl)
1769 mutbitset_iop_complement(v);
1770 return 0;
1771 }
1772
1773 static int
mutbitset_iop_iterable(NyMutBitSetObject * ms,int op,PyObject * v)1774 mutbitset_iop_iterable(NyMutBitSetObject *ms, int op, PyObject *v)
1775 {
1776 PyObject *it = 0; /* iter(v) */
1777 NyMutBitSetObject *tms;
1778 if (op == NyBits_AND) {
1779 tms = NyMutBitSet_New();
1780 if (!tms) return -1;
1781 op = NyBits_OR;
1782 }
1783 else
1784 tms = ms;
1785
1786
1787 it = PyObject_GetIter(v);
1788 if (it == NULL)
1789 goto Err;
1790 /* Run iterator to exhaustion. */
1791 for (;;) {
1792 PyObject *item = PyIter_Next(it);
1793 NyBit bit;
1794 if (item == NULL) {
1795 if (PyErr_Occurred())
1796 goto Err;
1797 break;
1798 }
1799 bit = bitno_from_object(item);
1800 Py_DECREF(item);
1801 if (bit == -1 && PyErr_Occurred())
1802 goto Err;
1803 if (mutbitset_iop_bitno(tms, op, bit) == -1)
1804 goto Err;
1805 }
1806 if (tms != ms) {
1807 if (mutbitset_iop_mutset(ms, NyBits_AND, tms) == -1)
1808 goto Err;
1809 Py_DECREF(tms);
1810 }
1811 Py_DECREF(it);
1812 return 0;
1813 Err:
1814 if (tms != ms) {
1815 Py_DECREF(tms);
1816 }
1817 Py_XDECREF(it);
1818 return -1;
1819 }
1820
1821 static int
mutbitset_iop_PyListObject(NyMutBitSetObject * ms,int op,PyObject * v)1822 mutbitset_iop_PyListObject(NyMutBitSetObject *ms, int op, PyObject *v)
1823 {
1824 NyBit size = PyList_GET_SIZE(v);
1825 NyBit i;
1826 NyMutBitSetObject *tms;
1827 if (op == NyBits_AND) {
1828 tms = NyMutBitSet_New();
1829 if (!tms) return -1;
1830 op = NyBits_OR;
1831 }
1832 else
1833 tms = ms;
1834 for (i = 0; i < size; i++) {
1835 NyBit bit = bitno_from_object(PyList_GET_ITEM(v, i));
1836 if (bit == -1 && PyErr_Occurred())
1837 goto Err;
1838 if (mutbitset_iop_bitno(tms, op, bit) == -1)
1839 goto Err;
1840 }
1841 if (tms != ms) {
1842 if (mutbitset_iop_mutset(ms, NyBits_AND, tms) == -1)
1843 goto Err;
1844 Py_DECREF(tms);
1845 }
1846 return 0;
1847
1848 Err:
1849 if (tms != ms) {
1850 Py_DECREF(tms);
1851 }
1852 return -1;
1853 }
1854
1855 static int
mutbitset_iop_PyTupleObject(NyMutBitSetObject * ms,int op,PyObject * v)1856 mutbitset_iop_PyTupleObject(NyMutBitSetObject *ms, int op, PyObject *v)
1857 {
1858 NyBit size = PyTuple_GET_SIZE(v);
1859 NyBit i;
1860 NyMutBitSetObject *tms;
1861 if (op == NyBits_AND) {
1862 tms = NyMutBitSet_New();
1863 if (!tms) return -1;
1864
1865 op = NyBits_OR;
1866 }
1867 else
1868 tms = ms;
1869 for (i = 0; i < size; i++) {
1870 NyBit bit = bitno_from_object(PyTuple_GET_ITEM(v, i));
1871 if (bit == -1 && PyErr_Occurred())
1872 goto Err;
1873 if (mutbitset_iop_bitno(tms, op, bit) == -1)
1874 goto Err;
1875 }
1876 if (tms != ms) {
1877 if (mutbitset_iop_mutset(ms, NyBits_AND, tms) == -1)
1878 goto Err;
1879 Py_DECREF(tms);
1880 }
1881 return 0;
1882
1883 Err:
1884 if (tms != ms) {
1885 Py_DECREF(tms);
1886 }
1887 return -1;
1888 }
1889
1890 static int
mutbitset_iop_PyDictObject(NyMutBitSetObject * ms,int op,PyObject * v)1891 mutbitset_iop_PyDictObject(NyMutBitSetObject *ms, int op, PyObject *v)
1892 {
1893 Py_ssize_t i;
1894 NyMutBitSetObject *tms;
1895 PyObject *key, *value;
1896 if (op == NyBits_AND) {
1897 tms = NyMutBitSet_New();
1898 if (!tms) return -1;
1899 op = NyBits_OR;
1900 }
1901 else
1902 tms = ms;
1903 i = 0;
1904 while (PyDict_Next(v, &i, &key, &value)) {
1905 NyBit bit = bitno_from_object(key);
1906 if (bit == -1 && PyErr_Occurred())
1907 goto Err;
1908 if (mutbitset_iop_bitno(tms, op, bit) == -1)
1909 goto Err;
1910 }
1911 if (tms != ms) {
1912 if (mutbitset_iop_mutset(ms, NyBits_AND, tms) == -1)
1913 goto Err;
1914 Py_DECREF(tms);
1915 }
1916 return 0;
1917
1918 Err:
1919 if (tms != ms) {
1920 Py_DECREF(tms);
1921 }
1922 return -1;
1923 }
1924
1925 static int
mutbitset_iop_PyLongObject(NyMutBitSetObject * ms,int op,PyObject * v)1926 mutbitset_iop_PyLongObject(NyMutBitSetObject *ms, int op, PyObject *v)
1927 {
1928 NyBits *buf;
1929 int r = -1;
1930 Py_ssize_t e;
1931 NyBit num_bits, num_poses, num_bytes;
1932 double x;
1933 int cpl = 0;
1934 PyObject *w = 0;
1935
1936 x = _PyLong_Frexp((PyLongObject *)v, &e);
1937 if (x == -1 && PyErr_Occurred())
1938 return -1;
1939 if (x < 0) {
1940 cpl = !cpl;
1941 op = cpl_conv_right(op, &cpl);
1942 w = PyNumber_Invert(v);
1943 if (!w) return -1;
1944 v = w;
1945 x = _PyLong_Frexp((PyLongObject *)v, &e);
1946 if (x == -1 && PyErr_Occurred())
1947 return -1;
1948 assert(x >= 0);
1949 }
1950 if (x != 0)
1951 num_bits = e;
1952 else
1953 num_bits = 0;
1954
1955 num_poses = (NyBit)(num_bits / NyBits_N + 1);
1956 /* fprintf(stderr, "x %f e %d num_bits %f num_poses %ld\n", x, e, num_bits, num_poses); */
1957 num_bytes = num_poses * sizeof(NyBits);
1958 buf = PyMem_New(NyBits, num_poses);
1959 if (!buf) {
1960 PyErr_NoMemory();
1961 goto Err1;
1962 }
1963 r = _PyLong_AsByteArray((PyLongObject *)v,
1964 (unsigned char *)buf,
1965 num_bytes,
1966 1, /* little_endian */
1967 0 /* is_signed */);
1968 if (r == -1) goto Err1;
1969 #if NyBits_IS_BIG_ENDIAN
1970 {
1971 NyBit pos;
1972 for (pos = 0; pos < num_poses; pos++) {
1973 buf[pos] = NyBits_BSWAP(buf[pos]);
1974 }
1975 }
1976 #endif
1977
1978 r = mutbitset_iop_bits(ms, op, 0, buf, num_poses);
1979 if (!r && cpl)
1980 r = mutbitset_iop_complement(ms);
1981 Err1:
1982 PyMem_Del(buf);
1983 Py_XDECREF(w);
1984 return r;
1985 }
1986
1987 PyObject *
mutbitset_iop(NyMutBitSetObject * v,int op,PyObject * w)1988 mutbitset_iop(NyMutBitSetObject *v, int op, PyObject *w)
1989 {
1990 int wt = 0;
1991 int r;
1992 anybitset_classify(w, &wt);
1993 if (wt == BITSET)
1994 r = mutbitset_iop_immbitset(v, op, (NyImmBitSetObject *)w);
1995 else if (wt == CPLSET)
1996 r = mutbitset_iop_cplbitset(v, op, (NyCplBitSetObject *)w);
1997 else if (wt == MUTSET)
1998 r = mutbitset_iop_mutset(v, op, (NyMutBitSetObject *)w);
1999 else if (PyLong_Check(w))
2000 r = mutbitset_iop_PyLongObject(v, op, w);
2001 else if (PyList_Check(w))
2002 r = mutbitset_iop_PyListObject(v, op, w);
2003 else if (PyTuple_Check(w))
2004 r = mutbitset_iop_PyTupleObject(v, op, w);
2005 else if (PyDict_Check(w))
2006 r = mutbitset_iop_PyDictObject(v, op, w);
2007 else if (PyDict_Check(w))
2008 r = mutbitset_iop_PyDictObject(v, op, w);
2009 else if (NyIterable_Check(w))
2010 r = mutbitset_iop_iterable(v, op, w);
2011 else {
2012 PyErr_Format(PyExc_TypeError,
2013 "operand for mutable bitset must be integer or iterable");
2014 return NULL;
2015 }
2016 if (r == -1)
2017 return NULL;
2018 else {
2019 Py_INCREF(v);
2020 return (PyObject *)v;
2021 }
2022 }
2023
2024 PyObject *
mutbitset_iand(NyMutBitSetObject * v,PyObject * w)2025 mutbitset_iand(NyMutBitSetObject *v, PyObject *w)
2026 {
2027 return mutbitset_iop(v, NyBits_AND, w);
2028 }
2029
2030 PyObject *
mutbitset_ior(NyMutBitSetObject * v,PyObject * w)2031 mutbitset_ior(NyMutBitSetObject *v, PyObject *w)
2032 {
2033 return mutbitset_iop(v, NyBits_OR, w);
2034 }
2035
2036 PyObject *
mutbitset_isub(NyMutBitSetObject * v,PyObject * w)2037 mutbitset_isub(NyMutBitSetObject *v, PyObject *w)
2038 {
2039 return mutbitset_iop(v, NyBits_SUB, w);
2040 }
2041
2042 PyObject *
mutbitset_ixor(NyMutBitSetObject * v,PyObject * w)2043 mutbitset_ixor(NyMutBitSetObject *v, PyObject *w)
2044 {
2045 return mutbitset_iop(v, NyBits_XOR, w);
2046 }
2047
2048 PyObject *
mutbitset_iter(NyMutBitSetObject * v)2049 mutbitset_iter(NyMutBitSetObject *v)
2050 {
2051 PyObject *bs = NyMutBitSet_AsImmBitSet(v);
2052 if (bs) {
2053 PyObject *iter = PyObject_GetIter(bs);
2054 Py_DECREF(bs);
2055 return iter;
2056 }
2057 return 0;
2058 }
2059
2060
2061 static NyMutBitSetObject *
mutbitset_subtype_new_from_arg(PyTypeObject * type,PyObject * arg)2062 mutbitset_subtype_new_from_arg(PyTypeObject *type, PyObject *arg)
2063 {
2064 NyMutBitSetObject *ms;
2065 NyImmBitSetObject *set = 0;
2066 NyUnionObject *root = 0;
2067 if (arg) {
2068 if (NyImmBitSet_Check(arg)) {
2069 set = (NyImmBitSetObject *)arg;
2070 Py_INCREF(set);
2071 } else if (NyMutBitSet_Check(arg)) {
2072 NyMutBitSetObject *oms = (NyMutBitSetObject *)arg;
2073 if (oms->root != &oms->fst_root) {
2074 root = oms->root;
2075 Py_INCREF(root);
2076 oms->cur_field = 0;
2077 }
2078 }
2079 }
2080 ms = NyMutBitSet_SubtypeNew(type, set, root);
2081 Py_XDECREF(set);
2082 Py_XDECREF(root);
2083 if (!ms) return 0;
2084 if (!(set || root)) {
2085 if (arg) {
2086 void *r = mutbitset_ior(ms, arg);
2087 Py_DECREF(ms);
2088 ms = r;
2089 }
2090 }
2091 return ms;
2092 }
2093
2094 static NyMutBitSetObject *
mutbitset_new_from_arg(PyObject * arg)2095 mutbitset_new_from_arg(PyObject *arg)
2096 {
2097 return mutbitset_subtype_new_from_arg(&NyMutBitSet_Type, arg);
2098 }
2099
2100 static PyObject *
mutbitset_new(PyTypeObject * type,PyObject * args,PyObject * kwds)2101 mutbitset_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2102 {
2103 PyObject *arg = NULL;
2104 static char *kwlist[] = {"arg", 0};
2105 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O:mutbitset_new",kwlist, &arg))
2106 return NULL;
2107 return (PyObject *)mutbitset_subtype_new_from_arg(type, arg);
2108 }
2109
2110 static Py_ssize_t
mutbitset_length(PyObject * _v)2111 mutbitset_length(PyObject *_v)
2112 {
2113 NyMutBitSetObject *v=(void*)_v;
2114 NySetField *s, *end_s;
2115 NyBitField *f, *end_f;
2116 int n = 0;
2117 if (v->cpl) {
2118 PyErr_SetString(PyExc_TypeError, "len() of complemented set is undefined");
2119 return -1;
2120 }
2121 for (s = mutbitset_getrange(v, &end_s); s < end_s; s++)
2122 for (f = sf_getrange(s, &end_f); f < end_f; f++) {
2123 NyBits bits = f->bits;
2124 if (bits) {
2125 n += bits_length(bits);
2126 if (n < 0) {
2127 PyErr_SetString(PyExc_OverflowError, "len() is too large");
2128 return -1;
2129 }
2130 }
2131 }
2132 return n;
2133 }
2134
2135 static int
mutbitset_nonzero(NyMutBitSetObject * v)2136 mutbitset_nonzero(NyMutBitSetObject *v)
2137 {
2138 NySetField *s, *end_s;
2139 NyBitField *f, *end_f;
2140 if (v->cpl)
2141 return 1;
2142 for (s = mutbitset_getrange(v, &end_s); s < end_s; s++)
2143 for (f = sf_getrange(s, &end_f); f < end_f; f++)
2144 if (f->bits)
2145 return 1;
2146 return 0;
2147 }
2148
2149 static PyObject *
mutbitset_repr(NyMutBitSetObject * a)2150 mutbitset_repr(NyMutBitSetObject *a)
2151 {
2152 char *fmt;
2153 PyObject *s, *iter;
2154 if (a->cpl) {
2155 fmt = "MutBitSet(~ImmBitSet(%R))";
2156 /* Subtle:
2157 Get around that mutbitset doesnt allow iteration when complemented -
2158 this getaround assumes iter copies it to an immutable bitset. */
2159 a->cpl = 0;
2160 iter = PySequence_List((PyObject *)a);
2161 a->cpl = 1;
2162 }
2163 else {
2164 fmt = "MutBitSet(%R)";
2165 iter = PySequence_List((PyObject *)a);
2166 }
2167 if (!iter) goto Fail;
2168 s = PyUnicode_FromFormat(fmt, iter);
2169 Py_XDECREF(iter);
2170 return s;
2171 Fail:
2172 Py_XDECREF(iter);
2173 return 0;
2174 }
2175
2176 static int
mutbitset_set_or_clr(NyMutBitSetObject * v,NyBit bitno,int set_or_clr)2177 mutbitset_set_or_clr(NyMutBitSetObject *v, NyBit bitno, int set_or_clr)
2178 {
2179 NyBitField f, *fp;
2180 int ap = set_or_clr;
2181 if (v->cpl)
2182 ap = !ap;
2183 bitno_to_field(bitno, &f);
2184 if (ap) {
2185 fp = mutbitset_findpos_ins(v, f.pos);
2186 if (!fp)
2187 return -1;
2188 if (fp->bits & f.bits)
2189 return set_or_clr;
2190 fp->bits |= f.bits;
2191 } else {
2192 fp = mutbitset_findpos_mut(v, f.pos);
2193 if (!(fp && (fp->bits & f.bits))) {
2194 return set_or_clr;
2195 }
2196 fp->bits &= ~f.bits;
2197 }
2198 return !set_or_clr;
2199 }
2200
2201
2202 int
NyMutBitSet_setbit(NyMutBitSetObject * v,NyBit bitno)2203 NyMutBitSet_setbit(NyMutBitSetObject *v, NyBit bitno)
2204 {
2205 return mutbitset_set_or_clr(v, bitno, 1);
2206 }
2207
2208 int
NyMutBitSet_clrbit(NyMutBitSetObject * v,NyBit bitno)2209 NyMutBitSet_clrbit(NyMutBitSetObject *v, NyBit bitno)
2210 {
2211 return mutbitset_set_or_clr(v, bitno, 0);
2212 }
2213
2214 static PyObject *
mutbitset_tasbit(NyMutBitSetObject * v,PyObject * w)2215 mutbitset_tasbit(NyMutBitSetObject *v, PyObject *w)
2216 {
2217 NyBit bitno = bitno_from_object(w);
2218 int r;
2219 if (bitno == -1 && PyErr_Occurred())
2220 return 0;
2221 r = NyMutBitSet_setbit(v, bitno);
2222 if (r == -1)
2223 return 0;
2224 return PyLong_FromSsize_t(r);
2225 }
2226
2227
2228 static PyObject *
mutbitset_tacbit(NyMutBitSetObject * v,PyObject * w)2229 mutbitset_tacbit(NyMutBitSetObject *v, PyObject *w)
2230 {
2231 NyBit bitno = bitno_from_object(w);
2232 int r;
2233 if (bitno == -1 && PyErr_Occurred())
2234 return 0;
2235 r = NyMutBitSet_clrbit(v, bitno);
2236 if (r == -1)
2237 return 0;
2238 return PyLong_FromSsize_t(r);
2239 }
2240
2241
2242 static int
bitfields_iterate(NyBitField * f,NyBitField * end_f,int (* visit)(NyBit,void *),void * arg)2243 bitfields_iterate(NyBitField *f, NyBitField *end_f,
2244 int (*visit)(NyBit, void *),
2245 void *arg)
2246 {
2247 for (;f < end_f; f++) {
2248 NyBits bits = f->bits;
2249 int bitpos = 0;
2250 while (bits) {
2251 while (!(bits & 1)) {
2252 bits >>= 1;
2253 bitpos += 1;
2254 }
2255 if (visit(f->pos * NyBits_N + bitpos, arg) == -1)
2256 return -1;
2257 bits >>= 1;
2258 bitpos += 1;
2259 }
2260 }
2261 return 0;
2262 }
2263
2264
2265 static int
mutbitset_iterate(NyMutBitSetObject * v,int (* visit)(NyBit,void *),void * arg)2266 mutbitset_iterate(NyMutBitSetObject *v,
2267 int (*visit)(NyBit, void *),
2268 void *arg)
2269 {
2270 NySetField *s, *end_s;
2271 for (s = mutbitset_getrange(v, &end_s); s < end_s; s++) {
2272 NyBitField *f, *end_f;
2273 f = sf_getrange(s, &end_f);
2274 if (bitfields_iterate(f, end_f, visit, arg) == -1)
2275 return -1;
2276 }
2277 return 0;
2278 }
2279
2280 static int
immbitset_iterate(NyImmBitSetObject * v,int (* visit)(NyBit,void *),void * arg)2281 immbitset_iterate(NyImmBitSetObject *v,
2282 int (*visit)(NyBit, void *),
2283 void *arg)
2284 {
2285 return bitfields_iterate(&v->ob_field[0], &v->ob_field[Py_SIZE(v)],
2286 visit, arg);
2287 }
2288
2289
2290 int
NyAnyBitSet_iterate(PyObject * v,NySetVisitor visit,void * arg)2291 NyAnyBitSet_iterate(PyObject *v,
2292 NySetVisitor visit,
2293 void *arg)
2294 {
2295 if (NyImmBitSet_Check(v))
2296 return immbitset_iterate((NyImmBitSetObject *)v, visit, arg);
2297 else if (NyMutBitSet_Check(v))
2298 return mutbitset_iterate((NyMutBitSetObject *)v, visit, arg);
2299 else {
2300 PyErr_Format(PyExc_TypeError,
2301 "operand for anybitset_iterate must be immbitset or mutset");
2302 return -1;
2303 }
2304 }
2305
2306
2307 static PyObject *
mutbitset_append_or_remove(NyMutBitSetObject * v,PyObject * w,int ap,char * errmsg)2308 mutbitset_append_or_remove(NyMutBitSetObject *v, PyObject *w, int ap, char *errmsg)
2309 {
2310 NyBitField f, *fp;
2311 NyBit bitno = bitno_from_object(w);
2312 if (bitno == -1 && PyErr_Occurred())
2313 return 0;
2314 bitno_to_field(bitno, &f);
2315 if (v->cpl)
2316 ap = !ap;
2317 if (ap) {
2318 fp = mutbitset_findpos_ins(v, f.pos);
2319 if (!fp)
2320 return 0;
2321 if (fp->bits & f.bits) {
2322 PyErr_Format(PyExc_ValueError,
2323 errmsg, bitno);
2324 return 0;
2325 }
2326 fp->bits |= f.bits;
2327 } else {
2328 fp = mutbitset_findpos_mut(v, f.pos);
2329 if (!(fp && (fp->bits & f.bits))) {
2330 PyErr_Format(PyExc_ValueError,
2331 errmsg, bitno);
2332 return 0;
2333 }
2334 fp->bits &= ~f.bits;
2335 }
2336 Py_INCREF(Py_None);
2337 return Py_None;
2338 }
2339
2340
2341 static PyObject *
mutbitset_add_or_discard(NyMutBitSetObject * v,PyObject * w,int what)2342 mutbitset_add_or_discard(NyMutBitSetObject *v, PyObject *w, int what)
2343 {
2344 NyBit bitno = bitno_from_object(w);
2345 int r;
2346 if (bitno == -1 && PyErr_Occurred())
2347 return 0;
2348 r = mutbitset_set_or_clr(v, bitno, what);
2349 if (r == -1)
2350 return 0;
2351 Py_INCREF(Py_None);
2352 return Py_None;
2353 }
2354
2355 static PyObject *
mutbitset_add(NyMutBitSetObject * v,PyObject * w)2356 mutbitset_add(NyMutBitSetObject *v, PyObject *w)
2357 {
2358 return mutbitset_add_or_discard(v, w, 1);
2359 }
2360
2361 static PyObject *
mutbitset_append(NyMutBitSetObject * v,PyObject * w)2362 mutbitset_append(NyMutBitSetObject *v, PyObject *w)
2363 {
2364 return mutbitset_append_or_remove(v, w, 1,
2365 "mutset.append(%ld): bit is already in the set.");
2366 }
2367
2368 static PyObject *
mutbitset_discard(NyMutBitSetObject * v,PyObject * w)2369 mutbitset_discard(NyMutBitSetObject *v, PyObject *w)
2370 {
2371 return mutbitset_add_or_discard(v, w, 0);
2372 }
2373
2374 static PyObject *
mutbitset_remove(NyMutBitSetObject * v,PyObject * w)2375 mutbitset_remove(NyMutBitSetObject *v, PyObject *w)
2376 {
2377 return mutbitset_append_or_remove(v, w, 0,
2378 "mutset.remove(%ld): bit is not in the set.");
2379 }
2380
2381 static PyObject *
_mutbitset_clear(NyMutBitSetObject * self,PyObject * args)2382 _mutbitset_clear(NyMutBitSetObject *self, PyObject *args)
2383 {
2384 if (NyMutBitSet_clear(self) == -1)
2385 return 0;
2386 Py_INCREF(Py_None);
2387 return Py_None;
2388
2389 }
2390
2391 NyBit
NyMutBitSet_pop(NyMutBitSetObject * v,NyBit i)2392 NyMutBitSet_pop(NyMutBitSetObject *v, NyBit i)
2393 {
2394 NyBit j;
2395 NySetField *s, *end_s;
2396 NyBitField *f, *end_f;
2397 NyBit ret = 0;
2398 s=0;end_s=0; /* avoid warnings */
2399 if (v->cpl) {
2400 PyErr_SetString(PyExc_ValueError,
2401 "pop(): The mutset is complemented, and doesn't support pop.\n");
2402 return -1;
2403 }
2404 if (i == - 1) {
2405 for (end_s = mutbitset_getrange_mut(v, &s); --s >= end_s;)
2406 for (end_f = sf_getrange_mut(s, &f); --f >= end_f;) {
2407 if (f->bits) {
2408 j = bits_last(f->bits);
2409 ret = f->pos * NyBits_N + j;
2410 f->bits &= ~(ONE_LONG<<j);
2411 if (f->bits)
2412 mutbitset_set_hi(v, s, f+1);
2413 else
2414 mutbitset_set_hi(v, s, f);
2415 return ret;
2416 }
2417 }
2418 } else if (i == 0) {
2419 for (s = mutbitset_getrange_mut(v, &end_s); s < end_s; s++)
2420 for (f = sf_getrange_mut(s, &end_f); f < end_f; f++) {
2421 if (f->bits) {
2422 j = bits_first(f->bits);
2423 ret = f->pos * NyBits_N + j;
2424 f->bits &= ~(ONE_LONG<<j);
2425 if (f->bits)
2426 mutbitset_set_lo(v, s, f);
2427 else
2428 mutbitset_set_lo(v, s, f+1);
2429 return ret;
2430 }
2431 }
2432 } else {
2433 PyErr_SetString(PyExc_IndexError, "pop(): index must be 0 or -1");
2434 return -1;
2435 }
2436 PyErr_SetString(PyExc_ValueError, "pop(): empty set");
2437 return -1;
2438 }
2439
2440 static PyObject *
mutbitset_pop(NyMutBitSetObject * v,PyObject * args)2441 mutbitset_pop(NyMutBitSetObject *v, PyObject *args)
2442 {
2443 NyBit i = -1;
2444 NyBit bit;
2445 if (!PyArg_ParseTuple(args, "|n:pop", &i))
2446 return NULL;
2447 bit = NyMutBitSet_pop(v, i);
2448 if (bit == -1 && PyErr_Occurred())
2449 return 0;
2450 return PyLong_FromSsize_t(bit); /// xxx from ...
2451 }
2452
2453 static PyObject *
mutbitset_slice(NyMutBitSetObject * a,NyBit ilow,NyBit ihigh)2454 mutbitset_slice(NyMutBitSetObject *a, NyBit ilow, NyBit ihigh)
2455 {
2456
2457 NySetField *ss, *se;
2458 if (ilow == 0 && ihigh == PY_SSIZE_T_MAX) {
2459 return NyMutBitSet_AsImmBitSet(a);
2460 }
2461 if (a->cpl) {
2462 PyErr_SetString(PyExc_IndexError,
2463 "mutbitset_slice(): The mutset is complemented, and doesn't support other slice than [:].\n");
2464 return NULL;
2465 }
2466 ss = mutbitset_getrange(a, &se);
2467 return (PyObject *)sf_slice(ss, se, ilow, ihigh);
2468 }
2469
2470
2471 /* stripped down & specialized version of PySlice_GetIndices
2472 Bitsets don't currently support other step than 1
2473 and don't support a constant-time length, so we need to do without that.
2474 Notes per 5/6 -03 comment on why sq_slice didn't work.
2475 */
2476
2477 static int
NySlice_GetIndices(PySliceObject * r,NyBit * start,NyBit * stop)2478 NySlice_GetIndices(PySliceObject *r, NyBit *start, NyBit *stop)
2479 {
2480 NyBit sstep, *step = &sstep;
2481 if (r->step == Py_None) {
2482 *step = 1;
2483 } else {
2484 if (!PyLong_Check(r->step)) return -1;
2485 *step = PyLong_AsSsize_t(r->step);
2486 if (*step != 1) {
2487 PyErr_SetString(PyExc_IndexError, "bitset slicing step must be 1");
2488 return -1;
2489 }
2490 }
2491 if (r->start == Py_None) {
2492 *start = 0;
2493 } else {
2494 if (!PyLong_Check(r->start)) return -1;
2495 *start = PyLong_AsSsize_t(r->start);
2496 }
2497 if (r->stop == Py_None) {
2498 *stop = PY_SSIZE_T_MAX;
2499 } else {
2500 if (!PyLong_Check(r->stop)) return -1;
2501 *stop = PyLong_AsSsize_t(r->stop);
2502 }
2503 return 0;
2504 }
2505
2506
2507
2508 static PyObject *
mutbitset_subscript(NyMutBitSetObject * v,PyObject * w)2509 mutbitset_subscript(NyMutBitSetObject *v, PyObject *w)
2510 {
2511 NyBit i;
2512 NySetField *s, *end_s;
2513 NyBitField *f, *end_f;
2514 if (PySlice_Check(w)) {
2515 NyBit start, stop;
2516 if (NySlice_GetIndices((PySliceObject *)w, &start, &stop) == -1)
2517 return NULL;
2518 return mutbitset_slice(v, start, stop);
2519 }
2520 i = PyLong_AsSsize_t(w);
2521 if (i == -1 && PyErr_Occurred())
2522 return 0;
2523 if (v->cpl) {
2524 PyErr_SetString(PyExc_IndexError,
2525 "mutbitset_subscript(): The mutset is complemented, and doesn't support indexing.\n");
2526 return NULL;
2527 }
2528 if (i == - 1) {
2529 for (end_s = mutbitset_getrange(v, &s); --s >= end_s;)
2530 for (end_f = sf_getrange(s, &f); --f >= end_f;)
2531 if (f->bits)
2532 return PyLong_FromSsize_t(field_last(f));
2533 } else if (i == 0) {
2534 for (s = mutbitset_getrange(v, &end_s); s < end_s; s++)
2535 for (f = sf_getrange(s, &end_f); f < end_f; f++)
2536 if (f->bits)
2537 return PyLong_FromSsize_t(field_first(f));
2538 } else {
2539 PyErr_SetString(PyExc_IndexError, "mutbitset_subscript(): index must be 0 or -1");
2540 return NULL;
2541 }
2542 PyErr_SetString(PyExc_IndexError, "mutbitset_subscript(): empty set");
2543 return NULL;
2544 }
2545
2546
2547
2548 NyCplBitSetObject *
NyCplBitSet_SubtypeNew(PyTypeObject * type,NyImmBitSetObject * v)2549 NyCplBitSet_SubtypeNew(PyTypeObject *type, NyImmBitSetObject *v)
2550 {
2551 if (type == &NyCplBitSet_Type && v == NyImmBitSet_Empty) {
2552 Py_INCREF(NyImmBitSet_Omega);
2553 return NyImmBitSet_Omega;
2554 } else {
2555 NyCplBitSetObject *w = (NyCplBitSetObject *) type->tp_alloc(type, 1);
2556 if (w) {
2557 w->ob_val = v;
2558 Py_INCREF(v);
2559 n_cplbitset++;
2560 }
2561 return w;
2562 }
2563 }
2564
2565 NyCplBitSetObject *
NyCplBitSet_New(NyImmBitSetObject * v)2566 NyCplBitSet_New(NyImmBitSetObject *v)
2567 {
2568 return NyCplBitSet_SubtypeNew(&NyCplBitSet_Type, v);
2569 }
2570
2571 NyCplBitSetObject *
NyCplBitSet_New_Del(NyImmBitSetObject * v)2572 NyCplBitSet_New_Del(NyImmBitSetObject *v)
2573 {
2574 if (v) {
2575 NyCplBitSetObject *w = NyCplBitSet_New(v);
2576 Py_DECREF(v);
2577 return w;
2578 }
2579 return 0;
2580 }
2581
2582 static NyBitField *
immbitset_findpos(NyImmBitSetObject * v,NyBit pos)2583 immbitset_findpos(NyImmBitSetObject *v, NyBit pos)
2584 {
2585 NyBitField *f = v->ob_field;
2586 NyBitField *hi = & v->ob_field[Py_SIZE(v)];
2587 f = bitfield_binsearch(f, hi, pos);
2588 if (!(f < hi && f->pos == pos))
2589 return 0;
2590 return f;
2591 }
2592
2593
2594 static NyImmBitSetObject *
immbitset_op(NyImmBitSetObject * v,int op,NyImmBitSetObject * w)2595 immbitset_op(NyImmBitSetObject *v, int op, NyImmBitSetObject *w)
2596 {
2597 NyBit z, pos;
2598 NyBits bits, a, b;
2599 NyImmBitSetObject *dst = 0;
2600 NyBitField *zf, *vf, *wf, *ve, *we;
2601 ve = &v->ob_field[Py_SIZE(v)];
2602 we = &w->ob_field[Py_SIZE(w)];
2603 for (z = 0, zf = 0; ;) {
2604 for (vf = &v->ob_field[0], wf = &w->ob_field[0];;) {
2605 if (vf < ve) {
2606 if (wf < we) {
2607 if (vf->pos <= wf->pos) {
2608 pos = vf->pos;
2609 a = vf->bits;
2610 if (vf->pos == wf->pos) {
2611 b = wf->bits;
2612 wf++;
2613 } else {
2614 b = NyBits_EMPTY;
2615 }
2616 vf++;
2617 } else { /* (vf->pos > wf->pos) { */
2618 pos = wf->pos;
2619 a = NyBits_EMPTY;
2620 b = wf->bits;
2621 wf++;
2622 }
2623 } else {
2624 pos = vf->pos;
2625 a = vf->bits;
2626 vf++;
2627 b = NyBits_EMPTY;
2628 }
2629 } else if (wf < we) {
2630 pos = wf->pos;
2631 a = NyBits_EMPTY;
2632 b = wf->bits;
2633 wf++;
2634 } else
2635 break;
2636 switch(op) {
2637 case NyBits_AND: bits = a & b; break;
2638 case NyBits_OR : bits = a | b; break;
2639 case NyBits_XOR: bits = a ^ b; break;
2640 case NyBits_SUB: bits = a & ~b; break;
2641 default : bits = 0; /* slicence undefined-warning */
2642 assert(0);
2643 }
2644 if (bits) {
2645 if (zf) {
2646 zf->pos = pos;
2647 zf->bits = bits;
2648 zf++;
2649 } else {
2650 z++;
2651 }
2652 }
2653 }
2654 if (zf) {
2655 return dst;
2656 } else {
2657 dst = NyImmBitSet_New(z);
2658 if (!dst)
2659 return dst;
2660 zf = & dst->ob_field[0];
2661 }
2662 }
2663 }
2664
2665 static PyObject *
cpl_immbitset_op(NyImmBitSetObject * v,int op,NyImmBitSetObject * w)2666 cpl_immbitset_op(NyImmBitSetObject *v, int op, NyImmBitSetObject *w)
2667 {
2668 return (PyObject *)NyCplBitSet_New_Del(immbitset_op(v, op, w));
2669 }
2670
2671 static PyObject *
immbitset_and(NyImmBitSetObject * v,PyObject * w,int wt)2672 immbitset_and(NyImmBitSetObject *v, PyObject *w, int wt)
2673 {
2674 switch (wt) {
2675 case BITSET:
2676 return (PyObject *)immbitset_op(v, NyBits_AND, (NyImmBitSetObject *)w);
2677 case CPLSET:
2678 return (PyObject *)immbitset_op(v, NyBits_SUB, cplbitset_cpl((NyCplBitSetObject *)w));
2679 default:
2680 Py_INCREF(Py_NotImplemented);
2681 return Py_NotImplemented;
2682 }
2683 }
2684
2685
2686 int
NyImmBitSet_hasbit(NyImmBitSetObject * v,NyBit bit)2687 NyImmBitSet_hasbit(NyImmBitSetObject *v, NyBit bit)
2688 {
2689 NyBitField f, *fp;
2690 bitno_to_field(bit, &f);
2691 fp = immbitset_findpos(v, f.pos);
2692 if (!fp)
2693 return 0;
2694 return (fp->bits & f.bits) != 0;
2695
2696 }
2697
2698 static int
immbitset_contains(NyImmBitSetObject * v,PyObject * w)2699 immbitset_contains(NyImmBitSetObject *v, PyObject *w)
2700 {
2701 NyBit bit = bitno_from_object(w);
2702 if (bit == -1 && PyErr_Occurred())
2703 return -1;
2704 return NyImmBitSet_hasbit(v, bit);
2705 }
2706
2707 static void
immbitset_dealloc(PyObject * v)2708 immbitset_dealloc(PyObject *v)
2709 {
2710 Py_TYPE(v)->tp_free((PyObject *)v);
2711 n_immbitset--;
2712 }
2713
2714 static Py_hash_t
immbitset_hash(NyImmBitSetObject * v)2715 immbitset_hash(NyImmBitSetObject *v)
2716 {
2717 NyBitField *f = &v->ob_field[0];
2718 NyBitField *f_stop = &v->ob_field[Py_SIZE(v)];
2719 Py_hash_t h = 0x1d567f9f;
2720 while (f < f_stop) {
2721 h ^= f->bits ^ f->pos;
2722 f++;
2723 }
2724 h += (h >> 16);
2725 h += (h >> 8);
2726 h += (h >> 4);
2727 h += (h << 7);
2728 if (h == -1)
2729 h = -2;
2730 return h;
2731
2732 }
2733
2734 static PyObject *
immbitset_complement(NyImmBitSetObject * v)2735 immbitset_complement(NyImmBitSetObject *v)
2736 {
2737 return (PyObject *)NyCplBitSet_New(v);
2738 }
2739
2740 static Py_ssize_t
immbitset_length(PyObject * _v)2741 immbitset_length(PyObject *_v)
2742 {
2743 NyImmBitSetObject *v=(void*)_v;
2744
2745 Py_ssize_t n = v->ob_length;
2746 if (n == -1) {
2747 Py_ssize_t i;
2748 for (i = 0, n = 0; i < Py_SIZE(v); i++) {
2749 n += bits_length(v->ob_field[i].bits);
2750 if (n < 0) {
2751 PyErr_SetString(PyExc_OverflowError, "len() of this immbitset is too large to tell");
2752 return -1;
2753 }
2754 }
2755 v->ob_length = n;
2756 }
2757 return n;
2758 }
2759
2760 Py_ssize_t
NyAnyBitSet_length(PyObject * v)2761 NyAnyBitSet_length(PyObject *v)
2762 {
2763 if (NyImmBitSet_Check(v))
2764 return immbitset_length(v);
2765 else if (NyMutBitSet_Check(v))
2766 return mutbitset_length(v);
2767 else {
2768 PyErr_SetString(PyExc_ValueError, "NyAnyBitSet_length: bitset required.");
2769 return -1;
2770 }
2771 }
2772
2773 int
pos_add_check(NyBit a,NyBit b)2774 pos_add_check(NyBit a, NyBit b)
2775 {
2776 NyBit tst;
2777 tst = a + b;
2778 if (NyPos_MIN <= tst && tst <= NyPos_MAX)
2779 return 0;
2780 else
2781 return -1;
2782 }
2783
2784 static NyImmBitSetObject *
immbitset_lshift(NyImmBitSetObject * v,NyBit w)2785 immbitset_lshift(NyImmBitSetObject *v, NyBit w)
2786 {
2787 NyBit posshift;
2788 NyBit remshift;
2789 NyBit n;
2790 NyBit lopos, hipos;
2791 NyBit i;
2792 if (v == NyImmBitSet_Empty) {
2793 Py_INCREF(NyImmBitSet_Empty);
2794 return NyImmBitSet_Empty;
2795 }
2796 n = Py_SIZE(v);
2797 lopos = v->ob_field[0].pos;
2798 hipos = v->ob_field[n-1].pos;
2799 remshift = bitno_modiv(w, &posshift);
2800 if (remshift) {
2801 if (!(v->ob_field[0].bits << remshift))
2802 lopos++;
2803 if ((v->ob_field[Py_SIZE(v)-1].bits >> (NyBits_N - remshift)))
2804 hipos++;
2805 }
2806 if (pos_add_check(lopos, posshift) ||
2807 pos_add_check(hipos, posshift)) {
2808 PyErr_SetString(PyExc_OverflowError, "immbitset_lshift(): too large shift count");
2809 return 0;
2810 }
2811 if (!remshift) {
2812 NyImmBitSetObject *ret = NyImmBitSet_New(n);
2813 if (!ret)
2814 return 0;
2815 for (i = 0; i < n; i++) {
2816 ret->ob_field[i].bits = v->ob_field[i].bits;
2817 ret->ob_field[i].pos = v->ob_field[i].pos + posshift;
2818 }
2819 return ret;
2820 } else {
2821 NyMutBitSetObject *ms = NyMutBitSet_New();
2822 NyBitField fs[2], *f;
2823 if (!ms)
2824 return 0;
2825 f = v->ob_field;
2826 for (i = 0; i < n; i++) {
2827 fs[0].pos = f->pos + posshift;
2828 fs[1].pos = f->pos + posshift + 1;
2829 fs[0].bits = f->bits << remshift;
2830 fs[1].bits = f->bits >> (NyBits_N - remshift);
2831 if (mutbitset_ior_fields(ms, &fs[0], 2) == -1) {
2832 Py_DECREF(ms);
2833 return 0;
2834 }
2835 f++;
2836 }
2837 return (NyImmBitSetObject *)mutbitset_as_immbitset_and_del(ms);
2838 }
2839 }
2840
2841 NyImmBitSetObject *
sf_slice(NySetField * ss,NySetField * se,NyBit ilow,NyBit ihigh)2842 sf_slice(NySetField *ss, NySetField *se, NyBit ilow, NyBit ihigh)
2843 {
2844 NyBit nbits = 0;
2845 NyBit nbitswanted;
2846 NyBit nfields = 0;
2847 NyBit i;
2848 NySetField *s;
2849 NyBitField *f, *fe, *fs, *g;
2850 NyImmBitSetObject *bs;
2851 if (ilow == 0 && ihigh > 0) {
2852 nbitswanted = ihigh;
2853 for (s = ss; s < se; s++) {
2854 for (f = sf_getrange(s, &fe); f < fe; f++) {
2855 if (nbits >= nbitswanted)
2856 break;
2857 if (f->bits) {
2858 nbits += bits_length(f->bits);
2859 nfields += 1;
2860 }
2861 }
2862 if (nbits >= nbitswanted)
2863 break;
2864 }
2865 bs = NyImmBitSet_New(nfields);
2866 g = bs->ob_field;
2867 i = 0;
2868 for (s = ss; s < se; s++) {
2869 for (f = sf_getrange(s, &fe); f < fe; f++) {
2870 if (i >= nfields)
2871 break;
2872 if (f->bits) {
2873 g->bits = f->bits;
2874 g->pos = f->pos;
2875 g++;
2876 i++;
2877 }
2878 }
2879 if (i >= nfields)
2880 break;
2881 }
2882 if (nbits > nbitswanted) {
2883 assert(g > bs->ob_field);
2884 g--;
2885 while (nbits > nbitswanted) {
2886 g->bits &= ~(ONE_LONG<<bits_last(g->bits));
2887 nbits--;
2888 }
2889 }
2890 return bs;
2891 } else if (ilow < 0 && ihigh == PY_SSIZE_T_MAX) {
2892 nbitswanted = - ilow;
2893 for (s = se; --s >= ss;) {
2894 for (fs = sf_getrange(s, &f); --f >= fs; ) {
2895 if (nbits >= nbitswanted)
2896 break;
2897 if (f->bits) {
2898 nbits += bits_length(f->bits);
2899 nfields += 1;
2900 }
2901 }
2902 if (nbits >= nbitswanted)
2903 break;
2904 }
2905 bs = NyImmBitSet_New(nfields);
2906 g = bs->ob_field + nfields - 1;
2907 i = 0;
2908 for (s = se; --s >= ss;) {
2909 for (fs = sf_getrange(s, &f); --f >= fs; ) {
2910 if (i >= nfields)
2911 break;
2912 if (f->bits) {
2913 g->bits = f->bits;
2914 g->pos = f->pos;
2915 g--;
2916 i++;
2917 }
2918 }
2919 if (i >= nfields)
2920 break;
2921 }
2922 if (nbits > nbitswanted) {
2923 g++;
2924 assert(g == bs->ob_field);
2925 while (nbits > nbitswanted) {
2926 g->bits &= ~(ONE_LONG<<bits_first(g->bits));
2927 nbits--;
2928 }
2929 }
2930 return bs;
2931 } else {
2932 PyErr_SetString(PyExc_IndexError, "this slice index form is not implemented");
2933 return NULL;
2934 }
2935
2936 }
2937
2938 static NyImmBitSetObject *
immbitset_slice(NyImmBitSetObject * a,NyBit ilow,NyBit ihigh)2939 immbitset_slice(NyImmBitSetObject *a, NyBit ilow, NyBit ihigh)
2940 {
2941
2942 NySetField s;
2943 if (ilow == 0 && ihigh == PY_SSIZE_T_MAX) {
2944 Py_INCREF(a);
2945 return a;
2946 }
2947 s.lo = a->ob_field;
2948 s.hi = a->ob_field + Py_SIZE(a);
2949 return sf_slice(&s, (&s)+1, ilow, ihigh);
2950 }
2951
2952
2953 static PyObject *
immbitset_subscript(NyImmBitSetObject * v,PyObject * w)2954 immbitset_subscript(NyImmBitSetObject *v, PyObject *w)
2955 {
2956 NyBit i;
2957 if (PySlice_Check(w)) {
2958 NyBit start, stop;
2959 if (NySlice_GetIndices((PySliceObject *)w, &start, &stop) == -1)
2960 return NULL;
2961 return (PyObject *)immbitset_slice(v, start, stop);
2962 }
2963 i = PyLong_AsSsize_t(w);
2964 if (i == -1 && PyErr_Occurred())
2965 return 0;
2966 if (v == NyImmBitSet_Empty) {
2967 PyErr_SetString(PyExc_IndexError, "empty immbitset - index out of range");
2968 return 0;
2969 }
2970 if (i == 0) {
2971 return PyLong_FromSsize_t(field_first(v->ob_field));
2972 } else if (i == -1) {
2973 return PyLong_FromSsize_t(field_last(&v->ob_field[Py_SIZE(v)-1]));
2974 } else {
2975 PyErr_SetString(PyExc_IndexError, "immbitset_subscript(): index must be 0 or -1");
2976 return NULL;
2977 }
2978 }
2979
2980 PyObject *
immbitset_int(NyImmBitSetObject * v)2981 immbitset_int(NyImmBitSetObject *v)
2982 {
2983 NyBit num_poses, pos;
2984 NyBits bits, *buf;
2985 NyBitField *f = &v->ob_field[0];
2986 NyBitField *f_stop = &v->ob_field[Py_SIZE(v)];
2987 PyObject *r;
2988 if (f >= f_stop)
2989 return PyLong_FromSsize_t(0L);
2990
2991 if (f->pos < 0) {
2992 PyErr_SetString(PyExc_OverflowError,
2993 "immbitset with negative bits can not be converted to int");
2994 return 0;
2995 }
2996 num_poses = (f_stop-1)->pos + 1;
2997 if (num_poses > NyPos_MAX) {
2998 PyErr_SetString(PyExc_OverflowError, "immbitset too large to convert to int");
2999 return 0;
3000 }
3001 buf = PyMem_New(NyBits, num_poses);
3002 if (!buf) {
3003 PyErr_NoMemory();
3004 return 0;
3005 }
3006 for (pos = 0; pos < num_poses; pos++) {
3007 if (pos == f->pos) {
3008 bits = f->bits;
3009 #if NyBits_IS_BIG_ENDIAN
3010 bits = NyBits_BSWAP(bits);
3011 #endif
3012 f++;
3013 } else {
3014 bits = NyBits_EMPTY;
3015 }
3016 buf[pos] = bits;
3017 }
3018 r = _PyLong_FromByteArray((unsigned char *)buf, /* bytes */
3019 num_poses * sizeof(NyBits), /* n = number of bytes*/
3020 1, /* Always little endian here */
3021 0); /* not is_signed, never here */
3022 PyMem_Del(buf);
3023 return r;
3024 }
3025
3026 static PyObject *
immbitset_new(PyTypeObject * type,PyObject * args,PyObject * kwds)3027 immbitset_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
3028 {
3029 PyObject *arg = NULL;
3030 static char *kwlist[] = {"arg", 0};
3031 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O:immbitset", kwlist, &arg))
3032 return NULL;
3033 return (PyObject *)NyImmBitSet_SubtypeNewArg(type, arg);
3034 }
3035
3036
3037 static char immbitset_doc[] =
3038 "immbitset() -> empty immutable bitset\n"
3039 "immbitset(bitset) -> immutable bitset with bitset's bits\n"
3040 "immbitset(iterable) -> immutable bitset with iterable's bits (int items)\n"
3041 "immbitset(integer) -> immutable bitset with integer's bits (binary 2-complement)\n"
3042 "\n"
3043 "Return an immutable bitset. It will be complemented if the argument\n"
3044 "is a complemented bitset or a negative integer. If the argument is an\n"
3045 "immutable bitset, the result is the same object.\n"
3046 ;
3047
3048
3049 static PyObject *
immbitset(PyTypeObject * unused,PyObject * args,PyObject * kwds)3050 immbitset(PyTypeObject *unused, PyObject *args, PyObject *kwds)
3051 {
3052 PyObject *arg = NULL;
3053 PyObject *ret;
3054 int clas;
3055 static char *kwlist[] = {"arg", 0};
3056 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O:immbitset", kwlist, &arg))
3057 return NULL;
3058 if (arg == NULL)
3059 return (PyObject *)NyImmBitSet_New(0);
3060 else {
3061 clas = NOSET;
3062 ret = anybitset_convert(arg, &clas);
3063 if (clas == NOSET) {
3064 if (ret) {
3065 PyErr_Format(PyExc_TypeError,
3066 "operand for immbitset must be a bitset, iterable or integer");
3067 Py_DECREF(ret);
3068 }
3069 return NULL;
3070 }
3071 return ret;
3072 }
3073 }
3074
3075 static int
immbitset_nonzero(NyImmBitSetObject * v)3076 immbitset_nonzero(NyImmBitSetObject *v)
3077 {
3078 return v != NyImmBitSet_Empty;
3079 }
3080
3081 static int
sf_tst_sf(NySetField * as,NySetField * ase,int op,NySetField * bs,NySetField * bse)3082 sf_tst_sf(NySetField *as, NySetField *ase, int op, NySetField *bs, NySetField *bse)
3083 {
3084 NyBitField *af, *afe, *bf, *bfe;
3085 NyBits a, b, c;
3086
3087 if (op == NyBits_TRUE)
3088 return 1;
3089
3090 if (as < ase) {
3091 af = sf_getrange(as, &afe);
3092 as++;
3093 } else
3094 af = afe = 0;
3095
3096 if (bs < bse) {
3097 bf = sf_getrange(bs, &bfe);
3098 bs++;
3099 } else
3100 bf = bfe = 0;
3101
3102 for (;;) {
3103 if (af < afe) {
3104 if (bf < bfe) {
3105 if (af->pos < bf->pos) {
3106 a = af++->bits;
3107 b = 0;
3108 } else {
3109 if (af->pos == bf->pos) {
3110 a = af++->bits;
3111 } else {
3112 a = 0;
3113 }
3114 b = bf++->bits;
3115 if (bf == bfe) {
3116 if (bs < bse) {
3117 bf = sf_getrange(bs, &bfe);
3118 bs++;
3119 }
3120 }
3121 }
3122 } else {
3123 a = af++->bits;
3124 b = 0;
3125 }
3126 if (af == afe) {
3127 if (as < ase) {
3128 af = sf_getrange(as, &afe);
3129 as++;
3130 }
3131 }
3132 } else if (bf < bfe) {
3133 a = 0;
3134 b = bf++->bits;
3135 if (bf == bfe) {
3136 if (bs < bse) {
3137 bf = sf_getrange(bs, &bfe);
3138 bs++;
3139 }
3140 }
3141 } else
3142 return 0;
3143
3144 switch (op) {
3145 case NyBits_AND : c = a & b; break;
3146 case NyBits_OR : c = a | b; break;
3147 case NyBits_XOR : c = a ^ b; break;
3148 case NyBits_SUB : c = a & ~b; break;
3149 case NyBits_SUBR: c = ~a & b; break;
3150 default : c = 0; /* silence undefined-warning */
3151 assert(0);
3152 }
3153 if (c)
3154 return 1;
3155 }
3156 }
3157
3158
3159 void
claset_load(PyObject * v,int vt,int * cpl,NySetField * vst,NySetField ** vs,NySetField ** vse)3160 claset_load(PyObject *v, int vt, int *cpl, NySetField *vst, NySetField **vs, NySetField **vse)
3161 {
3162 switch (vt) {
3163 case BITSET: {
3164 NyImmBitSetObject *bs = (NyImmBitSetObject *)v;
3165 *cpl = 0;
3166 vst->lo = bs->ob_field;
3167 vst->hi = bs->ob_field+Py_SIZE(bs);
3168 *vs = vst;
3169 *vse = vst+1;
3170 break;
3171 }
3172 case CPLSET: {
3173 NyImmBitSetObject *bs = cplbitset_cpl((NyCplBitSetObject *)v);
3174 *cpl = 1;
3175 vst->lo = bs->ob_field;
3176 vst->hi = bs->ob_field+Py_SIZE(bs);
3177 *vs = vst;
3178 *vse = vst+1;
3179 break;
3180 }
3181 case MUTSET: {
3182 NyMutBitSetObject *ms = (NyMutBitSetObject *)v;
3183 *cpl = ms->cpl;
3184 *vs = union_getrange(ms->root, vse);
3185 break;
3186 }
3187 default:
3188 assert(0);
3189 }
3190 }
3191
3192 static PyObject *
claset_richcompare(PyObject * v,int vt,PyObject * w,int op)3193 claset_richcompare(PyObject *v, int vt, PyObject *w, int op)
3194 {
3195 NySetField *vs, *vse, *ws, *wse, vst, wst;
3196 int vcpl, wcpl;
3197 int cpl = 0;
3198 int swap = 0;
3199 int decw = 0;
3200 int tst;
3201 int res;
3202 PyObject *ret = 0;
3203 int wt;
3204 anybitset_classify(w, &wt);
3205 if (wt == NOSET) {
3206 PyErr_SetString(PyExc_TypeError, "bitset_richcompare: some bitset expected");
3207 return 0;
3208 /* We might consider returning NotImplemented but ... we might want
3209 to implement it here and then we would get a compatibility problem!
3210 See also Notes May 19 2005.
3211 Py_INCREF(Py_NotImplemented);
3212 return Py_NotImplemented;
3213 */
3214
3215
3216 }
3217 switch(op) {
3218 case Py_EQ:
3219 case Py_LE:
3220 case Py_LT: break;
3221 case Py_NE: cpl = 1; op = Py_EQ; break;
3222 case Py_GE: swap = 1; op = Py_LE; break;
3223 case Py_GT: swap = 1; op = Py_LT; break;
3224 default : assert(0);
3225 }
3226 if (swap) {
3227 PyObject *nw = v;
3228 int nwt = vt;
3229 v = w;
3230 vt = wt;
3231 w = nw;
3232 wt = nwt;
3233 }
3234 claset_load(v, vt, &vcpl, &vst, &vs, &vse);
3235 claset_load(w, wt, &wcpl, &wst, &ws, &wse);
3236 switch (op) {
3237 case Py_EQ:
3238 if (vcpl == wcpl) {
3239 res = !sf_tst_sf(vs, vse, NyBits_XOR, ws, wse);
3240 } else
3241 res = 0;
3242 break;
3243 case Py_LE:
3244 case Py_LT:
3245 switch (vcpl * 2 | wcpl) {
3246 case 0 : tst = NyBits_SUB; break;
3247 case 1 : tst = NyBits_AND; break;
3248 case 2 : tst = NyBits_TRUE; break;
3249 case 3 : tst = NyBits_SUBR; break;
3250 default: tst = NyBits_TRUE; /* Silence gcc undefined-warning */
3251 assert(0);
3252 }
3253 res = !sf_tst_sf(vs, vse, tst, ws, wse);
3254 if (res && op == Py_LT && vcpl == wcpl) {
3255 res = sf_tst_sf(vs, vse, NyBits_XOR, ws, wse);
3256 }
3257 break;
3258 default:
3259 res = 0; /* silence undefined-warning */
3260 assert(0);
3261 }
3262 if (cpl)
3263 res = !res;
3264 ret = res ? Py_True:Py_False;
3265 if (decw) {
3266 Py_DECREF(w);
3267 }
3268 Py_INCREF(ret);
3269 return ret;
3270 }
3271
3272 static PyObject *
immbitset_richcompare(NyImmBitSetObject * v,PyObject * w,int op)3273 immbitset_richcompare(NyImmBitSetObject *v, PyObject *w, int op)
3274 {
3275 return claset_richcompare((PyObject *)v, BITSET, w, op);
3276 }
3277
3278
3279 static PyObject *
cplbitset_richcompare(NyCplBitSetObject * v,PyObject * w,int op)3280 cplbitset_richcompare(NyCplBitSetObject *v, PyObject *w, int op)
3281 {
3282 return claset_richcompare((PyObject *)v, CPLSET, w, op);
3283 }
3284
3285
3286 static PyObject *
mutbitset_richcompare(NyMutBitSetObject * v,PyObject * w,int op)3287 mutbitset_richcompare(NyMutBitSetObject *v, PyObject *w, int op)
3288 {
3289 return claset_richcompare((PyObject *)v, MUTSET, w, op);
3290 }
3291
3292
3293 static PyObject *
immbitset_or(NyImmBitSetObject * v,PyObject * w,int wt)3294 immbitset_or(NyImmBitSetObject *v, PyObject *w, int wt)
3295 {
3296 switch (wt) {
3297 case BITSET:
3298 return (PyObject *)immbitset_op(v, NyBits_OR, (NyImmBitSetObject *)w);
3299 case CPLSET:
3300 return cpl_immbitset_op(cplbitset_cpl((NyCplBitSetObject *)w), NyBits_SUB, v);
3301 default:
3302 Py_INCREF(Py_NotImplemented);
3303 return Py_NotImplemented;
3304 }
3305 }
3306
3307 static PyObject *
immbitset_repr(NyImmBitSetObject * a)3308 immbitset_repr(NyImmBitSetObject *a)
3309 {
3310 PyObject *s, *iter;
3311 NyBit len;
3312 len = Py_SIZE(a);
3313 if (len == 0) {
3314 return PyUnicode_FromString("ImmBitSet([])");
3315 }
3316 iter = PySequence_List((PyObject *)a);
3317 if (!iter) goto Fail;
3318 s = PyUnicode_FromFormat("ImmBitSet(%R)", iter);
3319 Py_XDECREF(iter);
3320 return s;
3321 Fail:
3322 Py_XDECREF(iter);
3323 return 0;
3324 }
3325
3326 static PyObject *
immbitset_sub(NyImmBitSetObject * v,PyObject * w,int wt)3327 immbitset_sub(NyImmBitSetObject *v, PyObject *w, int wt)
3328 {
3329 switch (wt) {
3330 case BITSET:
3331 return (PyObject *)immbitset_op(v, NyBits_SUB, (NyImmBitSetObject *)w);
3332 case CPLSET:
3333 return (PyObject *)immbitset_op(v, NyBits_AND, cplbitset_cpl((NyCplBitSetObject *)w));
3334 default:
3335 Py_INCREF(Py_NotImplemented);
3336 return Py_NotImplemented;
3337 }
3338 }
3339
3340
3341
3342 static PyObject *
immbitset_xor(NyImmBitSetObject * v,PyObject * w,int wt)3343 immbitset_xor(NyImmBitSetObject *v, PyObject *w, int wt)
3344 {
3345 switch (wt) {
3346 case BITSET:
3347 return (PyObject *)immbitset_op(v, NyBits_XOR, (NyImmBitSetObject *)w);
3348 case CPLSET:
3349 return cpl_immbitset_op(v, NyBits_XOR, cplbitset_cpl((NyCplBitSetObject *)w));
3350 default:
3351 Py_INCREF(Py_NotImplemented);
3352 return Py_NotImplemented;
3353 }
3354 }
3355
3356
3357 typedef struct {
3358 PyObject_HEAD
3359 NyImmBitSetObject *immbitset;
3360 NyBit fldpos;
3361 NyBit bitpos;
3362 } NyImmBitSetIterObject;
3363
3364
3365 PyObject *
immbitset_iter(NyImmBitSetObject * v)3366 immbitset_iter(NyImmBitSetObject *v)
3367 {
3368 NyImmBitSetIterObject *iter;
3369 iter = PyObject_New(NyImmBitSetIterObject, &NyImmBitSetIter_Type);
3370 if (iter) {
3371 iter->immbitset = v;
3372 Py_INCREF(v);
3373 iter->fldpos = 0;
3374 iter->bitpos = 0;
3375 }
3376 return (PyObject *)iter;
3377 }
3378
3379 static void
bsiter_dealloc(NyImmBitSetIterObject * v)3380 bsiter_dealloc(NyImmBitSetIterObject *v)
3381 {
3382 Py_DECREF(v->immbitset);
3383 PyObject_DEL(v);
3384 }
3385
3386 static PyObject *
bsiter_getiter(PyObject * it)3387 bsiter_getiter(PyObject *it)
3388 {
3389 Py_INCREF(it);
3390 return it;
3391 }
3392
3393 static PyObject *
bsiter_iternext(NyImmBitSetIterObject * bi)3394 bsiter_iternext(NyImmBitSetIterObject *bi)
3395 {
3396 NyImmBitSetObject *bs = bi->immbitset;
3397 NyBit fldpos = bi->fldpos;
3398 if (fldpos < Py_SIZE(bs)) {
3399 NyBit bitpos = bi->bitpos;
3400 NyBitField *f = &bs->ob_field[fldpos];
3401 NyBits bits = f->bits >> bitpos;
3402 NyBit rebit;
3403 while (!(bits & 1)) {
3404 bits >>= 1;
3405 bitpos += 1;
3406 }
3407 rebit = f->pos * NyBits_N + bitpos;
3408 bits >>= 1;
3409 bitpos += 1;
3410 if (!bits) {
3411 fldpos += 1;
3412 bi->fldpos = fldpos;
3413 bitpos = 0;
3414 }
3415 bi->bitpos = bitpos;
3416 return PyLong_FromSsize_t(rebit);
3417 } else {
3418 return NULL;
3419 }
3420 }
3421
3422 static int
cplbitset_hasbit(NyCplBitSetObject * v,NyBit bit)3423 cplbitset_hasbit(NyCplBitSetObject *v, NyBit bit)
3424 {
3425 return !NyImmBitSet_hasbit(v->ob_val, bit);
3426 }
3427
3428 static int
cplbitset_contains(NyCplBitSetObject * v,PyObject * w)3429 cplbitset_contains(NyCplBitSetObject *v, PyObject *w)
3430 {
3431 NyBit bit = bitno_from_object(w);
3432 if (bit == -1 && PyErr_Occurred())
3433 return -1;
3434 return cplbitset_hasbit(v, bit);
3435 }
3436
3437 static void
cplbitset_dealloc(NyCplBitSetObject * v)3438 cplbitset_dealloc(NyCplBitSetObject *v)
3439 {
3440 Py_DECREF(v->ob_val);
3441 Py_TYPE(v)->tp_free((PyObject *)v);
3442 n_cplbitset--;
3443 }
3444
3445
3446 PyObject *
cplbitset_new(PyTypeObject * type,PyObject * args,PyObject * kwds)3447 cplbitset_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
3448 {
3449 PyObject *arg = NULL;
3450 static char *kwlist[] = {"arg", 0};
3451 if (!PyArg_ParseTupleAndKeywords(args, kwds, "O!:CplBitSet.__new__", kwlist,
3452 &NyImmBitSet_Type, &arg))
3453 return NULL;
3454 return (PyObject *)NyCplBitSet_SubtypeNew(type, (NyImmBitSetObject *)arg);
3455 }
3456
3457 static Py_hash_t
cplbitset_hash(NyCplBitSetObject * v)3458 cplbitset_hash(NyCplBitSetObject *v)
3459 {
3460 return ~immbitset_hash(v->ob_val);
3461 }
3462
3463 static NyImmBitSetObject *
cplbitset_cpl(NyCplBitSetObject * v)3464 cplbitset_cpl(NyCplBitSetObject*v)
3465 {
3466 return v->ob_val;
3467 }
3468
3469 static PyObject *
cplbitset_complement(NyCplBitSetObject * v)3470 cplbitset_complement(NyCplBitSetObject *v)
3471 {
3472 Py_INCREF(v->ob_val);
3473 return (PyObject *)v->ob_val;
3474 }
3475
3476 static PyObject *
cplbitset_int(NyCplBitSetObject * v)3477 cplbitset_int(NyCplBitSetObject *v)
3478 {
3479 PyObject *w = immbitset_int(v->ob_val); // xxx
3480 PyObject *x;
3481 if (!w) return 0;
3482 x = PyNumber_Invert(w);
3483 Py_DECREF(w);
3484 return x;
3485
3486 }
3487
3488 static int
cplbitset_nonzero(NyImmBitSetObject * v)3489 cplbitset_nonzero(NyImmBitSetObject *v)
3490 {
3491 return 1;
3492 }
3493
3494 static PyObject *
cplbitset_repr(NyCplBitSetObject * a)3495 cplbitset_repr(NyCplBitSetObject *a)
3496 {
3497 return PyUnicode_FromFormat("(~%R)", (PyObject *)a->ob_val);
3498 }
3499
3500 static PyObject *
cplbitset_lshift(NyCplBitSetObject * v,NyBit w)3501 cplbitset_lshift(NyCplBitSetObject *v, NyBit w)
3502 {
3503 return (PyObject *)NyCplBitSet_New_Del(immbitset_lshift(cplbitset_cpl(v), w));
3504 }
3505
3506 static PyObject *
cplbitset_and(NyCplBitSetObject * v,PyObject * w,int wt)3507 cplbitset_and(NyCplBitSetObject *v, PyObject *w, int wt)
3508 {
3509 switch (wt) {
3510 case BITSET:
3511 return (PyObject *)
3512 immbitset_op((NyImmBitSetObject *)w,
3513 NyBits_SUB,
3514 cplbitset_cpl(v));
3515
3516 case CPLSET:
3517 return cpl_immbitset_op(cplbitset_cpl(v),
3518 NyBits_OR,
3519 cplbitset_cpl((NyCplBitSetObject *)w));
3520 default:
3521 Py_INCREF(Py_NotImplemented);
3522 return Py_NotImplemented;
3523 }
3524 }
3525
3526 static PyObject *
cplbitset_or(NyCplBitSetObject * v,PyObject * w,int wt)3527 cplbitset_or(NyCplBitSetObject *v, PyObject *w, int wt)
3528 {
3529 switch (wt) {
3530 case BITSET:
3531 return cpl_immbitset_op(cplbitset_cpl(v),
3532 NyBits_SUB,
3533 (NyImmBitSetObject *)w);
3534
3535 case CPLSET:
3536 return cpl_immbitset_op(cplbitset_cpl(v),
3537 NyBits_AND,
3538 cplbitset_cpl((NyCplBitSetObject *)w));
3539 default:
3540 Py_INCREF(Py_NotImplemented);
3541 return Py_NotImplemented;
3542 }
3543 }
3544
3545 static PyObject *
cplbitset_sub(NyCplBitSetObject * v,PyObject * w,int wt)3546 cplbitset_sub(NyCplBitSetObject *v, PyObject *w, int wt)
3547 {
3548 switch (wt) {
3549 case BITSET:
3550 return cpl_immbitset_op(cplbitset_cpl(v),
3551 NyBits_OR,
3552 (NyImmBitSetObject *)w);
3553
3554 case CPLSET:
3555 return (PyObject *)
3556 immbitset_op(cplbitset_cpl((NyCplBitSetObject *)w),
3557 NyBits_SUB,
3558 cplbitset_cpl(v));
3559 default:
3560 Py_INCREF(Py_NotImplemented);
3561 return Py_NotImplemented;
3562 }
3563 }
3564
3565 static PyObject *
cplbitset_xor(NyCplBitSetObject * v,PyObject * w,int wt)3566 cplbitset_xor(NyCplBitSetObject *v, PyObject *w, int wt)
3567 {
3568 switch (wt) {
3569 case BITSET:
3570 return cpl_immbitset_op(cplbitset_cpl(v),
3571 NyBits_XOR,
3572 (NyImmBitSetObject *)w);
3573 case CPLSET:
3574 return (PyObject *)
3575 immbitset_op(cplbitset_cpl(v),
3576 NyBits_XOR,
3577 cplbitset_cpl((NyCplBitSetObject *)w));
3578 default:
3579 Py_INCREF(Py_NotImplemented);
3580 return Py_NotImplemented;
3581 }
3582 }
3583
3584 void
anybitset_classify(PyObject * v,int * vt)3585 anybitset_classify(PyObject *v, int *vt)
3586 {
3587 if (NyImmBitSet_Check(v))
3588 *vt = BITSET;
3589 else if (NyCplBitSet_Check(v))
3590 *vt = CPLSET;
3591 else if (NyMutBitSet_Check(v))
3592 *vt = MUTSET;
3593 else
3594 *vt = NOSET;
3595 }
3596
3597 static PyObject *
anybitset_convert(PyObject * v,int * vt)3598 anybitset_convert(PyObject *v, int *vt)
3599 {
3600 anybitset_classify(v, vt);
3601 if (*vt == BITSET || *vt == CPLSET) {
3602 Py_INCREF(v);
3603 return v;
3604 } else if (*vt == MUTSET)
3605 v = NyMutBitSet_AsImmBitSet((NyMutBitSetObject *)v);
3606 else if (PyLong_Check(v))
3607 v = NyImmBitSet_FromPyLongObject(v);
3608 else if (NyIterable_Check(v))
3609 v = (PyObject *)NyImmBitSet_FromIterable(v);
3610 else {
3611 Py_INCREF(v);
3612 return v;
3613 }
3614 if (v)
3615 anybitset_classify(v, vt);
3616 return v;
3617 }
3618
3619 typedef PyObject *(*immbitset_op_t)(NyImmBitSetObject *, PyObject *, int);
3620 typedef PyObject *(*cplbitset_op_t)(NyCplBitSetObject *, PyObject *, int);
3621
3622 static PyObject *
anybitset_op(PyObject * v,PyObject * w,immbitset_op_t immbitset_op,cplbitset_op_t cplbitset_op)3623 anybitset_op(PyObject *v, PyObject *w, immbitset_op_t immbitset_op, cplbitset_op_t cplbitset_op)
3624 {
3625 PyObject *c;
3626 int vt, wt;
3627 v = anybitset_convert(v, &vt);
3628 if (!v)
3629 return NULL;
3630 w = anybitset_convert(w, &wt);
3631 if (!w) {
3632 Py_DECREF(v);
3633 return NULL;
3634 }
3635 if (vt == BITSET)
3636 c = immbitset_op((NyImmBitSetObject *)v, w, wt);
3637 else if (vt == CPLSET)
3638 c = cplbitset_op((NyCplBitSetObject *)v, w, wt);
3639 else if (wt == BITSET)
3640 c = immbitset_op((NyImmBitSetObject *)w, v, vt);
3641 else if (wt == CPLSET)
3642 c = cplbitset_op((NyCplBitSetObject *)w, v, vt);
3643 else {
3644 Py_INCREF(Py_NotImplemented);
3645 c = Py_NotImplemented;
3646 }
3647 Py_DECREF(v);
3648 Py_DECREF(w);
3649 return c;
3650 }
3651
3652 static PyObject *
anybitset_and(PyObject * v,PyObject * w)3653 anybitset_and(PyObject *v, PyObject *w)
3654 {
3655 return anybitset_op(v, w, immbitset_and, cplbitset_and);
3656 }
3657
3658 static PyObject *
anybitset_or(PyObject * v,PyObject * w)3659 anybitset_or(PyObject *v, PyObject *w)
3660 {
3661 return anybitset_op(v, w, immbitset_or, cplbitset_or);
3662 }
3663
3664 static PyObject *
anybitset_sub(PyObject * v,PyObject * w)3665 anybitset_sub(PyObject *v, PyObject *w)
3666 {
3667 return anybitset_op(v, w, immbitset_sub, cplbitset_sub);
3668 }
3669
3670 static PyObject *
anybitset_xor(PyObject * v,PyObject * w)3671 anybitset_xor(PyObject *v, PyObject *w)
3672 {
3673 return anybitset_op(v, w, immbitset_xor, cplbitset_xor);
3674 }
3675
3676 static PyObject *
anybitset_lshift(PyObject * v,PyObject * w)3677 anybitset_lshift(PyObject *v, PyObject *w)
3678 {
3679 int vt;
3680 NyBit shiftby;
3681 PyObject *c;
3682 shiftby = bitno_from_object((PyObject *)w);
3683 if (shiftby == -1L && PyErr_Occurred())
3684 return 0;
3685 v = anybitset_convert(v, &vt);
3686 if (!v)
3687 return NULL;
3688 if (vt == BITSET)
3689 c = (PyObject *)immbitset_lshift((NyImmBitSetObject *)v, shiftby);
3690 else if (vt == CPLSET) {
3691 c = cplbitset_lshift((NyCplBitSetObject *)v, shiftby);
3692 }
3693 else {
3694 Py_INCREF(Py_NotImplemented);
3695 c = Py_NotImplemented;
3696 }
3697 Py_DECREF(v);
3698 return c;
3699 }
3700
3701 static PyNumberMethods immbitset_as_number = {
3702 .nb_subtract = (binaryfunc) anybitset_sub,
3703 .nb_bool = (inquiry) immbitset_nonzero,
3704 .nb_invert = (unaryfunc) immbitset_complement,
3705 .nb_lshift = (binaryfunc) anybitset_lshift,
3706 .nb_and = (binaryfunc) anybitset_and,
3707 .nb_xor = (binaryfunc) anybitset_xor,
3708 .nb_or = (binaryfunc) anybitset_or,
3709 .nb_int = (unaryfunc) immbitset_int,
3710 };
3711
3712 static NyMutBitSetObject *
immbitset_mutable_copy(PyObject * self,PyObject * args)3713 immbitset_mutable_copy(PyObject *self, PyObject *args)
3714 {
3715 return mutbitset_new_from_arg(self);
3716 }
3717
3718 static PyObject *
immbitset_reduce_flags(NyImmBitSetObject * self,int flags)3719 immbitset_reduce_flags(NyImmBitSetObject *self, int flags)
3720 {
3721 PyObject *a = PyTuple_New(2);
3722 PyObject *b = PyTuple_New(2);
3723 PyObject *c = PyLong_FromSsize_t(flags);
3724 PyObject *d = PyBytes_FromStringAndSize((char *)self->ob_field,
3725 Py_SIZE(self) * sizeof(self->ob_field[0]));
3726 if (!(a && b && c && d)) {
3727 Py_XDECREF(a);
3728 Py_XDECREF(b);
3729 Py_XDECREF(c);
3730 Py_XDECREF(d);
3731 return 0;
3732 }
3733 PyTuple_SET_ITEM(a, 0, NyBitSet_FormMethod);
3734 Py_INCREF(NyBitSet_FormMethod);
3735 PyTuple_SET_ITEM(a, 1, b);
3736 PyTuple_SET_ITEM(b, 0, c);
3737 PyTuple_SET_ITEM(b, 1, d);
3738 return a;
3739 }
3740
3741 static PyObject *
immbitset_reduce(NyImmBitSetObject * self,PyObject * args)3742 immbitset_reduce(NyImmBitSetObject *self, PyObject *args)
3743 {
3744 return immbitset_reduce_flags(self, 0);
3745 }
3746
3747 static PyMethodDef immbitset_methods[] = {
3748 {"mutcopy", (PyCFunction)immbitset_mutable_copy, METH_NOARGS, mutable_copy_doc},
3749 {"__reduce__", (PyCFunction)immbitset_reduce, METH_NOARGS, "helper for pickle"},
3750 {0} /* sentinel */
3751 };
3752
3753
3754 static PySequenceMethods immbitset_as_sequence = {
3755 .sq_contains = (objobjproc)immbitset_contains,
3756 };
3757
3758
3759 static PyMappingMethods immbitset_as_mapping = {
3760 .mp_length = immbitset_length,
3761 .mp_subscript = (binaryfunc)immbitset_subscript,
3762 };
3763
3764
3765 static PyObject *
immbitset_is_immutable(NyMutBitSetObject * v)3766 immbitset_is_immutable(NyMutBitSetObject *v)
3767 {
3768 Py_INCREF(Py_True);
3769 return (Py_True);
3770 }
3771
3772 char immbitset_is_immutable_doc[] =
3773 "S.is_immutable == True\n"
3774 "\n"
3775 "True since S is immutable.";
3776
3777 static PyGetSetDef immbitset_getsets[] = {
3778 {"is_immutable", (getter)immbitset_is_immutable, (setter)0, immbitset_is_immutable_doc},
3779 {0} /* Sentinel */
3780 };
3781
3782 PyTypeObject NyImmBitSet_Type = {
3783 PyVarObject_HEAD_INIT(NULL, 0)
3784 .tp_name = "guppy.sets.setsc.ImmBitSet",
3785 .tp_basicsize = sizeof(NyImmBitSetObject) - sizeof(NyBitField),
3786 .tp_itemsize = sizeof(NyBitField),
3787 .tp_dealloc = (destructor)immbitset_dealloc,
3788 .tp_repr = (reprfunc)immbitset_repr,
3789 .tp_as_number = &immbitset_as_number,
3790 .tp_as_sequence = &immbitset_as_sequence,
3791 .tp_as_mapping = &immbitset_as_mapping,
3792 .tp_hash = (hashfunc)immbitset_hash,
3793 .tp_getattro = PyObject_GenericGetAttr,
3794 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
3795 .tp_doc = ImmBitSet_doc,
3796 .tp_richcompare = (richcmpfunc)immbitset_richcompare,
3797 .tp_iter = (getiterfunc)immbitset_iter,
3798 .tp_methods = immbitset_methods,
3799 .tp_getset = immbitset_getsets,
3800 .tp_base = &NyBitSet_Type,
3801 .tp_alloc = PyType_GenericAlloc,
3802 .tp_new = immbitset_new,
3803 .tp_free = PyObject_Del,
3804 };
3805
3806 static PyNumberMethods cplbitset_as_number = {
3807 .nb_subtract = (binaryfunc) anybitset_sub,
3808 .nb_bool = (inquiry) cplbitset_nonzero,
3809 .nb_invert = (unaryfunc) cplbitset_complement,
3810 .nb_lshift = (binaryfunc) anybitset_lshift,
3811 .nb_and = (binaryfunc) anybitset_and,
3812 .nb_xor = (binaryfunc) anybitset_xor,
3813 .nb_or = (binaryfunc) anybitset_or,
3814 .nb_int = (unaryfunc) cplbitset_int,
3815 };
3816
3817 /* Implement "bit in cplbitset" */
3818 static PySequenceMethods cplbitset_as_sequence = {
3819 .sq_contains = (objobjproc)cplbitset_contains,
3820 };
3821
3822
3823 static NyMutBitSetObject *
cplbitset_mutable_copy(PyObject * self)3824 cplbitset_mutable_copy(PyObject *self)
3825 {
3826 return mutbitset_new_from_arg(self);
3827 }
3828
3829 static PyObject *
cplbitset_reduce(NyCplBitSetObject * self,PyObject * args)3830 cplbitset_reduce(NyCplBitSetObject *self, PyObject *args)
3831 {
3832 return immbitset_reduce_flags(cplbitset_cpl(self), NyForm_CPL);
3833 }
3834
3835 static PyMethodDef cplbitset_methods[] = {
3836 {"mutcopy", (PyCFunction)cplbitset_mutable_copy, METH_NOARGS, mutable_copy_doc},
3837 {"__reduce__", (PyCFunction)cplbitset_reduce, METH_NOARGS, "helper for pickle"},
3838 {0} /* sentinel */
3839 };
3840
3841
3842 int
cplbitset_traverse(NyHeapTraverse * ta)3843 cplbitset_traverse(NyHeapTraverse *ta)
3844 {
3845 return ta->visit((PyObject *)((NyCplBitSetObject *)ta->obj)->ob_val, ta->arg);
3846 }
3847
3848
3849 static PyGetSetDef cplbitset_getsets[] = {
3850 {"is_immutable", (getter)immbitset_is_immutable, (setter)0, immbitset_is_immutable_doc},
3851 {0} /* Sentinel */
3852 };
3853
3854
3855 PyTypeObject NyCplBitSet_Type = {
3856 PyVarObject_HEAD_INIT(NULL, 0)
3857 .tp_name = "guppy.sets.setsc.CplBitSet",
3858 .tp_basicsize = sizeof(NyCplBitSetObject),
3859 .tp_dealloc = (destructor)cplbitset_dealloc,
3860 .tp_repr = (reprfunc)cplbitset_repr,
3861 .tp_as_number = &cplbitset_as_number,
3862 .tp_as_sequence = &cplbitset_as_sequence,
3863 .tp_hash = (hashfunc)cplbitset_hash,
3864 .tp_getattro = PyObject_GenericGetAttr,
3865 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
3866 .tp_doc = cplbitset_doc,
3867 .tp_richcompare = (richcmpfunc)cplbitset_richcompare,
3868 .tp_methods = cplbitset_methods,
3869 .tp_getset = cplbitset_getsets,
3870 .tp_base = &NyBitSet_Type,
3871 .tp_alloc = PyType_GenericAlloc,
3872 .tp_new = cplbitset_new,
3873 .tp_free = PyObject_Del,
3874 };
3875
3876
3877 static PyNumberMethods mutbitset_as_number = {
3878 .nb_subtract = (binaryfunc) anybitset_sub,
3879 .nb_bool = (inquiry) mutbitset_nonzero,
3880 .nb_invert = (unaryfunc) mutbitset_complement,
3881 .nb_lshift = (binaryfunc) anybitset_lshift,
3882 .nb_and = (binaryfunc) anybitset_and,
3883 .nb_xor = (binaryfunc) anybitset_xor,
3884 .nb_or = (binaryfunc) anybitset_or,
3885 .nb_int = (unaryfunc) mutbitset_int,
3886 .nb_inplace_subtract = (binaryfunc)mutbitset_isub,
3887 .nb_inplace_and = (binaryfunc)mutbitset_iand,
3888 .nb_inplace_xor = (binaryfunc)mutbitset_ixor,
3889 .nb_inplace_or = (binaryfunc)mutbitset_ior,
3890 };
3891
3892 /* Implement "bit in mutset" */
3893 static PySequenceMethods mutbitset_as_sequence = {
3894 .sq_contains = (objobjproc)mutbitset_contains,
3895 };
3896
3897 static PyObject *
mutbitset_reduce(NyMutBitSetObject * self,PyObject * args)3898 mutbitset_reduce(NyMutBitSetObject *self, PyObject *args)
3899 {
3900 NyImmBitSetObject *bs = mutbitset_as_noncomplemented_immbitset(self);
3901 PyObject *ret;
3902 if (!bs)
3903 return 0;
3904 ret = immbitset_reduce_flags(bs, NyForm_MUT | (self->cpl?NyForm_CPL : 0));
3905 Py_DECREF(bs);
3906 return ret;
3907 }
3908
3909
3910 static NyMutBitSetObject *
mutbitset_mutable_copy(PyObject * self)3911 mutbitset_mutable_copy(PyObject *self)
3912 {
3913 return mutbitset_new_from_arg(self);
3914 }
3915
3916
3917 static PyMethodDef mutbitset_methods[] = {
3918 {"__reduce__", (PyCFunction)mutbitset_reduce, METH_NOARGS, "helper for pickle"},
3919 {"add", (PyCFunction)mutbitset_add, METH_O, add_doc},
3920 {"append", (PyCFunction)mutbitset_append, METH_O, append_doc},
3921 {"clear", (PyCFunction)_mutbitset_clear, METH_NOARGS, clear_doc},
3922 {"discard", (PyCFunction)mutbitset_discard, METH_O, discard_doc},
3923 {"pop", (PyCFunction)mutbitset_pop, METH_VARARGS, pop_doc},
3924 {"remove", (PyCFunction)mutbitset_remove, METH_O, remove_doc},
3925 {"mutcopy", (PyCFunction)mutbitset_mutable_copy, METH_NOARGS,
3926 mutable_copy_doc},
3927 {"tas", (PyCFunction)mutbitset_tasbit, METH_O, tasbit_doc},
3928 {"tac", (PyCFunction)mutbitset_tacbit, METH_O, tacbit_doc},
3929 {0} /* sentinel */
3930 };
3931
3932 static PyObject *
mutbitset_get_num_seg(NyMutBitSetObject * v)3933 mutbitset_get_num_seg(NyMutBitSetObject *v)
3934 {
3935 return PyLong_FromSsize_t(v->root->cur_size);
3936 }
3937
3938 size_t
generic_indisize(PyObject * v)3939 generic_indisize(PyObject *v)
3940 {
3941 NyBit size = Py_TYPE(v)->tp_basicsize;
3942 if (Py_TYPE(v)->tp_itemsize)
3943 size += Py_SIZE(v) * Py_TYPE(v)->tp_itemsize;
3944 return size;
3945 }
3946
3947
3948 static size_t
immbitset_indisize(NyImmBitSetObject * v)3949 immbitset_indisize(NyImmBitSetObject *v)
3950 {
3951 return generic_indisize((PyObject *)v);
3952 }
3953
3954 static size_t
cplbitset_indisize(NyCplBitSetObject * v)3955 cplbitset_indisize(NyCplBitSetObject *v)
3956 {
3957 return generic_indisize((PyObject *)v);
3958 }
3959
3960 size_t
mutbitset_indisize(NyMutBitSetObject * v)3961 mutbitset_indisize(NyMutBitSetObject *v)
3962 {
3963 NyBit size = Py_TYPE(v)->tp_basicsize;
3964 int i;
3965 if (v->root != &v->fst_root)
3966 size += Py_TYPE(v->root)->tp_basicsize +
3967 Py_SIZE(v->root) * Py_TYPE(v->root)->tp_basicsize;
3968 for (i = 0; i < v->root->cur_size; i++) {
3969 size += immbitset_indisize(v->root->ob_field[i].set);
3970 }
3971 return size;
3972 }
3973
3974 size_t
anybitset_indisize(PyObject * obj)3975 anybitset_indisize(PyObject *obj)
3976 {
3977 if (NyMutBitSet_Check(obj))
3978 return mutbitset_indisize((NyMutBitSetObject *)obj);
3979 else if (NyImmBitSet_Check(obj))
3980 return immbitset_indisize((NyImmBitSetObject *)obj);
3981 else if (NyCplBitSet_Check(obj))
3982 return cplbitset_indisize((NyCplBitSetObject *)obj);
3983 else {
3984 PyErr_SetString(PyExc_TypeError, "anybitset_indisize: some bitset expected");
3985 return -1;
3986 }
3987 }
3988
3989 static PyObject *
anybitset_get_indisize(NyMutBitSetObject * v)3990 anybitset_get_indisize(NyMutBitSetObject *v)
3991 {
3992 return PyLong_FromSsize_t(anybitset_indisize((PyObject *)v));
3993 }
3994
3995 char mutbitset_is_immutable_doc[] =
3996 "S.is_immutable == False\n"
3997 "\n"
3998 "False since S is not immmutable.";
3999
4000 static PyObject *
mutbitset_is_immutable(NyMutBitSetObject * v)4001 mutbitset_is_immutable(NyMutBitSetObject *v)
4002 {
4003 Py_INCREF(Py_False);
4004 return (Py_False);
4005 }
4006
4007 static PyGetSetDef mutbitset_getsets[] = {
4008 {"_num_seg", (getter)mutbitset_get_num_seg, (setter)0},
4009 {"_indisize", (getter)anybitset_get_indisize, (setter)0},
4010 {"is_immutable", (getter)mutbitset_is_immutable, (setter)0, mutbitset_is_immutable_doc},
4011 {0} /* Sentinel */
4012 };
4013
4014 #define OFF(x) offsetof(NyMutBitSetObject, x)
4015 static PyMemberDef mutbitset_members[] = {
4016 {"_splitting_size", T_INT, OFF(splitting_size)},
4017 {0} /* Sentinel */
4018 };
4019
4020 static PyMappingMethods mutbitset_as_mapping = {
4021 .mp_length = mutbitset_length,
4022 .mp_subscript = (binaryfunc)mutbitset_subscript,
4023 };
4024
4025 PyTypeObject NyMutBitSet_Type = {
4026 PyVarObject_HEAD_INIT(NULL, 0)
4027 .tp_name = "guppy.sets.setsc.MutBitSet",
4028 .tp_basicsize = sizeof(NyMutBitSetObject),
4029 .tp_dealloc = (destructor)mutbitset_dealloc,
4030 .tp_repr = (reprfunc)mutbitset_repr,
4031 .tp_as_number = &mutbitset_as_number,
4032 .tp_as_sequence = &mutbitset_as_sequence,
4033 .tp_as_mapping = &mutbitset_as_mapping,
4034 .tp_getattro = PyObject_GenericGetAttr,
4035 .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
4036 .tp_doc = mutbitset_doc,
4037 .tp_richcompare = (richcmpfunc)mutbitset_richcompare,
4038 .tp_iter = (getiterfunc)mutbitset_iter,
4039 .tp_methods = mutbitset_methods,
4040 .tp_members = mutbitset_members,
4041 .tp_getset = mutbitset_getsets,
4042 .tp_base = &NyBitSet_Type,
4043 .tp_alloc = PyType_GenericAlloc,
4044 .tp_new = mutbitset_new,
4045 .tp_free = PyObject_Del,
4046 };
4047
4048
4049 PyTypeObject NyImmBitSetIter_Type = {
4050 PyVarObject_HEAD_INIT(NULL, 0)
4051 .tp_name = "immbitset-iterator",
4052 .tp_basicsize = sizeof(NyImmBitSetIterObject),
4053 .tp_dealloc = (destructor)bsiter_dealloc,
4054 .tp_getattro = PyObject_GenericGetAttr,
4055 .tp_flags = Py_TPFLAGS_DEFAULT,
4056 .tp_iter = (getiterfunc)bsiter_getiter,
4057 .tp_iternext = (iternextfunc)bsiter_iternext,
4058 };
4059
4060 PyTypeObject NyUnion_Type = {
4061 PyVarObject_HEAD_INIT(NULL, 0)
4062 .tp_name = "guppy.sets.setsc.Union",
4063 .tp_basicsize = sizeof(NyUnionObject) - NyUnion_MINSIZE*sizeof(NySetField),
4064 .tp_itemsize = sizeof(NySetField),
4065 .tp_dealloc = (destructor)union_dealloc,
4066 .tp_getattro = PyObject_GenericGetAttr,
4067 .tp_flags = Py_TPFLAGS_DEFAULT,
4068 };
4069
4070
4071 static PyObject *
_NyImmBitSet_Singleton(PyObject * unused,PyObject * arg)4072 _NyImmBitSet_Singleton(PyObject *unused, PyObject *arg)
4073 {
4074 return (PyObject *)NyImmBitSet_Singleton(arg);
4075 }
4076
4077 /* Quoting Python/bltinmodule.c */
4078
4079 /* Return number of items in range/xrange (lo, hi, step). step > 0
4080 * required. Return a value < 0 if & only if the true value is too
4081 * large to fit in a Py_ssize_t.
4082 */
4083
4084 static Py_ssize_t
get_len_of_range(Py_ssize_t lo,Py_ssize_t hi,Py_ssize_t step)4085 get_len_of_range(Py_ssize_t lo, Py_ssize_t hi, Py_ssize_t step)
4086 {
4087 /* -------------------------------------------------------------
4088 If lo >= hi, the range is empty.
4089 Else if n values are in the range, the last one is
4090 lo + (n-1)*step, which must be <= hi-1. Rearranging,
4091 n <= (hi - lo - 1)/step + 1, so taking the floor of the RHS gives
4092 the proper value. Since lo < hi in this case, hi-lo-1 >= 0, so
4093 the RHS is non-negative and so truncation is the same as the
4094 floor. Letting M be the largest positive long, the worst case
4095 for the RHS numerator is hi=M, lo=-M-1, and then
4096 hi-lo-1 = M-(-M-1)-1 = 2*M. Therefore size_t has enough
4097 precision to compute the RHS exactly.
4098 ---------------------------------------------------------------*/
4099 Py_ssize_t n = 0;
4100 if (lo < hi) {
4101 size_t uhi = (size_t)hi;
4102 size_t ulo = (size_t)lo;
4103 size_t diff = uhi - ulo - 1;
4104 n = (Py_ssize_t)(diff / (size_t)step + 1);
4105 }
4106 return n;
4107 }
4108
4109 static PyObject *
NyImmBitSet_Range(NyBit lo,NyBit hi,NyBit step)4110 NyImmBitSet_Range(NyBit lo, NyBit hi, NyBit step)
4111 {
4112 NyBitField fst, *f, *fhi, fs[NyBits_N];
4113 NyImmBitSetObject *v;
4114
4115 NyBit bitno, bitno_per_block, hipos, hibit, bit, pos, fstbit;
4116 NyBit size, posadd, pos_per_block, d, lim, bign, bp;
4117 NyBit bitnos[NyBits_N+1];
4118
4119 NyBit blocksize, i, j, nf, nblocks, n, extra;
4120
4121 if (step <= 0) {
4122 PyErr_SetString(PyExc_ValueError, "bitrange() arg 3 must be positive");
4123 return NULL;
4124 }
4125 bign = get_len_of_range(lo, hi, step);
4126 n = (int)bign;
4127 if (bign < 0 || (NyBit)n != bign) {
4128 PyErr_SetString(PyExc_OverflowError,
4129 "bitrange() result has too many items");
4130 return NULL;
4131 }
4132
4133 if (n == 0) {
4134 Py_INCREF(NyImmBitSet_Empty);
4135 return (PyObject *)NyImmBitSet_Empty;
4136 }
4137
4138 bitno = lo;
4139 bit = bitno_modiv(bitno, &pos);
4140 hibit = bitno_modiv(hi, &hipos);
4141
4142 bp = 0;
4143 fst.pos = pos;
4144 fst.bits = ONE_LONG<<bit;
4145 bp++;
4146 if (step < NyBits_N) { /* has to check, add step may overflow */
4147 bit += step;
4148 lim = pos == hipos ? hibit : NyBits_N;
4149 while (bit < lim) {
4150 fst.bits |= ONE_LONG<<bit;
4151 bit += step;
4152 bp++;
4153 }
4154 }
4155 i = 0;
4156 if (bp < n) {
4157 bitno = lo + bp * step;
4158 fstbit = bitno_modiv(bitno, &pos);
4159 bit = fstbit;
4160 do {
4161 bitnos[i] = bitno;
4162 fs[i].bits = ONE_LONG<<bit;
4163 fs[i].pos = pos;
4164 bp++;
4165 if (step < NyBits_N) { /* has to check, add step may overflow */
4166 bit += step;
4167 lim = pos == hipos ? hibit : NyBits_N;
4168 while (bit < lim) {
4169 fs[i].bits |= ONE_LONG<<bit;
4170 bp++;
4171 bit += step;
4172 }
4173 }
4174 bitno = lo + bp * step;
4175 bit = bitno_modiv(bitno, &pos);
4176 i++;
4177 } while (! (bp >= n || bit == fstbit ));
4178 }
4179 if (bp >= n) {
4180 assert(bp == n);
4181 nblocks = 0;
4182 nf = i;
4183 size = 1 + nf;
4184 pos_per_block = 0; /* avoid spurious undefined-warning */
4185 blocksize = 0; /* avoid spurious undefined-warning */
4186 extra = 0;
4187 } else {
4188 bitnos[i] = bitno;
4189 blocksize = i;
4190 bitno_per_block = bitno - bitnos[0];
4191 pos_per_block = (pos - fs[0].pos);
4192 nblocks = (hipos - fs[0].pos) / pos_per_block - 1;
4193 if (nblocks < 1)
4194 nblocks = 1;
4195 bitno = bitnos[0] + nblocks * bitno_per_block;
4196 while (bitno <= hi - bitno_per_block) {
4197 nblocks++;
4198 bitno += bitno_per_block;
4199 }
4200 i = 0;
4201 while (bitno <= hi - (d = bitnos[i+1] - bitnos[i])) {
4202 i++;
4203 bitno += d;
4204 }
4205 assert(i < blocksize);
4206 nf = i;
4207
4208 extra = bitno < hi;
4209 size = 1 + nblocks * blocksize + nf + extra;
4210 }
4211
4212 v = NyImmBitSet_New(size);
4213 if (!v) return 0;
4214 f = v->ob_field;
4215 fhi = v->ob_field + Py_SIZE(v);
4216 (void)fhi; // if assert is preprocessed into nothing, it generates a warning
4217 assert(f < fhi);
4218 f->pos = fst.pos;
4219 f->bits = fst.bits;
4220 f++;
4221 for (i = 0, posadd = 0; i < nblocks; i++, posadd += pos_per_block) {
4222 for (j = 0; j < blocksize; j++, f++) {
4223 assert(f < fhi);
4224 f->pos = fs[j].pos + posadd;
4225 f->bits = fs[j].bits;
4226 }
4227 }
4228 for (i = 0; i < nf; i++, f++) {
4229 assert(f < fhi);
4230 f->pos = fs[i].pos + posadd;
4231 f->bits = fs[i].bits;
4232 }
4233 if (extra) {
4234 assert(f < fhi);
4235 bit = bitno_modiv(bitno, &f->pos);
4236 f->bits = ONE_LONG<<bit;
4237 if (step < NyBits_N) /* has to check, add may overflow */ {
4238 bit += step;
4239 lim = f->pos == hipos ? hibit : NyBits_N;
4240 while (bit < lim) {
4241 f->bits |= ONE_LONG<<bit;
4242 bit += step;
4243 }
4244 }
4245 f++;
4246 }
4247
4248 assert(f == fhi);
4249 return (PyObject *)v;
4250 }
4251
4252 static PyObject *
_NyImmBitSet_Range(PyObject * unused,PyObject * args)4253 _NyImmBitSet_Range(PyObject *unused, PyObject *args)
4254 {
4255 /* Borrows from builtin_range() in Python/bltinmodule.c*/
4256 NyBit ilow = 0, ihigh = 0, istep = 1;
4257
4258 if (PyTuple_Size(args) <= 1) {
4259 if (!PyArg_ParseTuple(args,
4260 "n;bitrange() requires 1-3 int arguments",
4261 &ihigh))
4262 return NULL;
4263 }
4264 else {
4265 if (!PyArg_ParseTuple(args,
4266 "nn|n;bitrange() requires 1-3 int arguments",
4267 &ilow, &ihigh, &istep))
4268 return NULL;
4269 }
4270 return NyImmBitSet_Range(ilow, ihigh, istep);
4271 }
4272
4273 static PyObject *
NyBitSet_Form(PyObject * args)4274 NyBitSet_Form(PyObject *args)
4275 {
4276 PyObject *str;
4277 NyImmBitSetObject *bs;
4278 char *s;
4279 Py_ssize_t len,sz;
4280 int flags;
4281 if (!(args && PyTuple_Check(args)) && PyTuple_GET_SIZE(args) == 2) {
4282 PyErr_SetString(PyExc_TypeError, "NyBitSet_Form() requires exactly 2 arguments");
4283 return 0;
4284 }
4285 if (!PyLong_Check(PyTuple_GET_ITEM(args, 0))) {
4286 PyErr_SetString(PyExc_TypeError, "NyBitSet_Form(): 1st arg must be an int");
4287 return 0;
4288 }
4289 flags = PyLong_AsLong(PyTuple_GET_ITEM(args, 0));
4290 str = PyTuple_GET_ITEM(args, 1);
4291 if (!PyBytes_Check(str)) {
4292 PyErr_SetString(PyExc_TypeError, "NyBitSet_Form(): 2nd arg must be bytes");
4293 return 0;
4294 }
4295 if (PyBytes_AsStringAndSize(str, &s, &len) == -1)
4296 return 0;
4297 sz = len / sizeof(NyBitField);
4298 bs = NyImmBitSet_New(sz);
4299 if (!bs)
4300 return 0;
4301 fp_move(bs->ob_field, (NyBitField *)s, sz);
4302 if (flags & NyForm_MUT) {
4303 NyMutBitSetObject *ms = mutbitset_new_from_arg((PyObject *)bs);
4304 Py_DECREF(bs);
4305 if (!ms) {
4306 return 0;
4307 }
4308 if (flags & NyForm_CPL)
4309 mutbitset_iop_complement(ms);
4310 return (PyObject *)ms;
4311 }
4312 if (flags & NyForm_CPL) {
4313 NyCplBitSetObject * cpl = NyCplBitSet_New(bs);
4314 Py_DECREF(bs);
4315 return (PyObject *)cpl;
4316 }
4317 return (PyObject *)bs;
4318 }
4319
4320 static PyObject *
_NyBitSet_Form(PyObject * unused,PyObject * args)4321 _NyBitSet_Form(PyObject *unused, PyObject *args)
4322 {
4323 return NyBitSet_Form(args);
4324 }
4325
4326 static PyMethodDef nybitset_methods[] =
4327 {
4328 {"immbit",(PyCFunction)_NyImmBitSet_Singleton, METH_O, bitsingle_doc},
4329 {"immbitrange",(PyCFunction)_NyImmBitSet_Range, METH_VARARGS, bitrange_doc},
4330 {"immbitset",(PyCFunction)immbitset, METH_VARARGS|METH_KEYWORDS, immbitset_doc},
4331 {"_bs",(PyCFunction)_NyBitSet_Form, METH_VARARGS, bitform_doc},
4332 {0}
4333 };
4334
4335 static NyBitSet_Exports nybitset_exports = {
4336 0,
4337 sizeof(NyBitSet_Exports),
4338 "NyBitSet_Exports v1.0",
4339 NyMutBitSet_New,
4340 NyMutBitSet_setbit,
4341 NyMutBitSet_clrbit,
4342 mutbitset_set_or_clr,
4343 NyMutBitSet_AsImmBitSet,
4344 NyAnyBitSet_iterate,
4345 NyMutBitSet_hasbit,
4346 NyImmBitSet_hasbit,
4347 cplbitset_hasbit,
4348 };
4349
4350
fsb_dx_nybitset_init(PyObject * m)4351 int fsb_dx_nybitset_init(PyObject *m)
4352 {
4353 PyObject *d;
4354
4355 Py_TYPE(&_NyImmBitSet_EmptyStruct) = &NyImmBitSet_Type;
4356 Py_TYPE(&_NyImmBitSet_OmegaStruct) = &NyCplBitSet_Type;
4357
4358 NYFILL(NyBitSet_Type);
4359 NYFILL(NyImmBitSet_Type);
4360 NYFILL(NyCplBitSet_Type);
4361 NYFILL(NyMutBitSet_Type);
4362 NYFILL(NyImmBitSetIter_Type);
4363 NYFILL(NyUnion_Type);
4364
4365 d = PyModule_GetDict(m);
4366 PyDict_SetItemString(d, "BitSet", (PyObject *)&NyBitSet_Type);
4367 PyDict_SetItemString(d, "CplBitSet", (PyObject *)&NyCplBitSet_Type);
4368 PyDict_SetItemString(d, "ImmBitSet", (PyObject *)&NyImmBitSet_Type);
4369 PyDict_SetItemString(d, "MutBitSet", (PyObject *)&NyMutBitSet_Type);
4370 PyDict_SetItemString(d,
4371 "NyBitSet_Exports",
4372 PyCapsule_New(
4373 &nybitset_exports,
4374 "guppy.sets.setsc.NybitSet_Exports",
4375 0)
4376 );
4377
4378 if (fsb_dx_addmethods(m, nybitset_methods, 0) == -1)
4379 goto error;
4380 NyBitSet_FormMethod = PyObject_GetAttrString(m, "_bs");
4381 if (!NyBitSet_FormMethod)
4382 goto error;
4383 {
4384 int i;
4385 /* initialize len() helper */
4386 for (i = 0; i < LEN_TAB_SIZE; i++) {
4387 unsigned b = i;
4388 int n = 0;
4389 while (b) {
4390 if (b & 1)
4391 n++;
4392 b >>= 1;
4393 }
4394 len_tab[i] = n;
4395 }
4396 }
4397
4398 return 0;
4399 error:
4400 return -1;
4401 }
4402