3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
25 */
26
27 /*
28 * Dynamic Host Configuration Protocol version 6, for IPv6. Supports
29 * RFCs 3315, 3319, 3646, 3898, 4075, 4242, 4280, 4580, 4649, and 4704.
30 */
31
32 #include <ctype.h>
33 #include <stdio.h>
34 #include <stdlib.h>
35 #include <string.h>
36 #include <time.h>
37 #include <sys/types.h>
38 #include <sys/socket.h>
39 #include <netinet/in.h>
40 #include <netinet/dhcp6.h>
41 #include <arpa/inet.h>
42 #include <dhcp_impl.h>
567 oldprefix = prot_prefix;
568 oldnest = prot_nest_prefix;
569 str = malloc(strlen(prot_nest_prefix) + strlen(prot_prefix) + 1);
570 if (str == NULL) {
571 prot_nest_prefix = prot_prefix;
572 } else {
573 (void) sprintf(str, "%s%s", prot_nest_prefix, prot_prefix);
574 prot_nest_prefix = str;
575 }
576 show_header(prefix, title, 0);
577 show_options(data, olen);
578 free(str);
579 prot_prefix = oldprefix;
580 prot_nest_prefix = oldnest;
581 }
582
583 static void
584 show_options(const uint8_t *data, int len)
585 {
586 dhcpv6_option_t d6o;
587 uint_t olen, retlen;
588 uint16_t val16;
589 uint16_t type;
590 uint32_t val32;
591 const uint8_t *ostart;
592 char *str, *sp;
593 char *oldnest;
594
595 /*
596 * Be very careful with negative numbers; ANSI signed/unsigned
597 * comparison doesn't work as expected.
598 */
599 while (len >= (signed)sizeof (d6o)) {
600 (void) memcpy(&d6o, data, sizeof (d6o));
601 d6o.d6o_code = ntohs(d6o.d6o_code);
602 d6o.d6o_len = olen = ntohs(d6o.d6o_len);
603 (void) snprintf(get_line(0, 0), get_line_remain(),
604 "Option Code = %u (%s)", d6o.d6o_code,
605 option_to_str(d6o.d6o_code));
606 ostart = data += sizeof (d6o);
607 len -= sizeof (d6o);
749 get_line_remain(),
750 *data == 255 ?
751 " Preference = %u (immediate)" :
752 " Preference = %u", *data);
753 }
754 break;
755 case DHCPV6_OPT_ELAPSED_TIME:
756 if (olen == sizeof (val16)) {
757 (void) memcpy(&val16, data, sizeof (val16));
758 val16 = ntohs(val16);
759 (void) snprintf(get_line(0, 0),
760 get_line_remain(),
761 " Elapsed Time = %u.%02u seconds",
762 val16 / 100, val16 % 100);
763 }
764 break;
765 case DHCPV6_OPT_RELAY_MSG:
766 if (olen > 0) {
767 oldnest = prot_nest_prefix;
768 prot_nest_prefix = prot_prefix;
769 retlen = interpret_dhcpv6(F_DTAIL, data, olen);
770 prot_prefix = prot_nest_prefix;
771 prot_nest_prefix = oldnest;
772 }
773 break;
774 case DHCPV6_OPT_AUTH: {
775 dhcpv6_auth_t d6a;
776
777 if (olen < DHCPV6_AUTH_SIZE - sizeof (d6o))
778 break;
779 (void) memcpy(&d6a, data - sizeof (d6o),
780 DHCPV6_AUTH_SIZE);
781 data += DHCPV6_AUTH_SIZE - sizeof (d6o);
782 olen += DHCPV6_AUTH_SIZE - sizeof (d6o);
783 (void) snprintf(get_line(0, 0), get_line_remain(),
784 " Protocol = %u (%s)", d6a.d6a_proto,
785 authproto_to_str(d6a.d6a_proto));
786 (void) snprintf(get_line(0, 0), get_line_remain(),
787 " Algorithm = %u (%s)", d6a.d6a_alg,
788 authalg_to_str(d6a.d6a_proto, d6a.d6a_alg));
789 (void) snprintf(get_line(0, 0), get_line_remain(),
|
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright 2017 Gary Mills
24 * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
25 * Use is subject to license terms.
26 */
27
28 /*
29 * Dynamic Host Configuration Protocol version 6, for IPv6. Supports
30 * RFCs 3315, 3319, 3646, 3898, 4075, 4242, 4280, 4580, 4649, and 4704.
31 */
32
33 #include <ctype.h>
34 #include <stdio.h>
35 #include <stdlib.h>
36 #include <string.h>
37 #include <time.h>
38 #include <sys/types.h>
39 #include <sys/socket.h>
40 #include <netinet/in.h>
41 #include <netinet/dhcp6.h>
42 #include <arpa/inet.h>
43 #include <dhcp_impl.h>
568 oldprefix = prot_prefix;
569 oldnest = prot_nest_prefix;
570 str = malloc(strlen(prot_nest_prefix) + strlen(prot_prefix) + 1);
571 if (str == NULL) {
572 prot_nest_prefix = prot_prefix;
573 } else {
574 (void) sprintf(str, "%s%s", prot_nest_prefix, prot_prefix);
575 prot_nest_prefix = str;
576 }
577 show_header(prefix, title, 0);
578 show_options(data, olen);
579 free(str);
580 prot_prefix = oldprefix;
581 prot_nest_prefix = oldnest;
582 }
583
584 static void
585 show_options(const uint8_t *data, int len)
586 {
587 dhcpv6_option_t d6o;
588 uint_t olen;
589 uint16_t val16;
590 uint16_t type;
591 uint32_t val32;
592 const uint8_t *ostart;
593 char *str, *sp;
594 char *oldnest;
595
596 /*
597 * Be very careful with negative numbers; ANSI signed/unsigned
598 * comparison doesn't work as expected.
599 */
600 while (len >= (signed)sizeof (d6o)) {
601 (void) memcpy(&d6o, data, sizeof (d6o));
602 d6o.d6o_code = ntohs(d6o.d6o_code);
603 d6o.d6o_len = olen = ntohs(d6o.d6o_len);
604 (void) snprintf(get_line(0, 0), get_line_remain(),
605 "Option Code = %u (%s)", d6o.d6o_code,
606 option_to_str(d6o.d6o_code));
607 ostart = data += sizeof (d6o);
608 len -= sizeof (d6o);
750 get_line_remain(),
751 *data == 255 ?
752 " Preference = %u (immediate)" :
753 " Preference = %u", *data);
754 }
755 break;
756 case DHCPV6_OPT_ELAPSED_TIME:
757 if (olen == sizeof (val16)) {
758 (void) memcpy(&val16, data, sizeof (val16));
759 val16 = ntohs(val16);
760 (void) snprintf(get_line(0, 0),
761 get_line_remain(),
762 " Elapsed Time = %u.%02u seconds",
763 val16 / 100, val16 % 100);
764 }
765 break;
766 case DHCPV6_OPT_RELAY_MSG:
767 if (olen > 0) {
768 oldnest = prot_nest_prefix;
769 prot_nest_prefix = prot_prefix;
770 (void) interpret_dhcpv6(F_DTAIL, data, olen);
771 prot_prefix = prot_nest_prefix;
772 prot_nest_prefix = oldnest;
773 }
774 break;
775 case DHCPV6_OPT_AUTH: {
776 dhcpv6_auth_t d6a;
777
778 if (olen < DHCPV6_AUTH_SIZE - sizeof (d6o))
779 break;
780 (void) memcpy(&d6a, data - sizeof (d6o),
781 DHCPV6_AUTH_SIZE);
782 data += DHCPV6_AUTH_SIZE - sizeof (d6o);
783 olen += DHCPV6_AUTH_SIZE - sizeof (d6o);
784 (void) snprintf(get_line(0, 0), get_line_remain(),
785 " Protocol = %u (%s)", d6a.d6a_proto,
786 authproto_to_str(d6a.d6a_proto));
787 (void) snprintf(get_line(0, 0), get_line_remain(),
788 " Algorithm = %u (%s)", d6a.d6a_alg,
789 authalg_to_str(d6a.d6a_proto, d6a.d6a_alg));
790 (void) snprintf(get_line(0, 0), get_line_remain(),
|