test-policy.c revision 78064
162583Sitojun/* $FreeBSD: head/lib/libipsec/test-policy.c 78064 2001-06-11 12:39:29Z ume $ */ 278064Sume/* $KAME: test-policy.c,v 1.14 2000/12/27 11:38:11 sakane Exp $ */ 362583Sitojun 455505Sshin/* 555505Sshin * Copyright (C) 1995, 1996, 1997, 1998, and 1999 WIDE Project. 655505Sshin * All rights reserved. 755505Sshin * 855505Sshin * Redistribution and use in source and binary forms, with or without 955505Sshin * modification, are permitted provided that the following conditions 1055505Sshin * are met: 1155505Sshin * 1. Redistributions of source code must retain the above copyright 1255505Sshin * notice, this list of conditions and the following disclaimer. 1355505Sshin * 2. Redistributions in binary form must reproduce the above copyright 1455505Sshin * notice, this list of conditions and the following disclaimer in the 1555505Sshin * documentation and/or other materials provided with the distribution. 1655505Sshin * 3. Neither the name of the project nor the names of its contributors 1755505Sshin * may be used to endorse or promote products derived from this software 1855505Sshin * without specific prior written permission. 1955505Sshin * 2055505Sshin * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 2155505Sshin * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 2255505Sshin * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2355505Sshin * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 2455505Sshin * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2555505Sshin * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2655505Sshin * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2755505Sshin * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2855505Sshin * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2955505Sshin * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 3055505Sshin * SUCH DAMAGE. 3155505Sshin */ 3255505Sshin 3355505Sshin#include <sys/types.h> 3455505Sshin#include <sys/param.h> 3555505Sshin#include <sys/socket.h> 3655505Sshin 3755505Sshin#include <netinet/in.h> 3857855Sshin#include <net/pfkeyv2.h> 3955505Sshin#include <netkey/key_debug.h> 4055505Sshin#include <netinet6/ipsec.h> 4155505Sshin 4255505Sshin#include <stdio.h> 4355505Sshin#include <stdlib.h> 4455505Sshin#include <unistd.h> 4555505Sshin#include <string.h> 4662583Sitojun#include <errno.h> 4755505Sshin#include <err.h> 4855505Sshin 4978064Sume#include "libpfkey.h" 5078064Sume 5162583Sitojunstruct req_t { 5262583Sitojun int result; /* expected result; 0:ok 1:ng */ 5362583Sitojun char *str; 5462583Sitojun} reqs[] = { 5562583Sitojun{ 0, "out ipsec" }, 5662583Sitojun{ 1, "must_error" }, 5762583Sitojun{ 1, "in ipsec must_error" }, 5862583Sitojun{ 1, "out ipsec esp/must_error" }, 5962583Sitojun{ 1, "out discard" }, 6062583Sitojun{ 1, "out none" }, 6162583Sitojun{ 0, "in entrust" }, 6262583Sitojun{ 0, "out entrust" }, 6362583Sitojun{ 1, "out ipsec esp" }, 6462583Sitojun{ 0, "in ipsec ah/transport" }, 6562583Sitojun{ 1, "in ipsec ah/tunnel" }, 6662583Sitojun{ 0, "out ipsec ah/transport/" }, 6762583Sitojun{ 1, "out ipsec ah/tunnel/" }, 6862583Sitojun{ 0, "in ipsec esp / transport / 10.0.0.1-10.0.0.2" }, 6962583Sitojun{ 0, "in ipsec esp/tunnel/::1-::2" }, 7062583Sitojun{ 1, "in ipsec esp/tunnel/10.0.0.1-::2" }, 7162583Sitojun{ 0, "in ipsec esp/tunnel/::1-::2/require" }, 7262583Sitojun{ 0, "out ipsec ah/transport//use" }, 7362583Sitojun{ 1, "out ipsec ah/transport esp/use" }, 7462583Sitojun{ 1, "in ipsec ah/transport esp/tunnel" }, 7562583Sitojun{ 0, "in ipsec ah/transport esp/tunnel/::1-::1" }, 7662583Sitojun{ 0, "in ipsec 7755505Sshin ah / transport 7862583Sitojun esp / tunnel / ::1-::2" }, 7962583Sitojun{ 0, "out ipsec 8062583Sitojun ah/transport/::1-::2 esp/tunnel/::3-::4/use ah/transport/::5-::6/require 8162583Sitojun ah/transport/::1-::2 esp/tunnel/::3-::4/use ah/transport/::5-::6/require 8262583Sitojun ah/transport/::1-::2 esp/tunnel/::3-::4/use ah/transport/::5-::6/require 8362583Sitojun " }, 8462583Sitojun{ 0, "out ipsec esp/transport/fec0::10-fec0::11/use" }, 8555505Sshin}; 8655505Sshin 8762583Sitojunint test1 __P((void)); 8862583Sitojunint test1sub1 __P((struct req_t *)); 8962583Sitojunint test1sub2 __P((char *, int)); 9062583Sitojunint test2 __P((void)); 9162583Sitojunint test2sub __P((int)); 9255505Sshin 9355505Sshinint 9455505Sshinmain(ac, av) 9555505Sshin int ac; 9655505Sshin char **av; 9755505Sshin{ 9862583Sitojun test1(); 9962583Sitojun test2(); 10062583Sitojun 10162583Sitojun exit(0); 10262583Sitojun} 10362583Sitojun 10462583Sitojunint 10562583Sitojuntest1() 10662583Sitojun{ 10755505Sshin int i; 10862583Sitojun int result; 10955505Sshin 11062583Sitojun printf("TEST1\n"); 11162583Sitojun for (i = 0; i < sizeof(reqs)/sizeof(reqs[0]); i++) { 11262583Sitojun printf("#%d [%s]\n", i + 1, reqs[i].str); 11355505Sshin 11462583Sitojun result = test1sub1(&reqs[i]); 11562583Sitojun if (result == 0 && reqs[i].result == 1) { 11678064Sume warnx("ERROR: expecting failure.\n"); 11762583Sitojun } else if (result == 1 && reqs[i].result == 0) { 11878064Sume warnx("ERROR: expecting success.\n"); 11955505Sshin } 12062583Sitojun } 12155505Sshin 12262583Sitojun return 0; 12362583Sitojun} 12455505Sshin 12562583Sitojunint 12662583Sitojuntest1sub1(req) 12762583Sitojun struct req_t *req; 12862583Sitojun{ 12962583Sitojun char *buf; 13055505Sshin 13162583Sitojun buf = ipsec_set_policy(req->str, strlen(req->str)); 13262583Sitojun if (buf == NULL) { 13362583Sitojun printf("ipsec_set_policy: %s\n", ipsec_strerror()); 13462583Sitojun return 1; 13562583Sitojun } 13662583Sitojun 13762583Sitojun if (test1sub2(buf, PF_INET) != 0 13862583Sitojun || test1sub2(buf, PF_INET6) != 0) { 13955505Sshin free(buf); 14062583Sitojun return 1; 14155505Sshin } 14262583Sitojun#if 0 14362583Sitojun kdebug_sadb_x_policy((struct sadb_ext *)buf); 14462583Sitojun#endif 14555505Sshin 14662583Sitojun free(buf); 14755505Sshin return 0; 14855505Sshin} 14955505Sshin 15055505Sshinint 15162583Sitojuntest1sub2(policy, family) 15255505Sshin char *policy; 15355505Sshin int family; 15455505Sshin{ 15562583Sitojun int so; 15662583Sitojun int proto = 0, optname = 0; 15755505Sshin int len; 15855505Sshin char getbuf[1024]; 15955505Sshin 16055505Sshin switch (family) { 16155505Sshin case PF_INET: 16255505Sshin proto = IPPROTO_IP; 16355505Sshin optname = IP_IPSEC_POLICY; 16455505Sshin break; 16555505Sshin case PF_INET6: 16655505Sshin proto = IPPROTO_IPV6; 16755505Sshin optname = IPV6_IPSEC_POLICY; 16855505Sshin break; 16955505Sshin } 17055505Sshin 17155505Sshin if ((so = socket(family, SOCK_DGRAM, 0)) < 0) 17255505Sshin err(1, "socket"); 17355505Sshin 17455505Sshin len = ipsec_get_policylen(policy); 17562583Sitojun#if 0 17662583Sitojun printf("\tsetlen:%d\n", len); 17762583Sitojun#endif 17862583Sitojun 17955505Sshin if (setsockopt(so, proto, optname, policy, len) < 0) { 18062583Sitojun printf("fail to set sockopt; %s\n", strerror(errno)); 18162583Sitojun close(so); 18262583Sitojun return 1; 18355505Sshin } 18455505Sshin 18555505Sshin memset(getbuf, 0, sizeof(getbuf)); 18662583Sitojun memcpy(getbuf, policy, sizeof(struct sadb_x_policy)); 18755505Sshin if (getsockopt(so, proto, optname, getbuf, &len) < 0) { 18862583Sitojun printf("fail to get sockopt; %s\n", strerror(errno)); 18962583Sitojun close(so); 19062583Sitojun return 1; 19155505Sshin } 19255505Sshin 19355505Sshin { 19455505Sshin char *buf = NULL; 19555505Sshin 19662583Sitojun#if 0 19755505Sshin printf("\tgetlen:%d\n", len); 19862583Sitojun#endif 19955505Sshin 20055505Sshin if ((buf = ipsec_dump_policy(getbuf, NULL)) == NULL) { 20155505Sshin printf("%s\n", ipsec_strerror()); 20262583Sitojun close(so); 20362583Sitojun return 1; 20455505Sshin } 20562583Sitojun#if 0 20662583Sitojun printf("\t[%s]\n", buf); 20762583Sitojun#endif 20862583Sitojun free(buf); 20955505Sshin } 21055505Sshin 21155505Sshin close (so); 21262583Sitojun return 0; 21362583Sitojun} 21455505Sshin 21562583Sitojunchar addr[] = { 21662583Sitojun 28, 28, 0, 0, 21762583Sitojun 0, 0, 0, 0, 21862583Sitojun 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 21962583Sitojun 0, 0, 0, 0, 22062583Sitojun}; 22162583Sitojun 22262583Sitojunint 22362583Sitojuntest2() 22462583Sitojun{ 22562583Sitojun int so; 22662583Sitojun char *pol1 = "out ipsec"; 22762583Sitojun char *pol2 = "out ipsec ah/transport//use"; 22862583Sitojun char *sp1, *sp2; 22962583Sitojun int splen1, splen2; 23062583Sitojun int spid; 23162583Sitojun struct sadb_msg *m; 23262583Sitojun 23362583Sitojun printf("TEST2\n"); 23462583Sitojun if (getuid() != 0) 23562583Sitojun errx(1, "root privilege required.\n"); 23662583Sitojun 23762583Sitojun sp1 = ipsec_set_policy(pol1, strlen(pol1)); 23862583Sitojun splen1 = ipsec_get_policylen(sp1); 23962583Sitojun sp2 = ipsec_set_policy(pol2, strlen(pol2)); 24062583Sitojun splen2 = ipsec_get_policylen(sp2); 24162583Sitojun 24262583Sitojun if ((so = pfkey_open()) < 0) 24362583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 24462583Sitojun 24562583Sitojun printf("spdflush()\n"); 24662583Sitojun if (pfkey_send_spdflush(so) < 0) 24762583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 24862583Sitojun m = pfkey_recv(so); 24962583Sitojun free(m); 25078064Sume 25178064Sume#if 0 25262583Sitojun printf("spdsetidx()\n"); 25362583Sitojun if (pfkey_send_spdsetidx(so, (struct sockaddr *)addr, 128, 25462583Sitojun (struct sockaddr *)addr, 128, 25562583Sitojun 255, sp1, splen1, 0) < 0) 25662583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 25762583Sitojun m = pfkey_recv(so); 25862583Sitojun free(m); 25962583Sitojun 26062583Sitojun printf("spdupdate()\n"); 26162583Sitojun if (pfkey_send_spdupdate(so, (struct sockaddr *)addr, 128, 26262583Sitojun (struct sockaddr *)addr, 128, 26362583Sitojun 255, sp2, splen2, 0) < 0) 26462583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 26562583Sitojun m = pfkey_recv(so); 26662583Sitojun free(m); 26762583Sitojun 26878064Sume sleep(4); 26978064Sume 27062583Sitojun printf("spddelete()\n"); 27162583Sitojun if (pfkey_send_spddelete(so, (struct sockaddr *)addr, 128, 27262583Sitojun (struct sockaddr *)addr, 128, 27362583Sitojun 255, sp1, splen1, 0) < 0) 27462583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 27562583Sitojun m = pfkey_recv(so); 27662583Sitojun free(m); 27762583Sitojun 27862583Sitojun printf("spdadd()\n"); 27962583Sitojun if (pfkey_send_spdadd(so, (struct sockaddr *)addr, 128, 28062583Sitojun (struct sockaddr *)addr, 128, 28162583Sitojun 255, sp2, splen2, 0) < 0) 28262583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 28362583Sitojun spid = test2sub(so); 28462583Sitojun 28562583Sitojun printf("spdget(%u)\n", spid); 28662583Sitojun if (pfkey_send_spdget(so, spid) < 0) 28762583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 28862583Sitojun m = pfkey_recv(so); 28962583Sitojun free(m); 29062583Sitojun 29178064Sume sleep(4); 29278064Sume 29362583Sitojun printf("spddelete2()\n"); 29462583Sitojun if (pfkey_send_spddelete2(so, spid) < 0) 29562583Sitojun errx(1, "ERROR: %s\n", ipsec_strerror()); 29662583Sitojun m = pfkey_recv(so); 29762583Sitojun free(m); 29878064Sume#endif 29962583Sitojun 30078064Sume printf("spdadd() with lifetime's 10(s)\n"); 30178064Sume if (pfkey_send_spdadd2(so, (struct sockaddr *)addr, 128, 30278064Sume (struct sockaddr *)addr, 128, 30378064Sume 255, 0, 10, sp2, splen2, 0) < 0) 30478064Sume errx(1, "ERROR: %s\n", ipsec_strerror()); 30578064Sume spid = test2sub(so); 30678064Sume 30778064Sume#if 0 30862583Sitojun /* expecting failure */ 30962583Sitojun printf("spdupdate()\n"); 31062583Sitojun if (pfkey_send_spdupdate(so, (struct sockaddr *)addr, 128, 31162583Sitojun (struct sockaddr *)addr, 128, 31262583Sitojun 255, sp2, splen2, 0) == 0) { 31378064Sume warnx("ERROR: expecting failure.\n"); 31462583Sitojun } 31578064Sume#endif 31662583Sitojun 31755505Sshin return 0; 31855505Sshin} 31955505Sshin 32062583Sitojunint 32162583Sitojuntest2sub(so) 32262583Sitojun int so; 32362583Sitojun{ 32462583Sitojun struct sadb_msg *msg; 32562583Sitojun caddr_t mhp[SADB_EXT_MAX + 1]; 32662583Sitojun 32762583Sitojun if ((msg = pfkey_recv(so)) == NULL) 32862583Sitojun errx(1, "ERROR: pfkey_recv failure.\n"); 32962583Sitojun if (pfkey_align(msg, mhp) < 0) 33062583Sitojun errx(1, "ERROR: pfkey_align failure.\n"); 33162583Sitojun 33262583Sitojun return ((struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY])->sadb_x_policy_id; 33362583Sitojun} 33462583Sitojun 335