From patchwork Thu May 23 15:06:03 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jeff Layton X-Patchwork-Id: 2607621 Return-Path: X-Original-To: patchwork-cifs-client@patchwork.kernel.org Delivered-To: patchwork-process-083081@patchwork2.kernel.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by patchwork2.kernel.org (Postfix) with ESMTP id 1BD57DFB78 for ; Thu, 23 May 2013 15:06:32 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1759358Ab3EWPGb (ORCPT ); Thu, 23 May 2013 11:06:31 -0400 Received: from mail-qc0-f181.google.com ([209.85.216.181]:51545 "EHLO mail-qc0-f181.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1759203Ab3EWPGa (ORCPT ); Thu, 23 May 2013 11:06:30 -0400 Received: by mail-qc0-f181.google.com with SMTP id u11so1793907qcx.26 for ; Thu, 23 May 2013 08:06:29 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=sender:from:to:cc:subject:date:message-id:x-mailer:in-reply-to :references:x-gm-message-state; bh=/5XOxgy8yMNbuw0fanRZlGaARP0QNWCg1bYp1GIJZgU=; b=W78na4wID6GLrdyF7pv7DG77g4TtKn8SiNn/MmV4HEJB1QgQgmso6idj54nKEP5Cx0 Ym5hhBfre6VxlsVK3/kS1om0dFnXW0oGjF3c13uZ+dEd/bQkZZxegj7a7y0XtPru+ipj oNMX0q17xV3e04wV1uMIQt/y7B2XAT3IYLRevKqViuXIE+eiYKUOeZUMJgqauwvagQlk roz0ALXZnW3fM62R6y/oU2wfiqZo3PMDKqFDzx4lxvYWmRVq7sCWFY4AALbCOSyjNhBQ 0D0emGSK4TFvh+If3nL7Y/inXgMItSCyHoEzFl8dcj18akQgu6mUCYvskV+6sZxZ1bDG yzVA== X-Received: by 10.224.126.196 with SMTP id d4mr12116890qas.57.1369321589728; Thu, 23 May 2013 08:06:29 -0700 (PDT) Received: from salusa.poochiereds.net (cpe-107-015-113-143.nc.res.rr.com. [107.15.113.143]) by mx.google.com with ESMTPSA id y1sm12688520qad.5.2013.05.23.08.06.28 for (version=TLSv1.2 cipher=RC4-SHA bits=128/128); Thu, 23 May 2013 08:06:29 -0700 (PDT) From: Jeff Layton To: smfrench@gmail.com Cc: linux-cifs@vger.kernel.org, idra@samba.org Subject: [PATCH 19/19] cifs: try to handle the MUST SecurityFlags sanely Date: Thu, 23 May 2013 11:06:03 -0400 Message-Id: <1369321563-16893-20-git-send-email-jlayton@redhat.com> X-Mailer: git-send-email 1.8.1.4 In-Reply-To: <1369321563-16893-1-git-send-email-jlayton@redhat.com> References: <1369321563-16893-1-git-send-email-jlayton@redhat.com> X-Gm-Message-State: ALoCoQm9UU/55/1QELENdnX5r3kVxBl9OTB29w+XRFj19IN4sJcDikZW7GgU7LvIYcC6vxwE3IyV Sender: linux-cifs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-cifs@vger.kernel.org The cifs.ko SecurityFlags interface wins my award for worst-designed interface ever, but we're sort of stuck with it since it's documented and people do use it (even if it doesn't work correctly). Case in point -- you can specify multiple sets of "MUST" flags. It makes absolutely no sense, but you can do it. What should the effect be in such a case? No one knows or seems to have considered this, so let's define it now. If you try to specify multiple MUST flags, clear any other MAY or MUST bits except for the ones that involve signing. Signed-off-by: Jeff Layton Reviewed-by: Pavel Shilovsky --- fs/cifs/cifs_debug.c | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/fs/cifs/cifs_debug.c b/fs/cifs/cifs_debug.c index 856f8f5..d21339a 100644 --- a/fs/cifs/cifs_debug.c +++ b/fs/cifs/cifs_debug.c @@ -595,6 +595,32 @@ static int cifs_security_flags_proc_open(struct inode *inode, struct file *file) return single_open(file, cifs_security_flags_proc_show, NULL); } +/* + * Ensure that if someone sets a MUST flag, that we disable all other MAY + * flags except for the ones corresponding to the given MUST flag. If there are + * multiple MUST flags, then try to prefer more secure ones. + */ +static void +cifs_security_flags_handle_must_flags(unsigned int *flags) +{ + unsigned int signflags = *flags & CIFSSEC_MUST_SIGN; + + if ((*flags & CIFSSEC_MUST_KRB5) == CIFSSEC_MUST_KRB5) + *flags = CIFSSEC_MUST_KRB5; + else if ((*flags & CIFSSEC_MUST_NTLMSSP) == CIFSSEC_MUST_NTLMSSP) + *flags = CIFSSEC_MUST_NTLMSSP; + else if ((*flags & CIFSSEC_MUST_NTLMV2) == CIFSSEC_MUST_NTLMV2) + *flags = CIFSSEC_MUST_NTLMV2; + else if ((*flags & CIFSSEC_MUST_NTLM) == CIFSSEC_MUST_NTLM) + *flags = CIFSSEC_MUST_NTLM; + else if ((*flags & CIFSSEC_MUST_LANMAN) == CIFSSEC_MUST_LANMAN) + *flags = CIFSSEC_MUST_LANMAN; + else if ((*flags & CIFSSEC_MUST_PLNTXT) == CIFSSEC_MUST_PLNTXT) + *flags = CIFSSEC_MUST_PLNTXT; + + *flags |= signflags; +} + static ssize_t cifs_security_flags_proc_write(struct file *file, const char __user *buffer, size_t count, loff_t *ppos) { @@ -648,6 +674,8 @@ static ssize_t cifs_security_flags_proc_write(struct file *file, return -EINVAL; } + cifs_security_flags_handle_must_flags(&flags); + /* flags look ok - update the global security flags for cifs module */ global_secflags = flags; if (global_secflags & CIFSSEC_MUST_SIGN) {