1 /* site.c - manage communication with a remote network site */
3 /* The 'site' code doesn't know anything about the structure of the
4 packets it's transmitting. In fact, under the new netlink
5 configuration scheme it doesn't need to know anything at all about
6 IP addresses, except how to contact its peer. This means it could
7 potentially be used to tunnel other protocols too (IPv6, IPX, plain
8 old Ethernet frames) if appropriate netlink code can be written
9 (and that ought not to be too hard, eg. using the TUN/TAP device to
10 pretend to be an Ethernet interface). */
12 /* At some point in the future the netlink code will be asked for
13 configuration information to go in the PING/PONG packets at the end
14 of the key exchange. */
20 #include <sys/socket.h>
24 #include "unaligned.h"
27 #define SETUP_BUFFER_LEN 2048
29 #define DEFAULT_KEY_LIFETIME 3600000 /* One hour */
30 #define DEFAULT_KEY_RENEGOTIATE_GAP 300000 /* Five minutes */
31 #define DEFAULT_SETUP_RETRIES 5
32 #define DEFAULT_SETUP_TIMEOUT 2000
33 #define DEFAULT_WAIT_TIME 20000
35 /* Each site can be in one of several possible states. */
38 SITE_STOP - nothing is allowed to happen; tunnel is down;
39 all session keys have been erased
40 -> SITE_RUN upon external instruction
41 SITE_RUN - site up, maybe with valid key
42 -> SITE_RESOLVE upon outgoing packet and no valid key
43 we start name resolution for the other end of the tunnel
44 -> SITE_SENTMSG2 upon valid incoming message 1 and suitable time
45 we send an appropriate message 2
46 SITE_RESOLVE - waiting for name resolution
47 -> SITE_SENTMSG1 upon successful resolution
48 we send an appropriate message 1
49 -> SITE_SENTMSG2 upon valid incoming message 1 (then abort resolution)
50 we abort resolution and
51 -> SITE_WAIT on timeout or resolution failure
53 -> SITE_SENTMSG2 upon valid incoming message 1 from higher priority end
54 -> SITE_SENTMSG3 upon valid incoming message 2
55 -> SITE_WAIT on timeout
57 -> SITE_SENTMSG4 upon valid incoming message 3
58 -> SITE_WAIT on timeout
60 -> SITE_SENTMSG5 upon valid incoming message 4
61 -> SITE_WAIT on timeout
63 -> SITE_RUN upon valid incoming message 5
64 -> SITE_WAIT on timeout
66 -> SITE_RUN upon valid incoming message 6
67 -> SITE_WAIT on timeout
68 SITE_WAIT - failed to establish key; do nothing for a while
69 -> SITE_RUN on timeout
74 #define SITE_RESOLVE 2
75 #define SITE_SENTMSG1 3
76 #define SITE_SENTMSG2 4
77 #define SITE_SENTMSG3 5
78 #define SITE_SENTMSG4 6
79 #define SITE_SENTMSG5 7
82 static cstring_t state_name(uint32_t state)
85 case 0: return "STOP";
87 case 2: return "RESOLVE";
88 case 3: return "SENTMSG1";
89 case 4: return "SENTMSG2";
90 case 5: return "SENTMSG3";
91 case 6: return "SENTMSG4";
92 case 7: return "SENTMSG5";
93 case 8: return "WAIT";
94 default: return "*bad state*";
100 #define LOG_UNEXPECTED 0x00000001
101 #define LOG_SETUP_INIT 0x00000002
102 #define LOG_SETUP_TIMEOUT 0x00000004
103 #define LOG_ACTIVATE_KEY 0x00000008
104 #define LOG_TIMEOUT_KEY 0x00000010
105 #define LOG_SEC 0x00000020
106 #define LOG_STATE 0x00000040
107 #define LOG_DROP 0x00000080
108 #define LOG_DUMP 0x00000100
109 #define LOG_ERROR 0x00000400
111 static struct flagstr log_event_table[]={
112 { "unexpected", LOG_UNEXPECTED },
113 { "setup-init", LOG_SETUP_INIT },
114 { "setup-timeout", LOG_SETUP_TIMEOUT },
115 { "activate-key", LOG_ACTIVATE_KEY },
116 { "timeout-key", LOG_TIMEOUT_KEY },
117 { "security", LOG_SEC },
118 { "state-change", LOG_STATE },
119 { "packet-drop", LOG_DROP },
120 { "dump-packets", LOG_DUMP },
121 { "errors", LOG_ERROR },
122 { "default", LOG_SETUP_INIT|LOG_SETUP_TIMEOUT|
123 LOG_ACTIVATE_KEY|LOG_TIMEOUT_KEY|LOG_SEC|LOG_ERROR },
124 { "all", 0xffffffff },
131 /* configuration information */
134 string_t tunname; /* localname<->remotename by default, used in logs */
135 string_t address; /* DNS name for bootstrapping, optional */
136 int remoteport; /* Port for bootstrapping, optional */
137 struct netlink_if *netlink;
138 struct comm_if *comm;
139 struct resolver_if *resolver;
141 struct random_if *random;
142 struct rsaprivkey_if *privkey;
143 struct rsapubkey_if *pubkey;
144 struct transform_if *transform;
146 struct hash_if *hash;
148 uint32_t setup_retries; /* How many times to send setup packets */
149 uint32_t setup_timeout; /* Initial timeout for setup packets */
150 uint32_t wait_timeout; /* How long to wait if setup unsuccessful */
151 uint32_t key_lifetime; /* How long a key lasts once set up */
152 uint32_t key_renegotiate_time; /* If we see traffic (or a keepalive)
153 after this time, initiate a new
155 bool_t keepalive; /* Send keepalives to detect peer failure (not yet
158 uint8_t *setupsig; /* Expected signature of incoming MSG1 packets */
159 uint32_t setupsiglen; /* Allows us to discard packets quickly if
160 they are not for us */
161 bool_t setup_priority; /* Do we have precedence if both sites emit
162 message 1 simultaneously? */
165 /* runtime information */
167 uint64_t now; /* Most recently seen time */
169 /* The currently established session */
170 uint32_t remote_session_id;
171 struct transform_inst_if *current_transform;
172 bool_t current_valid;
173 uint64_t current_key_timeout; /* End of life of current key */
174 uint64_t renegotiate_key_time; /* When we can negotiate a new key */
175 struct sockaddr_in peer; /* Current address of peer */
176 bool_t peer_valid; /* Peer address becomes invalid when key times out,
177 but only if we have a DNS name for our peer */
179 /* The current key setup protocol exchange. We can only be
180 involved in one of these at a time. There's a potential for
181 denial of service here (the attacker keeps sending a setup
182 packet; we keep trying to continue the exchange, and have to
183 timeout before we can listen for another setup packet); perhaps
184 we should keep a list of 'bad' sources for setup packets. */
185 uint32_t setup_session_id;
186 struct sockaddr_in setup_peer;
187 uint8_t localN[NONCELEN]; /* Nonces for key exchange */
188 uint8_t remoteN[NONCELEN];
189 struct buffer_if buffer; /* Current outgoing key exchange packet */
190 uint32_t retries; /* Number of retries remaining */
191 uint64_t timeout; /* Timeout for current state */
193 uint8_t *sharedsecret;
194 struct transform_inst_if *new_transform; /* For key setup/verify */
197 static void slog(struct site *st, uint32_t event, cstring_t msg, ...)
205 if (event&st->log_events) {
207 case LOG_UNEXPECTED: class=M_INFO; break;
208 case LOG_SETUP_INIT: class=M_INFO; break;
209 case LOG_SETUP_TIMEOUT: class=M_NOTICE; break;
210 case LOG_ACTIVATE_KEY: class=M_INFO; break;
211 case LOG_TIMEOUT_KEY: class=M_INFO; break;
212 case LOG_SEC: class=M_SECURITY; break;
213 case LOG_STATE: class=M_DEBUG; break;
214 case LOG_DROP: class=M_DEBUG; break;
215 case LOG_DUMP: class=M_DEBUG; break;
216 case LOG_ERROR: class=M_ERR; break;
217 default: class=M_ERR; break;
220 vsnprintf(buf,240,msg,ap);
221 st->log->log(st->log->st,class,"%s: %s",st->tunname,buf);
226 static void set_link_quality(struct site *st);
227 static void delete_key(struct site *st, cstring_t reason, uint32_t loglevel);
228 static bool_t initiate_key_setup(struct site *st, cstring_t reason);
229 static void enter_state_run(struct site *st);
230 static bool_t enter_state_resolve(struct site *st);
231 static bool_t enter_new_state(struct site *st,uint32_t next);
232 static void enter_state_wait(struct site *st);
234 #define CHECK_AVAIL(b,l) do { if ((b)->size<(l)) return False; } while(0)
235 #define CHECK_EMPTY(b) do { if ((b)->size!=0) return False; } while(0)
236 #define CHECK_TYPE(b,t) do { uint32_t type; \
237 CHECK_AVAIL((b),4); \
238 type=buf_unprepend_uint32((b)); \
239 if (type!=(t)) return False; } while(0)
258 /* Build any of msg1 to msg4. msg5 and msg6 are built from the inside
259 out using a transform of config data supplied by netlink */
260 static bool_t generate_msg(struct site *st, uint32_t type, cstring_t what)
266 st->retries=st->setup_retries;
267 BUF_ALLOC(&st->buffer,what);
268 buffer_init(&st->buffer,0);
269 buf_append_uint32(&st->buffer,
270 (type==LABEL_MSG1?0:st->setup_session_id));
271 buf_append_uint32(&st->buffer,(uint32_t)st);
272 buf_append_uint32(&st->buffer,type);
273 buf_append_string(&st->buffer,st->localname);
274 buf_append_string(&st->buffer,st->remotename);
275 memcpy(buf_append(&st->buffer,NONCELEN),st->localN,NONCELEN);
276 if (type==LABEL_MSG1) return True;
277 memcpy(buf_append(&st->buffer,NONCELEN),st->remoteN,NONCELEN);
278 if (type==LABEL_MSG2) return True;
280 if (hacky_par_mid_failnow()) return False;
282 dhpub=st->dh->makepublic(st->dh->st,st->dhsecret,st->dh->len);
283 buf_append_string(&st->buffer,dhpub);
285 hash=safe_malloc(st->hash->len, "generate_msg");
286 hst=st->hash->init();
287 st->hash->update(hst,st->buffer.start,st->buffer.size);
288 st->hash->final(hst,hash);
289 sig=st->privkey->sign(st->privkey->st,hash,st->hash->len);
290 buf_append_string(&st->buffer,sig);
296 static bool_t unpick_msg(struct site *st, uint32_t type,
297 struct buffer_if *msg, struct msg *m)
299 m->hashstart=msg->start;
301 m->dest=buf_unprepend_uint32(msg);
303 m->source=buf_unprepend_uint32(msg);
304 CHECK_TYPE(msg,type);
306 m->remlen=buf_unprepend_uint16(msg);
307 CHECK_AVAIL(msg,m->remlen);
308 m->remote=buf_unprepend(msg,m->remlen);
310 m->loclen=buf_unprepend_uint16(msg);
311 CHECK_AVAIL(msg,m->loclen);
312 m->local=buf_unprepend(msg,m->loclen);
313 CHECK_AVAIL(msg,NONCELEN);
314 m->nR=buf_unprepend(msg,NONCELEN);
315 if (type==LABEL_MSG1) {
319 CHECK_AVAIL(msg,NONCELEN);
320 m->nL=buf_unprepend(msg,NONCELEN);
321 if (type==LABEL_MSG2) {
326 m->pklen=buf_unprepend_uint16(msg);
327 CHECK_AVAIL(msg,m->pklen);
328 m->pk=buf_unprepend(msg,m->pklen);
329 m->hashlen=msg->start-m->hashstart;
331 m->siglen=buf_unprepend_uint16(msg);
332 CHECK_AVAIL(msg,m->siglen);
333 m->sig=buf_unprepend(msg,m->siglen);
338 static bool_t check_msg(struct site *st, uint32_t type, struct msg *m,
341 if (type==LABEL_MSG1) return True;
343 /* Check that the site names and our nonce have been sent
344 back correctly, and then store our peer's nonce. */
345 if (memcmp(m->remote,st->remotename,strlen(st->remotename)!=0)) {
346 *error="wrong remote site name";
349 if (memcmp(m->local,st->localname,strlen(st->localname)!=0)) {
350 *error="wrong local site name";
353 if (memcmp(m->nL,st->localN,NONCELEN)!=0) {
354 *error="wrong locally-generated nonce";
357 if (type==LABEL_MSG2) return True;
358 if (memcmp(m->nR,st->remoteN,NONCELEN)!=0) {
359 *error="wrong remotely-generated nonce";
362 if (type==LABEL_MSG3) return True;
363 if (type==LABEL_MSG4) return True;
364 *error="unknown message type";
368 static bool_t generate_msg1(struct site *st)
370 st->random->generate(st->random->st,NONCELEN,st->localN);
371 return generate_msg(st,LABEL_MSG1,"site:MSG1");
374 static bool_t process_msg1(struct site *st, struct buffer_if *msg1,
375 struct sockaddr_in *src)
379 /* We've already determined we're in an appropriate state to
380 process an incoming MSG1, and that the MSG1 has correct values
383 if (!unpick_msg(st,LABEL_MSG1,msg1,&m)) return False;
386 st->setup_session_id=m.source;
387 memcpy(st->remoteN,m.nR,NONCELEN);
391 static bool_t generate_msg2(struct site *st)
393 st->random->generate(st->random->st,NONCELEN,st->localN);
394 return generate_msg(st,LABEL_MSG2,"site:MSG2");
397 static bool_t process_msg2(struct site *st, struct buffer_if *msg2,
398 struct sockaddr_in *src)
403 if (!unpick_msg(st,LABEL_MSG2,msg2,&m)) return False;
404 if (!check_msg(st,LABEL_MSG2,&m,&err)) {
405 slog(st,LOG_SEC,"msg2: %s",err);
408 st->setup_session_id=m.source;
409 memcpy(st->remoteN,m.nR,NONCELEN);
413 static bool_t generate_msg3(struct site *st)
415 /* Now we have our nonce and their nonce. Think of a secret key,
416 and create message number 3. */
417 st->random->generate(st->random->st,st->dh->len,st->dhsecret);
418 return generate_msg(st,LABEL_MSG3,"site:MSG3");
421 static bool_t process_msg3(struct site *st, struct buffer_if *msg3,
422 struct sockaddr_in *src)
429 if (!unpick_msg(st,LABEL_MSG3,msg3,&m)) return False;
430 if (!check_msg(st,LABEL_MSG3,&m,&err)) {
431 slog(st,LOG_SEC,"msg3: %s",err);
435 /* Check signature and store g^x mod m */
436 hash=safe_malloc(st->hash->len, "process_msg3");
437 hst=st->hash->init();
438 st->hash->update(hst,m.hashstart,m.hashlen);
439 st->hash->final(hst,hash);
440 /* Terminate signature with a '0' - cheating, but should be ok */
442 if (!st->pubkey->check(st->pubkey->st,hash,st->hash->len,m.sig)) {
443 slog(st,LOG_SEC,"msg3 signature failed check!");
449 /* Terminate their DH public key with a '0' */
451 /* Invent our DH secret key */
452 st->random->generate(st->random->st,st->dh->len,st->dhsecret);
454 /* Generate the shared key */
455 st->dh->makeshared(st->dh->st,st->dhsecret,st->dh->len,m.pk,
456 st->sharedsecret,st->transform->keylen);
458 /* Set up the transform */
459 st->new_transform->setkey(st->new_transform->st,st->sharedsecret,
460 st->transform->keylen);
465 static bool_t generate_msg4(struct site *st)
467 /* We have both nonces, their public key and our private key. Generate
468 our public key, sign it and send it to them. */
469 return generate_msg(st,LABEL_MSG4,"site:MSG4");
472 static bool_t process_msg4(struct site *st, struct buffer_if *msg4,
473 struct sockaddr_in *src)
480 if (!unpick_msg(st,LABEL_MSG4,msg4,&m)) return False;
481 if (!check_msg(st,LABEL_MSG4,&m,&err)) {
482 slog(st,LOG_SEC,"msg4: %s",err);
486 /* Check signature and store g^x mod m */
487 hash=safe_malloc(st->hash->len, "process_msg4");
488 hst=st->hash->init();
489 st->hash->update(hst,m.hashstart,m.hashlen);
490 st->hash->final(hst,hash);
491 /* Terminate signature with a '0' - cheating, but should be ok */
493 if (!st->pubkey->check(st->pubkey->st,hash,st->hash->len,m.sig)) {
494 slog(st,LOG_SEC,"msg4 signature failed check!");
500 /* Terminate their DH public key with a '0' */
502 /* Generate the shared key */
503 st->dh->makeshared(st->dh->st,st->dhsecret,st->dh->len,m.pk,
504 st->sharedsecret,st->transform->keylen);
505 /* Set up the transform */
506 st->new_transform->setkey(st->new_transform->st,st->sharedsecret,
507 st->transform->keylen);
518 static bool_t unpick_msg0(struct site *st, struct buffer_if *msg0,
522 m->dest=buf_unprepend_uint32(msg0);
524 m->source=buf_unprepend_uint32(msg0);
526 m->type=buf_unprepend_uint32(msg0);
528 /* Leaves transformed part of buffer untouched */
531 static bool_t generate_msg5(struct site *st)
533 cstring_t transform_err;
535 BUF_ALLOC(&st->buffer,"site:MSG5");
536 /* We are going to add four words to the message */
537 buffer_init(&st->buffer,st->transform->max_start_pad+(4*4));
538 /* Give the netlink code an opportunity to put its own stuff in the
539 message (configuration information, etc.) */
540 st->netlink->output_config(st->netlink->st,&st->buffer);
541 buf_prepend_uint32(&st->buffer,LABEL_MSG5);
542 st->new_transform->forwards(st->new_transform->st,&st->buffer,
544 buf_prepend_uint32(&st->buffer,LABEL_MSG5);
545 buf_prepend_uint32(&st->buffer,(uint32_t)st);
546 buf_prepend_uint32(&st->buffer,st->setup_session_id);
548 st->retries=st->setup_retries;
552 static bool_t process_msg5(struct site *st, struct buffer_if *msg5,
553 struct sockaddr_in *src)
556 cstring_t transform_err;
558 if (!unpick_msg0(st,msg5,&m)) return False;
560 if (st->new_transform->reverse(st->new_transform->st,
561 msg5,&transform_err)) {
562 /* There's a problem */
563 slog(st,LOG_SEC,"process_msg5: transform: %s",transform_err);
566 /* Buffer should now contain untransformed PING packet data */
568 if (buf_unprepend_uint32(msg5)!=LABEL_MSG5) {
569 slog(st,LOG_SEC,"MSG5/PING packet contained wrong label");
572 if (!st->netlink->check_config(st->netlink->st,msg5)) {
573 slog(st,LOG_SEC,"MSG5/PING packet contained bad netlink config");
580 static bool_t generate_msg6(struct site *st)
582 cstring_t transform_err;
584 BUF_ALLOC(&st->buffer,"site:MSG6");
585 /* We are going to add four words to the message */
586 buffer_init(&st->buffer,st->transform->max_start_pad+(4*4));
587 /* Give the netlink code an opportunity to put its own stuff in the
588 message (configuration information, etc.) */
589 st->netlink->output_config(st->netlink->st,&st->buffer);
590 buf_prepend_uint32(&st->buffer,LABEL_MSG6);
591 st->new_transform->forwards(st->new_transform->st,&st->buffer,
593 buf_prepend_uint32(&st->buffer,LABEL_MSG6);
594 buf_prepend_uint32(&st->buffer,(uint32_t)st);
595 buf_prepend_uint32(&st->buffer,st->setup_session_id);
597 st->retries=1; /* Peer will retransmit MSG5 if this packet gets lost */
601 static bool_t process_msg6(struct site *st, struct buffer_if *msg6,
602 struct sockaddr_in *src)
605 cstring_t transform_err;
607 if (!unpick_msg0(st,msg6,&m)) return False;
609 if (st->new_transform->reverse(st->new_transform->st,
610 msg6,&transform_err)) {
611 /* There's a problem */
612 slog(st,LOG_SEC,"process_msg6: transform: %s",transform_err);
615 /* Buffer should now contain untransformed PING packet data */
617 if (buf_unprepend_uint32(msg6)!=LABEL_MSG6) {
618 slog(st,LOG_SEC,"MSG6/PONG packet contained invalid data");
621 if (!st->netlink->check_config(st->netlink->st,msg6)) {
622 slog(st,LOG_SEC,"MSG6/PONG packet contained bad netlink config");
629 static bool_t process_msg0(struct site *st, struct buffer_if *msg0,
630 struct sockaddr_in *src)
633 cstring_t transform_err;
636 if (!st->current_valid) {
637 slog(st,LOG_DROP,"incoming message but no current key -> dropping");
638 return initiate_key_setup(st,"incoming message but no current key");
641 if (!unpick_msg0(st,msg0,&m)) return False;
643 if (st->current_transform->reverse(st->current_transform->st,
644 msg0,&transform_err)) {
645 /* There's a problem */
646 slog(st,LOG_SEC,"transform: %s",transform_err);
647 return initiate_key_setup(st,"incoming message would not decrypt");
650 type=buf_unprepend_uint32(msg0);
653 /* We must forget about the current session. */
654 delete_key(st,"request from peer",LOG_SEC);
658 /* Deliver to netlink layer */
659 st->netlink->deliver(st->netlink->st,msg0);
663 slog(st,LOG_SEC,"incoming encrypted message of type %08x "
670 static void dump_packet(struct site *st, struct buffer_if *buf,
671 struct sockaddr_in *addr, bool_t incoming)
673 uint32_t dest=ntohl(*(uint32_t *)buf->start);
674 uint32_t source=ntohl(*(uint32_t *)(buf->start+4));
675 uint32_t msgtype=ntohl(*(uint32_t *)(buf->start+8));
677 if (st->log_events & LOG_DUMP)
678 slilog(st->log,M_DEBUG,"%s: %s: %08x<-%08x: %08x:",
679 st->tunname,incoming?"incoming":"outgoing",
680 dest,source,msgtype);
683 static uint32_t site_status(void *st)
688 static bool_t send_msg(struct site *st)
691 dump_packet(st,&st->buffer,&st->setup_peer,False);
692 st->comm->sendmsg(st->comm->st,&st->buffer,&st->setup_peer);
693 st->timeout=st->now+st->setup_timeout;
697 slog(st,LOG_SETUP_TIMEOUT,"timed out sending key setup packet "
698 "(in state %s)",state_name(st->state));
699 enter_state_wait(st);
704 static void site_resolve_callback(void *sst, struct in_addr *address)
708 if (st->state!=SITE_RESOLVE) {
709 slog(st,LOG_UNEXPECTED,"site_resolve_callback called unexpectedly");
713 memset(&st->setup_peer,0,sizeof(st->setup_peer));
714 st->setup_peer.sin_family=AF_INET;
715 st->setup_peer.sin_port=htons(st->remoteport);
716 st->setup_peer.sin_addr=*address;
717 enter_new_state(st,SITE_SENTMSG1);
719 /* Resolution failed */
720 slog(st,LOG_ERROR,"resolution of %s failed",st->address);
725 static bool_t initiate_key_setup(struct site *st, cstring_t reason)
727 if (st->state!=SITE_RUN) return False;
728 slog(st,LOG_SETUP_INIT,"initiating key exchange (%s)",reason);
730 slog(st,LOG_SETUP_INIT,"resolving peer address");
731 return enter_state_resolve(st);
732 } else if (st->peer_valid) {
733 slog(st,LOG_SETUP_INIT,"using old peer address");
734 st->setup_peer=st->peer;
735 return enter_new_state(st,SITE_SENTMSG1);
737 slog(st,LOG_SETUP_INIT,"key exchange failed: no address for peer");
741 static void activate_new_key(struct site *st)
743 struct transform_inst_if *t;
745 /* We have two transform instances, which we swap between active
747 t=st->current_transform;
748 st->current_transform=st->new_transform;
753 st->current_valid=True;
754 st->current_key_timeout=st->now+st->key_lifetime;
755 st->renegotiate_key_time=st->now+st->key_renegotiate_time;
756 st->peer=st->setup_peer;
758 st->remote_session_id=st->setup_session_id;
760 slog(st,LOG_ACTIVATE_KEY,"new key activated");
764 static void delete_key(struct site *st, cstring_t reason, uint32_t loglevel)
766 if (st->current_valid) {
767 slog(st,loglevel,"session closed (%s)",reason);
769 st->current_valid=False;
770 st->current_transform->delkey(st->current_transform->st);
771 st->current_key_timeout=0;
772 set_link_quality(st);
776 static void state_assert(struct site *st, bool_t ok)
778 if (!ok) fatal("site:state_assert");
781 static void enter_state_stop(struct site *st)
785 delete_key(st,"entering state STOP",LOG_TIMEOUT_KEY);
786 st->new_transform->delkey(st->new_transform->st);
789 static void set_link_quality(struct site *st)
792 if (st->current_valid)
793 quality=LINK_QUALITY_UP;
794 else if (st->state==SITE_WAIT || st->state==SITE_STOP)
795 quality=LINK_QUALITY_DOWN;
796 else if (st->address)
797 quality=LINK_QUALITY_DOWN_CURRENT_ADDRESS;
798 else if (st->peer_valid)
799 quality=LINK_QUALITY_DOWN_STALE_ADDRESS;
801 quality=LINK_QUALITY_DOWN;
803 st->netlink->set_quality(st->netlink->st,quality);
806 static void enter_state_run(struct site *st)
808 slog(st,LOG_STATE,"entering state RUN");
812 st->setup_session_id=0;
813 memset(&st->setup_peer,0,sizeof(st->setup_peer));
814 memset(st->localN,0,NONCELEN);
815 memset(st->remoteN,0,NONCELEN);
816 st->new_transform->delkey(st->new_transform->st);
817 memset(st->dhsecret,0,st->dh->len);
818 memset(st->sharedsecret,0,st->transform->keylen);
819 set_link_quality(st);
822 static bool_t enter_state_resolve(struct site *st)
824 state_assert(st,st->state==SITE_RUN);
825 slog(st,LOG_STATE,"entering state RESOLVE");
826 st->state=SITE_RESOLVE;
827 st->resolver->request(st->resolver->st,st->address,
828 site_resolve_callback,st);
832 static bool_t enter_new_state(struct site *st, uint32_t next)
834 bool_t (*gen)(struct site *st);
837 slog(st,LOG_STATE,"entering state %s",state_name(next));
840 state_assert(st,st->state==SITE_RUN || st->state==SITE_RESOLVE);
844 state_assert(st,st->state==SITE_RUN || st->state==SITE_RESOLVE ||
845 st->state==SITE_SENTMSG1 || st->state==SITE_WAIT);
849 state_assert(st,st->state==SITE_SENTMSG1);
850 BUF_FREE(&st->buffer);
854 state_assert(st,st->state==SITE_SENTMSG2);
855 BUF_FREE(&st->buffer);
859 state_assert(st,st->state==SITE_SENTMSG3);
860 BUF_FREE(&st->buffer);
864 state_assert(st,st->state==SITE_SENTMSG4);
865 BUF_FREE(&st->buffer);
870 fatal("enter_new_state(%s): invalid new state",state_name(next));
874 if (hacky_par_start_failnow()) return False;
876 r= gen(st) && send_msg(st);
879 st->setup_retries, st->setup_timeout,
884 if (next==SITE_RUN) {
885 BUF_FREE(&st->buffer); /* Never reused */
886 st->timeout=0; /* Never retransmit */
887 activate_new_key(st);
891 slog(st,LOG_ERROR,"error entering state %s",state_name(next));
892 st->buffer.free=False; /* Unconditionally use the buffer; it may be
893 in either state, and enter_state_wait() will
895 enter_state_wait(st);
899 /* msg7 tells our peer that we're about to forget our key */
900 static bool_t send_msg7(struct site *st, cstring_t reason)
902 cstring_t transform_err;
904 if (st->current_valid && st->peer_valid && st->buffer.free) {
905 BUF_ALLOC(&st->buffer,"site:MSG7");
906 buffer_init(&st->buffer,st->transform->max_start_pad+(4*3));
907 buf_append_uint32(&st->buffer,LABEL_MSG7);
908 buf_append_string(&st->buffer,reason);
909 st->current_transform->forwards(st->current_transform->st,
910 &st->buffer, &transform_err);
911 buf_prepend_uint32(&st->buffer,LABEL_MSG0);
912 buf_prepend_uint32(&st->buffer,(uint32_t)st);
913 buf_prepend_uint32(&st->buffer,st->remote_session_id);
914 st->comm->sendmsg(st->comm->st,&st->buffer,&st->peer);
915 BUF_FREE(&st->buffer);
921 /* We go into this state if our peer becomes uncommunicative. Similar to
922 the "stop" state, we forget all session keys for a while, before
923 re-entering the "run" state. */
924 static void enter_state_wait(struct site *st)
926 slog(st,LOG_STATE,"entering state WAIT");
927 st->timeout=st->now+st->wait_timeout;
929 st->peer_valid=False;
930 set_link_quality(st);
931 BUF_FREE(&st->buffer); /* will have had an outgoing packet in it */
932 /* XXX Erase keys etc. */
935 static inline void site_settimeout(uint64_t timeout, uint64_t *now,
939 uint64_t offset=timeout-*now;
940 if (offset>INT_MAX) offset=INT_MAX;
941 if (*timeout_io<0 || offset<*timeout_io)
946 static int site_beforepoll(void *sst, struct pollfd *fds, int *nfds_io,
947 int *timeout_io, const struct timeval *tv_now,
952 *nfds_io=0; /* We don't use any file descriptors */
955 /* Work out when our next timeout is. The earlier of 'timeout' or
956 'current_key_timeout'. A stored value of '0' indicates no timeout
958 site_settimeout(st->timeout, now, timeout_io);
959 site_settimeout(st->current_key_timeout, now, timeout_io);
961 return 0; /* success */
964 /* NB site_afterpoll will be called before site_beforepoll is ever called */
965 static void site_afterpoll(void *sst, struct pollfd *fds, int nfds,
966 const struct timeval *tv_now, uint64_t *now)
971 if (st->timeout && *now>st->timeout) {
973 if (st->state>=SITE_SENTMSG1 && st->state<=SITE_SENTMSG5) {
974 if (!hacky_par_start_failnow())
976 } else if (st->state==SITE_WAIT) {
979 slog(st,LOG_ERROR,"site_afterpoll: unexpected timeout, state=%d",
983 if (st->current_key_timeout && *now>st->current_key_timeout) {
984 delete_key(st,"maximum key life exceeded",LOG_TIMEOUT_KEY);
988 /* This function is called by the netlink device to deliver packets
989 intended for the remote network. The packet is in "raw" wire
990 format, but is guaranteed to be word-aligned. */
991 static void site_outgoing(void *sst, struct buffer_if *buf)
994 cstring_t transform_err;
996 if (st->state==SITE_STOP) {
1001 /* In all other states we consider delivering the packet if we have
1002 a valid key and a valid address to send it to. */
1003 if (st->current_valid && st->peer_valid) {
1004 /* Transform it and send it */
1006 buf_prepend_uint32(buf,LABEL_MSG9);
1007 st->current_transform->forwards(st->current_transform->st,
1008 buf, &transform_err);
1009 buf_prepend_uint32(buf,LABEL_MSG0);
1010 buf_prepend_uint32(buf,(uint32_t)st);
1011 buf_prepend_uint32(buf,st->remote_session_id);
1012 st->comm->sendmsg(st->comm->st,buf,&st->peer);
1015 /* See whether we should start negotiating a new key */
1016 if (st->now > st->renegotiate_key_time)
1017 initiate_key_setup(st,"outgoing packet in renegotiation window");
1021 slog(st,LOG_DROP,"discarding outgoing packet of size %d",buf->size);
1023 initiate_key_setup(st,"outgoing packet");
1026 /* This function is called by the communication device to deliver
1027 packets from our peers. */
1028 static bool_t site_incoming(void *sst, struct buffer_if *buf,
1029 struct sockaddr_in *source)
1031 struct site *st=sst;
1032 uint32_t dest=ntohl(*(uint32_t *)buf->start);
1035 /* It could be for any site - it should have LABEL_MSG1 and
1036 might have our name and our peer's name in it */
1037 if (buf->size<(st->setupsiglen+8+NONCELEN)) return False;
1038 if (memcmp(buf->start+8,st->setupsig,st->setupsiglen)==0) {
1039 /* It's addressed to us. Decide what to do about it. */
1040 dump_packet(st,buf,source,True);
1041 if (st->state==SITE_RUN || st->state==SITE_RESOLVE ||
1042 st->state==SITE_WAIT) {
1043 /* We should definitely process it */
1044 if (process_msg1(st,buf,source)) {
1045 slog(st,LOG_SETUP_INIT,"key setup initiated by peer");
1046 enter_new_state(st,SITE_SENTMSG2);
1048 slog(st,LOG_ERROR,"failed to process incoming msg1");
1052 } else if (st->state==SITE_SENTMSG1) {
1053 /* We've just sent a message 1! They may have crossed on
1054 the wire. If we have priority then we ignore the
1055 incoming one, otherwise we process it as usual. */
1056 if (st->setup_priority) {
1058 slog(st,LOG_DUMP,"crossed msg1s; we are higher "
1059 "priority => ignore incoming msg1");
1062 slog(st,LOG_DUMP,"crossed msg1s; we are lower "
1063 "priority => use incoming msg1");
1064 if (process_msg1(st,buf,source)) {
1065 BUF_FREE(&st->buffer); /* Free our old message 1 */
1066 enter_new_state(st,SITE_SENTMSG2);
1068 slog(st,LOG_ERROR,"failed to process an incoming "
1069 "crossed msg1 (we have low priority)");
1075 /* The message 1 was received at an unexpected stage of the
1076 key setup. XXX POLICY - what do we do? */
1077 slog(st,LOG_UNEXPECTED,"unexpected incoming message 1");
1081 return False; /* Not for us. */
1083 if (dest==(uint32_t)st) {
1084 /* Explicitly addressed to us */
1085 uint32_t msgtype=ntohl(get_uint32(buf->start+8));
1086 if (msgtype!=LABEL_MSG0) dump_packet(st,buf,source,True);
1089 /* If the source is our current peer then initiate a key setup,
1090 because our peer's forgotten the key */
1091 if (get_uint32(buf->start+4)==st->remote_session_id) {
1092 initiate_key_setup(st,"received a NAK");
1094 slog(st,LOG_SEC,"bad incoming NAK");
1098 process_msg0(st,buf,source);
1101 /* Setup packet: should not have been explicitly addressed
1103 slog(st,LOG_SEC,"incoming explicitly addressed msg1");
1106 /* Setup packet: expected only in state SENTMSG1 */
1107 if (st->state!=SITE_SENTMSG1) {
1108 slog(st,LOG_UNEXPECTED,"unexpected MSG2");
1109 } else if (process_msg2(st,buf,source))
1110 enter_new_state(st,SITE_SENTMSG3);
1112 slog(st,LOG_SEC,"invalid MSG2");
1116 /* Setup packet: expected only in state SENTMSG2 */
1117 if (st->state!=SITE_SENTMSG2) {
1118 slog(st,LOG_UNEXPECTED,"unexpected MSG3");
1119 } else if (process_msg3(st,buf,source))
1120 enter_new_state(st,SITE_SENTMSG4);
1122 slog(st,LOG_SEC,"invalid MSG3");
1126 /* Setup packet: expected only in state SENTMSG3 */
1127 if (st->state!=SITE_SENTMSG3) {
1128 slog(st,LOG_UNEXPECTED,"unexpected MSG4");
1129 } else if (process_msg4(st,buf,source))
1130 enter_new_state(st,SITE_SENTMSG5);
1132 slog(st,LOG_SEC,"invalid MSG4");
1136 /* Setup packet: expected only in state SENTMSG4 */
1137 /* (may turn up in state RUN if our return MSG6 was lost
1138 and the new key has already been activated. In that
1139 case we should treat it as an ordinary PING packet. We
1140 can't pass it to process_msg5() because the
1141 new_transform will now be unkeyed. XXX) */
1142 if (st->state!=SITE_SENTMSG4) {
1143 slog(st,LOG_UNEXPECTED,"unexpected MSG5");
1144 } else if (process_msg5(st,buf,source)) {
1145 enter_new_state(st,SITE_RUN);
1147 slog(st,LOG_SEC,"invalid MSG5");
1151 /* Setup packet: expected only in state SENTMSG5 */
1152 if (st->state!=SITE_SENTMSG5) {
1153 slog(st,LOG_UNEXPECTED,"unexpected MSG6");
1154 } else if (process_msg6(st,buf,source)) {
1155 BUF_FREE(&st->buffer); /* Free message 5 */
1156 activate_new_key(st);
1158 slog(st,LOG_SEC,"invalid MSG6");
1162 slog(st,LOG_SEC,"received message of unknown type 0x%08x",
1173 static void site_control(void *vst, bool_t run)
1175 struct site *st=vst;
1176 if (run) enter_state_run(st);
1177 else enter_state_stop(st);
1180 static void site_phase_hook(void *sst, uint32_t newphase)
1182 struct site *st=sst;
1184 /* The program is shutting down; tell our peer */
1185 send_msg7(st,"shutting down");
1188 static list_t *site_apply(closure_t *self, struct cloc loc, dict_t *context,
1195 st=safe_malloc(sizeof(*st),"site_apply");
1197 st->cl.description="site";
1198 st->cl.type=CL_SITE;
1200 st->cl.interface=&st->ops;
1202 st->ops.control=site_control;
1203 st->ops.status=site_status;
1205 /* First parameter must be a dict */
1206 item=list_elem(args,0);
1207 if (!item || item->type!=t_dict)
1208 cfgfatal(loc,"site","parameter must be a dictionary\n");
1210 dict=item->data.dict;
1211 st->localname=dict_read_string(dict, "local-name", True, "site", loc);
1212 st->remotename=dict_read_string(dict, "name", True, "site", loc);
1213 /* Sanity check (which also allows the 'sites' file to include
1214 site() closures for all sites including our own): refuse to
1215 talk to ourselves */
1216 if (strcmp(st->localname,st->remotename)==0) {
1217 Message(M_DEBUG,"site %s: local-name==name -> ignoring this site\n",
1222 st->netlink=find_cl_if(dict,"link",CL_NETLINK,True,"site",loc);
1223 st->comm=find_cl_if(dict,"comm",CL_COMM,True,"site",loc);
1224 st->resolver=find_cl_if(dict,"resolver",CL_RESOLVER,True,"site",loc);
1225 st->log=find_cl_if(dict,"log",CL_LOG,True,"site",loc);
1226 st->random=find_cl_if(dict,"random",CL_RANDOMSRC,True,"site",loc);
1228 st->privkey=find_cl_if(dict,"local-key",CL_RSAPRIVKEY,True,"site",loc);
1229 st->address=dict_read_string(dict, "address", False, "site", loc);
1231 st->remoteport=dict_read_number(dict,"port",True,"site",loc,0);
1232 else st->remoteport=0;
1233 st->pubkey=find_cl_if(dict,"key",CL_RSAPUBKEY,True,"site",loc);
1236 find_cl_if(dict,"transform",CL_TRANSFORM,True,"site",loc);
1238 st->dh=find_cl_if(dict,"dh",CL_DH,True,"site",loc);
1239 st->hash=find_cl_if(dict,"hash",CL_HASH,True,"site",loc);
1241 st->key_lifetime=dict_read_number(
1242 dict,"key-lifetime",False,"site",loc,DEFAULT_KEY_LIFETIME);
1243 if (st->key_lifetime < DEFAULT_KEY_RENEGOTIATE_GAP)
1244 st->key_renegotiate_time=st->key_lifetime/2;
1246 st->key_renegotiate_time=st->key_lifetime-DEFAULT_KEY_RENEGOTIATE_GAP;
1247 st->setup_retries=dict_read_number(
1248 dict,"setup-retries",False,"site",loc,DEFAULT_SETUP_RETRIES);
1249 st->setup_timeout=dict_read_number(
1250 dict,"setup-timeout",False,"site",loc,DEFAULT_SETUP_TIMEOUT);
1251 st->wait_timeout=dict_read_number(
1252 dict,"wait-time",False,"site",loc,DEFAULT_WAIT_TIME);
1253 st->key_renegotiate_time=dict_read_number(
1254 dict,"renegotiate-time",False,"site",loc,st->key_lifetime);
1255 if (st->key_renegotiate_time > st->key_lifetime) {
1256 cfgfatal(loc,"site",
1257 "renegotiate-time must be less than key-lifetime\n");
1259 st->keepalive=dict_read_bool(dict,"keepalive",False,"site",loc,False);
1261 st->log_events=string_list_to_word(dict_lookup(dict,"log-events"),
1262 log_event_table,"site");
1264 st->tunname=safe_malloc(strlen(st->localname)+strlen(st->remotename)+5,
1266 sprintf(st->tunname,"%s<->%s",st->localname,st->remotename);
1268 /* The information we expect to see in incoming messages of type 1 */
1269 st->setupsiglen=strlen(st->remotename)+strlen(st->localname)+8;
1270 st->setupsig=safe_malloc(st->setupsiglen,"site_apply");
1271 put_uint32(st->setupsig+0,LABEL_MSG1);
1272 put_uint16(st->setupsig+4,strlen(st->remotename));
1273 memcpy(&st->setupsig[6],st->remotename,strlen(st->remotename));
1274 put_uint16(st->setupsig+(6+strlen(st->remotename)),strlen(st->localname));
1275 memcpy(&st->setupsig[8+strlen(st->remotename)],st->localname,
1276 strlen(st->localname));
1277 st->setup_priority=(strcmp(st->localname,st->remotename)>0);
1279 buffer_new(&st->buffer,SETUP_BUFFER_LEN);
1281 /* We are interested in poll(), but only for timeouts. We don't have
1282 any fds of our own. */
1283 register_for_poll(st, site_beforepoll, site_afterpoll, 0, "site");
1286 st->current_valid=False;
1287 st->current_key_timeout=0;
1288 st->peer_valid=False;
1289 /* XXX mlock these */
1290 st->dhsecret=safe_malloc(st->dh->len,"site:dhsecret");
1291 st->sharedsecret=safe_malloc(st->transform->keylen,"site:sharedsecret");
1293 /* We need to register the remote networks with the netlink device */
1294 st->netlink->reg(st->netlink->st, site_outgoing, st,
1295 st->transform->max_start_pad+(4*4)+
1296 st->comm->min_start_pad,
1297 st->transform->max_end_pad+st->comm->min_end_pad);
1299 st->comm->request_notify(st->comm->st, st, site_incoming);
1301 st->current_transform=st->transform->create(st->transform->st);
1302 st->new_transform=st->transform->create(st->transform->st);
1304 enter_state_stop(st);
1306 add_hook(PHASE_SHUTDOWN,site_phase_hook,st);
1308 return new_closure(&st->cl);
1311 init_module site_module;
1312 void site_module(dict_t *dict)
1314 add_closure(dict,"site",site_apply);