ibf.h 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255
  1. /*
  2. This file is part of GNUnet
  3. Copyright (C) 2012 GNUnet e.V.
  4. GNUnet is free software: you can redistribute it and/or modify it
  5. under the terms of the GNU Affero General Public License as published
  6. by the Free Software Foundation, either version 3 of the License,
  7. or (at your option) any later version.
  8. GNUnet is distributed in the hope that it will be useful, but
  9. WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. Affero General Public License for more details.
  12. You should have received a copy of the GNU Affero General Public License
  13. along with this program. If not, see <http://www.gnu.org/licenses/>.
  14. SPDX-License-Identifier: AGPL3.0-or-later
  15. */
  16. /**
  17. * @file set/ibf.h
  18. * @brief invertible bloom filter
  19. * @author Florian Dold
  20. */
  21. #ifndef GNUNET_CONSENSUS_IBF_H
  22. #define GNUNET_CONSENSUS_IBF_H
  23. #include "platform.h"
  24. #include "gnunet_util_lib.h"
  25. #ifdef __cplusplus
  26. extern "C"
  27. {
  28. #if 0 /* keep Emacsens' auto-indent happy */
  29. }
  30. #endif
  31. #endif
  32. /**
  33. * Keys that can be inserted into and removed from an IBF.
  34. */
  35. struct IBF_Key
  36. {
  37. uint64_t key_val;
  38. };
  39. /**
  40. * Hash of an IBF key.
  41. */
  42. struct IBF_KeyHash
  43. {
  44. uint32_t key_hash_val;
  45. };
  46. /**
  47. * Type of the count field of IBF buckets.
  48. */
  49. struct IBF_Count
  50. {
  51. int8_t count_val;
  52. };
  53. /**
  54. * Size of one ibf bucket in bytes
  55. */
  56. #define IBF_BUCKET_SIZE (sizeof (struct IBF_Count) + sizeof (struct IBF_Key) + \
  57. sizeof (struct IBF_KeyHash))
  58. /**
  59. * Invertible bloom filter (IBF).
  60. *
  61. * An IBF is a counting bloom filter that has the ability to restore
  62. * the hashes of its stored elements with high probability.
  63. */
  64. struct InvertibleBloomFilter
  65. {
  66. /**
  67. * How many cells does this IBF have?
  68. */
  69. uint32_t size;
  70. /**
  71. * In how many cells do we hash one element?
  72. * Usually 4 or 3.
  73. */
  74. uint8_t hash_num;
  75. /**
  76. * Xor sums of the elements' keys, used to identify the elements.
  77. * Array of 'size' elements.
  78. */
  79. struct IBF_Key *key_sum;
  80. /**
  81. * Xor sums of the hashes of the keys of inserted elements.
  82. * Array of 'size' elements.
  83. */
  84. struct IBF_KeyHash *key_hash_sum;
  85. /**
  86. * How many times has a bucket been hit?
  87. * Can be negative, as a result of IBF subtraction.
  88. * Array of 'size' elements.
  89. */
  90. struct IBF_Count *count;
  91. };
  92. /**
  93. * Write buckets from an ibf to a buffer.
  94. * Exactly (IBF_BUCKET_SIZE*ibf->size) bytes are written to buf.
  95. *
  96. * @param ibf the ibf to write
  97. * @param start with which bucket to start
  98. * @param count how many buckets to write
  99. * @param buf buffer to write the data to
  100. */
  101. void
  102. ibf_write_slice (const struct InvertibleBloomFilter *ibf,
  103. uint32_t start,
  104. uint32_t count,
  105. void *buf);
  106. /**
  107. * Read buckets from a buffer into an ibf.
  108. *
  109. * @param buf pointer to the buffer to read from
  110. * @param start which bucket to start at
  111. * @param count how many buckets to read
  112. * @param ibf the ibf to write to
  113. */
  114. void
  115. ibf_read_slice (const void *buf,
  116. uint32_t start,
  117. uint32_t count,
  118. struct InvertibleBloomFilter *ibf);
  119. /**
  120. * Create a key from a hashcode.
  121. *
  122. * @param hash the hashcode
  123. * @return a key
  124. */
  125. struct IBF_Key
  126. ibf_key_from_hashcode (const struct GNUNET_HashCode *hash);
  127. /**
  128. * Create a hashcode from a key, by replicating the key
  129. * until the hascode is filled
  130. *
  131. * @param key the key
  132. * @param dst hashcode to store the result in
  133. */
  134. void
  135. ibf_hashcode_from_key (struct IBF_Key key, struct GNUNET_HashCode *dst);
  136. /**
  137. * Create an invertible bloom filter.
  138. *
  139. * @param size number of IBF buckets
  140. * @param hash_num number of buckets one element is hashed in, usually 3 or 4
  141. * @return the newly created invertible bloom filter, NULL on error
  142. */
  143. struct InvertibleBloomFilter *
  144. ibf_create (uint32_t size, uint8_t hash_num);
  145. /**
  146. * Insert a key into an IBF.
  147. *
  148. * @param ibf the IBF
  149. * @param key the element's hash code
  150. */
  151. void
  152. ibf_insert (struct InvertibleBloomFilter *ibf, struct IBF_Key key);
  153. /**
  154. * Remove a key from an IBF.
  155. *
  156. * @param ibf the IBF
  157. * @param key the element's hash code
  158. */
  159. void
  160. ibf_remove (struct InvertibleBloomFilter *ibf, struct IBF_Key key);
  161. /**
  162. * Subtract ibf2 from ibf1, storing the result in ibf1.
  163. * The two IBF's must have the same parameters size and hash_num.
  164. *
  165. * @param ibf1 IBF that is subtracted from
  166. * @param ibf2 IBF that will be subtracted from ibf1
  167. */
  168. void
  169. ibf_subtract (struct InvertibleBloomFilter *ibf1,
  170. const struct InvertibleBloomFilter *ibf2);
  171. /**
  172. * Decode and remove an element from the IBF, if possible.
  173. *
  174. * @param ibf the invertible bloom filter to decode
  175. * @param ret_side sign of the cell's count where the decoded element came from.
  176. * A negative sign indicates that the element was recovered
  177. * resides in an IBF that was previously subtracted from.
  178. * @param ret_id receives the hash code of the decoded element, if successful
  179. * @return #GNUNET_YES if decoding an element was successful,
  180. * #GNUNET_NO if the IBF is empty,
  181. * #GNUNET_SYSERR if the decoding has failed
  182. */
  183. int
  184. ibf_decode (struct InvertibleBloomFilter *ibf,
  185. int *ret_side,
  186. struct IBF_Key *ret_id);
  187. /**
  188. * Create a copy of an IBF, the copy has to be destroyed properly.
  189. *
  190. * @param ibf the IBF to copy
  191. */
  192. struct InvertibleBloomFilter *
  193. ibf_dup (const struct InvertibleBloomFilter *ibf);
  194. /**
  195. * Destroy all resources associated with the invertible bloom filter.
  196. * No more ibf_*-functions may be called on ibf after calling destroy.
  197. *
  198. * @param ibf the intertible bloom filter to destroy
  199. */
  200. void
  201. ibf_destroy (struct InvertibleBloomFilter *ibf);
  202. #if 0 /* keep Emacsens' auto-indent happy */
  203. {
  204. #endif
  205. #ifdef __cplusplus
  206. }
  207. #endif
  208. #endif