From: Sasha Levin Date: Sat, 1 Aug 2020 01:07:05 +0000 (-0400) Subject: Fixes for 4.4 X-Git-Tag: v5.7.13~71 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=9b8922bc2d16ffe45e6e0463f6a055ca419cedb8;p=thirdparty%2Fkernel%2Fstable-queue.git Fixes for 4.4 Signed-off-by: Sasha Levin --- diff --git a/queue-4.4/ath9k-release-allocated-buffer-if-timed-out.patch b/queue-4.4/ath9k-release-allocated-buffer-if-timed-out.patch new file mode 100644 index 00000000000..cc9b4b2322b --- /dev/null +++ b/queue-4.4/ath9k-release-allocated-buffer-if-timed-out.patch @@ -0,0 +1,34 @@ +From 5fe906752de89e962a6de127a9c6799254c2f674 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 6 Sep 2019 13:59:30 -0500 +Subject: ath9k: release allocated buffer if timed out + +From: Navid Emamdoost + +[ Upstream commit 728c1e2a05e4b5fc52fab3421dce772a806612a2 ] + +In ath9k_wmi_cmd, the allocated network buffer needs to be released +if timeout happens. Otherwise memory will be leaked. + +Signed-off-by: Navid Emamdoost +Signed-off-by: Kalle Valo +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath9k/wmi.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/net/wireless/ath/ath9k/wmi.c b/drivers/net/wireless/ath/ath9k/wmi.c +index 8f14897ae5a33..f100533eb7adc 100644 +--- a/drivers/net/wireless/ath/ath9k/wmi.c ++++ b/drivers/net/wireless/ath/ath9k/wmi.c +@@ -340,6 +340,7 @@ int ath9k_wmi_cmd(struct wmi *wmi, enum wmi_cmd_id cmd_id, + ath_dbg(common, WMI, "Timeout waiting for WMI command: %s\n", + wmi_cmd_to_name(cmd_id)); + mutex_unlock(&wmi->op_mutex); ++ kfree_skb(skb); + return -ETIMEDOUT; + } + +-- +2.25.1 + diff --git a/queue-4.4/ath9k_htc-release-allocated-buffer-if-timed-out.patch b/queue-4.4/ath9k_htc-release-allocated-buffer-if-timed-out.patch new file mode 100644 index 00000000000..e5a81bfaef9 --- /dev/null +++ b/queue-4.4/ath9k_htc-release-allocated-buffer-if-timed-out.patch @@ -0,0 +1,51 @@ +From f3b80890bd16e7b2c1fb0f8703205355075a6266 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 6 Sep 2019 13:26:03 -0500 +Subject: ath9k_htc: release allocated buffer if timed out + +From: Navid Emamdoost + +[ Upstream commit 853acf7caf10b828102d92d05b5c101666a6142b ] + +In htc_config_pipe_credits, htc_setup_complete, and htc_connect_service +if time out happens, the allocated buffer needs to be released. +Otherwise there will be memory leak. + +Signed-off-by: Navid Emamdoost +Signed-off-by: Kalle Valo +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath9k/htc_hst.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/net/wireless/ath/ath9k/htc_hst.c b/drivers/net/wireless/ath/ath9k/htc_hst.c +index 257b6ee51e54b..1af216aa5adae 100644 +--- a/drivers/net/wireless/ath/ath9k/htc_hst.c ++++ b/drivers/net/wireless/ath/ath9k/htc_hst.c +@@ -175,6 +175,7 @@ static int htc_config_pipe_credits(struct htc_target *target) + time_left = wait_for_completion_timeout(&target->cmd_wait, HZ); + if (!time_left) { + dev_err(target->dev, "HTC credit config timeout\n"); ++ kfree_skb(skb); + return -ETIMEDOUT; + } + +@@ -211,6 +212,7 @@ static int htc_setup_complete(struct htc_target *target) + time_left = wait_for_completion_timeout(&target->cmd_wait, HZ); + if (!time_left) { + dev_err(target->dev, "HTC start timeout\n"); ++ kfree_skb(skb); + return -ETIMEDOUT; + } + +@@ -284,6 +286,7 @@ int htc_connect_service(struct htc_target *target, + if (!time_left) { + dev_err(target->dev, "Service connection timeout for: %d\n", + service_connreq->service_id); ++ kfree_skb(skb); + return -ETIMEDOUT; + } + +-- +2.25.1 + diff --git a/queue-4.4/f2fs-check-if-file-namelen-exceeds-max-value.patch b/queue-4.4/f2fs-check-if-file-namelen-exceeds-max-value.patch new file mode 100644 index 00000000000..acd8be85d8c --- /dev/null +++ b/queue-4.4/f2fs-check-if-file-namelen-exceeds-max-value.patch @@ -0,0 +1,38 @@ +From 8a6e5910b2a0014ada5510bd21a838ccce6e4a7f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 7 Jan 2019 15:02:34 +0800 +Subject: f2fs: check if file namelen exceeds max value + +From: Sheng Yong + +[ Upstream commit 720db068634c91553a8e1d9a0fcd8c7050e06d2b ] + +Dentry bitmap is not enough to detect incorrect dentries. So this patch +also checks the namelen value of a dentry. + +Signed-off-by: Gong Chen +Signed-off-by: Sheng Yong +Reviewed-by: Chao Yu +Signed-off-by: Jaegeuk Kim +Signed-off-by: Sasha Levin +--- + fs/f2fs/dir.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +diff --git a/fs/f2fs/dir.c b/fs/f2fs/dir.c +index 437ec6e38d41d..b40681e91ebe2 100644 +--- a/fs/f2fs/dir.c ++++ b/fs/f2fs/dir.c +@@ -807,7 +807,8 @@ bool f2fs_fill_dentries(struct dir_context *ctx, struct f2fs_dentry_ptr *d, + + /* check memory boundary before moving forward */ + bit_pos += GET_DENTRY_SLOTS(le16_to_cpu(de->name_len)); +- if (unlikely(bit_pos > d->max)) { ++ if (unlikely(bit_pos > d->max || ++ le16_to_cpu(de->name_len) > F2FS_NAME_LEN)) { + f2fs_msg(F2FS_I_SB(d->inode)->sb, KERN_WARNING, + "%s: corrupted namelen=%d, run fsck to fix.", + __func__, le16_to_cpu(de->name_len)); +-- +2.25.1 + diff --git a/queue-4.4/f2fs-check-memory-boundary-by-insane-namelen.patch b/queue-4.4/f2fs-check-memory-boundary-by-insane-namelen.patch new file mode 100644 index 00000000000..ee65c73accf --- /dev/null +++ b/queue-4.4/f2fs-check-memory-boundary-by-insane-namelen.patch @@ -0,0 +1,51 @@ +From 830774f263ff218d0acf94f448289c871d76e8ea Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 14 Nov 2018 12:40:30 -0800 +Subject: f2fs: check memory boundary by insane namelen + +From: Jaegeuk Kim + +[ Upstream commit 4e240d1bab1ead280ddf5eb05058dba6bbd57d10 ] + +If namelen is corrupted to have very long value, fill_dentries can copy +wrong memory area. + +Reviewed-by: Chao Yu +Signed-off-by: Jaegeuk Kim +Signed-off-by: Sasha Levin +--- + fs/f2fs/dir.c | 11 ++++++++++- + 1 file changed, 10 insertions(+), 1 deletion(-) + +diff --git a/fs/f2fs/dir.c b/fs/f2fs/dir.c +index 92a240616f520..437ec6e38d41d 100644 +--- a/fs/f2fs/dir.c ++++ b/fs/f2fs/dir.c +@@ -805,6 +805,16 @@ bool f2fs_fill_dentries(struct dir_context *ctx, struct f2fs_dentry_ptr *d, + de_name.name = d->filename[bit_pos]; + de_name.len = le16_to_cpu(de->name_len); + ++ /* check memory boundary before moving forward */ ++ bit_pos += GET_DENTRY_SLOTS(le16_to_cpu(de->name_len)); ++ if (unlikely(bit_pos > d->max)) { ++ f2fs_msg(F2FS_I_SB(d->inode)->sb, KERN_WARNING, ++ "%s: corrupted namelen=%d, run fsck to fix.", ++ __func__, le16_to_cpu(de->name_len)); ++ set_sbi_flag(sbi, SBI_NEED_FSCK); ++ return -EINVAL; ++ } ++ + if (f2fs_encrypted_inode(d->inode)) { + int save_len = fstr->len; + int ret; +@@ -829,7 +839,6 @@ bool f2fs_fill_dentries(struct dir_context *ctx, struct f2fs_dentry_ptr *d, + le32_to_cpu(de->ino), d_type)) + return true; + +- bit_pos += GET_DENTRY_SLOTS(le16_to_cpu(de->name_len)); + ctx->pos = start_pos + bit_pos; + } + return false; +-- +2.25.1 + diff --git a/queue-4.4/media-rc-prevent-memory-leak-in-cx23888_ir_probe.patch b/queue-4.4/media-rc-prevent-memory-leak-in-cx23888_ir_probe.patch new file mode 100644 index 00000000000..e01b53a3c71 --- /dev/null +++ b/queue-4.4/media-rc-prevent-memory-leak-in-cx23888_ir_probe.patch @@ -0,0 +1,40 @@ +From 8a4a18a06e958aa757f7f9ca7d76d11d776103c8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 25 Sep 2019 12:02:41 -0300 +Subject: media: rc: prevent memory leak in cx23888_ir_probe + +From: Navid Emamdoost + +[ Upstream commit a7b2df76b42bdd026e3106cf2ba97db41345a177 ] + +In cx23888_ir_probe if kfifo_alloc fails the allocated memory for state +should be released. + +Signed-off-by: Navid Emamdoost +Signed-off-by: Sean Young +Signed-off-by: Mauro Carvalho Chehab +Signed-off-by: Sasha Levin +--- + drivers/media/pci/cx23885/cx23888-ir.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/drivers/media/pci/cx23885/cx23888-ir.c b/drivers/media/pci/cx23885/cx23888-ir.c +index c1aa888af7054..83864a99d3a66 100644 +--- a/drivers/media/pci/cx23885/cx23888-ir.c ++++ b/drivers/media/pci/cx23885/cx23888-ir.c +@@ -1179,8 +1179,11 @@ int cx23888_ir_probe(struct cx23885_dev *dev) + return -ENOMEM; + + spin_lock_init(&state->rx_kfifo_lock); +- if (kfifo_alloc(&state->rx_kfifo, CX23888_IR_RX_KFIFO_SIZE, GFP_KERNEL)) ++ if (kfifo_alloc(&state->rx_kfifo, CX23888_IR_RX_KFIFO_SIZE, ++ GFP_KERNEL)) { ++ kfree(state); + return -ENOMEM; ++ } + + state->dev = dev; + sd = &state->sd; +-- +2.25.1 + diff --git a/queue-4.4/net-phy-mdio-bcm-unimac-fix-potential-null-dereferen.patch b/queue-4.4/net-phy-mdio-bcm-unimac-fix-potential-null-dereferen.patch new file mode 100644 index 00000000000..e903da5c74b --- /dev/null +++ b/queue-4.4/net-phy-mdio-bcm-unimac-fix-potential-null-dereferen.patch @@ -0,0 +1,49 @@ +From ab3672e8a2503ccebf18ec644bdff42b637be3ec Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 11 Jan 2018 11:21:51 +0000 +Subject: net: phy: mdio-bcm-unimac: fix potential NULL dereference in + unimac_mdio_probe() + +From: Wei Yongjun + +[ Upstream commit 297a6961ffb8ff4dc66c9fbf53b924bd1dda05d5 ] + +platform_get_resource() may fail and return NULL, so we should +better check it's return value to avoid a NULL pointer dereference +a bit later in the code. + +This is detected by Coccinelle semantic patch. + +@@ +expression pdev, res, n, t, e, e1, e2; +@@ + +res = platform_get_resource(pdev, t, n); ++ if (!res) ++ return -EINVAL; +... when != res == NULL +e = devm_ioremap(e1, res->start, e2); + +Signed-off-by: Wei Yongjun +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + drivers/net/phy/mdio-bcm-unimac.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/drivers/net/phy/mdio-bcm-unimac.c b/drivers/net/phy/mdio-bcm-unimac.c +index 4bde5e728fe0a..fd8692b477c96 100644 +--- a/drivers/net/phy/mdio-bcm-unimac.c ++++ b/drivers/net/phy/mdio-bcm-unimac.c +@@ -177,6 +177,8 @@ static int unimac_mdio_probe(struct platform_device *pdev) + return -ENOMEM; + + r = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (!r) ++ return -EINVAL; + + /* Just ioremap, as this MDIO block is usually integrated into an + * Ethernet MAC controller register range +-- +2.25.1 + diff --git a/queue-4.4/nfs-move-call-to-security_inode_listsecurity-into-nf.patch b/queue-4.4/nfs-move-call-to-security_inode_listsecurity-into-nf.patch new file mode 100644 index 00000000000..96e818f4a1a --- /dev/null +++ b/queue-4.4/nfs-move-call-to-security_inode_listsecurity-into-nf.patch @@ -0,0 +1,166 @@ +From 6e0c2b7294ab3d76f91af35aff171433041ebe24 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 2 Dec 2015 14:44:41 +0100 +Subject: nfs: Move call to security_inode_listsecurity into nfs_listxattr + +From: Andreas Gruenbacher + +[ Upstream commit c4803c497fbdb37e96af614813a7cfb434b6682a ] + +Add a nfs_listxattr operation. Move the call to security_inode_listsecurity +from list operation of the "security.*" xattr handler to nfs_listxattr. + +Signed-off-by: Andreas Gruenbacher +Cc: Trond Myklebust +Cc: Anna Schumaker +Cc: linux-nfs@vger.kernel.org +Signed-off-by: Al Viro +Signed-off-by: Sasha Levin +--- + fs/nfs/nfs4proc.c | 53 ++++++++++++++++++++++++++------------ + fs/xattr.c | 4 +++ + security/smack/smack_lsm.c | 2 -- + 3 files changed, 40 insertions(+), 19 deletions(-) + +diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c +index 0308b56896382..566afcc36adb5 100644 +--- a/fs/nfs/nfs4proc.c ++++ b/fs/nfs/nfs4proc.c +@@ -6296,10 +6296,6 @@ static size_t nfs4_xattr_list_nfs4_acl(const struct xattr_handler *handler, + } + + #ifdef CONFIG_NFS_V4_SECURITY_LABEL +-static inline int nfs4_server_supports_labels(struct nfs_server *server) +-{ +- return server->caps & NFS_CAP_SECURITY_LABEL; +-} + + static int nfs4_xattr_set_nfs4_label(const struct xattr_handler *handler, + struct dentry *dentry, const char *key, +@@ -6321,29 +6317,34 @@ static int nfs4_xattr_get_nfs4_label(const struct xattr_handler *handler, + return -EOPNOTSUPP; + } + +-static size_t nfs4_xattr_list_nfs4_label(const struct xattr_handler *handler, +- struct dentry *dentry, char *list, +- size_t list_len, const char *name, +- size_t name_len) ++static ssize_t ++nfs4_listxattr_nfs4_label(struct inode *inode, char *list, size_t list_len) + { +- size_t len = 0; ++ int len = 0; + +- if (nfs_server_capable(d_inode(dentry), NFS_CAP_SECURITY_LABEL)) { +- len = security_inode_listsecurity(d_inode(dentry), NULL, 0); +- if (list && len <= list_len) +- security_inode_listsecurity(d_inode(dentry), list, len); ++ if (nfs_server_capable(inode, NFS_CAP_SECURITY_LABEL)) { ++ len = security_inode_listsecurity(inode, list, list_len); ++ if (list_len && len > list_len) ++ return -ERANGE; + } + return len; + } + + static const struct xattr_handler nfs4_xattr_nfs4_label_handler = { + .prefix = XATTR_SECURITY_PREFIX, +- .list = nfs4_xattr_list_nfs4_label, + .get = nfs4_xattr_get_nfs4_label, + .set = nfs4_xattr_set_nfs4_label, + }; +-#endif + ++#else ++ ++static ssize_t ++nfs4_listxattr_nfs4_label(struct inode *inode, char *list, size_t list_len) ++{ ++ return 0; ++} ++ ++#endif + + /* + * nfs_fhget will use either the mounted_on_fileid or the fileid +@@ -8773,6 +8774,24 @@ const struct nfs4_minor_version_ops *nfs_v4_minor_ops[] = { + #endif + }; + ++ssize_t nfs4_listxattr(struct dentry *dentry, char *list, size_t size) ++{ ++ ssize_t error, error2; ++ ++ error = generic_listxattr(dentry, list, size); ++ if (error < 0) ++ return error; ++ if (list) { ++ list += error; ++ size -= error; ++ } ++ ++ error2 = nfs4_listxattr_nfs4_label(d_inode(dentry), list, size); ++ if (error2 < 0) ++ return error2; ++ return error + error2; ++} ++ + static const struct inode_operations nfs4_dir_inode_operations = { + .create = nfs_create, + .lookup = nfs_lookup, +@@ -8789,7 +8808,7 @@ static const struct inode_operations nfs4_dir_inode_operations = { + .setattr = nfs_setattr, + .getxattr = generic_getxattr, + .setxattr = generic_setxattr, +- .listxattr = generic_listxattr, ++ .listxattr = nfs4_listxattr, + .removexattr = generic_removexattr, + }; + +@@ -8799,7 +8818,7 @@ static const struct inode_operations nfs4_file_inode_operations = { + .setattr = nfs_setattr, + .getxattr = generic_getxattr, + .setxattr = generic_setxattr, +- .listxattr = generic_listxattr, ++ .listxattr = nfs4_listxattr, + .removexattr = generic_removexattr, + }; + +diff --git a/fs/xattr.c b/fs/xattr.c +index 09441c396798d..5ba5565609eed 100644 +--- a/fs/xattr.c ++++ b/fs/xattr.c +@@ -735,6 +735,8 @@ generic_listxattr(struct dentry *dentry, char *buffer, size_t buffer_size) + + if (!buffer) { + for_each_xattr_handler(handlers, handler) { ++ if (!handler->list) ++ continue; + size += handler->list(handler, dentry, NULL, 0, + NULL, 0); + } +@@ -742,6 +744,8 @@ generic_listxattr(struct dentry *dentry, char *buffer, size_t buffer_size) + char *buf = buffer; + + for_each_xattr_handler(handlers, handler) { ++ if (!handler->list) ++ continue; + size = handler->list(handler, dentry, buf, buffer_size, + NULL, 0); + if (size > buffer_size) +diff --git a/security/smack/smack_lsm.c b/security/smack/smack_lsm.c +index 716433e630529..d37c1963e8ca3 100644 +--- a/security/smack/smack_lsm.c ++++ b/security/smack/smack_lsm.c +@@ -1513,8 +1513,6 @@ static int smack_inode_getsecurity(const struct inode *inode, + * @inode: the object + * @buffer: where they go + * @buffer_size: size of buffer +- * +- * Returns 0 on success, -EINVAL otherwise + */ + static int smack_inode_listsecurity(struct inode *inode, char *buffer, + size_t buffer_size) +-- +2.25.1 + diff --git a/queue-4.4/scsi-libsas-direct-call-probe-and-destruct.patch b/queue-4.4/scsi-libsas-direct-call-probe-and-destruct.patch new file mode 100644 index 00000000000..1518c0e8d9c --- /dev/null +++ b/queue-4.4/scsi-libsas-direct-call-probe-and-destruct.patch @@ -0,0 +1,304 @@ +From eae554124abfbd7f11ba9ed57da2ac4c47823b2c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 8 Dec 2017 17:42:09 +0800 +Subject: scsi: libsas: direct call probe and destruct + +From: Jason Yan + +[ Upstream commit 0558f33c06bb910e2879e355192227a8e8f0219d ] + +In commit 87c8331fcf72 ("[SCSI] libsas: prevent domain rediscovery +competing with ata error handling") introduced disco mutex to prevent +rediscovery competing with ata error handling and put the whole +revalidation in the mutex. But the rphy add/remove needs to wait for the +error handling which also grabs the disco mutex. This may leads to dead +lock.So the probe and destruct event were introduce to do the rphy +add/remove asynchronously and out of the lock. + +The asynchronously processed workers makes the whole discovery process +not atomic, the other events may interrupt the process. For example, +if a loss of signal event inserted before the probe event, the +sas_deform_port() is called and the port will be deleted. + +And sas_port_delete() may run before the destruct event, but the +port-x:x is the top parent of end device or expander. This leads to +a kernel WARNING such as: + +[ 82.042979] sysfs group 'power' not found for kobject 'phy-1:0:22' +[ 82.042983] ------------[ cut here ]------------ +[ 82.042986] WARNING: CPU: 54 PID: 1714 at fs/sysfs/group.c:237 +sysfs_remove_group+0x94/0xa0 +[ 82.043059] Call trace: +[ 82.043082] [] sysfs_remove_group+0x94/0xa0 +[ 82.043085] [] dpm_sysfs_remove+0x60/0x70 +[ 82.043086] [] device_del+0x138/0x308 +[ 82.043089] [] sas_phy_delete+0x38/0x60 +[ 82.043091] [] do_sas_phy_delete+0x6c/0x80 +[ 82.043093] [] device_for_each_child+0x58/0xa0 +[ 82.043095] [] sas_remove_children+0x40/0x50 +[ 82.043100] [] sas_destruct_devices+0x64/0xa0 +[ 82.043102] [] process_one_work+0x1fc/0x4b0 +[ 82.043104] [] worker_thread+0x50/0x490 +[ 82.043105] [] kthread+0xfc/0x128 +[ 82.043107] [] ret_from_fork+0x10/0x50 + +Make probe and destruct a direct call in the disco and revalidate function, +but put them outside the lock. The whole discovery or revalidate won't +be interrupted by other events. And the DISCE_PROBE and DISCE_DESTRUCT +event are deleted as a result of the direct call. + +Introduce a new list to destruct the sas_port and put the port delete after +the destruct. This makes sure the right order of destroying the sysfs +kobject and fix the warning above. + +In sas_ex_revalidate_domain() have a loop to find all broadcasted +device, and sometimes we have a chance to find the same expander twice. +Because the sas_port will be deleted at the end of the whole revalidate +process, sas_port with the same name cannot be added before this. +Otherwise the sysfs will complain of creating duplicate filename. Since +the LLDD will send broadcast for every device change, we can only +process one expander's revalidation. + +[mkp: kbuild test robot warning] + +Signed-off-by: Jason Yan +CC: John Garry +CC: Johannes Thumshirn +CC: Ewan Milne +CC: Christoph Hellwig +CC: Tomas Henzl +CC: Dan Williams +Reviewed-by: Hannes Reinecke +Signed-off-by: Martin K. Petersen +Signed-off-by: Sasha Levin +--- + drivers/scsi/libsas/sas_ata.c | 1 - + drivers/scsi/libsas/sas_discover.c | 32 +++++++++++++++++------------- + drivers/scsi/libsas/sas_expander.c | 8 +++----- + drivers/scsi/libsas/sas_internal.h | 1 + + drivers/scsi/libsas/sas_port.c | 3 +++ + include/scsi/libsas.h | 3 +-- + include/scsi/scsi_transport_sas.h | 1 + + 7 files changed, 27 insertions(+), 22 deletions(-) + +diff --git a/drivers/scsi/libsas/sas_ata.c b/drivers/scsi/libsas/sas_ata.c +index 6f5e2720ffad1..e018e76b156b1 100644 +--- a/drivers/scsi/libsas/sas_ata.c ++++ b/drivers/scsi/libsas/sas_ata.c +@@ -732,7 +732,6 @@ int sas_discover_sata(struct domain_device *dev) + if (res) + return res; + +- sas_discover_event(dev->port, DISCE_PROBE); + return 0; + } + +diff --git a/drivers/scsi/libsas/sas_discover.c b/drivers/scsi/libsas/sas_discover.c +index b200edc665a58..d6365e2fcc603 100644 +--- a/drivers/scsi/libsas/sas_discover.c ++++ b/drivers/scsi/libsas/sas_discover.c +@@ -221,13 +221,9 @@ void sas_notify_lldd_dev_gone(struct domain_device *dev) + } + } + +-static void sas_probe_devices(struct work_struct *work) ++static void sas_probe_devices(struct asd_sas_port *port) + { + struct domain_device *dev, *n; +- struct sas_discovery_event *ev = to_sas_discovery_event(work); +- struct asd_sas_port *port = ev->port; +- +- clear_bit(DISCE_PROBE, &port->disc.pending); + + /* devices must be domain members before link recovery and probe */ + list_for_each_entry(dev, &port->disco_list, disco_list_node) { +@@ -303,7 +299,6 @@ int sas_discover_end_dev(struct domain_device *dev) + res = sas_notify_lldd_dev_found(dev); + if (res) + return res; +- sas_discover_event(dev->port, DISCE_PROBE); + + return 0; + } +@@ -362,13 +357,9 @@ static void sas_unregister_common_dev(struct asd_sas_port *port, struct domain_d + sas_put_device(dev); + } + +-static void sas_destruct_devices(struct work_struct *work) ++void sas_destruct_devices(struct asd_sas_port *port) + { + struct domain_device *dev, *n; +- struct sas_discovery_event *ev = to_sas_discovery_event(work); +- struct asd_sas_port *port = ev->port; +- +- clear_bit(DISCE_DESTRUCT, &port->disc.pending); + + list_for_each_entry_safe(dev, n, &port->destroy_list, disco_list_node) { + list_del_init(&dev->disco_list_node); +@@ -379,6 +370,16 @@ static void sas_destruct_devices(struct work_struct *work) + } + } + ++static void sas_destruct_ports(struct asd_sas_port *port) ++{ ++ struct sas_port *sas_port, *p; ++ ++ list_for_each_entry_safe(sas_port, p, &port->sas_port_del_list, del_list) { ++ list_del_init(&sas_port->del_list); ++ sas_port_delete(sas_port); ++ } ++} ++ + void sas_unregister_dev(struct asd_sas_port *port, struct domain_device *dev) + { + if (!test_bit(SAS_DEV_DESTROY, &dev->state) && +@@ -393,7 +394,6 @@ void sas_unregister_dev(struct asd_sas_port *port, struct domain_device *dev) + if (!test_and_set_bit(SAS_DEV_DESTROY, &dev->state)) { + sas_rphy_unlink(dev->rphy); + list_move_tail(&dev->disco_list_node, &port->destroy_list); +- sas_discover_event(dev->port, DISCE_DESTRUCT); + } + } + +@@ -499,6 +499,8 @@ static void sas_discover_domain(struct work_struct *work) + port->port_dev = NULL; + } + ++ sas_probe_devices(port); ++ + SAS_DPRINTK("DONE DISCOVERY on port %d, pid:%d, result:%d\n", port->id, + task_pid_nr(current), error); + } +@@ -532,6 +534,10 @@ static void sas_revalidate_domain(struct work_struct *work) + port->id, task_pid_nr(current), res); + out: + mutex_unlock(&ha->disco_mutex); ++ ++ sas_destruct_devices(port); ++ sas_destruct_ports(port); ++ sas_probe_devices(port); + } + + /* ---------- Events ---------- */ +@@ -587,10 +593,8 @@ void sas_init_disc(struct sas_discovery *disc, struct asd_sas_port *port) + static const work_func_t sas_event_fns[DISC_NUM_EVENTS] = { + [DISCE_DISCOVER_DOMAIN] = sas_discover_domain, + [DISCE_REVALIDATE_DOMAIN] = sas_revalidate_domain, +- [DISCE_PROBE] = sas_probe_devices, + [DISCE_SUSPEND] = sas_suspend_devices, + [DISCE_RESUME] = sas_resume_devices, +- [DISCE_DESTRUCT] = sas_destruct_devices, + }; + + disc->pending = 0; +diff --git a/drivers/scsi/libsas/sas_expander.c b/drivers/scsi/libsas/sas_expander.c +index 7e8274938a3ee..ff3289a41c157 100644 +--- a/drivers/scsi/libsas/sas_expander.c ++++ b/drivers/scsi/libsas/sas_expander.c +@@ -1935,7 +1935,8 @@ static void sas_unregister_devs_sas_addr(struct domain_device *parent, + sas_port_delete_phy(phy->port, phy->phy); + sas_device_set_phy(found, phy->port); + if (phy->port->num_phys == 0) +- sas_port_delete(phy->port); ++ list_add_tail(&phy->port->del_list, ++ &parent->port->sas_port_del_list); + phy->port = NULL; + } + } +@@ -2145,7 +2146,7 @@ int sas_ex_revalidate_domain(struct domain_device *port_dev) + struct domain_device *dev = NULL; + + res = sas_find_bcast_dev(port_dev, &dev); +- while (res == 0 && dev) { ++ if (res == 0 && dev) { + struct expander_device *ex = &dev->ex_dev; + int i = 0, phy_id; + +@@ -2157,9 +2158,6 @@ int sas_ex_revalidate_domain(struct domain_device *port_dev) + res = sas_rediscover(dev, phy_id); + i = phy_id + 1; + } while (i < ex->num_phys); +- +- dev = NULL; +- res = sas_find_bcast_dev(port_dev, &dev); + } + return res; + } +diff --git a/drivers/scsi/libsas/sas_internal.h b/drivers/scsi/libsas/sas_internal.h +index 9cf0bc260b0e7..2cbbd113d8984 100644 +--- a/drivers/scsi/libsas/sas_internal.h ++++ b/drivers/scsi/libsas/sas_internal.h +@@ -98,6 +98,7 @@ int sas_try_ata_reset(struct asd_sas_phy *phy); + void sas_hae_reset(struct work_struct *work); + + void sas_free_device(struct kref *kref); ++void sas_destruct_devices(struct asd_sas_port *port); + + #ifdef CONFIG_SCSI_SAS_HOST_SMP + extern int sas_smp_host_handler(struct Scsi_Host *shost, struct request *req, +diff --git a/drivers/scsi/libsas/sas_port.c b/drivers/scsi/libsas/sas_port.c +index d3c5297c6c89e..5d3244c8f2801 100644 +--- a/drivers/scsi/libsas/sas_port.c ++++ b/drivers/scsi/libsas/sas_port.c +@@ -66,6 +66,7 @@ static void sas_resume_port(struct asd_sas_phy *phy) + rc = sas_notify_lldd_dev_found(dev); + if (rc) { + sas_unregister_dev(port, dev); ++ sas_destruct_devices(port); + continue; + } + +@@ -219,6 +220,7 @@ void sas_deform_port(struct asd_sas_phy *phy, int gone) + + if (port->num_phys == 1) { + sas_unregister_domain_devices(port, gone); ++ sas_destruct_devices(port); + sas_port_delete(port->port); + port->port = NULL; + } else { +@@ -323,6 +325,7 @@ static void sas_init_port(struct asd_sas_port *port, + INIT_LIST_HEAD(&port->dev_list); + INIT_LIST_HEAD(&port->disco_list); + INIT_LIST_HEAD(&port->destroy_list); ++ INIT_LIST_HEAD(&port->sas_port_del_list); + spin_lock_init(&port->phy_list_lock); + INIT_LIST_HEAD(&port->phy_list); + port->ha = sas_ha; +diff --git a/include/scsi/libsas.h b/include/scsi/libsas.h +index 706a7017885c2..8a27e35b20803 100644 +--- a/include/scsi/libsas.h ++++ b/include/scsi/libsas.h +@@ -87,10 +87,8 @@ enum discover_event { + DISCE_DISCOVER_DOMAIN = 0U, + DISCE_REVALIDATE_DOMAIN = 1, + DISCE_PORT_GONE = 2, +- DISCE_PROBE = 3, + DISCE_SUSPEND = 4, + DISCE_RESUME = 5, +- DISCE_DESTRUCT = 6, + DISC_NUM_EVENTS = 7, + }; + +@@ -269,6 +267,7 @@ struct asd_sas_port { + struct list_head dev_list; + struct list_head disco_list; + struct list_head destroy_list; ++ struct list_head sas_port_del_list; + enum sas_linkrate linkrate; + + struct sas_work work; +diff --git a/include/scsi/scsi_transport_sas.h b/include/scsi/scsi_transport_sas.h +index 0bd71e2702e31..e6c7ff5c08d56 100644 +--- a/include/scsi/scsi_transport_sas.h ++++ b/include/scsi/scsi_transport_sas.h +@@ -145,6 +145,7 @@ struct sas_port { + + struct mutex phy_list_mutex; + struct list_head phy_list; ++ struct list_head del_list; /* libsas only */ + }; + + #define dev_to_sas_port(d) \ +-- +2.25.1 + diff --git a/queue-4.4/series b/queue-4.4/series new file mode 100644 index 00000000000..3936cc3b25a --- /dev/null +++ b/queue-4.4/series @@ -0,0 +1,9 @@ +xfs-don-t-call-xfs_da_shrink_inode-with-null-bp.patch +net-phy-mdio-bcm-unimac-fix-potential-null-dereferen.patch +media-rc-prevent-memory-leak-in-cx23888_ir_probe.patch +ath9k_htc-release-allocated-buffer-if-timed-out.patch +ath9k-release-allocated-buffer-if-timed-out.patch +f2fs-check-memory-boundary-by-insane-namelen.patch +f2fs-check-if-file-namelen-exceeds-max-value.patch +nfs-move-call-to-security_inode_listsecurity-into-nf.patch +scsi-libsas-direct-call-probe-and-destruct.patch diff --git a/queue-4.4/xfs-don-t-call-xfs_da_shrink_inode-with-null-bp.patch b/queue-4.4/xfs-don-t-call-xfs_da_shrink_inode-with-null-bp.patch new file mode 100644 index 00000000000..639dff3cf7e --- /dev/null +++ b/queue-4.4/xfs-don-t-call-xfs_da_shrink_inode-with-null-bp.patch @@ -0,0 +1,48 @@ +From f89ca7c692c5db56c9e89d1c225af4669ee13434 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 8 Jun 2018 09:53:49 -0700 +Subject: xfs: don't call xfs_da_shrink_inode with NULL bp + +From: Eric Sandeen + +[ Upstream commit bb3d48dcf86a97dc25fe9fc2c11938e19cb4399a ] + +xfs_attr3_leaf_create may have errored out before instantiating a buffer, +for example if the blkno is out of range. In that case there is no work +to do to remove it, and in fact xfs_da_shrink_inode will lead to an oops +if we try. + +This also seems to fix a flaw where the original error from +xfs_attr3_leaf_create gets overwritten in the cleanup case, and it +removes a pointless assignment to bp which isn't used after this. + +Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=199969 +Reported-by: Xu, Wen +Tested-by: Xu, Wen +Signed-off-by: Eric Sandeen +Reviewed-by: Darrick J. Wong +Signed-off-by: Darrick J. Wong +Signed-off-by: Sasha Levin +--- + fs/xfs/libxfs/xfs_attr_leaf.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +diff --git a/fs/xfs/libxfs/xfs_attr_leaf.c b/fs/xfs/libxfs/xfs_attr_leaf.c +index 01a5ecfedfcf1..445a3f2f871fb 100644 +--- a/fs/xfs/libxfs/xfs_attr_leaf.c ++++ b/fs/xfs/libxfs/xfs_attr_leaf.c +@@ -779,9 +779,8 @@ xfs_attr_shortform_to_leaf(xfs_da_args_t *args) + ASSERT(blkno == 0); + error = xfs_attr3_leaf_create(args, blkno, &bp); + if (error) { +- error = xfs_da_shrink_inode(args, 0, bp); +- bp = NULL; +- if (error) ++ /* xfs_attr3_leaf_create may not have instantiated a block */ ++ if (bp && (xfs_da_shrink_inode(args, 0, bp) != 0)) + goto out; + xfs_idata_realloc(dp, size, XFS_ATTR_FORK); /* try to put */ + memcpy(ifp->if_u1.if_data, tmpbuffer, size); /* it back */ +-- +2.25.1 +