aboutsummaryrefslogtreecommitdiff
path: root/net
diff options
context:
space:
mode:
Diffstat (limited to 'net')
-rw-r--r--net/socket.c18
1 files changed, 15 insertions, 3 deletions
diff --git a/net/socket.c b/net/socket.c
index b7f357804..2e6a155e2 100644
--- a/net/socket.c
+++ b/net/socket.c
@@ -524,7 +524,10 @@ static int sockfs_setattr(struct dentry *dentry, struct iattr *iattr)
if (!err && (iattr->ia_valid & ATTR_UID)) {
struct socket *sock = SOCKET_I(dentry->d_inode);
- sock->sk->sk_uid = iattr->ia_uid;
+ if (sock->sk)
+ sock->sk->sk_uid = iattr->ia_uid;
+ else
+ err = -ENOENT;
}
return err;
@@ -592,12 +595,16 @@ const struct file_operations bad_sock_fops = {
* an inode not a file.
*/
-void sock_release(struct socket *sock)
+static void __sock_release(struct socket *sock, struct inode *inode)
{
if (sock->ops) {
struct module *owner = sock->ops->owner;
+ if (inode)
+ mutex_lock(&inode->i_mutex);
sock->ops->release(sock);
+ if (inode)
+ mutex_unlock(&inode->i_mutex);
sock->ops = NULL;
module_put(owner);
}
@@ -615,6 +622,11 @@ void sock_release(struct socket *sock)
}
sock->file = NULL;
}
+
+void sock_release(struct socket *sock)
+{
+ __sock_release(sock, NULL);
+}
EXPORT_SYMBOL(sock_release);
void sock_tx_timestamp(struct sock *sk, __u8 *tx_flags)
@@ -1199,7 +1211,7 @@ static int sock_close(struct inode *inode, struct file *filp)
pr_debug(KERN_INFO "[mtk_net][socekt]socket_close[%lu] \n",inode->i_ino);
}
#endif
- sock_release(SOCKET_I(inode));
+ __sock_release(SOCKET_I(inode), inode);
return 0;
}