... | ... |
@@ -27,6 +27,11 @@ |
27 | 27 |
#include <pthread.h> |
28 | 28 |
#include <assert.h> |
29 | 29 |
|
30 |
+#include <sys/types.h> |
|
31 |
+#include <sys/stat.h> |
|
32 |
+#include <fcntl.h> |
|
33 |
+#include <sys/mman.h> |
|
34 |
+ |
|
30 | 35 |
#include "md5.h" |
31 | 36 |
#include "mpool.h" |
32 | 37 |
#include "clamav.h" |
... | ... |
@@ -186,7 +191,7 @@ static int cacheset_lookup(struct cache_set *map, unsigned char *md5, size_t siz |
186 | 186 |
|
187 | 187 |
|
188 | 188 |
static int cacheset_init(struct cache_set *map, unsigned int entries) { |
189 |
- map->data = mpool_calloc(mempool, 256, sizeof(*map->data)); |
|
189 |
+ map->data = mpool_calloc(mempool, entries, sizeof(*map->data)); |
|
190 | 190 |
if (!map->data) |
191 | 191 |
return CL_EMEM; |
192 | 192 |
map->capacity = entries; |
... | ... |
@@ -205,24 +210,34 @@ struct node { |
205 | 205 |
struct node *left; |
206 | 206 |
struct node *right; |
207 | 207 |
struct node *up; |
208 |
+ struct node *next; |
|
209 |
+ struct node *prev; |
|
208 | 210 |
uint32_t size; |
209 | 211 |
}; |
210 | 212 |
|
211 | 213 |
struct cache_set { |
212 | 214 |
struct node *data; |
213 | 215 |
struct node *root; |
214 |
- unsigned int used; |
|
215 |
- unsigned int total; |
|
216 |
+ struct node *first; |
|
217 |
+ struct node *last; |
|
216 | 218 |
}; |
217 | 219 |
|
218 |
-static int cacheset_init(struct cache_set *map, unsigned int entries) { |
|
219 |
- map->data = mpool_calloc(mempool, entries, sizeof(*map->data)); |
|
220 |
- map->root = NULL; |
|
220 |
+static int cacheset_init(struct cache_set *cs, unsigned int entries) { |
|
221 |
+ unsigned int i; |
|
222 |
+ cs->data = mpool_calloc(mempool, entries, sizeof(*cs->data)); |
|
223 |
+ cs->root = NULL; |
|
221 | 224 |
|
222 |
- if(!map->data) |
|
225 |
+ if(!cs->data) |
|
223 | 226 |
return CL_EMEM; |
224 |
- map->used = 0; |
|
225 |
- map->total = entries; |
|
227 |
+ |
|
228 |
+ for(i=1; i<entries; i++) { |
|
229 |
+ cs->data[i-1].next = &cs->data[i]; |
|
230 |
+ cs->data[i].prev = &cs->data[i-1]; |
|
231 |
+ } |
|
232 |
+ |
|
233 |
+ cs->first = cs->data; |
|
234 |
+ cs->last = &cs->data[entries-1]; |
|
235 |
+ |
|
226 | 236 |
return 0; |
227 | 237 |
} |
228 | 238 |
|
... | ... |
@@ -232,43 +247,13 @@ static inline int cmp(int64_t *a, int64_t *b) { |
232 | 232 |
return ret; |
233 | 233 |
} |
234 | 234 |
|
235 |
-#ifdef CHECK_TREE |
|
236 |
-static int check_tree_rec(struct cache_set *cs, unsigned int *beenthere, struct node *node, struct node *parent) { |
|
237 |
- unsigned int item = node - cs->data; |
|
238 |
- if(!node) return 0; |
|
239 |
- if(beenthere[item]) return 1; |
|
240 |
- beenthere[item] = 1; |
|
241 |
- if(node->up != parent) return 1; |
|
242 |
- return check_tree_rec(cs, beenthere, node->left, node) | check_tree_rec(cs, beenthere, node->right, node); |
|
243 |
-} |
|
244 |
- |
|
245 |
-static void check_tree(struct cache_set *cs) { |
|
246 |
- unsigned int i, been_there[1024]; |
|
247 |
- memset(been_there, 0, sizeof(been_there)); |
|
248 |
- if(check_tree_rec(cs, been_there, cs->root, NULL)) { |
|
249 |
- cli_errmsg("tree fukkd up\n"); |
|
250 |
- abort(); |
|
251 |
- } |
|
252 |
- for(i=0; i<cs->used; i++) { |
|
253 |
- if(!been_there[i]) { |
|
254 |
- cli_errmsg("tree fukkd up\n"); |
|
255 |
- abort(); |
|
256 |
- } |
|
257 |
- } |
|
258 |
-} |
|
259 |
-#else |
|
260 |
-#define check_tree(a) |
|
261 |
-#endif |
|
262 |
- |
|
263 | 235 |
static int splay(int64_t *md5, struct cache_set *cs) { |
264 |
- struct node next = {{0, 0}, NULL, NULL, NULL, 0}, *right = &next, *left = &next, *temp, *root = cs->root; |
|
236 |
+ struct node next = {{0, 0}, NULL, NULL, NULL, NULL, NULL, 0}, *right = &next, *left = &next, *temp, *root = cs->root; |
|
265 | 237 |
int ret = 0; |
266 | 238 |
|
267 | 239 |
if(!root) |
268 | 240 |
return 0; |
269 | 241 |
|
270 |
- check_tree(cs); |
|
271 |
- |
|
272 | 242 |
while(1) { |
273 | 243 |
int comp = cmp(md5, root->digest); |
274 | 244 |
if(comp < 0) { |
... | ... |
@@ -318,7 +303,6 @@ static int splay(int64_t *md5, struct cache_set *cs) { |
318 | 318 |
root->up = NULL; |
319 | 319 |
cs->root = root; |
320 | 320 |
|
321 |
- check_tree(cs); |
|
322 | 321 |
return ret; |
323 | 322 |
} |
324 | 323 |
|
... | ... |
@@ -336,30 +320,35 @@ static void cacheset_add(struct cache_set *cs, unsigned char *md5, size_t size) |
336 | 336 |
|
337 | 337 |
memcpy(hash, md5, 16); |
338 | 338 |
if(splay(hash, cs)) |
339 |
- return; /* Already there */ |
|
340 |
- |
|
341 |
- if(cs->used == cs->total) { |
|
342 |
- struct node *parent; |
|
343 |
- int nodeno, bestnode, parents = 0; |
|
344 |
- for(nodeno = 0; nodeno < cs->total; nodeno++) { |
|
345 |
- parent = &cs->data[nodeno]; |
|
346 |
- if(!parent->left && !parent->right) { |
|
347 |
- int p=0; |
|
348 |
- do{ p++; } while(parent = parent->up); |
|
349 |
- if(p>=parents) { |
|
350 |
- parents = p; |
|
351 |
- bestnode = nodeno; |
|
352 |
- } |
|
353 |
- } |
|
354 |
- } |
|
355 |
- newnode=&cs->data[bestnode]; |
|
356 |
- parent = newnode->up; |
|
357 |
- if(parent->left == newnode) |
|
358 |
- parent->left = NULL; |
|
339 |
+ return; /* Already there */ |
|
340 |
+ |
|
341 |
+ newnode = cs->first; |
|
342 |
+ while(newnode) { |
|
343 |
+ if(!newnode->right && !newnode->left) |
|
344 |
+ break; |
|
345 |
+ newnode = newnode->next; |
|
346 |
+ } |
|
347 |
+ if(!newnode) { |
|
348 |
+ cli_errmsg("NO NEWNODE!\n"); |
|
349 |
+ abort(); |
|
350 |
+ } |
|
351 |
+ if(newnode->up) { |
|
352 |
+ if(newnode->up->left == newnode) |
|
353 |
+ newnode->up->left = NULL; |
|
359 | 354 |
else |
360 |
- parent->right = NULL; |
|
361 |
- } else |
|
362 |
- newnode = &cs->data[cs->used++]; |
|
355 |
+ newnode->up->right = NULL; |
|
356 |
+ } |
|
357 |
+ if(newnode->prev) |
|
358 |
+ newnode->prev->next = newnode->next; |
|
359 |
+ if(newnode->next) |
|
360 |
+ newnode->next->prev = newnode->prev; |
|
361 |
+ if(cs->first == newnode) |
|
362 |
+ cs->first = newnode->next; |
|
363 |
+ |
|
364 |
+ newnode->prev = cs->last; |
|
365 |
+ newnode->next = NULL; |
|
366 |
+ cs->last->next = newnode; |
|
367 |
+ cs->last = newnode; |
|
363 | 368 |
|
364 | 369 |
if(!cs->root) { |
365 | 370 |
newnode->left = NULL; |
... | ... |
@@ -384,6 +373,9 @@ static void cacheset_add(struct cache_set *cs, unsigned char *md5, size_t size) |
384 | 384 |
} |
385 | 385 |
#endif /* USE_SPLAY */ |
386 | 386 |
|
387 |
+/* #define TREES 1 */ |
|
388 |
+/* static inline unsigned int getkey(uint8_t *hash) { return 0; } */ |
|
389 |
+ |
|
387 | 390 |
#define TREES 256 |
388 | 391 |
static inline unsigned int getkey(uint8_t *hash) { return *hash; } |
389 | 392 |
|
... | ... |
@@ -400,6 +392,8 @@ static struct CACHE { |
400 | 400 |
} *cache = NULL; |
401 | 401 |
|
402 | 402 |
|
403 |
+static int cache_lookup_hash(unsigned char *md5, cli_ctx *ctx); |
|
404 |
+ |
|
403 | 405 |
int cl_cache_init(unsigned int entries) { |
404 | 406 |
unsigned int i; |
405 | 407 |
int ret; |
... | ... |
@@ -436,6 +430,27 @@ int cl_cache_init(unsigned int entries) { |
436 | 436 |
return 1; |
437 | 437 |
} |
438 | 438 |
} |
439 |
+ |
|
440 |
+ { |
|
441 |
+ int f = open("/home/acab/hashes", O_RDONLY); |
|
442 |
+ struct stat s; |
|
443 |
+ fstat(f, &s); |
|
444 |
+ char *pippo = mmap(NULL, s.st_size, PROT_READ, MAP_PRIVATE, f, 0); |
|
445 |
+ while(s.st_size >= 17) { |
|
446 |
+ if(*pippo == 'C') |
|
447 |
+ cache_lookup_hash(pippo+1, NULL); |
|
448 |
+ else if(*pippo == 'A') |
|
449 |
+ cache_add(pippo+1, NULL); |
|
450 |
+ else { |
|
451 |
+ printf("bad hash\n"); |
|
452 |
+ abort(); |
|
453 |
+ } |
|
454 |
+ pippo += 17; |
|
455 |
+ s.st_size -= 17; |
|
456 |
+ } |
|
457 |
+ printf("that's all\n"); |
|
458 |
+ abort(); |
|
459 |
+ } |
|
439 | 460 |
return 0; |
440 | 461 |
} |
441 | 462 |
|