chiark / gitweb /
4ca53cd75eaed2aeb3548a7f3716f99ebe3d628c
[secnet.git] / site.c
1 /* site.c - manage communication with a remote network site */
2
3 #include <stdio.h>
4 #include <sys/mman.h>
5
6 #include "secnet.h"
7 #include "util.h"
8 #include "unaligned.h"
9
10 #define SETUP_BUFFER_LEN 2048
11
12 #define DEFAULT_KEY_LIFETIME 3600000
13 #define DEFAULT_SETUP_RETRIES 5
14 #define DEFAULT_SETUP_TIMEOUT 1000
15 #define DEFAULT_WAIT_TIME 10000
16
17 /* Each site can be in one of several possible states. */
18
19 /* States:
20    SITE_STOP         - nothing is allowed to happen; tunnel is down;
21                        all session keys have been erased
22      -> SITE_RUN upon external instruction
23    SITE_RUN          - site up, maybe with valid key
24      -> SITE_RESOLVE upon outgoing packet and no valid key
25          we start name resolution for the other end of the tunnel
26      -> SITE_SENTMSG2 upon valid incoming message 1 and suitable time
27          we send an appropriate message 2
28    SITE_RESOLVE      - waiting for name resolution
29      -> SITE_SENTMSG1 upon successful resolution
30          we send an appropriate message 1
31      -> SITE_SENTMSG2 upon valid incoming message 1 (then abort resolution)
32          we abort resolution and 
33      -> SITE_WAIT on timeout or resolution failure
34    SITE_SENTMSG1
35      -> SITE_SENTMSG2 upon valid incoming message 1 from higher priority end
36      -> SITE_SENTMSG3 upon valid incoming message 2
37      -> SITE_WAIT on timeout
38    SITE_SENTMSG2
39      -> SITE_SENTMSG4 upon valid incoming message 3
40      -> SITE_WAIT on timeout
41    SITE_SENTMSG3
42      -> SITE_SENTMSG5 upon valid incoming message 4
43      -> SITE_WAIT on timeout
44    SITE_SENTMSG4
45      -> SITE_RUN upon valid incoming message 5
46      -> SITE_WAIT on timeout
47    SITE_SENTMSG5
48      -> SITE_RUN upon valid incoming message 6
49      -> SITE_WAIT on timeout
50    SITE_WAIT         - failed to establish key; do nothing for a while
51      -> SITE_RUN on timeout
52    */
53
54 #define SITE_STOP     0
55 #define SITE_RUN      1
56 #define SITE_RESOLVE  2
57 #define SITE_SENTMSG1 3
58 #define SITE_SENTMSG2 4
59 #define SITE_SENTMSG3 5
60 #define SITE_SENTMSG4 6
61 #define SITE_SENTMSG5 7
62 #define SITE_WAIT     8
63
64 static string_t state_name(uint32_t state)
65 {
66     switch (state) {
67     case 0: return "SITE_STOP";
68     case 1: return "SITE_RUN";
69     case 2: return "SITE_RESOLVE";
70     case 3: return "SITE_SENTMSG1";
71     case 4: return "SITE_SENTMSG2";
72     case 5: return "SITE_SENTMSG3";
73     case 6: return "SITE_SENTMSG4";
74     case 7: return "SITE_SENTMSG5";
75     case 8: return "SITE_WAIT";
76     default: return "*bad state*";
77     }
78 }
79
80 #define LABEL_MSG0 0x00020200
81 #define LABEL_MSG1 0x01010101
82 #define LABEL_MSG2 0x02020202
83 #define LABEL_MSG3 0x03030303
84 #define LABEL_MSG4 0x04040404
85 #define LABEL_MSG5 0x05050505
86 #define LABEL_MSG6 0x06060606
87 #define LABEL_MSG7 0x07070707
88 #define LABEL_MSG8 0x08080808
89 #define LABEL_MSG9 0x09090909
90
91 #define NONCELEN 8
92
93 #define LOG_UNEXPECTED    0x00000001
94 #define LOG_SETUP_INIT    0x00000002
95 #define LOG_SETUP_TIMEOUT 0x00000004
96 #define LOG_ACTIVATE_KEY  0x00000008
97 #define LOG_TIMEOUT_KEY   0x00000010
98 #define LOG_SEC      0x00000020
99 #define LOG_STATE         0x00000040
100 #define LOG_DROP          0x00000080
101 #define LOG_DUMP          0x00000100
102 #define LOG_ERROR         0x00000400
103
104 struct site {
105     closure_t cl;
106     struct site_if ops;
107 /* configuration information */
108     string_t localname;
109     string_t remotename;
110     string_t tunname; /* localname<->remotename by default */
111     string_t address; /* DNS name for bootstrapping, optional */
112     int remoteport;
113     struct netlink_if *netlink;
114     struct comm_if *comm;
115     struct resolver_if *resolver;
116     struct log_if *log;
117     struct random_if *random;
118     struct rsaprivkey_if *privkey;
119     struct subnet_list remotenets;
120     struct rsapubkey_if *pubkey;
121     struct transform_if *transform;
122     struct dh_if *dh;
123     struct hash_if *hash;
124     void *netlink_cid;
125
126     uint32_t setup_retries; /* How many times to send setup packets */
127     uint32_t setup_timeout; /* Initial timeout for setup packets */
128     uint32_t wait_timeout; /* How long to wait if setup unsuccessful */
129     uint32_t key_lifetime; /* How long a key lasts once set up */
130
131     uint8_t *setupsig; /* Expected signature of incoming MSG1 packets */
132     uint32_t setupsiglen; /* Allows us to discard packets quickly if
133                              they are not for us */
134     bool_t setup_priority; /* Do we have precedence if both sites emit
135                               message 1 simultaneously? */
136     uint32_t log_events;
137
138 /* runtime information */
139     uint32_t state;
140     uint64_t now; /* Most recently seen time */
141
142     uint32_t remote_session_id;
143     struct transform_inst_if *current_transform;
144     bool_t current_valid;
145     uint64_t current_key_timeout; /* End of life of current key */
146     struct sockaddr_in peer; /* Current address of peer */
147     bool_t peer_valid; /* Peer address becomes invalid when key times out,
148                           but only if we have a DNS name for our peer */
149
150     uint32_t setup_session_id;
151     struct sockaddr_in setup_peer;
152     uint8_t localN[NONCELEN]; /* Nonces for key exchange */
153     uint8_t remoteN[NONCELEN];
154     struct buffer_if buffer; /* Current outgoing key exchange packet */
155     uint32_t retries; /* Number of retries remaining */
156     uint64_t timeout; /* Timeout for current state */
157     uint8_t *dhsecret;
158     uint8_t *sharedsecret;
159
160     struct transform_inst_if *new_transform; /* For key setup/verify */
161 };
162
163 static void slog(struct site *st, uint32_t event, string_t msg, ...)
164 {
165     va_list ap;
166     uint8_t buf[240];
167
168     va_start(ap,msg);
169
170     if (event&st->log_events) {
171         vsnprintf(buf,240,msg,ap);
172         st->log->log(st->log->st,0,"%s: %s",st->tunname,buf);
173     }
174     va_end(ap);
175 }
176
177 static void enter_state_run(struct site *st);
178 static bool_t enter_state_resolve(struct site *st);
179 static bool_t enter_state_sentmsg1(struct site *st);
180 static bool_t enter_state_sentmsg2(struct site *st);
181 static bool_t enter_state_sentmsg3(struct site *st);
182 static bool_t enter_state_sentmsg4(struct site *st);
183 static bool_t enter_state_sentmsg5(struct site *st);
184 static void enter_state_wait(struct site *st);
185
186 #define CHECK_AVAIL(b,l) do { if ((b)->size<(l)) return False; } while(0)
187 #define CHECK_EMPTY(b) do { if ((b)->size!=0) return False; } while(0)
188 #define CHECK_TYPE(b,t) do { uint32_t type; \
189     CHECK_AVAIL((b),4); \
190     type=buf_unprepend_uint32((b)); \
191     if (type!=(t)) return False; } while(0)
192
193 struct msg {
194     uint8_t *hashstart;
195     uint32_t dest;
196     uint32_t source;
197     uint32_t remlen;
198     uint8_t *remote;
199     uint32_t loclen;
200     uint8_t *local;
201     uint8_t *nR;
202     uint8_t *nL;
203     uint32_t pklen;
204     uint8_t *pk;
205     uint32_t hashlen;
206     uint32_t siglen;
207     uint8_t *sig;
208 };
209
210 /* Build any of msg1 to msg4. msg5 and msg6 are built from the inside out
211    using a transform. */
212 static bool_t generate_msg(struct site *st, uint32_t type, string_t what)
213 {
214     void *hst;
215     uint8_t *hash=alloca(st->hash->len);
216     string_t dhpub, sig;
217
218     st->retries=st->setup_retries;
219     BUF_ALLOC(&st->buffer,what);
220     buffer_init(&st->buffer,0);
221     buf_append_uint32(&st->buffer,
222         (type==LABEL_MSG1?0:st->setup_session_id));
223     buf_append_uint32(&st->buffer,(uint32_t)st);
224     buf_append_uint32(&st->buffer,type);
225     buf_append_string(&st->buffer,st->localname);
226     buf_append_string(&st->buffer,st->remotename);
227     memcpy(buf_append(&st->buffer,NONCELEN),st->localN,NONCELEN);
228     if (type==LABEL_MSG1) return True;
229     memcpy(buf_append(&st->buffer,NONCELEN),st->remoteN,NONCELEN);
230     if (type==LABEL_MSG2) return True;
231     dhpub=st->dh->makepublic(st->dh->st,st->dhsecret,st->dh->len);
232     buf_append_string(&st->buffer,dhpub);
233     free(dhpub);
234     hst=st->hash->init();
235     st->hash->update(hst,st->buffer.start,st->buffer.size);
236     st->hash->final(hst,hash);
237     sig=st->privkey->sign(st->privkey->st,hash,st->hash->len);
238     buf_append_string(&st->buffer,sig);
239     free(sig);
240     return True;
241 }
242
243 static bool_t unpick_msg(struct site *st, uint32_t type,
244                          struct buffer_if *msg, struct msg *m)
245 {
246     m->hashstart=msg->start;
247     CHECK_AVAIL(msg,4);
248     m->dest=buf_unprepend_uint32(msg);
249     CHECK_AVAIL(msg,4);
250     m->source=buf_unprepend_uint32(msg);
251     CHECK_TYPE(msg,type);
252     CHECK_AVAIL(msg,2);
253     m->remlen=buf_unprepend_uint16(msg);
254     CHECK_AVAIL(msg,m->remlen);
255     m->remote=buf_unprepend(msg,m->remlen);
256     CHECK_AVAIL(msg,2);
257     m->loclen=buf_unprepend_uint16(msg);
258     CHECK_AVAIL(msg,m->loclen);
259     m->local=buf_unprepend(msg,m->loclen);
260     CHECK_AVAIL(msg,NONCELEN);
261     m->nR=buf_unprepend(msg,NONCELEN);
262     if (type==LABEL_MSG1) {
263         CHECK_EMPTY(msg);
264         return True;
265     }
266     CHECK_AVAIL(msg,NONCELEN);
267     m->nL=buf_unprepend(msg,NONCELEN);
268     if (type==LABEL_MSG2) {
269         CHECK_EMPTY(msg);
270         return True;
271     }
272     CHECK_AVAIL(msg,2);
273     m->pklen=buf_unprepend_uint16(msg);
274     CHECK_AVAIL(msg,m->pklen);
275     m->pk=buf_unprepend(msg,m->pklen);
276     m->hashlen=msg->start-m->hashstart;
277     CHECK_AVAIL(msg,2);
278     m->siglen=buf_unprepend_uint16(msg);
279     CHECK_AVAIL(msg,m->siglen);
280     m->sig=buf_unprepend(msg,m->siglen);
281     CHECK_EMPTY(msg);
282     return True;
283 }
284
285 static bool_t generate_msg1(struct site *st)
286 {
287     st->random->generate(st->random->st,NONCELEN,st->localN);
288     return generate_msg(st,LABEL_MSG1,"site:MSG1");
289 }
290
291 static bool_t process_msg1(struct site *st, struct buffer_if *msg1,
292                            struct sockaddr_in *src)
293 {
294     struct msg m;
295
296     /* We've already determined we're in an appropriate state to
297        process an incoming MSG1, and that the MSG1 has correct values
298        of A and B. */
299
300     if (!unpick_msg(st,LABEL_MSG1,msg1,&m)) return False;
301
302     /* XXX save src as our peer address here? */
303     st->setup_peer=*src;
304
305     st->setup_session_id=m.source;
306     memcpy(st->remoteN,m.nR,NONCELEN);
307     return True;
308 }
309
310 static bool_t generate_msg2(struct site *st)
311 {
312     st->random->generate(st->random->st,NONCELEN,st->localN);
313     return generate_msg(st,LABEL_MSG2,"site:MSG2");
314 }
315
316 static bool_t process_msg2(struct site *st, struct buffer_if *msg2,
317                            struct sockaddr_in *src)
318 {
319     struct msg m;
320
321     if (!unpick_msg(st,LABEL_MSG2,msg2,&m)) return False;
322
323     /* Check that the site names and our nonce have been sent
324        back correctly, and then store our peer's nonce. */ 
325     if (memcmp(m.remote,st->remotename,strlen(st->remotename)!=0)) {
326         slog(st,LOG_SEC,"msg2: bad B (remote site name)");
327         return False;
328     }
329     if (memcmp(m.local,st->localname,strlen(st->localname)!=0)) {
330         slog(st,LOG_SEC,"msg2: bad A (local site name)");
331         return False;
332     }
333     if (memcmp(m.nL,st->localN,NONCELEN)!=0) {
334         slog(st,LOG_SEC,"msg2: bad nA (locally generated nonce)");
335         return False;
336     }
337     st->setup_session_id=m.source;
338     memcpy(st->remoteN,m.nR,NONCELEN);
339     return True;
340 }
341
342 static bool_t generate_msg3(struct site *st)
343 {
344     /* Now we have our nonce and their nonce. Think of a secret key,
345        and create message number 3. */
346     st->random->generate(st->random->st,st->dh->len,st->dhsecret);
347     return generate_msg(st,LABEL_MSG3,"site:MSG3");
348 }
349
350 static bool_t process_msg3(struct site *st, struct buffer_if *msg3,
351                            struct sockaddr_in *src)
352 {
353     struct msg m;
354     uint8_t *hash=alloca(st->hash->len);
355     void *hst;
356
357     if (!unpick_msg(st,LABEL_MSG3,msg3,&m)) return False;
358
359     /* Check that the site names and nonces have been sent back
360        correctly */
361     if (memcmp(m.remote,st->remotename,strlen(st->remotename)!=0)) {
362         slog(st,LOG_SEC,"msg3: bad A (remote site name)");
363         return False;
364     }
365     if (memcmp(m.local,st->localname,strlen(st->localname)!=0)) {
366         slog(st,LOG_SEC,"msg3: bad B (local site name)");
367         return False;
368     }
369     if (memcmp(m.nR,st->remoteN,NONCELEN)!=0) {
370         slog(st,LOG_SEC,"msg3: bad nA (remotely generated nonce)");
371         return False;
372     }
373     if (memcmp(m.nL,st->localN,NONCELEN)!=0) {
374         slog(st,LOG_SEC,"msg3: bad nB (locally generated nonce)");
375         return False;
376     }
377     
378     /* Check signature and store g^x mod m */
379     hst=st->hash->init();
380     st->hash->update(hst,m.hashstart,m.hashlen);
381     st->hash->final(hst,hash);
382     /* Terminate signature with a '0' - cheating, but should be ok */
383     m.sig[m.siglen]=0;
384     if (!st->pubkey->check(st->pubkey->st,hash,st->hash->len,m.sig)) {
385         slog(st,LOG_SEC,"msg3 signature failed check!");
386         return False;
387     }
388
389     /* Terminate their DH public key with a '0' */
390     m.pk[m.pklen]=0;
391     /* Invent our DH secret key */
392     st->random->generate(st->random->st,st->dh->len,st->dhsecret);
393
394     /* Generate the shared key */
395     st->dh->makeshared(st->dh->st,st->dhsecret,st->dh->len,m.pk,
396                        st->sharedsecret,st->transform->keylen);
397
398     /* Set up the transform */
399     st->new_transform->setkey(st->new_transform->st,st->sharedsecret,
400                               st->transform->keylen);
401
402     return True;
403 }
404
405 static bool_t generate_msg4(struct site *st)
406 {
407     /* We have both nonces, their public key and our private key. Generate
408        our public key, sign it and send it to them. */
409     return generate_msg(st,LABEL_MSG4,"site:MSG4");
410 }
411
412 static bool_t process_msg4(struct site *st, struct buffer_if *msg4,
413                            struct sockaddr_in *src)
414 {
415     struct msg m;
416     uint8_t *hash=alloca(st->hash->len);
417     void *hst;
418
419     if (!unpick_msg(st,LABEL_MSG4,msg4,&m)) return False;
420
421     /* Check that the site names and nonces have been sent back
422        correctly */
423     if (memcmp(m.remote,st->remotename,strlen(st->remotename)!=0)) {
424         slog(st,LOG_SEC,"msg4: bad B (remote site name)");
425         return False;
426     }
427     if (memcmp(m.local,st->localname,strlen(st->localname)!=0)) {
428         slog(st,LOG_SEC,"msg4: bad A (local site name)");
429         return False;
430     }
431     if (memcmp(m.nR,st->remoteN,NONCELEN)!=0) {
432         slog(st,LOG_SEC,"msg4: bad nB (remotely generated nonce)");
433         return False;
434     }
435     if (memcmp(m.nL,st->localN,NONCELEN)!=0) {
436         slog(st,LOG_SEC,"msg4: bad nA (locally generated nonce)");
437         return False;
438     }
439     
440     /* Check signature and store g^x mod m */
441     hst=st->hash->init();
442     st->hash->update(hst,m.hashstart,m.hashlen);
443     st->hash->final(hst,hash);
444     /* Terminate signature with a '0' - cheating, but should be ok */
445     m.sig[m.siglen]=0;
446     if (!st->pubkey->check(st->pubkey->st,hash,st->hash->len,m.sig)) {
447         slog(st,LOG_SEC,"msg4 signature failed check!");
448         return False;
449     }
450
451     /* Terminate their DH public key with a '0' */
452     m.pk[m.pklen]=0;
453     /* Generate the shared key */
454     st->dh->makeshared(st->dh->st,st->dhsecret,st->dh->len,m.pk,
455                        st->sharedsecret,st->transform->keylen);
456     /* Set up the transform */
457     st->new_transform->setkey(st->new_transform->st,st->sharedsecret,
458                               st->transform->keylen);
459
460     return True;
461 }
462
463 static bool_t generate_msg5(struct site *st)
464 {
465     string_t transform_err;
466
467     BUF_ALLOC(&st->buffer,"site:MSG5");
468     /* We are going to add three words to the transformed message */
469     buffer_init(&st->buffer,st->transform->max_start_pad+(4*3));
470     buf_append_uint32(&st->buffer,LABEL_MSG5);
471     st->new_transform->forwards(st->new_transform->st,&st->buffer,
472                                 &transform_err);
473     buf_prepend_uint32(&st->buffer,LABEL_MSG5);
474     buf_prepend_uint32(&st->buffer,(uint32_t)st);
475     buf_prepend_uint32(&st->buffer,st->setup_session_id);
476
477     st->retries=st->setup_retries;
478     return True;
479 }
480
481 struct msg0 {
482     uint32_t dest;
483     uint32_t source;
484     uint32_t type;
485 };
486
487 static bool_t unpick_msg0(struct site *st, struct buffer_if *msg0,
488                           struct msg0 *m)
489 {
490     CHECK_AVAIL(msg0,4);
491     m->dest=buf_unprepend_uint32(msg0);
492     CHECK_AVAIL(msg0,4);
493     m->source=buf_unprepend_uint32(msg0);
494     CHECK_AVAIL(msg0,4);
495     m->type=buf_unprepend_uint32(msg0);
496     return True;
497     /* Leaves transformed part of buffer untouched */
498 }
499
500 static bool_t process_msg5(struct site *st, struct buffer_if *msg5,
501                            struct sockaddr_in *src)
502 {
503     struct msg0 m;
504     string_t transform_err;
505
506     if (!unpick_msg0(st,msg5,&m)) return False;
507
508     if (st->new_transform->reverse(st->new_transform->st,
509                                    msg5,&transform_err)) {
510         /* There's a problem */
511         slog(st,LOG_SEC,"process_msg5: transform: %s",transform_err);
512         return False;
513     }
514     /* Buffer should now contain untransformed PING packet data */
515     CHECK_AVAIL(msg5,4);
516     if (buf_unprepend_uint32(msg5)!=LABEL_MSG5) {
517         slog(st,LOG_SEC,"MSG5/PING packet contained invalid data");
518         return False;
519     }
520     CHECK_EMPTY(msg5);
521     return True;
522 }
523
524 static bool_t generate_msg6(struct site *st)
525 {
526     string_t transform_err;
527
528     BUF_ALLOC(&st->buffer,"site:MSG6");
529     /* We are going to add three words to the transformed message */
530     buffer_init(&st->buffer,st->transform->max_start_pad+(4*3));
531     buf_append_uint32(&st->buffer,LABEL_MSG6);
532     st->new_transform->forwards(st->new_transform->st,&st->buffer,
533                                 &transform_err);
534     buf_prepend_uint32(&st->buffer,LABEL_MSG6);
535     buf_prepend_uint32(&st->buffer,(uint32_t)st);
536     buf_prepend_uint32(&st->buffer,st->setup_session_id);
537
538     st->retries=1; /* Peer will retransmit MSG5 if necessary */
539     return True;
540 }
541
542 static bool_t process_msg6(struct site *st, struct buffer_if *msg6,
543                            struct sockaddr_in *src)
544 {
545     struct msg0 m;
546     string_t transform_err;
547
548     if (!unpick_msg0(st,msg6,&m)) return False;
549
550     if (st->new_transform->reverse(st->new_transform->st,
551                                    msg6,&transform_err)) {
552         /* There's a problem */
553         slog(st,LOG_SEC,"process_msg6: transform: %s",transform_err);
554         return False;
555     }
556     /* Buffer should now contain untransformed PING packet data */
557     CHECK_AVAIL(msg6,4);
558     if (buf_unprepend_uint32(msg6)!=LABEL_MSG6) {
559         slog(st,LOG_SEC,"MSG6/PONG packet contained invalid data");
560         return False;
561     }
562     CHECK_EMPTY(msg6);
563     return True;
564 }
565
566 static bool_t process_msg0(struct site *st, struct buffer_if *msg0,
567                            struct sockaddr_in *src)
568 {
569     struct msg0 m;
570     string_t transform_err;
571     uint32_t type;
572
573     if (!st->current_valid) {
574         slog(st,LOG_DROP,"incoming message but no current key -> dropping");
575         if (st->state==SITE_RUN) {
576             slog(st,LOG_SETUP_INIT|LOG_STATE,
577                  "now initiating setup of new key");
578             return enter_state_resolve(st);
579         }
580         return False;
581     }
582
583     if (!unpick_msg0(st,msg0,&m)) return False;
584
585     if (st->current_transform->reverse(st->current_transform->st,
586                                        msg0,&transform_err)) {
587         /* There's a problem */
588         slog(st,LOG_SEC,"transform: %s",transform_err);
589         return False;
590     }
591     CHECK_AVAIL(msg0,4);
592     type=buf_unprepend_uint32(msg0);
593     switch(type) {
594     case LABEL_MSG9:
595         /* Deliver to netlink layer */
596         st->netlink->deliver(st->netlink->st,st->netlink_cid,msg0);
597         return True;
598         break;
599     default:
600         slog(st,LOG_SEC,"incoming message of type %08x (unknown)",type);
601         break;
602     }
603     return False;
604 }
605
606 static void dump_packet(struct site *st, struct buffer_if *buf,
607                         struct sockaddr_in *addr, bool_t incoming)
608 {
609     uint32_t dest=ntohl(*(uint32_t *)buf->start);
610     uint32_t source=ntohl(*(uint32_t *)(buf->start+4));
611     uint32_t msgtype=ntohl(*(uint32_t *)(buf->start+8));
612
613     if (st->log_events & LOG_DUMP)
614         log(st->log,0,"(%s,%s): %s: %08x<-%08x: %08x:",
615             st->localname,st->remotename,incoming?"incoming":"outgoing",
616             dest,source,msgtype);
617 }
618
619 static uint32_t site_status(void *st)
620 {
621     return 0;
622 }
623
624 static bool_t send_msg(struct site *st)
625 {
626     if (st->retries>0) {
627         dump_packet(st,&st->buffer,&st->setup_peer,False);
628         st->comm->sendmsg(st->comm->st,&st->buffer,&st->setup_peer);
629         st->timeout=st->now+st->setup_timeout;
630         st->retries--;
631         return True;
632     } else {
633         slog(st,LOG_SETUP_TIMEOUT,"timed out sending key setup packet");
634         enter_state_wait(st);
635         return False;
636     }
637 }
638
639 static void site_resolve_callback(void *sst, struct in_addr *address)
640 {
641     struct site *st=sst;
642
643     if (st->state!=SITE_RESOLVE) {
644         slog(st,LOG_UNEXPECTED,"site_resolve_callback called unexpectedly");
645         return;
646     }
647     if (address) {
648         memset(&st->setup_peer,0,sizeof(st->setup_peer));
649         st->setup_peer.sin_family=AF_INET;
650         st->setup_peer.sin_port=htons(st->remoteport);
651         st->setup_peer.sin_addr=*address;
652         enter_state_sentmsg1(st);
653     } else {
654         /* Resolution failed */
655         slog(st,LOG_ERROR,"resolution of %s failed",st->address);
656         enter_state_run(st);
657     }
658 }
659
660 static void activate_new_key(struct site *st)
661 {
662     struct transform_inst_if *t;
663
664     t=st->current_transform;
665     st->current_transform=st->new_transform;
666     st->new_transform=t;
667
668     t->delkey(t->st);
669     st->state=SITE_RUN;
670     st->timeout=0;
671     st->current_valid=True;
672     st->current_key_timeout=st->now+st->key_lifetime;
673     st->peer=st->setup_peer;
674     st->peer_valid=True;
675     st->remote_session_id=st->setup_session_id;
676
677     slog(st,LOG_ACTIVATE_KEY,"new key activated");
678 }
679
680 static void state_assert(struct site *st, bool_t ok)
681 {
682     if (!ok) fatal("state_assert\n");
683 }
684
685 static void enter_state_stop(struct site *st)
686 {
687     st->state=SITE_STOP;
688     st->timeout=0;
689     st->current_transform->delkey(st->current_transform->st);
690     st->current_valid=False;
691     st->current_key_timeout=0;
692     
693     st->peer_valid=False;
694     
695     st->new_transform->delkey(st->new_transform->st);
696 }
697
698 static void enter_state_run(struct site *st)
699 {
700     slog(st,LOG_STATE,"entering state RUN");
701     st->state=SITE_RUN;
702     st->timeout=0;
703     st->netlink->set_delivery(st->netlink->st,st->netlink_cid,True);
704     /* XXX get rid of key setup data */
705 }
706
707 static bool_t enter_state_resolve(struct site *st)
708 {
709     state_assert(st,st->state==SITE_RUN);
710     slog(st,LOG_STATE,"entering state RESOLVE");
711     st->state=SITE_RESOLVE;
712     st->resolver->request(st->resolver->st,st->address,
713                           site_resolve_callback,st);
714     return True;
715 }
716
717 static bool_t enter_state_sentmsg1(struct site *st)
718 {
719     state_assert(st,st->state==SITE_RUN || st->state==SITE_RESOLVE);
720     slog(st,LOG_STATE,"entering state SENTMSG1");
721     if (generate_msg1(st) && send_msg(st)) {
722         st->state=SITE_SENTMSG1;
723         return True;
724     }
725     slog(st,LOG_ERROR,"error entering state SENTMSG1");
726     st->buffer.free=False; /* Can't tell which it was, but enter_state_wait()
727                               will do a BUF_FREE() */
728     enter_state_wait(st);
729     return False;
730 }
731
732 static bool_t enter_state_sentmsg2(struct site *st)
733 {
734     state_assert(st,st->state==SITE_RUN || st->state==SITE_RESOLVE ||
735                  st->state==SITE_SENTMSG1 || st->state==SITE_WAIT);
736     slog(st,LOG_STATE,"entering state SENTMSG2");
737     if (generate_msg2(st) && send_msg(st)) {
738         st->state=SITE_SENTMSG2;
739         return True;
740     }
741     slog(st,LOG_ERROR,"error entering state SENTMSG2");
742     st->buffer.free=False;
743     enter_state_wait(st);
744     return False;
745 }
746
747 static bool_t enter_state_sentmsg3(struct site *st)
748 {
749     state_assert(st,st->state==SITE_SENTMSG1);
750     slog(st,LOG_STATE,"entering state SENTMSG3");
751     BUF_FREE(&st->buffer); /* Free message 1 */
752     if (generate_msg3(st) && send_msg(st)) {
753         st->state=SITE_SENTMSG3;
754         return True;
755     }
756     slog(st,LOG_ERROR,"error entering state SENTMSG3");
757     st->buffer.free=False;
758     enter_state_wait(st);
759     return False;
760 }
761
762 static bool_t enter_state_sentmsg4(struct site *st)
763 {
764     state_assert(st,st->state==SITE_SENTMSG2);
765     slog(st,LOG_STATE,"entering state SENTMSG4");
766     BUF_FREE(&st->buffer); /* Free message 2 */
767     if (generate_msg4(st) && send_msg(st)) {
768         st->state=SITE_SENTMSG4;
769         return True;
770     }
771     slog(st,LOG_ERROR,"error entering state SENTMSG4");
772     st->buffer.free=False;
773     enter_state_wait(st);
774     return False;
775 }
776
777 static bool_t enter_state_sentmsg5(struct site *st)
778 {
779     state_assert(st,st->state==SITE_SENTMSG3);
780     slog(st,LOG_STATE,"entering state SENTMSG5");
781     BUF_FREE(&st->buffer); /* Free message 3 */
782
783     if (generate_msg5(st) && send_msg(st)) {
784         st->state=SITE_SENTMSG5;
785         return True;
786     }
787     slog(st,LOG_ERROR,"error entering state SENTMSG5");
788     st->buffer.free=False;
789     enter_state_wait(st);
790     
791     return False;
792 }
793
794 static bool_t send_msg6(struct site *st)
795 {
796     state_assert(st,st->state==SITE_SENTMSG4);
797     slog(st,LOG_STATE,"entering state RUN after sending msg6");
798     BUF_FREE(&st->buffer); /* Free message 4 */
799     if (generate_msg6(st) && send_msg(st)) {
800         BUF_FREE(&st->buffer); /* Never reused */
801         st->timeout=0; /* Never retransmit */
802         activate_new_key(st);
803         return True;
804     }
805     slog(st,LOG_ERROR,"error entering state RUN after sending msg6");
806     st->buffer.free=False;
807     enter_state_wait(st);
808     return False;
809 }
810
811 /* We go into this state if our peer becomes uncommunicative. Similar to
812    the "stop" state, we forget all session keys for a while, before
813    re-entering the "run" state. */
814 static void enter_state_wait(struct site *st)
815 {
816     slog(st,LOG_STATE,"entering state WAIT");
817     st->timeout=st->now+st->wait_timeout;
818     st->state=SITE_WAIT;
819     st->peer_valid=False;
820     st->netlink->set_delivery(st->netlink->st,st->netlink_cid,False);
821     BUF_FREE(&st->buffer); /* will have had an outgoing packet in it */
822     /* XXX Erase keys etc. */
823 }
824
825 static int site_beforepoll(void *sst, struct pollfd *fds, int *nfds_io,
826                            int *timeout_io, const struct timeval *tv_now,
827                            uint64_t *now)
828 {
829     struct site *st=sst;
830
831     *nfds_io=0; /* We don't use any file descriptors */
832     st->now=*now;
833
834     /* Work out when our next timeout is. The earlier of 'timeout' or
835        'current_key_timeout'. A stored value of '0' indicates no timeout
836        active. */
837     if (st->timeout && st->timeout-*now < *timeout_io) {
838         *timeout_io=st->timeout-*now;
839     }
840
841     if (st->current_key_timeout && st->current_key_timeout-*now < *timeout_io)
842         *timeout_io=st->current_key_timeout-*now;
843
844     return 0; /* success */
845 }
846
847 /* NB site_afterpoll will be called before site_beforepoll is ever called */
848 static void site_afterpoll(void *sst, struct pollfd *fds, int nfds,
849                            const struct timeval *tv_now, uint64_t *now)
850 {
851     struct site *st=sst;
852
853     st->now=*now;
854     if (st->timeout && *now>st->timeout) {
855         /* Do stuff */
856         st->timeout=0;
857         if (st->state>=SITE_SENTMSG1 && st->state<=SITE_SENTMSG5)
858             send_msg(st);
859         else if (st->state==SITE_WAIT) {
860             enter_state_run(st);
861         } else {
862             slog(st,LOG_ERROR,"site_afterpoll: unexpected timeout, state=%d",
863                  st->state);
864         }
865     }
866     if (st->current_key_timeout && *now>st->current_key_timeout) {
867         slog(st,LOG_TIMEOUT_KEY,"maximum key life exceeded; session closed");
868         st->current_valid=False;
869         st->current_transform->delkey(st->current_transform->st);
870         st->current_key_timeout=0;
871     }
872 }
873
874 /* This function is called by the netlink device to deliver packets
875    intended for the remote network. The packet is in "raw" wire
876    format, but is guaranteed to be word-aligned. */
877 static void site_outgoing(void *sst, void *cid, struct buffer_if *buf)
878 {
879     struct site *st=sst;
880     string_t transform_err;
881     
882     if (st->state==SITE_STOP) {
883         BUF_FREE(buf);
884         return;
885     }
886
887     /* In all other states we consider delivering the packet if we have
888        a valid key and a valid address to send it to. */
889     if (st->current_valid && st->peer_valid) {
890         /* Transform it and send it */
891         buf_prepend_uint32(buf,LABEL_MSG9);
892         st->current_transform->forwards(st->current_transform->st,
893                                         buf, &transform_err);
894         buf_prepend_uint32(buf,LABEL_MSG0);
895         buf_prepend_uint32(buf,(uint32_t)st);
896         buf_prepend_uint32(buf,st->remote_session_id);
897         st->comm->sendmsg(st->comm->st,buf,&st->peer);
898         BUF_FREE(buf);
899         return;
900     }
901
902     if (st->state==SITE_RUN) {
903         BUF_FREE(buf); /* We throw the outgoing packet away */
904         slog(st,LOG_SETUP_INIT,"initiating key exchange");
905         enter_state_resolve(st);
906         return;
907     }
908
909     /* Otherwise we're in the middle of key setup or a wait - just
910        throw the outgoing packet away */
911     slog(st,LOG_DROP,"discarding outgoing packet");
912     BUF_FREE(buf);
913     return;
914 }
915
916 /* This function is called by the communication device to deliver
917    packets from our peers. */
918 static bool_t site_incoming(void *sst, struct buffer_if *buf,
919                             struct sockaddr_in *source)
920 {
921     struct site *st=sst;
922     uint32_t dest=ntohl(*(uint32_t *)buf->start);
923
924     if (dest==0) {
925         if (buf->size<(st->setupsiglen+8+NONCELEN)) return False;
926         /* It could be for any site - it should have LABEL_MSG1 and
927            might have our name and our peer's name in it */
928         if (memcmp(buf->start+8,st->setupsig,st->setupsiglen)==0) {
929             dump_packet(st,buf,source,True);
930             /* It's addressed to us. Decide what to do about it. */
931             if (st->state==SITE_RUN || st->state==SITE_RESOLVE ||
932                 st->state==SITE_WAIT) {
933                 /* We should definitely process it */
934                 if (process_msg1(st,buf,source)) {
935                     slog(st,LOG_SETUP_INIT,"key setup initiated by peer");
936                     enter_state_sentmsg2(st);
937                 } else {
938                     slog(st,LOG_ERROR,"failed to process incoming msg1");
939                 }
940                 BUF_FREE(buf);
941                 return True;
942             }
943             if (st->state==SITE_SENTMSG1) {
944                 /* We've just sent a message 1! They may have crossed on
945                    the wire. If we have priority then we ignore the
946                    incoming one, otherwise we process it as usual. */
947                 if (st->setup_priority) {
948                     BUF_FREE(buf);
949                     slog(st,LOG_DUMP,"crossed msg1s; we are higher "
950                          "priority => ignore incoming msg1");
951                     return True;
952                 } else {
953                     slog(st,LOG_DUMP,"crossed msg1s; we are lower "
954                          "priority => use incoming msg1");
955                     if (process_msg1(st,buf,source)) {
956                         BUF_FREE(&st->buffer); /* Free our old message 1 */
957                         enter_state_sentmsg2(st);
958                     } else {
959                         slog(st,LOG_ERROR,"failed to process an incoming "
960                              "crossed msg1 (we have low priority)");
961                     }
962                     BUF_FREE(buf);
963                     return True;
964                 }
965             }
966             /* The message 1 was received at an unexpected stage of the
967                key setup. XXX POLICY - what do we do? */
968             slog(st,LOG_UNEXPECTED,"unexpected incoming message 1");
969             BUF_FREE(buf);
970             return True;
971         }
972         return False; /* Not for us. */
973     }
974     if (dest==(uint32_t)st) {
975         uint32_t msgtype=ntohl(*(uint32_t *)(buf->start+8));
976         /* Explicitly addressed to us */
977         if (msgtype!=LABEL_MSG0) dump_packet(st,buf,source,True);
978         switch (msgtype) {
979         case LABEL_MSG0:
980             process_msg0(st,buf,source);
981             break;
982         case LABEL_MSG1:
983             /* Setup packet: should not have been explicitly addressed
984                to us */
985             slog(st,LOG_SEC,"incoming explicitly addressed msg1");
986             break;
987         case LABEL_MSG2:
988             /* Setup packet: expected only in state SENTMSG1 */
989             if (st->state!=SITE_SENTMSG1) {
990                 slog(st,LOG_UNEXPECTED,"unexpected MSG2");
991             } else if (process_msg2(st,buf,source))
992                 enter_state_sentmsg3(st);
993             else {
994                 slog(st,LOG_SEC,"invalid MSG2");
995             }
996             break;
997         case LABEL_MSG3:
998             /* Setup packet: expected only in state SENTMSG2 */
999             if (st->state!=SITE_SENTMSG2) {
1000                 slog(st,LOG_UNEXPECTED,"unexpected MSG3");
1001             } else if (process_msg3(st,buf,source))
1002                 enter_state_sentmsg4(st);
1003             else {
1004                 slog(st,LOG_SEC,"invalid MSG3");
1005             }
1006             break;
1007         case LABEL_MSG4:
1008             /* Setup packet: expected only in state SENTMSG3 */
1009             if (st->state!=SITE_SENTMSG3) {
1010                 slog(st,LOG_UNEXPECTED,"unexpected MSG4");
1011             } else if (process_msg4(st,buf,source))
1012                 enter_state_sentmsg5(st);
1013             else {
1014                 slog(st,LOG_SEC,"invalid MSG4");
1015             }
1016             break;
1017         case LABEL_MSG5:
1018             /* Setup packet: expected only in state SENTMSG4 */
1019             /* (may turn up in state RUN if our return MSG6 was lost
1020                and the new key has already been activated. In that
1021                case we should treat it as an ordinary PING packet. We
1022                can't pass it to process_msg5() because the
1023                new_transform will now be null. XXX) */
1024             if (st->state!=SITE_SENTMSG4) {
1025                 slog(st,LOG_UNEXPECTED,"unexpected MSG5");
1026             } else if (process_msg5(st,buf,source)) {
1027                 send_msg6(st);
1028             } else {
1029                 slog(st,LOG_SEC,"invalid MSG5");
1030             }
1031             break;
1032         case LABEL_MSG6:
1033             /* Setup packet: expected only in state SENTMSG5 */
1034             if (st->state!=SITE_SENTMSG5) {
1035                 slog(st,LOG_UNEXPECTED,"unexpected MSG6");
1036             } else if (process_msg6(st,buf,source)) {
1037                 BUF_FREE(&st->buffer); /* Free message 5 */
1038                 activate_new_key(st);
1039             } else {
1040                 slog(st,LOG_SEC,"invalid MSG6");
1041             }
1042             break;
1043         case LABEL_MSG8:
1044             /* NAK packet: enter state where we ping and check for response */
1045             slog(st,LOG_ERROR,"received a NAK");
1046             break;
1047         default:
1048             slog(st,LOG_SEC,"received message of unknown type 0x%08x",
1049                  msgtype);
1050             break;
1051         }
1052         BUF_FREE(buf);
1053         return True;
1054     }
1055
1056     return False;
1057 }
1058
1059 static void site_control(void *vst, bool_t run)
1060 {
1061     struct site *st=vst;
1062     if (run) enter_state_run(st);
1063     else enter_state_stop(st);
1064 }
1065
1066 static list_t *site_apply(closure_t *self, struct cloc loc, dict_t *context,
1067                           list_t *args)
1068 {
1069     struct site *st;
1070     item_t *item;
1071     dict_t *dict;
1072
1073     st=safe_malloc(sizeof(*st),"site_apply");
1074
1075     st->cl.description="site";
1076     st->cl.type=CL_SITE;
1077     st->cl.apply=NULL;
1078     st->cl.interface=&st->ops;
1079     st->ops.st=st;
1080     st->ops.control=site_control;
1081     st->ops.status=site_status;
1082
1083     /* First parameter must be a dict */
1084     item=list_elem(args,0);
1085     if (!item || item->type!=t_dict)
1086         cfgfatal(loc,"site","parameter must be a dictionary\n");
1087     
1088     dict=item->data.dict;
1089     st->netlink=find_cl_if(dict,"netlink",CL_NETLINK,True,"site",loc);
1090     st->comm=find_cl_if(dict,"comm",CL_COMM,True,"site",loc);
1091     st->resolver=find_cl_if(dict,"resolver",CL_RESOLVER,True,"site",loc);
1092     st->log=find_cl_if(dict,"log",CL_LOG,True,"site",loc);
1093     st->random=find_cl_if(dict,"random",CL_RANDOMSRC,True,"site",loc);
1094
1095     st->localname=dict_read_string(dict, "local-name", True, "site", loc);
1096     st->privkey=find_cl_if(dict,"local-key",CL_RSAPRIVKEY,True,"site",loc);
1097     st->remoteport=dict_read_number(dict,"port",True,"site",loc,0);
1098
1099     st->remotename=dict_read_string(dict, "name", True, "site", loc);
1100     st->address=dict_read_string(dict, "address", False, "site", loc);
1101     dict_read_subnet_list(dict, "networks", True, "site", loc,
1102                           &st->remotenets);
1103     st->pubkey=find_cl_if(dict,"key",CL_RSAPUBKEY,True,"site",loc);
1104
1105     st->transform=
1106         find_cl_if(dict,"transform",CL_TRANSFORM,True,"site",loc);
1107
1108     st->dh=find_cl_if(dict,"dh",CL_DH,True,"site",loc);
1109     st->hash=find_cl_if(dict,"hash",CL_HASH,True,"site",loc);
1110
1111     st->key_lifetime=dict_read_number(dict,"key-lifetime",
1112                                       False,"site",loc,DEFAULT_KEY_LIFETIME);
1113     st->setup_retries=dict_read_number(dict,"setup-retries",
1114                                        False,"site",loc,DEFAULT_SETUP_RETRIES);
1115     st->setup_timeout=dict_read_number(dict,"setup-timeout",
1116                                        False,"site",loc,DEFAULT_SETUP_TIMEOUT);
1117     st->wait_timeout=dict_read_number(dict,"wait-time",
1118                                       False,"site",loc,DEFAULT_WAIT_TIME);
1119     /* XXX should be configurable */
1120     st->log_events=LOG_SEC|LOG_ERROR|
1121         LOG_ACTIVATE_KEY|LOG_TIMEOUT_KEY|LOG_SETUP_INIT|LOG_SETUP_TIMEOUT;
1122
1123     st->tunname=safe_malloc(strlen(st->localname)+strlen(st->remotename)+5,
1124                             "site_apply");
1125     sprintf(st->tunname,"%s<->%s",st->localname,st->remotename);
1126
1127     /* The information we expect to see in incoming messages of type 1 */
1128     /* XXX fix this bit for unaligned access */
1129     st->setupsiglen=strlen(st->remotename)+strlen(st->localname)+8;
1130     st->setupsig=safe_malloc(st->setupsiglen,"site_apply");
1131     *(uint32_t *)&(st->setupsig[0])=LABEL_MSG1;
1132     *(uint16_t *)&(st->setupsig[4])=htons(strlen(st->remotename));
1133     memcpy(&st->setupsig[6],st->remotename,strlen(st->remotename));
1134     *(uint16_t *)&(st->setupsig[6+strlen(st->remotename)])=
1135         htons(strlen(st->localname));
1136     memcpy(&st->setupsig[8+strlen(st->remotename)],st->localname,
1137            strlen(st->localname));
1138     st->setup_priority=(strcmp(st->localname,st->remotename)>0);
1139
1140     buffer_new(&st->buffer,SETUP_BUFFER_LEN);
1141
1142     /* We are interested in poll(), but only for timeouts. We don't have
1143        any fds of our own. */
1144     register_for_poll(st, site_beforepoll, site_afterpoll, 0, "site");
1145     st->timeout=0;
1146
1147     st->current_valid=False;
1148     st->current_key_timeout=0;
1149     st->peer_valid=False;
1150     /* XXX mlock these */
1151     st->dhsecret=safe_malloc(st->dh->len,"site:dhsecret");
1152     st->sharedsecret=safe_malloc(st->transform->keylen,"site:sharedsecret");
1153
1154     /* We need to register the remote networks with the netlink device */
1155     st->netlink_cid=st->netlink->regnets(st->netlink->st, &st->remotenets,
1156                                          site_outgoing, st,
1157                                          st->transform->max_start_pad+(4*4),
1158                                          st->transform->max_end_pad,
1159                                          st->tunname);
1160
1161     st->comm->request_notify(st->comm->st, st, site_incoming);
1162
1163     st->current_transform=st->transform->create(st->transform->st);
1164     st->new_transform=st->transform->create(st->transform->st);
1165
1166     enter_state_stop(st);
1167
1168     return new_closure(&st->cl);
1169 }
1170
1171 init_module site_module;
1172 void site_module(dict_t *dict)
1173 {
1174     add_closure(dict,"site",site_apply);
1175 }