1 /*
2 * This file Copyright (C) 2008-2014 Mnemosyne LLC
3 *
4 * It may be used under the GNU GPL versions 2 or 3
5 * or any future license endorsed by Mnemosyne LLC.
6 *
7 */
8
9 #pragma once
10
11 #ifndef __TRANSMISSION__
12 #error only libtransmission should #include this header.
13 #endif
14
15 #include "transmission.h"
16
17 /** @brief Implementation of the BitTorrent spec's Bitfield array of bits */
18 typedef struct tr_bitfield
19 {
20 uint8_t* bits;
21 size_t alloc_count;
22
23 size_t bit_count;
24
25 size_t true_count;
26
27 /* Special cases for when full or empty but we don't know the bitCount.
28 This occurs when a magnet link's peers send have all / have none */
29 bool have_all_hint;
30 bool have_none_hint;
31 }
32 tr_bitfield;
33
34 /***
35 ****
36 ***/
37
38 void tr_bitfieldSetHasAll(tr_bitfield*);
39
40 void tr_bitfieldSetHasNone(tr_bitfield*);
41
42 void tr_bitfieldAdd(tr_bitfield*, size_t bit);
43
44 void tr_bitfieldRem(tr_bitfield*, size_t bit);
45
46 void tr_bitfieldAddRange(tr_bitfield*, size_t begin, size_t end);
47
48 void tr_bitfieldRemRange(tr_bitfield*, size_t begin, size_t end);
49
50 /***
51 **** life cycle
52 ***/
53
54 extern tr_bitfield const TR_BITFIELD_INIT;
55
56 void tr_bitfieldConstruct(tr_bitfield*, size_t bit_count);
57
tr_bitfieldDestruct(tr_bitfield * b)58 static inline void tr_bitfieldDestruct(tr_bitfield* b)
59 {
60 tr_bitfieldSetHasNone(b);
61 }
62
63 /***
64 ****
65 ***/
66
67 void tr_bitfieldSetFromFlags(tr_bitfield*, bool const* bytes, size_t n);
68
69 void tr_bitfieldSetFromBitfield(tr_bitfield*, tr_bitfield const*);
70
71 void tr_bitfieldSetRaw(tr_bitfield*, void const* bits, size_t byte_count, bool bounded);
72
73 void* tr_bitfieldGetRaw(tr_bitfield const* b, size_t* byte_count);
74
75 /***
76 ****
77 ***/
78
79 size_t tr_bitfieldCountRange(tr_bitfield const*, size_t begin, size_t end);
80
81 size_t tr_bitfieldCountTrueBits(tr_bitfield const* b);
82
tr_bitfieldHasAll(tr_bitfield const * b)83 static inline bool tr_bitfieldHasAll(tr_bitfield const* b)
84 {
85 return b->bit_count != 0 ? (b->true_count == b->bit_count) : b->have_all_hint;
86 }
87
tr_bitfieldHasNone(tr_bitfield const * b)88 static inline bool tr_bitfieldHasNone(tr_bitfield const* b)
89 {
90 return b->bit_count != 0 ? (b->true_count == 0) : b->have_none_hint;
91 }
92
93 bool tr_bitfieldHas(tr_bitfield const* b, size_t n);
94