NetBSD Problem Report #10986
Received: (qmail 6676 invoked from network); 11 Sep 2000 05:33:09 -0000
Message-Id: <20000911053226.3D31295F@renoir.sat.t.u-tokyo.ac.jp>
Date: Mon, 11 Sep 2000 14:32:26 +0900 (JST)
From: IWAMOTO Toshihiro <toshii@netbsd.org>
Sender: iwamoto@sat.t.u-tokyo.ac.jp
Reply-To: IWAMOTO Toshihiro <toshii@netbsd.org>
To: gnats-bugs@gnats.netbsd.org
Subject: mount_nfs doesn't fallback to IPv4
X-Send-Pr-Version: 3.95
>Number: 10986
>Category: bin
>Synopsis: mount_nfs doesn't fallback to IPv4
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: bin-bug-people
>State: open
>Class: sw-bug
>Submitter-Id: net
>Arrival-Date: Mon Sep 11 05:34:00 +0000 2000
>Closed-Date:
>Last-Modified: Wed Oct 02 17:06:00 +0000 2002
>Originator:
>Release: kernel is a few days ago -current,
>Organization:
>Environment:
System: NetBSD renoir.sat.t.u-tokyo.ac.jp 1.5E NetBSD 1.5E (RENOIR.MP) #0: Fri Sep 8 15:30:54 JST 2000 iwamoto@een.sat.t.u-tokyo.ac.jp:/export/home/iwamoto/syssrc/sys/arch/i386/compile/RENOIR.MP i386
>Description:
mount_nfs doesn't fallback to IPv4 operation when IPv6 nfs mount
is not available.
>How-To-Repeat:
Prepare a host with an IPv6 DNS record which is
1) a FreeBSD box running 4.1-STABLE something
2) a NetBSD box which denys IPv6 RPC requests by libwrap
(This can be achieved by disabling DNS reverse lookups or
explicitly writing hosts.{allow,deny}.)
>Fix:
Not provided.
It might be a good idea to have -4/-6 options which explicitly
selects IPv4/IPv6 connections.
>Release-Note:
>Audit-Trail:
From: IWAMOTO Toshihiro <iwamoto@sat.t.u-tokyo.ac.jp>
To: netbsd-bugs@netbsd.org
Cc: gnats-bugs@gnats.netbsd.org
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Mon, 11 Sep 2000 22:43:13 +0900
At Mon, 11 Sep 2000 14:32:26 +0900 (JST),
IWAMOTO Toshihiro <toshii@netbsd.org> wrote:
> >How-To-Repeat:
> Prepare a host with an IPv6 DNS record which is
> 1) a FreeBSD box running 4.1-STABLE something
> 2) a NetBSD box which denys IPv6 RPC requests by libwrap
> (This can be achieved by disabling DNS reverse lookups or
> explicitly writing hosts.{allow,deny}.)
Sorry, this sentence was certainly confusing.
I meant:
Prepare a NFS server host with an IPv6 DNS record which is
1) a FreeBSD box running 4.1-STABLE something
or,
2) a NetBSD box which denys IPv6 RPC requests by libwrap
In both cases, the NFS client is an ordinary 1.5E NetBSD box
(1.5_ALPHA2 behaved the same).
--
IWAMOTO Toshihiro
From: Benedikt Meurer <bmeurer@fwdn.de>
To: netbsd-bugs@netbsd.org
Cc: gnats-bugs@gnats.netbsd.org, iwamoto@sat.t.u-tokyo.ac.jp
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Mon, 30 Sep 2002 18:53:31 +0200
Hello,
I did a small change to mount_nfs to get -4/-6 options to explicitly
select IPv4/IPv6 connections.
HTH, Benedikt
Index: mount_nfs.c
===================================================================
RCS file: /cvsroot/basesrc/sbin/mount_nfs/mount_nfs.c,v
retrieving revision 1.34
diff -u -r1.34 mount_nfs.c
--- mount_nfs.c 2002/09/21 18:43:36 1.34
+++ mount_nfs.c 2002/09/30 16:44:59
@@ -170,6 +170,8 @@
int nfsproto = IPPROTO_UDP;
int force2 = 0;
int force3 = 0;
+int force4 = 0;
+int force6 = 0;
int mnttcp_ok = 1;
#ifdef NFSKERB
@@ -230,8 +232,7 @@
sizeof (struct nfsrpc_fullblock) != RPCX_FULLBLOCK ||
((char *)&ktick.kt) - ((char *)&ktick) != NFSX_UNSIGNED ||
((char *)ktick.kt.dat) - ((char *)&ktick) != 2 * NFSX_UNSIGNED)
- fprintf(stderr, "Yikes! NFSKERB structs not packed!!\n");
-
+ warnx ("Yikes! NFSKERB structs not packed!!");
#endif
retrycnt = DEF_RETRY;
@@ -240,7 +241,7 @@
nfsargs = nfsdefargs;
nfsargsp = &nfsargs;
while ((c = getopt(argc, argv,
- "23a:bcCdD:g:I:iKL:lm:o:PpqR:r:sTt:w:x:UX")) != -1)
+ "2346a:bcCdD:g:I:iKL:lm:o:PpqR:r:sTt:w:x:UX")) != -1)
switch (c) {
case '3':
if (force2)
@@ -253,6 +254,18 @@
force2 = 1;
nfsargsp->flags &= ~NFSMNT_NFSV3;
break;
+ case '4':
+ if (force6)
+ errx(1, "-4 and -6 are mutually exclusive");
+ force4 = 1;
+ nfsargsp->proto = IPPROTO_IPV4;
+ break;
+ case '6':
+ if (force4)
+ errx(1, "-4 and -6 are mutually exclusive");
+ force6 = 1;
+ nfsargsp->proto = IPPROTO_IPV6;
+ break;
case 'a':
num = strtol(optarg, &p, 10);
if (*p || num < 0)
@@ -674,6 +687,7 @@
memset(&hints, 0, sizeof hints);
hints.ai_flags = AI_NUMERICHOST;
hints.ai_socktype = nfsargsp->sotype;
+ hints.ai_protocol = nfsargsp->proto;
if (getaddrinfo(hostp, "nfs", &hints, &ai_nfs) == 0) {
if ((nfsargsp->flags & NFSMNT_KERB)) {
hints.ai_flags = 0;
@@ -907,7 +921,7 @@
usage()
{
(void)fprintf(stderr, "usage: mount_nfs %s\n%s\n%s\n%s\n%s\n",
-"[-23bcCdiKlpPqsTUX] [-a maxreadahead] [-D deadthresh]",
+"[-2346bcCdiKlpPqsTUX] [-a maxreadahead] [-D deadthresh]",
"\t[-g maxgroups] [-I readdirsize] [-L leaseterm] [-m realm]",
"\t[-o options] [-R retrycnt] [-r readsize] [-t timeout]",
"\t[-w writesize] [-x retrans]",
From: Andrew Brown <atatat@atatdot.net>
To: Benedikt Meurer <bmeurer@fwdn.de>
Cc: netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org,
iwamoto@sat.t.u-tokyo.ac.jp
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Mon, 30 Sep 2002 13:11:38 -0400
>@@ -907,7 +921,7 @@
> usage()
> {
> (void)fprintf(stderr, "usage: mount_nfs %s\n%s\n%s\n%s\n%s\n",
>-"[-23bcCdiKlpPqsTUX] [-a maxreadahead] [-D deadthresh]",
>+"[-2346bcCdiKlpPqsTUX] [-a maxreadahead] [-D deadthresh]",
> "\t[-g maxgroups] [-I readdirsize] [-L leaseterm] [-m realm]",
> "\t[-o options] [-R retrycnt] [-r readsize] [-t timeout]",
> "\t[-w writesize] [-x retrans]",
hmm...i can see trouble brewing as nfsv4 rolls in. what about using
-v[46] for selecting the ip version instead?
--
|-----< "CODE WARRIOR" >-----|
codewarrior@daemon.org * "ah! i see you have the internet
twofsonet@graffiti.com (Andrew Brown) that goes *ping*!"
werdna@squooshy.com * "information is power -- share the wealth."
From: Benedikt Meurer <bmeurer@fwdn.de>
To: Andrew Brown <atatat@atatdot.net>
Cc: netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org,
iwamoto@sat.t.u-tokyo.ac.jp
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Mon, 30 Sep 2002 19:23:41 +0200
On Mon, 30 Sep 2002, Andrew Brown wrote:
> >@@ -907,7 +921,7 @@
> > usage()
> > {
> > (void)fprintf(stderr, "usage: mount_nfs %s\n%s\n%s\n%s\n%s\n",
> >-"[-23bcCdiKlpPqsTUX] [-a maxreadahead] [-D deadthresh]",
> >+"[-2346bcCdiKlpPqsTUX] [-a maxreadahead] [-D deadthresh]",
> > "\t[-g maxgroups] [-I readdirsize] [-L leaseterm] [-m realm]",
> > "\t[-o options] [-R retrycnt] [-r readsize] [-t timeout]",
> > "\t[-w writesize] [-x retrans]",
>
> hmm...i can see trouble brewing as nfsv4 rolls in. what about using
> -v[46] for selecting the ip version instead?
Maybe, it would be the easiest way to add mount options "ipv4" and
"ipv6"?
Benedikt
--
Real Programmers think better when playing Adventure or Rogue
From: Benedikt Meurer <bmeurer@fwdn.de>
To: Andrew Brown <atatat@atatdot.net>
Cc: netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org,
iwamoto@sat.t.u-tokyo.ac.jp
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Tue, 1 Oct 2002 00:40:37 +0200
The following patch should work fine, also with NFSv4 (-4 ;-). I had
mixed up protocol family with protocol in my first patch :-(. I have
setup a FreeBSD nfsd for testing now, and as I can say, it works, when
using -o ipv4 to force the mount to use IPv4, even if there's an AAAA
record for the host. Maybe someone with a better knowledge of IPv4/IPv6
could have a look at the patch now.
HTH, Benedikt
Index: mount_nfs.c
===================================================================
RCS file: /cvsroot/basesrc/sbin/mount_nfs/mount_nfs.c,v
retrieving revision 1.34
diff -u -r1.34 mount_nfs.c
--- mount_nfs.c 2002/09/21 18:43:36 1.34
+++ mount_nfs.c 2002/09/30 22:31:57
@@ -107,6 +107,8 @@
#define ALTF_SOFT 0x800
#define ALTF_TCP 0x1000
#define ALTF_NFSV2 0x2000
+#define ALTF_IPV4 0x4000
+#define ALTF_IPV6 0x8000
static const struct mntopt mopts[] = {
MOPT_STDOPTS,
@@ -131,6 +133,8 @@
{ "soft", 0, ALTF_SOFT, 1 },
{ "tcp", 0, ALTF_TCP, 1 },
{ "nfsv2", 0, ALTF_NFSV2, 1 },
+ { "ipv4", 0, ALTF_IPV4, 1 },
+ { "ipv6", 0, ALTF_IPV6, 1 },
{ NULL }
};
@@ -170,6 +174,7 @@
int nfsproto = IPPROTO_UDP;
int force2 = 0;
int force3 = 0;
+int forcefamily = -1;
int mnttcp_ok = 1;
#ifdef NFSKERB
@@ -230,8 +235,7 @@
sizeof (struct nfsrpc_fullblock) != RPCX_FULLBLOCK ||
((char *)&ktick.kt) - ((char *)&ktick) != NFSX_UNSIGNED ||
((char *)ktick.kt.dat) - ((char *)&ktick) != 2 * NFSX_UNSIGNED)
- fprintf(stderr, "Yikes! NFSKERB structs not packed!!\n");
-
+ warnx ("Yikes! NFSKERB structs not packed!!");
#endif
retrycnt = DEF_RETRY;
@@ -345,6 +349,16 @@
force2 = 1;
nfsargsp->flags &= ~NFSMNT_NFSV3;
}
+ if((altflags & ALTF_IPV4) &&
+ (altflags & ALTF_IPV6)) {
+ errx(1,"ipv4 and ipv6 are mutually exclusive");
+ }
+ else if (altflags & ALTF_IPV4) {
+ forcefamily = PF_INET;
+ }
+ else if(altflags & ALTF_IPV6) {
+ forcefamily = PF_INET6;
+ }
if(altflags & ALTF_RDIRPLUS)
nfsargsp->flags |= NFSMNT_RDIRPLUS;
if(altflags & ALTF_MNTUDP)
@@ -674,6 +688,8 @@
memset(&hints, 0, sizeof hints);
hints.ai_flags = AI_NUMERICHOST;
hints.ai_socktype = nfsargsp->sotype;
+ if (forcefamily > 0)
+ hints.ai_family = forcefamily;
if (getaddrinfo(hostp, "nfs", &hints, &ai_nfs) == 0) {
if ((nfsargsp->flags & NFSMNT_KERB)) {
hints.ai_flags = 0;
From: itojun@iijlab.net
To: bmeurer@fwdn.de
Cc: Andrew Brown <atatat@atatdot.net>, netbsd-bugs@netbsd.org,
gnats-bugs@gnats.netbsd.org, iwamoto@sat.t.u-tokyo.ac.jp
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Tue, 01 Oct 2002 11:58:57 +0900
>The following patch should work fine, also with NFSv4 (-4 ;-). I had
>mixed up protocol family with protocol in my first patch :-(. I have
>setup a FreeBSD nfsd for testing now, and as I can say, it works, when
>using -o ipv4 to force the mount to use IPv4, even if there's an AAAA
>record for the host. Maybe someone with a better knowledge of IPv4/IPv6
>could have a look at the patch now.
looks fine for me, but not sure which is better between "ipv6" or
"inet6". the latter is in sync with netstat(8).
itojun
From: Jason R Thorpe <thorpej@wasabisystems.com>
To: itojun@iijlab.net
Cc: bmeurer@fwdn.de, Andrew Brown <atatat@atatdot.net>,
netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org,
iwamoto@sat.t.u-tokyo.ac.jp
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Mon, 30 Sep 2002 20:11:19 -0700
On Tue, Oct 01, 2002 at 11:58:57AM +0900, itojun@iijlab.net wrote:
> looks fine for me, but not sure which is better between "ipv6" or
> "inet6". the latter is in sync with netstat(8).
I prefer the "inet" names.
--
-- Jason R. Thorpe <thorpej@wasabisystems.com>
From: Frank van der Linden <fvdl@wasabisystems.com>
To: Jason R Thorpe <thorpej@wasabisystems.com>, itojun@iijlab.net,
bmeurer@fwdn.de, netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org
Cc:
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Tue, 1 Oct 2002 09:05:12 +0200
On Mon, Sep 30, 2002 at 08:11:19PM -0700, Jason R Thorpe wrote:
> I prefer the "inet" names.
The correct solution is to use a "proto=" option, like Solaris has.
Last time I looked into that, there was something that getmntopt(3)
didn't like about that, but I don't quite remember.
Please don't implement anything else.
- Frank
--
Frank van der Linden fvdl@wasabisystems.com
==============================================================================
Quality NetBSD Development, Support & Service. http://www.wasabisystems.com/
From: Benedikt Meurer <bmeurer@fwdn.de>
To: Frank van der Linden <fvdl@wasabisystems.com>
Cc: Jason R Thorpe <thorpej@wasabisystems.com>, itojun@iijlab.net,
netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Tue, 1 Oct 2002 12:29:22 +0200
On Tue, 01 Oct 2002, Frank van der Linden wrote:
> On Mon, Sep 30, 2002 at 08:11:19PM -0700, Jason R Thorpe wrote:
> > I prefer the "inet" names.
>
> The correct solution is to use a "proto=" option, like Solaris has.
> Last time I looked into that, there was something that getmntopt(3)
> didn't like about that, but I don't quite remember.
>
> Please don't implement anything else.
Ok, I don't have access to any solaris system for now, but somebody
sent me the mount_nfs(1M) man page :-). We would then use proto=
{tcp,tcp6,udp,udp6} options and use getnetconfigent("...") to get
the struct netconfig, right? That would also obsolete ALTF_TCP, since
we could specify proto={tcp,tcp6}, or do I missed something about that?
regards, Benedikt
--
Real Programmers think better when playing Adventure or Rogue
From: Andrew Brown <atatat@atatdot.net>
To: Benedikt Meurer <bmeurer@fwdn.de>
Cc: Frank van der Linden <fvdl@wasabisystems.com>,
Jason R Thorpe <thorpej@wasabisystems.com>, itojun@iijlab.net,
netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Tue, 1 Oct 2002 09:33:10 -0400
>> > I prefer the "inet" names.
>>
>> The correct solution is to use a "proto=" option, like Solaris has.
>> Last time I looked into that, there was something that getmntopt(3)
>> didn't like about that, but I don't quite remember.
>>
>> Please don't implement anything else.
>
>Ok, I don't have access to any solaris system for now, but somebody
>sent me the mount_nfs(1M) man page :-). We would then use proto=
>{tcp,tcp6,udp,udp6} options and use getnetconfigent("...") to get
>the struct netconfig, right? That would also obsolete ALTF_TCP, since
>we could specify proto={tcp,tcp6}, or do I missed something about that?
under separate cover.
--
|-----< "CODE WARRIOR" >-----|
codewarrior@daemon.org * "ah! i see you have the internet
twofsonet@graffiti.com (Andrew Brown) that goes *ping*!"
werdna@squooshy.com * "information is power -- share the wealth."
From: Benedikt Meurer <bmeurer@fwdn.de>
To: Andrew Brown <atatat@atatdot.net>
Cc: Frank van der Linden <fvdl@wasabisystems.com>,
Jason R Thorpe <thorpej@wasabisystems.com>, itojun@iijlab.net,
netbsd-bugs@netbsd.org, gnats-bugs@gnats.netbsd.org,
tech-userlevel@netbsd.org
Subject: Re: bin/10986: mount_nfs doesn't fallback to IPv4
Date: Wed, 2 Oct 2002 19:04:12 +0200
On Tue, 01 Oct 2002, Andrew Brown wrote:
> >> > I prefer the "inet" names.
> >>
> >> The correct solution is to use a "proto=" option, like Solaris has.
> >> Last time I looked into that, there was something that getmntopt(3)
> >> didn't like about that, but I don't quite remember.
> >>
> >> Please don't implement anything else.
> >
> >Ok, I don't have access to any solaris system for now, but somebody
> >sent me the mount_nfs(1M) man page :-). We would then use proto=
> >{tcp,tcp6,udp,udp6} options and use getnetconfigent("...") to get
> >the struct netconfig, right? That would also obsolete ALTF_TCP, since
> >we could specify proto={tcp,tcp6}, or do I missed something about that?
Ok. I changed mount_nfs to support proto=<netid> option as mentioned in
the mount_nfs(1M) Solaris man page. In addition, I added mntproto=<netid>
to explicitly set the mount protocol to use (if differs from nfs
proto), that will obsolete -U and mntudp, since we now have a more generic
way to specify the mount protocol. I also added a vers=<nfs version number>
option as mentioned in the solaris mount_nfs manual to allow a smooth
integration of NFSv4 (NFSv5, ...), so we do not need to add -<NFS version> and
nfsv<NFS version> options, whenever new NFS protocol versions come up. This
will obsolete -2/-3 and nfsv2/nfsv3 (it would be a pain to handle int force2,
force3, force4, .. and so on). So e.g. if you used something like
mount_nfs -3 -T -U host:/dirpath /localdir
before, you would now say
mount_nfs -o vers=3,proto=tcp,mntproto=udp host:/dirpath /localdir
(or even udp6/tcp6). So it'll be easy to add support for new NFS version
and even support for new protocols, I think. We could also get rid of the
sluggish ISO code with this approach.
Maybe we should also replace things like -w with wsize= and -t with timeo=,
or are there any objections to the use of Solaris-like options?
It would also be nice, if people could test my patch. I've tested it with
IPv4 and IPv6 nfsd/mountd, and it seems to work fine.
HTH, Benedikt
Index: mount_nfs.c
===================================================================
RCS file: /cvsroot/basesrc/sbin/mount_nfs/mount_nfs.c,v
retrieving revision 1.35
diff -u -r1.35 mount_nfs.c
--- mount_nfs.c 2002/10/01 03:08:56 1.35
+++ mount_nfs.c 2002/10/02 16:40:25
@@ -98,15 +98,18 @@
#define ALTF_DUMBTIMR 0x4
#define ALTF_INTR 0x8
#define ALTF_KERB 0x10
-#define ALTF_NFSV3 0x20
+#define ALTF_NFSV3 0x20 /* obsoleted by vers=3 */
#define ALTF_RDIRPLUS 0x40
-#define ALTF_MNTUDP 0x80
+#define ALTF_MNTUDP 0x80 /* obsoleted by mntproto=udp */
#define ALTF_NORESPORT 0x100
#define ALTF_SEQPACKET 0x200
#define ALTF_NQNFS 0x400
#define ALTF_SOFT 0x800
-#define ALTF_TCP 0x1000
-#define ALTF_NFSV2 0x2000
+#define ALTF_TCP 0x1000 /* obsoleted by proto=tcp */
+#define ALTF_NFSV2 0x2000 /* obsoleted by vers=2 */
+#define ALTF_PROTO 0x4000
+#define ALTF_VERS 0x8000
+#define ALTF_MNTPROTO 0x10000
static const struct mntopt mopts[] = {
MOPT_STDOPTS,
@@ -131,6 +134,9 @@
{ "soft", 0, ALTF_SOFT, 1 },
{ "tcp", 0, ALTF_TCP, 1 },
{ "nfsv2", 0, ALTF_NFSV2, 1 },
+ { "proto", 0, ALTF_PROTO, 1 },
+ { "vers", 0, ALTF_VERS, 1 },
+ { "mntproto", 0, ALTF_MNTPROTO, 1 },
{ NULL }
};
@@ -167,10 +173,9 @@
#define ISBGRND 2
int retrycnt;
int opflags = 0;
-int nfsproto = IPPROTO_UDP;
-int force2 = 0;
-int force3 = 0;
-int mnttcp_ok = 1;
+int forceversion = 0; /* this is better than having force2,force3,force4..*/
+int forcefamily = 0;
+char mntproto[7] = { 0, };
#ifdef NFSKERB
static char inst[INST_SZ];
@@ -198,6 +203,7 @@
static void usage __P((void));
static int xdr_dir __P((XDR *, char *));
static int xdr_fh __P((XDR *, struct nfhret *));
+static char * getoptval __P((const char *, const char *, char *, size_t));
#ifndef MOUNT_NOMAIN
int
@@ -219,6 +225,7 @@
struct nfs_args nfsargs;
struct nfsd_cargs ncd;
int mntflags, altflags, i, nfssvc_flag, num;
+ char buffer[32];
char *name, *p, *spec, *ospec;
#ifdef NFSKERB
uid_t last_ruid;
@@ -242,14 +249,16 @@
"23a:bcCdD:g:I:iKL:lm:o:PpqR:r:sTt:w:x:UX")) != -1)
switch (c) {
case '3':
- if (force2)
- errx(1, "-2 and -3 are mutually exclusive");
- force3 = 1;
+ warnx("-3 is obsolete, use vers=3 instead");
+ if (forceversion && forceversion != 3)
+ errx(1, "conflicting version options");
+ forceversion = 3;
break;
case '2':
- if (force3)
- errx(1, "-2 and -3 are mutually exclusive");
- force2 = 1;
+ warnx("-2 is obsolete, use vers=2 instead");
+ if (forceversion && forceversion != 2)
+ errx(1, "conflicting version options");
+ forceversion = 2;
nfsargsp->flags &= ~NFSMNT_NFSV3;
break;
case 'a':
@@ -334,20 +343,27 @@
nfsargsp->flags |= NFSMNT_KERB;
#endif
if (altflags & ALTF_NFSV3) {
- if (force2)
+ warnx("nfsv3 is obsolete, use vers=3 instead");
+ if (forceversion && forceversion != 3)
errx(1, "conflicting version options");
- force3 = 1;
+ forceversion = 3;
}
if (altflags & ALTF_NFSV2) {
- if (force3)
+ warnx("nfsv2 is obsolete, use vers=2 instead");
+ if (forceversion && forceversion != 2)
errx(1, "conflicting version options");
- force2 = 1;
+ forceversion = 2;
nfsargsp->flags &= ~NFSMNT_NFSV3;
}
if (altflags & ALTF_RDIRPLUS)
nfsargsp->flags |= NFSMNT_RDIRPLUS;
- if (altflags & ALTF_MNTUDP)
- mnttcp_ok = 0;
+ if (altflags & ALTF_MNTUDP) {
+ warnx("mntudp is obsolete, use mntproto=udp "
+ "instead");
+ if (*mntproto && strcmp(mntproto, "udp"))
+ errx(1, "conflicting mntproto options");
+ strlcpy(mntproto,"udp",sizeof(mntproto));
+ }
if (altflags & ALTF_NORESPORT)
nfsargsp->flags &= ~NFSMNT_RESVPORT;
#ifdef ISO
@@ -355,16 +371,98 @@
nfsargsp->sotype = SOCK_SEQPACKET;
#endif
if (altflags & ALTF_NQNFS) {
- if (force2)
+ if (forceversion && forceversion != 3)
errx(1, "nqnfs only available with v3");
- force3 = 1;
+ forceversion = 3;
nfsargsp->flags |= NFSMNT_NQNFS;
}
if (altflags & ALTF_SOFT)
nfsargsp->flags |= NFSMNT_SOFT;
if (altflags & ALTF_TCP) {
+ warnx("tcp is obsolete, use proto=tcp instead");
nfsargsp->sotype = SOCK_STREAM;
- nfsproto = IPPROTO_TCP;
+ }
+ /* proto=<netid> should be the suggested way of
+ * selecting a specific mount/nfs protocol, since its
+ * a more generic way, which allows easy addition
+ * of new protocols, without having to add any
+ * further arguments/options to mount_nfs. ALTF_TCP
+ * should therefore be considered obsolete (maybe
+ * ALTF_MNTUDP too, but i'm not sure).
+ * - Benedikt Meurer
+ */
+ if (altflags & ALTF_PROTO) {
+ struct netconfig *nc;
+
+ if (getoptval(optarg, "proto", buffer,
+ sizeof(buffer)) == NULL)
+ errx(1, "invalid proto option");
+
+ if ((nc = getnetconfigent (buffer)) == NULL)
+ errx(1, "%s: %s", buffer, nc_sperror());
+
+ /* XXX Is there any generic way? */
+ if (!strcmp(nc->nc_protofmly, NC_INET))
+ forcefamily = PF_INET;
+ else if (!strcmp(nc->nc_protofmly, NC_INET6))
+ forcefamily = PF_INET6;
+ else
+ errx(1, "%s: protocol family not "
+ "supported", nc->nc_protofmly);
+
+ /* XXX Is there any generic way? */
+ if (!strcmp(nc->nc_proto, NC_TCP))
+ nfsargsp->sotype = SOCK_STREAM;
+ else if (!strcmp(nc->nc_proto, NC_UDP))
+ nfsargsp->sotype = SOCK_DGRAM;
+ else
+ errx(1, "%s: unsupported protocol",
+ nc->nc_proto);
+
+ freenetconfigent(nc);
+ }
+ /* vers=<NFS version number> should be the suggested
+ * way of specifing NFS protocol version to use, else
+ * we'll probably end up with nfsv2,nfsv3,nfsv4,...
+ * options. I think the Solaris like vers option is
+ * easier to handle.
+ * - Benedikt Meurer
+ */
+ if (altflags & ALTF_VERS) {
+ if (getoptval(optarg, "vers", buffer,
+ sizeof(buffer)) == NULL)
+ errx(1, "invalid vers option");
+
+ num = strtol(buffer, &p, 10);
+ if (*p || num <= 0)
+ errx(1, "illegal version -- %s",buffer);
+
+ warnx("vers: %d, forceversion: %d", num, forceversion);
+ if (forceversion && forceversion != num)
+ errx(1,"conflicting version options");
+
+ switch (num) {
+ case 3:
+ forceversion = 3;
+ nfsargsp->flags |= NFSMNT_NFSV3;
+ break;
+ case 2:
+ forceversion = 2;
+ nfsargsp->flags &= ~NFSMNT_NFSV3;
+ break;
+ default:
+ errx(1,"unsupported version -- %s",
+ buffer);
+ }
+ }
+ if (altflags & ALTF_MNTPROTO) {
+ if (getoptval(optarg,"mntproto",buffer,
+ sizeof(buffer)) == NULL) {
+ errx(1,"invalid mntproto option");
+ }
+ if (*mntproto && strcmp(mntproto, buffer))
+ errx(1, "conflicting mntproto options");
+ strlcpy(mntproto, buffer, sizeof(mntproto));
}
altflags = 0;
break;
@@ -375,9 +473,9 @@
nfsargsp->flags &= ~NFSMNT_RESVPORT;
break;
case 'q':
- if (force2)
+ if (forceversion && forceversion != 3)
errx(1, "nqnfs only available with v3");
- force3 = 1;
+ forceversion = 3;
nfsargsp->flags |= NFSMNT_NQNFS;
break;
case 'R':
@@ -403,7 +501,6 @@
break;
case 'T':
nfsargsp->sotype = SOCK_STREAM;
- nfsproto = IPPROTO_TCP;
break;
case 't':
num = strtol(optarg, &p, 10);
@@ -430,7 +527,9 @@
nfsargsp->flags |= NFSMNT_XLATECOOKIE;
break;
case 'U':
- mnttcp_ok = 0;
+ if (*mntproto && strcmp(mntproto, "udp"))
+ errx(1, "conflicting mntproto options");
+ strlcpy(mntproto, "udp", sizeof(mntproto));
break;
default:
usage();
@@ -455,7 +554,7 @@
if ((retval = mount(MOUNT_NFS, name, mntflags, nfsargsp))) {
/* Did we just default to v3 on a v2-only kernel?
* If so, default to v2 & try again */
- if ((errno == EPROGMISMATCH) && !force3) {
+ if ((errno == EPROGMISMATCH) && forceversion < 3) {
nfsargsp->flags &= ~NFSMNT_NFSV3;
retval = mount(MOUNT_NFS, name, mntflags, nfsargsp);
}
@@ -575,7 +674,7 @@
char fbuf[2048];
(void)snprintb(fbuf, sizeof(fbuf), NFSMNT_BITS, nfsargsp->flags);
- printf("version=%d, addrlen=%d, sotype=%d, proto=%d, fhsize=%d, "
+ (void)printf("version=%d, addrlen=%d, sotype=%d, proto=%d, fhsize=%d, "
"flags=%s, wsize=%d, rsize=%d, readdirsize=%d, timeo=%d, "
"retrans=%d, maxgrouplist=%d, readahead=%d, leaseterm=%d, "
"deadthresh=%d\n",
@@ -673,6 +772,7 @@
memset(&hints, 0, sizeof hints);
hints.ai_flags = AI_NUMERICHOST;
hints.ai_socktype = nfsargsp->sotype;
+ hints.ai_family = forcefamily;
if (getaddrinfo(hostp, "nfs", &hints, &ai_nfs) == 0) {
if ((nfsargsp->flags & NFSMNT_KERB)) {
hints.ai_flags = 0;
@@ -702,12 +802,17 @@
}
#endif /* NFSKERB */
- if (force2) {
+ switch (forceversion) {
+ case 2:
nfsvers = NFS_VER2;
mntvers = RPCMNT_VER1;
- } else {
+ break;
+ case 0: case 3: /* defaults to NFSv3 */
nfsvers = NFS_VER3;
mntvers = RPCMNT_VER3;
+ break;
+ default:
+ errx(1, "unsupported nfs version \'%d\'", forceversion);
}
orgcnt = retrycnt;
nfhret.stat = EACCES; /* Mark not yet successful */
@@ -729,6 +834,10 @@
netid = "udp";
}
+ /* mount protocol defaults to connection protocol */
+ if (*mntproto == '\0')
+ strlcpy(mntproto, netid, sizeof(mntproto));
+
nconf = getnetconfigent(netid);
tryagain:
@@ -757,7 +866,7 @@
* socket.
*/
clp = clnt_tp_create(hostp, RPCPROG_MNT, mntvers,
- mnttcp_ok ? nconf : getnetconfigent("udp"));
+ getnetconfigent(mntproto));
if (clp == NULL) {
if ((opflags & ISBGRND) == 0) {
clnt_pcreateerror(
@@ -778,7 +887,8 @@
xdr_dir, spec, xdr_fh, &nfhret, try);
switch (clnt_stat) {
case RPC_PROGVERSMISMATCH:
- if (nfsvers == NFS_VER3 && !force3) {
+ if (nfsvers == NFS_VER3 &&
+ forceversion < 3) {
nfsvers = NFS_VER2;
mntvers = RPCMNT_VER1;
nfsargsp->flags &=
@@ -898,6 +1008,41 @@
return (1);
};
return (0);
+}
+
+static char *
+getoptval(options, option, bufp, len)
+ const char *options;
+ const char *option;
+ char *bufp;
+ size_t len;
+{
+ /* XXX shouldn't we merge this code with getmntopts? Maybe using a
+ * callback function? Or we could add something like m_wantval and
+ * m_valuep to the mntopts struct.
+ */
+ char *optbuf, *opt, *p;
+
+ if ((optbuf = strdup(options)) == NULL)
+ err(1, NULL);
+
+ for (opt = optbuf; (opt = strtok(opt, ",")) != NULL; opt = NULL) {
+ if ((p = strchr(opt, '=')) == NULL) {
+ free(optbuf);
+ return NULL;
+ }
+
+ *p++ = '\0';
+
+ if (!strcasecmp(opt, option)) {
+ strlcpy(bufp, p, len);
+ free(optbuf);
+ return bufp;
+ }
+ }
+
+ free(optbuf);
+ return NULL;
}
static void
>Unformatted:
userland is from 1.5 branch of the same date.
(Contact us)
$NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2007
The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.