• Oleg Nesterov's avatar
    fput: task_work_add() can fail if the caller has passed exit_task_work() · e7b2c406
    Oleg Nesterov authored
    fput() assumes that it can't be called after exit_task_work() but
    this is not true, for example free_ipc_ns()->shm_destroy() can do
    this. In this case fput() silently leaks the file.
    
    Change it to fallback to delayed_fput_work if task_work_add() fails.
    The patch looks complicated but it is not, it changes the code from
    
    	if (PF_KTHREAD) {
    		schedule_work(...);
    		return;
    	}
    	task_work_add(...)
    
    to
    	if (!PF_KTHREAD) {
    		if (!task_work_add(...))
    			return;
    		/* fallback */
    	}
    	schedule_work(...);
    
    As for shm_destroy() in particular, we could make another fix but I
    think this change makes sense anyway. There could be another similar
    user, it is not safe to assume that task_work_add() can't fail.
    Reported-by: default avatarAndrey Vagin <avagin@openvz.org>
    Signed-off-by: default avatarOleg Nesterov <oleg@redhat.com>
    Signed-off-by: default avatarAl Viro <viro@zeniv.linux.org.uk>
    e7b2c406
file_table.c 12.4 KB