2 This file is part of GNUnet.
3 (C) 2012 Christian Grothoff (and other contributing authors)
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
10 GNUnet is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
22 * @file consensus/gnunet-consensus-ibf
23 * @brief tool for reconciling data with invertible bloom filters
24 * @author Florian Dold
29 #include "gnunet_common.h"
30 #include "gnunet_container_lib.h"
31 #include "gnunet_util_lib.h"
35 static unsigned int asize = 10;
36 static unsigned int bsize = 10;
37 static unsigned int csize = 10;
38 static unsigned int hash_num = 3;
39 static unsigned int ibf_size = 80;
42 static struct GNUNET_CONTAINER_MultiHashMap *set_a;
43 static struct GNUNET_CONTAINER_MultiHashMap *set_b;
44 /* common elements in a and b */
45 static struct GNUNET_CONTAINER_MultiHashMap *set_c;
47 static struct InvertibleBloomFilter *ibf_a;
48 static struct InvertibleBloomFilter *ibf_b;
53 insert_iterator (void *cls,
54 const struct GNUNET_HashCode *key,
57 struct InvertibleBloomFilter *ibf = (struct InvertibleBloomFilter *) cls;
58 ibf_insert (ibf, key);
64 run (void *cls, char *const *args, const char *cfgfile,
65 const struct GNUNET_CONFIGURATION_Handle *cfg)
67 struct GNUNET_HashCode id;
72 set_a = GNUNET_CONTAINER_multihashmap_create (((asize == 0) ? 1 : (asize + csize)),
74 set_b = GNUNET_CONTAINER_multihashmap_create (((bsize == 0) ? 1 : (bsize + csize)),
76 set_c = GNUNET_CONTAINER_multihashmap_create (((csize == 0) ? 1 : csize),
79 printf ("hash-num=%u, size=%u, #(A-B)=%u, #(B-A)=%u, #(A&B)=%u\n",
80 hash_num, ibf_size, asize, bsize, csize);
85 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &id);
86 if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_a, &id))
88 printf("A: %s\n", GNUNET_h2s (&id));
89 GNUNET_CONTAINER_multihashmap_put (
90 set_a, &id, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
96 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &id);
97 if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_a, &id))
99 if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_b, &id))
101 printf("B: %s\n", GNUNET_h2s (&id));
102 GNUNET_CONTAINER_multihashmap_put (
103 set_b, &id, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
109 GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &id);
110 if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_a, &id))
112 if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_b, &id))
114 printf("C: %s\n", GNUNET_h2s (&id));
115 GNUNET_CONTAINER_multihashmap_put (
116 set_c, &id, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY);
121 ibf_a = ibf_create (ibf_size, hash_num, 0);
122 ibf_b = ibf_create (ibf_size, hash_num, 0);
124 GNUNET_CONTAINER_multihashmap_iterate (set_a, &insert_iterator, ibf_a);
125 GNUNET_CONTAINER_multihashmap_iterate (set_b, &insert_iterator, ibf_b);
126 GNUNET_CONTAINER_multihashmap_iterate (set_c, &insert_iterator, ibf_a);
127 GNUNET_CONTAINER_multihashmap_iterate (set_c, &insert_iterator, ibf_b);
130 printf ("-----------------\n");
131 ibf_subtract (ibf_a, ibf_b);
135 res = ibf_decode (ibf_a, &side, &id);
136 if (GNUNET_SYSERR == res)
138 printf ("decode failed\n");
141 if (GNUNET_NO == res)
143 if ((0 == GNUNET_CONTAINER_multihashmap_size (set_b)) &&
144 (0 == GNUNET_CONTAINER_multihashmap_size (set_a)))
145 printf ("decode succeeded\n");
147 printf ("decode missed elements\n");
151 printf("R: %s\n", GNUNET_h2s (&id));
152 printf("s: %d\n", side);
155 res = GNUNET_CONTAINER_multihashmap_remove (set_a, &id, NULL);
157 res = GNUNET_CONTAINER_multihashmap_remove (set_b, &id, NULL);
158 if (GNUNET_YES != res)
160 printf ("decoded wrong element\n");
167 main (int argc, char **argv)
169 static const struct GNUNET_GETOPT_CommandLineOption options[] = {
171 gettext_noop ("number of element in set A-B"), 1,
172 &GNUNET_GETOPT_set_uint, &asize},
174 gettext_noop ("number of element in set B-A"), 1,
175 &GNUNET_GETOPT_set_uint, &bsize},
177 gettext_noop ("number of common elements in A and B"), 1,
178 &GNUNET_GETOPT_set_uint, &csize},
179 {'k', "hash-num", NULL,
180 gettext_noop ("hash num"), 1,
181 &GNUNET_GETOPT_set_uint, &hash_num},
182 {'s', "ibf-size", NULL,
183 gettext_noop ("ibf size"), 1,
184 &GNUNET_GETOPT_set_uint, &ibf_size},
185 GNUNET_GETOPT_OPTION_END
187 GNUNET_PROGRAM_run2 (argc, argv, "gnunet-consensus-ibf",
189 options, &run, NULL, GNUNET_YES);