Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d0ff9348 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull VFS fixes from Al Viro:
 "Several fixes + obvious cleanup (you've missed a couple of open-coded
  can_lookup() back then)"

* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs:
  snd_pcm_link(): fix a leak...
  use can_lookup() instead of direct checks of ->i_op->lookup
  move exit_task_namespaces() outside of exit_notify()
  fput: task_work_add() can fail if the caller has passed exit_task_work()
  ncpfs: fix rmdir returns Device or resource busy
parents d58c6ff0 dd6c5cd8
Loading
Loading
Loading
Loading
+10 −9
Original line number Original line Diff line number Diff line
@@ -306,17 +306,18 @@ void fput(struct file *file)
{
{
	if (atomic_long_dec_and_test(&file->f_count)) {
	if (atomic_long_dec_and_test(&file->f_count)) {
		struct task_struct *task = current;
		struct task_struct *task = current;
		file_sb_list_del(file);
		if (unlikely(in_interrupt() || task->flags & PF_KTHREAD)) {
		unsigned long flags;
		unsigned long flags;

		file_sb_list_del(file);
		if (likely(!in_interrupt() && !(task->flags & PF_KTHREAD))) {
			init_task_work(&file->f_u.fu_rcuhead, ____fput);
			if (!task_work_add(task, &file->f_u.fu_rcuhead, true))
				return;
		}
		spin_lock_irqsave(&delayed_fput_lock, flags);
		spin_lock_irqsave(&delayed_fput_lock, flags);
		list_add(&file->f_u.fu_list, &delayed_fput_list);
		list_add(&file->f_u.fu_list, &delayed_fput_list);
		schedule_work(&delayed_fput_work);
		schedule_work(&delayed_fput_work);
		spin_unlock_irqrestore(&delayed_fput_lock, flags);
		spin_unlock_irqrestore(&delayed_fput_lock, flags);
			return;
		}
		init_task_work(&file->f_u.fu_rcuhead, ____fput);
		task_work_add(task, &file->f_u.fu_rcuhead, true);
	}
	}
}
}


+2 −2
Original line number Original line Diff line number Diff line
@@ -1976,7 +1976,7 @@ static int path_lookupat(int dfd, const char *name,
		err = complete_walk(nd);
		err = complete_walk(nd);


	if (!err && nd->flags & LOOKUP_DIRECTORY) {
	if (!err && nd->flags & LOOKUP_DIRECTORY) {
		if (!nd->inode->i_op->lookup) {
		if (!can_lookup(nd->inode)) {
			path_put(&nd->path);
			path_put(&nd->path);
			err = -ENOTDIR;
			err = -ENOTDIR;
		}
		}
@@ -2850,7 +2850,7 @@ finish_lookup:
	if ((open_flag & O_CREAT) && S_ISDIR(nd->inode->i_mode))
	if ((open_flag & O_CREAT) && S_ISDIR(nd->inode->i_mode))
		goto out;
		goto out;
	error = -ENOTDIR;
	error = -ENOTDIR;
	if ((nd->flags & LOOKUP_DIRECTORY) && !nd->inode->i_op->lookup)
	if ((nd->flags & LOOKUP_DIRECTORY) && !can_lookup(nd->inode))
		goto out;
		goto out;
	audit_inode(name, nd->path.dentry, 0);
	audit_inode(name, nd->path.dentry, 0);
finish_open:
finish_open:
+0 −9
Original line number Original line Diff line number Diff line
@@ -1029,15 +1029,6 @@ static int ncp_rmdir(struct inode *dir, struct dentry *dentry)
	DPRINTK("ncp_rmdir: removing %s/%s\n",
	DPRINTK("ncp_rmdir: removing %s/%s\n",
		dentry->d_parent->d_name.name, dentry->d_name.name);
		dentry->d_parent->d_name.name, dentry->d_name.name);


	/*
	 * fail with EBUSY if there are still references to this
	 * directory.
	 */
	dentry_unhash(dentry);
	error = -EBUSY;
	if (!d_unhashed(dentry))
		goto out;

	len = sizeof(__name);
	len = sizeof(__name);
	error = ncp_io2vol(server, __name, &len, dentry->d_name.name,
	error = ncp_io2vol(server, __name, &len, dentry->d_name.name,
			   dentry->d_name.len, !ncp_preserve_case(dir));
			   dentry->d_name.len, !ncp_preserve_case(dir));
+1 −1
Original line number Original line Diff line number Diff line
@@ -649,7 +649,6 @@ static void exit_notify(struct task_struct *tsk, int group_dead)
	 *	jobs, send them a SIGHUP and then a SIGCONT.  (POSIX 3.2.2.2)
	 *	jobs, send them a SIGHUP and then a SIGCONT.  (POSIX 3.2.2.2)
	 */
	 */
	forget_original_parent(tsk);
	forget_original_parent(tsk);
	exit_task_namespaces(tsk);


	write_lock_irq(&tasklist_lock);
	write_lock_irq(&tasklist_lock);
	if (group_dead)
	if (group_dead)
@@ -795,6 +794,7 @@ void do_exit(long code)
	exit_shm(tsk);
	exit_shm(tsk);
	exit_files(tsk);
	exit_files(tsk);
	exit_fs(tsk);
	exit_fs(tsk);
	exit_task_namespaces(tsk);
	exit_task_work(tsk);
	exit_task_work(tsk);
	check_stack_usage();
	check_stack_usage();
	exit_thread();
	exit_thread();
+2 −2
Original line number Original line Diff line number Diff line
@@ -1649,6 +1649,7 @@ static int snd_pcm_link(struct snd_pcm_substream *substream, int fd)
	}
	}
	if (!snd_pcm_stream_linked(substream)) {
	if (!snd_pcm_stream_linked(substream)) {
		substream->group = group;
		substream->group = group;
		group = NULL;
		spin_lock_init(&substream->group->lock);
		spin_lock_init(&substream->group->lock);
		INIT_LIST_HEAD(&substream->group->substreams);
		INIT_LIST_HEAD(&substream->group->substreams);
		list_add_tail(&substream->link_list, &substream->group->substreams);
		list_add_tail(&substream->link_list, &substream->group->substreams);
@@ -1663,7 +1664,6 @@ static int snd_pcm_link(struct snd_pcm_substream *substream, int fd)
 _nolock:
 _nolock:
	snd_card_unref(substream1->pcm->card);
	snd_card_unref(substream1->pcm->card);
	fput_light(file, fput_needed);
	fput_light(file, fput_needed);
	if (res < 0)
	kfree(group);
	kfree(group);
	return res;
	return res;
}
}