cscvs to tla changeset 62
[onak.git] / sixdegrees.c
1 /*
2  * sixdegrees.c - List the size of the six degrees of trust away from a key.
3  * 
4  * Jonathan McDowell <noodles@earth.li>
5  *
6  * Copyright 2001-2002 Project Purple.
7  */
8
9 #include <stdio.h>
10 #include <stdlib.h>
11
12 #include "hash.h"
13 #include "keydb.h"
14 #include "keystructs.h"
15 #include "ll.h"
16 #include "onak-conf.h"
17 #include "stats.h"
18
19 unsigned long countdegree(struct stats_key *have, int maxdegree)
20 {
21         unsigned long count = 0, curdegree = 0;
22         struct ll *curll, *nextll, *sigll, *tmp;
23
24         ++curdegree;
25
26         nextll = NULL;
27         curll = lladd(NULL, have);
28
29         while (curll != NULL && curdegree <= maxdegree) {
30                 sigll = cached_getkeysigs(((struct stats_key *)
31                                 curll->object)->keyid);
32                 while (sigll != NULL) {
33                         if (((struct stats_key *) sigll->object)->colour==0) {
34                                 /* We've never seen it. Count it, mark it and
35                                         explore its subtree */
36                                 count++;
37                                 ((struct stats_key *)sigll->object)->colour = 
38                                         curdegree;
39                                 ((struct stats_key *)sigll->object)->parent = 
40                                         ((struct stats_key *)
41                                          curll->object)->keyid;
42                                 nextll=lladd(nextll, sigll->object);
43                         }
44                         sigll = sigll->next;
45                 }
46                 tmp = curll->next;
47                 free(curll);
48                 curll = tmp;
49                 if (curll == NULL) {
50                         curll = nextll;
51                         nextll = NULL;
52                         ++curdegree;
53                 };
54         }
55         if (curll != NULL) {
56                 llfree(curll, NULL);
57                 curll = NULL;
58         }
59         if (nextll != NULL) {
60                 llfree(nextll, NULL);
61                 nextll = NULL;
62         }
63
64         return count;
65 }
66
67 void sixdegrees(uint64_t keyid)
68 {
69         struct stats_key *keyinfo;
70         int loop;
71         long degree;
72         char *uid;
73
74         cached_getkeysigs(keyid);
75
76         if ((keyinfo = findinhash(keyid)) == NULL) {
77                 printf("Couldn't find key 0x%llX.\n", keyid);
78                 return;
79         }
80
81         uid = keyid2uid(keyinfo->keyid);
82         printf("Six degrees for 0x%llX (%s):\n", keyinfo->keyid, uid);
83         free(uid);
84         uid = NULL;
85
86         puts("\t\tSigned by");
87         for (loop = 1; loop < 7; loop++) {
88                 initcolour(false);
89                 degree = countdegree(keyinfo, loop);
90                 printf("Degree %d:\t%8ld\n", loop, degree);
91                 /*
92                  * TODO: Used to have keys we signed as well but this takes a
93                  * lot of resource and isn't quite appropriate for something
94                  * intended to be run on the fly. Given this isn't a CGI at
95                  * present perhaps should be readded.
96                  */
97         }
98 }
99
100 int main(int argc, char *argv[])
101 {
102         uint64_t keyid = 0x5B430367;
103
104         if (argc == 2) {
105                 keyid = strtoll(argv[1], NULL, 16);
106         }
107
108         readconfig();
109         initdb();
110         inithash();
111         sixdegrees(keyid);
112         destroyhash();
113         cleanupdb();
114         cleanupconfig();
115
116         return 0;
117 }