1 /* $FreeBSD$ */ 2 /* $KAME: test-pfkey.c,v 1.4 2000/06/07 00:29:14 itojun Exp $ */ 3 4 /*- 5 * SPDX-License-Identifier: BSD-3-Clause 6 * 7 * Copyright (C) 1995, 1996, 1997, 1998, and 1999 WIDE Project. 8 * All rights reserved. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 3. Neither the name of the project nor the names of its contributors 19 * may be used to endorse or promote products derived from this software 20 * without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 25 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 32 * SUCH DAMAGE. 33 */ 34 35 #include <sys/types.h> 36 #include <sys/param.h> 37 #include <sys/socket.h> 38 #include <net/route.h> 39 #include <net/pfkeyv2.h> 40 #include <netinet/in.h> 41 #include <netipsec/keydb.h> 42 #include <netipsec/key_var.h> 43 #include <netipsec/key_debug.h> 44 45 #include <stdio.h> 46 #include <stdlib.h> 47 #include <limits.h> 48 #include <string.h> 49 #include <ctype.h> 50 #include <unistd.h> 51 #include <errno.h> 52 #include <netdb.h> 53 54 u_char m_buf[BUFSIZ]; 55 u_int m_len; 56 char *pname; 57 58 void Usage(void); 59 int sendkeymsg(void); 60 void key_setsadbmsg(u_int); 61 void key_setsadbsens(void); 62 void key_setsadbprop(void); 63 void key_setsadbid(u_int, caddr_t); 64 void key_setsadblft(u_int, u_int); 65 void key_setspirange(void); 66 void key_setsadbkey(u_int, caddr_t); 67 void key_setsadbsa(void); 68 void key_setsadbaddr(u_int, u_int, caddr_t); 69 void key_setsadbextbuf(caddr_t, int, caddr_t, int, caddr_t, int); 70 71 void 72 Usage() 73 { 74 printf("Usage:\t%s number\n", pname); 75 exit(0); 76 } 77 78 int 79 main(ac, av) 80 int ac; 81 char **av; 82 { 83 pname = *av; 84 85 if (ac == 1) Usage(); 86 87 key_setsadbmsg(atoi(*(av+1))); 88 sendkeymsg(); 89 90 exit(0); 91 } 92 93 /* %%% */ 94 int 95 sendkeymsg() 96 { 97 u_char rbuf[1024 * 32]; /* XXX: Enough ? Should I do MSG_PEEK ? */ 98 int so, len; 99 100 if ((so = socket(PF_KEY, SOCK_RAW, PF_KEY_V2)) < 0) { 101 perror("socket(PF_KEY)"); 102 goto end; 103 } 104 #if 0 105 { 106 #include <sys/time.h> 107 struct timeval tv; 108 tv.tv_sec = 1; 109 tv.tv_usec = 0; 110 if (setsockopt(so, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof(tv)) < 0) { 111 perror("setsockopt"); 112 goto end; 113 } 114 } 115 #endif 116 117 pfkey_sadump((struct sadb_msg *)m_buf); 118 119 if ((len = send(so, m_buf, m_len, 0)) < 0) { 120 perror("send"); 121 goto end; 122 } 123 124 if ((len = recv(so, rbuf, sizeof(rbuf), 0)) < 0) { 125 perror("recv"); 126 goto end; 127 } 128 129 pfkey_sadump((struct sadb_msg *)rbuf); 130 131 end: 132 (void)close(so); 133 return(0); 134 } 135 136 void 137 key_setsadbmsg(type) 138 u_int type; 139 { 140 struct sadb_msg m_msg; 141 142 memset(&m_msg, 0, sizeof(m_msg)); 143 m_msg.sadb_msg_version = PF_KEY_V2; 144 m_msg.sadb_msg_type = type; 145 m_msg.sadb_msg_errno = 0; 146 m_msg.sadb_msg_satype = SADB_SATYPE_ESP; 147 #if 0 148 m_msg.sadb_msg_reserved = 0; 149 #endif 150 m_msg.sadb_msg_seq = 0; 151 m_msg.sadb_msg_pid = getpid(); 152 153 m_len = sizeof(struct sadb_msg); 154 memcpy(m_buf, &m_msg, m_len); 155 156 switch (type) { 157 case SADB_GETSPI: 158 /*<base, address(SD), SPI range>*/ 159 key_setsadbaddr(SADB_EXT_ADDRESS_SRC, AF_INET, "10.0.3.4"); 160 key_setsadbaddr(SADB_EXT_ADDRESS_DST, AF_INET, "127.0.0.1"); 161 key_setspirange(); 162 /*<base, SA(*), address(SD)>*/ 163 break; 164 165 case SADB_ADD: 166 /* <base, SA, (lifetime(HSC),) address(SD), (address(P),) 167 key(AE), (identity(SD),) (sensitivity)> */ 168 key_setsadbaddr(SADB_EXT_ADDRESS_PROXY, AF_INET6, "3ffe::1"); 169 case SADB_UPDATE: 170 key_setsadbsa(); 171 key_setsadblft(SADB_EXT_LIFETIME_HARD, 10); 172 key_setsadblft(SADB_EXT_LIFETIME_SOFT, 5); 173 key_setsadbaddr(SADB_EXT_ADDRESS_SRC, AF_INET, "192.168.1.1"); 174 key_setsadbaddr(SADB_EXT_ADDRESS_DST, AF_INET, "10.0.3.4"); 175 /* XXX key_setsadbkey(SADB_EXT_KEY_AUTH, "abcde"); */ 176 key_setsadbkey(SADB_EXT_KEY_AUTH, "1234567812345678"); 177 key_setsadbkey(SADB_EXT_KEY_ENCRYPT, "12345678"); 178 key_setsadbid(SADB_EXT_IDENTITY_SRC, "hoge1234@hoge.com"); 179 key_setsadbid(SADB_EXT_IDENTITY_DST, "hage5678@hage.net"); 180 key_setsadbsens(); 181 /* <base, SA, (lifetime(HSC),) address(SD), (address(P),) 182 (identity(SD),) (sensitivity)> */ 183 break; 184 185 case SADB_DELETE: 186 /* <base, SA(*), address(SDP)> */ 187 key_setsadbsa(); 188 key_setsadbaddr(SADB_EXT_ADDRESS_SRC, AF_INET, "192.168.1.1"); 189 key_setsadbaddr(SADB_EXT_ADDRESS_DST, AF_INET, "10.0.3.4"); 190 key_setsadbaddr(SADB_EXT_ADDRESS_PROXY, AF_INET6, "3ffe::1"); 191 /* <base, SA(*), address(SDP)> */ 192 break; 193 194 case SADB_GET: 195 /* <base, SA(*), address(SDP)> */ 196 key_setsadbsa(); 197 key_setsadbaddr(SADB_EXT_ADDRESS_SRC, AF_INET, "192.168.1.1"); 198 key_setsadbaddr(SADB_EXT_ADDRESS_DST, AF_INET, "10.0.3.4"); 199 key_setsadbaddr(SADB_EXT_ADDRESS_PROXY, AF_INET6, "3ffe::1"); 200 /* <base, SA, (lifetime(HSC),) address(SD), (address(P),) 201 key(AE), (identity(SD),) (sensitivity)> */ 202 break; 203 204 case SADB_ACQUIRE: 205 /* <base, address(SD), (address(P),) (identity(SD),) 206 (sensitivity,) proposal> */ 207 key_setsadbaddr(SADB_EXT_ADDRESS_SRC, AF_INET, "192.168.1.1"); 208 key_setsadbaddr(SADB_EXT_ADDRESS_DST, AF_INET, "10.0.3.4"); 209 key_setsadbaddr(SADB_EXT_ADDRESS_PROXY, AF_INET6, "3ffe::1"); 210 key_setsadbid(SADB_EXT_IDENTITY_SRC, "hoge1234@hoge.com"); 211 key_setsadbid(SADB_EXT_IDENTITY_DST, "hage5678@hage.net"); 212 key_setsadbsens(); 213 key_setsadbprop(); 214 /* <base, address(SD), (address(P),) (identity(SD),) 215 (sensitivity,) proposal> */ 216 break; 217 218 case SADB_REGISTER: 219 /* <base> */ 220 /* <base, supported> */ 221 break; 222 223 case SADB_EXPIRE: 224 case SADB_FLUSH: 225 break; 226 227 case SADB_DUMP: 228 break; 229 230 case SADB_X_PROMISC: 231 /* <base> */ 232 /* <base, base(, others)> */ 233 break; 234 235 case SADB_X_PCHANGE: 236 break; 237 238 /* for SPD management */ 239 case SADB_X_SPDFLUSH: 240 case SADB_X_SPDDUMP: 241 break; 242 243 case SADB_X_SPDADD: 244 #if 0 245 { 246 struct sadb_x_policy m_policy; 247 248 m_policy.sadb_x_policy_len = PFKEY_UNIT64(sizeof(m_policy)); 249 m_policy.sadb_x_policy_exttype = SADB_X_EXT_POLICY; 250 m_policy.sadb_x_policy_type = SADB_X_PL_IPSEC; 251 m_policy.sadb_x_policy_esp_trans = 1; 252 m_policy.sadb_x_policy_ah_trans = 2; 253 m_policy.sadb_x_policy_esp_network = 3; 254 m_policy.sadb_x_policy_ah_network = 4; 255 m_policy.sadb_x_policy_reserved = 0; 256 257 memcpy(m_buf + m_len, &m_policy, sizeof(struct sadb_x_policy)); 258 m_len += sizeof(struct sadb_x_policy); 259 } 260 #endif 261 262 case SADB_X_SPDDELETE: 263 key_setsadbaddr(SADB_EXT_ADDRESS_SRC, AF_INET, "192.168.1.1"); 264 key_setsadbaddr(SADB_EXT_ADDRESS_DST, AF_INET, "10.0.3.4"); 265 break; 266 } 267 268 ((struct sadb_msg *)m_buf)->sadb_msg_len = PFKEY_UNIT64(m_len); 269 270 return; 271 } 272 273 void 274 key_setsadbsens() 275 { 276 struct sadb_sens m_sens; 277 u_char buf[64]; 278 u_int s, i, slen, ilen, len; 279 280 /* make sens & integ */ 281 s = htonl(0x01234567); 282 i = htonl(0x89abcdef); 283 slen = sizeof(s); 284 ilen = sizeof(i); 285 memcpy(buf, &s, slen); 286 memcpy(buf + slen, &i, ilen); 287 288 len = sizeof(m_sens) + PFKEY_ALIGN8(slen) + PFKEY_ALIGN8(ilen); 289 m_sens.sadb_sens_len = PFKEY_UNIT64(len); 290 m_sens.sadb_sens_exttype = SADB_EXT_SENSITIVITY; 291 m_sens.sadb_sens_dpd = 1; 292 m_sens.sadb_sens_sens_level = 2; 293 m_sens.sadb_sens_sens_len = PFKEY_ALIGN8(slen); 294 m_sens.sadb_sens_integ_level = 3; 295 m_sens.sadb_sens_integ_len = PFKEY_ALIGN8(ilen); 296 m_sens.sadb_sens_reserved = 0; 297 298 key_setsadbextbuf(m_buf, m_len, 299 (caddr_t)&m_sens, sizeof(struct sadb_sens), 300 buf, slen + ilen); 301 m_len += len; 302 303 return; 304 } 305 306 void 307 key_setsadbprop() 308 { 309 struct sadb_prop m_prop; 310 struct sadb_comb *m_comb; 311 u_char buf[256]; 312 u_int len = sizeof(m_prop) + sizeof(m_comb) * 2; 313 314 /* make prop & comb */ 315 m_prop.sadb_prop_len = PFKEY_UNIT64(len); 316 m_prop.sadb_prop_exttype = SADB_EXT_PROPOSAL; 317 m_prop.sadb_prop_replay = 0; 318 m_prop.sadb_prop_reserved[0] = 0; 319 m_prop.sadb_prop_reserved[1] = 0; 320 m_prop.sadb_prop_reserved[2] = 0; 321 322 /* the 1st is ESP DES-CBC HMAC-MD5 */ 323 m_comb = (struct sadb_comb *)buf; 324 m_comb->sadb_comb_auth = SADB_AALG_MD5HMAC; 325 m_comb->sadb_comb_encrypt = SADB_EALG_DESCBC; 326 m_comb->sadb_comb_flags = 0; 327 m_comb->sadb_comb_auth_minbits = 8; 328 m_comb->sadb_comb_auth_maxbits = 96; 329 m_comb->sadb_comb_encrypt_minbits = 64; 330 m_comb->sadb_comb_encrypt_maxbits = 64; 331 m_comb->sadb_comb_reserved = 0; 332 m_comb->sadb_comb_soft_allocations = 0; 333 m_comb->sadb_comb_hard_allocations = 0; 334 m_comb->sadb_comb_soft_bytes = 0; 335 m_comb->sadb_comb_hard_bytes = 0; 336 m_comb->sadb_comb_soft_addtime = 0; 337 m_comb->sadb_comb_hard_addtime = 0; 338 m_comb->sadb_comb_soft_usetime = 0; 339 m_comb->sadb_comb_hard_usetime = 0; 340 341 /* the 2st is ESP 3DES-CBC and AH HMAC-SHA1 */ 342 m_comb = (struct sadb_comb *)(buf + sizeof(*m_comb)); 343 m_comb->sadb_comb_auth = SADB_AALG_SHA1HMAC; 344 m_comb->sadb_comb_encrypt = SADB_EALG_3DESCBC; 345 m_comb->sadb_comb_flags = 0; 346 m_comb->sadb_comb_auth_minbits = 8; 347 m_comb->sadb_comb_auth_maxbits = 96; 348 m_comb->sadb_comb_encrypt_minbits = 64; 349 m_comb->sadb_comb_encrypt_maxbits = 64; 350 m_comb->sadb_comb_reserved = 0; 351 m_comb->sadb_comb_soft_allocations = 0; 352 m_comb->sadb_comb_hard_allocations = 0; 353 m_comb->sadb_comb_soft_bytes = 0; 354 m_comb->sadb_comb_hard_bytes = 0; 355 m_comb->sadb_comb_soft_addtime = 0; 356 m_comb->sadb_comb_hard_addtime = 0; 357 m_comb->sadb_comb_soft_usetime = 0; 358 m_comb->sadb_comb_hard_usetime = 0; 359 360 key_setsadbextbuf(m_buf, m_len, 361 (caddr_t)&m_prop, sizeof(struct sadb_prop), 362 buf, sizeof(*m_comb) * 2); 363 m_len += len; 364 365 return; 366 } 367 368 void 369 key_setsadbid(ext, str) 370 u_int ext; 371 caddr_t str; 372 { 373 struct sadb_ident m_id; 374 u_int idlen = strlen(str), len; 375 376 len = sizeof(m_id) + PFKEY_ALIGN8(idlen); 377 m_id.sadb_ident_len = PFKEY_UNIT64(len); 378 m_id.sadb_ident_exttype = ext; 379 m_id.sadb_ident_type = SADB_IDENTTYPE_USERFQDN; 380 m_id.sadb_ident_reserved = 0; 381 m_id.sadb_ident_id = getpid(); 382 383 key_setsadbextbuf(m_buf, m_len, 384 (caddr_t)&m_id, sizeof(struct sadb_ident), 385 str, idlen); 386 m_len += len; 387 388 return; 389 } 390 391 void 392 key_setsadblft(ext, time) 393 u_int ext, time; 394 { 395 struct sadb_lifetime m_lft; 396 397 m_lft.sadb_lifetime_len = PFKEY_UNIT64(sizeof(m_lft)); 398 m_lft.sadb_lifetime_exttype = ext; 399 m_lft.sadb_lifetime_allocations = 0x2; 400 m_lft.sadb_lifetime_bytes = 0x1000; 401 m_lft.sadb_lifetime_addtime = time; 402 m_lft.sadb_lifetime_usetime = 0x0020; 403 404 memcpy(m_buf + m_len, &m_lft, sizeof(struct sadb_lifetime)); 405 m_len += sizeof(struct sadb_lifetime); 406 407 return; 408 } 409 410 void 411 key_setspirange() 412 { 413 struct sadb_spirange m_spi; 414 415 m_spi.sadb_spirange_len = PFKEY_UNIT64(sizeof(m_spi)); 416 m_spi.sadb_spirange_exttype = SADB_EXT_SPIRANGE; 417 m_spi.sadb_spirange_min = 0x00001000; 418 m_spi.sadb_spirange_max = 0x00002000; 419 m_spi.sadb_spirange_reserved = 0; 420 421 memcpy(m_buf + m_len, &m_spi, sizeof(struct sadb_spirange)); 422 m_len += sizeof(struct sadb_spirange); 423 424 return; 425 } 426 427 void 428 key_setsadbkey(ext, str) 429 u_int ext; 430 caddr_t str; 431 { 432 struct sadb_key m_key; 433 u_int keylen = strlen(str); 434 u_int len; 435 436 len = sizeof(struct sadb_key) + PFKEY_ALIGN8(keylen); 437 m_key.sadb_key_len = PFKEY_UNIT64(len); 438 m_key.sadb_key_exttype = ext; 439 m_key.sadb_key_bits = keylen * 8; 440 m_key.sadb_key_reserved = 0; 441 442 key_setsadbextbuf(m_buf, m_len, 443 (caddr_t)&m_key, sizeof(struct sadb_key), 444 str, keylen); 445 m_len += len; 446 447 return; 448 } 449 450 void 451 key_setsadbsa() 452 { 453 struct sadb_sa m_sa; 454 455 m_sa.sadb_sa_len = PFKEY_UNIT64(sizeof(struct sadb_sa)); 456 m_sa.sadb_sa_exttype = SADB_EXT_SA; 457 m_sa.sadb_sa_spi = htonl(0x12345678); 458 m_sa.sadb_sa_replay = 4; 459 m_sa.sadb_sa_state = 0; 460 m_sa.sadb_sa_auth = SADB_AALG_MD5HMAC; 461 m_sa.sadb_sa_encrypt = SADB_EALG_DESCBC; 462 m_sa.sadb_sa_flags = 0; 463 464 memcpy(m_buf + m_len, &m_sa, sizeof(struct sadb_sa)); 465 m_len += sizeof(struct sadb_sa); 466 467 return; 468 } 469 470 void 471 key_setsadbaddr(ext, af, str) 472 u_int ext, af; 473 caddr_t str; 474 { 475 struct sadb_address m_addr; 476 u_int len; 477 struct addrinfo hints, *res; 478 const char *serv; 479 int plen; 480 481 switch (af) { 482 case AF_INET: 483 plen = sizeof(struct in_addr) << 3; 484 break; 485 case AF_INET6: 486 plen = sizeof(struct in6_addr) << 3; 487 break; 488 default: 489 /* XXX bark */ 490 exit(1); 491 } 492 493 /* make sockaddr buffer */ 494 memset(&hints, 0, sizeof(hints)); 495 hints.ai_family = af; 496 hints.ai_socktype = SOCK_DGRAM; /*dummy*/ 497 hints.ai_flags = AI_NUMERICHOST; 498 serv = (ext == SADB_EXT_ADDRESS_PROXY ? "0" : "4660"); /*0x1234*/ 499 if (getaddrinfo(str, serv, &hints, &res) != 0 || res->ai_next) { 500 /* XXX bark */ 501 exit(1); 502 } 503 504 len = sizeof(struct sadb_address) + PFKEY_ALIGN8(res->ai_addrlen); 505 m_addr.sadb_address_len = PFKEY_UNIT64(len); 506 m_addr.sadb_address_exttype = ext; 507 m_addr.sadb_address_proto = 508 (ext == SADB_EXT_ADDRESS_PROXY ? 0 : IPPROTO_TCP); 509 m_addr.sadb_address_prefixlen = plen; 510 m_addr.sadb_address_reserved = 0; 511 512 key_setsadbextbuf(m_buf, m_len, 513 (caddr_t)&m_addr, sizeof(struct sadb_address), 514 (caddr_t)res->ai_addr, res->ai_addrlen); 515 m_len += len; 516 517 freeaddrinfo(res); 518 519 return; 520 } 521 522 void 523 key_setsadbextbuf(dst, off, ebuf, elen, vbuf, vlen) 524 caddr_t dst, ebuf, vbuf; 525 int off, elen, vlen; 526 { 527 memset(dst + off, 0, elen + vlen); 528 memcpy(dst + off, (caddr_t)ebuf, elen); 529 memcpy(dst + off + elen, vbuf, vlen); 530 531 return; 532 } 533 534