aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTrond Myklebust <trond.myklebust@primarydata.com>2017-02-22 18:35:32 -0500
committerJ. Bruce Fields <bfields@redhat.com>2017-02-27 18:04:08 -0500
commitd3635ff07e8ca598d44f72bbf5d6c65b8ebeeb46 (patch)
treeb0de5bf1afd7508f312d2ea60183e5a9c8b58222
parent7259f1dfe718234fee3f87d98d082e7f98d1d712 (diff)
nfsd: fix configuration of supported minor versions
When the user turns off all minor versions of NFSv4, that should be equivalent to turning off NFSv4 support, so a mount attempt using NFSv4 should get RPC_PROG_MISMATCH, not NFSERR_MINOR_VERS_MISMATCH. Allow the user to use either '4.0' or '4' to enable or disable minor version 0. Other minor versions are still enabled or disabled using the '4.x' format. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com> Signed-off-by: J. Bruce Fields <bfields@redhat.com>
-rw-r--r--fs/nfsd/nfsctl.c16
-rw-r--r--fs/nfsd/nfssvc.c14
2 files changed, 22 insertions, 8 deletions
diff --git a/fs/nfsd/nfsctl.c b/fs/nfsd/nfsctl.c
index d54fb0e3f30e..4bbba88416dc 100644
--- a/fs/nfsd/nfsctl.c
+++ b/fs/nfsd/nfsctl.c
@@ -561,6 +561,7 @@ static ssize_t __write_versions(struct file *file, char *buf, size_t size)
561 len = qword_get(&mesg, vers, size); 561 len = qword_get(&mesg, vers, size);
562 if (len <= 0) return -EINVAL; 562 if (len <= 0) return -EINVAL;
563 do { 563 do {
564 enum vers_op cmd;
564 sign = *vers; 565 sign = *vers;
565 if (sign == '+' || sign == '-') 566 if (sign == '+' || sign == '-')
566 num = simple_strtol((vers+1), &minorp, 0); 567 num = simple_strtol((vers+1), &minorp, 0);
@@ -571,21 +572,20 @@ static ssize_t __write_versions(struct file *file, char *buf, size_t size)
571 return -EINVAL; 572 return -EINVAL;
572 if (kstrtouint(minorp+1, 0, &minor) < 0) 573 if (kstrtouint(minorp+1, 0, &minor) < 0)
573 return -EINVAL; 574 return -EINVAL;
574 if (nfsd_minorversion(minor, sign == '-' ? 575 } else
575 NFSD_CLEAR : NFSD_SET) < 0) 576 minor = 0;
576 return -EINVAL; 577 cmd = sign == '-' ? NFSD_CLEAR : NFSD_SET;
577 goto next;
578 }
579 switch(num) { 578 switch(num) {
580 case 2: 579 case 2:
581 case 3: 580 case 3:
582 case 4: 581 nfsd_vers(num, cmd);
583 nfsd_vers(num, sign == '-' ? NFSD_CLEAR : NFSD_SET);
584 break; 582 break;
583 case 4:
584 if (nfsd_minorversion(minor, cmd) >= 0)
585 break;
585 default: 586 default:
586 return -EINVAL; 587 return -EINVAL;
587 } 588 }
588 next:
589 vers += len + 1; 589 vers += len + 1;
590 } while ((len = qword_get(&mesg, vers, size)) > 0); 590 } while ((len = qword_get(&mesg, vers, size)) > 0);
591 /* If all get turned off, turn them back on, as 591 /* If all get turned off, turn them back on, as
diff --git a/fs/nfsd/nfssvc.c b/fs/nfsd/nfssvc.c
index 2e378d0479ad..efd66da99201 100644
--- a/fs/nfsd/nfssvc.c
+++ b/fs/nfsd/nfssvc.c
@@ -153,6 +153,18 @@ int nfsd_vers(int vers, enum vers_op change)
153 return 0; 153 return 0;
154} 154}
155 155
156static void
157nfsd_adjust_nfsd_versions4(void)
158{
159 unsigned i;
160
161 for (i = 0; i <= NFSD_SUPPORTED_MINOR_VERSION; i++) {
162 if (nfsd_supported_minorversions[i])
163 return;
164 }
165 nfsd_vers(4, NFSD_CLEAR);
166}
167
156int nfsd_minorversion(u32 minorversion, enum vers_op change) 168int nfsd_minorversion(u32 minorversion, enum vers_op change)
157{ 169{
158 if (minorversion > NFSD_SUPPORTED_MINOR_VERSION) 170 if (minorversion > NFSD_SUPPORTED_MINOR_VERSION)
@@ -160,9 +172,11 @@ int nfsd_minorversion(u32 minorversion, enum vers_op change)
160 switch(change) { 172 switch(change) {
161 case NFSD_SET: 173 case NFSD_SET:
162 nfsd_supported_minorversions[minorversion] = true; 174 nfsd_supported_minorversions[minorversion] = true;
175 nfsd_vers(4, NFSD_SET);
163 break; 176 break;
164 case NFSD_CLEAR: 177 case NFSD_CLEAR:
165 nfsd_supported_minorversions[minorversion] = false; 178 nfsd_supported_minorversions[minorversion] = false;
179 nfsd_adjust_nfsd_versions4();
166 break; 180 break;
167 case NFSD_TEST: 181 case NFSD_TEST:
168 return nfsd_supported_minorversions[minorversion]; 182 return nfsd_supported_minorversions[minorversion];