Patch "ppp: ensure file->private_data can't be overridden" has been added to the 4.4-stable tree
Subsystems (3)
This is a note to let you know that I've just added the patch titled
ppp: ensure file->private_data can't be overridden
to the 4.4-stable tree which can be found at:
http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary
The filename of the patch is:
ppp-ensure-file-private_data-can-t-be-overridden.patch
and it can be found in the queue-4.4 subdirectory.
If you, or anyone else, feels it should not be added to the stable tree, please let <[email protected]> know about it.
Quoted 1 line
From foo@baz Sat Apr 16 10:02:53 PDT 2016
From: Guillaume Nault <[email protected]>
Date: Mon, 14 Mar 2016 21:17:16 +0100
Subject: ppp: ensure file->private_data can't be overridden
From: Guillaume Nault <[email protected]>
[ Upstream commit e8e56ffd9d2973398b60ece1f1bebb8d67b4d032 ]
Locking ppp_mutex must be done before dereferencing file->private_data, otherwise it could be modified before ppp_unattached_ioctl() takes the lock. This could lead ppp_unattached_ioctl() to override ->private_data, thus leaking reference to the ppp_file previously pointed to.
v2: lock all ppp_ioctl() instead of just checking private_data in
ppp_unattached_ioctl(), to avoid ambiguous behaviour.
--- drivers/net/ppp/ppp_generic.c | 31 +++++++++++++++++-------------- 1 file changed, 17 insertions(+), 14 deletions(-)
drivers/net/ppp/ppp_generic.c +17 -14
@@ -567,7 +567,7 @@ static int get_filter(void __user *arg,static long ppp_ioctl (struct file *file,unsigned int cmd,unsigned long arg) { -struct ppp_file *pf = file->private_data; +struct ppp_file *pf;struct ppp *ppp;int err = -EFAULT , val, val2, i;struct ppp_idle idle;
@@ -577,9 +577,14 @@ static long ppp_ioctl(struct file *file,void __user *argp = (void __user *)arg;int __user *p = argp; -if (!pf) -return ppp_unattached_ioctl (current->nsproxy->net_ns, - pf, file, cmd, arg); +mutex_lock (&ppp_mutex); + + pf = file->private_data; +if (!pf) { + err =ppp_unattached_ioctl (current->nsproxy->net_ns, + pf, file, cmd, arg); + goto out; + }if (cmd ==PPPIOCDETACH ) {/*
@@ -594,7 +599,6 @@ static long ppp_ioctl(struct file *file,* this fd and reopening /dev/ppp. */ err = -EINVAL ; -mutex_lock (&ppp_mutex);if (pf->kind ==INTERFACE ) { ppp =PF_TO_PPP (pf);rtnl_lock ();
@@ -608,15 +612,13 @@ static long ppp_ioctl(struct file *file, }else pr_warn ("PPPIOCDETACH file->f_count=%ld\n" ,atomic_long_read (&file->f_count)); -mutex_unlock (&ppp_mutex); -return err; + goto out; }if (pf->kind ==CHANNEL ) {struct channel *pch;struct ppp_channel *chan; -mutex_lock (&ppp_mutex); pch =PF_TO_CHANNEL (pf);switch (cmd) {
@@ -638,17 +640,16 @@ static long ppp_ioctl(struct file *file, err = chan->ops->ioctl (chan, cmd, arg);up_read (&pch->chan_sem); } -mutex_unlock (&ppp_mutex); -return err; + goto out; }if (pf->kind !=INTERFACE ) {/* can't happen */ pr_err ("PPP: not interface or channel??\n" ); -return -EINVAL ; + err = -EINVAL ; + goto out; } -mutex_lock (&ppp_mutex); ppp =PF_TO_PPP (pf);switch (cmd) {case PPPIOCSMRU :
@@ -823,7 +824,10 @@ static long ppp_ioctl(struct file *file,default : err = -ENOTTY ; } + +out:mutex_unlock (&ppp_mutex); +return err; }
@@ -836,7 +840,6 @@ static int ppp_unattached_ioctl(struct nstruct ppp_net *pn;int __user *p = (int __user *)arg; -mutex_lock (&ppp_mutex);switch (cmd) {case PPPIOCNEWUNIT :/* Create a new ppp unit */
@@ -886,7 +889,7 @@ static int ppp_unattached_ioctl(struct ndefault : err = -ENOTTY ; } -mutex_unlock (&ppp_mutex); +return err; }
Patches currently in stable-queue which might be from [email protected] are
queue-4.4/ppp-release-rtnl-mutex-when-interface-creation-fails.patch queue-4.4/ppp-take-reference-on-channels-netns.patch queue-4.4/ppp-ensure-file-private_data-can-t-be-overridden.patch