5.7.6-rc1 review
Subsystems (5)
Greg Kroah-Hartman
maintainerPATCH 138/477 s390/qdio: consistently restore the IRQ handler
In reply to Greg Kroah-HartmanFrom: Julian Wiedmann <[email protected]>
[ Upstream commit 7b942b4be971d49cb185ce4690d7fbf94636e88a ]
For rolling back after an error, qdio_establish() calls qdio_shutdown(). If the error occurs early enough, then the qdio_irq's state still is QDIO_IRQ_STATE_INACTIVE and qdio_shutdown() does nothing.
But at _any_ point where qdio_establish() bails out in this way, qdio_setup_irq() will have already replaced the IRQ handler. This then won't be restored after an early error, and the device can end up being returned to the device driver with qdio's IRQ handler still installed.
Slightly reorder qdio_setup_irq() so we can be 100% sure that the IRQ handler was replaced. Then fix the bug in qdio_establish() by calling a helper that rolls back only the IRQ handler modification.
Also use the new helper in qdio_shutdown() to keep things in sync, and slightly clean up the locking while doing so.
This makes minor semantical changes, but holding setup_mutex gives us sufficient leeway to eg. pull qdio_shutdown_thinint() outside of the ccwdev lock's scope.
--- drivers/s390/cio/qdio.h | 1 + drivers/s390/cio/qdio_main.c | 18 +++++------------- drivers/s390/cio/qdio_setup.c | 20 ++++++++++++++++---- 3 files changed, 22 insertions(+), 17 deletions(-)
drivers/s390/cio/qdio.h +1 -0
@@ -389,6 +389,7 @@ int qdio_setup_get_ssqd(struct qdio_irq *irq_ptr,struct subchannel_id *schid, struct qdio_ssqd_desc *data);int qdio_setup_irq (struct qdio_irq *irq_ptr,struct qdio_initialize *init_data); +void qdio_shutdown_irq (struct qdio_irq *irq);void qdio_print_subchannel_info (struct qdio_irq *irq_ptr);void qdio_release_memory (struct qdio_irq *irq_ptr);int qdio_setup_init (void );
drivers/s390/cio/qdio_main.c +5 -13
@@ -1154,35 +1154,27 @@ int qdio_shutdown(struct ccw_device *cdev, int how)/* cleanup subchannel */ spin_lock_irq (get_ccwdev_lock (cdev)); - +qdio_set_state (irq_ptr,QDIO_IRQ_STATE_CLEANUP );if (how &QDIO_FLAG_CLEANUP_USING_CLEAR ) rc =ccw_device_clear (cdev,QDIO_DOING_CLEANUP );else /* default behaviour is halt */ rc =ccw_device_halt (cdev,QDIO_DOING_CLEANUP ); +spin_unlock_irq (get_ccwdev_lock (cdev));if (rc) {DBF_ERROR ("%4x SHUTD ERR" , irq_ptr->schid.sch_no);DBF_ERROR ("rc:%4d" , rc); goto no_cleanup; } -qdio_set_state (irq_ptr,QDIO_IRQ_STATE_CLEANUP ); -spin_unlock_irq (get_ccwdev_lock (cdev));wait_event_interruptible_timeout (cdev->private->wait_q, irq_ptr->state ==QDIO_IRQ_STATE_INACTIVE || irq_ptr->state ==QDIO_IRQ_STATE_ERR ,10 *HZ ); -spin_lock_irq (get_ccwdev_lock (cdev)); no_cleanup:qdio_shutdown_thinint (irq_ptr); - -/* restore interrupt handler */ -if ((void *)cdev->handler == (void *)qdio_int_handler) { - cdev->handler = irq_ptr->orig_handler; - cdev->private->intparm =0 ; - } -spin_unlock_irq (get_ccwdev_lock (cdev)); +qdio_shutdown_irq (irq_ptr);qdio_set_state (irq_ptr,QDIO_IRQ_STATE_INACTIVE );mutex_unlock (&irq_ptr->setup_mutex);
@@ -1352,8 +1344,8 @@ int qdio_establish(struct ccw_device *cdev, rc =qdio_establish_thinint (irq_ptr);if (rc) { +qdio_shutdown_irq (irq_ptr);mutex_unlock (&irq_ptr->setup_mutex); -qdio_shutdown (cdev,QDIO_FLAG_CLEANUP_USING_CLEAR );return rc; }
@@ -1371,8 +1363,8 @@ int qdio_establish(struct ccw_device *cdev,if (rc) {DBF_ERROR ("%4x est IO ERR" , irq_ptr->schid.sch_no);DBF_ERROR ("rc:%4x" , rc); +qdio_shutdown_irq (irq_ptr);mutex_unlock (&irq_ptr->setup_mutex); -qdio_shutdown (cdev,QDIO_FLAG_CLEANUP_USING_CLEAR );return rc; }
drivers/s390/cio/qdio_setup.c +16 -4
@@ -491,6 +491,12 @@ int qdio_setup_irq(struct qdio_irq *irq_ptr, struct qdio_initialize *init_data)/* qdr, qib, sls, slsbs, slibs, sbales are filled now */ +/* set our IRQ handler */ +spin_lock_irq (get_ccwdev_lock (cdev)); + irq_ptr->orig_handler = cdev->handler; + cdev->handler = qdio_int_handler; +spin_unlock_irq (get_ccwdev_lock (cdev)); +/* get qdio commands */ ciw =ccw_device_get_ciw (cdev,CIW_TYPE_EQUEUE );if (!ciw) {
@@ -506,12 +512,18 @@ int qdio_setup_irq(struct qdio_irq *irq_ptr, struct qdio_initialize *init_data) } irq_ptr->aqueue = *ciw; -/* set new interrupt handler */ +return 0 ; +} + +void qdio_shutdown_irq (struct qdio_irq *irq) +{ +struct ccw_device *cdev = irq->cdev; + +/* restore IRQ handler */ spin_lock_irq (get_ccwdev_lock (cdev)); - irq_ptr->orig_handler = cdev->handler; - cdev->handler = qdio_int_handler; + cdev->handler = irq->orig_handler; + cdev->private->intparm =0 ;spin_unlock_irq (get_ccwdev_lock (cdev)); -return 0 ; }void qdio_print_subchannel_info (struct qdio_irq *irq_ptr)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 139/477 s390/qdio: tear down thinint indicator after early error
In reply to Greg Kroah-HartmanFrom: Julian Wiedmann <[email protected]>
[ Upstream commit 68a381746f20e5435206173e22d0a011ef78790e ]
qdio_establish() calls qdio_establish_thinint(), but later has an error exit path that doesn't roll this call back. Fix it.
--- drivers/s390/cio/qdio_main.c | 1 + 1 file changed, 1 insertion(+)
drivers/s390/cio/qdio_main.c +1 -0
@@ -1363,6 +1363,7 @@ int qdio_establish(struct ccw_device *cdev,if (rc) {DBF_ERROR ("%4x est IO ERR" , irq_ptr->schid.sch_no);DBF_ERROR ("rc:%4x" , rc); +qdio_shutdown_thinint (irq_ptr);qdio_shutdown_irq (irq_ptr);mutex_unlock (&irq_ptr->setup_mutex);return rc;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 140/477 s390/qdio: put thinint indicator after early error
In reply to Greg Kroah-HartmanFrom: Julian Wiedmann <[email protected]>
[ Upstream commit 75e82bec6b2622c6f455b7a543fb5476a5d0eed7 ]
qdio_establish() calls qdio_setup_thinint() via qdio_setup_irq(). If the subsequent qdio_establish_thinint() fails, we miss to put the DSCI again. Thus the DSCI isn't available for re-use. Given enough of such errors, we could end up with having only the shared DSCI available.
Merge qdio_setup_thinint() into qdio_establish_thinint(), and deal with such an error internally.
--- drivers/s390/cio/qdio.h | 1 - drivers/s390/cio/qdio_setup.c | 1 - drivers/s390/cio/qdio_thinint.c | 14 ++++++++------ 3 files changed, 8 insertions(+), 8 deletions(-)
drivers/s390/cio/qdio.h +0 -1
@@ -364,7 +364,6 @@ static inline int multicast_outbound(struct qdio_q *q)extern u64 last_ai_time;/* prototypes for thin interrupt */ -void qdio_setup_thinint (struct qdio_irq *irq_ptr);int qdio_establish_thinint (struct qdio_irq *irq_ptr);void qdio_shutdown_thinint (struct qdio_irq *irq_ptr);void tiqdio_add_device (struct qdio_irq *irq_ptr);
drivers/s390/cio/qdio_setup.c +0 -1
@@ -480,7 +480,6 @@ int qdio_setup_irq(struct qdio_irq *irq_ptr, struct qdio_initialize *init_data) }setup_qib (irq_ptr, init_data); -qdio_setup_thinint (irq_ptr); set_impl_params(irq_ptr, init_data->qib_param_field_format, init_data->qib_param_field, init_data->input_slib_elements,
drivers/s390/cio/qdio_thinint.c +8 -6
@@ -227,17 +227,19 @@ int __init tiqdio_register_thinints(void)int qdio_establish_thinint (struct qdio_irq *irq_ptr) { +int rc; +if (!is_thinint_irq (irq_ptr))return 0 ; -return set_subchannel_ind (irq_ptr,0 ); -} -void qdio_setup_thinint (struct qdio_irq *irq_ptr) -{ -if (!is_thinint_irq (irq_ptr)) -return ; irq_ptr->dsci =get_indicator ();DBF_HEX (&irq_ptr->dsci,sizeof (void *)); + + rc =set_subchannel_ind (irq_ptr,0 ); +if (rc) +put_indicator (irq_ptr->dsci); + +return rc; }void qdio_shutdown_thinint (struct qdio_irq *irq_ptr)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 141/477 staging: wfx: fix overflow in frame counters
In reply to Greg Kroah-HartmanFrom: Jérôme Pouiller <[email protected]>
[ Upstream commit 87066173e34b0ca5d041d5519e6bb030b1958184 ]
It has been reported that trying to send small packets of data could produce a "inconsistent notification" warning.
It seems that in some circumstances, the number of frame queued in the driver could greatly increase and exceed UCHAR_MAX. So the field "buffered" from struct sta_priv can overflow.
Just increase the size of "bueffered" to fix the problem.
--- drivers/staging/wfx/sta.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/staging/wfx/sta.h +1 -1
@@ -37,7 +37,7 @@ struct wfx_grp_addr_table {struct wfx_sta_priv {int link_id;int vif_id; -u8 buffered[IEEE80211_NUM_TIDS ]; +int buffered[IEEE80211_NUM_TIDS ];// Ensure atomicity of "buffered" and calls to ieee80211_sta_set_buffered() spinlock_t lock; };
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 142/477 staging: wfx: fix double init of tx_policy_upload_work
In reply to Greg Kroah-HartmanFrom: Jérôme Pouiller <[email protected]>
[ Upstream commit 6ae0878b4800c7042d35c0fb4c6baabb62621ecc ]
The work_struct tx_policy_upload_work was initialized twice.
--- drivers/staging/wfx/sta.c | 1 - 1 file changed, 1 deletion(-)
drivers/staging/wfx/sta.c +0 -1
@@ -1049,7 +1049,6 @@ int wfx_add_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif)init_completion (&wvif->scan_complete);INIT_WORK (&wvif->scan_work, wfx_hw_scan_work); -INIT_WORK (&wvif->tx_policy_upload_work, wfx_tx_policy_upload_work);mutex_unlock (&wdev->conf_mutex);hif_set_macaddr (wvif, vif->addr);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 143/477 tty: hvc: Fix data abort due to race in hvc_open
In reply to Greg Kroah-HartmanFrom: Raghavendra Rao Ananta <[email protected]>
[ Upstream commit e2bd1dcbe1aa34ff5570b3427c530e4332ecf0fe ]
Potentially, hvc_open() can be called in parallel when two tasks calls open() on /dev/hvcX. In such a scenario, if the hp->ops->notifier_add() callback in the function fails, where it sets the tty->driver_data to NULL, the parallel hvc_open() can see this NULL and cause a memory abort. Hence, serialize hvc_open and check if tty->private_data is NULL before proceeding ahead.
The issue can be easily reproduced by launching two tasks simultaneously that does nothing but open() and close() on /dev/hvcX.
For example:
$ ./simple_open_close /dev/hvc0 & ./simple_open_close /dev/hvc0 &
--- drivers/tty/hvc/hvc_console.c | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-)
drivers/tty/hvc/hvc_console.c +14 -2
@@ -75,6 +75,8 @@ static LIST_HEAD(hvc_structs);*/ static DEFINE_MUTEX (hvc_structs_mutex); +/* Mutex to serialize hvc_open */ +static DEFINE_MUTEX (hvc_open_mutex);/* * This value is used to assign a tty->index value to a hvc_struct based * upon order of exposure via hvc_probe(), when we can not match it to
@@ -346,16 +348,24 @@ static int hvc_install(struct tty_driver *driver, struct tty_struct *tty)*/ static int hvc_open (struct tty_struct *tty,struct file * filp) { -struct hvc_struct *hp = tty->driver_data; +struct hvc_struct *hp;unsigned long flags;int rc =0 ; +mutex_lock (&hvc_open_mutex); + + hp = tty->driver_data; +if (!hp) { + rc = -EIO ; + goto out; + } +spin_lock_irqsave (&hp->port.lock, flags);/* Check and then increment for fast path open. */ if (hp->port.count++ >0 ) {spin_unlock_irqrestore (&hp->port.lock, flags);hvc_kick (); -return 0 ; + goto out; }/* else count == 0 */ spin_unlock_irqrestore (&hp->port.lock, flags);
@@ -383,6 +393,8 @@ static int hvc_open(struct tty_struct *tty, struct file * filp)/* Force wakeup of the polling thread */ hvc_kick (); +out: +mutex_unlock (&hvc_open_mutex);return rc; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 144/477 slimbus: ngd: get drvdata from correct device
In reply to Greg Kroah-HartmanFrom: Srinivas Kandagatla <[email protected]>
[ Upstream commit b58c663059b484f7ff547d076a34cf6d7a302e56 ]
Get drvdata directly from parent instead of ngd dev, as ngd dev can probe defer and previously set drvdata will become null.
--- drivers/slimbus/qcom-ngd-ctrl.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/slimbus/qcom-ngd-ctrl.c +2 -2
@@ -1361,7 +1361,6 @@ static int of_qcom_slim_ngd_register(struct device *parent, ngd->pdev->driver_override =QCOM_SLIM_NGD_DRV_NAME ; ngd->pdev->dev.of_node = node; ctrl->ngd = ngd; -platform_set_drvdata (ngd->pdev, ctrl);platform_device_add (ngd->pdev); ngd->base = ctrl->base + ngd->id * data->offset +
@@ -1376,12 +1375,13 @@ static int of_qcom_slim_ngd_register(struct device *parent,static int qcom_slim_ngd_probe (struct platform_device *pdev) { -struct qcom_slim_ngd_ctrl *ctrl =platform_get_drvdata (pdev);struct device *dev = &pdev->dev; +struct qcom_slim_ngd_ctrl *ctrl =dev_get_drvdata (dev->parent);int ret; ctrl->ctrl.dev = dev; +platform_set_drvdata (pdev, ctrl);pm_runtime_use_autosuspend (dev);pm_runtime_set_autosuspend_delay (dev,QCOM_SLIM_NGD_AUTOSUSPEND );pm_runtime_set_suspended (dev);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 145/477 gpio: mlxbf2: fix return value check in mlxbf2_gpio_get_lock_res()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit 66d8ad67aab3bc6f55e7de81565cd0d4875bd851 ]
In case of error, the function devm_ioremap() returns NULL pointer not ERR_PTR(). The IS_ERR() test in the return value check should be replaced with NULL test.
--- drivers/gpio/gpio-mlxbf2.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/gpio/gpio-mlxbf2.c +2 -2
@@ -110,8 +110,8 @@ static int mlxbf2_gpio_get_lock_res(struct platform_device *pdev) } yu_arm_gpio_lock_param.io =devm_ioremap (dev, res->start, size); -if (IS_ERR (yu_arm_gpio_lock_param.io)) - ret =PTR_ERR (yu_arm_gpio_lock_param.io); +if (!yu_arm_gpio_lock_param.io) + ret = -ENOMEM ; exit:mutex_unlock (yu_arm_gpio_lock_param.lock);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 146/477 of: property: Fix create device links for all child-supplier dependencies
In reply to Greg Kroah-HartmanFrom: Nicolas Saenz Julienne <[email protected]>
[ Upstream commit ed3655729182a59b9bef1b564c6fc2dcbbbe954e ]
Upon adding a new device from a DT node, we scan its properties and its children's properties in order to create a consumer/supplier relationship between the device and the property provider.
That said, it's possible for some of the node's children to be disabled, which will create links that'll never be fulfilled.
To get around this, use the for_each_available_child_of_node() function instead of for_each_available_node() when iterating over the node's children.
--- drivers/of/property.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/of/property.c +1 -1
@@ -1296,7 +1296,7 @@ static int of_link_to_suppliers(struct device *dev,if (of_link_property (dev, con_np, p->name)) ret = -ENODEV ; -for_each_child_of_node (con_np, child) +for_each_available_child_of_node (con_np, child)if (of_link_to_suppliers (dev, child) && !ret) ret = -EAGAIN ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 147/477 of: property: Do not link to disabled devices
In reply to Greg Kroah-HartmanFrom: Nicolas Saenz Julienne <[email protected]>
[ Upstream commit 7456427af9def0fec5508dd8b861556038ee96a8 ]
When creating a consumer/supplier relationship between two devices, make sure the supplier node is actually active. Otherwise this will create a link relationship that will never be fulfilled. This, in the worst case scenario, will hang the system during boot.
Note that, in practice, the fact that a device-tree represented consumer/supplier relationship isn't fulfilled will not prevent devices from successfully probing.
--- drivers/of/property.c | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-)
drivers/of/property.c +13 -1
@@ -1045,8 +1045,20 @@ static int of_link_to_phandle(struct device *dev, struct device_node *sup_np,* Find the device node that contains the supplier phandle. It may be * @sup_np or it may be an ancestor of @sup_np. */ -while (sup_np && !of_find_property (sup_np,"compatible" ,NULL )) +while (sup_np) { + +/* Don't allow linking to a disabled supplier */ +if (!of_device_is_available (sup_np)) { +of_node_put (sup_np); + sup_np =NULL ; + } + +if (of_find_property (sup_np,"compatible" ,NULL )) +break ; + sup_np =of_get_next_parent (sup_np); + } +if (!sup_np) {dev_dbg (dev,"Not linking to %pOFP - No device\n" , tmp_np);return -ENODEV ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 148/477 clk: meson: meson8b: Fix the first parent of vid_pll_in_sel
In reply to Greg Kroah-HartmanFrom: Martin Blumenstingl <[email protected]>
[ Upstream commit da1978ac3d6cf278dedf5edbf350445a0fff2f08 ]
Use hdmi_pll_lvds_out as parent of the vid_pll_in_sel clock. It's not easy to see that the vendor kernel does the same, but it actually does. meson_clk_pll_ops in mainline still cannot fully recalculate all rates from the HDMI PLL registers because some register bits (at the time of writing it's unknown which bits are used for this) double the HDMI PLL output rate (compared to simply considering M, N and FRAC) for some (but not all) PLL settings.
Update the vid_pll_in_sel parent so our clock calculation works for simple clock settings like the CVBS output (where no rate doubling is going on). The PLL ops need to be fixed later on for more complex clock settings (all HDMI rates).
--- drivers/clk/meson/meson8b.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/clk/meson/meson8b.c +1 -1
@@ -1077,7 +1077,7 @@ static struct clk_regmap meson8b_vid_pll_in_sel = {* Meson8m2: vid2_pll */ .parent_hws = (const struct clk_hw *[]) { - &meson8b_hdmi_pll_dco.hw + &meson8b_hdmi_pll_lvds_out.hw }, .num_parents = 1, .flags = CLK_SET_RATE_PARENT,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 149/477 clk: meson: meson8b: Fix the polarity of the RESET_N lines
In reply to Greg Kroah-HartmanFrom: Martin Blumenstingl <[email protected]>
[ Upstream commit 0d3051c790ed2ef6bd91b92b07220313f06b95b3 ]
CLKC_RESET_VID_DIVIDER_CNTL_RESET_N_POST and CLKC_RESET_VID_DIVIDER_CNTL_RESET_N_PRE are active low. This means:
- asserting them requires setting the register value to 0
- de-asserting them requires setting the register value to 1
Set the register value accordingly for these two reset lines by setting the inverted the register value compared to all other reset lines.
--- drivers/clk/meson/meson8b.c | 79 ++++++++++++++++++++++++++----------- 1 file changed, 56 insertions(+), 23 deletions(-)
drivers/clk/meson/meson8b.c +56 -23
@@ -3506,54 +3506,87 @@ static struct clk_regmap *const meson8b_clk_regmaps[] = {static const struct meson8b_clk_reset_line {u32 reg;u8 bit_idx; +bool active_low; } meson8b_clk_reset_bits[] = { [CLKC_RESET_L2_CACHE_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =30 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =30 , + .active_low = false, }, [CLKC_RESET_AXI_64_TO_128_BRIDGE_A5_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =29 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =29 , + .active_low = false, }, [CLKC_RESET_SCU_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =28 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =28 , + .active_low = false, }, [CLKC_RESET_CPU3_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =27 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =27 , + .active_low = false, }, [CLKC_RESET_CPU2_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =26 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =26 , + .active_low = false, }, [CLKC_RESET_CPU1_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =25 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =25 , + .active_low = false, }, [CLKC_RESET_CPU0_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =24 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =24 , + .active_low = false, }, [CLKC_RESET_A5_GLOBAL_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =18 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =18 , + .active_low = false, }, [CLKC_RESET_A5_AXI_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =17 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =17 , + .active_low = false, }, [CLKC_RESET_A5_ABP_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL0 , .bit_idx =16 + .reg =HHI_SYS_CPU_CLK_CNTL0 , + .bit_idx =16 , + .active_low = false, }, [CLKC_RESET_AXI_64_TO_128_BRIDGE_MMC_SOFT_RESET ] = { - .reg =HHI_SYS_CPU_CLK_CNTL1 , .bit_idx =30 + .reg =HHI_SYS_CPU_CLK_CNTL1 , + .bit_idx =30 , + .active_low = false, }, [CLKC_RESET_VID_CLK_CNTL_SOFT_RESET ] = { - .reg =HHI_VID_CLK_CNTL , .bit_idx =15 + .reg =HHI_VID_CLK_CNTL , + .bit_idx =15 , + .active_low = false, }, [CLKC_RESET_VID_DIVIDER_CNTL_SOFT_RESET_POST ] = { - .reg =HHI_VID_DIVIDER_CNTL , .bit_idx =7 + .reg =HHI_VID_DIVIDER_CNTL , + .bit_idx =7 , + .active_low = false, }, [CLKC_RESET_VID_DIVIDER_CNTL_SOFT_RESET_PRE ] = { - .reg =HHI_VID_DIVIDER_CNTL , .bit_idx =3 + .reg =HHI_VID_DIVIDER_CNTL , + .bit_idx =3 , + .active_low = false, }, [CLKC_RESET_VID_DIVIDER_CNTL_RESET_N_POST ] = { - .reg =HHI_VID_DIVIDER_CNTL , .bit_idx =1 + .reg =HHI_VID_DIVIDER_CNTL , + .bit_idx =1 , + .active_low = true, }, [CLKC_RESET_VID_DIVIDER_CNTL_RESET_N_PRE ] = { - .reg =HHI_VID_DIVIDER_CNTL , .bit_idx =0 + .reg =HHI_VID_DIVIDER_CNTL , + .bit_idx =0 , + .active_low = true, }, };
@@ -3562,22 +3595,22 @@ static int meson8b_clk_reset_update(struct reset_controller_dev *rcdev, {struct meson8b_clk_reset *meson8b_clk_reset = container_of(rcdev, struct meson8b_clk_reset, reset); -unsigned long flags;const struct meson8b_clk_reset_line *reset; +unsigned int value =0 ; +unsigned long flags;if (id >=ARRAY_SIZE (meson8b_clk_reset_bits))return -EINVAL ; reset = &meson8b_clk_reset_bits[id]; +if (assert != reset->active_low) + value =BIT (reset->bit_idx); +spin_lock_irqsave (&meson_clk_lock, flags); -if (assert) -regmap_update_bits (meson8b_clk_reset->regmap, reset->reg, -BIT (reset->bit_idx),BIT (reset->bit_idx)); -else -regmap_update_bits (meson8b_clk_reset->regmap, reset->reg, -BIT (reset->bit_idx),0 ); +regmap_update_bits (meson8b_clk_reset->regmap, reset->reg, +BIT (reset->bit_idx), value);spin_unlock_irqrestore (&meson_clk_lock, flags);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 150/477 clk: meson: meson8b: Fix the vclk_div{1, 2, 4, 6, 12}_en gate bits
In reply to Greg Kroah-HartmanFrom: Martin Blumenstingl <[email protected]>
[ Upstream commit 8bb629cfb28f4dad9d47f69249366e50ae5edc25 ]
The DIV{1,2,4,6,12}_EN bits are actually located in HHI_VID_CLK_CNTL register:
- HHI_VID_CLK_CNTL[0] = DIV1_EN
- HHI_VID_CLK_CNTL[1] = DIV2_EN
- HHI_VID_CLK_CNTL[2] = DIV4_EN
- HHI_VID_CLK_CNTL[3] = DIV6_EN
- HHI_VID_CLK_CNTL[4] = DIV12_EN
Update the bits accordingly so we will enable the bits in the correct register once we switch these clocks to be mutable.
--- drivers/clk/meson/meson8b.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-)
drivers/clk/meson/meson8b.c +5 -5
@@ -1213,7 +1213,7 @@ static struct clk_regmap meson8b_vclk_in_en = {static struct clk_regmap meson8b_vclk_div1_gate = { .data = &(struct clk_regmap_gate_data ){ - .offset =HHI_VID_CLK_DIV , + .offset =HHI_VID_CLK_CNTL , .bit_idx =0 , }, .hw.init = &(struct clk_init_data ){
@@ -1243,7 +1243,7 @@ static struct clk_fixed_factor meson8b_vclk_div2_div = {static struct clk_regmap meson8b_vclk_div2_div_gate = { .data = &(struct clk_regmap_gate_data ){ - .offset =HHI_VID_CLK_DIV , + .offset =HHI_VID_CLK_CNTL , .bit_idx =1 , }, .hw.init = &(struct clk_init_data ){
@@ -1273,7 +1273,7 @@ static struct clk_fixed_factor meson8b_vclk_div4_div = {static struct clk_regmap meson8b_vclk_div4_div_gate = { .data = &(struct clk_regmap_gate_data ){ - .offset =HHI_VID_CLK_DIV , + .offset =HHI_VID_CLK_CNTL , .bit_idx =2 , }, .hw.init = &(struct clk_init_data ){
@@ -1303,7 +1303,7 @@ static struct clk_fixed_factor meson8b_vclk_div6_div = {static struct clk_regmap meson8b_vclk_div6_div_gate = { .data = &(struct clk_regmap_gate_data ){ - .offset =HHI_VID_CLK_DIV , + .offset =HHI_VID_CLK_CNTL , .bit_idx =3 , }, .hw.init = &(struct clk_init_data ){
@@ -1333,7 +1333,7 @@ static struct clk_fixed_factor meson8b_vclk_div12_div = {static struct clk_regmap meson8b_vclk_div12_div_gate = { .data = &(struct clk_regmap_gate_data ){ - .offset =HHI_VID_CLK_DIV , + .offset =HHI_VID_CLK_CNTL , .bit_idx =4 , }, .hw.init = &(struct clk_init_data ){
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 151/477 gpio: pca953x: fix handling of automatic address incrementing
In reply to Greg Kroah-HartmanFrom: Uwe Kleine-König <[email protected]>
[ Upstream commit bcf41dc480b179bfb669a232080a2e26dc7294b4 ]
Some of the chips supported by the pca953x driver need the most significant bit in the address word set to automatically increment the address pointer on subsequent reads and writes (example: PCA9505). With this bit unset the same register is read multiple times on a multi-byte read sequence. Other chips must not have this bit set and autoincrement always (example: PCA9555).
Up to now this AI bit was interpreted to be part of the address, which resulted in inconsistent regmap caching when a register was written with AI set and then read without it. This happened for the PCA9505 in pca953x_gpio_set_multiple() where pca953x_read_regs() bulk read from the cache for registers 0x8-0xc and then wrote to registers 0x88-0x8c. (Side
note: reading 5 values from offset 0x8 yiels OP0 5 times because AI must be set to get OP0-OP4, which is another bug that is resolved here as a by-product.) The same problem happens when calls to gpio_set_value() and gpio_set_array_value() were mixed.
With this patch the AI bit is always set for chips that support it. This works as there are no code locations that make use of the behaviour with AI unset (for the chips that support it).
Note that the call to pca953x_setup_gpio() had to be done a bit earlier to make the NBANK macro work.
The history of this bug is a bit complicated. Commit b32cecb46bdc ("gpio: pca953x: Extract the register address mangling to single function") changed which chips and functions are affected. Commit 3b00691cc46a ("gpio: pca953x: hack to fix 24 bit gpio expanders") used some duct tape to make the driver at least appear to work. Commit 49427232764d ("gpio: pca953x: Perform basic regmap conversion") introduced the caching. Commit b4818afeacbd ("gpio: pca953x: Add set_multiple to allow multiple bits to be set in one write.") introduced the .set_multiple() callback which didn't work for chips that need the AI bit which was fixed later for some chips in 8958262af3fb ("gpio:
pca953x: Repair multi-byte IO address increment on PCA9575"). So I'm sorry, I don't know which commit I should pick for a Fixes: line.
--- drivers/gpio/gpio-pca953x.c | 44 +++++++++++++++++++++++-------------- 1 file changed, 28 insertions(+), 16 deletions(-)
drivers/gpio/gpio-pca953x.c +28 -16
@@ -307,8 +307,22 @@ static const struct regmap_config pca953x_i2c_regmap = { .volatile_reg = pca953x_volatile_register, .cache_type = REGCACHE_RBTREE, -/* REVISIT: should be 0x7f but some 24 bit chips use REG_ADDR_AI */ - .max_register = 0xff, + .max_register = 0x7f, +}; + +static const struct regmap_config pca953x_ai_i2c_regmap = { + .reg_bits =8 , + .val_bits =8 , + + .read_flag_mask =REG_ADDR_AI , + .write_flag_mask =REG_ADDR_AI , + + .readable_reg = pca953x_readable_register, + .writeable_reg = pca953x_writeable_register, + .volatile_reg = pca953x_volatile_register, + + .cache_type =REGCACHE_RBTREE , + .max_register =0x7f , }; static u8 pca953x_recalc_addr(struct pca953x_chip *chip, int reg, int off,
@@ -319,18 +333,6 @@ static u8 pca953x_recalc_addr(struct pca953x_chip *chip, int reg, int off,int pinctrl = (reg &PCAL_PINCTRL_MASK ) <<1 ;u8 regaddr = pinctrl | addr | (off /BANK_SZ ); -/* Single byte read doesn't need AI bit set. */ -if (!addrinc) -return regaddr; - -/* Chips with 24 and more GPIOs always support Auto Increment */ -if (write &&NBANK (chip) >2 ) - regaddr |=REG_ADDR_AI ; - -/* PCA9575 needs address-increment on multi-byte writes */ -if (PCA_CHIP_TYPE (chip->driver_data) ==PCA957X_TYPE ) - regaddr |=REG_ADDR_AI ; -return regaddr; }
@@ -863,6 +865,7 @@ static int pca953x_probe(struct i2c_client *client,int ret;u32 invert =0 ;struct regulator *reg; +const struct regmap_config *regmap_config; chip =devm_kzalloc (&client->dev,sizeof (*chip),GFP_KERNEL );if (chip ==NULL )
@@ -925,7 +928,17 @@ static int pca953x_probe(struct i2c_client *client,i2c_set_clientdata (client, chip); - chip->regmap =devm_regmap_init_i2c (client, &pca953x_i2c_regmap); +pca953x_setup_gpio (chip, chip->driver_data &PCA_GPIO_MASK ); + +if (NBANK (chip) >2 ||PCA_CHIP_TYPE (chip->driver_data) ==PCA957X_TYPE ) { +dev_info (&client->dev,"using AI\n" ); + regmap_config = &pca953x_ai_i2c_regmap; + }else { +dev_info (&client->dev,"using no AI\n" ); + regmap_config = &pca953x_i2c_regmap; + } + + chip->regmap =devm_regmap_init_i2c (client, regmap_config);if (IS_ERR (chip->regmap)) { ret =PTR_ERR (chip->regmap); goto err_exit;
@@ -956,7 +969,6 @@ static int pca953x_probe(struct i2c_client *client,/* initialize cached registers from their original values. * we can't share this chip with another i2c master. */ -pca953x_setup_gpio (chip, chip->driver_data &PCA_GPIO_MASK );if (PCA_CHIP_TYPE (chip->driver_data) ==PCA953X_TYPE ) { chip->regs = &pca953x_regs;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 152/477 ASoC: component: suppress uninitialized-variable warning
In reply to Greg Kroah-HartmanFrom: Arnd Bergmann <[email protected]>
[ Upstream commit be16a0f0dc8fab8e25d9cdbeb4f8f28afc9186d2 ]
Old versions of gcc (tested on gcc-4.8) produce a warning for correct code:
sound/soc/soc-compress.c: In function 'soc_compr_open':sound/soc/soc-compress.c:75:28: error: 'component' is used uninitialized in this function [-Werror=uninitialized]
struct snd_soc_component *component, *save = NULL;
Change the for_each_rtd_components() macro to ensure 'component' gets initialized to a value the compiler does not complain about.
--- include/sound/soc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
include/sound/soc.h +1 -1
@@ -1177,7 +1177,7 @@ struct snd_soc_pcm_runtime {#define asoc_rtd_to_codec (rtd, n) (rtd)->dais[n + (rtd)->num_cpus]#define for_each_rtd_components (rtd, i, component) \ - for ((i) = 0; \ + for ((i) = 0, component = NULL; \ ((i) < rtd->num_components) && ((component) = rtd->components[i]);\ (i)++)#define for_each_rtd_cpu_dais (rtd, i, dai) \
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 153/477 thermal/drivers/ti-soc-thermal: Avoid dereferencing ERR_PTR
In reply to Greg Kroah-HartmanFrom: Sudip Mukherjee <[email protected]>
[ Upstream commit 7440f518dad9d861d76c64956641eeddd3586f75 ]
On error the function ti_bandgap_get_sensor_data() returns the error code in ERR_PTR() but we only checked if the return value is NULL or not. And, so we can dereference an error code inside ERR_PTR. While at it, convert a check to IS_ERR_OR_NULL.
--- drivers/thermal/ti-soc-thermal/ti-thermal-common.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
drivers/thermal/ti-soc-thermal/ti-thermal-common.c +3 -3
@@ -169,7 +169,7 @@ int ti_thermal_expose_sensor(struct ti_bandgap *bgp, int id, data =ti_bandgap_get_sensor_data (bgp, id); -if (!data ||IS_ERR (data)) +if (!IS_ERR_OR_NULL (data)) data =ti_thermal_build_data (bgp, id);if (!data)
@@ -196,7 +196,7 @@ int ti_thermal_remove_sensor(struct ti_bandgap *bgp, int id) data =ti_bandgap_get_sensor_data (bgp, id); -if (data && data->ti_thermal) { +if (!IS_ERR_OR_NULL (data) && data->ti_thermal) {if (data->our_zone)thermal_zone_device_unregister (data->ti_thermal); }
@@ -262,7 +262,7 @@ int ti_thermal_unregister_cpu_cooling(struct ti_bandgap *bgp, int id) data =ti_bandgap_get_sensor_data (bgp, id); -if (data) { +if (!IS_ERR_OR_NULL (data)) {cpufreq_cooling_unregister (data->cool_dev);if (data->policy)cpufreq_cpu_put (data->policy);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 154/477 ASoC: rt5682: fix I2C/Soundwire dependencies
In reply to Greg Kroah-HartmanFrom: Arnd Bergmann <[email protected]>
[ Upstream commit fd443a20c2f0950f3c31765a08f7dd49b3bc69cb ]
If one of the two is a loadable module, the combined driver must not be built-in:
aarch64-linux-ld: sound/soc/codecs/rt5682.o: in function `rt5682_sdw_hw_free':
rt5682.c:(.text+0xb34): undefined reference to `sdw_stream_remove_slave'
aarch64-linux-ld: sound/soc/codecs/rt5682.o: in function `rt5682_sdw_hw_params':
rt5682.c:(.text+0xe78): undefined reference to `sdw_stream_add_slave'
In particular, the soundwire driver must not be built-in if CONFIG_I2C=m.
--- sound/soc/codecs/Kconfig | 3 +++ 1 file changed, 3 insertions(+)
sound/soc/codecs/Kconfig +3 -0
@@ -1136,10 +1136,13 @@ config SND_SOC_RT5677_SPI config SND_SOC_RT5682 tristate depends on I2C || SOUNDWIRE + depends on SOUNDWIRE || !SOUNDWIRE + depends on I2C || !I2C config SND_SOC_RT5682_SDW tristate "Realtek RT5682 Codec - SDW" depends on SOUNDWIRE + depends on I2C || !I2C select SND_SOC_RT5682 select REGMAP_SOUNDWIRE
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 155/477 arm64: dts: meson-g12b-ugoos-am6: fix board compatible
In reply to Greg Kroah-HartmanFrom: Neil Armstrong <[email protected]>
[ Upstream commit 5c28dcbb3a1be167c07784b5f710ec602a57bea2 ]
Add missing amlogic,s922x in the board compatible list.
It fixes:meson-g12b-ugoos-am6.dt.yaml: /: compatible: ['ugoos,am6', 'amlogic,g12b'] is not valid under any of the given schemas
--- arch/arm64/boot/dts/amlogic/meson-g12b-ugoos-am6.dts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/arm64/boot/dts/amlogic/meson-g12b-ugoos-am6.dts +1 -1
@@ -14,7 +14,7 @@ #include <dt-bindings/sound/meson-g12a-tohdmitx.h> / { - compatible = "ugoos,am6", "amlogic,g12b"; + compatible = "ugoos,am6", "amlogic,s922x", "amlogic,g12b"; model = "Ugoos AM6"; aliases {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 156/477 arm64: dts: meson: fix leds subnodes name
In reply to Greg Kroah-HartmanFrom: Neil Armstrong <[email protected]>
[ Upstream commit 08dc0e5dd9aabd52cff9e94febe6b282d29deca4 ]
Fix the leds subnode names to match (^led-[0-9a-f]$|led)
It fixes:meson-g12b-a311d-khadas-vim3.dt.yaml: leds: 'red', 'white' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-g12b-s922x-khadas-vim3.dt.yaml: leds: 'red', 'white' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-g12b-odroid-n2.dt.yaml: leds: 'blue' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-nanopi-k2.dt.yaml: leds: 'stat' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-nexbox-a95x.dt.yaml: leds: 'blue' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-odroidc2.dt.yaml: leds: 'blue' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-vega-s95-pro.dt.yaml: leds: 'blue' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-vega-s95-meta.dt.yaml: leds: 'blue' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-vega-s95-telos.dt.yaml: leds: 'blue' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-wetek-hub.dt.yaml: leds: 'system' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxbb-wetek-play2.dt.yaml: leds: 'ethernet', 'system', 'wifi' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxl-s905x-libretech-cc.dt.yaml: leds: 'blue', 'system' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxl-s905d-libretech-pc.dt.yaml: leds: 'blue', 'green' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxm-rbox-pro.dt.yaml: leds: 'blue', 'red' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-gxm-s912-libretech-pc.dt.yaml: leds: 'blue', 'green' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-sm1-sei610.dt.yaml: leds: 'bluetooth' does not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+' meson-sm1-khadas-vim3l.dt.yaml: leds: 'red', 'white' do not match any of the regexes: '(^led-[0-9a-f]$|led)', 'pinctrl-[0-9]+'
--- arch/arm64/boot/dts/amlogic/meson-gx-libretech-pc.dtsi | 4 ++-- arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 2 +- arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts | 2 +- arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 2 +- arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi | 2 +- arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts | 4 ++-- arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi | 2 +- arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 4 ++-- arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts | 4 ++-- arch/arm64/boot/dts/amlogic/meson-khadas-vim3.dtsi | 4 ++-- arch/arm64/boot/dts/amlogic/meson-sm1-sei610.dts | 2 +- 11 files changed, 16 insertions(+), 16 deletions(-)
arch/arm64/boot/dts/amlogic/meson-gx-libretech-pc.dtsi +2 -2
@@ -96,14 +96,14 @@ leds { compatible = "gpio-leds"; - green { + led-green { color = <LED_COLOR_ID_GREEN>; function = LED_FUNCTION_DISK_ACTIVITY; gpios = <&gpio_ao GPIOAO_9 GPIO_ACTIVE_HIGH>; linux,default-trigger = "disk-activity"; }; - blue { + led-blue { color = <LED_COLOR_ID_BLUE>; function = LED_FUNCTION_STATUS; gpios = <&gpio GPIODV_28 GPIO_ACTIVE_HIGH>;
arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts +1 -1
@@ -29,7 +29,7 @@ leds { compatible = "gpio-leds"; - stat { + led-stat { label = "nanopi-k2:blue:stat"; gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_HIGH>; default-state = "on";
arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts +1 -1
@@ -31,7 +31,7 @@ leds { compatible = "gpio-leds"; - blue { + led-blue { label = "a95x:system-status"; gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_LOW>; linux,default-trigger = "heartbeat";
arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +1 -1
@@ -49,7 +49,7 @@ leds { compatible = "gpio-leds"; - blue { + led-blue { label = "c2:blue:alive"; gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_LOW>; linux,default-trigger = "heartbeat";
arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi +1 -1
@@ -20,7 +20,7 @@ leds { compatible = "gpio-leds"; - blue { + led-blue { label = "vega-s95:blue:on"; gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_HIGH>; default-state = "on";
arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts +2 -2
@@ -14,13 +14,13 @@ model = "WeTek Play 2"; leds { - wifi { + led-wifi { label = "wetek-play:wifi-status"; gpios = <&gpio GPIODV_26 GPIO_ACTIVE_HIGH>; default-state = "off"; }; - ethernet { + led-ethernet { label = "wetek-play:ethernet-status"; gpios = <&gpio GPIODV_27 GPIO_ACTIVE_HIGH>; default-state = "off";
arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi +1 -1
@@ -25,7 +25,7 @@ leds { compatible = "gpio-leds"; - system { + led-system { label = "wetek-play:system-status"; gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_HIGH>; default-state = "on";
arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +2 -2
@@ -54,14 +54,14 @@ leds { compatible = "gpio-leds"; - system { + led-system { label = "librecomputer:system-status"; gpios = <&gpio GPIODV_24 GPIO_ACTIVE_HIGH>; default-state = "on"; panic-indicator; }; - blue { + led-blue { label = "librecomputer:blue"; gpios = <&gpio_ao GPIOAO_2 GPIO_ACTIVE_HIGH>; linux,default-trigger = "heartbeat";
arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts +2 -2
@@ -36,13 +36,13 @@ leds { compatible = "gpio-leds"; - blue { + led-blue { label = "rbox-pro:blue:on"; gpios = <&gpio_ao GPIOAO_9 GPIO_ACTIVE_HIGH>; default-state = "on"; }; - red { + led-red { label = "rbox-pro:red:standby"; gpios = <&gpio GPIODV_28 GPIO_ACTIVE_HIGH>; default-state = "off";
arch/arm64/boot/dts/amlogic/meson-khadas-vim3.dtsi +2 -2
@@ -39,13 +39,13 @@ leds { compatible = "gpio-leds"; - white { + led-white { label = "vim3:white:sys"; gpios = <&gpio_ao GPIOAO_4 GPIO_ACTIVE_LOW>; linux,default-trigger = "heartbeat"; }; - red { + led-red { label = "vim3:red"; gpios = <&gpio_expander 5 GPIO_ACTIVE_LOW>; };
arch/arm64/boot/dts/amlogic/meson-sm1-sei610.dts +1 -1
@@ -104,7 +104,7 @@ leds { compatible = "gpio-leds"; - bluetooth { + led-bluetooth { label = "sei610:blue:bt"; gpios = <&gpio GPIOC_7 (GPIO_ACTIVE_LOW | GPIO_OPEN_DRAIN)>; default-state = "off";
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 157/477 ASoC: SOF: Update correct LED status at the first time usage of update_mute_led()
In reply to Greg Kroah-HartmanFrom: Kai-Heng Feng <[email protected]>
[ Upstream commit 49c22696348d6e7c8a2ecfd7e60fddfe188ded82 ]
At the first time update_mute_led() gets called, if channels are already muted, the temp value equals to led_value as 0, skipping the following LED setting.
So set led_value to -1 as an uninitialized state, to update the correct LED status at first time usage.
--- sound/soc/sof/control.c | 4 ++-- sound/soc/sof/sof-audio.h | 2 +- sound/soc/sof/topology.c | 2 ++ 3 files changed, 5 insertions(+), 3 deletions(-)
sound/soc/sof/control.c +2 -2
@@ -19,8 +19,8 @@ static void update_mute_led(struct snd_sof_control *scontrol,struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol) { - unsigned int temp = 0; -unsigned int mask; + int temp = 0; +int mask;int i; mask =1U <<snd_ctl_get_ioffidx (kcontrol, &ucontrol->id);
sound/soc/sof/sof-audio.h +1 -1
@@ -56,7 +56,7 @@ struct snd_sof_pcm {struct snd_sof_led_control {unsigned int use_led;unsigned int direction; -unsigned int led_value; +int led_value; };/* ALSA SOF Kcontrol device */
sound/soc/sof/topology.c +2 -0
@@ -1203,6 +1203,8 @@ static int sof_control_load(struct snd_soc_component *scomp, int index,return ret; } + scontrol->led_ctl.led_value =-1 ; + dobj->private = scontrol;list_add (&scontrol->list, &sdev->kcontrol_list);return ret;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 158/477 clk: meson: meson8b: Dont rely on u-boot to init all GP_PLL registers
In reply to Greg Kroah-HartmanFrom: Martin Blumenstingl <[email protected]>
[ Upstream commit a29ae8600d50ece1856b062a39ed296b8b952259 ]
Not all u-boot versions initialize the HHI_GP_PLL_CNTL[2-5] registers. In that case all HHI_GPLL_PLL_CNTL[1-5] registers are 0x0 and when booting Linux the PLL fails to lock.
The initialization sequence from u-boot is:
- put the PLL into reset
- write 0x59C88000 to HHI_GP_PLL_CNTL2
- write 0xCA463823 to HHI_GP_PLL_CNTL3
- write 0x0286A027 to HHI_GP_PLL_CNTL4
- write 0x00003000 to HHI_GP_PLL_CNTL5
- set M, N, OD and the enable bit
- take the PLL out of reset
- check if it has locked
- disable the PLL
In Linux we already initialize M, N, OD, the enable and the reset bits. Also the HHI_GP_PLL_CNTL[2-5] registers with these magic values (the exact meaning is unknown) so the PLL can lock when the vendor u-boot did not initialize these registers yet.
--- drivers/clk/meson/meson8b.c | 9 +++++++++ drivers/clk/meson/meson8b.h | 4 ++++ 2 files changed, 13 insertions(+)
drivers/clk/meson/meson8b.c +9 -0
@@ -1918,6 +1918,13 @@ static struct clk_regmap meson8b_mali = { }, }; +static const struct reg_sequence meson8m2_gp_pll_init_regs[] = { + { .reg =HHI_GP_PLL_CNTL2 , .def =0x59c88000 }, + { .reg =HHI_GP_PLL_CNTL3 , .def =0xca463823 }, + { .reg =HHI_GP_PLL_CNTL4 , .def =0x0286a027 }, + { .reg =HHI_GP_PLL_CNTL5 , .def =0x00003000 }, +}; +static const struct pll_params_table meson8m2_gp_pll_params_table[] = {PLL_PARAMS (182 ,3 ), {/* sentinel */ },
@@ -1951,6 +1958,8 @@ static struct clk_regmap meson8m2_gp_pll_dco = { .width = 1, }, .table = meson8m2_gp_pll_params_table, + .init_regs = meson8m2_gp_pll_init_regs, + .init_count = ARRAY_SIZE(meson8m2_gp_pll_init_regs), }, .hw.init = &(struct clk_init_data ){ .name ="gp_pll_dco" ,
drivers/clk/meson/meson8b.h +4 -0
@@ -20,6 +20,10 @@* [0] http://dn.odroid.com/S805/Datasheet/S805_Datasheet%20V0.8%2020150126.pdf */ #define HHI_GP_PLL_CNTL 0x40/* 0x10 offset in data sheet */ +#define HHI_GP_PLL_CNTL2 0x44/* 0x11 offset in data sheet */ +#define HHI_GP_PLL_CNTL3 0x48/* 0x12 offset in data sheet */ +#define HHI_GP_PLL_CNTL4 0x4C/* 0x13 offset in data sheet */ +#define HHI_GP_PLL_CNTL5 0x50/* 0x14 offset in data sheet */ #define HHI_VIID_CLK_DIV 0x128/* 0x4a offset in data sheet */ #define HHI_VIID_CLK_CNTL 0x12c/* 0x4b offset in data sheet */ #define HHI_GCLK_MPEG0 0x140/* 0x50 offset in data sheet */
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 159/477 ASoC: max98373: reorder max98373_reset() in resume
In reply to Greg Kroah-HartmanFrom: Yong Zhi <[email protected]>
[ Upstream commit 1a446873d7dd3a450f685928ce7f1907bde4583d ]
During S3 test, the following error was observed:
[ 726.174237] i2c_designware i2c_designware.0: platform_pm_resume+0x0/0x3d returned 0 after 0 usecs [ 726.184187] max98373 i2c-MX98373:00: calling max98373_resume+0x0/0x30 [snd_soc_max98373] @ 12698, parent: i2c-11 [ 726.195589] max98373 i2c-MX98373:00: Reset command failed. (ret:-16)
When calling regmap_update_bits(), since map->reg_update_bits is NULL, _regmap_read() is entered with the following logic:
if (!map->cache_bypass) {
ret = regcache_read(map, reg, val);
if (ret == 0)
return 0;
}
if (map->cache_only)
return -EBUSY;regcache_read() hits -EINVAL because MAX98373_R2000_SW_RESET is volatile, as map->cache_only is set by codec suspend, thus -EBUSY is returned. Fix by moving max98373_reset() after cache_only set to false in max98373_resume().
--- sound/soc/codecs/max98373.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
sound/soc/codecs/max98373.c +1 -1
@@ -850,8 +850,8 @@ static int max98373_resume(struct device *dev) {struct max98373_priv *max98373 =dev_get_drvdata (dev); -max98373_reset (max98373, dev);regcache_cache_only (max98373->regmap, false); +max98373_reset (max98373, dev);regcache_sync (max98373->regmap);return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 160/477 soundwire: slave: dont init debugfs on device registration error
In reply to Greg Kroah-HartmanFrom: Pierre-Louis Bossart <[email protected]>
[ Upstream commit 8893ab5e8ee5d7c12e0fc1dca4a309475064473d ]
The error handling flow seems incorrect, there is no reason to try and add debugfs support if the device registration did not succeed. Return on error.
--- drivers/soundwire/slave.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/soundwire/slave.c +2 -0
@@ -68,6 +68,8 @@ static int sdw_slave_add(struct sdw_bus *bus,list_del (&slave->node);mutex_unlock (&bus->bus_lock);put_device (&slave->dev); + +return ret; }sdw_slave_debugfs_init (slave);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 161/477 ARM: dts: aspeed: ast2600: Set arch timer always-on
In reply to Greg Kroah-HartmanFrom: Eddie James <[email protected]>
[ Upstream commit c998f40f2ae6a48e93206e2c1ea0691479989611 ]
According to ASPEED, FTTMR010 is not intended to be used in the AST2600. The arch timer should be used, but Linux doesn't enable high-res timers without being assured that the arch timer is always on, so set that property in the devicetree.
The FTTMR010 device is described by set to disabled.
This fixes highres timer support for AST2600.
--- arch/arm/boot/dts/aspeed-g6.dtsi | 2 ++ 1 file changed, 2 insertions(+)
arch/arm/boot/dts/aspeed-g6.dtsi +2 -0
@@ -65,6 +65,7 @@ <GIC_PPI 10 (GIC_CPU_MASK_SIMPLE(2) | IRQ_TYPE_LEVEL_LOW)>; clocks = <&syscon ASPEED_CLK_HPLL>; arm,cpu-registers-not-fw-configured; + always-on; }; ahb {
@@ -368,6 +369,7 @@ <&gic GIC_SPI 23 IRQ_TYPE_LEVEL_HIGH>; clocks = <&syscon ASPEED_CLK_APB1>; clock-names = "PCLK"; + status = "disabled"; }; uart1: serial@1e783000 {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 162/477 ARM: dts: aspeed: Change KCS nodes to v2 binding
In reply to Greg Kroah-HartmanFrom: Andrew Jeffery <[email protected]>
[ Upstream commit fa4c8ec6feaa3237f5d44cb8c6d0aa0dff6e1bcc ]
Fixes the following warnings for both g5 and g6 SoCs:
arch/arm/boot/dts/aspeed-g5.dtsi:376.19-381.8: Warning
(unit_address_vs_reg): /ahb/apb/lpc@1e789000/lpc-bmc@0/kcs1@0: node
has a unit name, but no reg property--- .../dts/aspeed-bmc-facebook-tiogapass.dts | 4 ++-- arch/arm/boot/dts/aspeed-g5.dtsi | 24 +++++++++---------- arch/arm/boot/dts/aspeed-g6.dtsi | 23 +++++++++--------- 3 files changed, 26 insertions(+), 25 deletions(-)
arch/arm/boot/dts/aspeed-bmc-facebook-tiogapass.dts +2 -2
@@ -112,13 +112,13 @@ &kcs2 { // BMC KCS channel 2 status = "okay"; - kcs_addr = <0xca8>; + aspeed,lpc-io-reg = <0xca8>; }; &kcs3 { // BMC KCS channel 3 status = "okay"; - kcs_addr = <0xca2>; + aspeed,lpc-io-reg = <0xca2>; }; &mac0 {
arch/arm/boot/dts/aspeed-g5.dtsi +12 -12
@@ -426,22 +426,22 @@ #size-cells = <1>; ranges = <0x0 0x0 0x80>; - kcs1: kcs1@0 { - compatible = "aspeed,ast2500-kcs-bmc"; + kcs1: kcs@24 { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x24 0x1>, <0x30 0x1>, <0x3c 0x1>; interrupts = <8>; - kcs_chan = <1>; status = "disabled"; }; - kcs2: kcs2@0 { - compatible = "aspeed,ast2500-kcs-bmc"; + kcs2: kcs@28 { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x28 0x1>, <0x34 0x1>, <0x40 0x1>; interrupts = <8>; - kcs_chan = <2>; status = "disabled"; }; - kcs3: kcs3@0 { - compatible = "aspeed,ast2500-kcs-bmc"; + kcs3: kcs@2c { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x2c 0x1>, <0x38 0x1>, <0x44 0x1>; interrupts = <8>; - kcs_chan = <3>; status = "disabled"; }; };
@@ -455,10 +455,10 @@ #size-cells = <1>; ranges = <0x0 0x80 0x1e0>; - kcs4: kcs4@0 { - compatible = "aspeed,ast2500-kcs-bmc"; + kcs4: kcs@94 { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x94 0x1>, <0x98 0x1>, <0x9c 0x1>; interrupts = <8>; - kcs_chan = <4>; status = "disabled"; };
arch/arm/boot/dts/aspeed-g6.dtsi +12 -11
@@ -435,22 +435,23 @@ #size-cells = <1>; ranges = <0x0 0x0 0x80>; - kcs1: kcs1@0 { - compatible = "aspeed,ast2600-kcs-bmc"; + kcs1: kcs@24 { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x24 0x1>, <0x30 0x1>, <0x3c 0x1>; interrupts = <GIC_SPI 138 IRQ_TYPE_LEVEL_HIGH>; kcs_chan = <1>; status = "disabled"; }; - kcs2: kcs2@0 { - compatible = "aspeed,ast2600-kcs-bmc"; + kcs2: kcs@28 { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x28 0x1>, <0x34 0x1>, <0x40 0x1>; interrupts = <GIC_SPI 139 IRQ_TYPE_LEVEL_HIGH>; - kcs_chan = <2>; status = "disabled"; }; - kcs3: kcs3@0 { - compatible = "aspeed,ast2600-kcs-bmc"; + kcs3: kcs@2c { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x2c 0x1>, <0x38 0x1>, <0x44 0x1>; interrupts = <GIC_SPI 140 IRQ_TYPE_LEVEL_HIGH>; - kcs_chan = <3>; status = "disabled"; }; };
@@ -464,10 +465,10 @@ #size-cells = <1>; ranges = <0x0 0x80 0x1e0>; - kcs4: kcs4@0 { - compatible = "aspeed,ast2600-kcs-bmc"; + kcs4: kcs@94 { + compatible = "aspeed,ast2500-kcs-bmc-v2"; + reg = <0x94 0x1>, <0x98 0x1>, <0x9c 0x1>; interrupts = <GIC_SPI 141 IRQ_TYPE_LEVEL_HIGH>; - kcs_chan = <4>; status = "disabled"; };
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 163/477 HID: intel-ish-hid: avoid bogus uninitialized-variable warning
In reply to Greg Kroah-HartmanFrom: Arnd Bergmann <[email protected]>
[ Upstream commit 0b66fb3e6b7a53688f8e20945ac78cd3d832c65f ]
Older compilers like gcc-4.8 don't see that the variable is initialized when it is used:
In file included from include/linux/compiler_types.h:68:0,
from <command-line>:0:
drivers/hid/intel-ish-hid/ishtp-fw-loader.c: In function 'load_fw_from_host':
include/linux/compiler-gcc.h:75:45: warning: 'fw_info.ldr_capability.max_dma_buf_size' may be used uninitialized in this function [-Wmaybe-uninitialized]
#define __UNIQUE_ID(prefix) __PASTE(__PASTE(__UNIQUE_ID_, prefix), __COUNTER__)
^
drivers/hid/intel-ish-hid/ishtp-fw-loader.c:770:22: note: 'fw_info.ldr_capability.max_dma_buf_size' was declared here
struct shim_fw_info fw_info;
^Make sure to initialize it before returning an error from ish_query_loader_prop().
--- drivers/hid/intel-ish-hid/ishtp-fw-loader.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/hid/intel-ish-hid/ishtp-fw-loader.c +2 -0
@@ -480,6 +480,7 @@ static int ish_query_loader_prop(struct ishtp_cl_data *client_data, sizeof(ldr_xfer_query_resp));if (rv <0 ) { client_data->flag_retry = true; + *fw_info = (struct shim_fw_info ){};return rv; }
@@ -489,6 +490,7 @@ static int ish_query_loader_prop(struct ishtp_cl_data *client_data,"data size %d is not equal to size of loader_xfer_query_response %zu\n" , rv, sizeof(struct loader_xfer_query_response)); client_data->flag_retry = true; + *fw_info = (struct shim_fw_info ){};return -EMSGSIZE ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 164/477 usb: dwc3: gadget: Properly handle ClearFeature(halt)
In reply to Greg Kroah-HartmanFrom: Thinh Nguyen <[email protected]>
[ Upstream commit cb11ea56f37a36288cdd0a4799a983ee3aa437dd ]
DWC3 must not issue CLEAR_STALL command to control endpoints. The controller automatically clears the STALL when it receives the SETUP token. Also, when the driver receives ClearFeature(halt_ep), DWC3 must stop any active transfer from the endpoint and give back all the requests to the function drivers.
--- drivers/usb/dwc3/gadget.c | 36 +++++++++++++++++++++++++++++++++--- 1 file changed, 33 insertions(+), 3 deletions(-)
drivers/usb/dwc3/gadget.c +33 -3
@@ -1508,6 +1508,10 @@ static void dwc3_gadget_ep_skip_trbs(struct dwc3_ep *dep, struct dwc3_request *r {int i; +/* If req->trb is not set, then the request has not started */ +if (!req->trb) +return ; +/* * If request was already started, this means we had to * stop the transfer. With that we also need to ignore
@@ -1598,6 +1602,8 @@ int __dwc3_gadget_ep_set_halt(struct dwc3_ep *dep, int value, int protocol) {struct dwc3_gadget_ep_cmd_params params;struct dwc3 *dwc = dep->dwc; +struct dwc3_request *req; +struct dwc3_request *tmp;int ret;if (usb_endpoint_xfer_isoc (dep->endpoint.desc)) {
@@ -1634,13 +1640,37 @@ int __dwc3_gadget_ep_set_halt(struct dwc3_ep *dep, int value, int protocol)else dep->flags |=DWC3_EP_STALL ; }else { +/* +* Don't issue CLEAR_STALL command to control endpoints. The +* controller automatically clears the STALL when it receives +* the SETUP token. +*/ +if (dep->number <=1 ) { + dep->flags &= ~(DWC3_EP_STALL |DWC3_EP_WEDGE ); +return 0 ; + } ret =dwc3_send_clear_stall_ep_cmd (dep); -if (ret) +if (ret) {dev_err (dwc->dev,"failed to clear STALL on %s\n" , dep->name); -else - dep->flags &= ~(DWC3_EP_STALL |DWC3_EP_WEDGE ); +return ret; + } + + dep->flags &= ~(DWC3_EP_STALL |DWC3_EP_WEDGE ); + +dwc3_stop_active_transfer (dep, true, true); + +list_for_each_entry_safe (req, tmp, &dep->started_list, list) +dwc3_gadget_move_cancelled_request (req); + +list_for_each_entry_safe (req, tmp, &dep->pending_list, list) +dwc3_gadget_move_cancelled_request (req); + +if (!(dep->flags &DWC3_EP_END_TRANSFER_PENDING )) { + dep->flags &= ~DWC3_EP_DELAY_START ; +dwc3_gadget_ep_cleanup_cancelled_requests (dep); + } }return ret;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 165/477 usb: dwc3: meson-g12a: check return of dwc3_meson_g12a_usb_init
In reply to Greg Kroah-HartmanFrom: Neil Armstrong <[email protected]>
[ Upstream commit 8f5bc1ec770c2bdc8c604ba4119a77d81d8f3529 ]
The dwc3_meson_g12a_usb_init function can return an error, check it.
--- drivers/usb/dwc3/dwc3-meson-g12a.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/usb/dwc3/dwc3-meson-g12a.c +3 -1
@@ -525,7 +525,9 @@ static int dwc3_meson_g12a_probe(struct platform_device *pdev)/* Get dr_mode */ priv->otg_mode =usb_get_dr_mode (dev); -dwc3_meson_g12a_usb_init (priv); + ret =dwc3_meson_g12a_usb_init (priv); +if (ret) + goto err_disable_clks;/* Init PHYs */ for (i =0 ; i <PHY_COUNT ; ++i) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 166/477 usb: dwc3: gadget: Properly handle failed kick_transfer
In reply to Greg Kroah-HartmanFrom: Thinh Nguyen <[email protected]>
[ Upstream commit 8d99087c2db863c5fa3a4a1f3cb82b3a493705ca ]
If dwc3 fails to issue START_TRANSFER/UPDATE_TRANSFER command, then we should properly end an active transfer and give back all the started requests. However if it's for an isoc endpoint, the failure maybe due to bus-expiry status. In this case, don't give back the requests and wait for the next retry.
--- drivers/usb/dwc3/gadget.c | 24 ++++++++++++++++-------- 1 file changed, 16 insertions(+), 8 deletions(-)
drivers/usb/dwc3/gadget.c +16 -8
@@ -1220,6 +1220,8 @@ static void dwc3_prepare_trbs(struct dwc3_ep *dep) } } +static void dwc3_gadget_ep_cleanup_cancelled_requests (struct dwc3_ep *dep); +static int __dwc3_gadget_kick_transfer (struct dwc3_ep *dep) {struct dwc3_gadget_ep_cmd_params params;
@@ -1259,14 +1261,20 @@ static int __dwc3_gadget_kick_transfer(struct dwc3_ep *dep) ret =dwc3_send_gadget_ep_cmd (dep, cmd, ¶ms);if (ret <0 ) { -/* -* FIXME we need to iterate over the list of requests -* here and stop, unmap, free and del each of the linked -* requests instead of what we do now. -*/ -if (req->trb) -memset (req->trb,0 ,sizeof (struct dwc3_trb )); -dwc3_gadget_del_and_unmap_request (dep, req, ret); +struct dwc3_request *tmp; + +if (ret == -EAGAIN ) +return ret; + +dwc3_stop_active_transfer (dep, true, true); + +list_for_each_entry_safe (req, tmp, &dep->started_list, list) +dwc3_gadget_move_cancelled_request (req); + +/* If ep isn't started, then there's no end transfer pending */ +if (!(dep->flags &DWC3_EP_END_TRANSFER_PENDING )) +dwc3_gadget_ep_cleanup_cancelled_requests (dep); +return ret; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 167/477 staging: wilc1000: Increase the size of wid_list array
In reply to Greg Kroah-HartmanFrom: Oscar Carter <[email protected]>
[ Upstream commit a4338ed2e1cf724563956ec5f91deeaabfedbe23 ]
Increase by one the size of wid_list array as index variable can reach a value of 5. If this happens, an out-of-bounds access is performed.
Also, use a #define instead of a hard-coded literal for the new array size.
Addresses-Coverity-ID: 1451981 ("Out-of-bounds access")
--- drivers/staging/wilc1000/hif.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/staging/wilc1000/hif.c +3 -1
@@ -11,6 +11,8 @@#define WILC_FALSE_FRMWR_CHANNEL 100 +#define WILC_SCAN_WID_LIST_SIZE 6 +struct wilc_rcvd_mac_info {u8 status; };
@@ -151,7 +153,7 @@ int wilc_scan(struct wilc_vif *vif, u8 scan_source, u8 scan_type, void *user_arg, struct cfg80211_scan_request *request) { int result = 0; -struct wid wid_list[5 ]; +struct wid wid_list[WILC_SCAN_WID_LIST_SIZE ];u32 index =0 ;u32 i, scan_timeout;u8 *buffer;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 168/477 staging: sm750fb: add missing case while setting FB_VISUAL
In reply to Greg Kroah-HartmanFrom: Matej Dujava <[email protected]>
[ Upstream commit fa90133377f4a7f15a937df6ad55133bb57c5665 ]
Switch statement does not contain all cases: 8, 16, 24, 32. This patch will add missing one (24)
--- drivers/staging/sm750fb/sm750.c | 1 + 1 file changed, 1 insertion(+)
drivers/staging/sm750fb/sm750.c +1 -0
@@ -898,6 +898,7 @@ static int lynxfb_set_fbinfo(struct fb_info *info, int index) fix->visual =FB_VISUAL_PSEUDOCOLOR ;break ;case 16 : +case 24 :case 32 : fix->visual =FB_VISUAL_TRUECOLOR ;break ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 169/477 staging: wfx: avoid compiler warning on empty array
In reply to Greg Kroah-HartmanFrom: Arnd Bergmann <[email protected]>
[ Upstream commit 2eeefd3787fdc6319124945d453774be95b97897 ]
When CONFIG_OF is disabled, gcc-9 produces a warning about the wfx_sdio_of_match[] array having a declaration without a dimension:
drivers/staging/wfx/bus_sdio.c:159:34: error: array 'wfx_sdio_of_match' assumed to have one element [-Werror]
159 | static const struct of_device_id wfx_sdio_of_match[];
| ^~~~~~~~~~~~~~~~~Move the proper declaration up and out of the #ifdef instead.
--- drivers/staging/wfx/bus_sdio.c | 19 ++++++++----------- 1 file changed, 8 insertions(+), 11 deletions(-)
drivers/staging/wfx/bus_sdio.c +8 -11
@@ -156,7 +156,13 @@ static const struct hwbus_ops wfx_sdio_hwbus_ops = { .align_size = wfx_sdio_align_size, }; -static const struct of_device_id wfx_sdio_of_match[]; +static const struct of_device_id wfx_sdio_of_match[] = { + { .compatible ="silabs,wfx-sdio" }, + { .compatible ="silabs,wf200" }, + { }, +}; +MODULE_DEVICE_TABLE (of, wfx_sdio_of_match); +static int wfx_sdio_probe (struct sdio_func *func,const struct sdio_device_id *id) {
@@ -248,15 +254,6 @@ static const struct sdio_device_id wfx_sdio_ids[] = { };MODULE_DEVICE_TABLE (sdio, wfx_sdio_ids); -#ifdef CONFIG_OF -static const struct of_device_id wfx_sdio_of_match[] = { - { .compatible ="silabs,wfx-sdio" }, - { .compatible ="silabs,wf200" }, - { }, -}; -MODULE_DEVICE_TABLE (of, wfx_sdio_of_match); -#endif -struct sdio_driver wfx_sdio_driver = { .name ="wfx-sdio" , .id_table = wfx_sdio_ids,
@@ -264,6 +261,6 @@ struct sdio_driver wfx_sdio_driver = { .remove = wfx_sdio_remove, .drv = { .owner = THIS_MODULE, - .of_match_table = of_match_ptr(wfx_sdio_of_match), + .of_match_table = wfx_sdio_of_match, } };
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 170/477 PCI: v3-semi: Fix a memory leak in v3_pci_probe() error handling paths
In reply to Greg Kroah-HartmanFrom: Christophe JAILLET <[email protected]>
[ Upstream commit bca718988b9008d0d5f504e2d318178fc84958c1 ]
If we fails somewhere in 'v3_pci_probe()', we need to free 'host'.
Use the managed version of 'pci_alloc_host_bridge()' to do that easily. The use of managed resources is already widely used in this driver.
--- drivers/pci/controller/pci-v3-semi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/pci/controller/pci-v3-semi.c +1 -1
@@ -720,7 +720,7 @@ static int v3_pci_probe(struct platform_device *pdev)int irq;int ret; - host =pci_alloc_host_bridge (sizeof (*v3)); + host =devm_pci_alloc_host_bridge (dev,sizeof (*v3));if (!host)return -ENOMEM ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 171/477 i2c: pxa: fix i2c_pxa_scream_blue_murder() debug output
In reply to Greg Kroah-HartmanFrom: Russell King <[email protected]>
[ Upstream commit 88b73ee7ca4c90baf136ed5a8377fc5a9b73ac08 ]
The IRQ log output is supposed to appear on a single line. However, commit 3a2dc1677b60 ("i2c: pxa: Update debug function to dump more info on error") resulted in it being printed one-entry-per-line, which is excessively long.
Fixing this is not a trivial matter; using pr_cont() doesn't work as the previous dev_dbg() may not have been compiled in, or may be dynamic.
Since the rest of this function output is at error level, and is also debug output, promote this to error level as well to avoid this problem.
Reduce the number of always zero prefix digits to save screen real- estate.
--- drivers/i2c/busses/i2c-pxa.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-)
drivers/i2c/busses/i2c-pxa.c +3 -4
@@ -311,11 +311,10 @@ static void i2c_pxa_scream_blue_murder(struct pxa_i2c *i2c, const char *why)dev_err (dev,"IBMR: %08x IDBR: %08x ICR: %08x ISR: %08x\n" ,readl (_IBMR (i2c)),readl (_IDBR (i2c)),readl (_ICR (i2c)),readl (_ISR (i2c))); -dev_dbg (dev,"log: " ); +dev_err (dev,"log:" );for (i =0 ; i < i2c->irqlogidx; i++) -pr_debug ("[%08x:%08x] " , i2c->isrlog[i], i2c->icrlog[i]); - - pr_debug("\n"); +pr_cont (" [%03x:%05x]" , i2c->isrlog[i], i2c->icrlog[i]); + pr_cont("\n"); }#else /* ifdef DEBUG */
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 172/477 drivers: base: Fix NULL pointer exception in __platform_driver_probe() if a driver developer is foolish
In reply to Greg Kroah-HartmanFrom: Kuppuswamy Sathyanarayanan <[email protected]>
[ Upstream commit 388bcc6ecc609fca1b4920de7dc3806c98ec535e ]
If platform bus driver registration is failed then, accessing platform bus spin lock (&drv->driver.bus->p->klist_drivers.k_lock) in __platform_driver_probe() without verifying the return value __platform_driver_register() can lead to NULL pointer exception.
So check the return value before attempting the spin lock.
One such example is below:
For a custom usecase, I have intentionally failed the platform bus registration and I expected all the platform device/driver registrations to fail gracefully. But I came across this panic issue.
[ 1.331067] BUG: kernel NULL pointer dereference, address: 00000000000000c8 [ 1.331118] #PF: supervisor write access in kernel mode [ 1.331163] #PF: error_code(0x0002) - not-present page [ 1.331208] PGD 0 P4D 0 [ 1.331233] Oops: 0002 [#1] PREEMPT SMP [ 1.331268] CPU: 3 PID: 1 Comm: swapper/0 Tainted: G W 5.6.0-00049-g670d35fb0144 #165 [ 1.331341] Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS 0.0.0 02/06/2015 [ 1.331406] RIP: 0010:_raw_spin_lock+0x15/0x30 [ 1.331588] RSP: 0000:ffffc9000001be70 EFLAGS: 00010246 [ 1.331632] RAX: 0000000000000000 RBX: 00000000000000c8 RCX: 0000000000000001 [ 1.331696] RDX: 0000000000000001 RSI: 0000000000000092 RDI: 0000000000000000 [ 1.331754] RBP: 00000000ffffffed R08: 0000000000000501 R09: 0000000000000001 [ 1.331817] R10: ffff88817abcc520 R11: 0000000000000670 R12: 00000000ffffffed [ 1.331881] R13: ffffffff82dbc268 R14: ffffffff832f070a R15: 0000000000000000 [ 1.331945] FS: 0000000000000000(0000) GS:ffff88817bd80000(0000) knlGS:0000000000000000 [ 1.332008] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 1.332062] CR2: 00000000000000c8 CR3: 000000000681e001 CR4: 00000000003606e0 [ 1.332126] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 [ 1.332189] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 [ 1.332252] Call Trace: [ 1.332281] __platform_driver_probe+0x92/0xee [ 1.332323] ? rtc_dev_init+0x2b/0x2b [ 1.332358] cmos_init+0x37/0x67 [ 1.332396] do_one_initcall+0x7d/0x168 [ 1.332428] kernel_init_freeable+0x16c/0x1c9 [ 1.332473] ? rest_init+0xc0/0xc0 [ 1.332508] kernel_init+0x5/0x100 [ 1.332543] ret_from_fork+0x1f/0x30 [ 1.332579] CR2: 00000000000000c8 [ 1.332616] ---[ end trace 3bd87f12e9010b87 ]--- [ 1.333549] note: swapper/0[1] exited with preempt_count 1 [ 1.333592] Kernel panic - not syncing: Attempted to kill init! exitcode=0x00000009 [ 1.333736] Kernel Offset: disabled
Note, this can only be triggered if a driver errors out from this call, which should never happen. If it does, the driver needs to be fixed.
--- drivers/base/platform.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/base/platform.c +2 -0
@@ -851,6 +851,8 @@ int __init_or_module __platform_driver_probe(struct platform_driver *drv,/* temporary section violation during probe() */ drv->probe = probe; retval = code =__platform_driver_register (drv, module); +if (retval) +return retval;/* * Fixup that section violation, being paranoid about code scanning
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 173/477 PCI: rcar: Fix incorrect programming of OB windows
In reply to Greg Kroah-HartmanFrom: Andrew Murray <[email protected]>
[ Upstream commit 2b9f217433e31d125fb697ca7974d3de3ecc3e92 ]
The outbound windows (PCIEPAUR(x), PCIEPALR(x)) describe a mapping between a CPU address (which is determined by the window number 'x') and a programmed PCI address - Thus allowing the controller to translate CPU accesses into PCI accesses.
However the existing code incorrectly writes the CPU address - lets fix this by writing the PCI address instead.
For memory transactions, existing DT users describe a 1:1 identity mapping and thus this change should have no effect. However the same isn't true for I/O.
--- drivers/pci/controller/pcie-rcar.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-)
drivers/pci/controller/pcie-rcar.c +5 -4
@@ -333,11 +333,12 @@ static struct pci_ops rcar_pcie_ops = { };static void rcar_pcie_setup_window (int win,struct rcar_pcie *pcie, -struct resource *res) +struct resource_entry *window) {/* Setup PCIe address space mappings for each resource */ resource_size_t size;resource_size_t res_start; +struct resource *res = window->res;u32 mask;rcar_pci_write_reg (pcie,0x00000000 ,PCIEPTCTLR (win));
@@ -351,9 +352,9 @@ static void rcar_pcie_setup_window(int win, struct rcar_pcie *pcie,rcar_pci_write_reg (pcie, mask <<7 ,PCIEPAMR (win));if (res->flags &IORESOURCE_IO ) - res_start =pci_pio_to_address (res->start); + res_start =pci_pio_to_address (res->start) - window->offset;else - res_start = res->start; + res_start = res->start - window->offset;rcar_pci_write_reg (pcie,upper_32_bits (res_start),PCIEPAUR (win)); rcar_pci_write_reg(pcie, lower_32_bits(res_start) & ~0x7F,
@@ -382,7 +383,7 @@ static int rcar_pcie_setup(struct list_head *resource, struct rcar_pcie *pci)switch (resource_type (res)) {case IORESOURCE_IO :case IORESOURCE_MEM : -rcar_pcie_setup_window (i, pci, res); +rcar_pcie_setup_window (i, pci, win); i++;break ;case IORESOURCE_BUS :
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 174/477 PCI/ASPM: Allow ASPM on links to PCIe-to-PCI/PCI-X Bridges
In reply to Greg Kroah-HartmanFrom: Kai-Heng Feng <[email protected]>
[ Upstream commit 66ff14e59e8a30690755b08bc3042359703fb07a ]
7d715a6c1ae5 ("PCI: add PCI Express ASPM support") added the ability for Linux to enable ASPM, but for some undocumented reason, it didn't enable ASPM on links where the downstream component is a PCIe-to-PCI/PCI-X Bridge.
Remove this exclusion so we can enable ASPM on these links.
The Dell OptiPlex 7080 mentioned in the bugzilla has a TI XIO2001 PCIe-to-PCI Bridge. Enabling ASPM on the link leading to it allows the Intel SoC to enter deeper Package C-states, which is a significant power savings.
[bhelgaas: commit log]
Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=207571
--- drivers/pci/pcie/aspm.c | 10 ---------- 1 file changed, 10 deletions(-)
drivers/pci/pcie/aspm.c +0 -10
@@ -628,16 +628,6 @@ static void pcie_aspm_cap_init(struct pcie_link_state *link, int blacklist)/* Setup initial capable state. Will be updated later */ link->aspm_capable = link->aspm_support; -/* -* If the downstream component has pci bridge function, don't -* do ASPM for now. -*/ -list_for_each_entry (child, &linkbus->devices, bus_list) { -if (pci_pcie_type (child) ==PCI_EXP_TYPE_PCI_BRIDGE ) { - link->aspm_disable =ASPM_STATE_ALL ; -break ; - } - }/* Get and check endpoint acceptable latencies */ list_for_each_entry (child, &linkbus->devices, bus_list) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 175/477 scsi: qla2xxx: Fix warning after FC target reset
In reply to Greg Kroah-HartmanFrom: Viacheslav Dubeyko <[email protected]>
[ Upstream commit f839544ccff60cbe534282aac68858fc3fb278ca ]
Currently, FC target reset finishes with the warning message:
[84010.596893] ------------[ cut here ]------------
[84010.596917] WARNING: CPU: 238 PID: 279973 at ../drivers/scsi/qla2xxx/qla_target.c:6644 qlt_enable_vha+0x1d0/0x260 [qla2xxx]
[84010.596918] Modules linked in: vrf af_packet 8021q garp mrp stp llc netlink_diag target_tatlin_tblock(OEX) dm_ec(OEX) ttln_rdma(OEX) dm_frontend(OEX) nvme_rdma nvmet tcm_qla2xxx iscsi_target_mod target_core_mod at24 nvmem_core pnv_php ipmi_watchdog ipmi_ssif vmx_crypto gf128mul crct10dif_vpmsum qla2xxx rpcrdma nvme_fc powernv_flash(X) nvme_fabrics uio_pdrv_genirq mtd rtc_opal(X) ibmpowernv(X) opal_prd(X) uio scsi_transport_fc i2c_opal(X) ses enclosure ipmi_poweroff ast i2c_algo_bit ttm bmc_mcu(OEX) drm_kms_helper syscopyarea sysfillrect sysimgblt fb_sys_fops drm drm_panel_orientation_quirks agpgart nfsd auth_rpcgss nfs_acl ipmi_powernv(X) lockd ipmi_devintf ipmi_msghandler grace dummy ext4 crc16 jbd2 mbcache sd_mod rdma_ucm ib_iser rdma_cm ib_umad iw_cm ib_ipoib libiscsi scsi_transport_iscsi ib_cm
[84010.596975] configfs mlx5_ib ib_uverbs ib_core mlx5_core crc32c_vpmsum xhci_pci xhci_hcd mpt3sas(OEX) tg3 usbcore mlxfw tls raid_class libphy scsi_transport_sas devlink ptp pps_core nvme nvme_core sunrpc dm_mirror dm_region_hash dm_log sg dm_multipath dm_mod scsi_dh_rdac scsi_dh_emc scsi_dh_alua scsi_mod autofs4
[84010.597001] Supported: Yes, External
[84010.597004] CPU: 238 PID: 279973 Comm: bash Tainted: G OE 4.12.14-197.29-default #1 SLE15-SP1
[84010.597006] task: c000000a104c0000 task.stack: c000000b52188000
[84010.597007] NIP: d00000001ffd7f78 LR: d00000001ffd7f6c CTR: c0000000001676c0
[84010.597008] REGS: c000000b5218b910 TRAP: 0700 Tainted: G OE (4.12.14-197.29-default)
[84010.597008] MSR: 900000010282b033 <SF,HV,VEC,VSX,EE,FP,ME,IR,DR,RI,LE,TM[E]>
[84010.597015] CR: 48242424 XER: 00000000
[84010.597016] CFAR: d00000001ff45d08 SOFTE: 1
GPR00: d00000001ffd7f6c c000000b5218bb90 d00000002001b228 0000000000000102
GPR04: 0000000000000001 0000000000000001 00013d91ed0a5e2d 0000000000000000
GPR08: c000000007793300 0000000000000000 0000000000000000 c000000a086e7818
GPR12: 0000000000002200 c000000007793300 0000000000000000 000000012bc937c0
GPR16: 000000012bbf7ed0 0000000000000000 000000012bc3dd10 0000000000000000
GPR20: 000000012bc4db28 0000010036442810 000000012bc97828 000000012bc96c70
GPR24: 00000100365b1550 0000000000000000 00000100363f3d80 c000000be20d3080
GPR28: c000000bda7eae00 c000000be20db7e8 c000000be20d3778 c000000be20db7e8
[84010.597042] NIP [d00000001ffd7f78] qlt_enable_vha+0x1d0/0x260 [qla2xxx]
[84010.597051] LR [d00000001ffd7f6c] qlt_enable_vha+0x1c4/0x260 [qla2xxx]
[84010.597051] Call Trace:
[84010.597061] [c000000b5218bb90] [d00000001ffd7f6c] qlt_enable_vha+0x1c4/0x260 [qla2xxx] (unreliable)
[84010.597064] [c000000b5218bc20] [d000000009820b6c] tcm_qla2xxx_tpg_enable_store+0xc4/0x130 [tcm_qla2xxx]
[84010.597067] [c000000b5218bcb0] [d0000000185d0e68] configfs_write_file+0xd0/0x190 [configfs]
[84010.597072] [c000000b5218bd00] [c0000000003d0edc] __vfs_write+0x3c/0x1e0
[84010.597074] [c000000b5218bd90] [c0000000003d2ea8] vfs_write+0xd8/0x220
[84010.597076] [c000000b5218bde0] [c0000000003d4ddc] SyS_write+0x6c/0x110
[84010.597079] [c000000b5218be30] [c00000000000b188] system_call+0x3c/0x130
[84010.597080] Instruction dump:
[84010.597082] 7d0050a8 7d084b78 7d0051ad 40c2fff4 7fa3eb78 4bf73965 60000000 7fa3eb78
[84010.597086] 4bf6dcd9 60000000 2fa30000 419eff40 <0fe00000> 4bffff38 e95f0058 a12a0180
[84010.597090] ---[ end trace e32abaf6e6fee826 ]---To reproduce:
echo 0x7fffffff > /sys/module/qla2xxx/parameters/logging modprobe target_core_mod
modprobe tcm_qla2xxx
mkdir /sys/kernel/config/target/qla2xxx
mkdir /sys/kernel/config/target/qla2xxx/<port-name>
mkdir /sys/kernel/config/target/qla2xxx/<port-name>/tpgt_1 echo 1 > /sys/kernel/config/target/qla2xxx/<port-name>/tpgt_1/enable echo 0 > /sys/kernel/config/target/qla2xxx/<port-name>/tpgt_1/enable echo 1 > /sys/kernel/config/target/qla2xxx/<port-name>/tpgt_1/enable
SYSTEM START
kernel: pid 327:drivers/scsi/qla2xxx/qla_init.c:2174 qla2x00_initialize_adapter(): vha->flags.online 0x0 <...>
kernel: pid 327:drivers/scsi/qla2xxx/qla_os.c:3444 qla2x00_probe_one(): vha->flags.online 0x1
echo 1 > /sys/kernel/config/target/qla2xxx/21:00:00:24:ff:86:a6:2a/tpgt_1/enable
kernel: pid 348:drivers/scsi/qla2xxx/qla_init.c:6641 qla2x00_abort_isp_cleanup(): vha->flags.online 0x0, ISP_ABORT_NEEDED 0x0 <...>
kernel: pid 348:drivers/scsi/qla2xxx/qla_init.c:6998 qla2x00_restart_isp(): vha->flags.online 0x0
echo 0 > /sys/kernel/config/target/qla2xxx/21:00:00:24:ff:86:a6:2a/tpgt_1/enable
kernel: pid 348:drivers/scsi/qla2xxx/qla_init.c:6641 qla2x00_abort_isp_cleanup(): vha->flags.online 0x0, ISP_ABORT_NEEDED 0x0 <...>
kernel: pid 1404:drivers/scsi/qla2xxx/qla_os.c:1107 qla2x00_wait_for_hba_online(): base_vha->flags.online 0x0
echo 1 > /sys/kernel/config/target/qla2xxx/21:00:00:24:ff:86:a6:2a/tpgt_1/enable
kernel: pid 1404:drivers/scsi/qla2xxx/qla_os.c:1107 qla2x00_wait_for_hba_online(): base_vha->flags.online 0x0
kernel: -----------[ cut here ]-----------
kernel: WARNING: CPU: 1 PID: 1404 at drivers/scsi/qla2xxx/qla_target.c:6654 qlt_enable_vha+0x1e0/0x280 [qla2xxx]
The issue happens because no real ISP reset is executed. The qla2x00_abort_isp(scsi_qla_host_t *vha) function expects that vha->flags.online will be not zero for ISP reset procedure. This patch sets vha->flags.online to 1 before calling ->abort_isp() for starting the ISP reset.
--- drivers/scsi/qla2xxx/qla_os.c | 1 + 1 file changed, 1 insertion(+)
drivers/scsi/qla2xxx/qla_os.c +1 -0
@@ -6871,6 +6871,7 @@ qla2x00_do_dpc(void *data)if (do_reset && !(test_and_set_bit (ABORT_ISP_ACTIVE , &base_vha->dpc_flags))) { + base_vha->flags.online =1 ;ql_dbg (ql_dbg_dpc, base_vha,0x4007 ,"ISP abort scheduled.\n" );if (ha->isp_ops->abort_isp (base_vha)) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 176/477 ALSA: firewire-lib: fix invalid assignment to union data for directional parameter
In reply to Greg Kroah-HartmanFrom: Takashi Sakamoto <[email protected]>
[ Upstream commit 8304cf77c92038cd1c50c27b69d30be695cc8003 ]
Although the value of FDF is used just for outgoing stream, the assignment to union member is done for both directions of stream. At present this causes no issue because the value of same position is reassigned later for opposite stream. However, it's better to add if statement.
--- sound/firewire/amdtp-am824.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
sound/firewire/amdtp-am824.c +2 -1
@@ -82,7 +82,8 @@ int amdtp_am824_set_parameters(struct amdtp_stream *s, unsigned int rate,if (err <0 )return err; - s->ctx_data.rx.fdf =AMDTP_FDF_AM824 | s->sfc; +if (s->direction ==AMDTP_OUT_STREAM ) + s->ctx_data.rx.fdf =AMDTP_FDF_AM824 | s->sfc; p->pcm_channels = pcm_channels; p->midi_ports = midi_ports;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 177/477 power: supply: lp8788: Fix an error handling path in lp8788_charger_probe()
In reply to Greg Kroah-HartmanFrom: Christophe JAILLET <[email protected]>
[ Upstream commit 934ed3847a4ebc75b655659c4d2349ba4337941c ]
In the probe function, in case of error, resources allocated in 'lp8788_setup_adc_channel()' must be released.
This can be achieved easily by using the devm_ variant of 'iio_channel_get()'.
This has the extra benefit to simplify the remove function and to axe the 'lp8788_release_adc_channel()' function which is now useless.
--- drivers/power/supply/lp8788-charger.c | 18 ++---------------- 1 file changed, 2 insertions(+), 16 deletions(-)
drivers/power/supply/lp8788-charger.c +2 -16
@@ -572,27 +572,14 @@ static void lp8788_setup_adc_channel(struct device *dev,return ;/* ADC channel for battery voltage */ - chan =iio_channel_get (dev, pdata->adc_vbatt); + chan =devm_iio_channel_get (dev, pdata->adc_vbatt); pchg->chan[LP8788_VBATT ] =IS_ERR (chan) ?NULL : chan;/* ADC channel for battery temperature */ - chan =iio_channel_get (dev, pdata->adc_batt_temp); + chan =devm_iio_channel_get (dev, pdata->adc_batt_temp); pchg->chan[LP8788_BATT_TEMP ] =IS_ERR (chan) ?NULL : chan; } -static void lp8788_release_adc_channel (struct lp8788_charger *pchg) -{ -int i; - -for (i =0 ; i <LP8788_NUM_CHG_ADC ; i++) { -if (!pchg->chan[i]) -continue ; - -iio_channel_release (pchg->chan[i]); - pchg->chan[i] =NULL ; - } -} -static ssize_t lp8788_show_charger_status (struct device *dev,struct device_attribute *attr,char *buf) {
@@ -735,7 +722,6 @@ static int lp8788_charger_remove(struct platform_device *pdev)flush_work (&pchg->charger_work);lp8788_irq_unregister (pdev, pchg);lp8788_psy_unregister (pchg); -lp8788_release_adc_channel (pchg);return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 178/477 power: supply: smb347-charger: IRQSTAT_D is volatile
In reply to Greg Kroah-HartmanFrom: Dmitry Osipenko <[email protected]>
[ Upstream commit c32ea07a30630ace950e07ffe7a18bdcc25898e1 ]
Fix failure when USB cable is connected:
smb347 2-006a: reading IRQSTAT_D failed
--- drivers/power/supply/smb347-charger.c | 1 + 1 file changed, 1 insertion(+)
drivers/power/supply/smb347-charger.c +1 -0
@@ -1138,6 +1138,7 @@ static bool smb347_volatile_reg(struct device *dev, unsigned int reg)switch (reg) {case IRQSTAT_A :case IRQSTAT_C : +case IRQSTAT_D :case IRQSTAT_E :case IRQSTAT_F :case STAT_A :
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 179/477 PCI: brcmstb: Assert fundamental reset on initialization
In reply to Greg Kroah-HartmanFrom: Nicolas Saenz Julienne <[email protected]>
[ Upstream commit 22e21e51ce755399fd42055a3f668ee4af370881 ]
While preparing the driver for upstream this detail was missed.
If not asserted during the initialization process, devices connected on the bus will not be made aware of the internal reset happening. This, potentially resulting in unexpected behavior.
--- drivers/pci/controller/pcie-brcmstb.c | 1 + 1 file changed, 1 insertion(+)
drivers/pci/controller/pcie-brcmstb.c +1 -0
@@ -697,6 +697,7 @@ static int brcm_pcie_setup(struct brcm_pcie *pcie)/* Reset the bridge */ brcm_pcie_bridge_sw_init_set (pcie,1 ); +brcm_pcie_perst_set (pcie,1 );usleep_range (100 ,200 );
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 180/477 ASoC: SOF: core: fix error return code in sof_probe_continue()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit 7d8785bc7adbb4dc5ba8ee06994107637848ded8 ]
Fix to return negative error code -ENOMEM from the IPC init error handling case instead of 0, as done elsewhere in this function.
--- sound/soc/sof/core.c | 1 + 1 file changed, 1 insertion(+)
sound/soc/sof/core.c +1 -0
@@ -176,6 +176,7 @@ static int sof_probe_continue(struct snd_sof_dev *sdev)/* init the IPC */ sdev->ipc =snd_sof_ipc_init (sdev);if (!sdev->ipc) { + ret = -ENOMEM ;dev_err (sdev->dev,"error: failed to init DSP IPC %d\n" , ret); goto ipc_err; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 181/477 remoteproc/mediatek: fix invalid use of sizeof in scp_ipi_init()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit 8096f80a5c09b716be207eb042c4e40d6cdefbd2 ]
sizeof() when applied to a pointer typed expression gives the size of the pointer, not that of the pointed data.
--- drivers/remoteproc/mtk_scp.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/remoteproc/mtk_scp.c +2 -2
@@ -132,8 +132,8 @@ static int scp_ipi_init(struct mtk_scp *scp) (struct mtk_share_obj __iomem *)(scp->sram_base + recv_offset); scp->send_buf = (struct mtk_share_obj __iomem *)(scp->sram_base + send_offset); -memset_io (scp->recv_buf,0 ,sizeof (scp->recv_buf)); -memset_io (scp->send_buf,0 ,sizeof (scp->send_buf)); +memset_io (scp->recv_buf,0 ,sizeof (*scp->recv_buf)); +memset_io (scp->send_buf,0 ,sizeof (*scp->send_buf));return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 182/477 arm64: dts: msm8996: Fix CSI IRQ types
In reply to Greg Kroah-HartmanFrom: Loic Poulain <[email protected]>
[ Upstream commit 4a4a26317ec8aba575f6b85789a42639937bc1a4 ]
Each IRQ_TYPE_NONE interrupt causes a warning at boot. Fix that by defining an appropriate type.
--- arch/arm64/boot/dts/qcom/msm8996.dtsi | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-)
arch/arm64/boot/dts/qcom/msm8996.dtsi +10 -10
@@ -989,16 +989,16 @@ "csi_clk_mux", "vfe0", "vfe1"; - interrupts = <GIC_SPI 78 0>, - <GIC_SPI 79 0>, - <GIC_SPI 80 0>, - <GIC_SPI 296 0>, - <GIC_SPI 297 0>, - <GIC_SPI 298 0>, - <GIC_SPI 299 0>, - <GIC_SPI 309 0>, - <GIC_SPI 314 0>, - <GIC_SPI 315 0>; + interrupts = <GIC_SPI 78 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 79 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 80 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 296 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 297 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 298 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 299 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 309 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 314 IRQ_TYPE_EDGE_RISING>, + <GIC_SPI 315 IRQ_TYPE_EDGE_RISING>; interrupt-names = "csiphy0", "csiphy1", "csiphy2",
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 183/477 scsi: target: loopback: Fix READ with data and sensebytes
In reply to Greg Kroah-HartmanFrom: Bodo Stroesser <[email protected]>
[ Upstream commit c68a56736c129f5dd1632856956f9c3e04bae200 ]
We use tcm_loop with tape emulations running on tcmu.
In case application reads a short tape block with a longer READ, or a long tape block with a short READ, according to SCC spec data has to be tranferred _and_ sensebytes with ILI set and information field containing the residual count. Similar problem also exists when using fixed block size in READ.
Up to now tcm_loop is not prepared to handle sensebytes if input data is provided, as in tcm_loop_queue_data_in() it only sets SAM_STAT_GOOD and, if necessary, the residual count.
To fix the bug, the same handling for sensebytes as present in tcm_loop_queue_status() must be done in tcm_loop_queue_data_in() also.
After adding this handling, the two function now are nearly identical, so I created a single function with two wrappers.
--- drivers/target/loopback/tcm_loop.c | 36 +++++++++++++----------------- 1 file changed, 15 insertions(+), 21 deletions(-)
drivers/target/loopback/tcm_loop.c +15 -21
@@ -545,32 +545,15 @@ static int tcm_loop_write_pending(struct se_cmd *se_cmd)return 0 ; } -static int tcm_loop_queue_data_in (struct se_cmd *se_cmd) +static int tcm_loop_queue_data_or_status (const char *func, +struct se_cmd *se_cmd,u8 scsi_status) {struct tcm_loop_cmd *tl_cmd =container_of (se_cmd, struct tcm_loop_cmd, tl_se_cmd);struct scsi_cmnd *sc = tl_cmd->sc;pr_debug ("%s() called for scsi_cmnd: %p cdb: 0x%02x\n" , - __func__, sc, sc->cmnd[0 ]); - - sc->result =SAM_STAT_GOOD ; -set_host_byte (sc,DID_OK ); -if ((se_cmd->se_cmd_flags &SCF_OVERFLOW_BIT ) || - (se_cmd->se_cmd_flags &SCF_UNDERFLOW_BIT )) -scsi_set_resid (sc, se_cmd->residual_count); - sc->scsi_done (sc); -return 0 ; -} - -static int tcm_loop_queue_status (struct se_cmd *se_cmd) -{ -struct tcm_loop_cmd *tl_cmd =container_of (se_cmd, - struct tcm_loop_cmd, tl_se_cmd); -struct scsi_cmnd *sc = tl_cmd->sc; - -pr_debug ("%s() called for scsi_cmnd: %p cdb: 0x%02x\n" , - __func__, sc, sc->cmnd[0 ]); + func, sc, sc->cmnd[0 ]); if (se_cmd->sense_buffer && ((se_cmd->se_cmd_flags & SCF_TRANSPORT_TASK_SENSE) ||
@@ -581,7 +564,7 @@ static int tcm_loop_queue_status(struct se_cmd *se_cmd) sc->result =SAM_STAT_CHECK_CONDITION ;set_driver_byte (sc,DRIVER_SENSE ); }else - sc->result = se_cmd->scsi_status; + sc->result = scsi_status;set_host_byte (sc,DID_OK ); if ((se_cmd->se_cmd_flags & SCF_OVERFLOW_BIT) ||
@@ -591,6 +574,17 @@ static int tcm_loop_queue_status(struct se_cmd *se_cmd)return 0 ; } +static int tcm_loop_queue_data_in (struct se_cmd *se_cmd) +{ +return tcm_loop_queue_data_or_status (__func__, se_cmd,SAM_STAT_GOOD ); +} + +static int tcm_loop_queue_status (struct se_cmd *se_cmd) +{ +return tcm_loop_queue_data_or_status (__func__, + se_cmd, se_cmd->scsi_status); +} +static void tcm_loop_queue_tm_rsp (struct se_cmd *se_cmd) { struct tcm_loop_cmd *tl_cmd = container_of(se_cmd,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 184/477 scsi: mpt3sas: Fix double free warnings
In reply to Greg Kroah-HartmanFrom: Suganath Prabu S <[email protected]>
[ Upstream commit cbbfdb2a2416c9f0cde913cf09670097ac281282 ]
Fix following warning from Smatch static analyser:
drivers/scsi/mpt3sas/mpt3sas_base.c:5256 _base_allocate_memory_pools()
warn: 'ioc->hpr_lookup' double freed
drivers/scsi/mpt3sas/mpt3sas_base.c:5256 _base_allocate_memory_pools()
warn: 'ioc->internal_lookup' double freed
--- drivers/scsi/mpt3sas/mpt3sas_base.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/scsi/mpt3sas/mpt3sas_base.c +2 -0
@@ -4915,7 +4915,9 @@ _base_release_memory_pools(struct MPT3SAS_ADAPTER *ioc) }kfree (ioc->hpr_lookup); + ioc->hpr_lookup =NULL ;kfree (ioc->internal_lookup); + ioc->internal_lookup =NULL ;if (ioc->chain_lookup) {for (i =0 ; i < ioc->scsiio_depth; i++) { for (j = ioc->chains_per_prp_buffer;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 185/477 f2fs: Fix wrong stub helper update_sit_info
In reply to Greg Kroah-HartmanFrom: YueHaibing <[email protected]>
[ Upstream commit 48abe91ac1ad27cd5a5709f983dcf58f2b9a6b70 ]
update_sit_info should be f2fs_update_sit_info, otherwise build fails while no CONFIG_F2FS_STAT_FS.
--- fs/f2fs/f2fs.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
fs/f2fs/f2fs.h +1 -1
@@ -3656,7 +3656,7 @@ static inline int f2fs_build_stats(struct f2fs_sb_info *sbi) { return 0; }static inline void f2fs_destroy_stats (struct f2fs_sb_info *sbi) { }static inline void __init f2fs_create_root_stats (void ) { }static inline void f2fs_destroy_root_stats (void ) { } -static inline void update_sit_info (struct f2fs_sb_info *sbi) {} +static inline void f2fs_update_sit_info (struct f2fs_sb_info *sbi) {}#endif extern const struct file_operations f2fs_dir_operations;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 186/477 f2fs: fix potential use-after-free issue
In reply to Greg Kroah-HartmanFrom: Chao Yu <[email protected]>
[ Upstream commit f3494345ce9999624b36109252a4bf5f00e51a46 ]
In error path of f2fs_read_multi_pages(), it should let last referrer release decompress io context memory, otherwise, other referrer will cause use-after-free issue.
--- fs/f2fs/data.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
fs/f2fs/data.c +4 -4
@@ -2130,16 +2130,16 @@ submit_and_realloc: page->index, for_write);if (IS_ERR (bio)) { ret =PTR_ERR (bio); - bio =NULL ; dic->failed = true;if (refcount_sub_and_test (dic->nr_cpages - i, - &dic->ref)) + &dic->ref)) {f2fs_decompress_end_io (dic->rpages, cc->cluster_size, true, false); -f2fs_free_dic (dic); +f2fs_free_dic (dic); + }f2fs_put_dnode (&dn); - *bio_ret = bio; + *bio_ret =NULL ;return ret; } }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 187/477 f2fs: compress: fix zstd data corruption
In reply to Greg Kroah-HartmanFrom: Chao Yu <[email protected]>
[ Upstream commit 1454c978efbb57b052670d50023f48c759d704ce ]
During zstd compression, ZSTD_endStream() may return non-zero value because distination buffer is full, but there is still compressed data remained in intermediate buffer, it means that zstd algorithm can not save at last one block space, let's just writeback raw data instead of compressed one, this can fix data corruption when decompressing incomplete stored compression data.
--- fs/f2fs/compress.c | 7 +++++++ 1 file changed, 7 insertions(+)
fs/f2fs/compress.c +7 -0
@@ -369,6 +369,13 @@ static int zstd_compress_pages(struct compress_ctx *cc)return -EIO ; } +/* +* there is compressed data remained in intermediate buffer due to +* no more space in cbuf.cdata +*/ +if (ret) +return -EAGAIN ; + cc->clen = outbuf.pos;return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 188/477 um: do not evaluate compilers library path when cleaning
In reply to Greg Kroah-HartmanFrom: Masahiro Yamada <[email protected]>
[ Upstream commit 7e49afc03212010d0ee27532a75cfeb0125bd868 ]
Since commit a83e4ca26af8 ("kbuild: remove cc-option switch from -Wframe-larger-than="), 'make ARCH=um clean' emits an error message as follows:
$ make ARCH=um clean gcc: error: missing argument to '-Wframe-larger-than='
We do not care compiler flags when cleaning.
Use the '=' operator for lazy expansion because we do not use LDFLAGS_pcap.o or LDFLAGS_vde.o when cleaning.
While I was here, I removed the redundant -r option because it already exists in the recipe.
--- arch/um/drivers/Makefile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/um/drivers/Makefile +2 -2
@@ -18,9 +18,9 @@ ubd-objs := ubd_kern.o ubd_user.o port-objs := port_kern.o port_user.o harddog-objs := harddog_kern.o harddog_user.o -LDFLAGS_pcap.o := -r $(shell $(CC) $(KBUILD_CFLAGS) -print-file-name=libpcap.a) +LDFLAGS_pcap.o = $(shell $(CC) $(KBUILD_CFLAGS) -print-file-name=libpcap.a) -LDFLAGS_vde.o := -r $(shell $(CC) $(CFLAGS) -print-file-name=libvdeplug.a) +LDFLAGS_vde.o = $(shell $(CC) $(CFLAGS) -print-file-name=libvdeplug.a) targets := pcap_kern.o pcap_user.o vde_kern.o vde_user.o
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 189/477 unicore32: do not evaluate compilers library path when cleaning
In reply to Greg Kroah-HartmanFrom: Masahiro Yamada <[email protected]>
[ Upstream commit 081b4b54ff6c58be2ffcf09d42e5df8f031eacd0 ]
Since commit a83e4ca26af8 ("kbuild: remove cc-option switch from -Wframe-larger-than="), 'make ARCH=unicore32 clean' emits error messages as follows:
$ make ARCH=unicore32 clean gcc: error: missing argument to '-Wframe-larger-than=' gcc: error: missing argument to '-Wframe-larger-than='
We do not care compiler flags when cleaning.
Use the '=' operator for lazy expansion because we do not use GNU_LIBC_A or GNU_LIBGCC_A when cleaning.
--- arch/unicore32/lib/Makefile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/unicore32/lib/Makefile +2 -2
@@ -10,12 +10,12 @@ lib-y += strncpy_from_user.o strnlen_user.o lib-y += clear_user.o copy_page.o lib-y += copy_from_user.o copy_to_user.o -GNU_LIBC_A := $(shell $(CC) $(KBUILD_CFLAGS) -print-file-name=libc.a) +GNU_LIBC_A = $(shell $(CC) $(KBUILD_CFLAGS) -print-file-name=libc.a) GNU_LIBC_A_OBJS := memchr.o memcpy.o memmove.o memset.o GNU_LIBC_A_OBJS += strchr.o strrchr.o GNU_LIBC_A_OBJS += rawmemchr.o # needed by strrchr.o -GNU_LIBGCC_A := $(shell $(CC) $(KBUILD_CFLAGS) -print-file-name=libgcc.a) +GNU_LIBGCC_A = $(shell $(CC) $(KBUILD_CFLAGS) -print-file-name=libgcc.a) GNU_LIBGCC_A_OBJS := _ashldi3.o _ashrdi3.o _lshrdi3.o GNU_LIBGCC_A_OBJS += _divsi3.o _modsi3.o _ucmpdi2.o _umodsi3.o _udivsi3.o
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 190/477 SoC: rsnd: add interrupt support for SSI BUSIF buffer
In reply to Greg Kroah-HartmanFrom: Yongbo Zhang <[email protected]>
[ Upstream commit 66c705d07d784fb6b4622c6e47b6acae357472db ]
SSI BUSIF buffer is possible to overflow or underflow, especially in a hypervisor environment. If there is no interrupt support, it will eventually lead to errors in pcm data.
This patch adds overflow and underflow interrupt support for SSI BUSIF buffer.
--- sound/soc/sh/rcar/gen.c | 8 +++ sound/soc/sh/rcar/rsnd.h | 9 +++ sound/soc/sh/rcar/ssi.c | 145 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 162 insertions(+)
sound/soc/sh/rcar/gen.c +8 -0
@@ -224,6 +224,14 @@ static int rsnd_gen2_probe(struct rsnd_priv *priv)RSND_GEN_S_REG (SSI_SYS_STATUS5 ,0x884 ),RSND_GEN_S_REG (SSI_SYS_STATUS6 ,0x888 ),RSND_GEN_S_REG (SSI_SYS_STATUS7 ,0x88c ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE0 ,0x850 ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE1 ,0x854 ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE2 ,0x858 ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE3 ,0x85c ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE4 ,0x890 ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE5 ,0x894 ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE6 ,0x898 ), +RSND_GEN_S_REG (SSI_SYS_INT_ENABLE7 ,0x89c ),RSND_GEN_S_REG (HDMI0_SEL ,0x9e0 ), RSND_GEN_S_REG(HDMI1_SEL, 0x9e4),
sound/soc/sh/rcar/rsnd.h +9 -0
@@ -189,6 +189,14 @@ enum rsnd_reg {SSI_SYS_STATUS5 ,SSI_SYS_STATUS6 ,SSI_SYS_STATUS7 , +SSI_SYS_INT_ENABLE0 , +SSI_SYS_INT_ENABLE1 , +SSI_SYS_INT_ENABLE2 , +SSI_SYS_INT_ENABLE3 , +SSI_SYS_INT_ENABLE4 , +SSI_SYS_INT_ENABLE5 , +SSI_SYS_INT_ENABLE6 , +SSI_SYS_INT_ENABLE7 ,HDMI0_SEL ,HDMI1_SEL , SSI9_BUSIF0_MODE,
@@ -237,6 +245,7 @@ enum rsnd_reg {#define SSI9_BUSIF_ADINR (i) (SSI9_BUSIF0_ADINR + (i))#define SSI9_BUSIF_DALIGN (i) (SSI9_BUSIF0_DALIGN + (i))#define SSI_SYS_STATUS (i) (SSI_SYS_STATUS0 + (i)) +#define SSI_SYS_INT_ENABLE (i) (SSI_SYS_INT_ENABLE0 + (i))struct rsnd_priv ;
sound/soc/sh/rcar/ssi.c +145 -0
193 lines not on this page · raw message
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 191/477 ASoC: ux500: mop500: Fix some refcounted resources issues
In reply to Greg Kroah-HartmanFrom: Christophe JAILLET <[email protected]>
[ Upstream commit 4e8748fcaeec073e3ba794871ce86c545e4f961f ]
There are 2 issues here:
- if one of the 'of_parse_phandle' fails, calling 'mop500_of_node_put()' is a no-op because the 'mop500_dai_links' structure has not been initialized yet, so the referenced are not decremented
- The reference stored in 'mop500_dai_links[i].codecs' is refcounted only once in the probe and must be decremented only once.
--- sound/soc/ux500/mop500.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-)
sound/soc/ux500/mop500.c +7 -4
@@ -63,10 +63,11 @@ static void mop500_of_node_put(void) {int i; -for (i =0 ; i <2 ; i++) { +for (i =0 ; i <2 ; i++)of_node_put (mop500_dai_links[i].cpus->of_node); -of_node_put (mop500_dai_links[i].codecs->of_node); - } + +/* Both links use the same codec, which is refcounted only once */ +of_node_put (mop500_dai_links[0 ].codecs->of_node); } static int mop500_of_probe(struct platform_device *pdev,
@@ -81,7 +82,9 @@ static int mop500_of_probe(struct platform_device *pdev,if (!(msp_np[0 ] && msp_np[1 ] && codec_np)) {dev_err (&pdev->dev,"Phandle missing or invalid\n" ); -mop500_of_node_put (); +for (i =0 ; i <2 ; i++) +of_node_put (msp_np[i]); +of_node_put (codec_np);return -EINVAL ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 192/477 ASoC: ti: omap-mcbsp: Fix an error handling path in asoc_mcbsp_probe()
In reply to Greg Kroah-HartmanFrom: Christophe JAILLET <[email protected]>
[ Upstream commit 03990fd58d2b7c8f7d53e514ba9b8749fac260f9 ]
If an error occurs after the call to 'omap_mcbsp_init()', the reference to 'mcbsp->fclk' must be decremented, as already done in the remove function.
This can be achieved easily by using the devm_ variant of 'clk_get()' when the reference is taken in 'omap_mcbsp_init()'
This fixes the leak in the probe and has the side effect to simplify both the error handling path of 'omap_mcbsp_init()' and the remove function.
--- sound/soc/ti/omap-mcbsp.c | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-)
sound/soc/ti/omap-mcbsp.c +2 -6
@@ -686,7 +686,7 @@ static int omap_mcbsp_init(struct platform_device *pdev) mcbsp->dma_data[1 ].addr =omap_mcbsp_dma_reg_params (mcbsp,SNDRV_PCM_STREAM_CAPTURE ); - mcbsp->fclk =clk_get (&pdev->dev,"fck" ); + mcbsp->fclk =devm_clk_get (&pdev->dev,"fck" );if (IS_ERR (mcbsp->fclk)) { ret =PTR_ERR (mcbsp->fclk);dev_err (mcbsp->dev,"unable to get fck: %d\n" , ret);
@@ -711,7 +711,7 @@ static int omap_mcbsp_init(struct platform_device *pdev)if (ret) {dev_err (mcbsp->dev,"Unable to create additional controls\n" ); - goto err_thres; +return ret; } }
@@ -724,8 +724,6 @@ static int omap_mcbsp_init(struct platform_device *pdev) err_st:if (mcbsp->pdata->buffer_size)sysfs_remove_group (&mcbsp->dev->kobj, &additional_attr_group); -err_thres: -clk_put (mcbsp->fclk);return ret; }
@@ -1442,8 +1440,6 @@ static int asoc_mcbsp_remove(struct platform_device *pdev)omap_mcbsp_st_cleanup (pdev); -clk_put (mcbsp->fclk); -return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 193/477 pinctrl: rockchip: fix memleak in rockchip_dt_node_to_map
In reply to Greg Kroah-HartmanFrom: Dafna Hirschfeld <[email protected]>
[ Upstream commit d7faa8ffb6be57bf8233a4b5a636d76b83c51ce7 ]
In function rockchip_dt_node_to_map, a new_map variable is allocated by:
new_map = devm_kcalloc(pctldev->dev, map_num, sizeof(*new_map),
GFP_KERNEL);
This uses devres and attaches new_map to the pinctrl driver. This cause a leak since new_map is not released when the probed driver is removed. Fix it by using kcalloc to allocate new_map and free it in rockchip_dt_free_map
--- drivers/pinctrl/pinctrl-rockchip.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/pinctrl/pinctrl-rockchip.c +4 -3
@@ -508,8 +508,8 @@ static int rockchip_dt_node_to_map(struct pinctrl_dev *pctldev, } map_num += grp->npins; - new_map =devm_kcalloc (pctldev->dev, map_num,sizeof (*new_map), -GFP_KERNEL ); + + new_map =kcalloc (map_num,sizeof (*new_map),GFP_KERNEL );if (!new_map)return -ENOMEM ;
@@ -519,7 +519,7 @@ static int rockchip_dt_node_to_map(struct pinctrl_dev *pctldev,/* create mux map */ parent =of_get_parent (np);if (!parent) { -devm_kfree (pctldev->dev, new_map); +kfree (new_map);return -EINVAL ; } new_map[0 ].type =PIN_MAP_TYPE_MUX_GROUP ;
@@ -546,6 +546,7 @@ static int rockchip_dt_node_to_map(struct pinctrl_dev *pctldev,static void rockchip_dt_free_map (struct pinctrl_dev *pctldev,struct pinctrl_map *map,unsigned num_maps) { +kfree (map); }static const struct pinctrl_ops rockchip_pctrl_ops = {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 194/477 remoteproc: qcom_q6v5_mss: Drop accesses to MPSS PERPH register space
In reply to Greg Kroah-HartmanFrom: Sibi Sankar <[email protected]>
[ Upstream commit a9fdc79d488623d36341f0f3d08f5aa1bedb9d53 ]
7C retail devices using MSA based boot will result in a fuse combination which will prevent accesses to MSS PERPH register space where the mpss clocks and halt-nav reside. So drop all accesses to the MPSS PERPH register space. Issuing HALT NAV request and turning on the mss clocks as part of SSR will no longer be required since the modem firmware will have the necessary fixes to ensure that there are no pending NAV DMA transactions.
--- drivers/remoteproc/qcom_q6v5_mss.c | 102 +++++------------------------ 1 file changed, 18 insertions(+), 84 deletions(-)
drivers/remoteproc/qcom_q6v5_mss.c +18 -84
@@ -69,13 +69,9 @@#define AXI_HALTREQ_REG 0x0#define AXI_HALTACK_REG 0x4#define AXI_IDLE_REG 0x8 -#define NAV_AXI_HALTREQ_BIT BIT(0) -#define NAV_AXI_HALTACK_BIT BIT(1) -#define NAV_AXI_IDLE_BIT BIT(2)#define AXI_GATING_VALID_OVERRIDE BIT(0)#define HALT_ACK_TIMEOUT_US 100000 -#define NAV_HALT_ACK_TIMEOUT_US 200/* QDSP6SS_RESET */ #define Q6SS_STOP_CORE BIT(0)
@@ -143,7 +139,7 @@ struct rproc_hexagon_res {int version;bool need_mem_protection;bool has_alt_reset; -bool has_halt_nav; +bool has_spare_reg; };struct q6v5 {
@@ -154,13 +150,11 @@ struct q6v5 {void __iomem *rmb_base;struct regmap *halt_map; -struct regmap *halt_nav_map;struct regmap *conn_map;u32 halt_q6;u32 halt_modem;u32 halt_nc; -u32 halt_nav;u32 conn_box;struct reset_control *mss_restart;
@@ -206,7 +200,7 @@ struct q6v5 {struct qcom_sysmon *sysmon;bool need_mem_protection;bool has_alt_reset; -bool has_halt_nav; +bool has_spare_reg;int mpss_perm;int mba_perm;const char *hexagon_mdt_image;
@@ -427,21 +421,19 @@ static int q6v5_reset_assert(struct q6v5 *qproc)reset_control_assert (qproc->pdc_reset); ret =reset_control_reset (qproc->mss_restart);reset_control_deassert (qproc->pdc_reset); - }else if (qproc->has_halt_nav) { + }else if (qproc->has_spare_reg) {/* * When the AXI pipeline is being reset with the Q6 modem partly * operational there is possibility of AXI valid signal to * glitch, leading to spurious transactions and Q6 hangs. A work * around is employed by asserting the AXI_GATING_VALID_OVERRIDE -* BIT before triggering Q6 MSS reset. Both the HALTREQ and -* AXI_GATING_VALID_OVERRIDE are withdrawn post MSS assert -* followed by a MSS deassert, while holding the PDC reset. +* BIT before triggering Q6 MSS reset. AXI_GATING_VALID_OVERRIDE +* is withdrawn post MSS assert followed by a MSS deassert, +* while holding the PDC reset. */ reset_control_assert (qproc->pdc_reset);regmap_update_bits (qproc->conn_map, qproc->conn_box,AXI_GATING_VALID_OVERRIDE ,1 ); -regmap_update_bits (qproc->halt_nav_map, qproc->halt_nav, -NAV_AXI_HALTREQ_BIT ,0 );reset_control_assert (qproc->mss_restart);reset_control_deassert (qproc->pdc_reset); regmap_update_bits(qproc->conn_map, qproc->conn_box,
@@ -464,7 +456,7 @@ static int q6v5_reset_deassert(struct q6v5 *qproc) ret =reset_control_reset (qproc->mss_restart);writel (0 , qproc->rmb_base +RMB_MBA_ALT_RESET );reset_control_deassert (qproc->pdc_reset); - }else if (qproc->has_halt_nav) { + }else if (qproc->has_spare_reg) { ret =reset_control_reset (qproc->mss_restart); }else { ret =reset_control_deassert (qproc->mss_restart);
@@ -761,32 +753,6 @@ static void q6v5proc_halt_axi_port(struct q6v5 *qproc,regmap_write (halt_map, offset +AXI_HALTREQ_REG ,0 ); } -static void q6v5proc_halt_nav_axi_port (struct q6v5 *qproc, -struct regmap *halt_map, -u32 offset) -{ -unsigned int val; -int ret; - -/* Check if we're already idle */ - ret =regmap_read (halt_map, offset, &val); -if (!ret && (val &NAV_AXI_IDLE_BIT )) -return ; - -/* Assert halt request */ -regmap_update_bits (halt_map, offset,NAV_AXI_HALTREQ_BIT , -NAV_AXI_HALTREQ_BIT ); - -/* Wait for halt ack*/ -regmap_read_poll_timeout (halt_map, offset, val, - (val &NAV_AXI_HALTACK_BIT ), -5 ,NAV_HALT_ACK_TIMEOUT_US ); - - ret =regmap_read (halt_map, offset, &val); -if (ret || !(val &NAV_AXI_IDLE_BIT )) -dev_err (qproc->dev,"port failed halt\n" ); -} -static int q6v5_mpss_init_image (struct q6v5 *qproc,const struct firmware *fw) {unsigned long dma_attrs =DMA_ATTR_FORCE_CONTIGUOUS ;
@@ -951,9 +917,6 @@ static int q6v5_mba_load(struct q6v5 *qproc) halt_axi_ports:q6v5proc_halt_axi_port (qproc, qproc->halt_map, qproc->halt_q6);q6v5proc_halt_axi_port (qproc, qproc->halt_map, qproc->halt_modem); -if (qproc->has_halt_nav) -q6v5proc_halt_nav_axi_port (qproc, qproc->halt_nav_map, - qproc->halt_nav);q6v5proc_halt_axi_port (qproc, qproc->halt_map, qproc->halt_nc); reclaim_mba:
@@ -1001,9 +964,6 @@ static void q6v5_mba_reclaim(struct q6v5 *qproc)q6v5proc_halt_axi_port (qproc, qproc->halt_map, qproc->halt_q6);q6v5proc_halt_axi_port (qproc, qproc->halt_map, qproc->halt_modem); -if (qproc->has_halt_nav) -q6v5proc_halt_nav_axi_port (qproc, qproc->halt_nav_map, - qproc->halt_nav);q6v5proc_halt_axi_port (qproc, qproc->halt_map, qproc->halt_nc);if (qproc->version ==MSS_MSM8996 ) {/*
@@ -1447,36 +1407,12 @@ static int q6v5_init_mem(struct q6v5 *qproc, struct platform_device *pdev) qproc->halt_modem = args.args[1 ]; qproc->halt_nc = args.args[2 ]; -if (qproc->has_halt_nav) { -struct platform_device *nav_pdev; - +if (qproc->has_spare_reg) { ret =of_parse_phandle_with_fixed_args (pdev->dev.of_node, -"qcom,halt-nav-regs" , +"qcom,spare-regs" ,1 ,0 , &args);if (ret <0 ) { -dev_err (&pdev->dev,"failed to parse halt-nav-regs\n" ); -return -EINVAL ; - } - - nav_pdev =of_find_device_by_node (args.np); -of_node_put (args.np); -if (!nav_pdev) { -dev_err (&pdev->dev,"failed to get mss clock device\n" ); -return -EPROBE_DEFER ; - } - - qproc->halt_nav_map =dev_get_regmap (&nav_pdev->dev,NULL ); -if (!qproc->halt_nav_map) { -dev_err (&pdev->dev,"failed to get map from device\n" ); -return -EINVAL ; - } - qproc->halt_nav = args.args[0 ]; - - ret =of_parse_phandle_with_fixed_args (pdev->dev.of_node, -"qcom,halt-nav-regs" , -1 ,1 , &args); -if (ret <0 ) { -dev_err (&pdev->dev,"failed to parse halt-nav-regs\n" ); +dev_err (&pdev->dev,"failed to parse spare-regs\n" );return -EINVAL ; }
@@ -1562,7 +1498,7 @@ static int q6v5_init_reset(struct q6v5 *qproc)return PTR_ERR (qproc->mss_restart); } -if (qproc->has_alt_reset || qproc->has_halt_nav) { +if (qproc->has_alt_reset || qproc->has_spare_reg) { qproc->pdc_reset =devm_reset_control_get_exclusive (qproc->dev,"pdc_reset" );if (IS_ERR (qproc->pdc_reset)) {
@@ -1688,7 +1624,7 @@ static int q6v5_probe(struct platform_device *pdev)platform_set_drvdata (pdev, qproc); - qproc->has_halt_nav = desc->has_halt_nav; + qproc->has_spare_reg = desc->has_spare_reg; ret =q6v5_init_mem (qproc, pdev);if (ret) goto free_rproc;
@@ -1837,8 +1773,6 @@ static const struct rproc_hexagon_res sc7180_mss = { .active_clk_names = (char*[]){"mnoc_axi" ,"nav" , -"mss_nav" , -"mss_crypto" ,NULL }, .active_pd_names = (char *[]){
@@ -1853,7 +1787,7 @@ static const struct rproc_hexagon_res sc7180_mss = { }, .need_mem_protection = true, .has_alt_reset = false, - .has_halt_nav = true, + .has_spare_reg = true, .version = MSS_SC7180, };
@@ -1888,7 +1822,7 @@ static const struct rproc_hexagon_res sdm845_mss = { }, .need_mem_protection = true, .has_alt_reset = true, - .has_halt_nav = false, + .has_spare_reg = false, .version = MSS_SDM845, };
@@ -1915,7 +1849,7 @@ static const struct rproc_hexagon_res msm8998_mss = { }, .need_mem_protection = true, .has_alt_reset = false, - .has_halt_nav = false, + .has_spare_reg = false, .version = MSS_MSM8998, };
@@ -1945,7 +1879,7 @@ static const struct rproc_hexagon_res msm8996_mss = { }, .need_mem_protection = true, .has_alt_reset = false, - .has_halt_nav = false, + .has_spare_reg = false, .version = MSS_MSM8996, };
@@ -1978,7 +1912,7 @@ static const struct rproc_hexagon_res msm8916_mss = { }, .need_mem_protection = false, .has_alt_reset = false, - .has_halt_nav = false, + .has_spare_reg = false, .version = MSS_MSM8916, };
@@ -2019,7 +1953,7 @@ static const struct rproc_hexagon_res msm8974_mss = { }, .need_mem_protection = false, .has_alt_reset = false, - .has_halt_nav = false, + .has_spare_reg = false, .version = MSS_MSM8974, };
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 195/477 dlm: remove BUG() before panic()
In reply to Greg Kroah-HartmanFrom: Arnd Bergmann <[email protected]>
[ Upstream commit fe204591cc9480347af7d2d6029b24a62e449486 ]
Building a kernel with clang sometimes fails with an objtool error in dlm:
fs/dlm/lock.o: warning: objtool: revert_lock_pc()+0xbd: can't find jump dest instruction at .text+0xd7fc
The problem is that BUG() never returns and the compiler knows that anything after it is unreachable, however the panic still emits some code that does not get fully eliminated.
Having both BUG() and panic() is really pointless as the BUG() kills the current process and the subsequent panic() never hits. In most cases, we probably don't really want either and should replace the DLM_ASSERT() statements with WARN_ON(), as has been done for some of them.
Remove the BUG() here so the user at least sees the panic message and we can reliably build randconfig kernels.
--- fs/dlm/dlm_internal.h | 1 - 1 file changed, 1 deletion(-)
fs/dlm/dlm_internal.h +0 -1
@@ -97,7 +97,6 @@ do { \ __LINE__, __FILE__, #x, jiffies); \ {do} \ printk("\n"); \ - BUG(); \ panic("DLM: Record message above and reboot.\n"); \ } \ }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 196/477 phy: ti: j721e-wiz: Fix some error return code in wiz_probe()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit e2ae8bca494481a9f38fcd1d52943ac04e654745 ]
Fix to return negative error code from some error handling cases instead of 0, as done elsewhere in this function.
--- drivers/phy/ti/phy-j721e-wiz.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/phy/ti/phy-j721e-wiz.c +5 -1
@@ -794,8 +794,10 @@ static int wiz_probe(struct platform_device *pdev) } base =devm_ioremap (dev, res.start,resource_size (&res)); -if (!base) +if (!base) { + ret = -ENOMEM ; goto err_addr_to_resource; + } regmap =devm_regmap_init_mmio (dev, base, &wiz_regmap_config);if (IS_ERR (regmap)) {
@@ -812,6 +814,7 @@ static int wiz_probe(struct platform_device *pdev)if (num_lanes >WIZ_MAX_LANES ) {dev_err (dev,"Cannot support %d lanes\n" , num_lanes); + ret = -ENODEV ; goto err_addr_to_resource; }
@@ -897,6 +900,7 @@ static int wiz_probe(struct platform_device *pdev) serdes_pdev =of_platform_device_create (child_node,NULL , dev);if (!serdes_pdev) {dev_WARN (dev,"Unable to create SERDES platform device\n" ); + ret = -ENOMEM ; goto err_pdev_create; } wiz->serdes_pdev = serdes_pdev;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 197/477 USB: ohci-sm501: fix error return code in ohci_hcd_sm501_drv_probe()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit b919e077cccfbb77beb98809568b2fb0b4d113ec ]
Fix to return a negative error code from the error handling case instead of 0, as done elsewhere in this function.
--- drivers/usb/host/ohci-sm501.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/usb/host/ohci-sm501.c +4 -3
@@ -157,9 +157,10 @@ static int ohci_hcd_sm501_drv_probe(struct platform_device *pdev)* the call to usb_hcd_setup_local_mem() below does just that. */ -if (usb_hcd_setup_local_mem (hcd, mem->start, - mem->start - mem->parent->start, -resource_size (mem)) <0 ) + retval =usb_hcd_setup_local_mem (hcd, mem->start, + mem->start - mem->parent->start, +resource_size (mem)); +if (retval <0 ) goto err5; retval =usb_add_hcd (hcd, irq,IRQF_SHARED );if (retval)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 198/477 arm64: dts: qcom: db820c: Fix invalid pm8994 supplies
In reply to Greg Kroah-HartmanFrom: Bjorn Andersson <[email protected]>
[ Upstream commit 1cacdf5d3bb9644ac7b9339c611ac5b9dd90d09d ]
It's uncertain where the "vreg_s8a_l3a_input" comes from, but the supply for VDD_L3_L11 on PM8994 should be VREG_S3A_1P3, so correct this - and drop the vreg_s8a_l3a_input.
--- arch/arm64/boot/dts/qcom/apq8096-db820c.dtsi | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-)
arch/arm64/boot/dts/qcom/apq8096-db820c.dtsi +2 -12
@@ -117,16 +117,6 @@ regulator-max-microvolt = <3700000>; }; - vreg_s8a_l3a_input: vreg-s8a-l3a-input { - compatible = "regulator-fixed"; - regulator-name = "vreg_s8a_l3a_input"; - regulator-always-on; - regulator-boot-on; - - regulator-min-microvolt = <0>; - regulator-max-microvolt = <0>; - }; - wlan_en: wlan-en-1-8v { pinctrl-names = "default"; pinctrl-0 = <&wlan_en_gpios>;
@@ -705,14 +695,14 @@ vdd_s11-supply = <&vph_pwr>; vdd_s12-supply = <&vph_pwr>; vdd_l2_l26_l28-supply = <&vreg_s3a_1p3>; - vdd_l3_l11-supply = <&vreg_s8a_l3a_input>; + vdd_l3_l11-supply = <&vreg_s3a_1p3>; vdd_l4_l27_l31-supply = <&vreg_s3a_1p3>; vdd_l5_l7-supply = <&vreg_s5a_2p15>; vdd_l6_l12_l32-supply = <&vreg_s5a_2p15>; vdd_l8_l16_l30-supply = <&vph_pwr>; vdd_l14_l15-supply = <&vreg_s5a_2p15>; vdd_l25-supply = <&vreg_s3a_1p3>; - vdd_lvs1_2-supply = <&vreg_s4a_1p8>; + vdd_lvs1_lvs2-supply = <&vreg_s4a_1p8>; vreg_s3a_1p3: s3 { regulator-name = "vreg_s3a_1p3";
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 199/477 arm64: dts: qcom: c630: Add WiFi node
In reply to Greg Kroah-HartmanFrom: Bjorn Andersson <[email protected]>
[ Upstream commit 3fb298d0b2f2a1d47d53806d4ddf8f4ae83353cc ]
Specify regulators and enable the &wifi node. The firmware uses the 8 bit version of the host capability message, so specify this quirk.
--- arch/arm64/boot/dts/qcom/sdm850-lenovo-yoga-c630.dts | 11 +++++++++++ 1 file changed, 11 insertions(+)
arch/arm64/boot/dts/qcom/sdm850-lenovo-yoga-c630.dts +11 -0
@@ -577,3 +577,14 @@ }; }; }; + +&wifi { + status = "okay"; + + vdd-0.8-cx-mx-supply = <&vreg_l5a_0p8>; + vdd-1.8-xo-supply = <&vreg_l7a_1p8>; + vdd-1.3-rfa-supply = <&vreg_l17a_1p3>; + vdd-3.3-ch0-supply = <&vreg_l25a_3p3>; + + qcom,snoc-host-cap-8bit-quirk; +};
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 200/477 clk: ti: composite: fix memory leak
In reply to Greg Kroah-HartmanFrom: Tero Kristo <[email protected]>
[ Upstream commit c7c1cbbc9217ebb5601b88d138d4a5358548de9d ]
The parent_names is never released for a component clock definition, causing some memory leak. Fix by releasing it once it is no longer needed.
--- drivers/clk/ti/composite.c | 1 + 1 file changed, 1 insertion(+)
drivers/clk/ti/composite.c +1 -0
@@ -196,6 +196,7 @@ cleanup:if (!cclk->comp_clks[i])continue ;list_del (&cclk->comp_clks[i]->link); +kfree (cclk->comp_clks[i]->parent_names);kfree (cclk->comp_clks[i]); }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 201/477 PCI: Fix pci_register_host_bridge() device_register() error handling
In reply to Greg Kroah-HartmanFrom: Rob Herring <[email protected]>
[ Upstream commit 1b54ae8327a4d630111c8d88ba7906483ec6010b ]
If device_register() has an error, we should bail out of pci_register_host_bridge() rather than continuing on.
--- drivers/pci/probe.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
drivers/pci/probe.c +3 -2
@@ -909,9 +909,10 @@ static int pci_register_host_bridge(struct pci_host_bridge *bridge) goto free; err =device_register (&bridge->dev); -if (err) +if (err) {put_device (&bridge->dev); - + goto free; + } bus->bridge =get_device (&bridge->dev);device_enable_async_suspend (bus->bridge);pci_set_bus_of_node (bus);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 202/477 powerpc/64: Dont initialise init_task->thread.regs
In reply to Greg Kroah-HartmanFrom: Michael Ellerman <[email protected]>
[ Upstream commit 7ffa8b7dc11752827329e4e84a574ea6aaf24716 ]
Aneesh increased the size of struct pt_regs by 16 bytes and started seeing this WARN_ON:
smp: Bringing up secondary CPUs ...
------------[ cut here ]------------ WARNING: CPU: 0 PID: 0 at arch/powerpc/kernel/process.c:455 giveup_all+0xb4/0x110 Modules linked in: CPU: 0 PID: 0 Comm: swapper/0 Not tainted 5.7.0-rc2-gcc-8.2.0-1.g8f6a41f-default+ #318 NIP: c00000000001a2b4 LR: c00000000001a29c CTR: c0000000031d0000 REGS: c0000000026d3980 TRAP: 0700 Not tainted (5.7.0-rc2-gcc-8.2.0-1.g8f6a41f-default+) MSR: 800000000282b033 <SF,VEC,VSX,EE,FP,ME,IR,DR,RI,LE> CR: 48048224 XER: 00000000 CFAR: c000000000019cc8 IRQMASK: 1 GPR00: c00000000001a264 c0000000026d3c20 c0000000026d7200 800000000280b033 GPR04: 0000000000000001 0000000000000000 0000000000000077 30206d7372203164 GPR08: 0000000000002000 0000000002002000 800000000280b033 3230303030303030 GPR12: 0000000000008800 c0000000031d0000 0000000000800050 0000000002000066 GPR16: 000000000309a1a0 000000000309a4b0 000000000309a2d8 000000000309a890 GPR20: 00000000030d0098 c00000000264da40 00000000fd620000 c0000000ff798080 GPR24: c00000000264edf0 c0000001007469f0 00000000fd620000 c0000000020e5e90 GPR28: c00000000264edf0 c00000000264d200 000000001db60000 c00000000264d200 NIP [c00000000001a2b4] giveup_all+0xb4/0x110 LR [c00000000001a29c] giveup_all+0x9c/0x110 Call Trace: [c0000000026d3c20] [c00000000001a264] giveup_all+0x64/0x110 (unreliable) [c0000000026d3c90] [c00000000001ae34] __switch_to+0x104/0x480 [c0000000026d3cf0] [c000000000e0b8a0] __schedule+0x320/0x970 [c0000000026d3dd0] [c000000000e0c518] schedule_idle+0x38/0x70 [c0000000026d3df0] [c00000000019c7c8] do_idle+0x248/0x3f0 [c0000000026d3e70] [c00000000019cbb8] cpu_startup_entry+0x38/0x40 [c0000000026d3ea0] [c000000000011bb0] rest_init+0xe0/0xf8 [c0000000026d3ed0] [c000000002004820] start_kernel+0x990/0x9e0 [c0000000026d3f90] [c00000000000c49c] start_here_common+0x1c/0x400
Which was unexpected. The warning is checking the thread.regs->msr value of the task we are switching from:
usermsr = tsk->thread.regs->msr; ... WARN_ON((usermsr & MSR_VSX) && !((usermsr & MSR_FP) && (usermsr & MSR_VEC)));
ie. if MSR_VSX is set then both of MSR_FP and MSR_VEC are also set.
Dumping tsk->thread.regs->msr we see that it's: 0x1db60000
Which is not a normal looking MSR, in fact the only valid bit is MSR_VSX, all the other bits are reserved in the current definition of the MSR.
We can see from the oops that it was swapper/0 that we were switching from when we hit the warning, ie. init_task. So its thread.regs points to the base (high addresses) in init_stack.
Dumping the content of init_task->thread.regs, with the members of pt_regs annotated (the 16 bytes larger version), we see:
0000000000000000 c000000002780080 gpr[0] gpr[1] 0000000000000000 c000000002666008 gpr[2] gpr[3] c0000000026d3ed0 0000000000000078 gpr[4] gpr[5] c000000000011b68 c000000002780080 gpr[6] gpr[7] 0000000000000000 0000000000000000 gpr[8] gpr[9] c0000000026d3f90 0000800000002200 gpr[10] gpr[11] c000000002004820 c0000000026d7200 gpr[12] gpr[13] 000000001db60000 c0000000010aabe8 gpr[14] gpr[15] c0000000010aabe8 c0000000010aabe8 gpr[16] gpr[17] c00000000294d598 0000000000000000 gpr[18] gpr[19] 0000000000000000 0000000000001ff8 gpr[20] gpr[21] 0000000000000000 c00000000206d608 gpr[22] gpr[23] c00000000278e0cc 0000000000000000 gpr[24] gpr[25] 000000002fff0000 c000000000000000 gpr[26] gpr[27] 0000000002000000 0000000000000028 gpr[28] gpr[29] 000000001db60000 0000000004750000 gpr[30] gpr[31] 0000000002000000 000000001db60000 nip msr 0000000000000000 0000000000000000 orig_r3 ctr c00000000000c49c 0000000000000000 link xer 0000000000000000 0000000000000000 ccr softe 0000000000000000 0000000000000000 trap dar 0000000000000000 0000000000000000 dsisr result 0000000000000000 0000000000000000 ppr kuap 0000000000000000 0000000000000000 pad[2] pad[3]
This looks suspiciously like stack frames, not a pt_regs. If we look closely we can see return addresses from the stack trace above, c000000002004820 (start_kernel) and c00000000000c49c (start_here_common).
init_task->thread.regs is setup at build time in processor.h:
#define INIT_THREAD { \
.ksp = INIT_SP, \
.regs = (struct pt_regs *)INIT_SP - 1, /* XXX bogus, I think */ \The early boot code where we setup the initial stack is:
LOAD_REG_ADDR(r3,init_thread_union)
/* set up a stack pointer */
LOAD_REG_IMMEDIATE(r1,THREAD_SIZE)
add r1,r3,r1
li r0,0
stdu r0,-STACK_FRAME_OVERHEAD(r1)
Which creates a stack frame of size 112 bytes (STACK_FRAME_OVERHEAD). Which is far too small to contain a pt_regs.
So the result is init_task->thread.regs is pointing at some stack frames on the init stack, not at a pt_regs.
We have gotten away with this for so long because with pt_regs at its current size the MSR happens to point into the first frame, at a location that is not written to by the early asm. With the 16 byte expansion the MSR falls into the second frame, which is used by the compiler, and collides with a saved register that tends to be non-zero.
As far as I can see this has been wrong since the original merge of 64-bit ppc support, back in 2002.
Conceptually swapper should have no regs, it never entered from userspace, and in fact that's what we do on 32-bit. It's also presumably what the "bogus" comment is referring to.
So I think the right fix is to just not-initialise regs at all. I'm slightly worried this will break some code that isn't prepared for a NULL regs, but we'll have to see.
Remove the comment in head_64.S which refers to us setting up the regs (even though we never did), and is otherwise not really accurate any more.
--- arch/powerpc/include/asm/processor.h | 1 - arch/powerpc/kernel/head_64.S | 9 +-------- 2 files changed, 1 insertion(+), 9 deletions(-)
arch/powerpc/include/asm/processor.h +0 -1
@@ -301,7 +301,6 @@ struct thread_struct {#else #define INIT_THREAD { \ .ksp = INIT_SP, \ - .regs = (struct pt_regs *)INIT_SP - 1, /* XXX bogus, I think */ \ .addr_limit = KERNEL_DS, \ .fpexc_mode = 0, \ .fscr = FSCR_TAR | FSCR_EBB \
arch/powerpc/kernel/head_64.S +1 -8
@@ -947,15 +947,8 @@ start_here_multiplatform: std r0,0(r4) #endif - /* The following gets the stack set up with the regs */ - /* pointing to the real addr of the kernel stack. This is */ - /* all done to support the C function call below which sets */ - /* up the htab. This is done because we have relocated the */ - /* kernel but are still running in real mode. */ - - LOAD_REG_ADDR(r3,init_thread_union) - /* set up a stack pointer */ + LOAD_REG_ADDR(r3,init_thread_union) LOAD_REG_IMMEDIATE(r1,THREAD_SIZE) add r1,r3,r1 li r0,0
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 203/477 tty: n_gsm: Fix SOF skipping
In reply to Greg Kroah-HartmanFrom: Gregory CLEMENT <[email protected]>
[ Upstream commit 84d6f81c1fb58b56eba81ff0a36cf31946064b40 ]
For at least some modems like the TELIT LE910, skipping SOF makes transfers blocking indefinitely after a short amount of data transferred.
Given the small improvement provided by skipping the SOF (just one byte on about 100 bytes), it seems better to completely remove this "feature" than make it optional.
--- drivers/tty/n_gsm.c | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-)
drivers/tty/n_gsm.c +1 -7
@@ -677,7 +677,6 @@ static void gsm_data_kick(struct gsm_mux *gsm) {struct gsm_msg *msg, *nmsg;int len; -int skip_sof =0 ;list_for_each_entry_safe (msg, nmsg, &gsm->tx_list, list) {if (gsm->constipated && msg->addr)
@@ -699,15 +698,10 @@ static void gsm_data_kick(struct gsm_mux *gsm)print_hex_dump_bytes ("gsm_data_kick: " ,DUMP_PREFIX_OFFSET , gsm->txframe, len); - -if (gsm->output (gsm, gsm->txframe + skip_sof, - len - skip_sof) <0 ) +if (gsm->output (gsm, gsm->txframe, len) <0 )break ;/* FIXME: Can eliminate one SOF in many more cases */ gsm->tx_bytes -= msg->len; -/* For a burst of frames skip the extra SOF within the -burst */ - skip_sof =1 ;list_del (&msg->list);kfree (msg);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 204/477 tty: n_gsm: Fix waking up upper tty layer when room available
In reply to Greg Kroah-HartmanFrom: Gregory CLEMENT <[email protected]>
[ Upstream commit 01dbb362f0a114fbce19c8abe4cd6f4710e934d5 ]
Warn the upper layer when n_gms is ready to receive data again. Without this the associated virtual tty remains blocked indefinitely.
--- drivers/tty/n_gsm.c | 26 ++++++++++++++++++++++---- 1 file changed, 22 insertions(+), 4 deletions(-)
drivers/tty/n_gsm.c +22 -4
@@ -673,7 +673,7 @@ static struct gsm_msg *gsm_data_alloc(struct gsm_mux *gsm, u8 addr, int len,* FIXME: lock against link layer control transmissions */ -static void gsm_data_kick (struct gsm_mux *gsm) +static void gsm_data_kick (struct gsm_mux *gsm,struct gsm_dlci *dlci) {struct gsm_msg *msg, *nmsg;int len;
@@ -705,6 +705,24 @@ static void gsm_data_kick(struct gsm_mux *gsm)list_del (&msg->list);kfree (msg); + +if (dlci) { +tty_port_tty_wakeup (&dlci->port); + }else { +int i =0 ; + +for (i =0 ; i <NUM_DLCI ; i++) { +struct gsm_dlci *dlci; + + dlci = gsm->dlci[i]; +if (dlci ==NULL ) { + i++; +continue ; + } + +tty_port_tty_wakeup (&dlci->port); + } + } } }
@@ -756,7 +774,7 @@ static void __gsm_data_queue(struct gsm_dlci *dlci, struct gsm_msg *msg)/* Add to the actual output queue */ list_add_tail (&msg->list, &gsm->tx_list); gsm->tx_bytes += msg->len; -gsm_data_kick (gsm); +gsm_data_kick (gsm, dlci); }/**
@@ -1217,7 +1235,7 @@ static void gsm_control_message(struct gsm_mux *gsm, unsigned int command,gsm_control_reply (gsm,CMD_FCON ,NULL ,0 );/* Kick the link in case it is idling */ spin_lock_irqsave (&gsm->tx_lock, flags); -gsm_data_kick (gsm); +gsm_data_kick (gsm,NULL );spin_unlock_irqrestore (&gsm->tx_lock, flags);break ;case CMD_FCOFF :
@@ -2539,7 +2557,7 @@ static void gsmld_write_wakeup(struct tty_struct *tty)/* Queue poll */ clear_bit (TTY_DO_WRITE_WAKEUP , &tty->flags);spin_lock_irqsave (&gsm->tx_lock, flags); -gsm_data_kick (gsm); +gsm_data_kick (gsm,NULL );if (gsm->tx_bytes <TX_THRESH_LO ) {gsm_dlci_data_sweep (gsm); }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 205/477 staging: wfx: fix value of scan timeout
In reply to Greg Kroah-HartmanFrom: Jérôme Pouiller <[email protected]>
[ Upstream commit 6598b12d6635e8e3060863b84c04e472546ee126 ]
Before to start the scan request, the firmware signals (with a null frame) to the AP it won't be able to receive data. This frame can be long to send: up to 512TU. The current calculus of the scan timeout does not take into account this delay.
--- drivers/staging/wfx/hif_tx.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/staging/wfx/hif_tx.c +1 -1
@@ -268,7 +268,7 @@ int hif_scan(struct wfx_vif *wvif, struct cfg80211_scan_request *req, tmo_chan_bg =le32_to_cpu (body->max_channel_time) *USEC_PER_TU ; tmo_chan_fg =512 *USEC_PER_TU + body->probe_delay; tmo_chan_fg *= body->num_of_probe_requests; - tmo = chan_num *max (tmo_chan_bg, tmo_chan_fg); + tmo = chan_num *max (tmo_chan_bg, tmo_chan_fg) +512 *USEC_PER_TU ;wfx_fill_header (hif, wvif->id,HIF_REQ_ID_START_SCAN , buf_len); ret =wfx_cmd_send (wvif->wdev, hif,NULL ,0 , false);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 206/477 ALSA: usb-audio: fixing upper volume limit for RME Babyface Pro routing crosspoints
In reply to Greg Kroah-HartmanFrom: Thomas Ebeling <[email protected]>
[ Upstream commit 47b4f5f5b65680fbef7a7a9a4796b35f38a6e43e ]
In my initial patch, these were set too low.
--- sound/usb/mixer_quirks.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
sound/usb/mixer_quirks.c +2 -2
@@ -2191,7 +2191,7 @@ static int snd_rme_controls_create(struct usb_mixer_interface *mixer)* These devices exposes a couple of DSP functions via request to EP0. * Switches are available via control registers, while routing is controlled * by controlling the volume on each possible crossing point. -* Volume control is linear, from -inf (dec. 0) to +6dB (dec. 46341) with +* Volume control is linear, from -inf (dec. 0) to +6dB (dec. 65536) with * 0dB being at dec. 32768. */ enum {
@@ -2220,7 +2220,7 @@ enum {#define SND_BBFPRO_MIXER_VAL_MASK 0x3ffff#define SND_BBFPRO_MIXER_VAL_SHIFT 9#define SND_BBFPRO_MIXER_VAL_MIN 0 // -inf -#define SND_BBFPRO_MIXER_VAL_MAX 46341 // +6dB +#define SND_BBFPRO_MIXER_VAL_MAX 65536 // +6dB#define SND_BBFPRO_USBREQ_CTL_REG1 0x10#define SND_BBFPRO_USBREQ_CTL_REG2 0x17
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 207/477 ALSA: usb-audio: Add duplex sound support for USB devices using implicit feedback
In reply to Greg Kroah-HartmanFrom: Erwin Burema <[email protected]>
[ Upstream commit 10ce77e4817fef99e1166be7e6685a80c63bf77f ]
For USB sound devices using implicit feedback the endpoint used for this feedback should be able to be opened twice, once for required feedback and second time for audio data. This way these devices can be put in duplex audio mode. Since this only works if the settings of the endpoint don't change a check is included for this.
This fixes bug 207023 ("MOTU M2 regression on duplex audio") and should also fix bug 103751 ("M-Audio Fast Track Ultra usb audio device will not operate full-duplex")
--- sound/usb/card.h | 1 + sound/usb/endpoint.c | 195 ++++++++++++++++++++++++++++++++++++++++++- sound/usb/pcm.c | 5 ++ 3 files changed, 197 insertions(+), 4 deletions(-)
sound/usb/card.h +1 -0
@@ -108,6 +108,7 @@ struct snd_usb_endpoint {int iface, altsetting;int skip_packets;/* quirks for devices to ignore the first n packets in a stream */ +bool is_implicit_feedback;/* This endpoint is used as implicit feedback */ spinlock_t lock;struct list_head list;
sound/usb/endpoint.c +191 -4
213 lines not on this page · raw message
sound/usb/pcm.c +5 -0
@@ -404,6 +404,8 @@ add_sync_ep:if (!subs->sync_endpoint)return -EINVAL ; + subs->sync_endpoint->is_implicit_feedback =1 ; + subs->data_endpoint->sync_master = subs->sync_endpoint;return 1 ;
@@ -502,12 +504,15 @@ static int set_sync_endpoint(struct snd_usb_substream *subs, implicit_fb ?SND_USB_ENDPOINT_TYPE_DATA : SND_USB_ENDPOINT_TYPE_SYNC); +if (!subs->sync_endpoint) {if (is_playback && attr ==USB_ENDPOINT_SYNC_NONE )return 0 ;return -EINVAL ; } + subs->sync_endpoint->is_implicit_feedback = implicit_fb; + subs->data_endpoint->sync_master = subs->sync_endpoint;return 0 ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 208/477 HID: Add quirks for Trust Panora Graphic Tablet
In reply to Greg Kroah-HartmanFrom: Cristian Klein <[email protected]>
[ Upstream commit fb68ada81e65d593b51544fa43c284322107a742 ]
The Trust Panora Graphic Tablet has two interfaces. Interface zero reports pen movement, pen pressure and pen buttons. Interface one reports tablet buttons and tablet scroll. Both use the mouse protocol.
Without these quirks, libinput gets confused about what device it talks to.
For completeness, here is the usbhid-dump:
``` $ sudo usbhid-dump -d 145f:0212 003:013:001:DESCRIPTOR 1588949402.559961 05 0D 09 01 A1 01 85 07 A1 02 09 00 75 08 95 07 81 02 C0 C0 09 0E A1 01 85 05 09 23 A1 02 09 52 09 53 25 0A 75 08 95 02 B1 02 C0 C0 05 0C 09 36 A1 00 85 06 05 09 19 01 29 20 15 00 25 01 95 20 75 01 81 02 C0 003:013:000:DESCRIPTOR 1588949402.563942 05 01 09 02 A1 01 85 08 09 01 A1 00 05 09 19 01 29 03 15 00 25 01 95 03 75 01 81 02 95 05 81 01 05 01 09 30 09 31 09 38 09 00 15 81 25 7F 75 08 95 04 81 06 C0 C0 05 01 09 02 A1 01 85 09 09 01 A1 00 05 09 19 01 29 03 15 00 25 01 95 03 75 01 81 02 95 05 81 01 05 01 09 30 09 31 26 FF 7F 95 02 75 10 81 02 05 0D 09 30 26 FF 03 95 01 75 10 81 02 C0 C0 05 01 09 00 A1 01 85 04 A1 00 26 FF 00 09 00 75 08 95 07 B1 02 C0 C0 ```
--- drivers/hid/hid-ids.h | 3 +++ drivers/hid/hid-quirks.c | 1 + 2 files changed, 4 insertions(+)
drivers/hid/hid-ids.h +3 -0
@@ -1157,6 +1157,9 @@#define USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8882 0x8882#define USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8883 0x8883 +#define USB_VENDOR_ID_TRUST 0x145f +#define USB_DEVICE_ID_TRUST_PANORA_TABLET 0x0212 +#define USB_VENDOR_ID_TURBOX 0x062a#define USB_DEVICE_ID_TURBOX_KEYBOARD 0x0201#define USB_DEVICE_ID_ASUS_MD_5110 0x5110
drivers/hid/hid-quirks.c +1 -0
@@ -168,6 +168,7 @@ static const struct hid_device_id hid_quirks[] = { { HID_USB_DEVICE(USB_VENDOR_ID_TOUCHPACK, USB_DEVICE_ID_TOUCHPACK_RTS), HID_QUIRK_MULTI_INPUT }, { HID_USB_DEVICE(USB_VENDOR_ID_TPV, USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8882), HID_QUIRK_NOGET }, { HID_USB_DEVICE(USB_VENDOR_ID_TPV, USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8883), HID_QUIRK_NOGET }, + { HID_USB_DEVICE(USB_VENDOR_ID_TRUST, USB_DEVICE_ID_TRUST_PANORA_TABLET), HID_QUIRK_MULTI_INPUT | HID_QUIRK_HIDINPUT_FORCE }, { HID_USB_DEVICE(USB_VENDOR_ID_TURBOX, USB_DEVICE_ID_TURBOX_KEYBOARD), HID_QUIRK_NOGET }, { HID_USB_DEVICE(USB_VENDOR_ID_UCLOGIC, USB_DEVICE_ID_UCLOGIC_TABLET_KNA5), HID_QUIRK_MULTI_INPUT }, { HID_USB_DEVICE(USB_VENDOR_ID_UCLOGIC, USB_DEVICE_ID_UCLOGIC_TABLET_TWA60), HID_QUIRK_MULTI_INPUT },
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 209/477 PCI/PM: Assume ports without DLL Link Active train links in 100 ms
In reply to Greg Kroah-HartmanFrom: Mika Westerberg <[email protected]>
[ Upstream commit ec411e02b7a2e785a4ed9ed283207cd14f48699d ]
Kai-Heng Feng reported that it takes a long time (> 1 s) to resume Thunderbolt-connected devices from both runtime suspend and system sleep (s2idle).
This was because some Downstream Ports that support > 5 GT/s do not also support Data Link Layer Link Active reporting. Per PCIe r5.0 sec 6.6.1:
With a Downstream Port that supports Link speeds greater than 5.0 GT/s, software must wait a minimum of 100 ms after Link training completes before sending a Configuration Request to the device immediately below that Port. Software can determine when Link training completes by polling the Data Link Layer Link Active bit or by setting up an associated interrupt (see Section 6.7.3.3).
Sec 7.5.3.6 requires such Ports to support DLL Link Active reporting, but at least the Intel JHL6240 Thunderbolt 3 Bridge [8086:15c0] and the Intel JHL7540 Thunderbolt 3 Bridge [8086:15ea] do not.
Previously we tried to wait for Link training to complete, but since there was no DLL Link Active reporting, all we could do was wait the worst-case 1000 ms, then another 100 ms.
Instead of using the supported speeds to determine whether to wait for Link training, check whether the port supports DLL Link Active reporting. The Ports in question do not, so we'll wait only the 100 ms required for Ports that support Link speeds <= 5 GT/s.
This of course assumes these Ports always train the Link within 100 ms even if they are operating at > 5 GT/s, which is not required by the spec.
--- drivers/pci/pci.c | 30 +++++++++++++++++++++--------- 1 file changed, 21 insertions(+), 9 deletions(-)
drivers/pci/pci.c +21 -9
@@ -4660,7 +4660,8 @@ static int pci_pm_reset(struct pci_dev *dev, int probe)* pcie_wait_for_link_delay - Wait until link is active or inactive * @pdev: Bridge device * @active: waiting for active or inactive? -* @delay: Delay to wait after link has become active (in ms) +* @delay: Delay to wait after link has become active (in ms). Specify %0 +* for no delay. * * Use this to wait till link becomes active or inactive. */
@@ -4701,7 +4702,7 @@ static bool pcie_wait_for_link_delay(struct pci_dev *pdev, bool active,msleep (10 ); timeout -=10 ; } -if (active && ret) +if (active && ret && delay)msleep (delay);else if (ret != active) pci_info(pdev, "Data Link Layer Link Active not %s in 1000 msec\n",
@@ -4822,17 +4823,28 @@ void pci_bridge_wait_for_secondary_bus(struct pci_dev *dev)if (!pcie_downstream_port (dev))return ; -if (pcie_get_speed_cap (dev) <=PCIE_SPEED_5_0GT ) { -pci_dbg (dev,"waiting %d ms for downstream link\n" , delay); -msleep (delay); - }else { -pci_dbg (dev,"waiting %d ms for downstream link, after activation\n" , - delay); -if (!pcie_wait_for_link_delay (dev, true, delay)) { +/* +* Per PCIe r5.0, sec 6.6.1, for downstream ports that support +* speeds > 5 GT/s, we must wait for link training to complete +* before the mandatory delay. +* +* We can only tell when link training completes via DLL Link +* Active, which is required for downstream ports that support +* speeds > 5 GT/s (sec 7.5.3.6). Unfortunately some common +* devices do not implement Link Active reporting even when it's +* required, so we'll check for that directly instead of checking +* the supported link speed. We assume devices without Link Active +* reporting can train in 100 ms regardless of speed. +*/ +if (dev->link_active_reporting) { +pci_dbg (dev,"waiting for link to train\n" ); +if (!pcie_wait_for_link_delay (dev, true,0 )) {/* Did not train, no need to wait any further */ return ; } } +pci_dbg (child,"waiting %d ms to become accessible\n" , delay); +msleep (delay);if (!pci_device_is_present (child)) {pci_dbg (child,"waiting additional %d ms to become accessible\n" , delay);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 210/477 habanalabs: increase timeout during reset
In reply to Greg Kroah-HartmanFrom: Oded Gabbay <[email protected]>
[ Upstream commit 7a65ee046b2238e053f6ebb610e1a082cfc49490 ]
When doing training, the DL framework (e.g. tensorflow) performs hundreds of thousands of memory allocations and mappings. In case the driver needs to perform hard-reset during training, the driver kills the application and unmaps all those memory allocations. Unfortunately, because of that large amount of mappings, the driver isn't able to do that in the current timeout (5 seconds). Therefore, increase the timeout significantly to 30 seconds to avoid situation where the driver resets the device with active mappings, which sometime can cause a kernel bug.
BTW, it doesn't mean we will spend all the 30 seconds because the reset thread checks every one second if the unmap operation is done.
--- drivers/misc/habanalabs/habanalabs.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/misc/habanalabs/habanalabs.h +1 -1
@@ -23,7 +23,7 @@#define HL_MMAP_CB_MASK (0x8000000000000000ull >> PAGE_SHIFT) -#define HL_PENDING_RESET_PER_SEC 5 +#define HL_PENDING_RESET_PER_SEC 30#define HL_DEVICE_TIMEOUT_USEC 1000000/* 1 s */
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 211/477 arm64: dts: marvell: armada-37xx: Set pcie_reset_pin to gpio function
In reply to Greg Kroah-HartmanFrom: Marek Behún <[email protected]>
[ Upstream commit 715878016984b2617f6c1f177c50039e12e7bd5b ]
We found out that we are unable to control the PERST# signal via the default pin dedicated to be PERST# pin (GPIO2[3] pin) on A3700 SOC when this pin is in EP_PCIE1_Resetn mode. There is a register in the PCIe register space called PERSTN_GPIO_EN (D0088004[3]), but changing the value of this register does not change the pin output when measuring with voltmeter.
We do not know if this is a bug in the SOC, or if it works only when PCIe controller is in a certain state.
Commit f4c7d053d7f7 ("PCI: aardvark: Wait for endpoint to be ready before training link") says that when this pin changes pinctrl mode from EP_PCIE1_Resetn to GPIO, the PERST# signal is asserted for a brief moment.
So currently the situation is that on A3700 boards the PERST# signal is asserted in U-Boot (because the code in U-Boot issues reset via this pin via GPIO mode), and then in Linux by the obscure and undocumented mechanism described by the above mentioned commit.
We want to issue PERST# signal in a known way, therefore this patch changes the pcie_reset_pin function from "pcie" to "gpio" and adds the reset-gpios property to the PCIe node in device tree files of EspressoBin and Armada 3720 Dev Board (Turris Mox device tree already has this property and uDPU does not have a PCIe port).
--- arch/arm64/boot/dts/marvell/armada-3720-db.dts | 3 +++ arch/arm64/boot/dts/marvell/armada-3720-espressobin.dtsi | 1 + arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts | 4 ---- arch/arm64/boot/dts/marvell/armada-37xx.dtsi | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-)
arch/arm64/boot/dts/marvell/armada-3720-db.dts +3 -0
@@ -128,6 +128,9 @@ /* CON15(V2.0)/CON17(V1.4) : PCIe / CON15(V2.0)/CON12(V1.4) :mini-PCIe */ &pcie0 { + pinctrl-names = "default"; + pinctrl-0 = <&pcie_reset_pins &pcie_clkreq_pins>; + reset-gpios = <&gpiosb 3 GPIO_ACTIVE_LOW>; status = "okay"; };
arch/arm64/boot/dts/marvell/armada-3720-espressobin.dtsi +1 -0
@@ -47,6 +47,7 @@ phys = <&comphy1 0>; pinctrl-names = "default"; pinctrl-0 = <&pcie_reset_pins &pcie_clkreq_pins>; + reset-gpios = <&gpiosb 3 GPIO_ACTIVE_LOW>; }; /* J6 */
arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts +0 -4
@@ -128,10 +128,6 @@ }; }; -&pcie_reset_pins { - function = "gpio"; -}; - &pcie0 { pinctrl-names = "default"; pinctrl-0 = <&pcie_reset_pins &pcie_clkreq_pins>;
arch/arm64/boot/dts/marvell/armada-37xx.dtsi +1 -1
@@ -317,7 +317,7 @@ pcie_reset_pins: pcie-reset-pins { groups = "pcie1"; - function = "pcie"; + function = "gpio"; }; pcie_clkreq_pins: pcie-clkreq-pins {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 212/477 pinctrl: ocelot: Always register GPIO driver
In reply to Greg Kroah-HartmanFrom: Lars Povlsen <[email protected]>
[ Upstream commit 550713e33f4338c8596776828a936fd1e3bf35de ]
This fixes the situation where the GPIO controller is not used as an interrupt controller as well.
Previously, the driver would silently fail to register even the GPIO's. With this change, the driver will only register as an interrupt controller if a parent interrupt is provided.
--- drivers/pinctrl/pinctrl-ocelot.c | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-)
drivers/pinctrl/pinctrl-ocelot.c +15 -15
@@ -752,21 +752,21 @@ static int ocelot_gpiochip_register(struct platform_device *pdev, gc->of_node = info->dev->of_node; gc->label ="ocelot-gpio" ; - irq =irq_of_parse_and_map (pdev->dev.of_node,0 ); -if (irq <=0 ) -return irq; - - girq = &gc->irq; - girq->chip = &ocelot_irqchip; - girq->parent_handler = ocelot_irq_handler; - girq->num_parents =1 ; - girq->parents =devm_kcalloc (&pdev->dev,1 ,sizeof (*girq->parents), -GFP_KERNEL ); -if (!girq->parents) -return -ENOMEM ; - girq->parents[0 ] = irq; - girq->default_type =IRQ_TYPE_NONE ; - girq->handler = handle_edge_irq; + irq =irq_of_parse_and_map (gc->of_node,0 ); +if (irq) { + girq = &gc->irq; + girq->chip = &ocelot_irqchip; + girq->parent_handler = ocelot_irq_handler; + girq->num_parents =1 ; + girq->parents =devm_kcalloc (&pdev->dev,1 , +sizeof (*girq->parents), +GFP_KERNEL ); +if (!girq->parents) +return -ENOMEM ; + girq->parents[0 ] = irq; + girq->default_type =IRQ_TYPE_NONE ; + girq->handler = handle_edge_irq; + } ret =devm_gpiochip_add_data (&pdev->dev, gc, info);if (ret)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 213/477 ipmi: use vzalloc instead of kmalloc for user creation
In reply to Greg Kroah-HartmanFrom: Feng Tang <[email protected]>
[ Upstream commit 7c47a219b95d0e06b5ef5fcc7bad807895015eac ]
We met mulitple times of failure of staring bmc-watchdog, due to the runtime memory allocation failure of order 4.
bmc-watchdog: page allocation failure: order:4, mode:0x40cc0(GFP_KERNEL|__GFP_COMP), nodemask=(null),cpuset=/,mems_allowed=0-1
CPU: 1 PID: 2571 Comm: bmc-watchdog Not tainted 5.5.0-00045-g7d6bb61d6188c #1
Hardware name: Intel Corporation S2600WFT/S2600WFT, BIOS SE5C620.86B.00.01.0015.110720180833 11/07/2018
Call Trace:
dump_stack+0x66/0x8b
warn_alloc+0xfe/0x160
__alloc_pages_slowpath+0xd3e/0xd80
__alloc_pages_nodemask+0x2f0/0x340
kmalloc_order+0x18/0x70
kmalloc_order_trace+0x1d/0xb0
ipmi_create_user+0x55/0x2c0 [ipmi_msghandler]
ipmi_open+0x72/0x110 [ipmi_devintf]
chrdev_open+0xcb/0x1e0
do_dentry_open+0x1ce/0x380
path_openat+0x305/0x14f0
do_filp_open+0x9b/0x110
do_sys_open+0x1bd/0x250
do_syscall_64+0x5b/0x1f0
entry_SYSCALL_64_after_hwframe+0x44/0xa9Using vzalloc/vfree for creating ipmi_user heals the problem
Thanks to Stephen Rothwell for finding the vmalloc.h inclusion issue.
--- drivers/char/ipmi/ipmi_msghandler.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/char/ipmi/ipmi_msghandler.c +4 -3
@@ -33,6 +33,7 @@#include <linux/workqueue.h> #include <linux/uuid.h> #include <linux/nospec.h> +#include <linux/vmalloc.h> #define IPMI_DRIVER_VERSION "39.2"
@@ -1153,7 +1154,7 @@ static void free_user_work(struct work_struct *work) remove_work);cleanup_srcu_struct (&user->release_barrier); -kfree (user); +vfree (user); } int ipmi_create_user(unsigned int if_num,
@@ -1185,7 +1186,7 @@ int ipmi_create_user(unsigned int if_num,if (rv)return rv; - new_user =kmalloc (sizeof (*new_user),GFP_KERNEL ); + new_user =vzalloc (sizeof (*new_user));if (!new_user)return -ENOMEM ;
@@ -1232,7 +1233,7 @@ int ipmi_create_user(unsigned int if_num, out_kfree:srcu_read_unlock (&ipmi_interfaces_srcu, index); -kfree (new_user); +vfree (new_user);return rv; }EXPORT_SYMBOL (ipmi_create_user);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 214/477 ASoC: codecs: rt*-sdw: fix memory leak in set_sdw_stream()
In reply to Greg Kroah-HartmanFrom: Pierre-Louis Bossart <[email protected]>
[ Upstream commit 07b542fe831cbefce163ad1b3aa7292c8a6332b8 ]
Now that the sdw_stream is allocated in machine driver, set_sdw_stream() is also called with a NULL argument during the dailink shutdown.
In this case, the drivers should not allocate any memory, and just return.
Detected with KASAN/kmemleak.
--- sound/soc/codecs/rt1308-sdw.c | 3 +++ sound/soc/codecs/rt5682.c | 3 +++ sound/soc/codecs/rt700.c | 3 +++ sound/soc/codecs/rt711.c | 3 +++ sound/soc/codecs/rt715.c | 3 +++ 5 files changed, 15 insertions(+)
sound/soc/codecs/rt1308-sdw.c +3 -0
@@ -482,6 +482,9 @@ static int rt1308_set_sdw_stream(struct snd_soc_dai *dai, void *sdw_stream, {struct sdw_stream_data *stream; +if (!sdw_stream) +return 0 ; + stream =kzalloc (sizeof (*stream),GFP_KERNEL );if (!stream)return -ENOMEM ;
sound/soc/codecs/rt5682.c +3 -0
@@ -2958,6 +2958,9 @@ static int rt5682_set_sdw_stream(struct snd_soc_dai *dai, void *sdw_stream, {struct sdw_stream_data *stream; +if (!sdw_stream) +return 0 ; + stream =kzalloc (sizeof (*stream),GFP_KERNEL );if (!stream)return -ENOMEM ;
sound/soc/codecs/rt700.c +3 -0
@@ -860,6 +860,9 @@ static int rt700_set_sdw_stream(struct snd_soc_dai *dai, void *sdw_stream, {struct sdw_stream_data *stream; +if (!sdw_stream) +return 0 ; + stream =kzalloc (sizeof (*stream),GFP_KERNEL );if (!stream)return -ENOMEM ;
sound/soc/codecs/rt711.c +3 -0
@@ -906,6 +906,9 @@ static int rt711_set_sdw_stream(struct snd_soc_dai *dai, void *sdw_stream, {struct sdw_stream_data *stream; +if (!sdw_stream) +return 0 ; + stream =kzalloc (sizeof (*stream),GFP_KERNEL );if (!stream)return -ENOMEM ;
sound/soc/codecs/rt715.c +3 -0
@@ -530,6 +530,9 @@ static int rt715_set_sdw_stream(struct snd_soc_dai *dai, void *sdw_stream,struct sdw_stream_data *stream; +if (!sdw_stream) +return 0 ; + stream =kzalloc (sizeof (*stream),GFP_KERNEL );if (!stream)return -ENOMEM ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 215/477 powerpc/64s/exception: Fix machine check no-loss idle wakeup
In reply to Greg Kroah-HartmanFrom: Nicholas Piggin <[email protected]>
[ Upstream commit 8a5054d8cbbe03c68dcb0957c291c942132e4101 ]
The architecture allows for machine check exceptions to cause idle wakeups which resume at the 0x200 address which has to return via the idle wakeup code, but the early machine check handler is run first.
The case of a no state-loss sleep is broken because the early handler uses non-volatile register r1 , which is needed for the wakeup protocol, but it is not restored.
Fix this by loading r1 from the MCE exception frame before returning to the idle wakeup code. Also update the comment which has become stale since the idle rewrite in C.
This crash was found and fix confirmed with a machine check injection test in qemu powernv model (which is not upstream in qemu yet).
--- arch/powerpc/kernel/exceptions-64s.S | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-)
arch/powerpc/kernel/exceptions-64s.S +8 -6
@@ -1225,17 +1225,19 @@ EXC_COMMON_BEGIN(machine_check_idle_common) bl machine_check_queue_event /* - * We have not used any non-volatile GPRs here, and as a rule - * most exception code including machine check does not. - * Therefore PACA_NAPSTATELOST does not need to be set. Idle - * wakeup will restore volatile registers. + * GPR-loss wakeups are relatively straightforward, because the + * idle sleep code has saved all non-volatile registers on its + * own stack, and r1 in PACAR1. * - * Load the original SRR1 into r3 for pnv_powersave_wakeup_mce. + * For no-loss wakeups the r1 and lr registers used by the + * early machine check handler have to be restored first. r2 is + * the kernel TOC, so no need to restore it. * * Then decrement MCE nesting after finishing with the stack. */ ld r3,_MSR(r1) ld r4,_LINK(r1) + ld r1,GPR1(r1) lhz r11,PACA_IN_MCE(r13) subi r11,r11,1
@@ -1244,7 +1246,7 @@ EXC_COMMON_BEGIN(machine_check_idle_common) mtlr r4 rlwinm r10,r3,47-31,30,31 cmpwi cr1,r10,2 - bltlr cr1 /* no state loss, return to idle caller */ + bltlr cr1 /* no state loss, return to idle caller with r3=SRR1 */ b idle_return_gpr_loss #endif
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 216/477 powerpc/64s/exceptions: Machine check reconcile irq state
In reply to Greg Kroah-HartmanFrom: Nicholas Piggin <[email protected]>
[ Upstream commit f0fd9dd3c213c947dfb5bc2cad3ef5e30d3258ec ]
pseries fwnmi machine check code pops the soft-irq checks in rtas_call (after the next patch to remove rtas_token from this call path). Rather than play whack a mole with these and forever having fragile code, it seems better to have the early machine check handler perform the same kind of reconcile as the other NMI interrupts.
WARNING: CPU: 0 PID: 493 at arch/powerpc/kernel/irq.c:343
CPU: 0 PID: 493 Comm: a Tainted: G W
NIP: c00000000001ed2c LR: c000000000042c40 CTR: 0000000000000000
REGS: c0000001fffd38b0 TRAP: 0700 Tainted: G W
MSR: 8000000000021003 <SF,ME,RI,LE> CR: 28000488 XER: 00000000
CFAR: c00000000001ec90 IRQMASK: 0
GPR00: c000000000043820 c0000001fffd3b40 c0000000012ba300 0000000000000000
GPR04: 0000000048000488 0000000000000000 0000000000000000 00000000deadbeef
GPR08: 0000000000000080 0000000000000000 0000000000000000 0000000000001001
GPR12: 0000000000000000 c0000000014a0000 0000000000000000 0000000000000000
GPR16: 0000000000000000 0000000000000000 0000000000000000 0000000000000000
GPR20: 0000000000000000 0000000000000000 0000000000000000 0000000000000000
GPR24: 0000000000000000 0000000000000000 0000000000000000 0000000000000000
GPR28: 0000000000000000 0000000000000001 c000000001360810 0000000000000000
NIP [c00000000001ed2c] arch_local_irq_restore.part.0+0xac/0x100
LR [c000000000042c40] unlock_rtas+0x30/0x90
Call Trace:
[c0000001fffd3b40] [c000000001360810] 0xc000000001360810 (unreliable)
[c0000001fffd3b60] [c000000000043820] rtas_call+0x1c0/0x280
[c0000001fffd3bb0] [c0000000000dc328] fwnmi_release_errinfo+0x38/0x70
[c0000001fffd3c10] [c0000000000dcd8c] pseries_machine_check_realmode+0x1dc/0x540
[c0000001fffd3cd0] [c00000000003fe04] machine_check_early+0x54/0x70
[c0000001fffd3d00] [c000000000008384] machine_check_early_common+0x134/0x1f0
--- interrupt: 200 at 0x13f1307c8
LR = 0x7fff888b8528
Instruction dump:
60000000 7d2000a6 71298000 41820068 39200002 7d210164 4bffff9c 60000000
60000000 7d2000a6 71298000 4c820020 <0fe00000> 4e800020 60000000 60000000--- arch/powerpc/kernel/exceptions-64s.S | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+)
arch/powerpc/kernel/exceptions-64s.S +19 -0
@@ -1117,11 +1117,30 @@ END_FTR_SECTION_IFSET(CPU_FTR_HVMODE) li r10,MSR_RI mtmsrd r10,1 + /* + * Set IRQS_ALL_DISABLED and save PACAIRQHAPPENED (see + * system_reset_common) + */ + li r10,IRQS_ALL_DISABLED + stb r10,PACAIRQSOFTMASK(r13) + lbz r10,PACAIRQHAPPENED(r13) + std r10,RESULT(r1) + ori r10,r10,PACA_IRQ_HARD_DIS + stb r10,PACAIRQHAPPENED(r13) + addi r3,r1,STACK_FRAME_OVERHEAD bl machine_check_early std r3,RESULT(r1) /* Save result */ ld r12,_MSR(r1) + /* + * Restore soft mask settings. + */ + ld r10,RESULT(r1) + stb r10,PACAIRQHAPPENED(r13) + ld r10,SOFTE(r1) + stb r10,PACAIRQSOFTMASK(r13) + #ifdef CONFIG_PPC_P7_NAP /* * Check if thread was in power saving mode. We come here when any
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 217/477 powerpc/pseries/ras: Fix FWNMI_VALID off by one
In reply to Greg Kroah-HartmanFrom: Nicholas Piggin <[email protected]>
[ Upstream commit deb70f7a35a22dffa55b2c3aac71bc6fb0f486ce ]
This was discovered developing qemu fwnmi sreset support. This off-by-one bug means the last 16 bytes of the rtas area can not be used for a 16 byte save area.
It's not a serious bug, and QEMU implementation has to retain a workaround for old kernels, but it's good to tighten it.
--- arch/powerpc/platforms/pseries/ras.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
arch/powerpc/platforms/pseries/ras.c +3 -2
@@ -395,10 +395,11 @@ static irqreturn_t ras_error_interrupt(int irq, void *dev_id)/* * Some versions of FWNMI place the buffer inside the 4kB page starting at * 0x7000. Other versions place it inside the rtas buffer. We check both. +* Minimum size of the buffer is 16 bytes. */ #define VALID_FWNMI_BUFFER (A ) \ - ((((A) >= 0x7000) && ((A) < 0x7ff0)) || \ - (((A) >= rtas.base) && ((A) < (rtas.base + rtas.size - 16)))) + ((((A) >= 0x7000) && ((A) <= 0x8000 - 16)) || \ + (((A) >= rtas.base) && ((A) <= (rtas.base + rtas.size - 16))))static inline struct rtas_error_log *fwnmi_get_errlog (void ) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 218/477 PCI: aardvark: Train link immediately after enabling training
In reply to Greg Kroah-HartmanFrom: Pali Rohár <[email protected]>
[ Upstream commit 6964494582f56a3882c2c53b0edbfe99eb32b2e1 ]
Adding even 100ms (PCI_PM_D3COLD_WAIT) delay between enabling link training and starting link training causes detection issues with some buggy cards (such as Compex WLE900VX).
Move the code which enables link training immediately before the one which starts link traning.
This fixes detection issues of Compex WLE900VX card on Turris MOX after cold boot.
--- drivers/pci/controller/pci-aardvark.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-)
drivers/pci/controller/pci-aardvark.c +9 -6
@@ -300,11 +300,6 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie) reg |=LANE_COUNT_1 ;advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); -/* Enable link training */ - reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); - reg |=LINK_TRAINING_EN ; -advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); -/* Enable MSI */ reg =advk_readl (pcie,PCIE_CORE_CTRL2_REG ); reg |=PCIE_CORE_CTRL2_MSI_ENABLE ;
@@ -346,7 +341,15 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie)*/ msleep (PCI_PM_D3COLD_WAIT ); -/* Start link training */ +/* Enable link training */ + reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); + reg |=LINK_TRAINING_EN ; +advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); + +/* +* Start link training immediately after enabling it. +* This solves problems for some buggy cards. +*/ reg =advk_readl (pcie,PCIE_CORE_LINK_CTRL_STAT_REG ); reg |=PCIE_CORE_LINK_TRAINING ;advk_writel (pcie, reg,PCIE_CORE_LINK_CTRL_STAT_REG );
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 219/477 PCI: aardvark: Improve link training
In reply to Greg Kroah-HartmanFrom: Marek Behún <[email protected]>
[ Upstream commit 43fc679ced18006b12d918d7a8a4af392b7fbfe7 ]
Currently the aardvark driver trains link in PCIe gen2 mode. This may cause some buggy gen1 cards (such as Compex WLE900VX) to be unstable or even not detected. Moreover when ASPM code tries to retrain link second time, these cards may stop responding and link goes down. If gen1 is used this does not happen.
Unconditionally forcing gen1 is not a good solution since it may have performance impact on gen2 cards.
To overcome this, read 'max-link-speed' property (as defined in PCI device tree bindings) and use this as max gen mode. Then iteratively try link training at this mode or lower until successful. After successful link training choose final controller gen based on Negotiated Link Speed from Link Status register, which should match card speed.
--- drivers/pci/controller/pci-aardvark.c | 114 ++++++++++++++++++++------ 1 file changed, 89 insertions(+), 25 deletions(-)
drivers/pci/controller/pci-aardvark.c +89 -25
@@ -40,6 +40,7 @@#define PCIE_CORE_LINK_CTRL_STAT_REG 0xd0#define PCIE_CORE_LINK_L0S_ENTRY BIT(0)#define PCIE_CORE_LINK_TRAINING BIT(5) +#define PCIE_CORE_LINK_SPEED_SHIFT 16#define PCIE_CORE_LINK_WIDTH_SHIFT 20#define PCIE_CORE_ERR_CAPCTL_REG 0x118#define PCIE_CORE_ERR_CAPCTL_ECRC_CHK_TX BIT(5)
@@ -201,6 +202,7 @@ struct advk_pcie {struct mutex msi_used_lock;u16 msi_msg;int root_bus_nr; +int link_gen;struct pci_bridge_emul bridge; };
@@ -225,20 +227,16 @@ static int advk_pcie_link_up(struct advk_pcie *pcie)static int advk_pcie_wait_for_link (struct advk_pcie *pcie) { -struct device *dev = &pcie->pdev->dev;int retries;/* check if the link is up or not */ for (retries =0 ; retries <LINK_WAIT_MAX_RETRIES ; retries++) { -if (advk_pcie_link_up (pcie)) { -dev_info (dev,"link up\n" ); +if (advk_pcie_link_up (pcie))return 0 ; - }usleep_range (LINK_WAIT_USLEEP_MIN ,LINK_WAIT_USLEEP_MAX ); } -dev_err (dev,"link never came up\n" );return -ETIMEDOUT ; }
@@ -253,6 +251,85 @@ static void advk_pcie_wait_for_retrain(struct advk_pcie *pcie) } } +static int advk_pcie_train_at_gen (struct advk_pcie *pcie,int gen) +{ +int ret, neg_gen; +u32 reg; + +/* Setup link speed */ + reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); + reg &= ~PCIE_GEN_SEL_MSK ; +if (gen ==3 ) + reg |=SPEED_GEN_3 ; +else if (gen ==2 ) + reg |=SPEED_GEN_2 ; +else + reg |=SPEED_GEN_1 ; +advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); + +/* +* Enable link training. This is not needed in every call to this +* function, just once suffices, but it does not break anything either. +*/ + reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); + reg |=LINK_TRAINING_EN ; +advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); + +/* +* Start link training immediately after enabling it. +* This solves problems for some buggy cards. +*/ + reg =advk_readl (pcie,PCIE_CORE_LINK_CTRL_STAT_REG ); + reg |=PCIE_CORE_LINK_TRAINING ; +advk_writel (pcie, reg,PCIE_CORE_LINK_CTRL_STAT_REG ); + + ret =advk_pcie_wait_for_link (pcie); +if (ret) +return ret; + + reg =advk_readl (pcie,PCIE_CORE_LINK_CTRL_STAT_REG ); + neg_gen = (reg >>PCIE_CORE_LINK_SPEED_SHIFT ) &0xf ; + +return neg_gen; +} + +static void advk_pcie_train_link (struct advk_pcie *pcie) +{ +struct device *dev = &pcie->pdev->dev; +int neg_gen =-1 , gen; + +/* +* Try link training at link gen specified by device tree property +* 'max-link-speed'. If this fails, iteratively train at lower gen. +*/ +for (gen = pcie->link_gen; gen >0 ; --gen) { + neg_gen =advk_pcie_train_at_gen (pcie, gen); +if (neg_gen >0 ) +break ; + } + +if (neg_gen <0 ) + goto err; + +/* +* After successful training if negotiated gen is lower than requested, +* train again on negotiated gen. This solves some stability issues for +* some buggy gen1 cards. +*/ +if (neg_gen < gen) { + gen = neg_gen; + neg_gen =advk_pcie_train_at_gen (pcie, gen); + } + +if (neg_gen == gen) { +dev_info (dev,"link up at gen %i\n" , gen); +return ; + } + +err: +dev_err (dev,"link never came up\n" ); +} +static void advk_pcie_setup_hw (struct advk_pcie *pcie) {u32 reg;
@@ -288,12 +365,6 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie)PCIE_CORE_CTRL2_TD_ENABLE ;advk_writel (pcie, reg,PCIE_CORE_CTRL2_REG ); -/* Set GEN2 */ - reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); - reg &= ~PCIE_GEN_SEL_MSK ; - reg |=SPEED_GEN_2 ; -advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); -/* Set lane X1 */ reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); reg &= ~LANE_CNT_MSK ;
@@ -341,20 +412,7 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie)*/ msleep (PCI_PM_D3COLD_WAIT ); -/* Enable link training */ - reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); - reg |=LINK_TRAINING_EN ; -advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); - -/* -* Start link training immediately after enabling it. -* This solves problems for some buggy cards. -*/ - reg =advk_readl (pcie,PCIE_CORE_LINK_CTRL_STAT_REG ); - reg |=PCIE_CORE_LINK_TRAINING ; -advk_writel (pcie, reg,PCIE_CORE_LINK_CTRL_STAT_REG ); - -advk_pcie_wait_for_link (pcie); +advk_pcie_train_link (pcie); reg =advk_readl (pcie,PCIE_CORE_CMD_STATUS_REG ); reg |= PCIE_CORE_CMD_MEM_ACCESS_EN |
@@ -988,6 +1046,12 @@ static int advk_pcie_probe(struct platform_device *pdev) } pcie->root_bus_nr = bus->start; + ret =of_pci_get_max_link_speed (dev->of_node); +if (ret <=0 || ret >3 ) + pcie->link_gen =3 ; +else + pcie->link_gen = ret; +advk_pcie_setup_hw (pcie);advk_sw_pci_bridge_init (pcie);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 220/477 PCI: aardvark: Issue PERST via GPIO
In reply to Greg Kroah-HartmanFrom: Pali Rohár <[email protected]>
[ Upstream commit 5169a9851daaa2782a7bd2bb83d5b1bd224b2879 ]
Add support for issuing PERST via GPIO specified in 'reset-gpios' property (as described in PCI device tree bindings).
Some buggy cards (e.g. Compex WLE900VX or WLE1216) are not detected after reboot when PERST is not issued during driver initialization.
If bootloader already enabled link training then issuing PERST has no effect for some buggy cards (e.g. Compex WLE900VX) and these cards are not detected. We therefore clear the LINK_TRAINING_EN register before.
It was observed that Compex WLE900VX card needs to be in PERST reset for at least 10ms if bootloader enabled link training.
Tested on Turris MOX.
--- drivers/pci/controller/pci-aardvark.c | 43 ++++++++++++++++++++++++++- 1 file changed, 42 insertions(+), 1 deletion(-)
drivers/pci/controller/pci-aardvark.c +42 -1
@@ -9,6 +9,7 @@*/ #include <linux/delay.h> +#include <linux/gpio.h> #include <linux/interrupt.h> #include <linux/irq.h> #include <linux/irqdomain.h>
@@ -18,6 +19,7 @@#include <linux/platform_device.h> #include <linux/msi.h> #include <linux/of_address.h> +#include <linux/of_gpio.h> #include <linux/of_pci.h> #include "../pci.h"
@@ -204,6 +206,7 @@ struct advk_pcie {int root_bus_nr;int link_gen;struct pci_bridge_emul bridge; +struct gpio_desc *reset_gpio; };static inline void advk_writel (struct advk_pcie *pcie,u32 val,u64 reg)
@@ -330,10 +333,31 @@ err:dev_err (dev,"link never came up\n" ); } +static void advk_pcie_issue_perst (struct advk_pcie *pcie) +{ +u32 reg; + +if (!pcie->reset_gpio) +return ; + +/* PERST does not work for some cards when link training is enabled */ + reg =advk_readl (pcie,PCIE_CORE_CTRL0_REG ); + reg &= ~LINK_TRAINING_EN ; +advk_writel (pcie, reg,PCIE_CORE_CTRL0_REG ); + +/* 10ms delay is needed for some cards */ +dev_info (&pcie->pdev->dev,"issuing PERST via reset GPIO for 10ms\n" ); +gpiod_set_value_cansleep (pcie->reset_gpio,1 ); +usleep_range (10000 ,11000 ); +gpiod_set_value_cansleep (pcie->reset_gpio,0 ); +} +static void advk_pcie_setup_hw (struct advk_pcie *pcie) {u32 reg; +advk_pcie_issue_perst (pcie); +/* Set to Direct mode */ reg =advk_readl (pcie,CTRL_CONFIG_REG ); reg &= ~(CTRL_MODE_MASK <<CTRL_MODE_SHIFT );
@@ -406,7 +430,8 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie)/* * PERST# signal could have been asserted by pinctrl subsystem before -* probe() callback has been called, making the endpoint going into +* probe() callback has been called or issued explicitly by reset gpio +* function advk_pcie_issue_perst(), making the endpoint going into * fundamental reset. As required by PCI Express spec a delay for at * least 100ms after such a reset before link training is needed. */
@@ -1046,6 +1071,22 @@ static int advk_pcie_probe(struct platform_device *pdev) } pcie->root_bus_nr = bus->start; + pcie->reset_gpio =devm_gpiod_get_from_of_node (dev, dev->of_node, +"reset-gpios" ,0 , +GPIOD_OUT_LOW , +"pcie1-reset" ); + ret =PTR_ERR_OR_ZERO (pcie->reset_gpio); +if (ret) { +if (ret == -ENOENT ) { + pcie->reset_gpio =NULL ; + }else { +if (ret != -EPROBE_DEFER ) +dev_err (dev,"Failed to get reset-gpio: %i\n" , + ret); +return ret; + } + } + ret =of_pci_get_max_link_speed (dev->of_node);if (ret <=0 || ret >3 ) pcie->link_gen =3 ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 221/477 drivers: phy: sr-usb: do not use internal fsm for USB2 phy init
In reply to Greg Kroah-HartmanFrom: Bharat Gooty <[email protected]>
[ Upstream commit 6f0577d1411337a0d97d545abe4a784e9e611516 ]
During different reboot cycles, USB PHY PLL may not always lock during initialization and therefore can cause USB to be not usable.
Hence do not use internal FSM programming sequence for the USB PHY initialization.
--- drivers/phy/broadcom/phy-bcm-sr-usb.c | 55 +-------------------------- 1 file changed, 2 insertions(+), 53 deletions(-)
drivers/phy/broadcom/phy-bcm-sr-usb.c +2 -53
@@ -16,8 +16,6 @@ enum bcm_usb_phy_version { };enum bcm_usb_phy_reg { -PLL_NDIV_FRAC , -PLL_NDIV_INT ,PLL_CTRL ,PHY_CTRL ,PHY_PLL_CTRL ,
@@ -31,18 +29,11 @@ static const u8 bcm_usb_combo_phy_ss[] = { };static const u8 bcm_usb_combo_phy_hs[] = { - [PLL_NDIV_FRAC ] =0x04 , - [PLL_NDIV_INT ] =0x08 , [PLL_CTRL ] =0x0c , [PHY_CTRL ] =0x10 , }; -#define HSPLL_NDIV_INT_VAL 0x13 -#define HSPLL_NDIV_FRAC_VAL 0x1005 -static const u8 bcm_usb_hs_phy[] = { - [PLL_NDIV_FRAC ] =0x0 , - [PLL_NDIV_INT ] =0x4 , [PLL_CTRL ] =0x8 , [PHY_CTRL ] =0xc , };
@@ -52,7 +43,6 @@ enum pll_ctrl_bits {SSPLL_SUSPEND_EN ,PLL_SEQ_START , PLL_LOCK, - PLL_PDIV, }; static const u8 u3pll_ctrl[] = {
@@ -66,29 +56,17 @@ static const u8 u3pll_ctrl[] = {#define HSPLL_PDIV_VAL 0x1static const u8 u2pll_ctrl[] = { - [PLL_PDIV ] =1 , [PLL_RESETB ] =5 , [PLL_LOCK ] =6 , };enum bcm_usb_phy_ctrl_bits {CORERDY , -AFE_LDO_PWRDWNB , -AFE_PLL_PWRDWNB , -AFE_BG_PWRDWNB , -PHY_ISO ,PHY_RESETB ,PHY_PCTL , };#define PHY_PCTL_MASK 0xffff -/* -* 0x0806 of PCTL_VAL has below bits set -* BIT-8 : refclk divider 1 -* BIT-3:2: device mode; mode is not effect -* BIT-1: soft reset active low -*/ -#define HSPHY_PCTL_VAL 0x0806#define SSPHY_PCTL_VAL 0x0006static const u8 u3phy_ctrl[] = {
@@ -98,10 +76,6 @@ static const u8 u3phy_ctrl[] = {static const u8 u2phy_ctrl[] = { [CORERDY ] =0 , - [AFE_LDO_PWRDWNB ] =1 , - [AFE_PLL_PWRDWNB ] =2 , - [AFE_BG_PWRDWNB ] =3 , - [PHY_ISO ] =4 , [PHY_RESETB ] =5 , [PHY_PCTL ] =6 , };
@@ -186,38 +160,13 @@ static int bcm_usb_hs_phy_init(struct bcm_usb_phy_cfg *phy_cfg)int ret =0 ;void __iomem *regs = phy_cfg->regs;const u8 *offset; -u32 rd_data; offset = phy_cfg->offset; -writel (HSPLL_NDIV_INT_VAL , regs + offset[PLL_NDIV_INT ]); -writel (HSPLL_NDIV_FRAC_VAL , regs + offset[PLL_NDIV_FRAC ]); - - rd_data =readl (regs + offset[PLL_CTRL ]); - rd_data &= ~(HSPLL_PDIV_MASK << u2pll_ctrl[PLL_PDIV ]); - rd_data |= (HSPLL_PDIV_VAL << u2pll_ctrl[PLL_PDIV ]); -writel (rd_data, regs + offset[PLL_CTRL ]); - -/* Set Core Ready high */ -bcm_usb_reg32_setbits (regs + offset[PHY_CTRL ], -BIT (u2phy_ctrl[CORERDY ])); - -/* Maximum timeout for Core Ready done */ -msleep (30 ); - +bcm_usb_reg32_clrbits (regs + offset[PLL_CTRL ], +BIT (u2pll_ctrl[PLL_RESETB ]));bcm_usb_reg32_setbits (regs + offset[PLL_CTRL ],BIT (u2pll_ctrl[PLL_RESETB ])); -bcm_usb_reg32_setbits (regs + offset[PHY_CTRL ], -BIT (u2phy_ctrl[PHY_RESETB ])); - - - rd_data =readl (regs + offset[PHY_CTRL ]); - rd_data &= ~(PHY_PCTL_MASK << u2phy_ctrl[PHY_PCTL ]); - rd_data |= (HSPHY_PCTL_VAL << u2phy_ctrl[PHY_PCTL ]); -writel (rd_data, regs + offset[PHY_CTRL ]); - -/* Maximum timeout for PLL reset done */ -msleep (30 ); ret =bcm_usb_pll_lock_check (regs + offset[PLL_CTRL ],BIT (u2pll_ctrl[PLL_LOCK ]));
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 222/477 phy: cadence: sierra: Fix for USB3 U1/U2 state
In reply to Greg Kroah-HartmanFrom: Sanket Parmar <[email protected]>
[ Upstream commit 2bcf14ca1a2f3202954f812f380c7fa8127fbd7f ]
Updated values of USB3 related Sierra PHY registers. This change fixes USB3 device disconnect issue observed while enternig U1/U2 state.
--- drivers/phy/cadence/phy-cadence-sierra.c | 27 ++++++++++++------------ 1 file changed, 14 insertions(+), 13 deletions(-)
drivers/phy/cadence/phy-cadence-sierra.c +14 -13
@@ -685,10 +685,10 @@ static struct cdns_reg_pairs cdns_usb_cmn_regs_ext_ssc[] = {static struct cdns_reg_pairs cdns_usb_ln_regs_ext_ssc[] = { {0xFE0A ,SIERRA_DET_STANDEC_A_PREG }, {0x000F ,SIERRA_DET_STANDEC_B_PREG }, - {0x00A5 ,SIERRA_DET_STANDEC_C_PREG }, + {0x55A5 ,SIERRA_DET_STANDEC_C_PREG }, {0x69ad ,SIERRA_DET_STANDEC_D_PREG }, {0x0241 ,SIERRA_DET_STANDEC_E_PREG }, - {0x0010 ,SIERRA_PSM_LANECAL_DLY_A1_RESETS_PREG }, + {0x0110 ,SIERRA_PSM_LANECAL_DLY_A1_RESETS_PREG }, {0x0014 ,SIERRA_PSM_A0IN_TMR_PREG }, {0xCF00 ,SIERRA_PSM_DIAG_PREG }, {0x001F ,SIERRA_PSC_TX_A0_PREG },
@@ -696,7 +696,7 @@ static struct cdns_reg_pairs cdns_usb_ln_regs_ext_ssc[] = { {0x0003, SIERRA_PSC_TX_A2_PREG}, {0x0003, SIERRA_PSC_TX_A3_PREG}, {0x0FFF, SIERRA_PSC_RX_A0_PREG}, - {0x0619, SIERRA_PSC_RX_A1_PREG}, + {0x0003, SIERRA_PSC_RX_A1_PREG}, {0x0003, SIERRA_PSC_RX_A2_PREG}, {0x0001, SIERRA_PSC_RX_A3_PREG}, {0x0001, SIERRA_PLLCTRL_SUBRATE_PREG},
@@ -705,19 +705,19 @@ static struct cdns_reg_pairs cdns_usb_ln_regs_ext_ssc[] = { {0x00CA, SIERRA_CLKPATH_BIASTRIM_PREG}, {0x2512, SIERRA_DFE_BIASTRIM_PREG}, {0x0000, SIERRA_DRVCTRL_ATTEN_PREG}, - {0x873E, SIERRA_CLKPATHCTRL_TMR_PREG}, - {0x03CF, SIERRA_RX_CREQ_FLTR_A_MODE1_PREG}, - {0x01CE, SIERRA_RX_CREQ_FLTR_A_MODE0_PREG}, + {0x823E, SIERRA_CLKPATHCTRL_TMR_PREG}, + {0x078F, SIERRA_RX_CREQ_FLTR_A_MODE1_PREG}, + {0x078F, SIERRA_RX_CREQ_FLTR_A_MODE0_PREG}, {0x7B3C, SIERRA_CREQ_CCLKDET_MODE01_PREG}, - {0x033F, SIERRA_RX_CTLE_MAINTENANCE_PREG}, + {0x023C, SIERRA_RX_CTLE_MAINTENANCE_PREG}, {0x3232, SIERRA_CREQ_FSMCLK_SEL_PREG}, {0x0000, SIERRA_CREQ_EQ_CTRL_PREG}, - {0x8000, SIERRA_CREQ_SPARE_PREG}, + {0x0000, SIERRA_CREQ_SPARE_PREG}, {0xCC44, SIERRA_CREQ_EQ_OPEN_EYE_THRESH_PREG}, - {0x8453, SIERRA_CTLELUT_CTRL_PREG}, - {0x4110, SIERRA_DFE_ECMP_RATESEL_PREG}, - {0x4110, SIERRA_DFE_SMP_RATESEL_PREG}, - {0x0002, SIERRA_DEQ_PHALIGN_CTRL}, + {0x8452, SIERRA_CTLELUT_CTRL_PREG}, + {0x4121, SIERRA_DFE_ECMP_RATESEL_PREG}, + {0x4121, SIERRA_DFE_SMP_RATESEL_PREG}, + {0x0003, SIERRA_DEQ_PHALIGN_CTRL}, {0x3200, SIERRA_DEQ_CONCUR_CTRL1_PREG}, {0x5064, SIERRA_DEQ_CONCUR_CTRL2_PREG}, {0x0030, SIERRA_DEQ_EPIPWR_CTRL2_PREG},
@@ -725,7 +725,7 @@ static struct cdns_reg_pairs cdns_usb_ln_regs_ext_ssc[] = { {0x5A5A, SIERRA_DEQ_ERRCMP_CTRL_PREG}, {0x02F5, SIERRA_DEQ_OFFSET_CTRL_PREG}, {0x02F5, SIERRA_DEQ_GAIN_CTRL_PREG}, - {0x9A8A, SIERRA_DEQ_VGATUNE_CTRL_PREG}, + {0x9999, SIERRA_DEQ_VGATUNE_CTRL_PREG}, {0x0014, SIERRA_DEQ_GLUT0}, {0x0014, SIERRA_DEQ_GLUT1}, {0x0014, SIERRA_DEQ_GLUT2},
@@ -772,6 +772,7 @@ static struct cdns_reg_pairs cdns_usb_ln_regs_ext_ssc[] = { {0x000F, SIERRA_LFPSFILT_NS_PREG}, {0x0009, SIERRA_LFPSFILT_RD_PREG}, {0x0001, SIERRA_LFPSFILT_MP_PREG}, + {0x6013, SIERRA_SIGDET_SUPPORT_PREG}, {0x8013, SIERRA_SDFILT_H2L_A_PREG}, {0x8009, SIERRA_SDFILT_L2H_PREG}, {0x0024, SIERRA_RXBUFFER_CTLECTRL_PREG},
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 223/477 powerpc/ps3: Fix kexec shutdown hang
In reply to Greg Kroah-HartmanFrom: Geoff Levand <[email protected]>
[ Upstream commit 126554465d93b10662742128918a5fc338cda4aa ]
The ps3_mm_region_destroy() and ps3_mm_vas_destroy() routines are called very late in the shutdown via kexec's mmu_cleanup_all routine. By the time mmu_cleanup_all runs it is too late to use udbg_printf, and calling it will cause PS3 systems to hang.
Remove all debugging statements from ps3_mm_region_destroy() and ps3_mm_vas_destroy() and replace any error reporting with calls to lv1_panic.
With this change builds with 'DEBUG' defined will not cause kexec reboots to hang, and builds with 'DEBUG' defined or not will end in lv1_panic if an error is encountered.
--- arch/powerpc/platforms/ps3/mm.c | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-)
arch/powerpc/platforms/ps3/mm.c +12 -10
@@ -200,13 +200,14 @@ void ps3_mm_vas_destroy(void) {int result; -DBG ("%s:%d: map.vas_id = %llu\n" , __func__, __LINE__, map.vas_id); -if (map.vas_id) { result =lv1_select_virtual_address_space (0 ); -BUG_ON (result); - result =lv1_destruct_virtual_address_space (map.vas_id); -BUG_ON (result); + result +=lv1_destruct_virtual_address_space (map.vas_id); + +if (result) { +lv1_panic (0 ); + } + map.vas_id =0 ; } }
@@ -304,19 +305,20 @@ static void ps3_mm_region_destroy(struct mem_region *r)int result;if (!r->destroy) { -pr_info ("%s:%d: Not destroying high region: %llxh %llxh\n" , - __func__, __LINE__, r->base, r->size);return ; } -DBG ("%s:%d: r->base = %llxh\n" , __func__, __LINE__, r->base); -if (r->base) { result =lv1_release_memory (r->base); -BUG_ON (result); + +if (result) { +lv1_panic (0 ); + } + r->size = r->base = r->offset =0 ; map.total = map.rm.size; } +ps3_mm_set_repository_highmem (NULL ); }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 224/477 iommu/arm-smmu-v3: Dont reserve implementation defined register space
In reply to Greg Kroah-HartmanFrom: Jean-Philippe Brucker <[email protected]>
[ Upstream commit 52f3fab0067d6fa9e99c1b7f63265dd48ca76046 ]
Some SMMUv3 implementation embed the Perf Monitor Group Registers (PMCG) inside the first 64kB region of the SMMU. Since PMCG are managed by a separate driver, this layout causes resource reservation conflicts during boot.
To avoid this conflict, don't reserve the MMIO regions that are implementation defined. Although devm_ioremap_resource() still works on full pages under the hood, this way we benefit from resource conflict checks.
--- drivers/iommu/arm-smmu-v3.c | 35 +++++++++++++++++++++++++++++++---- 1 file changed, 31 insertions(+), 4 deletions(-)
drivers/iommu/arm-smmu-v3.c +31 -4
@@ -171,6 +171,8 @@#define ARM_SMMU_PRIQ_IRQ_CFG1 0xd8#define ARM_SMMU_PRIQ_IRQ_CFG2 0xdc +#define ARM_SMMU_REG_SZ 0xe00 +/* Common MSI config fields */ #define MSI_CFG0_ADDR_MASK GENMASK_ULL(51, 2)#define MSI_CFG2_SH GENMASK(5, 4)
@@ -628,6 +630,7 @@ struct arm_smmu_strtab_cfg {struct arm_smmu_device {struct device *dev;void __iomem *base; +void __iomem *page1;#define ARM_SMMU_FEAT_2_LVL_STRTAB (1 << 0)#define ARM_SMMU_FEAT_2_LVL_CDTAB (1 << 1)
@@ -733,9 +736,8 @@ static struct arm_smmu_option_prop arm_smmu_options[] = {static inline void __iomem *arm_smmu_page1_fixup (unsigned long offset,struct arm_smmu_device *smmu) { -if ((offset >SZ_64K ) && - (smmu->options &ARM_SMMU_OPT_PAGE0_REGS_ONLY )) - offset -=SZ_64K ; +if (offset >SZ_64K ) +return smmu->page1 + offset -SZ_64K ;return smmu->base + offset; }
@@ -4021,6 +4023,18 @@ err_reset_pci_ops: __maybe_unused;return err; } +static void __iomem *arm_smmu_ioremap (struct device *dev,resource_size_t start, +resource_size_t size) +{ +struct resource res = { + .flags =IORESOURCE_MEM , + .start = start, + .end = start + size -1 , + }; + +return devm_ioremap_resource (dev, &res); +} +static int arm_smmu_device_probe (struct platform_device *pdev) {int irq, ret;
@@ -4056,10 +4070,23 @@ static int arm_smmu_device_probe(struct platform_device *pdev) } ioaddr = res->start; - smmu->base =devm_ioremap_resource (dev, res); +/* +* Don't map the IMPLEMENTATION DEFINED regions, since they may contain +* the PMCG registers which are reserved by the PMU driver. +*/ + smmu->base =arm_smmu_ioremap (dev, ioaddr,ARM_SMMU_REG_SZ );if (IS_ERR (smmu->base))return PTR_ERR (smmu->base); +if (arm_smmu_resource_size (smmu) >SZ_64K ) { + smmu->page1 =arm_smmu_ioremap (dev, ioaddr +SZ_64K , +ARM_SMMU_REG_SZ ); +if (IS_ERR (smmu->page1)) +return PTR_ERR (smmu->page1); + }else { + smmu->page1 = smmu->base; + } +/* Interrupt lines */ irq =platform_get_irq_byname_optional (pdev,"combined" );
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 225/477 vfio-pci: Mask cap zero
In reply to Greg Kroah-HartmanFrom: Alex Williamson <[email protected]>
[ Upstream commit bc138db1b96264b9c1779cf18d5a3b186aa90066 ]
The PCI Code and ID Assignment Specification changed capability ID 0 from reserved to a NULL capability in the v1.1 revision. The NULL capability is defined to include only the 16-bit capability header, ie. only the ID and next pointer. Unfortunately vfio-pci creates a map of config space, where ID 0 is used to reserve the standard type 0 header. Finding an actual capability with this ID therefore results in a bogus range marked in that map and conflicts with subsequent capabilities. As this seems to be a dummy capability anyway and we already support dropping capabilities, let's hide this one rather than delving into the potentially subtle dependencies within our map.
Seen on an NVIDIA Tesla T4.
--- drivers/vfio/pci/vfio_pci_config.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-)
drivers/vfio/pci/vfio_pci_config.c +6 -1
@@ -1462,7 +1462,12 @@ static int vfio_cap_init(struct vfio_pci_device *vdev)if (ret)return ret; -if (cap <=PCI_CAP_ID_MAX ) { +/* +* ID 0 is a NULL capability, conflicting with our fake +* PCI_CAP_ID_BASIC. As it has no content, consider it +* hidden for now. +*/ +if (cap && cap <=PCI_CAP_ID_MAX ) { len = pci_cap_length[cap];if (len ==0xFF ) {/* Variable length */ len =vfio_cap_len (vdev, cap, pos);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 226/477 usb/ohci-platform: Fix a warning when hibernating
In reply to Greg Kroah-HartmanFrom: Qais Yousef <[email protected]>
[ Upstream commit 1cb3b0095c3d0bb96912bfbbce4fc006d41f367c ]
The following warning was observed when attempting to suspend to disk using a USB flash as a swap device.
[ 111.779649] ------------[ cut here ]------------ [ 111.788382] URB (____ptrval____) submitted while active [ 111.796646] WARNING: CPU: 3 PID: 365 at drivers/usb/core/urb.c:363 usb_submit_urb+0x3d8/0x590 [ 111.805417] Modules linked in: [ 111.808584] CPU: 3 PID: 365 Comm: kworker/3:2 Not tainted 5.6.0-rc6-00002-gdfd1731f9a3e-dirty #545 [ 111.817796] Hardware name: ARM Juno development board (r2) (DT) [ 111.823896] Workqueue: usb_hub_wq hub_event [ 111.828217] pstate: 60000005 (nZCv daif -PAN -UAO) [ 111.833156] pc : usb_submit_urb+0x3d8/0x590 [ 111.837471] lr : usb_submit_urb+0x3d8/0x590 [ 111.841783] sp : ffff800018de38b0 [ 111.845205] x29: ffff800018de38b0 x28: 0000000000000003 [ 111.850682] x27: ffff000970530b20 x26: ffff8000133fd000 [ 111.856159] x25: ffff8000133fd000 x24: ffff800018de3b38 [ 111.861635] x23: 0000000000000004 x22: 0000000000000c00 [ 111.867112] x21: 0000000000000000 x20: 00000000fffffff0 [ 111.872589] x19: ffff0009704e7a00 x18: ffffffffffffffff [ 111.878065] x17: 00000000a7c8f4bc x16: 000000002af33de8 [ 111.883542] x15: ffff8000133fda88 x14: 0720072007200720 [ 111.889019] x13: 0720072007200720 x12: 0720072007200720 [ 111.894496] x11: 0000000000000000 x10: 00000000a5286134 [ 111.899973] x9 : 0000000000000002 x8 : ffff000970c837a0 [ 111.905449] x7 : 0000000000000000 x6 : ffff800018de3570 [ 111.910926] x5 : 0000000000000001 x4 : 0000000000000003 [ 111.916401] x3 : 0000000000000000 x2 : ffff800013427118 [ 111.921879] x1 : 9d4e965b4b7d7c00 x0 : 0000000000000000 [ 111.927356] Call trace: [ 111.929892] usb_submit_urb+0x3d8/0x590 [ 111.933852] hub_activate+0x108/0x7f0 [ 111.937633] hub_resume+0xac/0x148 [ 111.941149] usb_resume_interface.isra.10+0x60/0x138 [ 111.946265] usb_resume_both+0xe4/0x140 [ 111.950225] usb_runtime_resume+0x24/0x30 [ 111.954365] __rpm_callback+0xdc/0x138 [ 111.958236] rpm_callback+0x34/0x98 [ 111.961841] rpm_resume+0x4a8/0x720 [ 111.965445] rpm_resume+0x50c/0x720 [ 111.969049] __pm_runtime_resume+0x4c/0xb8 [ 111.973276] usb_autopm_get_interface+0x28/0x60 [ 111.977948] hub_event+0x80/0x16d8 [ 111.981466] process_one_work+0x2a4/0x748 [ 111.985604] worker_thread+0x48/0x498 [ 111.989387] kthread+0x13c/0x140 [ 111.992725] ret_from_fork+0x10/0x18 [ 111.996415] irq event stamp: 354 [ 111.999756] hardirqs last enabled at (353): [<ffff80001019ea1c>] console_unlock+0x504/0x5b8 [ 112.008441] hardirqs last disabled at (354): [<ffff8000100a95d0>] do_debug_exception+0x1a8/0x258 [ 112.017479] softirqs last enabled at (350): [<ffff8000100818a4>] __do_softirq+0x4bc/0x568 [ 112.025984] softirqs last disabled at (343): [<ffff8000101145a4>] irq_exit+0x144/0x150 [ 112.034129] ---[ end trace dc96030b9cf6c8a3 ]---
The problem was tracked down to a missing call to pm_runtime_set_active() on resume in ohci-platform.
--- drivers/usb/host/ohci-platform.c | 5 +++++ 1 file changed, 5 insertions(+)
drivers/usb/host/ohci-platform.c +5 -0
@@ -299,6 +299,11 @@ static int ohci_platform_resume(struct device *dev) }ohci_resume (hcd, false); + +pm_runtime_disable (dev); +pm_runtime_set_active (dev); +pm_runtime_enable (dev); +return 0 ; }#endif /* CONFIG_PM_SLEEP */
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 227/477 drm/msm: Fix undefined "rd_full" link error
In reply to Greg Kroah-HartmanFrom: Bjorn Andersson <[email protected]>
[ Upstream commit 20aebe83698feb107d5a66b6cfd1d54459ccdfcf ]
rd_full should be defined outside the CONFIG_DEBUG_FS region, in order to be able to link the msm driver even when CONFIG_DEBUG_FS is disabled.
--- drivers/gpu/drm/msm/msm_rd.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/gpu/drm/msm/msm_rd.c +2 -2
@@ -29,8 +29,6 @@* or shader programs (if not emitted inline in cmdstream). */ -#ifdef CONFIG_DEBUG_FS -#include <linux/circ_buf.h> #include <linux/debugfs.h> #include <linux/kfifo.h>
@@ -47,6 +45,8 @@ bool rd_full = false;MODULE_PARM_DESC (rd_full,"If true, $debugfs/.../rd will snapshot all buffer contents" );module_param_named (rd_full, rd_full, bool,0600 ); +#ifdef CONFIG_DEBUG_FS +enum rd_sect_type {RD_NONE , RD_TEST, /* ascii text */
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 228/477 drm/msm/mdp5: Fix mdp5_init error path for failed mdp5_kms allocation
In reply to Greg Kroah-HartmanFrom: Roy Spliet <[email protected]>
[ Upstream commit e4337877c5d578722c0716f131fb774522013cf5 ]
When allocation for mdp5_kms fails, calling mdp5_destroy() leads to undefined behaviour, likely a nullptr exception or use-after-free troubles.
--- drivers/gpu/drm/msm/disp/mdp5/mdp5_kms.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/gpu/drm/msm/disp/mdp5/mdp5_kms.c +2 -1
@@ -943,7 +943,8 @@ static int mdp5_init(struct platform_device *pdev, struct drm_device *dev)return 0 ; fail: -mdp5_destroy (pdev); +if (mdp5_kms) +mdp5_destroy (pdev);return ret; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 229/477 ASoC: Intel: bytcr_rt5640: Add quirk for Toshiba Encore WT8-A tablet
In reply to Greg Kroah-HartmanFrom: Hans de Goede <[email protected]>
[ Upstream commit 0e0e10fde0e9808d1991268f5dca69fb36c025f7 ]
The Toshiba Encore WT8-A tablet almost fully works with the default settings for non-CR Bay Trail devices. The only problem is that its jack-detect switch is not inverted (it is active high instead of the normal active low).
Add a quirk for this model using the default settings + BYT_RT5640_JD_NOT_INV.
--- sound/soc/intel/boards/bytcr_rt5640.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
sound/soc/intel/boards/bytcr_rt5640.c +12 -0
@@ -742,6 +742,18 @@ static const struct dmi_system_id byt_rt5640_quirk_table[] = {BYT_RT5640_SSP0_AIF1 | BYT_RT5640_MCLK_EN), }, + { /* Toshiba Encore WT8-A */ + .matches = { +DMI_EXACT_MATCH (DMI_SYS_VENDOR ,"TOSHIBA" ), + DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "TOSHIBA WT8-A"), + }, + .driver_data = (void *)(BYT_RT5640_DMIC1_MAP | +BYT_RT5640_JD_SRC_JD2_IN4N | +BYT_RT5640_OVCD_TH_2000UA | +BYT_RT5640_OVCD_SF_0P75 | +BYT_RT5640_JD_NOT_INV | + BYT_RT5640_MCLK_EN), + }, { /* Catch-all for generic Insyde tablets, must be last */ .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Insyde"),
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 230/477 USB: host: ehci-mxc: Add error handling in ehci_mxc_drv_probe()
In reply to Greg Kroah-HartmanFrom: Tang Bin <[email protected]>
[ Upstream commit d49292025f79693d3348f8e2029a8b4703be0f0a ]
The function ehci_mxc_drv_probe() does not perform sufficient error checking after executing platform_get_irq(), thus fix it.
--- drivers/usb/host/ehci-mxc.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/usb/host/ehci-mxc.c +2 -0
@@ -50,6 +50,8 @@ static int ehci_mxc_drv_probe(struct platform_device *pdev) } irq =platform_get_irq (pdev,0 ); +if (irq <0 ) +return irq; hcd =usb_create_hcd (&ehci_mxc_hc_driver, dev,dev_name (dev));if (!hcd)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 231/477 tty: n_gsm: Fix bogus i++ in gsm_data_kick
In reply to Greg Kroah-HartmanFrom: Gregory CLEMENT <[email protected]>
[ Upstream commit 4dd31f1ffec6c370c3c2e0c605628bf5e16d5c46 ]
When submitting the previous fix "tty: n_gsm: Fix waking up upper tty layer when room available". It was suggested to switch from a while to a for loop, but when doing it, there was a remaining bogus i++.
This patch removes this i++ and also reorganizes the code making it more compact.
--- drivers/tty/n_gsm.c | 14 +++----------- 1 file changed, 3 insertions(+), 11 deletions(-)
drivers/tty/n_gsm.c +3 -11
@@ -711,17 +711,9 @@ static void gsm_data_kick(struct gsm_mux *gsm, struct gsm_dlci *dlci) }else {int i =0 ; -for (i =0 ; i <NUM_DLCI ; i++) { -struct gsm_dlci *dlci; - - dlci = gsm->dlci[i]; -if (dlci ==NULL ) { - i++; -continue ; - } - -tty_port_tty_wakeup (&dlci->port); - } +for (i =0 ; i <NUM_DLCI ; i++) +if (gsm->dlci[i]) +tty_port_tty_wakeup (&gsm->dlci[i]->port); } } }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 232/477 coresight: Fix support for sparsely populated ports
In reply to Greg Kroah-HartmanFrom: Suzuki K Poulose <[email protected]>
[ Upstream commit d375b356e687f2eefb51ddc3f1f2414cfa498f86 ]
On some systems the firmware may not describe all the ports connected to a component (e.g, for security reasons). This could be especially problematic for "funnels" where we could end up in modifying memory beyond the allocated space for refcounts.
e.g, for a funnel with input ports listed 0, 3, 5, nr_inport = 3. However the we could access refcnts[5] while checking for references, like :
[ 526.110401] ================================================================== [ 526.117988] BUG: KASAN: slab-out-of-bounds in funnel_enable+0x54/0x1b0 [ 526.124706] Read of size 4 at addr ffffff8135f9549c by task bash/1114 [ 526.131324] [ 526.132886] CPU: 3 PID: 1114 Comm: bash Tainted: G S 5.4.25 #232 [ 526.140397] Hardware name: Qualcomm Technologies, Inc. SC7180 IDP (DT) [ 526.147113] Call trace: [ 526.149653] dump_backtrace+0x0/0x188 [ 526.153431] show_stack+0x20/0x2c [ 526.156852] dump_stack+0xdc/0x144 [ 526.160370] print_address_description+0x3c/0x494 [ 526.165211] __kasan_report+0x144/0x168 [ 526.169170] kasan_report+0x10/0x18 [ 526.172769] check_memory_region+0x1a4/0x1b4 [ 526.177164] __kasan_check_read+0x18/0x24 [ 526.181292] funnel_enable+0x54/0x1b0 [ 526.185072] coresight_enable_path+0x104/0x198 [ 526.189649] coresight_enable+0x118/0x26c
...
[ 526.237782] Allocated by task 280: [ 526.241298] __kasan_kmalloc+0xf0/0x1ac [ 526.245249] kasan_kmalloc+0xc/0x14 [ 526.248849] __kmalloc+0x28c/0x3b4 [ 526.252361] coresight_register+0x88/0x250 [ 526.256587] funnel_probe+0x15c/0x228 [ 526.260365] dynamic_funnel_probe+0x20/0x2c [ 526.264679] amba_probe+0xbc/0x158 [ 526.268193] really_probe+0x144/0x408 [ 526.271970] driver_probe_device+0x70/0x140
...
[ 526.316810] [ 526.318364] Freed by task 0: [ 526.321344] (stack is not available) [ 526.325024] [ 526.326580] The buggy address belongs to the object at ffffff8135f95480 [ 526.326580] which belongs to the cache kmalloc-128 of size 128 [ 526.339439] The buggy address is located 28 bytes inside of [ 526.339439] 128-byte region [ffffff8135f95480, ffffff8135f95500) [ 526.351399] The buggy address belongs to the page: [ 526.356342] page:ffffffff04b7e500 refcount:1 mapcount:0 mapping:ffffff814b00c380 index:0x0 compound_mapcount: 0 [ 526.366711] flags: 0x4000000000010200(slab|head) [ 526.371475] raw: 4000000000010200 ffffffff05034008 ffffffff0501eb08 ffffff814b00c380 [ 526.379435] raw: 0000000000000000 0000000000190019 00000001ffffffff 0000000000000000 [ 526.387393] page dumped because: kasan: bad access detected [ 526.393128] [ 526.394681] Memory state around the buggy address: [ 526.399619] ffffff8135f95380: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc [ 526.407046] ffffff8135f95400: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc [ 526.414473] >ffffff8135f95480: 04 fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc [ 526.421900] ^ [ 526.426029] ffffff8135f95500: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc [ 526.433456] ffffff8135f95580: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc [ 526.440883] ==================================================================
To keep the code simple, we now track the maximum number of possible input/output connections to/from this component @ nr_inport and nr_outport in platform_data, respectively. Thus the output connections could be sparse and code is adjusted to skip the unspecified connections.
--- .../hwtracing/coresight/coresight-platform.c | 85 +++++++++++++------ drivers/hwtracing/coresight/coresight.c | 7 +- include/linux/coresight.h | 10 ++- 3 files changed, 72 insertions(+), 30 deletions(-)
drivers/hwtracing/coresight/coresight-platform.c +60 -25
@@ -87,6 +87,7 @@ static void of_coresight_get_ports_legacy(const struct device_node *node, int *nr_inport, int *nr_outport) { struct device_node *ep = NULL; +struct of_endpoint endpoint;int in =0 , out =0 ; do {
@@ -94,10 +95,16 @@ static void of_coresight_get_ports_legacy(const struct device_node *node,if (!ep)break ; -if (of_coresight_legacy_ep_is_input (ep)) - in++; -else - out++; +if (of_graph_parse_endpoint (ep, &endpoint)) +continue ; + +if (of_coresight_legacy_ep_is_input (ep)) { + in = (endpoint.port +1 > in) ? + endpoint.port +1 : in; + }else { + out = (endpoint.port +1 ) > out ? + endpoint.port +1 : out; + } }while (ep);
@@ -137,9 +144,16 @@ of_coresight_count_ports(struct device_node *port_parent) {int i =0 ;struct device_node *ep =NULL ; +struct of_endpoint endpoint; + +while ((ep =of_graph_get_next_endpoint (port_parent, ep))) { +/* Defer error handling to parsing */ +if (of_graph_parse_endpoint (ep, &endpoint)) +continue ; +if (endpoint.port +1 > i) + i = endpoint.port +1 ; + } -while ((ep =of_graph_get_next_endpoint (port_parent, ep))) - i++;return i; }
@@ -191,14 +205,12 @@ static int of_coresight_get_cpu(struct device *dev)* Parses the local port, remote device name and the remote port. * * Returns : -* 1 - If the parsing is successful and a connection record -* was created for an output connection. * 0 - If the parsing completed without any fatal errors. * -Errno - Fatal error, abort the scanning. */ static int of_coresight_parse_endpoint (struct device *dev,struct device_node *ep, -struct coresight_connection *conn) +struct coresight_platform_data *pdata) {int ret =0 ;struct of_endpoint endpoint, rendpoint;
@@ -206,6 +218,7 @@ static int of_coresight_parse_endpoint(struct device *dev,struct device_node *rep =NULL ;struct device *rdev =NULL ;struct fwnode_handle *rdev_fwnode; +struct coresight_connection *conn; do { /* Parse the local port details */
@@ -232,6 +245,13 @@ static int of_coresight_parse_endpoint(struct device *dev,break ; } + conn = &pdata->conns[endpoint.port]; +if (conn->child_fwnode) { +dev_warn (dev,"Duplicate output port %d\n" , + endpoint.port); + ret = -EINVAL ; +break ; + } conn->outport = endpoint.port;/* * Hold the refcount to the target device. This could be
@@ -244,7 +264,6 @@ static int of_coresight_parse_endpoint(struct device *dev, conn->child_fwnode =fwnode_handle_get (rdev_fwnode); conn->child_port = rendpoint.port;/* Connection record updated */ - ret =1 ; }while (0 );of_node_put (rparent);
@@ -258,7 +277,6 @@ static int of_get_coresight_platform_data(struct device *dev, struct coresight_platform_data *pdata) {int ret =0 ; -struct coresight_connection *conn;struct device_node *ep =NULL ;const struct device_node *parent =NULL ;bool legacy_binding = false;
@@ -287,8 +305,6 @@ static int of_get_coresight_platform_data(struct device *dev,dev_warn_once (dev,"Uses obsolete Coresight DT bindings\n" ); } - conn = pdata->conns; -/* Iterate through each output port to discover topology */ while ((ep =of_graph_get_next_endpoint (parent, ep))) {/*
@@ -300,15 +316,9 @@ static int of_get_coresight_platform_data(struct device *dev,if (legacy_binding &&of_coresight_legacy_ep_is_input (ep))continue ; - ret =of_coresight_parse_endpoint (dev, ep, conn); -switch (ret) { -case 1 : - conn++;/* Fall through */ -case 0 : -break ; -default : + ret =of_coresight_parse_endpoint (dev, ep, pdata); +if (ret)return ret; - } }return 0 ;
@@ -647,6 +657,16 @@ static int acpi_coresight_parse_link(struct acpi_device *adev,* coresight_remove_match(). */ conn->child_fwnode =fwnode_handle_get (&r_adev->fwnode); + }else if (dir ==ACPI_CORESIGHT_LINK_SLAVE ) { +/* +* We are only interested in the port number +* for the input ports at this component. +* Store the port number in child_port. +*/ + conn->child_port = fields[0 ].integer.value; + }else { +/* Invalid direction */ +return -EINVAL ; }return dir;
@@ -692,10 +712,20 @@ static int acpi_coresight_parse_graph(struct acpi_device *adev,return dir;if (dir ==ACPI_CORESIGHT_LINK_MASTER ) { - pdata->nr_outport++; +if (ptr->outport > pdata->nr_outport) + pdata->nr_outport = ptr->outport; ptr++; }else { - pdata->nr_inport++; +WARN_ON (pdata->nr_inport == ptr->child_port); +/* +* We do not track input port connections for a device. +* However we need the highest port number described, +* which can be recorded now and reuse this connection +* record for an output connection. Hence, do not move +* the ptr for input connections +*/ +if (ptr->child_port > pdata->nr_inport) + pdata->nr_inport = ptr->child_port; } }
@@ -704,8 +734,13 @@ static int acpi_coresight_parse_graph(struct acpi_device *adev,return rc;/* Copy the connection information to the final location */ -for (i =0 ; i < pdata->nr_outport; i++) - pdata->conns[i] = conns[i]; +for (i =0 ; conns + i < ptr; i++) { +int port = conns[i].outport; + +/* Duplicate output port */ +WARN_ON (pdata->conns[port].child_fwnode); + pdata->conns[port] = conns[i]; + }devm_kfree (&adev->dev, conns);return 0 ;
drivers/hwtracing/coresight/coresight.c +6 -1
@@ -1053,6 +1053,9 @@ static int coresight_orphan_match(struct device *dev, void *data)for (i =0 ; i < i_csdev->pdata->nr_outport; i++) { conn = &i_csdev->pdata->conns[i]; +/* Skip the port if FW doesn't describe it */ +if (!conn->child_fwnode) +continue ;/* We have found at least one orphan connection */ if (conn->child_dev ==NULL ) {/* Does it match this newly added device? */
@@ -1091,6 +1094,8 @@ static void coresight_fixup_device_conns(struct coresight_device *csdev)for (i =0 ; i < csdev->pdata->nr_outport; i++) {struct coresight_connection *conn = &csdev->pdata->conns[i]; +if (!conn->child_fwnode) +continue ; conn->child_dev =coresight_find_csdev_by_fwnode (conn->child_fwnode);if (!conn->child_dev)
@@ -1118,7 +1123,7 @@ static int coresight_remove_match(struct device *dev, void *data)for (i =0 ; i < iterator->pdata->nr_outport; i++) { conn = &iterator->pdata->conns[i]; -if (conn->child_dev ==NULL ) +if (conn->child_dev ==NULL || conn->child_fwnode ==NULL )continue ;if (csdev->dev.fwnode == conn->child_fwnode) {
include/linux/coresight.h +6 -4
@@ -100,10 +100,12 @@ union coresight_dev_subtype { };/** -* struct coresight_platform_data - data harvested from the DT specification -* @nr_inport: number of input ports for this component. -* @nr_outport: number of output ports for this component. -* @conns: Array of nr_outport connections from this component +* struct coresight_platform_data - data harvested from the firmware +* specification. +* +* @nr_inport: Number of elements for the input connections. +* @nr_outport: Number of elements for the output connections. +* @conns: Sparse array of nr_outport connections from this component. */ struct coresight_platform_data {int nr_inport;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 233/477 coresight: etm4x: Fix use-after-free of per-cpu etm drvdata
In reply to Greg Kroah-HartmanFrom: Suzuki K Poulose <[email protected]>
[ Upstream commit 3f4943d422c5febbb3c764670011a00eb2a86238 ]
etm probe could be deferred due to the dependency in the trace path chain and may be retried. We need to clear the per-cpu etmdrvdata entry for the etm in case of a failure to avoid use-after-free cases as reported below:
KASAN use-after-free bug in etm4_cpu_pm_notify():
[ 8.574566] coresight etm0: CPU0: ETM v4.2 initialized [ 8.581920] BUG: KASAN: use-after-free in etm4_cpu_pm_notify+0x580/0x2024 [ 8.581925] Read of size 8 at addr ffffff813304f8c8 by task swapper/3/0 [ 8.581927] [ 8.581934] CPU: 3 PID: 0 Comm: swapper/3 Tainted: G S W 5.4.28 #314 [ 8.587775] coresight etm1: CPU1: ETM v4.2 initialized [ 8.594195] Call trace: [ 8.594205] dump_backtrace+0x0/0x188 [ 8.594209] show_stack+0x20/0x2c [ 8.594216] dump_stack+0xdc/0x144 [ 8.594227] print_address_description+0x3c/0x494 [ 8.594232] __kasan_report+0x144/0x168 [ 8.601598] coresight etm2: CPU2: ETM v4.2 initialized [ 8.602563] kasan_report+0x10/0x18 [ 8.602568] check_memory_region+0x1a4/0x1b4 [ 8.602572] __kasan_check_read+0x18/0x24 [ 8.602577] etm4_cpu_pm_notify+0x580/0x2024 [ 8.665945] notifier_call_chain+0x5c/0x90 [ 8.670166] __atomic_notifier_call_chain+0x90/0xf8 [ 8.675182] cpu_pm_notify+0x40/0x6c [ 8.678858] cpu_pm_enter+0x38/0x80 [ 8.682451] psci_enter_idle_state+0x34/0x70 [ 8.686844] cpuidle_enter_state+0xb8/0x20c [ 8.691143] cpuidle_enter+0x38/0x4c [ 8.694820] call_cpuidle+0x3c/0x68 [ 8.698408] do_idle+0x1a0/0x280 [ 8.701729] cpu_startup_entry+0x24/0x28 [ 8.705768] secondary_start_kernel+0x15c/0x170 [ 8.710423] [ 8.711972] Allocated by task 242: [ 8.715473] __kasan_kmalloc+0xf0/0x1ac [ 8.719426] kasan_slab_alloc+0x14/0x1c [ 8.723375] __kmalloc_track_caller+0x23c/0x388 [ 8.728040] devm_kmalloc+0x38/0x94 [ 8.731632] etm4_probe+0x48/0x3c8 [ 8.735140] amba_probe+0xbc/0x158 [ 8.738645] really_probe+0x144/0x408 [ 8.742412] driver_probe_device+0x70/0x140 [ 8.746716] __device_attach_driver+0x9c/0x110 [ 8.751287] bus_for_each_drv+0x90/0xd8 [ 8.755236] __device_attach+0xb4/0x164 [ 8.759188] device_initial_probe+0x20/0x2c [ 8.763490] bus_probe_device+0x34/0x94 [ 8.767436] device_add+0x34c/0x3e0 [ 8.771029] amba_device_try_add+0x68/0x440 [ 8.775332] amba_deferred_retry_func+0x48/0xc8 [ 8.779997] process_one_work+0x344/0x648 [ 8.784127] worker_thread+0x2ac/0x47c [ 8.787987] kthread+0x128/0x138 [ 8.791313] ret_from_fork+0x10/0x18 [ 8.794993] [ 8.796532] Freed by task 242: [ 8.799684] __kasan_slab_free+0x15c/0x22c [ 8.803897] kasan_slab_free+0x10/0x1c [ 8.807761] kfree+0x25c/0x4bc [ 8.810913] release_nodes+0x240/0x2b0 [ 8.814767] devres_release_all+0x3c/0x54 [ 8.818887] really_probe+0x178/0x408 [ 8.822661] driver_probe_device+0x70/0x140 [ 8.826963] __device_attach_driver+0x9c/0x110 [ 8.831539] bus_for_each_drv+0x90/0xd8 [ 8.835487] __device_attach+0xb4/0x164 [ 8.839431] device_initial_probe+0x20/0x2c [ 8.843732] bus_probe_device+0x34/0x94 [ 8.847678] device_add+0x34c/0x3e0 [ 8.851274] amba_device_try_add+0x68/0x440 [ 8.855576] amba_deferred_retry_func+0x48/0xc8 [ 8.860240] process_one_work+0x344/0x648 [ 8.864366] worker_thread+0x2ac/0x47c [ 8.868228] kthread+0x128/0x138 [ 8.871557] ret_from_fork+0x10/0x18 [ 8.875231] [ 8.876782] The buggy address belongs to the object at ffffff813304f800 [ 8.876782] which belongs to the cache kmalloc-1k of size 1024 [ 8.889632] The buggy address is located 200 bytes inside of [ 8.889632] 1024-byte region [ffffff813304f800, ffffff813304fc00) [ 8.901761] The buggy address belongs to the page: [ 8.906695] page:ffffffff04ac1200 refcount:1 mapcount:0 mapping:ffffff8146c03800 index:0x0 compound_mapcount: 0 [ 8.917047] flags: 0x4000000000010200(slab|head) [ 8.921799] raw: 4000000000010200 dead000000000100 dead000000000122 ffffff8146c03800 [ 8.929753] raw: 0000000000000000 0000000000100010 00000001ffffffff 0000000000000000 [ 8.937703] page dumped because: kasan: bad access detected [ 8.943433] [ 8.944974] Memory state around the buggy address: [ 8.949903] ffffff813304f780: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc [ 8.957320] ffffff813304f800: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 8.964742] >ffffff813304f880: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 8.972157] ^ [ 8.977886] ffffff813304f900: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 8.985298] ffffff813304f980: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 8.992713] ==================================================================
--- drivers/hwtracing/coresight/coresight-etm4x.c | 1 + 1 file changed, 1 insertion(+)
drivers/hwtracing/coresight/coresight-etm4x.c +1 -0
@@ -1527,6 +1527,7 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)return 0 ; err_arch_supported: + etmdrvdata[drvdata->cpu] =NULL ;if (--etm4_count ==0 ) {etm4_cpu_pm_unregister ();
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 234/477 fpga: dfl: afu: Corrected error handling levels
In reply to Greg Kroah-HartmanFrom: Souptick Joarder <[email protected]>
[ Upstream commit c9d7e3da1f3c4cf5dddfc5d7ce4d76d013aba1cc ]
Corrected error handling goto sequnece. Level put_pages should be called when pinned pages >= 0 && pinned != npages. Level free_pages should be called when pinned pages < 0.
--- drivers/fpga/dfl-afu-dma-region.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/fpga/dfl-afu-dma-region.c +2 -2
@@ -61,10 +61,10 @@ static int afu_dma_pin_pages(struct dfl_feature_platform_data *pdata, region->pages);if (pinned <0 ) { ret = pinned; - goto put_pages; + goto free_pages; }else if (pinned != npages) { ret = -EFAULT ; - goto free_pages; + goto put_pages; }dev_dbg (dev,"%d pages pinned\n" , pinned);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 235/477 clk: samsung: exynos5433: Add IGNORE_UNUSED flag to sclk_i2s1
In reply to Greg Kroah-HartmanFrom: Marek Szyprowski <[email protected]>
[ Upstream commit 25bdae0f1c6609ceaf55fe6700654f0be2253d8e ]
Mark the SCLK clock for Exynos5433 I2S1 device with IGNORE_UNUSED flag to match its behaviour with SCLK clock for AUD_I2S (I2S0) device until a proper fix for Exynos I2S driver is ready.
This fixes the following synchronous abort issue revealed by the probe order change caused by the commit 93d2e4322aa7 ("of: platform: Batch fwnode parsing when adding all top level devices")
Internal error: synchronous external abort: 96000210 [#1] PREEMPT SMP Modules linked in: CPU: 0 PID: 50 Comm: kworker/0:1 Not tainted 5.7.0-rc5+ #701 Hardware name: Samsung TM2E board (DT) Workqueue: events deferred_probe_work_func pstate: 60000005 (nZCv daif -PAN -UAO) pc : samsung_i2s_probe+0x768/0x8f0 lr : samsung_i2s_probe+0x688/0x8f0 ... Call trace: samsung_i2s_probe+0x768/0x8f0 platform_drv_probe+0x50/0xa8 really_probe+0x108/0x370 driver_probe_device+0x54/0xb8 __device_attach_driver+0x90/0xc0 bus_for_each_drv+0x70/0xc8 __device_attach+0xdc/0x140 device_initial_probe+0x10/0x18 bus_probe_device+0x94/0xa0 deferred_probe_work_func+0x70/0xa8 process_one_work+0x2a8/0x718 worker_thread+0x48/0x470 kthread+0x134/0x160 ret_from_fork+0x10/0x1c Code: 17ffffaf d503201f f94086c0 91003000 (88dffc00) ---[ end trace ccf721c9400ddbd6 ]---
--- drivers/clk/samsung/clk-exynos5433.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/clk/samsung/clk-exynos5433.c +2 -1
@@ -1706,7 +1706,8 @@ static const struct samsung_gate_clock peric_gate_clks[] __initconst = {GATE (CLK_SCLK_PCM1 ,"sclk_pcm1" ,"sclk_pcm1_peric" ,ENABLE_SCLK_PERIC ,7 ,CLK_SET_RATE_PARENT ,0 ),GATE (CLK_SCLK_I2S1 ,"sclk_i2s1" ,"sclk_i2s1_peric" , -ENABLE_SCLK_PERIC ,6 ,CLK_SET_RATE_PARENT ,0 ), +ENABLE_SCLK_PERIC ,6 , +CLK_SET_RATE_PARENT |CLK_IGNORE_UNUSED ,0 ),GATE (CLK_SCLK_SPI2 ,"sclk_spi2" ,"sclk_spi2_peric" ,ENABLE_SCLK_PERIC ,5 ,CLK_SET_RATE_PARENT ,0 ), GATE(CLK_SCLK_SPI1, "sclk_spi1", "sclk_spi1_peric", ENABLE_SCLK_PERIC,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 236/477 RDMA/hns: Bugfix for querying qkey
In reply to Greg Kroah-HartmanFrom: Lijun Ou <[email protected]>
[ Upstream commit 349be276509455ac2f19fa4051ed773082c6a27e ]
The qkey queried through the query ud qp verb is a fixed value and it should be read from qp context.
--- drivers/infiniband/hw/hns/hns_roce_hw_v2.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/infiniband/hw/hns/hns_roce_hw_v2.c +1 -1
@@ -4639,7 +4639,7 @@ static int hns_roce_v2_query_qp(struct ib_qp *ibqp, struct ib_qp_attr *qp_attr, qp_attr->path_mig_state =IB_MIG_ARMED ; qp_attr->ah_attr.type =RDMA_AH_ATTR_TYPE_ROCE ;if (hr_qp->ibqp.qp_type ==IB_QPT_UD ) - qp_attr->qkey =V2_QKEY_VAL ; + qp_attr->qkey =le32_to_cpu (context.qkey_xrcd); qp_attr->rq_psn = roce_get_field(context.byte_108_rx_reqepsn, V2_QPC_BYTE_108_RX_REQ_EPSN_M,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 237/477 RDMA/hns: Fix cmdq parameter of querying pf timer resource
In reply to Greg Kroah-HartmanFrom: Lang Cheng <[email protected]>
[ Upstream commit 441c88d5b3ff80108ff536c6cf80591187015403 ]
The firmware has reduced the number of descriptions of command HNS_ROCE_OPC_QUERY_PF_TIMER_RES to 1. The driver needs to adapt, otherwise the hardware will report error 4(CMD_NEXT_ERR).
--- drivers/infiniband/hw/hns/hns_roce_hw_v2.c | 32 ++++++++-------------- 1 file changed, 12 insertions(+), 20 deletions(-)
drivers/infiniband/hw/hns/hns_roce_hw_v2.c +12 -20
@@ -1349,34 +1349,26 @@ static int hns_roce_query_pf_resource(struct hns_roce_dev *hr_dev)static int hns_roce_query_pf_timer_resource (struct hns_roce_dev *hr_dev) {struct hns_roce_pf_timer_res_a *req_a; -struct hns_roce_cmq_desc desc[2 ]; -int ret, i; +struct hns_roce_cmq_desc desc; +int ret; -for (i =0 ; i <2 ; i++) { -hns_roce_cmq_setup_basic_desc (&desc[i], -HNS_ROCE_OPC_QUERY_PF_TIMER_RES , - true); +hns_roce_cmq_setup_basic_desc (&desc,HNS_ROCE_OPC_QUERY_PF_TIMER_RES , + true); -if (i ==0 ) - desc[i].flag |=cpu_to_le16 (HNS_ROCE_CMD_FLAG_NEXT ); -else - desc[i].flag &= ~cpu_to_le16 (HNS_ROCE_CMD_FLAG_NEXT ); - } - - ret =hns_roce_cmq_send (hr_dev, desc,2 ); + ret =hns_roce_cmq_send (hr_dev, &desc,1 );if (ret)return ret; - req_a = (struct hns_roce_pf_timer_res_a *)desc[0 ].data; + req_a = (struct hns_roce_pf_timer_res_a *)desc.data; hr_dev->caps.qpc_timer_bt_num = -roce_get_field (req_a->qpc_timer_bt_idx_num, -PF_RES_DATA_1_PF_QPC_TIMER_BT_NUM_M , -PF_RES_DATA_1_PF_QPC_TIMER_BT_NUM_S ); +roce_get_field (req_a->qpc_timer_bt_idx_num, +PF_RES_DATA_1_PF_QPC_TIMER_BT_NUM_M , +PF_RES_DATA_1_PF_QPC_TIMER_BT_NUM_S ); hr_dev->caps.cqc_timer_bt_num = -roce_get_field (req_a->cqc_timer_bt_idx_num, -PF_RES_DATA_2_PF_CQC_TIMER_BT_NUM_M , -PF_RES_DATA_2_PF_CQC_TIMER_BT_NUM_S ); +roce_get_field (req_a->cqc_timer_bt_idx_num, +PF_RES_DATA_2_PF_CQC_TIMER_BT_NUM_M , +PF_RES_DATA_2_PF_CQC_TIMER_BT_NUM_S );return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 238/477 scsi: target: tcmu: Userspace must not complete queued commands
In reply to Greg Kroah-HartmanFrom: Bodo Stroesser <[email protected]>
[ Upstream commit 61fb2482216679b9e1e797440c148bb143a5040a ]
When tcmu queues a new command - no matter whether in command ring or in qfull_queue - a cmd_id from IDR udev->commands is assigned to the command.
If userspace sends a wrong command completion containing the cmd_id of a command on the qfull_queue, tcmu_handle_completions() finds the command in the IDR and calls tcmu_handle_completion() for it. This might do some nasty things because commands in qfull_queue do not have a valid dbi list.
To fix this bug, we no longer add queued commands to the idr. Instead the cmd_id is assign when a command is written to the command ring.
Due to this change I had to adapt the source code at several places where up to now an idr_for_each had been done.
[mkp: fix checkpatch warnings]
--- drivers/target/target_core_user.c | 154 ++++++++++++++---------------- 1 file changed, 71 insertions(+), 83 deletions(-)
drivers/target/target_core_user.c +71 -83
@@ -882,41 +882,24 @@ static inline size_t tcmu_cmd_get_cmd_size(struct tcmu_cmd *tcmu_cmd,return command_size; } -static int tcmu_setup_cmd_timer (struct tcmu_cmd *tcmu_cmd,unsigned int tmo, -struct timer_list *timer) +static void tcmu_setup_cmd_timer (struct tcmu_cmd *tcmu_cmd,unsigned int tmo, +struct timer_list *timer) { -struct tcmu_dev *udev = tcmu_cmd->tcmu_dev; -int cmd_id; - -if (tcmu_cmd->cmd_id) - goto setup_timer; - - cmd_id =idr_alloc (&udev->commands, tcmu_cmd,1 ,USHRT_MAX ,GFP_NOWAIT ); -if (cmd_id <0 ) { -pr_err ("tcmu: Could not allocate cmd id.\n" ); -return cmd_id; - } - tcmu_cmd->cmd_id = cmd_id; - -pr_debug ("allocated cmd %u for dev %s tmo %lu\n" , tcmu_cmd->cmd_id, - udev->name, tmo /MSEC_PER_SEC ); - -setup_timer:if (!tmo) -return 0 ; +return ; tcmu_cmd->deadline =round_jiffies_up (jiffies +msecs_to_jiffies (tmo));if (!timer_pending (timer))mod_timer (timer, tcmu_cmd->deadline); -return 0 ; +pr_debug ("Timeout set up for cmd %p, dev = %s, tmo = %lu\n" , tcmu_cmd, + tcmu_cmd->tcmu_dev->name, tmo /MSEC_PER_SEC ); }static int add_to_qfull_queue (struct tcmu_cmd *tcmu_cmd) {struct tcmu_dev *udev = tcmu_cmd->tcmu_dev;unsigned int tmo; -int ret;/* * For backwards compat if qfull_time_out is not set use
@@ -931,13 +914,11 @@ static int add_to_qfull_queue(struct tcmu_cmd *tcmu_cmd)else tmo =TCMU_TIME_OUT ; - ret =tcmu_setup_cmd_timer (tcmu_cmd, tmo, &udev->qfull_timer); -if (ret) -return ret; +tcmu_setup_cmd_timer (tcmu_cmd, tmo, &udev->qfull_timer);list_add_tail (&tcmu_cmd->queue_entry, &udev->qfull_queue); -pr_debug ("adding cmd %u on dev %s to ring space wait queue\n" , - tcmu_cmd->cmd_id, udev->name); +pr_debug ("adding cmd %p on dev %s to ring space wait queue\n" , + tcmu_cmd, udev->name);return 0 ; }
@@ -959,7 +940,7 @@ static int queue_cmd_ring(struct tcmu_cmd *tcmu_cmd, sense_reason_t *scsi_err)struct tcmu_mailbox *mb;struct tcmu_cmd_entry *entry;struct iovec *iov; -int iov_cnt, ret; +int iov_cnt, cmd_id;uint32_t cmd_head;uint64_t cdb_off;bool copy_to_data_area;
@@ -1060,14 +1041,21 @@ static int queue_cmd_ring(struct tcmu_cmd *tcmu_cmd, sense_reason_t *scsi_err) } entry->req.iov_bidi_cnt = iov_cnt; - ret =tcmu_setup_cmd_timer (tcmu_cmd, udev->cmd_time_out, - &udev->cmd_timer); -if (ret) { -tcmu_cmd_free_data (tcmu_cmd, tcmu_cmd->dbi_cnt); + cmd_id =idr_alloc (&udev->commands, tcmu_cmd,1 ,USHRT_MAX ,GFP_NOWAIT ); +if (cmd_id <0 ) { +pr_err ("tcmu: Could not allocate cmd id.\n" ); +tcmu_cmd_free_data (tcmu_cmd, tcmu_cmd->dbi_cnt); *scsi_err =TCM_OUT_OF_RESOURCES ;return -1 ; } + tcmu_cmd->cmd_id = cmd_id; + +pr_debug ("allocated cmd id %u for cmd %p dev %s\n" , tcmu_cmd->cmd_id, + tcmu_cmd, udev->name); + +tcmu_setup_cmd_timer (tcmu_cmd, udev->cmd_time_out, &udev->cmd_timer); + entry->hdr.cmd_id = tcmu_cmd->cmd_id;/*
@@ -1279,50 +1267,39 @@ static unsigned int tcmu_handle_completions(struct tcmu_dev *udev)return handled; } -static int tcmu_check_expired_cmd (int id,void *p,void *data) +static void tcmu_check_expired_ring_cmd (struct tcmu_cmd *cmd) { -struct tcmu_cmd *cmd = p; -struct tcmu_dev *udev = cmd->tcmu_dev; -u8 scsi_status;struct se_cmd *se_cmd; -bool is_running; - -if (test_bit (TCMU_CMD_BIT_EXPIRED , &cmd->flags)) -return 0 ;if (!time_after (jiffies, cmd->deadline)) -return 0 ; +return ; - is_running =test_bit (TCMU_CMD_BIT_INFLIGHT , &cmd->flags); +set_bit (TCMU_CMD_BIT_EXPIRED , &cmd->flags); +list_del_init (&cmd->queue_entry); se_cmd = cmd->se_cmd; + cmd->se_cmd =NULL ; -if (is_running) { -/* -* If cmd_time_out is disabled but qfull is set deadline -* will only reflect the qfull timeout. Ignore it. -*/ -if (!udev->cmd_time_out) -return 0 ; +pr_debug ("Timing out inflight cmd %u on dev %s.\n" , + cmd->cmd_id, cmd->tcmu_dev->name); -set_bit (TCMU_CMD_BIT_EXPIRED , &cmd->flags); -/* -* target_complete_cmd will translate this to LUN COMM FAILURE -*/ - scsi_status =SAM_STAT_CHECK_CONDITION ; -list_del_init (&cmd->queue_entry); - cmd->se_cmd =NULL ; - }else { -list_del_init (&cmd->queue_entry); -idr_remove (&udev->commands, id); -tcmu_free_cmd (cmd); - scsi_status =SAM_STAT_TASK_SET_FULL ; - } +target_complete_cmd (se_cmd,SAM_STAT_CHECK_CONDITION ); +} -pr_debug ("Timing out cmd %u on dev %s that is %s.\n" , - id, udev->name, is_running ?"inflight" :"queued" ); +static void tcmu_check_expired_queue_cmd (struct tcmu_cmd *cmd) +{ +struct se_cmd *se_cmd; -target_complete_cmd (se_cmd, scsi_status); -return 0 ; +if (!time_after (jiffies, cmd->deadline)) +return ; + +list_del_init (&cmd->queue_entry); + se_cmd = cmd->se_cmd; +tcmu_free_cmd (cmd); + +pr_debug ("Timing out queued cmd %p on dev %s.\n" , + cmd, cmd->tcmu_dev->name); + +target_complete_cmd (se_cmd,SAM_STAT_TASK_SET_FULL ); }static void tcmu_device_timedout (struct tcmu_dev *udev)
@@ -1407,16 +1384,15 @@ static struct se_device *tcmu_alloc_device(struct se_hba *hba, const char *name)return &udev->se_dev; } -static bool run_qfull_queue (struct tcmu_dev *udev,bool fail) +static void run_qfull_queue (struct tcmu_dev *udev,bool fail) {struct tcmu_cmd *tcmu_cmd, *tmp_cmd;LIST_HEAD (cmds); -bool drained = true;sense_reason_t scsi_ret;int ret;if (list_empty (&udev->qfull_queue)) -return true; +return ;pr_debug ("running %s's cmdr queue forcefail %d\n" , udev->name, fail);
@@ -1425,11 +1401,10 @@ static bool run_qfull_queue(struct tcmu_dev *udev, bool fail)list_for_each_entry_safe (tcmu_cmd, tmp_cmd, &cmds, queue_entry) {list_del_init (&tcmu_cmd->queue_entry); -pr_debug ("removing cmd %u on dev %s from queue\n" , - tcmu_cmd->cmd_id, udev->name); +pr_debug ("removing cmd %p on dev %s from queue\n" , + tcmu_cmd, udev->name);if (fail) { -idr_remove (&udev->commands, tcmu_cmd->cmd_id);/* * We were not able to even start the command, so * fail with busy to allow a retry in case runner
@@ -1444,10 +1419,8 @@ static bool run_qfull_queue(struct tcmu_dev *udev, bool fail) ret =queue_cmd_ring (tcmu_cmd, &scsi_ret);if (ret <0 ) { -pr_debug ("cmd %u on dev %s failed with %u\n" , - tcmu_cmd->cmd_id, udev->name, scsi_ret); - -idr_remove (&udev->commands, tcmu_cmd->cmd_id); +pr_debug ("cmd %p on dev %s failed with %u\n" , + tcmu_cmd, udev->name, scsi_ret);/* * Ignore scsi_ret for now. target_complete_cmd * drops it.
@@ -1462,13 +1435,11 @@ static bool run_qfull_queue(struct tcmu_dev *udev, bool fail)* the queue */ list_splice_tail (&cmds, &udev->qfull_queue); - drained = false;break ; } }tcmu_set_next_deadline (&udev->qfull_queue, &udev->qfull_timer); -return drained; }static int tcmu_irqcontrol (struct uio_info *info,s32 irq_on)
@@ -1652,6 +1623,8 @@ static void tcmu_dev_kref_release(struct kref *kref)if (tcmu_check_and_free_pending_cmd (cmd) !=0 ) all_expired = false; } +if (!list_empty (&udev->qfull_queue)) + all_expired = false;idr_destroy (&udev->commands);WARN_ON (!all_expired);
@@ -2037,9 +2010,6 @@ static void tcmu_reset_ring(struct tcmu_dev *udev, u8 err_level)mutex_lock (&udev->cmdr_lock);idr_for_each_entry (&udev->commands, cmd, i) { -if (!test_bit (TCMU_CMD_BIT_INFLIGHT , &cmd->flags)) -continue ; -pr_debug ("removing cmd %u on dev %s from ring (is expired %d)\n" , cmd->cmd_id, udev->name,test_bit (TCMU_CMD_BIT_EXPIRED , &cmd->flags));
@@ -2077,6 +2047,8 @@ static void tcmu_reset_ring(struct tcmu_dev *udev, u8 err_level)del_timer (&udev->cmd_timer); +run_qfull_queue (udev, false); +mutex_unlock (&udev->cmdr_lock); }
@@ -2698,6 +2670,7 @@ static void find_free_blocks(void)static void check_timedout_devices (void ) {struct tcmu_dev *udev, *tmp_dev; +struct tcmu_cmd *cmd, *tmp_cmd;LIST_HEAD (devs);spin_lock_bh (&timed_out_udevs_lock);
@@ -2708,9 +2681,24 @@ static void check_timedout_devices(void)spin_unlock_bh (&timed_out_udevs_lock);mutex_lock (&udev->cmdr_lock); -idr_for_each (&udev->commands, tcmu_check_expired_cmd,NULL ); -tcmu_set_next_deadline (&udev->inflight_queue, &udev->cmd_timer); +/* +* If cmd_time_out is disabled but qfull is set deadline +* will only reflect the qfull timeout. Ignore it. +*/ +if (udev->cmd_time_out) { +list_for_each_entry_safe (cmd, tmp_cmd, + &udev->inflight_queue, + queue_entry) { +tcmu_check_expired_ring_cmd (cmd); + } +tcmu_set_next_deadline (&udev->inflight_queue, + &udev->cmd_timer); + } +list_for_each_entry_safe (cmd, tmp_cmd, &udev->qfull_queue, + queue_entry) { +tcmu_check_expired_queue_cmd (cmd); + }tcmu_set_next_deadline (&udev->qfull_queue, &udev->qfull_timer);mutex_unlock (&udev->cmdr_lock);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 239/477 scsi: core: Fix incorrect usage of shost_for_each_device
In reply to Greg Kroah-HartmanFrom: Ye Bin <[email protected]>
[ Upstream commit 4dea170f4fb225984b4f2f1cf0a41d485177b905 ]
shost_for_each_device(sdev, shost) \ for ((sdev) = __scsi_iterate_devices((shost), NULL); \ (sdev); \ (sdev) = __scsi_iterate_devices((shost), (sdev)))
When terminating shost_for_each_device() iteration with break or return, scsi_device_put() should be used to prevent stale scsi device references from being left behind.
--- drivers/scsi/scsi_error.c | 2 ++ drivers/scsi/scsi_lib.c | 4 +++- 2 files changed, 5 insertions(+), 1 deletion(-)
drivers/scsi/scsi_error.c +2 -0
@@ -1412,6 +1412,7 @@ static int scsi_eh_stu(struct Scsi_Host *shost,sdev_printk (KERN_INFO , sdev,"%s: skip START_UNIT, past eh deadline\n" , current->comm)); +scsi_device_put (sdev);break ; } stu_scmd =NULL ;
@@ -1478,6 +1479,7 @@ static int scsi_eh_bus_device_reset(struct Scsi_Host *shost,sdev_printk (KERN_INFO , sdev,"%s: skip BDR, past eh deadline\n" , current->comm)); +scsi_device_put (sdev);break ; } bdr_scmd =NULL ;
drivers/scsi/scsi_lib.c +3 -1
@@ -2865,8 +2865,10 @@ scsi_host_unblock(struct Scsi_Host *shost, int new_state)shost_for_each_device (sdev, shost) { ret =scsi_internal_device_unblock (sdev, new_state); -if (ret) +if (ret) { +scsi_device_put (sdev);break ; + } }return ret; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 240/477 firmware: imx: scu: Fix possible memory leak in imx_scu_probe()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit 89f12d6509bff004852c51cb713a439a86816b24 ]
'chan_name' is malloced in imx_scu_probe() and should be freed before leaving from the error handling cases, otherwise it will cause memory leak.
--- drivers/firmware/imx/imx-scu.c | 1 + 1 file changed, 1 insertion(+)
drivers/firmware/imx/imx-scu.c +1 -0
@@ -314,6 +314,7 @@ static int imx_scu_probe(struct platform_device *pdev)if (ret != -EPROBE_DEFER )dev_err (dev,"Failed to request mbox chan %s ret %d\n" , chan_name, ret); +kfree (chan_name);return ret; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 241/477 fuse: fix copy_file_range cache issues
In reply to Greg Kroah-HartmanFrom: Miklos Szeredi <[email protected]>
[ Upstream commit 2c4656dfd994538176db30ce09c02cc0dfc361ae ]
a) Dirty cache needs to be written back not just in the writeback_cache case, since the dirty pages may come from memory maps.
b) The fuse_writeback_range() helper takes an inclusive interval, so the end position needs to be pos+len-1 instead of pos+len.
--- fs/fuse/file.c | 20 ++++++++------------ 1 file changed, 8 insertions(+), 12 deletions(-)
fs/fuse/file.c +8 -12
@@ -3280,13 +3280,11 @@ static ssize_t __fuse_copy_file_range(struct file *file_in, loff_t pos_in,if (file_inode (file_in)->i_sb !=file_inode (file_out)->i_sb)return -EXDEV ; -if (fc->writeback_cache) { -inode_lock (inode_in); - err =fuse_writeback_range (inode_in, pos_in, pos_in + len); -inode_unlock (inode_in); -if (err) -return err; - } +inode_lock (inode_in); + err =fuse_writeback_range (inode_in, pos_in, pos_in + len -1 ); +inode_unlock (inode_in); +if (err) +return err;inode_lock (inode_out);
@@ -3294,11 +3292,9 @@ static ssize_t __fuse_copy_file_range(struct file *file_in, loff_t pos_in,if (err) goto out; -if (fc->writeback_cache) { - err =fuse_writeback_range (inode_out, pos_out, pos_out + len); -if (err) - goto out; - } + err =fuse_writeback_range (inode_out, pos_out, pos_out + len -1 ); +if (err) + goto out;if (is_unstable)set_bit (FUSE_I_SIZE_UNSTABLE , &fi_out->state);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 242/477 fuse: copy_file_range should truncate cache
In reply to Greg Kroah-HartmanFrom: Miklos Szeredi <[email protected]>
[ Upstream commit 9b46418c40fe910e6537618f9932a8be78a3dd6c ]
After the copy operation completes the cache is not up-to-date. Truncate all pages in the interval that has successfully been copied.
Truncating completely copied dirty pages is okay, since the data has been overwritten anyway. Truncating partially copied dirty pages is not okay; add a comment for now.
--- fs/fuse/file.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+)
fs/fuse/file.c +22 -0
@@ -3292,6 +3292,24 @@ static ssize_t __fuse_copy_file_range(struct file *file_in, loff_t pos_in,if (err) goto out; +/* +* Write out dirty pages in the destination file before sending the COPY +* request to userspace. After the request is completed, truncate off +* pages (including partial ones) from the cache that have been copied, +* since these contain stale data at that point. +* +* This should be mostly correct, but if the COPY writes to partial +* pages (at the start or end) and the parts not covered by the COPY are +* written through a memory map after calling fuse_writeback_range(), +* then these partial page modifications will be lost on truncation. +* +* It is unlikely that someone would rely on such mixed style +* modifications. Yet this does give less guarantees than if the +* copying was performed with write(2). +* +* To fix this a i_mmap_sem style lock could be used to prevent new +* faults while the copy is ongoing. +*/ err =fuse_writeback_range (inode_out, pos_out, pos_out + len -1 );if (err) goto out;
@@ -3315,6 +3333,10 @@ static ssize_t __fuse_copy_file_range(struct file *file_in, loff_t pos_in,if (err) goto out; +truncate_inode_pages_range (inode_out->i_mapping, +ALIGN_DOWN (pos_out,PAGE_SIZE ), +ALIGN (pos_out + outarg.size,PAGE_SIZE ) -1 ); +if (fc->writeback_cache) {fuse_write_update_size (inode_out, pos_out + outarg.size);file_update_time (file_out);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 243/477 arm64: tegra: Fix ethernet phy-mode for Jetson Xavier
In reply to Greg Kroah-HartmanFrom: Jon Hunter <[email protected]>
[ Upstream commit bba25915b172c72f6fa635f091624d799e3c9cae ]
The 'phy-mode' property is currently defined as 'rgmii' for Jetson Xavier. This indicates that the RGMII RX and TX delays are set by the MAC and the internal delays set by the PHY are not used.
If the Marvell PHY driver is enabled, such that it is used and not the generic PHY, ethernet failures are seen (DHCP is failing to obtain an IP address) and this is caused because the Marvell PHY driver is disabling the internal RX and TX delays. For Jetson Xavier the internal PHY RX and TX delay should be used and so fix this by setting the 'phy-mode' to 'rgmii-id' and not 'rgmii'.
--- arch/arm64/boot/dts/nvidia/tegra194-p2888.dtsi | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/arm64/boot/dts/nvidia/tegra194-p2888.dtsi +1 -1
@@ -33,7 +33,7 @@ phy-reset-gpios = <&gpio TEGRA194_MAIN_GPIO(G, 5) GPIO_ACTIVE_LOW>; phy-handle = <&phy>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; mdio { #address-cells = <1>;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 244/477 arm64: tegra: Fix flag for 64-bit resources in ranges property
In reply to Greg Kroah-HartmanFrom: Vidya Sagar <[email protected]>
[ Upstream commit 3482a7afb261e2de9269a7f9ad0f4a3a82a83a53 ]
Fix flag in PCIe controllers device-tree nodes 'ranges' property to correctly represent 64-bit resources.
--- arch/arm64/boot/dts/nvidia/tegra194.dtsi | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-)
arch/arm64/boot/dts/nvidia/tegra194.dtsi +6 -6
@@ -1387,7 +1387,7 @@ bus-range = <0x0 0xff>; ranges = <0x81000000 0x0 0x30100000 0x0 0x30100000 0x0 0x00100000 /* downstream I/O (1MB) */ - 0xc2000000 0x12 0x00000000 0x12 0x00000000 0x0 0x30000000 /* prefetchable memory (768MB) */ + 0xc3000000 0x12 0x00000000 0x12 0x00000000 0x0 0x30000000 /* prefetchable memory (768MB) */ 0x82000000 0x0 0x40000000 0x12 0x30000000 0x0 0x10000000>; /* non-prefetchable memory (256MB) */ };
@@ -1432,7 +1432,7 @@ bus-range = <0x0 0xff>; ranges = <0x81000000 0x0 0x32100000 0x0 0x32100000 0x0 0x00100000 /* downstream I/O (1MB) */ - 0xc2000000 0x12 0x40000000 0x12 0x40000000 0x0 0x30000000 /* prefetchable memory (768MB) */ + 0xc3000000 0x12 0x40000000 0x12 0x40000000 0x0 0x30000000 /* prefetchable memory (768MB) */ 0x82000000 0x0 0x40000000 0x12 0x70000000 0x0 0x10000000>; /* non-prefetchable memory (256MB) */ };
@@ -1477,7 +1477,7 @@ bus-range = <0x0 0xff>; ranges = <0x81000000 0x0 0x34100000 0x0 0x34100000 0x0 0x00100000 /* downstream I/O (1MB) */ - 0xc2000000 0x12 0x80000000 0x12 0x80000000 0x0 0x30000000 /* prefetchable memory (768MB) */ + 0xc3000000 0x12 0x80000000 0x12 0x80000000 0x0 0x30000000 /* prefetchable memory (768MB) */ 0x82000000 0x0 0x40000000 0x12 0xb0000000 0x0 0x10000000>; /* non-prefetchable memory (256MB) */ };
@@ -1522,7 +1522,7 @@ bus-range = <0x0 0xff>; ranges = <0x81000000 0x0 0x36100000 0x0 0x36100000 0x0 0x00100000 /* downstream I/O (1MB) */ - 0xc2000000 0x14 0x00000000 0x14 0x00000000 0x3 0x40000000 /* prefetchable memory (13GB) */ + 0xc3000000 0x14 0x00000000 0x14 0x00000000 0x3 0x40000000 /* prefetchable memory (13GB) */ 0x82000000 0x0 0x40000000 0x17 0x40000000 0x0 0xc0000000>; /* non-prefetchable memory (3GB) */ };
@@ -1567,7 +1567,7 @@ bus-range = <0x0 0xff>; ranges = <0x81000000 0x0 0x38100000 0x0 0x38100000 0x0 0x00100000 /* downstream I/O (1MB) */ - 0xc2000000 0x18 0x00000000 0x18 0x00000000 0x3 0x40000000 /* prefetchable memory (13GB) */ + 0xc3000000 0x18 0x00000000 0x18 0x00000000 0x3 0x40000000 /* prefetchable memory (13GB) */ 0x82000000 0x0 0x40000000 0x1b 0x40000000 0x0 0xc0000000>; /* non-prefetchable memory (3GB) */ };
@@ -1616,7 +1616,7 @@ bus-range = <0x0 0xff>; ranges = <0x81000000 0x0 0x3a100000 0x0 0x3a100000 0x0 0x00100000 /* downstream I/O (1MB) */ - 0xc2000000 0x1c 0x00000000 0x1c 0x00000000 0x3 0x40000000 /* prefetchable memory (13GB) */ + 0xc3000000 0x1c 0x00000000 0x1c 0x00000000 0x3 0x40000000 /* prefetchable memory (13GB) */ 0x82000000 0x0 0x40000000 0x1f 0x40000000 0x0 0xc0000000>; /* non-prefetchable memory (3GB) */ };
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 245/477 powerpc/powernv: add NULL check after kzalloc
In reply to Greg Kroah-HartmanFrom: Chen Zhou <[email protected]>
[ Upstream commit ceffa63acce7165c442395b7d64a11ab8b5c5dca ]
Fixes coccicheck warning:
./arch/powerpc/platforms/powernv/opal.c:813:1-5:
alloc with no test, possible model on line 814
Add NULL check after kzalloc.
--- arch/powerpc/platforms/powernv/opal.c | 4 ++++ 1 file changed, 4 insertions(+)
arch/powerpc/platforms/powernv/opal.c +4 -0
@@ -811,6 +811,10 @@ static int opal_add_one_export(struct kobject *parent, const char *export_name, goto out; attr =kzalloc (sizeof (*attr),GFP_KERNEL ); +if (!attr) { + rc = -ENOMEM ; + goto out; + } name =kstrdup (export_name,GFP_KERNEL );if (!name) { rc = -ENOMEM ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 246/477 powerpc/64s/pgtable: fix an undefined behaviour
In reply to Greg Kroah-HartmanFrom: Qian Cai <[email protected]>
[ Upstream commit c2e929b18cea6cbf71364f22d742d9aad7f4677a ]
Booting a power9 server with hash MMU could trigger an undefined behaviour because pud_offset(p4d, 0) will do,
0 >> (PAGE_SHIFT:16 + PTE_INDEX_SIZE:8 + H_PMD_INDEX_SIZE:10)
Fix it by converting pud_index() and friends to static inline functions.
UBSAN: shift-out-of-bounds in arch/powerpc/mm/ptdump/ptdump.c:282:15 shift exponent 34 is too large for 32-bit type 'int' CPU: 6 PID: 1 Comm: swapper/0 Not tainted 5.6.0-rc4-next-20200303+ #13 Call Trace: dump_stack+0xf4/0x164 (unreliable) ubsan_epilogue+0x18/0x78 __ubsan_handle_shift_out_of_bounds+0x160/0x21c walk_pagetables+0x2cc/0x700 walk_pud at arch/powerpc/mm/ptdump/ptdump.c:282 (inlined by) walk_pagetables at arch/powerpc/mm/ptdump/ptdump.c:311 ptdump_check_wx+0x8c/0xf0 mark_rodata_ro+0x48/0x80 kernel_init+0x74/0x194 ret_from_kernel_thread+0x5c/0x74
--- arch/powerpc/include/asm/book3s/64/pgtable.h | 23 ++++++++++++++++---- 1 file changed, 19 insertions(+), 4 deletions(-)
arch/powerpc/include/asm/book3s/64/pgtable.h +19 -4
@@ -998,10 +998,25 @@ extern struct page *pgd_page(pgd_t pgd);#define pud_page_vaddr (pud) __va(pud_val(pud) & ~PUD_MASKED_BITS)#define pgd_page_vaddr (pgd) __va(pgd_val(pgd) & ~PGD_MASKED_BITS) -#define pgd_index (address) (((address) >> (PGDIR_SHIFT)) & (PTRS_PER_PGD - 1)) -#define pud_index (address) (((address) >> (PUD_SHIFT)) & (PTRS_PER_PUD - 1)) -#define pmd_index (address) (((address) >> (PMD_SHIFT)) & (PTRS_PER_PMD - 1)) -#define pte_index (address) (((address) >> (PAGE_SHIFT)) & (PTRS_PER_PTE - 1)) +static inline unsigned long pgd_index (unsigned long address) +{ +return (address >>PGDIR_SHIFT ) & (PTRS_PER_PGD -1 ); +} + +static inline unsigned long pud_index (unsigned long address) +{ +return (address >>PUD_SHIFT ) & (PTRS_PER_PUD -1 ); +} + +static inline unsigned long pmd_index (unsigned long address) +{ +return (address >>PMD_SHIFT ) & (PTRS_PER_PMD -1 ); +} + +static inline unsigned long pte_index (unsigned long address) +{ +return (address >>PAGE_SHIFT ) & (PTRS_PER_PTE -1 ); +}/* * Find an entry in a page-table-directory. We combine the address region
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 247/477 powerpc/kasan: Fix error detection on memory allocation
In reply to Greg Kroah-HartmanFrom: Christophe Leroy <[email protected]>
[ Upstream commit d132443a73d7a131775df46f33000f67ed92de1e ]
In case (k_start & PAGE_MASK) doesn't equal (kstart), 'va' will never be NULL allthough 'block' is NULL
Check the return of memblock_alloc() directly instead of the resulting address in the loop.
--- arch/powerpc/mm/kasan/kasan_init_32.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-)
arch/powerpc/mm/kasan/kasan_init_32.c +2 -3
@@ -76,15 +76,14 @@ static int __init kasan_init_region(void *start, size_t size)return ret; block =memblock_alloc (k_end - k_start,PAGE_SIZE ); +if (!block) +return -ENOMEM ;for (k_cur = k_start &PAGE_MASK ; k_cur < k_end; k_cur +=PAGE_SIZE ) {pmd_t *pmd =pmd_ptr_k (k_cur);void *va = block + k_cur - k_start;pte_t pte =pfn_pte (PHYS_PFN (__pa (va)),PAGE_KERNEL ); -if (!va) -return -ENOMEM ; -__set_pte_at (&init_mm, k_cur,pte_offset_kernel (pmd, k_cur), pte,0 ); }flush_tlb_kernel_range (k_start, k_end);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 248/477 dm zoned: return NULL if dmz_get_zone_for_reclaim() fails to find a zone
In reply to Greg Kroah-HartmanFrom: Hannes Reinecke <[email protected]>
[ Upstream commit 489dc0f06a5837f87482c0ce61d830d24e17082e ]
The only case where dmz_get_zone_for_reclaim() cannot return a zone is if the respective lists are empty. So we should just return a simple NULL value here as we really don't have an error code which would make sense.
--- drivers/md/dm-zoned-metadata.c | 4 ++-- drivers/md/dm-zoned-reclaim.c | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-)
drivers/md/dm-zoned-metadata.c +2 -2
@@ -1554,7 +1554,7 @@ static struct dm_zone *dmz_get_rnd_zone_for_reclaim(struct dmz_metadata *zmd)return dzone; } -return ERR_PTR (-EBUSY ); +return NULL ; }/*
@@ -1574,7 +1574,7 @@ static struct dm_zone *dmz_get_seq_zone_for_reclaim(struct dmz_metadata *zmd)return zone; } -return ERR_PTR (-EBUSY ); +return NULL ; }/*
drivers/md/dm-zoned-reclaim.c +2 -2
@@ -349,8 +349,8 @@ static int dmz_do_reclaim(struct dmz_reclaim *zrc)/* Get a data zone */ dzone =dmz_get_zone_for_reclaim (zmd); -if (IS_ERR (dzone)) -return PTR_ERR (dzone); +if (!dzone) +return -EBUSY ; start = jiffies;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 249/477 RDMA/efa: Fix setting of wrong bit in get/set_feature commands
In reply to Greg Kroah-HartmanFrom: Gal Pressman <[email protected]>
[ Upstream commit cc8a635e24acf2793605f243c913c51b8c3702ab ]
When using a control buffer the ctrl_data bit should be set in order to indicate the control buffer address is valid, not ctrl_data_indirect which is used when the control buffer itself is indirect.
--- drivers/infiniband/hw/efa/efa_com_cmd.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/infiniband/hw/efa/efa_com_cmd.c +2 -2
@@ -388,7 +388,7 @@ static int efa_com_get_feature_ex(struct efa_com_dev *edev,if (control_buff_size)EFA_SET (&get_cmd.aq_common_descriptor.flags, -EFA_ADMIN_AQ_COMMON_DESC_CTRL_DATA_INDIRECT ,1 ); +EFA_ADMIN_AQ_COMMON_DESC_CTRL_DATA ,1 ); efa_com_set_dma_addr(control_buf_dma_addr, &get_cmd.control_buffer.address.mem_addr_high,
@@ -540,7 +540,7 @@ static int efa_com_set_feature_ex(struct efa_com_dev *edev,if (control_buff_size) { set_cmd->aq_common_descriptor.flags =0 ;EFA_SET (&set_cmd->aq_common_descriptor.flags, -EFA_ADMIN_AQ_COMMON_DESC_CTRL_DATA_INDIRECT ,1 ); +EFA_ADMIN_AQ_COMMON_DESC_CTRL_DATA ,1 );efa_com_set_dma_addr (control_buf_dma_addr, &set_cmd->control_buffer.address.mem_addr_high, &set_cmd->control_buffer.address.mem_addr_low);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 250/477 xen/cpuhotplug: Fix initial CPU offlining for PV(H) guests
In reply to Greg Kroah-HartmanFrom: Boris Ostrovsky <[email protected]>
[ Upstream commit c54b071c192dfe8061336f650ceaf358e6386e0b ]
Commit a926f81d2f6c ("xen/cpuhotplug: Replace cpu_up/down() with device_online/offline()") replaced cpu_down() with device_offline() call which requires that the CPU has been registered before. This registration, however, happens later from topology_init() which is called as subsys_initcall(). setup_vcpu_hotplug_event(), on the other hand, is invoked earlier, during arch_initcall().
As result, booting a PV(H) guest with vcpus < maxvcpus causes a crash.
Move setup_vcpu_hotplug_event() (and therefore setup_cpu_watcher()) to late_initcall(). In addition, instead of performing all offlining steps in setup_cpu_watcher() simply call disable_hotplug_cpu().
--- drivers/xen/cpu_hotplug.c | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-)
drivers/xen/cpu_hotplug.c +3 -5
@@ -93,10 +93,8 @@ static int setup_cpu_watcher(struct notifier_block *notifier, (void )register_xenbus_watch (&cpu_watch);for_each_possible_cpu (cpu) { -if (vcpu_online (cpu) ==0 ) { -device_offline (get_cpu_device (cpu)); -set_cpu_present (cpu, false); - } +if (vcpu_online (cpu) ==0 ) +disable_hotplug_cpu (cpu); }return NOTIFY_DONE ;
@@ -119,5 +117,5 @@ static int __init setup_vcpu_hotplug_event(void)return 0 ; } -arch_initcall (setup_vcpu_hotplug_event); +late_initcall (setup_vcpu_hotplug_event);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 251/477 PCI/PTM: Inherit Switch Downstream Port PTM settings from Upstream Port
In reply to Greg Kroah-HartmanFrom: Bjorn Helgaas <[email protected]>
[ Upstream commit 7b38fd9760f51cc83d80eed2cfbde8b5ead9e93a ]
Except for Endpoints, we enable PTM at enumeration-time. Previously we did not account for the fact that Switch Downstream Ports are not permitted to have a PTM capability; their PTM behavior is controlled by the Upstream Port (PCIe r5.0, sec 7.9.16). Since Downstream Ports don't have a PTM capability, we did not mark them as "ptm_enabled", which meant that pci_enable_ptm() on an Endpoint failed because there was no PTM path to it.
Mark Downstream Ports as "ptm_enabled" if their Upstream Port has PTM enabled.
--- drivers/pci/pcie/ptm.c | 22 +++++++++++++++++----- 1 file changed, 17 insertions(+), 5 deletions(-)
drivers/pci/pcie/ptm.c +17 -5
@@ -39,10 +39,6 @@ void pci_ptm_init(struct pci_dev *dev)if (!pci_is_pcie (dev))return ; - pos =pci_find_ext_capability (dev,PCI_EXT_CAP_ID_PTM ); -if (!pos) -return ; -/* * Enable PTM only on interior devices (root ports, switch ports, * etc.) on the assumption that it causes no link traffic until an
@@ -52,6 +48,23 @@ void pci_ptm_init(struct pci_dev *dev) pci_pcie_type(dev) == PCI_EXP_TYPE_RC_END))return ; +/* +* Switch Downstream Ports are not permitted to have a PTM +* capability; their PTM behavior is controlled by the Upstream +* Port (PCIe r5.0, sec 7.9.16). +*/ + ups =pci_upstream_bridge (dev); +if (pci_pcie_type (dev) ==PCI_EXP_TYPE_DOWNSTREAM && + ups && ups->ptm_enabled) { + dev->ptm_granularity = ups->ptm_granularity; + dev->ptm_enabled =1 ; +return ; + } + + pos =pci_find_ext_capability (dev,PCI_EXT_CAP_ID_PTM ); +if (!pos) +return ; +pci_read_config_dword (dev, pos +PCI_PTM_CAP , &cap); local_clock = (cap &PCI_PTM_GRANULARITY_MASK ) >>8 ;
@@ -61,7 +74,6 @@ void pci_ptm_init(struct pci_dev *dev)* the spec recommendation (PCIe r3.1, sec 7.32.3), select the * furthest upstream Time Source as the PTM Root. */ - ups =pci_upstream_bridge (dev);if (ups && ups->ptm_enabled) { ctrl =PCI_PTM_CTRL_ENABLE ;if (ups->ptm_granularity ==0 )
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 252/477 bus: mhi: core: Read transfer length from an event properly
In reply to Greg Kroah-HartmanFrom: Hemant Kumar <[email protected]>
[ Upstream commit ee75cedf82d832561af8ba8380aeffd00a9eea77 ]
When MHI Driver receives an EOT event, it reads xfer_len from the event in the last TRE. The value is under control of the MHI device and never validated by Host MHI driver. The value should never be larger than the real size of the buffer but a malicious device can set the value 0xFFFF as maximum. This causes driver to memory overflow (both read or write). Fix this issue by reading minimum of transfer length from event and the buffer length provided.
--- drivers/bus/mhi/core/main.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-)
drivers/bus/mhi/core/main.c +7 -2
@@ -513,7 +513,10 @@ static int parse_xfer_event(struct mhi_controller *mhi_cntrl, mhi_cntrl->unmap_single (mhi_cntrl, buf_info); result.buf_addr = buf_info->cb_buf; - result.bytes_xferd = xfer_len; + +/* truncate to buf len if xfer_len is larger */ + result.bytes_xferd = +min_t (u16, xfer_len, buf_info->len);mhi_del_ring_element (mhi_cntrl, buf_ring);mhi_del_ring_element (mhi_cntrl, tre_ring); local_rp = tre_ring->rp;
@@ -597,7 +600,9 @@ static int parse_rsc_event(struct mhi_controller *mhi_cntrl, result.transaction_status = (ev_code ==MHI_EV_CC_OVERFLOW ) ? -EOVERFLOW :0 ; - result.bytes_xferd = xfer_len; + +/* truncate to buf len if xfer_len is larger */ + result.bytes_xferd =min_t (u16, xfer_len, buf_info->len); result.buf_addr = buf_info->cb_buf; result.dir = mhi_chan->dir;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 253/477 PCI: dwc: pci-dra7xx: Use devm_platform_ioremap_resource_byname()
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit c8a119779f5609de8dcd98630f71cc7f1b2e4e8c ]
platform_get_resource() may fail and return NULL, so we had better check its return value to avoid a NULL pointer dereference a bit later in the code. Fix it to use devm_platform_ioremap_resource_byname() instead of calling platform_get_resource_byname() and devm_ioremap().
--- drivers/pci/controller/dwc/pci-dra7xx.c | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-)
drivers/pci/controller/dwc/pci-dra7xx.c +3 -5
@@ -840,7 +840,6 @@ static int __init dra7xx_pcie_probe(struct platform_device *pdev)struct phy **phy;struct device_link **link;void __iomem *base; -struct resource *res;struct dw_pcie *pci;struct dra7xx_pcie *dra7xx;struct device *dev = &pdev->dev;
@@ -877,10 +876,9 @@ static int __init dra7xx_pcie_probe(struct platform_device *pdev)return irq; } - res =platform_get_resource_byname (pdev,IORESOURCE_MEM ,"ti_conf" ); - base =devm_ioremap (dev, res->start,resource_size (res)); -if (!base) -return -ENOMEM ; + base =devm_platform_ioremap_resource_byname (pdev,"ti_conf" ); +if (IS_ERR (base)) +return PTR_ERR (base); phy_count =of_property_count_strings (np,"phy-names" );if (phy_count <0 ) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 254/477 PCI: dwc: Fix inner MSI IRQ domain registration
In reply to Greg Kroah-HartmanFrom: Marc Zyngier <[email protected]>
[ Upstream commit 0414b93e78d87ecc24ae1a7e61fe97deb29fa2f4 ]
On a system that uses the internal DWC MSI widget, I get this warning from debugfs when CONFIG_GENERIC_IRQ_DEBUGFS is selected:
debugfs: File ':soc:pcie@fc000000' in directory 'domains' already present!
This is due to the fact that the DWC MSI code tries to register two IRQ domains for the same firmware node, without telling the low level code how to distinguish them (by setting a bus token). This further confuses debugfs which tries to create corresponding files for each domain.
Fix it by tagging the inner domain as DOMAIN_BUS_NEXUS, which is the closest thing we have as to "generic MSI".
--- drivers/pci/controller/dwc/pcie-designware-host.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/pci/controller/dwc/pcie-designware-host.c +2 -0
@@ -264,6 +264,8 @@ int dw_pcie_allocate_domains(struct pcie_port *pp)return -ENOMEM ; } +irq_domain_update_bus_token (pp->irq_domain,DOMAIN_BUS_NEXUS ); + pp->msi_domain =pci_msi_create_irq_domain (fwnode, &dw_pcie_msi_domain_info, pp->irq_domain);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 255/477 PCI: amlogic: meson: Dont use FAST_LINK_MODE to set up link
In reply to Greg Kroah-HartmanFrom: Marc Zyngier <[email protected]>
[ Upstream commit 87dccf09323fc363bd0d072fcc12b96622ab8c69 ]
The vim3l board does not work with a standard PCIe switch (ASM1184e), spitting all kind of errors - hinting at HW misconfiguration (no link, port enumeration issues, etc).
According to the the Synopsys DWC PCIe Reference Manual, in the section dedicated to the PLCR register, bit 7 is described (FAST_LINK_MODE) as:
"Sets all internal timers to fast mode for simulation purposes."
it is sound to set this bit from a simulation perspective, but on actual silicon, which expects timers to have a nominal value, it is not.
Make sure the FAST_LINK_MODE bit is cleared when configuring the RC to solve this problem.
--- drivers/pci/controller/dwc/pci-meson.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/pci/controller/dwc/pci-meson.c +2 -2
@@ -289,11 +289,11 @@ static void meson_pcie_init_dw(struct meson_pcie *mp)meson_cfg_writel (mp, val,PCIE_CFG0 ); val =meson_elb_readl (mp,PCIE_PORT_LINK_CTRL_OFF ); - val &= ~LINK_CAPABLE_MASK ; + val &= ~(LINK_CAPABLE_MASK |FAST_LINK_MODE );meson_elb_writel (mp, val,PCIE_PORT_LINK_CTRL_OFF ); val =meson_elb_readl (mp,PCIE_PORT_LINK_CTRL_OFF ); - val |=LINK_CAPABLE_X1 |FAST_LINK_MODE ; + val |=LINK_CAPABLE_X1 ;meson_elb_writel (mp, val,PCIE_PORT_LINK_CTRL_OFF ); val =meson_elb_readl (mp,PCIE_GEN2_CTRL_OFF );
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 256/477 iio: light: gp2ap002: Take runtime PM reference on light read
In reply to Greg Kroah-HartmanFrom: Jonathan Bakker <[email protected]>
[ Upstream commit f6dbf83c17cb223ceabd7c42d441414f3e0e8a86 ]
The light sensor needs the regulators to be enabled which means the runtime PM needs to be on. This only happened when the proximity part of the chip was enabled.
As fallout from this change, only report changes to the prox state in the interrupt handler when it is explicitly enabled.
--- drivers/iio/light/gp2ap002.c | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-)
drivers/iio/light/gp2ap002.c +16 -3
@@ -158,6 +158,9 @@ static irqreturn_t gp2ap002_prox_irq(int irq, void *d)int val;int ret; +if (!gp2ap002->enabled) + goto err_retrig; + ret =regmap_read (gp2ap002->map,GP2AP002_PROX , &val);if (ret) {dev_err (gp2ap002->dev,"error reading proximity\n" );
@@ -247,6 +250,8 @@ static int gp2ap002_read_raw(struct iio_dev *indio_dev,struct gp2ap002 *gp2ap002 =iio_priv (indio_dev);int ret; +pm_runtime_get_sync (gp2ap002->dev); +switch (mask) {case IIO_CHAN_INFO_RAW :switch (chan->type) {
@@ -255,13 +260,21 @@ static int gp2ap002_read_raw(struct iio_dev *indio_dev,if (ret <0 )return ret; *val = ret; -return IIO_VAL_INT ; + ret =IIO_VAL_INT ; + goto out;default : -return -EINVAL ; + ret = -EINVAL ; + goto out; }default : -return -EINVAL ; + ret = -EINVAL ; } + +out: +pm_runtime_mark_last_busy (gp2ap002->dev); +pm_runtime_put_autosuspend (gp2ap002->dev); + +return ret; }static int gp2ap002_init (struct gp2ap002 *gp2ap002)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 257/477 IB/cma: Fix ports memory leak in cma_configfs
In reply to Greg Kroah-HartmanFrom: Maor Gottlieb <[email protected]>
[ Upstream commit 63a3345c2d42a9b29e1ce2d3a4043689b3995cea ]
The allocated ports structure in never freed. The free function should be called by release_cma_ports_group, but the group is never released since we don't remove its default group.
Remove default groups when device group is deleted.
--- drivers/infiniband/core/cma_configfs.c | 13 +++++++++++++ 1 file changed, 13 insertions(+)
drivers/infiniband/core/cma_configfs.c +13 -0
@@ -322,8 +322,21 @@ fail:return ERR_PTR (err); } +static void drop_cma_dev (struct config_group *cgroup,struct config_item *item) +{ +struct config_group *group = + container_of(item, struct config_group, cg_item); +struct cma_dev_group *cma_dev_group = + container_of(group, struct cma_dev_group, device_group); + +configfs_remove_default_groups (&cma_dev_group->ports_group); +configfs_remove_default_groups (&cma_dev_group->device_group); +config_item_put (item); +} +static struct configfs_group_operations cma_subsys_group_ops = { .make_group = make_cma_dev, + .drop_item = drop_cma_dev, };static const struct config_item_type cma_subsys_type = {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 258/477 selftests/timens: handle a case when alarm clocks are not supported
In reply to Greg Kroah-HartmanFrom: Andrei Vagin <[email protected]>
[ Upstream commit 558ae0355a91c7d28fdf4c0011bee6ebb5118632 ]
This can happen if a testing node doesn't have RTC (real time clock) hardware or it doesn't support alarms.
--- tools/testing/selftests/timens/clock_nanosleep.c | 2 +- tools/testing/selftests/timens/timens.c | 2 +- tools/testing/selftests/timens/timens.h | 13 ++++++++++++- tools/testing/selftests/timens/timer.c | 5 +++++ tools/testing/selftests/timens/timerfd.c | 5 +++++ 5 files changed, 24 insertions(+), 3 deletions(-)
tools/testing/selftests/timens/clock_nanosleep.c +1 -1
@@ -119,7 +119,7 @@ int main(int argc, char *argv[])ksft_set_plan (4 ); -check_config_posix_timers (); +check_supported_timers ();if (unshare_timens ())return 1 ;
tools/testing/selftests/timens/timens.c +1 -1
@@ -155,7 +155,7 @@ int main(int argc, char *argv[])nscheck (); -check_config_posix_timers (); +check_supported_timers ();ksft_set_plan (ARRAY_SIZE (clocks) *2 );
tools/testing/selftests/timens/timens.h +12 -1
@@ -14,15 +14,26 @@#endif static int config_posix_timers = true; +static int config_alarm_timers = true; -static inline void check_config_posix_timers (void ) +static inline void check_supported_timers (void ) { +struct timespec ts; +if (timer_create (-1 ,0 ,0 ) ==-1 && errno ==ENOSYS ) config_posix_timers = false; + +if (clock_gettime (CLOCK_BOOTTIME_ALARM , &ts) ==-1 && errno ==EINVAL ) + config_alarm_timers = false; }static inline bool check_skip (int clockid) { +if (!config_alarm_timers && clockid ==CLOCK_BOOTTIME_ALARM ) { +ksft_test_result_skip ("CLOCK_BOOTTIME_ALARM isn't supported\n" ); +return true; + } +if (config_posix_timers)return false;
tools/testing/selftests/timens/timer.c +5 -0
@@ -22,6 +22,9 @@ int run_test(int clockid, struct timespec now)timer_t fd;int i; +if (check_skip (clockid)) +return 0 ; +for (i =0 ; i <2 ; i++) {struct sigevent sevp = {.sigev_notify =SIGEV_NONE };int flags =0 ;
@@ -74,6 +77,8 @@ int main(int argc, char *argv[])nscheck (); +check_supported_timers (); +ksft_set_plan (3 );clock_gettime (CLOCK_MONOTONIC , &mtime_now);
tools/testing/selftests/timens/timerfd.c +5 -0
@@ -28,6 +28,9 @@ int run_test(int clockid, struct timespec now)long long elapsed;int fd, i; +if (check_skip (clockid)) +return 0 ; +if (tclock_gettime (clockid, &now))return pr_perror ("clock_gettime(%d)" , clockid);
@@ -81,6 +84,8 @@ int main(int argc, char *argv[])nscheck (); +check_supported_timers (); +ksft_set_plan (3 );clock_gettime (CLOCK_MONOTONIC , &mtime_now);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 259/477 watchdog: da9062: No need to ping manually before setting timeout
In reply to Greg Kroah-HartmanFrom: Stefan Riedmueller <[email protected]>
[ Upstream commit a0948ddba65f4f6d3cfb5e2b84685485d0452966 ]
There is actually no need to ping the watchdog before disabling it during timeout change. Disabling the watchdog already takes care of resetting the counter.
This fixes an issue during boot when the userspace watchdog handler takes over and the watchdog is already running. Opening the watchdog in this case leads to the first ping and directly after that without the required heartbeat delay a second ping issued by the set_timeout call. Due to the missing delay this resulted in a reset.
--- drivers/watchdog/da9062_wdt.c | 5 ----- 1 file changed, 5 deletions(-)
drivers/watchdog/da9062_wdt.c +0 -5
@@ -58,11 +58,6 @@ static int da9062_wdt_update_timeout_register(struct da9062_watchdog *wdt, unsigned int regval) {struct da9062 *chip = wdt->hw; -int ret; - - ret =da9062_reset_watchdog_timer (wdt); -if (ret) -return ret; regmap_update_bits(chip->regmap, DA9062AA_CONTROL_D,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 260/477 usb: dwc2: gadget: move gadget resume after the core is in L0 state
In reply to Greg Kroah-HartmanFrom: Fabrice Gasnier <[email protected]>
[ Upstream commit 8c935deacebb8fac8f41378701eb79d12f3c2e2d ]
When the remote wakeup interrupt is triggered, lx_state is resumed from L2 to L0 state. But when the gadget resume is called, lx_state is still L2. This prevents the resume callback to queue any request. Any attempt to queue a request from resume callback will result in:
- "submit request only in active state" debug message to be issued
- dwc2_hsotg_ep_queue() returns -EAGAIN
Call the gadget resume routine after the core is in L0 state.
--- drivers/usb/dwc2/core_intr.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/usb/dwc2/core_intr.c +5 -2
@@ -416,10 +416,13 @@ static void dwc2_handle_wakeup_detected_intr(struct dwc2_hsotg *hsotg)if (ret && (ret != -ENOTSUPP ))dev_err (hsotg->dev,"exit power_down failed\n" ); +/* Change to L0 state */ + hsotg->lx_state =DWC2_L0 ;call_gadget (hsotg, resume); + }else { +/* Change to L0 state */ + hsotg->lx_state =DWC2_L0 ; } -/* Change to L0 state */ - hsotg->lx_state =DWC2_L0 ; }else {if (hsotg->params.power_down)return ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 261/477 USB: gadget: udc: s3c2410_udc: Remove pointless NULL check in s3c2410_udc_nuke
In reply to Greg Kroah-HartmanFrom: Nathan Chancellor <[email protected]>
[ Upstream commit 7a0fbcf7c308920bc6116b3a5fb21c8cc5fec128 ]
Clang warns:
drivers/usb/gadget/udc/s3c2410_udc.c:255:11: warning: comparison of address of 'ep->queue' equal to a null pointer is always false [-Wtautological-pointer-compare]
if (&ep->queue == NULL)
~~~~^~~~~ ~~~~1 warning generated.
It is not wrong, queue is not a pointer so if ep is not NULL, the address of queue cannot be NULL. No other driver does a check like this and this check has been around since the driver was first introduced, presumably with no issues so it does not seem like this check should be something else. Just remove it.
Commit afe956c577b2d ("kbuild: Enable -Wtautological-compare") exposed this but it is not the root cause of the warning.
--- drivers/usb/gadget/udc/s3c2410_udc.c | 4 ---- 1 file changed, 4 deletions(-)
drivers/usb/gadget/udc/s3c2410_udc.c +0 -4
@@ -251,10 +251,6 @@ static void s3c2410_udc_done(struct s3c2410_ep *ep,static void s3c2410_udc_nuke (struct s3c2410_udc *udc,struct s3c2410_ep *ep,int status) { -/* Sanity check */ -if (&ep->queue ==NULL ) -return ; -while (!list_empty (&ep->queue)) {struct s3c2410_request *req; req = list_entry(ep->queue.next, struct s3c2410_request,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 262/477 usb: gadget: lpc32xx_udc: dont dereference ep pointer before null check
In reply to Greg Kroah-HartmanFrom: Colin Ian King <[email protected]>
[ Upstream commit eafa80041645cd7604c4357b1a0cd4a3c81f2227 ]
Currently pointer ep is being dereferenced before it is null checked leading to a null pointer dereference issue. Fix this by only assigning pointer udc once ep is known to be not null. Also remove a debug message that requires a valid udc which may not be possible at that point.
Addresses-Coverity: ("Dereference before null check")
--- drivers/usb/gadget/udc/lpc32xx_udc.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-)
drivers/usb/gadget/udc/lpc32xx_udc.c +6 -5
@@ -1614,17 +1614,17 @@ static int lpc32xx_ep_enable(struct usb_ep *_ep, const struct usb_endpoint_descriptor *desc) { struct lpc32xx_ep *ep = container_of(_ep, struct lpc32xx_ep, ep); -struct lpc32xx_udc *udc = ep->udc; +struct lpc32xx_udc *udc;u16 maxpacket;u32 tmp;unsigned long flags;/* Verify EP data */ if ((!_ep) || (!ep) || (!desc) || - (desc->bDescriptorType !=USB_DT_ENDPOINT )) { -dev_dbg (udc->dev,"bad ep or descriptor\n" ); + (desc->bDescriptorType !=USB_DT_ENDPOINT ))return -EINVAL ; - } + + udc = ep->udc; maxpacket =usb_endpoint_maxp (desc);if ((maxpacket ==0 ) || (maxpacket > ep->maxpacket)) {dev_dbg (udc->dev,"bad ep descriptor's packet size\n" );
@@ -1872,7 +1872,7 @@ static int lpc32xx_ep_dequeue(struct usb_ep *_ep, struct usb_request *_req)static int lpc32xx_ep_set_halt (struct usb_ep *_ep,int value) { struct lpc32xx_ep *ep = container_of(_ep, struct lpc32xx_ep, ep); -struct lpc32xx_udc *udc = ep->udc; +struct lpc32xx_udc *udc;unsigned long flags;if ((!ep) || (ep->hwep_num <=1 ))
@@ -1882,6 +1882,7 @@ static int lpc32xx_ep_set_halt(struct usb_ep *_ep, int value)if (ep->is_in)return -EAGAIN ; + udc = ep->udc;spin_lock_irqsave (&udc->lock, flags);if (value ==1 ) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 263/477 usb: gadget: fix potential double-free in m66592_probe.
In reply to Greg Kroah-HartmanFrom: Qiushi Wu <[email protected]>
[ Upstream commit 44734a594196bf1d474212f38fe3a0d37a73278b ]
m66592_free_request() is called under label "err_add_udc" and "clean_up", and m66592->ep0_req is not set to NULL after first free, leading to a double-free. Fix this issue by setting m66592->ep0_req to NULL after the first free.
--- drivers/usb/gadget/udc/m66592-udc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/usb/gadget/udc/m66592-udc.c +1 -1
@@ -1667,7 +1667,7 @@ static int m66592_probe(struct platform_device *pdev) err_add_udc:m66592_free_request (&m66592->ep[0 ].ep, m66592->ep0_req); - + m66592->ep0_req =NULL ; clean_up3:if (m66592->pdata->on_chip) {clk_disable (m66592->clk);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 264/477 usb: gadget: Fix issue with config_ep_by_speed function
In reply to Greg Kroah-HartmanFrom: Pawel Laszczak <[email protected]>
[ Upstream commit 5d363120aa548ba52d58907a295eee25f8207ed2 ]
This patch adds new config_ep_by_speed_and_alt function which extends the config_ep_by_speed about alt parameter.
This additional parameter allows to find proper usb_ss_ep_comp_descriptor.
Problem has appeared during testing f_tcm (BOT/UAS) driver function.
f_tcm function for SS use array of headers for both BOT/UAS alternate setting:
static struct usb_descriptor_header *uasp_ss_function_desc[] = {
(struct usb_descriptor_header *) &bot_intf_desc, (struct usb_descriptor_header *) &uasp_ss_bi_desc, (struct usb_descriptor_header *) &bot_bi_ep_comp_desc, (struct usb_descriptor_header *) &uasp_ss_bo_desc, (struct usb_descriptor_header *) &bot_bo_ep_comp_desc,
(struct usb_descriptor_header *) &uasp_intf_desc, (struct usb_descriptor_header *) &uasp_ss_bi_desc, (struct usb_descriptor_header *) &uasp_bi_ep_comp_desc, (struct usb_descriptor_header *) &uasp_bi_pipe_desc, (struct usb_descriptor_header *) &uasp_ss_bo_desc, (struct usb_descriptor_header *) &uasp_bo_ep_comp_desc, (struct usb_descriptor_header *) &uasp_bo_pipe_desc, (struct usb_descriptor_header *) &uasp_ss_status_desc, (struct usb_descriptor_header *) &uasp_status_in_ep_comp_desc, (struct usb_descriptor_header *) &uasp_status_pipe_desc, (struct usb_descriptor_header *) &uasp_ss_cmd_desc, (struct usb_descriptor_header *) &uasp_cmd_comp_desc, (struct usb_descriptor_header *) &uasp_cmd_pipe_desc, NULL,
};
The first 5 descriptors are associated with BOT alternate setting, and others are associated with UAS.
During handling UAS alternate setting f_tcm driver invokes config_ep_by_speed and this function sets incorrect companion endpoint descriptor in usb_ep object.
Instead setting ep->comp_desc to uasp_bi_ep_comp_desc function in this case set ep->comp_desc to uasp_ss_bi_desc.
This is due to the fact that it searches endpoint based on endpoint address:
for_each_ep_desc(speed_desc, d_spd) {
chosen_desc = (struct usb_endpoint_descriptor *)*d_spd;
if (chosen_desc->bEndpoitAddress == _ep->address)
goto ep_found;
}And in result it uses the descriptor from BOT alternate setting instead UAS.
Finally, it causes that controller driver during enabling endpoints detect that just enabled endpoint for bot.
--- drivers/usb/gadget/composite.c | 78 ++++++++++++++++++++++++++-------- include/linux/usb/composite.h | 3 ++ 2 files changed, 64 insertions(+), 17 deletions(-)
drivers/usb/gadget/composite.c +61 -17
@@ -96,40 +96,43 @@ function_descriptors(struct usb_function *f, }/** -* next_ep_desc() - advance to the next EP descriptor +* next_desc() - advance to the next desc_type descriptor * @t: currect pointer within descriptor array +* @desc_type: descriptor type * -* Return: next EP descriptor or NULL +* Return: next desc_type descriptor or NULL * -* Iterate over @t until either EP descriptor found or +* Iterate over @t until either desc_type descriptor found or * NULL (that indicates end of list) encountered */ static struct usb_descriptor_header ** -next_ep_desc (struct usb_descriptor_header **t) +next_desc (struct usb_descriptor_header **t,u8 desc_type) {for (; *t; t++) { -if ((*t)->bDescriptorType ==USB_DT_ENDPOINT ) +if ((*t)->bDescriptorType == desc_type)return t; }return NULL ; }/* -* for_each_ep_desc()- iterate over endpoint descriptors in the -* descriptors list -* @start: pointer within descriptor array. -* @ep_desc: endpoint descriptor to use as the loop cursor +* for_each_desc() - iterate over desc_type descriptors in the +* descriptors list +* @start: pointer within descriptor array. +* @iter_desc: desc_type descriptor to use as the loop cursor +* @desc_type: wanted descriptr type */ -#define for_each_ep_desc (start, ep_desc) \ - for (ep_desc = next_ep_desc(start); \ - ep_desc; ep_desc = next_ep_desc(ep_desc+1)) +#define for_each_desc (start, iter_desc, desc_type) \ + for (iter_desc = next_desc(start, desc_type); \ + iter_desc; iter_desc = next_desc(iter_desc + 1, desc_type))/** -* config_ep_by_speed() - configures the given endpoint +* config_ep_by_speed_and_alt() - configures the given endpoint * according to gadget speed. * @g: pointer to the gadget * @f: usb function * @_ep: the endpoint to configure +* @alt: alternate setting number * * Return: error code, 0 on success *
@@ -142,11 +145,13 @@ next_ep_desc(struct usb_descriptor_header **t)* Note: the supplied function should hold all the descriptors * for supported speeds */ -int config_ep_by_speed (struct usb_gadget *g, -struct usb_function *f, -struct usb_ep *_ep) +int config_ep_by_speed_and_alt (struct usb_gadget *g, +struct usb_function *f, +struct usb_ep *_ep, +u8 alt) {struct usb_endpoint_descriptor *chosen_desc =NULL ; +struct usb_interface_descriptor *int_desc =NULL ;struct usb_descriptor_header **speed_desc =NULL ;struct usb_ss_ep_comp_descriptor *comp_desc =NULL ;
@@ -182,8 +187,21 @@ int config_ep_by_speed(struct usb_gadget *g,default : speed_desc = f->fs_descriptors; } + +/* find correct alternate setting descriptor */ +for_each_desc (speed_desc, d_spd,USB_DT_INTERFACE ) { + int_desc = (struct usb_interface_descriptor *)*d_spd; + +if (int_desc->bAlternateSetting == alt) { + speed_desc = d_spd; + goto intf_found; + } + } +return -EIO ; + +intf_found:/* find descriptors */ -for_each_ep_desc (speed_desc, d_spd) { +for_each_desc (speed_desc, d_spd,USB_DT_ENDPOINT ) { chosen_desc = (struct usb_endpoint_descriptor *)*d_spd;if (chosen_desc->bEndpointAddress == _ep->address) goto ep_found;
@@ -237,6 +255,32 @@ ep_found: }return 0 ; } +EXPORT_SYMBOL_GPL (config_ep_by_speed_and_alt); + +/** +* config_ep_by_speed() - configures the given endpoint +* according to gadget speed. +* @g: pointer to the gadget +* @f: usb function +* @_ep: the endpoint to configure +* +* Return: error code, 0 on success +* +* This function chooses the right descriptors for a given +* endpoint according to gadget speed and saves it in the +* endpoint desc field. If the endpoint already has a descriptor +* assigned to it - overwrites it with currently corresponding +* descriptor. The endpoint maxpacket field is updated according +* to the chosen descriptor. +* Note: the supplied function should hold all the descriptors +* for supported speeds +*/ +int config_ep_by_speed (struct usb_gadget *g, +struct usb_function *f, +struct usb_ep *_ep) +{ +return config_ep_by_speed_and_alt (g, f, _ep,0 ); +}EXPORT_SYMBOL_GPL (config_ep_by_speed);/**
include/linux/usb/composite.h +3 -0
@@ -249,6 +249,9 @@ int usb_function_activate(struct usb_function *);int usb_interface_id (struct usb_configuration *,struct usb_function *); +int config_ep_by_speed_and_alt (struct usb_gadget *g,struct usb_function *f, +struct usb_ep *_ep,u8 alt); +int config_ep_by_speed (struct usb_gadget *g,struct usb_function *f,struct usb_ep *_ep);
Signature · 1 line
2.25.1
Re: [PATCH 5.7 264/477] usb: gadget: Fix issue with config_ep_by_speed function
Hi!
Quoted 9 lines
[ Upstream commit
5d363120aa548ba52d58907a295eee25f8207ed2]This patch adds new
config_ep_by_speed_and_altfunction which extends theconfig_ep_by_speedabout alt parameter. This additional parameter allows to find properusb_ss_ep_comp_descriptor.drivers/usb/gadget/composite.c | 78 ++++++++++++++++++++++++++-------- include/linux/usb/composite.h | 3 ++
It seems that (at least for 4.19) we applied rather big patch to merge unused function.
Best regards,
Pavel
Signature · 2 lines
(english) http://www.livejournal.com/~pavelmachek (cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html
Greg Kroah-Hartman
maintainerPATCH 265/477 pinctrl: Fix return value about devm_platform_ioremap_resource()
In reply to Greg Kroah-HartmanFrom: Tiezhu Yang <[email protected]>
[ Upstream commit b5d9ff10dca49f4d4b7846c3751c6bec50d07375 ]
When call function devm_platform_ioremap_resource(), we should use IS_ERR() to check the return value and return PTR_ERR() if failed.
--- drivers/pinctrl/bcm/pinctrl-bcm281xx.c | 2 +- drivers/pinctrl/pinctrl-at91-pio4.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-)
drivers/pinctrl/bcm/pinctrl-bcm281xx.c +1 -1
@@ -1406,7 +1406,7 @@ static int __init bcm281xx_pinctrl_probe(struct platform_device *pdev) pdata->reg_base =devm_platform_ioremap_resource (pdev,0 );if (IS_ERR (pdata->reg_base)) {dev_err (&pdev->dev,"Failed to ioremap MEM resource\n" ); -return -ENODEV ; +return PTR_ERR (pdata->reg_base); }/* Initialize the dynamic part of pinctrl_desc */
drivers/pinctrl/pinctrl-at91-pio4.c +1 -1
@@ -1019,7 +1019,7 @@ static int atmel_pinctrl_probe(struct platform_device *pdev) atmel_pioctrl->reg_base =devm_platform_ioremap_resource (pdev,0 );if (IS_ERR (atmel_pioctrl->reg_base)) -return -EINVAL ; +return PTR_ERR (atmel_pioctrl->reg_base); atmel_pioctrl->clk =devm_clk_get (dev,NULL );if (IS_ERR (atmel_pioctrl->clk)) {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 266/477 scripts: headers_install: Exit with error on config leak
In reply to Greg Kroah-HartmanFrom: Siddharth Gupta <[email protected]>
[ Upstream commit 5967577231f9b19acd5a59485e9075964065bbe3 ]
Misuse of CONFIG_* in UAPI headers should result in an error. These config options can be set in userspace by the user application which includes these headers to control the APIs and structures being used in a kernel which supports multiple targets.
--- scripts/headers_install.sh | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-)
scripts/headers_install.sh +6 -5
@@ -64,7 +64,7 @@ configs=$(sed -e ' d ' $OUTFILE) -# The entries in the following list are not warned. +# The entries in the following list do not result in an error. # Please do not add a new entry. This list is only for existing ones. # The list will be reduced gradually, and deleted eventually. (hopefully) #
@@ -98,18 +98,19 @@ include/uapi/linux/raw.h:CONFIG_MAX_RAW_DEVS for c in $configs do - warn=1 + leak_error=1 for ignore in $config_leak_ignores do if echo "$INFILE:$c" | grep -q "$ignore$"; then - warn= + leak_error= break fi done - if [ "$warn" = 1 ]; then - echo "warning: $INFILE: leak $c to user-space" >&2 + if [ "$leak_error" = 1 ]; then + echo "error: $INFILE: leak $c to user-space" >&2 + exit 1 fi done
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 267/477 RDMA/iw_cxgb4: cleanup device debugfs entries on ULD remove
In reply to Greg Kroah-HartmanFrom: Potnuri Bharat Teja <[email protected]>
[ Upstream commit 49ea0c036ede81f126f1a9389d377999fdf5c5a1 ]
Remove device specific debugfs entries immediately if LLD detaches a particular ULD device in case of fatal PCI errors.
--- drivers/infiniband/hw/cxgb4/device.c | 1 + 1 file changed, 1 insertion(+)
drivers/infiniband/hw/cxgb4/device.c +1 -0
@@ -953,6 +953,7 @@ void c4iw_dealloc(struct uld_ctx *ctx)static void c4iw_remove (struct uld_ctx *ctx) {pr_debug ("c4iw_dev %p\n" , ctx->dev); +debugfs_remove_recursive (ctx->dev->debugfs_root);c4iw_unregister_device (ctx->dev);c4iw_dealloc (ctx); }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 268/477 x86/apic: Make TSC deadline timer detection message visible
In reply to Greg Kroah-HartmanFrom: Borislav Petkov <[email protected]>
[ Upstream commit de308d1815c9e8fe602a958c5c76142ff6501d75 ]
The commit
c84cb3735fd5 ("x86/apic: Move TSC deadline timer debug printk")
removed the message which said that the deadline timer was enabled. It added a pr_debug() message which is issued when deadline timer validation succeeds.
Well, issued only when CONFIG_DYNAMIC_DEBUG is enabled - otherwise pr_debug() calls get optimized away if DEBUG is not defined in the compilation unit.
Therefore, make the above message pr_info() so that it is visible in dmesg.
--- arch/x86/kernel/apic/apic.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/x86/kernel/apic/apic.c +1 -1
@@ -2093,7 +2093,7 @@ void __init init_apic_mappings(void)unsigned int new_apicid;if (apic_validate_deadline_timer ()) -pr_debug ("TSC deadline timer available\n" ); +pr_info ("TSC deadline timer available\n" );if (x2apic_mode) { boot_cpu_physical_apicid =read_apic_id ();
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 269/477 mfd: stmfx: Reset chip on resume as supply was disabled
In reply to Greg Kroah-HartmanFrom: Amelie Delaunay <[email protected]>
[ Upstream commit e583649d87ec090444aa5347af0927cd6e8581ae ]
STMFX supply is disabled during suspend. To avoid a too early access to the STMFX firmware on resume, reset the chip and wait for its firmware to be loaded.
--- drivers/mfd/stmfx.c | 7 +++++++ 1 file changed, 7 insertions(+)
drivers/mfd/stmfx.c +7 -0
@@ -501,6 +501,13 @@ static int stmfx_resume(struct device *dev) } } +/* Reset STMFX - supply has been stopped during suspend */ + ret =stmfx_chip_reset (stmfx); +if (ret) { +dev_err (stmfx->dev,"Failed to reset chip: %d\n" , ret); +return ret; + } + ret =regmap_raw_write (stmfx->map,STMFX_REG_SYS_CTRL , &stmfx->bkp_sysctrl,sizeof (stmfx->bkp_sysctrl));if (ret)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 270/477 mfd: stmfx: Fix stmfx_irq_init error path
In reply to Greg Kroah-HartmanFrom: Amelie Delaunay <[email protected]>
[ Upstream commit 60c2c4bcb9202acad4cc26af20b44b6bd7874f7b ]
In case the interrupt signal can't be configured, IRQ domain needs to be removed.
--- drivers/mfd/stmfx.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-)
drivers/mfd/stmfx.c +7 -2
@@ -287,14 +287,19 @@ static int stmfx_irq_init(struct i2c_client *client) ret =regmap_write (stmfx->map,STMFX_REG_IRQ_OUT_PIN , irqoutpin);if (ret) -return ret; + goto irq_exit; ret =devm_request_threaded_irq (stmfx->dev, client->irq,NULL , stmfx_irq_handler, irqtrigger |IRQF_ONESHOT ,"stmfx" , stmfx);if (ret) -stmfx_irq_exit (client); + goto irq_exit; + +return 0 ; + +irq_exit: +stmfx_irq_exit (client);return ret; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 271/477 mfd: stmfx: Disable IRQ in suspend to avoid spurious interrupt
In reply to Greg Kroah-HartmanFrom: Amelie Delaunay <[email protected]>
[ Upstream commit 97eda5dcc2cde5dcc778bef7a9344db3b6bf8ef5 ]
When STMFX supply is stopped, spurious interrupt can occur. To avoid that, disable the interrupt in suspend before disabling the regulator and re-enable it at the end of resume.
--- drivers/mfd/stmfx.c | 6 ++++++ include/linux/mfd/stmfx.h | 1 + 2 files changed, 7 insertions(+)
drivers/mfd/stmfx.c +6 -0
@@ -296,6 +296,8 @@ static int stmfx_irq_init(struct i2c_client *client)if (ret) goto irq_exit; + stmfx->irq = client->irq; +return 0 ; irq_exit:
@@ -486,6 +488,8 @@ static int stmfx_suspend(struct device *dev)if (ret)return ret; +disable_irq (stmfx->irq); +if (stmfx->vdd)return regulator_disable (stmfx->vdd);
@@ -529,6 +533,8 @@ static int stmfx_resume(struct device *dev)if (ret)return ret; +enable_irq (stmfx->irq); + return 0; }#endif
include/linux/mfd/stmfx.h +1 -0
@@ -109,6 +109,7 @@ struct stmfx {struct device *dev;struct regmap *map;struct regulator *vdd; +int irq;struct irq_domain *irq_domain;struct mutex lock;/* IRQ bus lock */ u8 irq_src;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 272/477 mfd: wcd934x: Drop kfree for memory allocated with devm_kzalloc
In reply to Greg Kroah-HartmanFrom: Wei Yongjun <[email protected]>
[ Upstream commit 652b7b6740eb52d98377a881c7730e36997f00ab ]
It's not necessary to free memory allocated with devm_kzalloc and using kfree leads to a double free.
--- drivers/mfd/wcd934x.c | 1 - 1 file changed, 1 deletion(-)
drivers/mfd/wcd934x.c +0 -1
@@ -280,7 +280,6 @@ static void wcd934x_slim_remove(struct slim_device *sdev)regulator_bulk_disable (WCD934X_MAX_SUPPLY , ddata->supplies);mfd_remove_devices (&sdev->dev); -kfree (ddata); }static const struct slim_device_id wcd934x_slim_id[] = {
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 273/477 powerpc/32s: Dont warn when mapping RO data ROX.
In reply to Greg Kroah-HartmanFrom: Christophe Leroy <[email protected]>
[ Upstream commit 4b19f96a81bceaf0bcf44d79c0855c61158065ec ]
Mapping RO data as ROX is not an issue since that data cannot be modified to introduce an exploit.
PPC64 accepts to have RO data mapped ROX, as a trade off between kernel size and strictness of protection.
On PPC32, kernel size is even more critical as amount of memory is usually small.
Depending on the number of available IBATs, the last IBATs might overflow the end of text. Only warn if it crosses the end of RO data.
--- arch/powerpc/mm/book3s32/mmu.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
arch/powerpc/mm/book3s32/mmu.c +4 -2
@@ -187,6 +187,7 @@ void mmu_mark_initmem_nx(void)int i;unsigned long base = (unsigned long )_stext -PAGE_OFFSET ;unsigned long top = (unsigned long )_etext -PAGE_OFFSET ; +unsigned long border = (unsigned long )__init_begin -PAGE_OFFSET ;unsigned long size;if (IS_ENABLED (CONFIG_PPC_BOOK3S_601 ))
@@ -201,9 +202,10 @@ void mmu_mark_initmem_nx(void) size =block_size (base, top); size =max (size,128UL <<10 );if ((top - base) > size) { -if (strict_kernel_rwx_enabled ()) -pr_warn ("Kernel _etext not properly aligned\n" ); size <<=1 ; +if (strict_kernel_rwx_enabled () && base + size > border) +pr_warn ("Some RW data is getting mapped X. " +"Adjust CONFIG_DATA_SHIFT to avoid that.\n" ); }setibat (i++,PAGE_OFFSET + base, base, size,PAGE_KERNEL_TEXT ); base += size;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 274/477 powerpc/8xx: Drop CONFIG_8xx_COPYBACK option
In reply to Greg Kroah-HartmanFrom: Christophe Leroy <[email protected]>
[ Upstream commit d3efcd38c0b99162d889e36a30425345a18edb33 ]
CONFIG_8xx_COPYBACK was there to help disabling copyback cache mode for debuging hardware. But nobody will design new boards with 8xx now.
All 8xx platforms select it, so make it the default and remove the option.
Also remove the Mx_RESETVAL values which are pretty useless and hide the real value while reading code.
--- arch/powerpc/configs/adder875_defconfig | 1 - arch/powerpc/configs/ep88xc_defconfig | 1 - arch/powerpc/configs/mpc866_ads_defconfig | 1 - arch/powerpc/configs/mpc885_ads_defconfig | 1 - arch/powerpc/configs/tqm8xx_defconfig | 1 - arch/powerpc/include/asm/nohash/32/mmu-8xx.h | 2 -- arch/powerpc/kernel/head_8xx.S | 15 +-------------- arch/powerpc/platforms/8xx/Kconfig | 9 --------- 8 files changed, 1 insertion(+), 30 deletions(-)
arch/powerpc/configs/adder875_defconfig +0 -1
@@ -10,7 +10,6 @@ CONFIG_EXPERT=y # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y CONFIG_PPC_ADDER875=y -CONFIG_8xx_COPYBACK=y CONFIG_GEN_RTC=y CONFIG_HZ_1000=y # CONFIG_SECCOMP is not set
arch/powerpc/configs/ep88xc_defconfig +0 -1
@@ -12,7 +12,6 @@ CONFIG_EXPERT=y # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y CONFIG_PPC_EP88XC=y -CONFIG_8xx_COPYBACK=y CONFIG_GEN_RTC=y CONFIG_HZ_100=y # CONFIG_SECCOMP is not set
arch/powerpc/configs/mpc866_ads_defconfig +0 -1
@@ -12,7 +12,6 @@ CONFIG_EXPERT=y # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y CONFIG_MPC86XADS=y -CONFIG_8xx_COPYBACK=y CONFIG_GEN_RTC=y CONFIG_HZ_1000=y CONFIG_MATH_EMULATION=y
arch/powerpc/configs/mpc885_ads_defconfig +0 -1
@@ -11,7 +11,6 @@ CONFIG_EXPERT=y # CONFIG_VM_EVENT_COUNTERS is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y -CONFIG_8xx_COPYBACK=y CONFIG_GEN_RTC=y CONFIG_HZ_100=y # CONFIG_SECCOMP is not set
arch/powerpc/configs/tqm8xx_defconfig +0 -1
@@ -15,7 +15,6 @@ CONFIG_MODULE_SRCVERSION_ALL=y # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y CONFIG_TQM8XX=y -CONFIG_8xx_COPYBACK=y # CONFIG_8xx_CPU15 is not set CONFIG_GEN_RTC=y CONFIG_HZ_100=y
arch/powerpc/include/asm/nohash/32/mmu-8xx.h +0 -2
@@ -19,7 +19,6 @@#define MI_RSV4I 0x08000000/* Reserve 4 TLB entries */ #define MI_PPCS 0x02000000/* Use MI_RPN prob/priv state */ #define MI_IDXMASK 0x00001f00/* TLB index to be loaded */ -#define MI_RESETVAL 0x00000000/* Value of register at reset */ /* These are the Ks and Kp from the PowerPC books. For proper operation, * Ks = 0, Kp = 1.
@@ -95,7 +94,6 @@#define MD_TWAM 0x04000000/* Use 4K page hardware assist */ #define MD_PPCS 0x02000000/* Use MI_RPN prob/priv state */ #define MD_IDXMASK 0x00001f00/* TLB index to be loaded */ -#define MD_RESETVAL 0x04000000/* Value of register at reset */ #define SPRN_M_CASID 793/* Address space ID (context) to match */ #define MC_ASIDMASK 0x0000000f/* Bits used for ASID value */
arch/powerpc/kernel/head_8xx.S +1 -14
@@ -779,10 +779,7 @@ start_here: initial_mmu: li r8, 0 mtspr SPRN_MI_CTR, r8 /* remove PINNED ITLB entries */ - lis r10, MD_RESETVAL@h -#ifndef CONFIG_8xx_COPYBACK - oris r10, r10, MD_WTDEF@h -#endif + lis r10, MD_TWAM@h mtspr SPRN_MD_CTR, r10 /* remove PINNED DTLB entries */ tlbia /* Invalidate all TLB entries */
@@ -857,17 +854,7 @@ initial_mmu: mtspr SPRN_DC_CST, r8 lis r8, IDC_ENABLE@h mtspr SPRN_IC_CST, r8 -#ifdef CONFIG_8xx_COPYBACK - mtspr SPRN_DC_CST, r8 -#else - /* For a debug option, I left this here to easily enable - * the write through cache mode - */ - lis r8, DC_SFWT@h mtspr SPRN_DC_CST, r8 - lis r8, IDC_ENABLE@h - mtspr SPRN_DC_CST, r8 -#endif /* Disable debug mode entry on breakpoints */ mfspr r8, SPRN_DER #ifdef CONFIG_PERF_EVENTS
arch/powerpc/platforms/8xx/Kconfig +0 -9
@@ -98,15 +98,6 @@ menu "MPC8xx CPM Options" # 8xx specific questions. comment "Generic MPC8xx Options" -config 8xx_COPYBACK - bool "Copy-Back Data Cache (else Writethrough)" - help - Saying Y here will cause the cache on an MPC8xx processor to be used - in Copy-Back mode. If you say N here, it is used in Writethrough - mode. - - If in doubt, say Y here. - config 8xx_GPIO bool "GPIO API Support" select GPIOLIB
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 275/477 ASoC: fix incomplete error-handling in img_i2s_in_probe.
In reply to Greg Kroah-HartmanFrom: Qiushi Wu <[email protected]>
[ Upstream commit 25bf943e4e7b47282bd86ae7d39e039217ebb007 ]
Function "pm_runtime_get_sync()" is not handled by "pm_runtime_put()" if "PTR_ERR(rst) == -EPROBE_DEFER". Fix this issue by adding "pm_runtime_put()" into this error path.
--- sound/soc/img/img-i2s-in.c | 1 + 1 file changed, 1 insertion(+)
sound/soc/img/img-i2s-in.c +1 -0
@@ -482,6 +482,7 @@ static int img_i2s_in_probe(struct platform_device *pdev)if (IS_ERR (rst)) {if (PTR_ERR (rst) == -EPROBE_DEFER ) { ret = -EPROBE_DEFER ; +pm_runtime_put (&pdev->dev); goto err_suspend; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 276/477 scsi: target: tcmu: Fix a use after free in tcmu_check_expired_queue_cmd()
In reply to Greg Kroah-HartmanFrom: Dan Carpenter <[email protected]>
[ Upstream commit 9d7464b18892332e35ff37f0b024429a1a9835e6 ]
The pr_debug() dereferences "cmd" after we already freed it by calling tcmu_free_cmd(cmd). The debug printk needs to be done earlier.
--- drivers/target/target_core_user.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
drivers/target/target_core_user.c +3 -3
@@ -1292,13 +1292,13 @@ static void tcmu_check_expired_queue_cmd(struct tcmu_cmd *cmd)if (!time_after (jiffies, cmd->deadline))return ; +pr_debug ("Timing out queued cmd %p on dev %s.\n" , + cmd, cmd->tcmu_dev->name); +list_del_init (&cmd->queue_entry); se_cmd = cmd->se_cmd;tcmu_free_cmd (cmd); -pr_debug ("Timing out queued cmd %p on dev %s.\n" , - cmd, cmd->tcmu_dev->name); -target_complete_cmd (se_cmd,SAM_STAT_TASK_SET_FULL ); }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 277/477 clk: bcm2835: Fix return type of bcm2835_register_gate
In reply to Greg Kroah-HartmanFrom: Nathan Chancellor <[email protected]>
[ Upstream commit f376c43bec4f8ee8d1ba5c5c4cfbd6e84fb279cb ]
bcm2835_register_gate is used as a callback for the clk_register member of bcm2835_clk_desc, which expects a struct clk_hw * return type but bcm2835_register_gate returns a struct clk *.
This discrepancy is hidden by the fact that bcm2835_register_gate is cast to the typedef bcm2835_clk_register by the _REGISTER macro. This turns out to be a control flow integrity violation, which is how this was noticed.
Change the return type of bcm2835_register_gate to be struct clk_hw * and use clk_hw_register_gate to do so. This should be a non-functional change as clk_register_gate calls clk_hw_register_gate anyways but this is needed to avoid issues with further changes.
--- drivers/clk/bcm/clk-bcm2835.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-)
drivers/clk/bcm/clk-bcm2835.c +5 -5
@@ -1448,13 +1448,13 @@ static struct clk_hw *bcm2835_register_clock(struct bcm2835_cprman *cprman,return &clock->hw; } -static struct clk *bcm2835_register_gate (struct bcm2835_cprman *cprman, +static struct clk_hw *bcm2835_register_gate (struct bcm2835_cprman *cprman,const struct bcm2835_gate_data *data) { -return clk_register_gate (cprman->dev, data->name, data->parent, -CLK_IGNORE_UNUSED |CLK_SET_RATE_GATE , - cprman->regs + data->ctl_reg, -CM_GATE_BIT ,0 , &cprman->regs_lock); +return clk_hw_register_gate (cprman->dev, data->name, data->parent, +CLK_IGNORE_UNUSED |CLK_SET_RATE_GATE , + cprman->regs + data->ctl_reg, +CM_GATE_BIT ,0 , &cprman->regs_lock); } typedef struct clk_hw *(*bcm2835_clk_register)(struct bcm2835_cprman *cprman,
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 278/477 scsi: ufs-qcom: Fix scheduling while atomic issue
In reply to Greg Kroah-HartmanFrom: Jeffrey Hugo <[email protected]>
[ Upstream commit 3be60b564de49875e47974c37fabced893cd0931 ]
ufs_qcom_dump_dbg_regs() uses usleep_range, a sleeping function, but can be called from atomic context in the following flow:
ufshcd_intr -> ufshcd_sl_intr -> ufshcd_check_errors -> ufshcd_print_host_regs -> ufshcd_vops_dbg_register_dump -> ufs_qcom_dump_dbg_regs
This causes a boot crash on the Lenovo Miix 630 when the interrupt is handled on the idle thread.
Fix the issue by switching to udelay().
--- drivers/scsi/ufs/ufs-qcom.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
drivers/scsi/ufs/ufs-qcom.c +3 -3
@@ -1658,11 +1658,11 @@ static void ufs_qcom_dump_dbg_regs(struct ufs_hba *hba)/* sleep a bit intermittently as we are dumping too much data */ ufs_qcom_print_hw_debug_reg_all (hba,NULL , ufs_qcom_dump_regs_wrapper); -usleep_range (1000 ,1100 ); +udelay (1000 );ufs_qcom_testbus_read (hba); -usleep_range (1000 ,1100 ); +udelay (1000 );ufs_qcom_print_unipro_testbus (hba); -usleep_range (1000 ,1100 ); +udelay (1000 ); }/**
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 279/477 clk: zynqmp: Fix divider2 calculation
In reply to Greg Kroah-HartmanFrom: Tejas Patel <[email protected]>
[ Upstream commit b8c1049c68d634a412ed5980ae666ed7c8839305 ]
zynqmp_get_divider2_val() calculates, divider value of type DIV2 clock, considering best possible combination of DIV1 and DIV2.
To find best possible values of DIV1 and DIV2, DIV1's parent rate should be consider and not DIV2's parent rate since it would rate of div1 clock. Consider a below topology,
out_clk->div2_clk->div1_clk->fixed_parent
where out_clk = (fixed_parent/div1_clk) / div2_clk, so parent clock of div1_clk (i.e. out_clk) should be divided by div1_clk and div2_clk.
Existing code divides parent rate of div2_clk's clock instead of div1_clk's parent rate, which is wrong.
Fix the same by considering div1's parent clock rate.
--- drivers/clk/zynqmp/divider.c | 17 ++++++++++++----- 1 file changed, 12 insertions(+), 5 deletions(-)
drivers/clk/zynqmp/divider.c +12 -5
@@ -111,23 +111,30 @@ static unsigned long zynqmp_clk_divider_recalc_rate(struct clk_hw *hw,static void zynqmp_get_divider2_val (struct clk_hw *hw,unsigned long rate, -unsigned long parent_rate,struct zynqmp_clk_divider *divider,int *bestdiv) {int div1;int div2;long error =LONG_MAX ; -struct clk_hw *parent_hw =clk_hw_get_parent (hw); -struct zynqmp_clk_divider *pdivider =to_zynqmp_clk_divider (parent_hw); +unsigned long div1_prate; +struct clk_hw *div1_parent_hw; +struct clk_hw *div2_parent_hw =clk_hw_get_parent (hw); +struct zynqmp_clk_divider *pdivider = +to_zynqmp_clk_divider (div2_parent_hw);if (!pdivider)return ; + div1_parent_hw =clk_hw_get_parent (div2_parent_hw); +if (!div1_parent_hw) +return ; + + div1_prate =clk_hw_get_rate (div1_parent_hw); *bestdiv =1 ;for (div1 =1 ; div1 <= pdivider->max_div;) {for (div2 =1 ; div2 <= divider->max_div;) { -long new_error = ((parent_rate / div1) / div2) - rate; +long new_error = ((div1_prate / div1) / div2) - rate;if (abs (new_error) <abs (error)) { *bestdiv = div2;
@@ -192,7 +199,7 @@ static long zynqmp_clk_divider_round_rate(struct clk_hw *hw,*/ if (div_type ==TYPE_DIV2 && (clk_hw_get_flags (hw) &CLK_SET_RATE_PARENT )) { -zynqmp_get_divider2_val (hw, rate, *prate, divider, &bestdiv); +zynqmp_get_divider2_val (hw, rate, divider, &bestdiv); }if ((clk_hw_get_flags (hw) &CLK_SET_RATE_PARENT ) && divider->is_frac)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 280/477 scsi: iscsi: Fix deadlock on recovery path during GFP_IO reclaim
In reply to Greg Kroah-HartmanFrom: Gabriel Krisman Bertazi <[email protected]>
[ Upstream commit 7e7cd796f2776d055351d80328f45633bbb0aae5 ]
iSCSI suffers from a deadlock in case a management command submitted via the netlink socket sleeps on an allocation while holding the rx_queue_mutex if that allocation causes a memory reclaim that writebacks to a failed iSCSI device. The recovery procedure can never make progress to recover the failed disk or abort outstanding IO operations to complete the reclaim (since rx_queue_mutex is locked), thus locking the system.
Nevertheless, just marking all allocations under rx_queue_mutex as GFP_NOIO (or locking the userspace process with something like PF_MEMALLOC_NOIO) is not enough, since the iSCSI command code relies on other subsystems that try to grab locked mutexes, whose threads are GFP_IO, leading to the same deadlock. One instance where this situation can be observed is in the backtraces below, stitched from multiple bugs reports, involving the kobj uevent sent when a session is created.
The root of the problem is not the fact that iSCSI does GFP_IO allocations, that is acceptable. The actual problem is that rx_queue_mutex has a very large granularity, covering every unrelated netlink command execution at the same time as the error recovery path.
The proposed fix leverages the recently added mechanism to stop failed connections from the kernel, by enabling it to execute even though a management command from the netlink socket is being run (rx_queue_mutex is held), provided that the command is known to be safe. It splits the rx_queue_mutex in two mutexes, one protecting from concurrent command execution from the netlink socket, and one protecting stop_conn from racing with other connection management operations that might conflict with it.
It is not very pretty, but it is the simplest way to resolve the deadlock. I considered making it a lock per connection, but some external mutex would still be needed to deal with iscsi_if_destroy_conn.
The patch was tested by forcing a memory shrinker (unrelated, but used bufio/dm-verity) to reclaim iSCSI pages every time ISCSI_UEVENT_CREATE_SESSION happens, which is reasonable to simulate reclaims that might happen with GFP_KERNEL on that path. Then, a faulty hung target causes a connection to fail during intensive IO, at the same time a new session is added by iscsid.
The following stacktraces are stiches from several bug reports, showing a case where the deadlock can happen.
iSCSI-write
holding: rx_queue_mutex
waiting: uevent_sock_mutex
kobject_uevent_env+0x1bd/0x419
kobject_uevent+0xb/0xd
device_add+0x48a/0x678
scsi_add_host_with_dma+0xc5/0x22d
iscsi_host_add+0x53/0x55
iscsi_sw_tcp_session_create+0xa6/0x129
iscsi_if_rx+0x100/0x1247
netlink_unicast+0x213/0x4f0
netlink_sendmsg+0x230/0x3c0 iscsi_fail iscsi_conn_failure
waiting: rx_queue_mutex
schedule_preempt_disabled+0x325/0x734
__mutex_lock_slowpath+0x18b/0x230
mutex_lock+0x22/0x40
iscsi_conn_failure+0x42/0x149
worker_thread+0x24a/0xbc0 EventManager_
holding: uevent_sock_mutex
waiting: dm_bufio_client->lock
dm_bufio_lock+0xe/0x10
shrink+0x34/0xf7
shrink_slab+0x177/0x5d0
do_try_to_free_pages+0x129/0x470
try_to_free_mem_cgroup_pages+0x14f/0x210
memcg_kmem_newpage_charge+0xa6d/0x13b0
__alloc_pages_nodemask+0x4a3/0x1a70
fallback_alloc+0x1b2/0x36c
__kmalloc_node_track_caller+0xb9/0x10d0
__alloc_skb+0x83/0x2f0
kobject_uevent_env+0x26b/0x419
dm_kobject_uevent+0x70/0x79
dev_suspend+0x1a9/0x1e7
ctl_ioctl+0x3e9/0x411
dm_ctl_ioctl+0x13/0x17
do_vfs_ioctl+0xb3/0x460
SyS_ioctl+0x5e/0x90 MemcgReclaimerD"
holding: dm_bufio_client->lock
waiting: stuck io to finish (needs iscsi_fail thread to progress)
schedule at ffffffffbd603618 io_schedule at ffffffffbd603ba4 do_io_schedule at ffffffffbdaf0d94 __wait_on_bit at ffffffffbd6008a6 out_of_line_wait_on_bit at ffffffffbd600960 wait_on_bit.constprop.10 at ffffffffbdaf0f17 __make_buffer_clean at ffffffffbdaf18ba __cleanup_old_buffer at ffffffffbdaf192f shrink at ffffffffbdaf19fd do_shrink_slab at ffffffffbd6ec000 shrink_slab at ffffffffbd6ec24a do_try_to_free_pages at ffffffffbd6eda09 try_to_free_mem_cgroup_pages at ffffffffbd6ede7e mem_cgroup_resize_limit at ffffffffbd7024c0 mem_cgroup_write at ffffffffbd703149 cgroup_file_write at ffffffffbd6d9c6e sys_write at ffffffffbd6662ea system_call_fastpath at ffffffffbdbc34a2
--- drivers/scsi/scsi_transport_iscsi.c | 64 +++++++++++++++++++++-------- 1 file changed, 47 insertions(+), 17 deletions(-)
drivers/scsi/scsi_transport_iscsi.c +47 -17
@@ -1616,6 +1616,12 @@ static DECLARE_TRANSPORT_CLASS(iscsi_connection_class,static struct sock *nls;static DEFINE_MUTEX (rx_queue_mutex); +/* +* conn_mutex protects the {start,bind,stop,destroy}_conn from racing +* against the kernel stop_connection recovery mechanism +*/ +static DEFINE_MUTEX (conn_mutex); +static LIST_HEAD (sesslist);static LIST_HEAD (sessdestroylist);static DEFINE_SPINLOCK (sesslock);
@@ -2445,6 +2451,32 @@ int iscsi_offload_mesg(struct Scsi_Host *shost, }EXPORT_SYMBOL_GPL (iscsi_offload_mesg); +/* +* This can be called without the rx_queue_mutex, if invoked by the kernel +* stop work. But, in that case, it is guaranteed not to race with +* iscsi_destroy by conn_mutex. +*/ +static void iscsi_if_stop_conn (struct iscsi_cls_conn *conn,int flag) +{ +/* +* It is important that this path doesn't rely on +* rx_queue_mutex, otherwise, a thread doing allocation on a +* start_session/start_connection could sleep waiting on a +* writeback to a failed iscsi device, that cannot be recovered +* because the lock is held. If we don't hold it here, the +* kernel stop_conn_work_fn has a chance to stop the broken +* session and resolve the allocation. +* +* Still, the user invoked .stop_conn() needs to be serialized +* with stop_conn_work_fn by a private mutex. Not pretty, but +* it works. +*/ +mutex_lock (&conn_mutex); + conn->transport->stop_conn (conn, flag); +mutex_unlock (&conn_mutex); + +} +static void stop_conn_work_fn (struct work_struct *work) {struct iscsi_cls_conn *conn, *tmp;
@@ -2463,30 +2495,17 @@ static void stop_conn_work_fn(struct work_struct *work)uint32_t sid =iscsi_conn_get_sid (conn);struct iscsi_cls_session *session; -mutex_lock (&rx_queue_mutex); - session =iscsi_session_lookup (sid);if (session) {if (system_state !=SYSTEM_RUNNING ) { session->recovery_tmo =0 ; - conn->transport->stop_conn (conn, -STOP_CONN_TERM ); +iscsi_if_stop_conn (conn,STOP_CONN_TERM ); }else { - conn->transport->stop_conn (conn, -STOP_CONN_RECOVER ); +iscsi_if_stop_conn (conn,STOP_CONN_RECOVER ); } }list_del_init (&conn->conn_list_err); - -mutex_unlock (&rx_queue_mutex); - -/* we don't want to hold rx_queue_mutex for too long, -* for instance if many conns failed at the same time, -* since this stall other iscsi maintenance operations. -* Give other users a chance to proceed. -*/ -cond_resched (); } }
@@ -2846,8 +2865,11 @@ iscsi_if_destroy_conn(struct iscsi_transport *transport, struct iscsi_uevent *evspin_unlock_irqrestore (&connlock, flags);ISCSI_DBG_TRANS_CONN (conn,"Destroying transport conn\n" ); + +mutex_lock (&conn_mutex);if (transport->destroy_conn) transport->destroy_conn (conn); +mutex_unlock (&conn_mutex);return 0 ; }
@@ -3689,9 +3711,12 @@ iscsi_if_recv_msg(struct sk_buff *skb, struct nlmsghdr *nlh, uint32_t *group)break ; } +mutex_lock (&conn_mutex); ev->r.retcode = transport->bind_conn (session, conn, ev->u.b_conn.transport_eph, ev->u.b_conn.is_leading); +mutex_unlock (&conn_mutex); +if (ev->r.retcode || !transport->ep_connect)break ;
@@ -3713,9 +3738,11 @@ iscsi_if_recv_msg(struct sk_buff *skb, struct nlmsghdr *nlh, uint32_t *group)case ISCSI_UEVENT_START_CONN : conn =iscsi_conn_lookup (ev->u.start_conn.sid, ev->u.start_conn.cid);if (conn) { +mutex_lock (&conn_mutex); ev->r.retcode = transport->start_conn (conn);if (!ev->r.retcode) conn->state =ISCSI_CONN_UP ; +mutex_unlock (&conn_mutex); }else err = -EINVAL ;
@@ -3723,17 +3750,20 @@ iscsi_if_recv_msg(struct sk_buff *skb, struct nlmsghdr *nlh, uint32_t *group)case ISCSI_UEVENT_STOP_CONN : conn =iscsi_conn_lookup (ev->u.stop_conn.sid, ev->u.stop_conn.cid);if (conn) - transport->stop_conn (conn, ev->u.stop_conn.flag); +iscsi_if_stop_conn (conn, ev->u.stop_conn.flag);else err = -EINVAL ;break ;case ISCSI_UEVENT_SEND_PDU : conn =iscsi_conn_lookup (ev->u.send_pdu.sid, ev->u.send_pdu.cid); -if (conn) +if (conn) { +mutex_lock (&conn_mutex); ev->r.retcode = transport->send_pdu (conn, (struct iscsi_hdr *)((char *)ev +sizeof (*ev)), (char *)ev +sizeof (*ev) + ev->u.send_pdu.hdr_size, ev->u.send_pdu.data_size); +mutex_unlock (&conn_mutex); + }else err = -EINVAL ;break ;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 281/477 scsi: ufs: ti-j721e-ufs: Fix unwinding of pm_runtime changes
In reply to Greg Kroah-HartmanFrom: Vignesh Raghavendra <[email protected]>
[ Upstream commit 22617e21633142dd2b81541cb3b95d6fb59aa85f ]
Fix unwinding of pm_runtime changes when bailing out of driver probe due to a failure and also on removal of driver.
--- drivers/scsi/ufs/ti-j721e-ufs.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-)
drivers/scsi/ufs/ti-j721e-ufs.c +10 -3
@@ -32,14 +32,14 @@ static int ti_j721e_ufs_probe(struct platform_device *pdev) ret =pm_runtime_get_sync (dev);if (ret <0 ) {pm_runtime_put_noidle (dev); -return ret; + goto disable_pm; }/* Select MPHY refclk frequency */ clk =devm_clk_get (dev,NULL );if (IS_ERR (clk)) {dev_err (dev,"Cannot claim MPHY clock.\n" ); -return PTR_ERR (clk); + goto clk_err; } clk_rate =clk_get_rate (clk);if (clk_rate ==26000000 )
@@ -54,16 +54,23 @@ static int ti_j721e_ufs_probe(struct platform_device *pdev) dev);if (ret) {dev_err (dev,"failed to populate child nodes %d\n" , ret); -pm_runtime_put_sync (dev); + goto clk_err; }return ret; + +clk_err: +pm_runtime_put_sync (dev); +disable_pm: +pm_runtime_disable (dev); +return ret; }static int ti_j721e_ufs_remove (struct platform_device *pdev) {of_platform_depopulate (&pdev->dev);pm_runtime_put_sync (&pdev->dev); +pm_runtime_disable (&pdev->dev);return 0 ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 282/477 KVM: PPC: Book3S HV: Ignore kmemleak false positives
In reply to Greg Kroah-HartmanFrom: Qian Cai <[email protected]>
[ Upstream commit 0aca8a5575544bd21b3363058afb8f1e81505150 ]
kvmppc_pmd_alloc() and kvmppc_pte_alloc() allocate some memory but then pud_populate() and pmd_populate() will use __pa() to reference the newly allocated memory.
Since kmemleak is unable to track the physical memory resulting in false positives, silence those by using kmemleak_ignore().
unreferenced object 0xc000201c382a1000 (size 4096):
comm "qemu-kvm", pid 124828, jiffies 4295733767 (age 341.250s) hex dump (first 32 bytes):
c0 00 20 09 f4 60 03 87 c0 00 20 10 72 a0 03 87 .. ..`.... .r... c0 00 20 0e 13 a0 03 87 c0 00 20 1b dc c0 03 87 .. ....... .....
backtrace:
[<000000004cc2790f>] kvmppc_create_pte+0x838/0xd20 [kvm_hv] kvmppc_pmd_alloc at arch/powerpc/kvm/book3s_64_mmu_radix.c:366 (inlined by) kvmppc_create_pte at arch/powerpc/kvm/book3s_64_mmu_radix.c:590 [<00000000d123c49a>] kvmppc_book3s_instantiate_page+0x2e0/0x8c0 [kvm_hv] [<00000000bb549087>] kvmppc_book3s_radix_page_fault+0x1b4/0x2b0 [kvm_hv] [<0000000086dddc0e>] kvmppc_book3s_hv_page_fault+0x214/0x12a0 [kvm_hv] [<000000005ae9ccc2>] kvmppc_vcpu_run_hv+0xc5c/0x15f0 [kvm_hv] [<00000000d22162ff>] kvmppc_vcpu_run+0x34/0x48 [kvm] [<00000000d6953bc4>] kvm_arch_vcpu_ioctl_run+0x314/0x420 [kvm] [<000000002543dd54>] kvm_vcpu_ioctl+0x33c/0x950 [kvm] [<0000000048155cd6>] ksys_ioctl+0xd8/0x130 [<0000000041ffeaa7>] sys_ioctl+0x28/0x40 [<000000004afc4310>] system_call_exception+0x114/0x1e0 [<00000000fb70a873>] system_call_common+0xf0/0x278
unreferenced object 0xc0002001f0c03900 (size 256):
comm "qemu-kvm", pid 124830, jiffies 4295735235 (age 326.570s) hex dump (first 32 bytes):
c0 00 20 10 fa a0 03 87 c0 00 20 10 fa a1 03 87 .. ....... ..... c0 00 20 10 fa a2 03 87 c0 00 20 10 fa a3 03 87 .. ....... .....
backtrace:
[<0000000023f675b8>] kvmppc_create_pte+0x854/0xd20 [kvm_hv] kvmppc_pte_alloc at arch/powerpc/kvm/book3s_64_mmu_radix.c:356 (inlined by) kvmppc_create_pte at arch/powerpc/kvm/book3s_64_mmu_radix.c:593 [<00000000d123c49a>] kvmppc_book3s_instantiate_page+0x2e0/0x8c0 [kvm_hv] [<00000000bb549087>] kvmppc_book3s_radix_page_fault+0x1b4/0x2b0 [kvm_hv] [<0000000086dddc0e>] kvmppc_book3s_hv_page_fault+0x214/0x12a0 [kvm_hv] [<000000005ae9ccc2>] kvmppc_vcpu_run_hv+0xc5c/0x15f0 [kvm_hv] [<00000000d22162ff>] kvmppc_vcpu_run+0x34/0x48 [kvm] [<00000000d6953bc4>] kvm_arch_vcpu_ioctl_run+0x314/0x420 [kvm] [<000000002543dd54>] kvm_vcpu_ioctl+0x33c/0x950 [kvm] [<0000000048155cd6>] ksys_ioctl+0xd8/0x130 [<0000000041ffeaa7>] sys_ioctl+0x28/0x40 [<000000004afc4310>] system_call_exception+0x114/0x1e0 [<00000000fb70a873>] system_call_common+0xf0/0x278
--- arch/powerpc/kvm/book3s_64_mmu_radix.c | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-)
arch/powerpc/kvm/book3s_64_mmu_radix.c +14 -2
@@ -353,7 +353,13 @@ static struct kmem_cache *kvm_pmd_cache;static pte_t *kvmppc_pte_alloc (void ) { -return kmem_cache_alloc (kvm_pte_cache,GFP_KERNEL ); +pte_t *pte; + + pte =kmem_cache_alloc (kvm_pte_cache,GFP_KERNEL ); +/* pmd_populate() will only reference _pa(pte). */ +kmemleak_ignore (pte); + +return pte; }static void kvmppc_pte_free (pte_t *ptep)
@@ -363,7 +369,13 @@ static void kvmppc_pte_free(pte_t *ptep)static pmd_t *kvmppc_pmd_alloc (void ) { -return kmem_cache_alloc (kvm_pmd_cache,GFP_KERNEL ); +pmd_t *pmd; + + pmd =kmem_cache_alloc (kvm_pmd_cache,GFP_KERNEL ); +/* pud_populate() will only reference _pa(pmd). */ +kmemleak_ignore (pmd); + +return pmd; }static void kvmppc_pmd_free (pmd_t *pmdp)
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 283/477 KVM: PPC: Book3S: Fix some RCU-list locks
In reply to Greg Kroah-HartmanFrom: Qian Cai <[email protected]>
[ Upstream commit ab8b65be183180c3eef405d449163964ecc4b571 ]
It is unsafe to traverse kvm->arch.spapr_tce_tables and stt->iommu_tables without the RCU read lock held. Also, add cond_resched_rcu() in places with the RCU read lock held that could take a while to finish.
arch/powerpc/kvm/book3s_64_vio.c:76 RCU-list traversed in non-reader section!!
other info that might help us debug this:
rcu_scheduler_active = 2, debug_locks = 1
no locks held by qemu-kvm/4265.
stack backtrace: CPU: 96 PID: 4265 Comm: qemu-kvm Not tainted 5.7.0-rc4-next-20200508+ #2 Call Trace: [c000201a8690f720] [c000000000715948] dump_stack+0xfc/0x174 (unreliable) [c000201a8690f770] [c0000000001d9470] lockdep_rcu_suspicious+0x140/0x164 [c000201a8690f7f0] [c008000010b9fb48] kvm_spapr_tce_release_iommu_group+0x1f0/0x220 [kvm] [c000201a8690f870] [c008000010b8462c] kvm_spapr_tce_release_vfio_group+0x54/0xb0 [kvm] [c000201a8690f8a0] [c008000010b84710] kvm_vfio_destroy+0x88/0x140 [kvm] [c000201a8690f8f0] [c008000010b7d488] kvm_put_kvm+0x370/0x600 [kvm] [c000201a8690f990] [c008000010b7e3c0] kvm_vm_release+0x38/0x60 [kvm] [c000201a8690f9c0] [c0000000005223f4] __fput+0x124/0x330 [c000201a8690fa20] [c000000000151cd8] task_work_run+0xb8/0x130 [c000201a8690fa70] [c0000000001197e8] do_exit+0x4e8/0xfa0 [c000201a8690fb70] [c00000000011a374] do_group_exit+0x64/0xd0 [c000201a8690fbb0] [c000000000132c90] get_signal+0x1f0/0x1200 [c000201a8690fcc0] [c000000000020690] do_notify_resume+0x130/0x3c0 [c000201a8690fda0] [c000000000038d64] syscall_exit_prepare+0x1a4/0x280 [c000201a8690fe20] [c00000000000c8f8] system_call_common+0xf8/0x278
====
arch/powerpc/kvm/book3s_64_vio.c:368 RCU-list traversed in non-reader section!!
other info that might help us debug this:
rcu_scheduler_active = 2, debug_locks = 1
2 locks held by qemu-kvm/4264:
#0: c000201ae2d000d8 (&vcpu->mutex){+.+.}-{3:3}, at: kvm_vcpu_ioctl+0xdc/0x950 [kvm] #1: c000200c9ed0c468 (&kvm->srcu){....}-{0:0}, at: kvmppc_h_put_tce+0x88/0x340 [kvm]
====
arch/powerpc/kvm/book3s_64_vio.c:108 RCU-list traversed in non-reader section!!
other info that might help us debug this:
rcu_scheduler_active = 2, debug_locks = 1
1 lock held by qemu-kvm/4257:
#0: c000200b1b363a40 (&kv->lock){+.+.}-{3:3}, at: kvm_vfio_set_attr+0x598/0x6c0 [kvm]
====
arch/powerpc/kvm/book3s_64_vio.c:146 RCU-list traversed in non-reader section!!
other info that might help us debug this:
rcu_scheduler_active = 2, debug_locks = 1
1 lock held by qemu-kvm/4257:
#0: c000200b1b363a40 (&kv->lock){+.+.}-{3:3}, at: kvm_vfio_set_attr+0x598/0x6c0 [kvm]
--- arch/powerpc/kvm/book3s_64_vio.c | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-)
arch/powerpc/kvm/book3s_64_vio.c +14 -4
@@ -73,6 +73,7 @@ extern void kvm_spapr_tce_release_iommu_group(struct kvm *kvm,struct kvmppc_spapr_tce_iommu_table *stit, *tmp;struct iommu_table_group *table_group =NULL ; +rcu_read_lock ();list_for_each_entry_rcu (stt, &kvm->arch.spapr_tce_tables, list) { table_group =iommu_group_get_iommudata (grp);
@@ -87,7 +88,9 @@ extern void kvm_spapr_tce_release_iommu_group(struct kvm *kvm,kref_put (&stit->kref, kvm_spapr_tce_liobn_put); } } +cond_resched_rcu (); } +rcu_read_unlock (); } extern long kvm_spapr_tce_attach_iommu_group(struct kvm *kvm, int tablefd,
@@ -105,12 +108,14 @@ extern long kvm_spapr_tce_attach_iommu_group(struct kvm *kvm, int tablefd,if (!f.file)return -EBADF ; +rcu_read_lock ();list_for_each_entry_rcu (stt, &kvm->arch.spapr_tce_tables, list) {if (stt == f.file->private_data) { found = true;break ; } } +rcu_read_unlock ();fdput (f);
@@ -143,6 +148,7 @@ extern long kvm_spapr_tce_attach_iommu_group(struct kvm *kvm, int tablefd,if (!tbl)return -EINVAL ; +rcu_read_lock ();list_for_each_entry_rcu (stit, &stt->iommu_tables, next) {if (tbl != stit->tbl)continue ;
@@ -150,14 +156,17 @@ extern long kvm_spapr_tce_attach_iommu_group(struct kvm *kvm, int tablefd,if (!kref_get_unless_zero (&stit->kref)) {/* stit is being destroyed */ iommu_tce_table_put (tbl); +rcu_read_unlock ();return -ENOTTY ; }/* * The table is already known to this KVM, we just increased * its KVM reference counter and can return. */ +rcu_read_unlock ();return 0 ; } +rcu_read_unlock (); stit =kzalloc (sizeof (*stit),GFP_KERNEL );if (!stit) {
@@ -365,18 +374,19 @@ static long kvmppc_tce_validate(struct kvmppc_spapr_tce_table *stt,if (kvmppc_tce_to_ua (stt->kvm, tce, &ua))return H_TOO_HARD ; +rcu_read_lock ();list_for_each_entry_rcu (stit, &stt->iommu_tables, next) {unsigned long hpa =0 ;struct mm_iommu_table_group_mem_t *mem;long shift = stit->tbl->it_page_shift; mem =mm_iommu_lookup (stt->kvm->mm, ua,1ULL << shift); -if (!mem) -return H_TOO_HARD ; - -if (mm_iommu_ua_to_hpa (mem, ua, shift, &hpa)) +if (!mem ||mm_iommu_ua_to_hpa (mem, ua, shift, &hpa)) { +rcu_read_unlock ();return H_TOO_HARD ; + } } +rcu_read_unlock ();return H_SUCCESS ; }
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 284/477 KVM: PPC: Book3S HV: Relax check on H_SVM_INIT_ABORT
In reply to Greg Kroah-HartmanFrom: Laurent Dufour <[email protected]>
[ Upstream commit e3326ae3d59e443a379367c6936941d6ab55d316 ]
The commit 8c47b6ff29e3 ("KVM: PPC: Book3S HV: Check caller of H_SVM_* Hcalls") added checks of secure bit of SRR1 to filter out the Hcall reserved to the Ultravisor.
However, the Hcall H_SVM_INIT_ABORT is made by the Ultravisor passing the context of the VM calling UV_ESM. This allows the Hypervisor to return to the guest without going through the Ultravisor. Thus the Secure bit of SRR1 is not set in that particular case.
In the case a regular VM is calling H_SVM_INIT_ABORT, this hcall will be filtered out in kvmppc_h_svm_init_abort() because kvm->arch.secure_guest is not set in that case.
--- arch/powerpc/kvm/book3s_hv.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)
arch/powerpc/kvm/book3s_hv.c +8 -3
@@ -1099,9 +1099,14 @@ int kvmppc_pseries_do_hcall(struct kvm_vcpu *vcpu) ret =kvmppc_h_svm_init_done (vcpu->kvm);break ;case H_SVM_INIT_ABORT : - ret =H_UNSUPPORTED ; -if (kvmppc_get_srr1 (vcpu) &MSR_S ) - ret =kvmppc_h_svm_init_abort (vcpu->kvm); +/* +* Even if that call is made by the Ultravisor, the SSR1 value +* is the guest context one, with the secure bit clear as it has +* not yet been secured. So we can't check it here. +* Instead the kvm->arch.secure_guest flag is checked inside +* kvmppc_h_svm_init_abort(). +*/ + ret =kvmppc_h_svm_init_abort (vcpu->kvm);break ;default :
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 285/477 clk: sprd: return correct type of value for _sprd_pll_recalc_rate
In reply to Greg Kroah-HartmanFrom: Chunyan Zhang <[email protected]>
[ Upstream commit c2f30986d418f26abefc2eec90ebf06716c970d2 ]
The function _sprd_pll_recalc_rate() defines return value to unsigned long, but it would return a negative value when malloc fail, changing to return its parent_rate makes more sense, since if the callback .recalc_rate() is not set, the framework returns the parent_rate as well.
--- drivers/clk/sprd/pll.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/clk/sprd/pll.c +1 -1
@@ -106,7 +106,7 @@ static unsigned long _sprd_pll_recalc_rate(const struct sprd_pll *pll, cfg =kcalloc (regs_num,sizeof (*cfg),GFP_KERNEL );if (!cfg) -return -ENOMEM ; +return parent_rate;for (i =0 ; i < regs_num; i++) cfg[i] =sprd_pll_read (pll, i);
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 286/477 clk: ast2600: Fix AHB clock divider for A1
In reply to Greg Kroah-HartmanFrom: Eddie James <[email protected]>
[ Upstream commit 2d491066ccd4286538450c227fc5094ceb04b494 ]
The latest specs for the AST2600 A1 chip include some different bit definitions for calculating the AHB clock divider. Implement these in order to get the correct AHB clock value in Linux.
--- drivers/clk/clk-ast2600.c | 31 +++++++++++++++++++++++++------ 1 file changed, 25 insertions(+), 6 deletions(-)
drivers/clk/clk-ast2600.c +25 -6
@@ -642,14 +642,22 @@ static const u32 ast2600_a0_axi_ahb_div_table[] = { 2, 2, 3, 5, }; -static const u32 ast2600_a1_axi_ahb_div_table[] = { -4 ,6 ,2 ,4 , +static const u32 ast2600_a1_axi_ahb_div0_tbl[] = { +3 ,2 ,3 ,4 , +}; + +static const u32 ast2600_a1_axi_ahb_div1_tbl[] = { +3 ,4 ,6 ,8 , +}; + +static const u32 ast2600_a1_axi_ahb200_tbl[] = { +3 ,4 ,3 ,4 ,2 ,2 ,2 ,2 , };static void __init aspeed_g6_cc (struct regmap *map) {struct clk_hw *hw; -u32 val, div, chip_id, axi_div, ahb_div; +u32 val, div, divbits, chip_id, axi_div, ahb_div;clk_hw_register_fixed_rate (NULL ,"clkin" ,NULL ,0 ,25000000 );
@@ -679,11 +687,22 @@ static void __init aspeed_g6_cc(struct regmap *map)else axi_div =2 ; + divbits = (val >>11 ) &0x3 ;regmap_read (map,ASPEED_G6_SILICON_REV , &chip_id); -if (chip_id &BIT (16 )) - ahb_div = ast2600_a1_axi_ahb_div_table[(val >>11 ) &0x3 ]; -else +if (chip_id &BIT (16 )) { +if (!divbits) { + ahb_div = ast2600_a1_axi_ahb200_tbl[(val >>8 ) &0x3 ]; +if (val &BIT (16 )) + ahb_div *=2 ; + }else { +if (val &BIT (16 )) + ahb_div = ast2600_a1_axi_ahb_div1_tbl[divbits]; +else + ahb_div = ast2600_a1_axi_ahb_div0_tbl[divbits]; + } + }else { ahb_div = ast2600_a0_axi_ahb_div_table[(val >>11 ) &0x3 ]; + } hw =clk_hw_register_fixed_factor (NULL ,"ahb" ,"hpll" ,0 ,1 , axi_div * ahb_div); aspeed_g6_clk_data->hws[ASPEED_CLK_AHB ] = hw;
Signature · 1 line
2.25.1
Greg Kroah-Hartman
maintainerPATCH 287/477 misc: xilinx-sdfec: improve get_user_pages_fast() error handling
In reply to Greg Kroah-HartmanFrom: John Hubbard <[email protected]>
[ Upstream commit 57343d51613227373759f5b0f2eede257fd4b82e ]
This fixes the case of get_user_pages_fast() returning a -errno. The result needs to be stored in a signed integer. And for safe signed/unsigned comparisons, it's best to keep everything signed. And get_user_pages_fast() also expects a signed value for number of pages to pin.
Therefore, change most relevant variables, from u32 to int. Leave "n" unsigned, for convenience in checking for overflow. And provide a WARN_ON_ONCE() and early return, if overflow occurs.
Also, as long as we're tidying up: rename the page array from page, to pages, in order to match the conventions used in most other call sites.
--- drivers/misc/xilinx_sdfec.c | 27 +++++++++++++++++---------- 1 file changed, 17 insertions(+), 10 deletions(-)
drivers/misc/xilinx_sdfec.c +17 -10
@@ -602,10 +602,10 @@ static int xsdfec_table_write(struct xsdfec_dev *xsdfec, u32 offset, const u32 depth) {u32 reg =0 ; -u32 res; -u32 n, i; +int res, i, nr_pages; +u32 n;u32 *addr =NULL ; -struct page *page[MAX_NUM_PAGES ]; +struct page *pages[MAX_NUM_PAGES ];/* * Writes that go beyond the length of
@@ -622,15 +622,22 @@ static int xsdfec_table_write(struct xsdfec_dev *xsdfec, u32 offset,if ((len *XSDFEC_REG_WIDTH_JUMP ) %PAGE_SIZE ) n +=1 ; - res =get_user_pages_fast ((unsigned long )src_ptr, n,0 , page); -if (res < n) { -for (i =0 ; i < res; i++) -put_page (page[i]); +if (WARN_ON_ONCE (n >INT_MAX )) +return -EINVAL ; + + nr_pages = n; + + res =get_user_pages_fast ((unsigned long )src_ptr, nr_pages,0 , pages); +if (res < nr_pages) { +if (res >0 ) { +for (i =0 ; i < res; i++) +put_page (pages[i]); + }return -EINVAL ; } - for (i = 0; i < n; i++) { - addr = kmap(page[i]); + for (i = 0; i < nr_pages; i++) { + addr = kmap(pages[i]); do { xsdfec_regwrite(xsdfec, base_addr + ((offset + reg) *
@@ -639,7 +646,7 @@ static int xsdfec_table_write(struct xsdfec_dev *xsdfec, u32 offset, reg++; }while ((reg < len) && ((reg *XSDFEC_REG_WIDTH_JUMP ) %PAGE_SIZE )); -put_page (page[i]); +put_page (pages[i]); }return reg; }
Signature · 9 lines
2.25.1 _______________________________________________ linux-arm-kernel mailing list [email protected] http://lists.infradead.org/mailman/listinfo/linux-arm-kernel