diff options
Diffstat (limited to 'kernel')
-rw-r--r-- | kernel/fork.c | 20 |
1 files changed, 14 insertions, 6 deletions
diff --git a/kernel/fork.c b/kernel/fork.c index c08cf05dd59b..208dd99f13bc 100644 --- a/kernel/fork.c +++ b/kernel/fork.c | |||
@@ -1606,7 +1606,7 @@ asmlinkage long sys_unshare(unsigned long unshare_flags) | |||
1606 | struct mm_struct *mm, *new_mm = NULL, *active_mm = NULL; | 1606 | struct mm_struct *mm, *new_mm = NULL, *active_mm = NULL; |
1607 | struct files_struct *fd, *new_fd = NULL; | 1607 | struct files_struct *fd, *new_fd = NULL; |
1608 | struct sem_undo_list *new_ulist = NULL; | 1608 | struct sem_undo_list *new_ulist = NULL; |
1609 | struct nsproxy *new_nsproxy, *old_nsproxy; | 1609 | struct nsproxy *new_nsproxy = NULL, *old_nsproxy = NULL; |
1610 | struct uts_namespace *uts, *new_uts = NULL; | 1610 | struct uts_namespace *uts, *new_uts = NULL; |
1611 | 1611 | ||
1612 | check_unshare_flags(&unshare_flags); | 1612 | check_unshare_flags(&unshare_flags); |
@@ -1634,18 +1634,24 @@ asmlinkage long sys_unshare(unsigned long unshare_flags) | |||
1634 | if ((err = unshare_utsname(unshare_flags, &new_uts))) | 1634 | if ((err = unshare_utsname(unshare_flags, &new_uts))) |
1635 | goto bad_unshare_cleanup_semundo; | 1635 | goto bad_unshare_cleanup_semundo; |
1636 | 1636 | ||
1637 | if (new_fs || new_ns || new_sigh || new_mm || new_fd || new_ulist || | 1637 | if (new_ns || new_uts) { |
1638 | new_uts) { | ||
1639 | |||
1640 | old_nsproxy = current->nsproxy; | 1638 | old_nsproxy = current->nsproxy; |
1641 | new_nsproxy = dup_namespaces(old_nsproxy); | 1639 | new_nsproxy = dup_namespaces(old_nsproxy); |
1642 | if (!new_nsproxy) { | 1640 | if (!new_nsproxy) { |
1643 | err = -ENOMEM; | 1641 | err = -ENOMEM; |
1644 | goto bad_unshare_cleanup_uts; | 1642 | goto bad_unshare_cleanup_uts; |
1645 | } | 1643 | } |
1644 | } | ||
1645 | |||
1646 | if (new_fs || new_ns || new_sigh || new_mm || new_fd || new_ulist || | ||
1647 | new_uts) { | ||
1646 | 1648 | ||
1647 | task_lock(current); | 1649 | task_lock(current); |
1648 | current->nsproxy = new_nsproxy; | 1650 | |
1651 | if (new_nsproxy) { | ||
1652 | current->nsproxy = new_nsproxy; | ||
1653 | new_nsproxy = old_nsproxy; | ||
1654 | } | ||
1649 | 1655 | ||
1650 | if (new_fs) { | 1656 | if (new_fs) { |
1651 | fs = current->fs; | 1657 | fs = current->fs; |
@@ -1687,9 +1693,11 @@ asmlinkage long sys_unshare(unsigned long unshare_flags) | |||
1687 | } | 1693 | } |
1688 | 1694 | ||
1689 | task_unlock(current); | 1695 | task_unlock(current); |
1690 | put_nsproxy(old_nsproxy); | ||
1691 | } | 1696 | } |
1692 | 1697 | ||
1698 | if (new_nsproxy) | ||
1699 | put_nsproxy(new_nsproxy); | ||
1700 | |||
1693 | bad_unshare_cleanup_uts: | 1701 | bad_unshare_cleanup_uts: |
1694 | if (new_uts) | 1702 | if (new_uts) |
1695 | put_uts_ns(new_uts); | 1703 | put_uts_ns(new_uts); |