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