10Sstevel@tonic-gate /*
20Sstevel@tonic-gate * CDDL HEADER START
30Sstevel@tonic-gate *
40Sstevel@tonic-gate * The contents of this file are subject to the terms of the
50Sstevel@tonic-gate * Common Development and Distribution License, Version 1.0 only
60Sstevel@tonic-gate * (the "License"). You may not use this file except in compliance
70Sstevel@tonic-gate * with the License.
80Sstevel@tonic-gate *
90Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
100Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing.
110Sstevel@tonic-gate * See the License for the specific language governing permissions
120Sstevel@tonic-gate * and limitations under the License.
130Sstevel@tonic-gate *
140Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each
150Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
160Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the
170Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying
180Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner]
190Sstevel@tonic-gate *
200Sstevel@tonic-gate * CDDL HEADER END
210Sstevel@tonic-gate */
220Sstevel@tonic-gate /*
23*410Skcpoon * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
24*410Skcpoon * Use is subject to license terms.
250Sstevel@tonic-gate */
260Sstevel@tonic-gate
27*410Skcpoon #pragma ident "%Z%%M% %I% %E% SMI"
280Sstevel@tonic-gate
290Sstevel@tonic-gate #include <stdio.h>
300Sstevel@tonic-gate #include <ctype.h>
310Sstevel@tonic-gate #include <string.h>
320Sstevel@tonic-gate #include <fcntl.h>
330Sstevel@tonic-gate #include <string.h>
340Sstevel@tonic-gate #include <sys/types.h>
350Sstevel@tonic-gate #include <sys/time.h>
360Sstevel@tonic-gate
370Sstevel@tonic-gate #include <sys/socket.h>
380Sstevel@tonic-gate #include <sys/sockio.h>
390Sstevel@tonic-gate #include <net/if.h>
400Sstevel@tonic-gate #include <netinet/in_systm.h>
410Sstevel@tonic-gate #include <netinet/in.h>
420Sstevel@tonic-gate #include <netinet/ip.h>
430Sstevel@tonic-gate #include <netinet/if_ether.h>
440Sstevel@tonic-gate #include <netinet/udp.h>
450Sstevel@tonic-gate #include "snoop.h"
460Sstevel@tonic-gate
470Sstevel@tonic-gate extern char *dlc_header;
480Sstevel@tonic-gate
49*410Skcpoon int
interpret_udp(int flags,struct udphdr * udp,int iplen,int fraglen)50*410Skcpoon interpret_udp(int flags, struct udphdr *udp, int iplen, int fraglen)
510Sstevel@tonic-gate {
520Sstevel@tonic-gate char *data;
530Sstevel@tonic-gate int udplen;
540Sstevel@tonic-gate int sunrpc;
550Sstevel@tonic-gate char *pname;
560Sstevel@tonic-gate char buff [32];
570Sstevel@tonic-gate
580Sstevel@tonic-gate if (fraglen < sizeof (struct udphdr))
590Sstevel@tonic-gate return (fraglen); /* incomplete header */
600Sstevel@tonic-gate
610Sstevel@tonic-gate data = (char *)udp + sizeof (struct udphdr);
62*410Skcpoon udplen = ntohs((ushort_t)udp->uh_ulen) - sizeof (struct udphdr);
630Sstevel@tonic-gate fraglen -= sizeof (struct udphdr);
640Sstevel@tonic-gate if (fraglen > udplen)
650Sstevel@tonic-gate fraglen = udplen;
660Sstevel@tonic-gate
670Sstevel@tonic-gate if (flags & F_SUM) {
680Sstevel@tonic-gate (void) sprintf(get_sum_line(),
690Sstevel@tonic-gate "UDP D=%d S=%d LEN=%d",
700Sstevel@tonic-gate ntohs(udp->uh_dport),
710Sstevel@tonic-gate ntohs(udp->uh_sport),
72*410Skcpoon ntohs((ushort_t)udp->uh_ulen));
730Sstevel@tonic-gate }
740Sstevel@tonic-gate
750Sstevel@tonic-gate sunrpc = !reservedport(IPPROTO_UDP, ntohs(udp->uh_dport)) &&
760Sstevel@tonic-gate !reservedport(IPPROTO_UDP, ntohs(udp->uh_sport)) &&
770Sstevel@tonic-gate valid_rpc(data, udplen);
780Sstevel@tonic-gate
790Sstevel@tonic-gate if (flags & F_DTAIL) {
800Sstevel@tonic-gate show_header("UDP: ", "UDP Header", udplen);
810Sstevel@tonic-gate show_space();
82*410Skcpoon (void) sprintf(get_line((char *)(uintptr_t)udp->uh_sport -
83*410Skcpoon dlc_header, 1), "Source port = %d", ntohs(udp->uh_sport));
840Sstevel@tonic-gate
850Sstevel@tonic-gate if (sunrpc) {
860Sstevel@tonic-gate pname = "(Sun RPC)";
870Sstevel@tonic-gate } else {
880Sstevel@tonic-gate pname = getportname(IPPROTO_UDP, ntohs(udp->uh_dport));
890Sstevel@tonic-gate if (pname == NULL) {
900Sstevel@tonic-gate pname = "";
910Sstevel@tonic-gate } else {
920Sstevel@tonic-gate (void) sprintf(buff, "(%s)", pname);
930Sstevel@tonic-gate pname = buff;
940Sstevel@tonic-gate }
950Sstevel@tonic-gate }
96*410Skcpoon (void) sprintf(get_line((char *)(uintptr_t)udp->uh_dport -
97*410Skcpoon dlc_header, 1), "Destination port = %d %s",
98*410Skcpoon ntohs(udp->uh_dport), pname);
99*410Skcpoon (void) sprintf(get_line((char *)(uintptr_t)udp->uh_ulen -
100*410Skcpoon dlc_header, 1), "Length = %d %s",
101*410Skcpoon ntohs((ushort_t)udp->uh_ulen),
102*410Skcpoon udplen > fraglen ?
103*410Skcpoon "(Not all data contained in this fragment)"
104*410Skcpoon : "");
105*410Skcpoon (void) sprintf(get_line((char *)(uintptr_t)udp->uh_sum -
106*410Skcpoon dlc_header, 1), "Checksum = %04X %s",
107*410Skcpoon ntohs(udp->uh_sum),
108*410Skcpoon udp->uh_sum == 0 ? "(no checksum)" : "");
1090Sstevel@tonic-gate show_space();
1100Sstevel@tonic-gate }
1110Sstevel@tonic-gate
1120Sstevel@tonic-gate
1130Sstevel@tonic-gate /* go to the next protocol layer */
1140Sstevel@tonic-gate
1150Sstevel@tonic-gate if (!interpret_reserved(flags, IPPROTO_UDP,
1160Sstevel@tonic-gate ntohs(udp->uh_sport),
1170Sstevel@tonic-gate ntohs(udp->uh_dport),
1180Sstevel@tonic-gate data, fraglen)) {
1190Sstevel@tonic-gate if (fraglen > 0 && sunrpc)
1200Sstevel@tonic-gate interpret_rpc(flags, data, fraglen, IPPROTO_UDP);
1210Sstevel@tonic-gate }
1220Sstevel@tonic-gate
1230Sstevel@tonic-gate return (fraglen);
1240Sstevel@tonic-gate }
125