1 /* 2 * CDDL HEADER START 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 2010 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 /* 28 * Copyright 2012 David Hoeppner. All rights reserved. 29 */ 30 31 /* 32 * Functions related to MIB-II and kstat. 33 */ 34 35 #include <sys/types.h> 36 #include <sys/tihdr.h> 37 #include <sys/policy.h> 38 #include <sys/tsol/tnet.h> 39 40 #include <inet/common.h> 41 #include <inet/ip.h> 42 #include <inet/kstatcom.h> 43 #include <inet/snmpcom.h> 44 45 #include <sys/cmn_err.h> 46 47 #include "dccp_impl.h" 48 49 static int dccp_snmp_state(dccp_t *); 50 51 static int 52 dccp_snmp_state(dccp_t *dccp) 53 { 54 if (dccp == NULL) { 55 return (0); 56 } 57 58 switch(dccp->dccp_state) { 59 case DCCPS_CLOSED: 60 return (MIB2_DCCP_closed); 61 default: 62 return (0); 63 } 64 } 65 66 /* 67 * Get the MIB-II stats. 68 */ 69 mblk_t * 70 dccp_snmp_get(queue_t *q, mblk_t *mpctl) 71 { 72 conn_t *connp = Q_TO_CONN(q); 73 connf_t *connfp; 74 ip_stack_t *ips; 75 dccp_stack_t *dccps; 76 struct opthdr *optp; 77 mblk_t *mp2ctl; 78 mblk_t *mpdata; 79 mblk_t *mp_conn_ctl = NULL; 80 mblk_t *mp_conn_tail; 81 mblk_t *mp_attr_ctl = NULL; 82 mblk_t *mp_attr_tail; 83 size_t dccp_mib_size; 84 size_t dce_size; 85 zoneid_t zoneid; 86 int i; 87 mib2_dccpConnEntry_t dce; 88 89 mp2ctl = copymsg(mpctl); 90 91 if (mpctl == NULL || 92 (mpdata = mpctl->b_cont) == NULL || 93 (mp_conn_ctl = copymsg(mpctl)) == NULL || 94 (mp_attr_ctl = copymsg(mpctl)) == NULL) { 95 freemsg(mp_conn_ctl); 96 freemsg(mp_attr_ctl); 97 freemsg(mpctl); 98 freemsg(mp2ctl); 99 return (NULL); 100 } 101 102 ips = connp->conn_netstack->netstack_ip; 103 dccps = connp->conn_netstack->netstack_dccp; 104 dce_size = sizeof (mib2_dccpConnEntry_t); 105 zoneid = Q_TO_CONN(q)->conn_zoneid; 106 107 for (i = 0; i < CONN_G_HASH_SIZE; i++) { 108 ips = dccps->dccps_netstack->netstack_ip; 109 110 connfp = &ips->ips_ipcl_globalhash_fanout[i]; 111 connp = NULL; 112 113 while ((connp = ipcl_get_next_conn(connfp, connp, 114 IPCL_DCCPCONN)) != NULL) { 115 dccp_t *dccp; 116 117 if (connp->conn_zoneid != zoneid) { 118 continue; 119 } 120 121 dccp = connp->conn_dccp; 122 123 dce.dccpConnState = dccp_snmp_state(dccp); 124 125 if (connp->conn_ipversion == IPV4_VERSION || 126 (dccp->dccp_state <= DCCPS_LISTEN)) { 127 dce.dccpConnRemAddress = 128 connp->conn_faddr_v4; 129 dce.dccpConnLocalAddress = 130 connp->conn_laddr_v4; 131 } 132 133 dce.dccpConnLocalPort = ntohs(connp->conn_lport); 134 dce.dccpConnRemPort = ntohs(connp->conn_fport); 135 136 dce.dccpConnCreationProcess = (connp->conn_cpid < 0) ? 137 MIB2_UNKNOWN_PROCESS : connp->conn_cpid; 138 dce.dccpConnCreationTime = connp->conn_open_time; 139 140 (void) snmp_append_data2(mp_conn_ctl->b_cont, 141 &mp_conn_tail, (char *)&dce, dce_size); 142 } 143 } 144 145 optp = (struct opthdr *)&mp_conn_ctl->b_rptr[ 146 sizeof (struct T_optmgmt_ack)]; 147 optp->level = MIB2_DCCP; 148 optp->name = MIB2_DCCP_CONN; 149 optp->len = msgdsize(mp_conn_ctl->b_cont); 150 qreply(q, mp_conn_ctl); 151 152 return (mp2ctl); 153 }