[BACK]Return to atalk.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / netstat

Annotation of src/usr.bin/netstat/atalk.c, Revision 1.19

1.19    ! blambert    1: /*     $OpenBSD: atalk.c,v 1.18 2010/05/23 10:12:42 chl Exp $  */
1.1       denny       2: /*     $NetBSD: atalk.c,v 1.2 1997/05/22 17:21:26 christos Exp $       */
                      3:
                      4: /*
                      5:  * Copyright (c) 1983, 1988, 1993
                      6:  *     The Regents of the University of California.  All rights reserved.
                      7:  *
                      8:  * Redistribution and use in source and binary forms, with or without
                      9:  * modification, are permitted provided that the following conditions
                     10:  * are met:
                     11:  * 1. Redistributions of source code must retain the above copyright
                     12:  *    notice, this list of conditions and the following disclaimer.
                     13:  * 2. Redistributions in binary form must reproduce the above copyright
                     14:  *    notice, this list of conditions and the following disclaimer in the
                     15:  *    documentation and/or other materials provided with the distribution.
1.11      millert    16:  * 3. Neither the name of the University nor the names of its contributors
1.1       denny      17:  *    may be used to endorse or promote products derived from this software
                     18:  *    without specific prior written permission.
                     19:  *
                     20:  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
                     21:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     22:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     23:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
                     24:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     25:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     26:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     27:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     28:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     29:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     30:  * SUCH DAMAGE.
                     31:  */
                     32:
                     33: #include <sys/param.h>
                     34: #include <sys/queue.h>
                     35: #include <sys/socket.h>
                     36: #include <sys/socketvar.h>
                     37: #include <sys/mbuf.h>
                     38: #include <sys/protosw.h>
1.15      deraadt    39: #include <sys/sysctl.h>
1.1       denny      40: #include <netdb.h>
                     41:
                     42: #include <net/route.h>
                     43: #include <net/if.h>
                     44:
                     45: /* #include <netinet/tcp_fsm.h> */
                     46:
                     47: #include <netatalk/at.h>
                     48: #include <netatalk/ddp_var.h>
                     49:
1.17      chl        50: #include <err.h>
1.1       denny      51: #include <errno.h>
                     52: #include <stdio.h>
                     53: #include <string.h>
                     54: #include "netstat.h"
                     55:
                     56: struct ddpcb    ddpcb;
                     57: struct socket   sockb;
                     58:
                     59: static int first = 1;
                     60:
1.7       millert    61: static char *at_pr_net(struct sockaddr_at *, int);
                     62: static char *at_pr_host(struct sockaddr_at *, int);
                     63: static char *at_pr_range(struct sockaddr_at *);
                     64: static char *at_pr_port(struct sockaddr_at *);
1.1       denny      65:
                     66: /*
                     67:  * Print a summary of connections related to a Network Systems
                     68:  * protocol.  For XXX, also give state of connection.
                     69:  * Listening processes (aflag) are suppressed unless the
                     70:  * -a (all) flag is specified.
                     71:  */
                     72:
                     73: static char *
1.10      deraadt    74: at_pr_net(struct sockaddr_at *sat, int numeric)
1.1       denny      75: {
                     76:        static char mybuf[50];
                     77:
                     78:        if (!numeric) {
                     79:                switch (sat->sat_addr.s_net) {
                     80:                case 0xffff:
                     81:                        return "????";
                     82:                case ATADDR_ANYNET:
                     83:                        return ("*");
                     84:                }
                     85:        }
1.6       mickey     86:        (void) snprintf(mybuf, sizeof(mybuf), "%hu",
1.1       denny      87:            ntohs(sat->sat_addr.s_net));
                     88:        return mybuf;
                     89: }
                     90:
                     91: static char *
1.10      deraadt    92: at_pr_host(struct sockaddr_at *sat, int numeric)
1.1       denny      93: {
                     94:        static char mybuf[50];
                     95:
                     96:        if (!numeric) {
                     97:                switch (sat->sat_addr.s_node) {
                     98:                case ATADDR_BCAST:
                     99:                        return "bcast";
                    100:                case ATADDR_ANYNODE:
                    101:                        return ("*");
                    102:                }
                    103:        }
1.6       mickey    104:        (void) snprintf(mybuf, sizeof(mybuf), "%d",
1.1       denny     105:            (unsigned int) sat->sat_addr.s_node);
                    106:        return mybuf;
                    107: }
                    108:
                    109: static char *
1.10      deraadt   110: at_pr_port(struct sockaddr_at *sat)
1.1       denny     111: {
                    112:        static char mybuf[50];
                    113:        struct servent *serv;
                    114:
                    115:        switch (sat->sat_port) {
                    116:        case ATADDR_ANYPORT:
                    117:                return ("*");
                    118:        case 0xff:
                    119:                return "????";
                    120:        default:
                    121:                if (nflag)
                    122:                        (void) snprintf(mybuf, sizeof(mybuf), "%d",
                    123:                            (unsigned int) sat->sat_port);
                    124:                else {
                    125:                        serv = getservbyport(sat->sat_port, "ddp");
                    126:                        if (serv == NULL)
                    127:                                (void) snprintf(mybuf, sizeof(mybuf), "%d",
                    128:                                    (unsigned int) sat->sat_port);
                    129:                        else
                    130:                                (void) snprintf(mybuf, sizeof(mybuf), "%s",
                    131:                                    serv->s_name);
                    132:                }
1.6       mickey    133:
1.1       denny     134:                return mybuf;
                    135:        }
                    136: }
                    137:
                    138: static char *
1.10      deraadt   139: at_pr_range(struct sockaddr_at *sat)
1.1       denny     140: {
                    141:        static char mybuf[50];
                    142:
1.10      deraadt   143:        if (sat->sat_range.r_netrange.nr_firstnet !=
                    144:            sat->sat_range.r_netrange.nr_lastnet) {
1.1       denny     145:                (void) snprintf(mybuf, sizeof(mybuf), "%d-%d",
1.8       deraadt   146:                    ntohs(sat->sat_range.r_netrange.nr_firstnet),
                    147:                    ntohs(sat->sat_range.r_netrange.nr_lastnet));
1.1       denny     148:        } else {
                    149:                (void) snprintf(mybuf, sizeof(mybuf), "%d",
1.8       deraadt   150:                    ntohs(sat->sat_range.r_netrange.nr_firstnet));
1.1       denny     151:        }
                    152:        return mybuf;
                    153: }
                    154:
                    155:
                    156: /* what == 0 for addr only == 3
                    157:  *     1 for net
                    158:  *     2 for host
                    159:  *     4 for port
                    160:  *     8 for numeric only
                    161:  */
                    162: char *
1.10      deraadt   163: atalk_print(const struct sockaddr *sa, int what)
1.1       denny     164: {
                    165:        struct sockaddr_at *sat = (struct sockaddr_at *) sa;
                    166:        static char mybuf[50];
                    167:        int numeric = (what & 0x08);
                    168:
                    169:        mybuf[0] = 0;
                    170:        switch (what & 0x13) {
                    171:        case 0:
                    172:                mybuf[0] = 0;
                    173:                break;
                    174:        case 1:
                    175:                (void) snprintf(mybuf, sizeof(mybuf), "%s",
                    176:                    at_pr_net(sat, numeric));
                    177:                break;
                    178:        case 2:
                    179:                (void) snprintf(mybuf, sizeof(mybuf), "%s",
                    180:                    at_pr_host(sat, numeric));
                    181:                break;
                    182:        case 3:
                    183:                (void) snprintf(mybuf, sizeof(mybuf), "%s.%s",
1.8       deraadt   184:                    at_pr_net(sat, numeric),
                    185:                    at_pr_host(sat, numeric));
1.1       denny     186:                break;
                    187:        case 0x10:
                    188:                (void) snprintf(mybuf, sizeof(mybuf), "%s", at_pr_range(sat));
                    189:        }
                    190:        if (what & 4) {
                    191:                (void) snprintf(mybuf + strlen(mybuf),
                    192:                    sizeof(mybuf) - strlen(mybuf), ".%s",
                    193:                    at_pr_port(sat));
                    194:        }
                    195:        return mybuf;
                    196: }
                    197:
                    198: void
1.19    ! blambert  199: atalkprotopr(u_long off, char *name, int af)
1.1       denny     200: {
                    201:        struct ddpcb    cb;
1.5       mpech     202:        struct ddpcb *prev, *next;
1.1       denny     203:        struct ddpcb   *initial;
                    204:
                    205:        if (off == 0)
                    206:                return;
1.13      jaredy    207:        if (kread(off, &initial, sizeof(struct ddpcb *)) < 0)
1.1       denny     208:                return;
                    209:        ddpcb = cb;
                    210:        prev = (struct ddpcb *) off;
                    211:        for (next = initial; next != NULL; prev = next) {
1.6       mickey    212:                u_long  ppcb = (u_long) next;
1.1       denny     213:
1.13      jaredy    214:                if (kread((u_long) next, &ddpcb, sizeof(ddpcb)) < 0)
1.1       denny     215:                        return;
                    216:                next = ddpcb.ddp_next;
                    217: #if 0
                    218:                if (!aflag && atalk_nullhost(ddpcb.ddp_lsat)) {
                    219:                        continue;
                    220:                }
                    221: #endif
1.13      jaredy    222:                if (kread((u_long) ddpcb.ddp_socket, &sockb,
                    223:                    sizeof(sockb)) < 0)
1.1       denny     224:                        return;
                    225:                if (first) {
                    226:                        printf("Active ATALK connections");
                    227:                        if (aflag)
                    228:                                printf(" (including servers)");
                    229:                        putchar('\n');
                    230:                        if (Aflag)
                    231:                                printf("%-8.8s ", "PCB");
                    232:                        printf(Aflag ?
                    233:                            "%-5.5s %-6.6s %-6.6s  %-18.18s %-18.18s %s\n" :
1.8       deraadt   234:                            "%-5.5s %-6.6s %-6.6s  %-22.22s %-22.22s %s\n",
                    235:                            "Proto", "Recv-Q", "Send-Q",
                    236:                            "Local Address", "Foreign Address", "(state)");
1.1       denny     237:                        first = 0;
                    238:                }
                    239:                if (Aflag)
                    240:                        printf("%8lx ", ppcb);
                    241:                printf("%-5.5s %6ld %6ld ", name, sockb.so_rcv.sb_cc,
1.6       mickey    242:                    sockb.so_snd.sb_cc);
1.1       denny     243:                printf(Aflag ? " %-18.18s" : " %-22.22s", atalk_print(
1.8       deraadt   244:                    (struct sockaddr *) & ddpcb.ddp_lsat, 7));
1.1       denny     245:                printf(Aflag ? " %-18.18s" : " %-22.22s", atalk_print(
1.8       deraadt   246:                    (struct sockaddr *) & ddpcb.ddp_fsat, 7));
1.1       denny     247:                putchar('\n');
                    248:        }
                    249: }
                    250:
                    251: #define p(f, m) if (ddpstat.f || sflag <= 1) \
1.8       deraadt   252:        printf(m, ddpstat.f, plural(ddpstat.f))
1.1       denny     253: #define p2(f1, f2, m) if (ddpstat.f1 || ddpstat.f2 || sflag <= 1) \
1.8       deraadt   254:        printf(m, ddpstat.f1, plural(ddpstat.f1), ddpstat.f2, plural(ddpstat.f2))
1.1       denny     255: #define p3(f, m) if (ddpstat.f || sflag <= 1) \
1.8       deraadt   256:        printf(m, ddpstat.f, plurales(ddpstat.f))
1.1       denny     257:
                    258: /*
                    259:  * Dump DDP statistics structure.
                    260:  */
                    261: void
1.15      deraadt   262: ddp_stats(char *name)
1.1       denny     263: {
                    264:        struct ddpstat  ddpstat;
1.15      deraadt   265:        int mib[] = { CTL_NET, AF_APPLETALK, ATPROTO_DDP, DDPCTL_STATS };
                    266:        size_t len = sizeof(ddpstat);
1.1       denny     267:
1.15      deraadt   268:        if (sysctl(mib, sizeof(mib) / sizeof(mib[0]),
                    269:            &ddpstat, &len, NULL, 0) == -1) {
                    270:                if (errno != ENOPROTOOPT)
                    271:                        warn(name);
1.1       denny     272:                return;
1.15      deraadt   273:        }
                    274:
1.1       denny     275:        printf("%s:\n", name);
                    276:        p(ddps_short, "\t%ld packet%s with short headers\n");
                    277:        p(ddps_long, "\t%ld packet%s with long headers\n");
                    278:        p(ddps_nosum, "\t%ld packet%s with no checksum\n");
                    279:        p(ddps_tooshort, "\t%ld packet%s were too short\n");
                    280:        p(ddps_badsum, "\t%ld packet%s with bad checksum\n");
                    281:        p(ddps_toosmall, "\t%ld packet%s with not enough data\n");
                    282:        p(ddps_forward, "\t%ld packet%s forwarded\n");
                    283:        p(ddps_cantforward, "\t%ld packet%s rcvd for unreachable dest\n");
                    284:        p(ddps_nosockspace, "\t%ld packet%s dropped due to no socket space\n");
                    285: }