1 /*
   2  * This file and its contents are supplied under the terms of the
   3  * Common Development and Distribution License ("CDDL"), version 1.0.
   4  * You may only use this file in accordance with the terms of version
   5  * 1.0 of the CDDL.
   6  *
   7  * A full copy of the text of the CDDL should have accompanied this
   8  * source.  A copy of the CDDL is also available via the Internet at
   9  * http://www.illumos.org/license/CDDL.
  10  */
  11 
  12 /*
  13  * Copyright (c) 2017 Joyent, Inc.
  14  */
  15 
  16 #include <pthread.h>
  17 #include <umem.h>
  18 #include <err.h>
  19 #include <sys/debug.h>
  20 #include <bunyan.h>
  21 #include <time.h>
  22 #include <string.h>
  23 #include "defs.h"
  24 #include "worker.h"
  25 #include "pkt.h"
  26 #include "timer.h"
  27 #include "pkcs11.h"
  28 #include "ikev2_proto.h"
  29 #include "ikev2_sa.h"
  30 #include "config.h"
  31 #include "ikev2_pkt.h"
  32 #include "ikev2_enum.h"
  33 
  34 static boolean_t find_config(pkt_t *, sockaddr_u_t, sockaddr_u_t);
  35 static boolean_t add_nat(pkt_t *);
  36 static boolean_t check_nats(pkt_t *);
  37 static void check_vendor(pkt_t *);
  38 static boolean_t add_vendor(pkt_t *);
  39 static boolean_t add_rule_proposals(pkt_t *restrict,
  40     const config_rule_t *restrict, uint64_t);
  41 static boolean_t add_cookie(pkt_t *restrict, void *restrict, size_t len);
  42 
  43 /*
  44  * New inbound IKE_SA_INIT exchange
  45  */
  46 void
  47 ikev2_sa_init_inbound_init(pkt_t *pkt)
  48 {
  49         ikev2_sa_t *sa = pkt->pkt_sa;
  50         pkt_t *resp = NULL;
  51         sockaddr_u_t laddr = { .sau_ss = &sa->laddr };
  52         sockaddr_u_t raddr = { .sau_ss = &sa->raddr };
  53         size_t noncelen = 0;
  54 
  55         VERIFY(!(sa->flags & I2SA_INITIATOR));
  56 
  57         if (!find_config(pkt, laddr, raddr))
  58                 goto fail;
  59         if (!check_nats(pkt))
  60                 goto fail;
  61         check_vendor(pkt);
  62 
  63         sa->init = pkt;
  64 
  65         resp = ikev2_pkt_new_response(pkt);
  66         if (resp == NULL)
  67                 goto fail;
  68 
  69         /* XXX: SA */
  70         /* XXX: KE */
  71 
  72         if (!ikev2_add_nonce(resp, noncelen))
  73                 goto fail;
  74         if (!add_nat(resp))
  75                 goto fail;
  76 
  77         /* XXX: other notifications */
  78 
  79         if (!add_vendor(resp))
  80                 goto fail;
  81 
  82         if (!ikev2_send(resp, B_FALSE))
  83                 goto fail;
  84         return;
  85 
  86 fail:
  87         ikev2_pkt_free(pkt);
  88         ikev2_pkt_free(resp);
  89         /* XXX: anything else */
  90 }
  91 
  92 void
  93 ikev2_sa_init_inbound_resp(pkt_t *pkt)
  94 {
  95         pkt_notify_t *cookie = pkt_get_notify(pkt, (uint16_t)IKEV2_N_COOKIE,
  96             NULL);
  97 
  98         if (cookie != NULL) {
  99                 pkt_t *out = pkt->pkt_sa->init;
 100 
 101                 if (!add_cookie(out, cookie->pn_ptr, cookie->pn_len) ||
 102                     !ikev2_send(out, B_FALSE)) {
 103                         /* XXX: destroy IKE SA */
 104                 }
 105                 return;
 106         }
 107 
 108 }
 109 
 110 void
 111 ikev2_sa_init_outbound(ikev2_sa_t *i2sa)
 112 {
 113         pkt_t *pkt = NULL;
 114         sockaddr_u_t laddr = { .sau_ss = &i2sa->laddr };
 115         sockaddr_u_t raddr = { .sau_ss = &i2sa->raddr };
 116         size_t noncelen = 0;
 117 
 118         VERIFY(i2sa->flags & I2SA_INITIATOR);
 119 
 120         pkt = ikev2_pkt_new_initiator(i2sa, IKEV2_EXCH_IKE_SA_INIT);
 121 
 122         if (!find_config(pkt, laddr, raddr))
 123                 goto fail;
 124 
 125         /* XXX: COOKIE */
 126 
 127         if (!add_rule_proposals(pkt, i2sa->i2sa_rule, 0))
 128                 goto fail;
 129 
 130         /* XXX: KE */
 131 
 132         if (!ikev2_add_nonce(pkt, noncelen))
 133                 goto fail;
 134         if (!add_nat(pkt))
 135                 goto fail;
 136         if (!add_vendor(pkt))
 137                 goto fail;
 138 
 139         /* XXX: CERTREQ */
 140 
 141         i2sa->init = pkt;
 142 
 143         if (!ikev2_send(pkt, B_FALSE))
 144                 goto fail;
 145         return;
 146 
 147 fail:
 148         ikev2_pkt_free(pkt);
 149         /* XXX: destroy SA? */
 150 }
 151 
 152 /*
 153  * XXX: These two functions should probably be moved at some point so they
 154  * can be used both for initial IKE SA creation and for IKE re-keying
 155  * (which operates as a type of CREATE_CHILD_SA exchange
 156  */
 157 static boolean_t
 158 add_rule_xform(pkt_t *restrict pkt, const config_xf_t *restrict xf)
 159 {
 160         encr_modes_t mode = ikev2_encr_mode(xf->xf_encr);
 161         boolean_t ok = B_TRUE;
 162 
 163         ok &= ikev2_add_xf_encr(pkt, xf->xf_encr, xf->xf_minbits,
 164             xf->xf_maxbits);
 165 
 166         /*
 167          * For all currently known combined mode ciphers, we don't need
 168          * to also include an integrity transform
 169          */
 170         if (!MODE_IS_COMBINED(mode))
 171                 ok &= ikev2_add_xform(pkt, IKEV2_XF_AUTH, xf->xf_auth);
 172 
 173         ok &= ikev2_add_xform(pkt, IKEV2_XF_DH, xf->xf_dh);
 174 
 175         /*
 176          * XXX: IKEV1 determined the PRF based on the authentication method.
 177          * IKEV2 allows it to be negotiated separately.  Eventually we
 178          * should probably add an option to specify it in a transform
 179          * definition.  For now, we just include all the ones we support
 180          * in decreasing order of preference.
 181          */
 182         ikev2_prf_t supported[] = {
 183             IKEV2_PRF_HMAC_SHA2_512,
 184             IKEV2_PRF_HMAC_SHA2_384,
 185             IKEV2_PRF_HMAC_SHA2_256,
 186             IKEV2_PRF_HMAC_SHA1,
 187             IKEV2_PRF_HMAC_MD5
 188         };
 189 
 190         for (size_t i = 0; i < ARRAY_SIZE(supported); i++)
 191                 ok &= ikev2_add_xform(pkt, IKEV2_XF_PRF, supported[i]);
 192 
 193         return (ok);
 194 }
 195 
 196 static boolean_t
 197 add_rule_proposals(pkt_t *restrict pkt, const config_rule_t *restrict rule,
 198     uint64_t spi)
 199 {
 200         boolean_t ok = B_TRUE;
 201 
 202         if (!ikev2_add_sa(pkt))
 203                 return (B_FALSE);
 204 
 205         for (uint8_t i = 0; rule->rule_xf[i] != NULL; i++) {
 206                 /* RFC7296 3.3.1 proposal numbers start with 1 */
 207                 ok &= ikev2_add_prop(pkt, i + 1, IKEV2_PROTO_IKE, spi);
 208                 ok &= add_rule_xform(pkt, rule->rule_xf[i]);
 209         }
 210 
 211         return (ok);
 212 }
 213 
 214 static boolean_t
 215 find_config(pkt_t *pkt, sockaddr_u_t laddr, sockaddr_u_t raddr)
 216 {
 217         ikev2_sa_t *sa = pkt->pkt_sa;
 218 
 219         sa->i2sa_rule = config_get_rule(&laddr, &raddr);
 220 
 221         if (sa->i2sa_rule->rule_xf[0] == NULL) {
 222                 bunyan_debug(sa->i2sa_log, "No rules found", BUNYAN_T_END);
 223                 ikev2_no_proposal_chosen(sa, pkt, IKEV2_PROTO_IKE, 0);
 224                 return (B_FALSE);
 225         }
 226 
 227         if (RULE_IS_DEFAULT(sa->i2sa_rule)) {
 228                 bunyan_debug(sa->i2sa_log, "Using default rule", BUNYAN_T_END);
 229         } else {
 230                 bunyan_debug(sa->i2sa_log, "Found rule",
 231                     BUNYAN_T_STRING, "label", sa->i2sa_rule->rule_label,
 232                     BUNYAN_T_END);
 233         }
 234         return (B_TRUE);
 235 }
 236 
 237 #define NAT_LEN (20)
 238 /*
 239  * Check if the NAT {src,dest} payload matches our IP address.
 240  * Return 0 if match (i.e. no nat)
 241  *     1 if match
 242  *     -1 on error
 243  */
 244 static int
 245 check_one_nat(pkt_t *pkt, pkt_notify_t *n)
 246 {
 247         bunyan_logger_t *l = pkt->pkt_sa->i2sa_log;
 248         CK_SESSION_HANDLE h = p11h;
 249         sockaddr_u_t addr;
 250         CK_MECHANISM mech = { .mechanism = CKM_SHA_1 };
 251         buf_t buf[3];
 252         CK_BYTE data[NAT_LEN] = { 0 };
 253         buf_t out = { .b_ptr = data, .b_len = sizeof (data) };
 254         CK_LONG len = 0;
 255         CK_RV rv;
 256 
 257         switch (n->pn_type) {
 258         case IKEV2_N_NAT_DETECTION_SOURCE_IP:
 259                 addr.sau_ss = &pkt->pkt_sa->laddr;
 260                 break;
 261         case IKEV2_N_NAT_DETECTION_DESTINATION_IP:
 262                 addr.sau_ss = &pkt->pkt_sa->raddr;
 263                 break;
 264         default:
 265                 INVALID(n->pn_type);
 266                 /*NOTREACHED*/
 267                 return (-1);
 268         }
 269 
 270         buf[0].b_ptr = (CK_BYTE_PTR)&pkt->pkt_raw;
 271         buf[0].b_len = 2 * sizeof (uint64_t);
 272 
 273         switch (addr.sau_ss->ss_family) {
 274         case AF_INET:
 275                 buf[1].b_ptr = (CK_BYTE_PTR)&addr.sau_sin->sin_addr;
 276                 buf[1].b_len = sizeof (in_addr_t);
 277                 buf[2].b_ptr = (CK_BYTE_PTR)&addr.sau_sin->sin_port;
 278                 buf[2].b_len = sizeof (addr.sau_sin->sin_port);
 279                 break;
 280         case AF_INET6:
 281                 buf[1].b_ptr = (CK_BYTE_PTR)&addr.sau_sin6->sin6_addr;
 282                 buf[1].b_len = sizeof (in6_addr_t);
 283                 buf[2].b_ptr = (CK_BYTE_PTR)&addr.sau_sin6->sin6_port;
 284                 buf[2].b_len = sizeof (addr.sau_sin6->sin6_port);
 285                 break;
 286         default:
 287                 INVALID("addr.sau_ss->ss_family");
 288                 return (-1);
 289         }
 290 
 291         if (n->pn_len != NAT_LEN) {
 292                 bunyan_error(l, "Invalid notify payload size",
 293                     BUNYAN_T_STRING, "notify_type",
 294                     ikev2_notify_str(n->pn_type),
 295                     BUNYAN_T_UINT32, "payload_size", (uint32_t)n->pn_len,
 296                     BUNYAN_T_UINT32, "expected_size", (uint32_t)NAT_LEN,
 297                     BUNYAN_T_END);
 298                 return (-1);
 299         }
 300 
 301         if (!pkcs11_digest(CKM_SHA_1, buf, ARRAY_SIZE(buf), &out, l))
 302                 return (-1);
 303 
 304         VERIFY3U(n->pn_len, ==, sizeof (data));
 305         if (memcmp(n->pn_ptr, data, sizeof (data)) == 0)
 306                 return (0);
 307 
 308         return (1);
 309 }
 310 
 311 /*
 312  * Perform NAT detection and update IKEV2 SA accordingly.  Return B_FALSE on
 313  * error, B_TRUE if no error.
 314  */
 315 static boolean_t
 316 check_nats(pkt_t *pkt)
 317 {
 318         ikev2_sa_t *sa = pkt->pkt_sa;
 319         pkt_notify_t *n = NULL;
 320         int rc = 0;
 321         boolean_t local_nat = B_TRUE;
 322         boolean_t remote_nat = B_TRUE;
 323 
 324         /*
 325          * Since the SOURCE/DESTINATION designation is from the perspective
 326          * of the remote side, the local/remote notion is reversed on our
 327          * side.
 328          */
 329         n = pkt_get_notify(pkt, IKEV2_N_NAT_DETECTION_SOURCE_IP, NULL);
 330         if (n == NULL) {
 331                 /* If the notification isn't present, assume no NAT */
 332                 remote_nat = B_FALSE;
 333         } else {
 334                 while (n != NULL) {
 335                         rc = check_one_nat(pkt, n);
 336                         if (rc == -1) {
 337                                 return (B_FALSE);
 338                         } else if (rc == 0) {
 339                                 remote_nat = B_FALSE;
 340                                 break;
 341                         }
 342                         n = pkt_get_notify(pkt,
 343                             IKEV2_N_NAT_DETECTION_SOURCE_IP, n);
 344                 }
 345         }
 346 
 347         if (remote_nat) {
 348                 bunyan_debug(sa->i2sa_log, "Remote NAT detected", BUNYAN_T_END);
 349                 sa->flags |= I2SA_NAT_REMOTE;
 350         }
 351 
 352         n = pkt_get_notify(pkt, IKEV2_N_NAT_DETECTION_DESTINATION_IP, NULL);
 353         if (n == NULL) {
 354                 /* Similar as above */
 355                 local_nat = B_FALSE;
 356         } else {
 357                 while (n != NULL) {
 358                         rc = check_one_nat(pkt, n);
 359                         if (rc == -1) {
 360                                 return (B_FALSE);
 361                         } else if (rc == 0) {
 362                                 local_nat = B_FALSE;
 363                                 break;
 364                         }
 365                         n = pkt_get_notify(pkt,
 366                             IKEV2_N_NAT_DETECTION_DESTINATION_IP, n);
 367                 }
 368         }
 369 
 370         if (local_nat) {
 371                 bunyan_debug(sa->i2sa_log, "Local NAT detected", BUNYAN_T_END);
 372                 sa->flags |= I2SA_NAT_LOCAL;
 373         }
 374 
 375         return (B_TRUE);
 376 }
 377 
 378 /*
 379  * RFC7296 2.23 -- Add NAT detection notifiation payloads.  The notification
 380  * payload consists of the SHA-1 has of the SPIs (in order as they appear in
 381  * the header), IP address, and port.
 382  */
 383 static boolean_t
 384 add_nat(pkt_t *pkt)
 385 {
 386         bunyan_logger_t *l = pkt->pkt_sa->i2sa_log;
 387         sockaddr_u_t addr[2];
 388         uint64_t spi[2];
 389         ikev2_notify_type_t ntype[2];
 390         buf_t buf[3];
 391 
 392         addr[0].sau_ss = &pkt->pkt_sa->laddr;
 393         addr[1].sau_ss = &pkt->pkt_sa->raddr;
 394         ntype[0] = IKEV2_N_NAT_DETECTION_SOURCE_IP;
 395         ntype[1] = IKEV2_N_NAT_DETECTION_DESTINATION_IP;
 396 
 397         /*
 398          * These normally don't get converted to network byte order until
 399          * the packet has finished construction, so we need to do local
 400          * conversion for the NAT payload creation
 401          */
 402         spi[0] = htonll(pkt->pkt_header.initiator_spi);
 403         spi[1] = htonll(pkt->pkt_header.responder_spi);
 404 
 405         buf[0].b_ptr = (CK_BYTE_PTR)&spi;
 406         buf[0].b_len = sizeof (spi);
 407 
 408         for (int i = 0; i < 2; i++) {
 409                 uchar_t data[NAT_LEN] = { 0 };
 410                 buf_t out = { .b_ptr = data, .b_len = sizeof (data) };
 411 
 412                 switch (addr[i].sau_ss->ss_family) {
 413                 case AF_INET:
 414                         buf[1].b_ptr = (CK_BYTE_PTR)&addr[i].sau_sin->sin_addr;
 415                         buf[1].b_len = sizeof (in_addr_t);
 416                         buf[2].b_ptr = (CK_BYTE_PTR)&addr[i].sau_sin->sin_port;
 417                         buf[2].b_len = sizeof (addr[i].sau_sin->sin_port);
 418                         break;
 419                 case AF_INET6:
 420                         buf[1].b_ptr =
 421                             (CK_BYTE_PTR)&addr[i].sau_sin6->sin6_addr;
 422                         buf[1].b_len = sizeof (in6_addr_t);
 423                         buf[2].b_ptr =
 424                             (CK_BYTE_PTR)&addr[i].sau_sin6->sin6_port;
 425                         buf[2].b_len = sizeof (addr[i].sau_sin6->sin6_port);
 426                         break;
 427                 default:
 428                         INVALID("addr.sau_ss->ss_family");
 429                         return (B_FALSE);
 430                 }
 431 
 432                 if (!pkcs11_digest(CKM_SHA_1, buf, ARRAY_SIZE(buf), &out, l))
 433                         return (B_FALSE);
 434 
 435                 if (!ikev2_add_notify(pkt, IKEV2_PROTO_IKE, 0, ntype[i],
 436                      data, sizeof (data)))
 437                         return (B_FALSE);
 438         }
 439 
 440         return (B_TRUE);
 441 }
 442 
 443 static void
 444 check_vendor(pkt_t *pkt)
 445 {
 446         ikev2_sa_t *sa = pkt->pkt_sa;
 447 
 448         for (uint16_t i = 0; i < pkt->pkt_payload_count; i++) {
 449                 pkt_payload_t *pay = pkt_payload(pkt, i);
 450 
 451                 if (pay->pp_type != IKEV2_PAYLOAD_VENDOR)
 452                         continue;
 453                 if (pay->pp_len != sizeof (VENDOR_STR_ILLUMOS_1))
 454                         continue;
 455 
 456                 if (memcmp(VENDOR_STR_ILLUMOS_1, pay->pp_ptr,
 457                     sizeof (VENDOR_STR_ILLUMOS_1)) == 0) {
 458                         bunyan_debug(sa->i2sa_log,
 459                             "Found illumos_1 vendor payload", BUNYAN_T_END);
 460                         sa->vendor = VENDOR_ILLUMOS_1;
 461                 }
 462         }
 463 }
 464 
 465 static boolean_t
 466 add_vendor(pkt_t *pkt)
 467 {
 468         return (ikev2_add_vendor(pkt, (uchar_t *)VENDOR_STR_ILLUMOS_1,
 469             sizeof (VENDOR_STR_ILLUMOS_1)));
 470 }
 471 
 472 static boolean_t
 473 add_cookie(pkt_t *restrict pkt, void *restrict cookie, size_t len)
 474 {
 475         pkt_notify_t *n = pkt_get_notify(pkt, IKEV2_N_COOKIE, NULL);
 476         uint8_t *start = (uint8_t *)pkt_start(pkt) + sizeof (ike_header_t) +
 477             sizeof (ikev2_payload_t);
 478         ssize_t total = sizeof (ikev2_payload_t) + sizeof (ikev2_notify_t) +
 479             len;
 480         size_t num = 1;
 481         ikev2_notify_t ntfy = {
 482             .n_protoid = IKEV2_PROTO_IKE,
 483             .n_spisize = 0,
 484             .n_type = htons((uint16_t)IKEV2_N_COOKIE)
 485         };
 486 
 487         /*
 488          * If there's no existing cookie payload, make room for one,
 489          * otherwise just shift existing payloads (if necessary) to reuse
 490          * existing cookie payload
 491          */
 492         if (n == NULL) {
 493                 total += sizeof (ikev2_payload_t) + sizeof (ikev2_notify_t);
 494                 num = 1;
 495         } else {
 496                 /* Per RFC7296 2.6, this better be the first payload */
 497                 VERIFY3P(start, ==, (uint8_t *)n->pn_ptr);
 498                 total += len - (ssize_t)n->pn_len;
 499                 num = 0;
 500         }
 501 
 502         if (total > 0 && pkt_write_left(pkt) < total)
 503                 return (B_FALSE);
 504 
 505         if (!(pkt->pkt_header.flags & IKEV2_FLAG_INITIATOR)) {
 506                 /* Simple case, we are responding with own cookie */
 507 
 508                 /* Should be the only payload */
 509                 VERIFY3U(pkt->pkt_payload_count, ==, 0);
 510 
 511                 return (ikev2_add_notify(pkt, IKEV2_PROTO_IKE, 0,
 512                     IKEV2_N_COOKIE, cookie, len));
 513         }
 514 
 515         /* Make room to insert new first payload */
 516         if (!pkt_pay_shift(pkt, (uint8_t)IKEV2_PAYLOAD_NOTIFY, num, total))
 517                 return (B_FALSE);
 518 
 519         (void) memcpy(start, &ntfy, sizeof (ntfy));
 520         (void) memcpy(start + sizeof (ntfy), cookie, len);
 521         return (B_TRUE);
 522 }