]>
Commit | Line | Data |
---|---|---|
1 | #include "../nterfacer/nterfacer.h" | |
2 | #include "../lib/strlfunc.h" | |
3 | #include "../core/nsmalloc.h" | |
4 | #include "trusts.h" | |
5 | #include <stdio.h> | |
6 | #include <string.h> | |
7 | ||
8 | #define Stringify(x) __Stringify(x) | |
9 | #define __Stringify(x) #x | |
10 | ||
11 | static void tm_trustdump(trustmigration *tm); | |
12 | ||
13 | static void tm_fini(trustmigration *tm, int errcode) { | |
14 | tm->fini(tm->tag, errcode); | |
15 | ||
16 | if(tm->schedule) { | |
17 | nterfacer_freeline(tm->schedule); | |
18 | tm->schedule = NULL; | |
19 | } | |
20 | ||
21 | nsfree(POOL_TRUSTS, tm); | |
22 | } | |
23 | ||
24 | void migration_stop(trustmigration *tm) { | |
25 | tm_fini(tm, MIGRATION_STOPPED); | |
26 | } | |
27 | ||
28 | static void tm_stage2(int failure, int linec, char **linev, void *tag) { | |
29 | trustmigration *tm = tag; | |
30 | char *finishline; | |
31 | unsigned int groupcount, totallines, i, dummy; | |
32 | ||
33 | #ifdef TRUSTS_MIGRATION_DEBUG | |
34 | Error("trusts", ERR_INFO, "Migration total lines: %d", linec); | |
35 | ||
36 | for(i=0;i<linec;i++) | |
37 | Error("trusts", ERR_INFO, "Migration line %d: |%s|", i, linev[i]); | |
38 | #endif | |
39 | ||
40 | tm->schedule = NULL; | |
41 | if(failure || (linec < 1)) { | |
42 | tm_fini(tm, 7); | |
43 | return; | |
44 | } | |
45 | ||
46 | finishline = linev[linec - 1]; | |
47 | if(sscanf(finishline, "Start ID cannot exceed current maximum group ID (#%u).", &dummy) == 1) { | |
48 | /* the list was truncated while we were reading it, we're done! */ | |
49 | tm_fini(tm, 0); | |
50 | return; | |
51 | } | |
52 | ||
53 | if(sscanf(finishline, "End of list, %u groups and %u lines returned.", &groupcount, &totallines) != 2) { | |
54 | tm_fini(tm, 8); | |
55 | return; | |
56 | } | |
57 | ||
58 | if(totallines != linec - 1) { | |
59 | tm_fini(tm, 9); | |
60 | return; | |
61 | } | |
62 | ||
63 | for(i=0;i<linec-1;i++) { | |
64 | char *linestart = &linev[i][2], type = linev[i][0]; | |
65 | if(type == 'G') { | |
66 | trustgroup tg; | |
67 | ||
68 | if(!parsetg(linestart, &tg, 1)) { | |
69 | tm_fini(tm, 150); | |
70 | return; | |
71 | } | |
72 | ||
73 | if(tg.id >= tm->cur) | |
74 | tm->group(tm->tag, &tg); | |
75 | ||
76 | freesstring(tg.name); | |
77 | freesstring(tg.createdby); | |
78 | freesstring(tg.contact); | |
79 | freesstring(tg.comment); | |
80 | ||
81 | if(tg.id < tm->cur) { | |
82 | tm_fini(tm, 11); | |
83 | return; | |
84 | } | |
85 | ||
86 | if(tg.id > tm->cur) | |
87 | tm->cur = tg.id; | |
88 | } else if (type == 'H') { | |
89 | trusthost th; | |
90 | unsigned int groupid; | |
91 | ||
92 | if(!parseth(linestart, &th, &groupid, 1)) { | |
93 | tm_fini(tm, 151); | |
94 | return; | |
95 | } | |
96 | ||
97 | if(groupid < tm->cur) { | |
98 | tm_fini(tm, 11); | |
99 | return; | |
100 | } | |
101 | ||
102 | if(groupid > tm->cur) | |
103 | tm->cur = groupid; | |
104 | ||
105 | tm->host(tm->tag, &th, groupid); | |
106 | } else { | |
107 | tm_fini(tm, 11); | |
108 | return; | |
109 | } | |
110 | } | |
111 | ||
112 | tm_trustdump(tm); | |
113 | } | |
114 | ||
115 | static void tm_trustdump(trustmigration *tm) { | |
116 | char buf[100]; | |
117 | ||
118 | if(tm->cur >= tm->count) { | |
119 | tm_fini(tm, 0); | |
120 | return; | |
121 | } | |
122 | ||
123 | tm->cur++; | |
124 | ||
125 | snprintf(buf, sizeof(buf), "trustdump #%d 1", tm->cur); | |
126 | tm->schedule = nterfacer_sendline("R", "relay", 4, (char *[]){"2", "^(Start ID cannot exceed current maximum group ID \\(#\\d+\\)|End of list, 1 groups and \\d+ lines returned\\.)$", "O", buf}, tm_stage2, tm); | |
127 | } | |
128 | ||
129 | static void tm_stage1(int failure, int linec, char **linev, void *tag) { | |
130 | int count; | |
131 | trustmigration *tm = tag; | |
132 | ||
133 | tm->schedule = NULL; | |
134 | ||
135 | if(failure || (linec != 1)) { | |
136 | tm_fini(tm, 12); | |
137 | return; | |
138 | } | |
139 | ||
140 | if(sscanf(linev[0], "Start ID cannot exceed current maximum group ID (#%u).", &count) != 1) { | |
141 | tm_fini(tm, 13); | |
142 | return; | |
143 | } | |
144 | ||
145 | Error("trusts", ERR_INFO, "Migration in progress, total groups: %d", count); | |
146 | ||
147 | tm->count = count; | |
148 | ||
149 | tm_trustdump(tm); | |
150 | } | |
151 | ||
152 | trustmigration *migration_start(TrustMigrationGroup group, TrustMigrationHost host, TrustMigrationFini fini, void *tag) { | |
153 | trustmigration *tm = nsmalloc(POOL_TRUSTS, sizeof(trustmigration)); | |
154 | if(!tm) | |
155 | return NULL; | |
156 | ||
157 | tm->group = group; | |
158 | tm->host = host; | |
159 | tm->fini = fini; | |
160 | tm->count = 0; | |
161 | tm->cur = 0; | |
162 | tm->tag = tag; | |
163 | ||
164 | tm->schedule = nterfacer_sendline("R", "relay", 4, (char *[]){"1", "1", "O", "trustdump #9999999 1"}, tm_stage1, tm); | |
165 | if(!tm->schedule) { | |
166 | nsfree(POOL_TRUSTS, tm); | |
167 | return NULL; | |
168 | } | |
169 | ||
170 | return tm; | |
171 | } |