Subject: bin/3207: showmount(8) uses RPC over UDP
To: None <gnats-bugs@gnats.netbsd.org>
From: None <Michael.Eriksson@era-t.ericsson.se>
List: netbsd-bugs
Date: 02/11/1997 12:04:19
>Number: 3207
>Category: bin
>Synopsis: showmount(8) uses RPC over UDP
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: bin-bug-people (Utility Bug People)
>State: open
>Class: sw-bug
>Submitter-Id: net
>Arrival-Date: Tue Feb 11 03:20:01 1997
>Last-Modified:
>Originator: Michael Eriksson
>Organization:
Ericsson Radio Systems AB
>Release: 1.2
>Environment:
NetBSD 1.2
>Description:
showmount(8) uses callrpc(3), which implicitly uses UDP for transport.
Responses can sometimes be too big for a UDP packet (8 kbytes of
encoded data), and the program will fail. Thus, the program should use
TCP for transport instead.
>How-To-Repeat:
% showmount -a nfsserver
>Fix:
*** /usr/src/usr.bin/showmount/showmount.c Wed May 1 20:14:10 1996
--- showmount.c Tue Feb 11 10:18:35 1997
***************
*** 113,121 ****
{
struct exportslist *exp;
struct grouplist *grp;
! int estat, rpcs = 0, mntvers = 1;
char *host;
! int ch;
while ((ch = getopt(argc, argv, "ade3")) != -1)
switch((char)ch) {
--- 113,126 ----
{
struct exportslist *exp;
struct grouplist *grp;
! struct sockaddr_in clnt_sin;
! struct hostent *hp;
! struct timeval timeout;
! int rpcs = 0, mntvers = 1;
! enum clnt_stat estat;
! CLIENT *client;
char *host;
! int ch, clnt_sock;
while ((ch = getopt(argc, argv, "ade3")) != -1)
switch((char)ch) {
***************
*** 154,175 ****
if (rpcs == 0)
rpcs = DODUMP;
! if (rpcs & DODUMP)
! if ((estat = callrpc(host, RPCPROG_MNT, mntvers,
! RPCMNT_DUMP, xdr_void, (char *)0,
! xdr_mntdump, (char *)&mntdump)) != 0) {
fprintf(stderr, "showmount: Can't do Mountdump rpc: ");
clnt_perrno(estat);
exit(1);
}
! if (rpcs & DOEXPORTS)
! if ((estat = callrpc(host, RPCPROG_MNT, mntvers,
! RPCMNT_EXPORT, xdr_void, (char *)0,
! xdr_exports, (char *)&exports)) != 0) {
fprintf(stderr, "showmount: Can't do Exports rpc: ");
clnt_perrno(estat);
exit(1);
}
/* Now just print out the results */
if (rpcs & DODUMP) {
--- 159,200 ----
if (rpcs == 0)
rpcs = DODUMP;
! if ((hp = gethostbyname(host)) == NULL) {
! fprintf(stderr, "showmount: unknown host %s\n", host);
! exit(1);
! }
! bzero(&clnt_sin, sizeof clnt_sin);
! clnt_sin.sin_len = sizeof clnt_sin;
! clnt_sin.sin_family = AF_INET;
! bcopy(hp->h_addr, (char *)&clnt_sin.sin_addr, hp->h_length);
! clnt_sock = RPC_ANYSOCK;
! client = clnttcp_create(&clnt_sin, RPCPROG_MNT, mntvers,
! &clnt_sock, 0, 0);
! if (client == NULL) {
! clnt_pcreateerror("showmount: clnttcp_create");
! exit(1);
! }
! timeout.tv_sec = 30;
! timeout.tv_usec = 0;
!
! if (rpcs & DODUMP) {
! estat = clnt_call(client, RPCMNT_DUMP, xdr_void, (char *)0,
! xdr_mntdump, (char *)&mntdump, timeout);
! if (estat != RPC_SUCCESS) {
fprintf(stderr, "showmount: Can't do Mountdump rpc: ");
clnt_perrno(estat);
exit(1);
}
! }
! if (rpcs & DOEXPORTS) {
! estat = clnt_call(client, RPCMNT_EXPORT, xdr_void, (char *)0,
! xdr_exports, (char *)&exports, timeout);
! if (estat != RPC_SUCCESS) {
fprintf(stderr, "showmount: Can't do Exports rpc: ");
clnt_perrno(estat);
exit(1);
}
+ }
/* Now just print out the results */
if (rpcs & DODUMP) {
>Audit-Trail:
>Unformatted: