6.6.64-rc1 review
Subsystems (5)
Greg Kroah-Hartman
maintainerPATCH 404/676 net/ipv6: delete temporary address if mngtmpaddr is removed or unmanaged
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hangbin Liu <[email protected]>
[ Upstream commit 00b5b7aab9e422d00d5a9d03d7e0760a76b5d57f ]
RFC8981 section 3.4 says that existing temporary addresses must have their lifetimes adjusted so that no temporary addresses should ever remain "valid" or "preferred" longer than the incoming SLAAC Prefix Information. This would strongly imply in Linux's case that if the "mngtmpaddr" address is deleted or un-flagged as such, its corresponding temporary addresses must be cleared out right away.
But now the temporary address is renewed even after ‘mngtmpaddr’ is removed or becomes unmanaged as manage_tempaddrs() set temporary addresses prefered/valid time to 0, and later in addrconf_verify_rtnl() all checkings failed to remove the addresses. Fix this by deleting the temporary address directly for these situations.
--- net/ipv6/addrconf.c | 41 +++++++++++++++++++++++++++++------------ 1 file changed, 29 insertions(+), 12 deletions(-)
net/ipv6/addrconf.c +29 -12
@@ -2535,6 +2535,24 @@ static struct inet6_dev *addrconf_add_dev(struct net_device *dev)return idev; } +static void delete_tempaddrs (struct inet6_dev *idev, +struct inet6_ifaddr *ifp) +{ +struct inet6_ifaddr *ift, *tmp; + +write_lock_bh (&idev->lock); +list_for_each_entry_safe (ift, tmp, &idev->tempaddr_list, tmp_list) { +if (ift->ifpub != ifp) +continue ; + +in6_ifa_hold (ift); +write_unlock_bh (&idev->lock); +ipv6_del_addr (ift); +write_lock_bh (&idev->lock); + } +write_unlock_bh (&idev->lock); +} + static void manage_tempaddrs(struct inet6_dev *idev, struct inet6_ifaddr *ifp, __u32 valid_lft, __u32 prefered_lft,
@@ -3076,11 +3094,12 @@ static int inet6_addr_del(struct net *net, int ifindex, u32 ifa_flags,in6_ifa_hold (ifp);read_unlock_bh (&idev->lock); -if (!(ifp->flags &IFA_F_TEMPORARY ) && - (ifa_flags &IFA_F_MANAGETEMPADDR )) -manage_tempaddrs (idev, ifp,0 ,0 , false, - jiffies);ipv6_del_addr (ifp); + +if (!(ifp->flags &IFA_F_TEMPORARY ) && + (ifp->flags &IFA_F_MANAGETEMPADDR )) +delete_tempaddrs (idev, ifp); +addrconf_verify_rtnl (net);if (ipv6_addr_is_multicast (pfx)) { ipv6_mc_config(net->ipv6.mc_autojoin_sk,
@@ -4891,14 +4910,12 @@ static int inet6_addr_modify(struct net *net, struct inet6_ifaddr *ifp, }if (was_managetempaddr || ifp->flags &IFA_F_MANAGETEMPADDR ) { -if (was_managetempaddr && - !(ifp->flags &IFA_F_MANAGETEMPADDR )) { - cfg->valid_lft =0 ; - cfg->preferred_lft =0 ; - } -manage_tempaddrs (ifp->idev, ifp, cfg->valid_lft, - cfg->preferred_lft, !was_managetempaddr, - jiffies); +if (was_managetempaddr && !(ifp->flags &IFA_F_MANAGETEMPADDR )) +delete_tempaddrs (ifp->idev, ifp); +else +manage_tempaddrs (ifp->idev, ifp, cfg->valid_lft, + cfg->preferred_lft, !was_managetempaddr, + jiffies); }addrconf_verify_rtnl (net);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 405/676 net: mdio-ipq4019: add missing error check
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Rosen Penev <[email protected]>
[ Upstream commit 9cc8d0ecdd2aad42e377e971e3bb114339df609e ]
If an optional resource is found but fails to remap, return on failure. Avoids any potential problems when using the iomapped resource as the assumption is that it's available.
--- drivers/net/mdio/mdio-ipq4019.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
drivers/net/mdio/mdio-ipq4019.c +4 -1
@@ -255,8 +255,11 @@ static int ipq4019_mdio_probe(struct platform_device *pdev)/* The platform resource is provided on the chipset IPQ5018 */ /* This resource is optional */ res =platform_get_resource (pdev,IORESOURCE_MEM ,1 ); -if (res) +if (res) { priv->eth_ldo_rdy =devm_ioremap_resource (&pdev->dev, res); +if (IS_ERR (priv->eth_ldo_rdy)) +return PTR_ERR (priv->eth_ldo_rdy); + } bus->name ="ipq4019_mdio" ; bus->read = ipq4019_mdio_read_c22;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 406/676 marvell: pxa168_eth: fix call balance of pep->clk handling routines
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Vitalii Mordan <[email protected]>
[ Upstream commit b032ae57d4fe2b2445e3bc190db6fcaa8c102f68 ]
If the clock pep->clk was not enabled in pxa168_eth_probe, it should not be disabled in any path.
Conversely, if it was enabled in pxa168_eth_probe, it must be disabled in all error paths to ensure proper cleanup.
Use the devm_clk_get_enabled helper function to ensure proper call balance for pep->clk.
Found by Linux Verification Center (linuxtesting.org) with Klever.
--- drivers/net/ethernet/marvell/pxa168_eth.c | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-)
drivers/net/ethernet/marvell/pxa168_eth.c +4 -10
@@ -1394,18 +1394,15 @@ static int pxa168_eth_probe(struct platform_device *pdev)printk (KERN_NOTICE "PXA168 10/100 Ethernet Driver\n" ); - clk =devm_clk_get (&pdev->dev,NULL ); + clk =devm_clk_get_enabled (&pdev->dev,NULL );if (IS_ERR (clk)) { -dev_err (&pdev->dev,"Fast Ethernet failed to get clock\n" ); +dev_err (&pdev->dev,"Fast Ethernet failed to get and enable clock\n" );return -ENODEV ; } -clk_prepare_enable (clk); dev =alloc_etherdev (sizeof (struct pxa168_eth_private )); -if (!dev) { - err = -ENOMEM ; - goto err_clk; - } +if (!dev) +return -ENOMEM ;platform_set_drvdata (pdev, dev); pep =netdev_priv (dev);
@@ -1523,8 +1520,6 @@ static int pxa168_eth_probe(struct platform_device *pdev)mdiobus_free (pep->smi_bus); err_netdev:free_netdev (dev); -err_clk: -clk_disable_unprepare (clk);return err; }
@@ -1542,7 +1537,6 @@ static int pxa168_eth_remove(struct platform_device *pdev)if (dev->phydev)phy_disconnect (dev->phydev); -clk_disable_unprepare (pep->clk);mdiobus_unregister (pep->smi_bus);mdiobus_free (pep->smi_bus);unregister_netdev (dev);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 407/676 net: stmmac: dwmac-socfpga: Set RX watchdog interrupt as broken
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Maxime Chevallier <[email protected]>
[ Upstream commit 407618d66dba55e7db1278872e8be106808bbe91 ]
On DWMAC3 and later, there's a RX Watchdog interrupt that's used for interrupt coalescing. It's known to be buggy on some platforms, and dwmac-socfpga appears to be one of them. Changing the interrupt coalescing from ethtool doesn't appear to have any effect here.
Without disabling RIWT (Received Interrupt Watchdog Timer, I believe...), we observe latencies while receiving traffic that amount to around ~0.4ms. This was discovered with NTP but can be easily reproduced with a simple ping. Without this patch :
64 bytes from 192.168.5.2: icmp_seq=1 ttl=64 time=0.657 ms
With this patch :
64 bytes from 192.168.5.2: icmp_seq=1 ttl=64 time=0.254 ms
--- drivers/net/ethernet/stmicro/stmmac/dwmac-socfpga.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/net/ethernet/stmicro/stmmac/dwmac-socfpga.c +2 -0
@@ -429,6 +429,8 @@ static int socfpga_dwmac_probe(struct platform_device *pdev) plat_dat->bsp_priv = dwmac; plat_dat->fix_mac_speed = socfpga_dwmac_fix_mac_speed; + plat_dat->riwt_off =1 ; + ret =stmmac_dvr_probe (&pdev->dev, plat_dat, &stmmac_res);if (ret) goto err_remove_config_dt;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 408/676 octeontx2-af: RPM: Fix mismatch in lmac type
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hariprasad Kelam <[email protected]>
[ Upstream commit 7ebbbb23ea5b6d051509cb11399afac5042c9266 ]
Due to a bug in the previous patch, there is a mismatch between the lmac type reported by the driver and the actual hardware configuration.
--- drivers/net/ethernet/marvell/octeontx2/af/rpm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/net/ethernet/marvell/octeontx2/af/rpm.c +1 -1
@@ -450,7 +450,7 @@ u8 rpm_get_lmac_type(void *rpmd, int lmac_id)int err; req =FIELD_SET (CMDREG_ID ,CGX_CMD_GET_LINK_STS , req); - err =cgx_fwi_cmd_generic (req, &resp, rpm,0 ); + err =cgx_fwi_cmd_generic (req, &resp, rpm, lmac_id);if (!err)return FIELD_GET (RESP_LINKSTAT_LMAC_TYPE , resp);return err;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 409/676 octeontx2-af: RPM: Fix low network performance
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hariprasad Kelam <[email protected]>
[ Upstream commit d1e8884e050c1255a9ceb477f5ff926ee9214a23 ]
Low network performance is observed even on RPMs with larger FIFO lengths.
The cn10kb silicon has three RPM blocks with the following FIFO sizes:
--------------------
| RPM0 | 256KB |
| RPM1 | 256KB |
| RPM2 | 128KB |
--------------------The current design stores the FIFO length in a common structure for all RPMs (mac_ops). As a result, the FIFO length of the last RPM is applied to all RPMs, leading to reduced network performance.
This patch resolved the problem by storing the fifo length in per MAC structure (cgx).
--- drivers/net/ethernet/marvell/octeontx2/af/cgx.c | 9 +++++++-- drivers/net/ethernet/marvell/octeontx2/af/cgx.h | 1 + drivers/net/ethernet/marvell/octeontx2/af/lmac_common.h | 5 ++++- drivers/net/ethernet/marvell/octeontx2/af/rpm.c | 6 +++--- drivers/net/ethernet/marvell/octeontx2/af/rvu_cgx.c | 9 ++++----- 5 files changed, 19 insertions(+), 11 deletions(-)
drivers/net/ethernet/marvell/octeontx2/af/cgx.c +7 -2
@@ -110,6 +110,11 @@ struct mac_ops *get_mac_ops(void *cgxd)return ((struct cgx *)cgxd)->mac_ops; } +u32 cgx_get_fifo_len (void *cgxd) +{ +return ((struct cgx *)cgxd)->fifo_len; +} +void cgx_write (struct cgx *cgx,u64 lmac,u64 offset,u64 val) { writeq(val, cgx->reg_base + (lmac << cgx->mac_ops->lmac_offset) +
@@ -499,7 +504,7 @@ static u32 cgx_get_lmac_fifo_len(void *cgxd, int lmac_id)u8 num_lmacs;u32 fifo_len; - fifo_len = cgx->mac_ops->fifo_len; + fifo_len = cgx->fifo_len; num_lmacs = cgx->mac_ops->get_nr_lmacs (cgx);switch (num_lmacs) {
@@ -1740,7 +1745,7 @@ static void cgx_populate_features(struct cgx *cgx)u64 cfg; cfg =cgx_read (cgx,0 ,CGX_CONST ); - cgx->mac_ops->fifo_len =FIELD_GET (CGX_CONST_RXFIFO_SIZE , cfg); + cgx->fifo_len =FIELD_GET (CGX_CONST_RXFIFO_SIZE , cfg); cgx->max_lmac_per_mac =FIELD_GET (CGX_CONST_MAX_LMACS , cfg);if (is_dev_rpm (cgx))
drivers/net/ethernet/marvell/octeontx2/af/cgx.h +1 -0
@@ -184,4 +184,5 @@ int cgx_lmac_get_pfc_frm_cfg(void *cgxd, int lmac_id, u8 *tx_pause,int verify_lmac_fc_cfg (void *cgxd,int lmac_id,u8 tx_pause,u8 rx_pause,int pfvf_idx);int cgx_lmac_reset (void *cgxd,int lmac_id,u8 pf_req_flr); +u32 cgx_get_fifo_len (void *cgxd);#endif /* CGX_H */
drivers/net/ethernet/marvell/octeontx2/af/lmac_common.h +4 -1
@@ -72,7 +72,6 @@ struct mac_ops {u8 irq_offset;u8 int_ena_bit;u8 lmac_fwi; -u32 fifo_len;bool non_contiguous_serdes_lane;/* RPM & CGX differs in number of Receive/transmit stats */ u8 rx_stats_cnt;
@@ -141,6 +140,10 @@ struct cgx {u8 lmac_count;/* number of LMACs per MAC could be 4 or 8 */ u8 max_lmac_per_mac; +/* length of fifo varies depending on the number +* of LMACS +*/ +u32 fifo_len;#define MAX_LMAC_COUNT 8struct lmac *lmac_idmap[MAX_LMAC_COUNT ];struct work_struct cgx_cmd_work;
drivers/net/ethernet/marvell/octeontx2/af/rpm.c +3 -3
@@ -463,7 +463,7 @@ u32 rpm_get_lmac_fifo_len(void *rpmd, int lmac_id)u8 num_lmacs;u32 fifo_len; - fifo_len = rpm->mac_ops->fifo_len; + fifo_len = rpm->fifo_len; num_lmacs = rpm->mac_ops->get_nr_lmacs (rpm);switch (num_lmacs) {
@@ -516,9 +516,9 @@ u32 rpm2_get_lmac_fifo_len(void *rpmd, int lmac_id)*/ max_lmac = (rpm_read (rpm,0 ,CGX_CONST ) >>24 ) &0xFF ;if (max_lmac >4 ) - fifo_len = rpm->mac_ops->fifo_len /2 ; + fifo_len = rpm->fifo_len /2 ;else - fifo_len = rpm->mac_ops->fifo_len; + fifo_len = rpm->fifo_len;if (lmac_id <4 ) { num_lmacs =hweight8 (lmac_info &0xF );
drivers/net/ethernet/marvell/octeontx2/af/rvu_cgx.c +4 -5
@@ -895,13 +895,12 @@ int rvu_mbox_handler_cgx_features_get(struct rvu *rvu,u32 rvu_cgx_get_fifolen (struct rvu *rvu) { -struct mac_ops *mac_ops; -u32 fifo_len; +void *cgxd =rvu_first_cgx_pdata (rvu); - mac_ops =get_mac_ops (rvu_first_cgx_pdata (rvu)); - fifo_len = mac_ops ? mac_ops->fifo_len :0 ; +if (!cgxd) +return 0 ; -return fifo_len; +return cgx_get_fifo_len (cgxd); }u32 rvu_cgx_get_lmac_fifolen (struct rvu *rvu,int cgx,int lmac)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 410/676 octeontx2-pf: Reset MAC stats during probe
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sai Krishna <[email protected]>
[ Upstream commit 4c6ce450a8bb4bdf71959fd226414b079f0f0e02 ]
Reset CGX/RPM MAC HW statistics at the time of driver probe()
Stable-dep-of: 07cd1eb166a3 ("octeontx2-af: RPM: fix stale RSFEC counters")
--- .../net/ethernet/marvell/octeontx2/af/cgx.c | 27 +++++++++++++++++ .../net/ethernet/marvell/octeontx2/af/cgx.h | 1 + .../marvell/octeontx2/af/lmac_common.h | 1 + .../net/ethernet/marvell/octeontx2/af/mbox.h | 1 + .../net/ethernet/marvell/octeontx2/af/rpm.c | 17 +++++++++++ .../net/ethernet/marvell/octeontx2/af/rpm.h | 3 ++ .../ethernet/marvell/octeontx2/af/rvu_cgx.c | 29 +++++++++++++++++++ .../marvell/octeontx2/nic/otx2_common.h | 1 + .../ethernet/marvell/octeontx2/nic/otx2_pf.c | 20 +++++++++++++ 9 files changed, 100 insertions(+)
drivers/net/ethernet/marvell/octeontx2/af/cgx.c +27 -0
@@ -24,6 +24,8 @@#define DRV_NAME "Marvell-CGX/RPM"#define DRV_STRING "Marvell CGX/RPM Driver" +#define CGX_RX_STAT_GLOBAL_INDEX 9 +static LIST_HEAD (cgx_list);/* Convert firmware speed encoding to user format(Mbps) */
@@ -706,6 +708,30 @@ u64 cgx_features_get(void *cgxd)return ((struct cgx *)cgxd)->hw_features; } +int cgx_stats_reset (void *cgxd,int lmac_id) +{ +struct cgx *cgx = cgxd; +int stat_id; + +if (!is_lmac_valid (cgx, lmac_id)) +return -ENODEV ; + +for (stat_id =0 ; stat_id <CGX_RX_STATS_COUNT ; stat_id++) { +if (stat_id >=CGX_RX_STAT_GLOBAL_INDEX ) +/* pass lmac as 0 for CGX_CMR_RX_STAT9-12 */ +cgx_write (cgx,0 , + (CGXX_CMRX_RX_STAT0 + (stat_id *8 )),0 ); +else +cgx_write (cgx, lmac_id, + (CGXX_CMRX_RX_STAT0 + (stat_id *8 )),0 ); + } + +for (stat_id =0 ; stat_id <CGX_TX_STATS_COUNT ; stat_id++) +cgx_write (cgx, lmac_id,CGXX_CMRX_TX_STAT0 + (stat_id *8 ),0 ); + +return 0 ; +} +static int cgx_set_fec_stats_count (struct cgx_link_user_info *linfo) {if (!linfo->fec)
@@ -1795,6 +1821,7 @@ static struct mac_ops cgx_mac_ops = { .pfc_config = cgx_lmac_pfc_config, .mac_get_pfc_frm_cfg = cgx_lmac_get_pfc_frm_cfg, .mac_reset = cgx_lmac_reset, + .mac_stats_reset = cgx_stats_reset, };static int cgx_probe (struct pci_dev *pdev,const struct pci_device_id *id)
drivers/net/ethernet/marvell/octeontx2/af/cgx.h +1 -0
@@ -141,6 +141,7 @@ int cgx_lmac_evh_register(struct cgx_event_cb *cb, void *cgxd, int lmac_id);int cgx_lmac_evh_unregister (void *cgxd,int lmac_id);int cgx_get_tx_stats (void *cgxd,int lmac_id,int idx,u64 *tx_stat);int cgx_get_rx_stats (void *cgxd,int lmac_id,int idx,u64 *rx_stat); +int cgx_stats_reset (void *cgxd,int lmac_id);int cgx_lmac_rx_tx_enable (void *cgxd,int lmac_id,bool enable);int cgx_lmac_tx_enable (void *cgxd,int lmac_id,bool enable);int cgx_lmac_addr_set (u8 cgx_id,u8 lmac_id,u8 *mac_addr);
drivers/net/ethernet/marvell/octeontx2/af/lmac_common.h +1 -0
@@ -131,6 +131,7 @@ struct mac_ops {/* FEC stats */ int (*get_fec_stats)(void *cgxd,int lmac_id,struct cgx_fec_stats_rsp *rsp); +int (*mac_stats_reset)(void *cgxd,int lmac_id); };struct cgx {
drivers/net/ethernet/marvell/octeontx2/af/mbox.h +1 -0
@@ -174,6 +174,7 @@ M(CGX_FEC_STATS, 0x217, cgx_fec_stats, msg_req, cgx_fec_stats_rsp) \M (CGX_SET_LINK_MODE ,0x218 , cgx_set_link_mode, cgx_set_link_mode_req,\ cgx_set_link_mode_rsp) \ M(CGX_GET_PHY_FEC_STATS, 0x219, cgx_get_phy_fec_stats, msg_req, msg_rsp) \ +M(CGX_STATS_RST, 0x21A, cgx_stats_rst, msg_req, msg_rsp) \M (CGX_FEATURES_GET ,0x21B , cgx_features_get, msg_req, \ cgx_features_info_msg) \M (RPM_STATS ,0x21C , rpm_stats, msg_req, rpm_stats_rsp) \
drivers/net/ethernet/marvell/octeontx2/af/rpm.c +17 -0
@@ -38,6 +38,7 @@ static struct mac_ops rpm_mac_ops = { .pfc_config = rpm_lmac_pfc_config, .mac_get_pfc_frm_cfg = rpm_lmac_get_pfc_frm_cfg, .mac_reset = rpm_lmac_reset, + .mac_stats_reset = rpm_stats_reset, };static struct mac_ops rpm2_mac_ops = {
@@ -70,6 +71,7 @@ static struct mac_ops rpm2_mac_ops = { .pfc_config = rpm_lmac_pfc_config, .mac_get_pfc_frm_cfg = rpm_lmac_get_pfc_frm_cfg, .mac_reset = rpm_lmac_reset, + .mac_stats_reset = rpm_stats_reset, };bool is_dev_rpm2 (void *rpmd)
@@ -443,6 +445,21 @@ int rpm_get_tx_stats(void *rpmd, int lmac_id, int idx, u64 *tx_stat)return 0 ; } +int rpm_stats_reset (void *rpmd,int lmac_id) +{ +rpm_t *rpm = rpmd; +u64 cfg; + +if (!is_lmac_valid (rpm, lmac_id)) +return -ENODEV ; + + cfg =rpm_read (rpm,0 ,RPMX_MTI_STAT_STATN_CONTROL ); + cfg |=RPMX_CMD_CLEAR_TX |RPMX_CMD_CLEAR_RX |BIT_ULL (lmac_id); +rpm_write (rpm,0 ,RPMX_MTI_STAT_STATN_CONTROL , cfg); + +return 0 ; +} +u8 rpm_get_lmac_type (void *rpmd,int lmac_id) {rpm_t *rpm = rpmd;
drivers/net/ethernet/marvell/octeontx2/af/rpm.h +3 -0
@@ -85,6 +85,8 @@#define RPMX_MTI_STAT_STATN_CONTROL 0x10018#define RPMX_MTI_STAT_DATA_HI_CDC 0x10038#define RPMX_RSFEC_RX_CAPTURE BIT_ULL(27) +#define RPMX_CMD_CLEAR_RX BIT_ULL(30) +#define RPMX_CMD_CLEAR_TX BIT_ULL(31)#define RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_2 0x40050#define RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_3 0x40058#define RPMX_MTI_FCFECX_VL0_CCW_LO 0x38618
@@ -134,4 +136,5 @@ int rpm2_get_nr_lmacs(void *rpmd);bool is_dev_rpm2 (void *rpmd);int rpm_get_fec_stats (void *cgxd,int lmac_id,struct cgx_fec_stats_rsp *rsp);int rpm_lmac_reset (void *rpmd,int lmac_id,u8 pf_req_flr); +int rpm_stats_reset (void *rpmd,int lmac_id);#endif /* RPM_H */
drivers/net/ethernet/marvell/octeontx2/af/rvu_cgx.c +29 -0
@@ -604,6 +604,35 @@ int rvu_mbox_handler_rpm_stats(struct rvu *rvu, struct msg_req *req,return rvu_lmac_get_stats (rvu, req, (void *)rsp); } +int rvu_mbox_handler_cgx_stats_rst (struct rvu *rvu,struct msg_req *req, +struct msg_rsp *rsp) +{ +int pf =rvu_get_pf (req->hdr.pcifunc); +struct rvu_pfvf *parent_pf; +struct mac_ops *mac_ops; +u8 cgx_idx, lmac; +void *cgxd; + +if (!is_cgx_config_permitted (rvu, req->hdr.pcifunc)) +return LMAC_AF_ERR_PERM_DENIED ; + + parent_pf = &rvu->pf[pf]; +/* To ensure reset cgx stats won't affect VF stats, +* check if it used by only PF interface. +* If not, return +*/ +if (parent_pf->cgx_users >1 ) { +dev_info (rvu->dev,"CGX busy, could not reset statistics\n" ); +return 0 ; + } + +rvu_get_cgx_lmac_id (rvu->pf2cgxlmac_map[pf], &cgx_idx, &lmac); + cgxd =rvu_cgx_pdata (cgx_idx, rvu); + mac_ops =get_mac_ops (cgxd); + +return mac_ops->mac_stats_reset (cgxd, lmac); +} +int rvu_mbox_handler_cgx_fec_stats (struct rvu *rvu,struct msg_req *req,struct cgx_fec_stats_rsp *rsp)
drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h +1 -0
@@ -961,6 +961,7 @@ void otx2_get_mac_from_af(struct net_device *netdev);void otx2_config_irq_coalescing (struct otx2_nic *pfvf,int qidx);int otx2_config_pause_frm (struct otx2_nic *pfvf);void otx2_setup_segmentation (struct otx2_nic *pfvf); +int otx2_reset_mac_stats (struct otx2_nic *pfvf);/* RVU block related APIs */ int otx2_attach_npa_nix (struct otx2_nic *pfvf);
drivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c +20 -0
@@ -1150,6 +1150,23 @@ static int otx2_cgx_config_linkevents(struct otx2_nic *pf, bool enable)return err; } +int otx2_reset_mac_stats (struct otx2_nic *pfvf) +{ +struct msg_req *req; +int err; + +mutex_lock (&pfvf->mbox.lock); + req =otx2_mbox_alloc_msg_cgx_stats_rst (&pfvf->mbox); +if (!req) { +mutex_unlock (&pfvf->mbox.lock); +return -ENOMEM ; + } + + err =otx2_sync_mbox_msg (&pfvf->mbox); +mutex_unlock (&pfvf->mbox.lock); +return err; +} +static int otx2_cgx_config_loopback (struct otx2_nic *pf,bool enable) {struct msg_req *msg;
@@ -3038,6 +3055,9 @@ static int otx2_probe(struct pci_dev *pdev, const struct pci_device_id *id) netdev->min_mtu =OTX2_MIN_MTU ; netdev->max_mtu =otx2_get_max_mtu (pf); +/* reset CGX/RPM MAC stats */ +otx2_reset_mac_stats (pf); + err =register_netdev (netdev);if (err) {dev_err (dev,"Failed to register netdevice\n" );
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 411/676 octeontx2-af: RPM: fix stale RSFEC counters
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hariprasad Kelam <[email protected]>
[ Upstream commit 07cd1eb166a3fa7244afa74d48bd13c9df7c559d ]
The earlier patch sets the 'Stats control register' for RPM receive/transmit statistics instead of RSFEC statistics, causing the driver to return stale FEC counters.
--- drivers/net/ethernet/marvell/octeontx2/af/rpm.c | 13 +++++++++---- drivers/net/ethernet/marvell/octeontx2/af/rpm.h | 4 +++- 2 files changed, 12 insertions(+), 5 deletions(-)
drivers/net/ethernet/marvell/octeontx2/af/rpm.c +9 -4
@@ -699,6 +699,10 @@ int rpm_get_fec_stats(void *rpmd, int lmac_id, struct cgx_fec_stats_rsp *rsp)if (rpm->lmac_idmap[lmac_id]->link_info.fec ==OTX2_FEC_NONE )return 0 ; +/* latched registers FCFECX_CW_HI/RSFEC_STAT_FAST_DATA_HI_CDC are common +* for all counters. Acquire lock to ensure serialized reads +*/ +mutex_lock (&rpm->lock);if (rpm->lmac_idmap[lmac_id]->link_info.fec ==OTX2_FEC_BASER ) { val_lo =rpm_read (rpm, lmac_id,RPMX_MTI_FCFECX_VL0_CCW_LO ); val_hi =rpm_read (rpm, lmac_id,RPMX_MTI_FCFECX_CW_HI );
@@ -725,20 +729,21 @@ int rpm_get_fec_stats(void *rpmd, int lmac_id, struct cgx_fec_stats_rsp *rsp) } }else {/* enable RS-FEC capture */ - cfg =rpm_read (rpm,0 ,RPMX_MTI_STAT_STATN_CONTROL ); + cfg =rpm_read (rpm,0 ,RPMX_MTI_RSFEC_STAT_STATN_CONTROL ); cfg |=RPMX_RSFEC_RX_CAPTURE |BIT (lmac_id); -rpm_write (rpm,0 ,RPMX_MTI_STAT_STATN_CONTROL , cfg); +rpm_write (rpm,0 ,RPMX_MTI_RSFEC_STAT_STATN_CONTROL , cfg); val_lo =rpm_read (rpm,0 ,RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_2 ); - val_hi =rpm_read (rpm,0 ,RPMX_MTI_STAT_DATA_HI_CDC ); + val_hi =rpm_read (rpm,0 ,RPMX_MTI_RSFEC_STAT_FAST_DATA_HI_CDC ); rsp->fec_corr_blks = (val_hi <<32 | val_lo); val_lo =rpm_read (rpm,0 ,RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_3 ); - val_hi =rpm_read (rpm,0 ,RPMX_MTI_STAT_DATA_HI_CDC ); + val_hi =rpm_read (rpm,0 ,RPMX_MTI_RSFEC_STAT_FAST_DATA_HI_CDC ); rsp->fec_uncorr_blks = (val_hi <<32 | val_lo); } +mutex_unlock (&rpm->lock);return 0 ; }
drivers/net/ethernet/marvell/octeontx2/af/rpm.h +3 -1
@@ -84,9 +84,11 @@/* FEC stats */ #define RPMX_MTI_STAT_STATN_CONTROL 0x10018#define RPMX_MTI_STAT_DATA_HI_CDC 0x10038 -#define RPMX_RSFEC_RX_CAPTURE BIT_ULL(27) +#define RPMX_RSFEC_RX_CAPTURE BIT_ULL(28)#define RPMX_CMD_CLEAR_RX BIT_ULL(30)#define RPMX_CMD_CLEAR_TX BIT_ULL(31) +#define RPMX_MTI_RSFEC_STAT_STATN_CONTROL 0x40018 +#define RPMX_MTI_RSFEC_STAT_FAST_DATA_HI_CDC 0x40000#define RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_2 0x40050#define RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_3 0x40058#define RPMX_MTI_FCFECX_VL0_CCW_LO 0x38618
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 412/676 octeontx2-af: RPM: fix stale FCFEC counters
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hariprasad Kelam <[email protected]>
[ Upstream commit 6fc2164108462b913a1290fa2c44054c70b060ef ]
The corrected words register(FCFECX_VL0_CCW_LO)/Uncorrected words register (FCFECX_VL0_NCCW_LO) of FCFEC counter has different LMAC offset which needs to be accessed differently.
--- .../net/ethernet/marvell/octeontx2/af/rpm.c | 24 +++++++++---------- .../net/ethernet/marvell/octeontx2/af/rpm.h | 10 ++++---- 2 files changed, 17 insertions(+), 17 deletions(-)
drivers/net/ethernet/marvell/octeontx2/af/rpm.c +12 -12
@@ -704,27 +704,27 @@ int rpm_get_fec_stats(void *rpmd, int lmac_id, struct cgx_fec_stats_rsp *rsp)*/ mutex_lock (&rpm->lock);if (rpm->lmac_idmap[lmac_id]->link_info.fec ==OTX2_FEC_BASER ) { - val_lo =rpm_read (rpm, lmac_id,RPMX_MTI_FCFECX_VL0_CCW_LO ); - val_hi =rpm_read (rpm, lmac_id,RPMX_MTI_FCFECX_CW_HI ); + val_lo =rpm_read (rpm,0 ,RPMX_MTI_FCFECX_VL0_CCW_LO (lmac_id)); + val_hi =rpm_read (rpm,0 ,RPMX_MTI_FCFECX_CW_HI (lmac_id)); rsp->fec_corr_blks = (val_hi <<16 | val_lo); - val_lo =rpm_read (rpm, lmac_id,RPMX_MTI_FCFECX_VL0_NCCW_LO ); - val_hi =rpm_read (rpm, lmac_id,RPMX_MTI_FCFECX_CW_HI ); + val_lo =rpm_read (rpm,0 ,RPMX_MTI_FCFECX_VL0_NCCW_LO (lmac_id)); + val_hi =rpm_read (rpm,0 ,RPMX_MTI_FCFECX_CW_HI (lmac_id)); rsp->fec_uncorr_blks = (val_hi <<16 | val_lo);/* 50G uses 2 Physical serdes lines */ if (rpm->lmac_idmap[lmac_id]->link_info.lmac_type_id ==LMAC_MODE_50G_R ) { - val_lo =rpm_read (rpm, lmac_id, -RPMX_MTI_FCFECX_VL1_CCW_LO ); - val_hi =rpm_read (rpm, lmac_id, -RPMX_MTI_FCFECX_CW_HI ); + val_lo =rpm_read (rpm,0 , +RPMX_MTI_FCFECX_VL1_CCW_LO (lmac_id)); + val_hi =rpm_read (rpm,0 , +RPMX_MTI_FCFECX_CW_HI (lmac_id)); rsp->fec_corr_blks += (val_hi <<16 | val_lo); - val_lo =rpm_read (rpm, lmac_id, -RPMX_MTI_FCFECX_VL1_NCCW_LO ); - val_hi =rpm_read (rpm, lmac_id, -RPMX_MTI_FCFECX_CW_HI ); + val_lo =rpm_read (rpm,0 , +RPMX_MTI_FCFECX_VL1_NCCW_LO (lmac_id)); + val_hi =rpm_read (rpm,0 , +RPMX_MTI_FCFECX_CW_HI (lmac_id)); rsp->fec_uncorr_blks += (val_hi <<16 | val_lo); } }else {
drivers/net/ethernet/marvell/octeontx2/af/rpm.h +5 -5
@@ -91,11 +91,11 @@#define RPMX_MTI_RSFEC_STAT_FAST_DATA_HI_CDC 0x40000#define RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_2 0x40050#define RPMX_MTI_RSFEC_STAT_COUNTER_CAPTURE_3 0x40058 -#define RPMX_MTI_FCFECX_VL0_CCW_LO 0x38618 -#define RPMX_MTI_FCFECX_VL0_NCCW_LO 0x38620 -#define RPMX_MTI_FCFECX_VL1_CCW_LO 0x38628 -#define RPMX_MTI_FCFECX_VL1_NCCW_LO 0x38630 -#define RPMX_MTI_FCFECX_CW_HI 0x38638 +#define RPMX_MTI_FCFECX_VL0_CCW_LO (a) (0x38618 + ((a) * 0x40)) +#define RPMX_MTI_FCFECX_VL0_NCCW_LO (a) (0x38620 + ((a) * 0x40)) +#define RPMX_MTI_FCFECX_VL1_CCW_LO (a) (0x38628 + ((a) * 0x40)) +#define RPMX_MTI_FCFECX_VL1_NCCW_LO (a) (0x38630 + ((a) * 0x40)) +#define RPMX_MTI_FCFECX_CW_HI (a) (0x38638 + ((a) * 0x40))/* CN10KB CSR Declaration */ #define RPM2_CMRX_SW_INT 0x1b0
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 413/676 octeontx2-af: Quiesce traffic before NIX block reset
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hariprasad Kelam <[email protected]>
[ Upstream commit 762ca6eed026346d9d41ed5ac633083c4f1e5071 ]
During initialization, the AF driver resets all blocks. The RPM (MAC) block and NIX block operate on a credit-based model. When the NIX block resets during active traffic flow, it doesn't release credits to the RPM block. This causes the RPM FIFO to overflow, leading to receive traffic struck.
To address this issue, the patch introduces the following changes:
1. Stop receiving traffic at the MAC level during AF driver initialization.
2. Perform an X2P reset (prevents RXFIFO of all LMACS from pushing data)
3. Reset the NIX block.
4. Clear the X2P reset and re-enable receiving traffic.
--- .../net/ethernet/marvell/octeontx2/af/cgx.c | 61 +++++++++++++++++++ .../net/ethernet/marvell/octeontx2/af/cgx.h | 4 ++ .../marvell/octeontx2/af/lmac_common.h | 2 + .../net/ethernet/marvell/octeontx2/af/rpm.c | 42 +++++++++++++ .../net/ethernet/marvell/octeontx2/af/rpm.h | 4 ++ .../net/ethernet/marvell/octeontx2/af/rvu.c | 1 + .../net/ethernet/marvell/octeontx2/af/rvu.h | 1 + .../ethernet/marvell/octeontx2/af/rvu_cgx.c | 36 +++++++++-- 8 files changed, 145 insertions(+), 6 deletions(-)
drivers/net/ethernet/marvell/octeontx2/af/cgx.c +61 -0
@@ -214,6 +214,24 @@ u8 cgx_lmac_get_p2x(int cgx_id, int lmac_id)return (cfg &CMR_P2X_SEL_MASK ) >>CMR_P2X_SEL_SHIFT ; } +static u8 cgx_get_nix_resetbit (struct cgx *cgx) +{ +int first_lmac; +u8 p2x; + +/* non 98XX silicons supports only NIX0 block */ +if (cgx->pdev->subsystem_device !=PCI_SUBSYS_DEVID_98XX ) +return CGX_NIX0_RESET ; + + first_lmac =find_first_bit (&cgx->lmac_bmap, cgx->max_lmac_per_mac); + p2x =cgx_lmac_get_p2x (cgx->cgx_id, first_lmac); + +if (p2x ==CMR_P2X_SEL_NIX1 ) +return CGX_NIX1_RESET ; +else +return CGX_NIX0_RESET ; +} +/* Ensure the required lock for event queue(where asynchronous events are * posted) is acquired before calling this API. Else an asynchronous event(with * latest link status) can reach the destination before this function returns
@@ -1726,6 +1744,8 @@ static int cgx_lmac_init(struct cgx *cgx) lmac->lmac_type = cgx->mac_ops->get_lmac_type (cgx, lmac->lmac_id); } +/* Start X2P reset on given MAC block */ + cgx->mac_ops->mac_x2p_reset (cgx, true);return cgx_lmac_verify_fwi_version (cgx); err_bitmap_free:
@@ -1791,6 +1811,45 @@ static u8 cgx_get_rxid_mapoffset(struct cgx *cgx)return 0x60 ; } +static void cgx_x2p_reset (void *cgxd,bool enable) +{ +struct cgx *cgx = cgxd; +int lmac_id; +u64 cfg; + +if (enable) { +for_each_set_bit (lmac_id, &cgx->lmac_bmap, cgx->max_lmac_per_mac) + cgx->mac_ops->mac_enadis_rx (cgx, lmac_id, false); + +usleep_range (1000 ,2000 ); + + cfg =cgx_read (cgx,0 ,CGXX_CMR_GLOBAL_CONFIG ); + cfg |=cgx_get_nix_resetbit (cgx) |CGX_NSCI_DROP ; +cgx_write (cgx,0 ,CGXX_CMR_GLOBAL_CONFIG , cfg); + }else { + cfg =cgx_read (cgx,0 ,CGXX_CMR_GLOBAL_CONFIG ); + cfg &= ~(cgx_get_nix_resetbit (cgx) |CGX_NSCI_DROP ); +cgx_write (cgx,0 ,CGXX_CMR_GLOBAL_CONFIG , cfg); + } +} + +static int cgx_enadis_rx (void *cgxd,int lmac_id,bool enable) +{ +struct cgx *cgx = cgxd; +u64 cfg; + +if (!is_lmac_valid (cgx, lmac_id)) +return -ENODEV ; + + cfg =cgx_read (cgx, lmac_id,CGXX_CMRX_CFG ); +if (enable) + cfg |=DATA_PKT_RX_EN ; +else + cfg &= ~DATA_PKT_RX_EN ; +cgx_write (cgx, lmac_id,CGXX_CMRX_CFG , cfg); +return 0 ; +} +static struct mac_ops cgx_mac_ops = { .name ="cgx" , .csr_offset =0 ,
@@ -1822,6 +1881,8 @@ static struct mac_ops cgx_mac_ops = { .mac_get_pfc_frm_cfg = cgx_lmac_get_pfc_frm_cfg, .mac_reset = cgx_lmac_reset, .mac_stats_reset = cgx_stats_reset, + .mac_x2p_reset = cgx_x2p_reset, + .mac_enadis_rx = cgx_enadis_rx, };static int cgx_probe (struct pci_dev *pdev,const struct pci_device_id *id)
drivers/net/ethernet/marvell/octeontx2/af/cgx.h +4 -0
@@ -32,6 +32,10 @@#define CGX_LMAC_TYPE_MASK 0xF#define CGXX_CMRX_INT 0x040#define FW_CGX_INT BIT_ULL(1) +#define CGXX_CMR_GLOBAL_CONFIG 0x08 +#define CGX_NIX0_RESET BIT_ULL(2) +#define CGX_NIX1_RESET BIT_ULL(3) +#define CGX_NSCI_DROP BIT_ULL(9)#define CGXX_CMRX_INT_ENA_W1S 0x058#define CGXX_CMRX_RX_ID_MAP 0x060#define CGXX_CMRX_RX_STAT0 0x070
drivers/net/ethernet/marvell/octeontx2/af/lmac_common.h +2 -0
@@ -132,6 +132,8 @@ struct mac_ops {int (*get_fec_stats)(void *cgxd,int lmac_id,struct cgx_fec_stats_rsp *rsp);int (*mac_stats_reset)(void *cgxd,int lmac_id); +void (*mac_x2p_reset)(void *cgxd,bool enable); +int (*mac_enadis_rx)(void *cgxd,int lmac_id,bool enable); };struct cgx {
drivers/net/ethernet/marvell/octeontx2/af/rpm.c +42 -0
57 lines not on this page · raw message
drivers/net/ethernet/marvell/octeontx2/af/rpm.h +4 -0
@@ -17,6 +17,8 @@/* Registers */ #define RPMX_CMRX_CFG 0x00 +#define RPMX_CMR_GLOBAL_CFG 0x08 +#define RPM_NIX0_RESET BIT_ULL(3)#define RPMX_RX_TS_PREPEND BIT_ULL(22)#define RPMX_TX_PTP_1S_SUPPORT BIT_ULL(17)#define RPMX_CMRX_RX_ID_MAP 0x80
@@ -139,4 +141,6 @@ bool is_dev_rpm2(void *rpmd);int rpm_get_fec_stats (void *cgxd,int lmac_id,struct cgx_fec_stats_rsp *rsp);int rpm_lmac_reset (void *rpmd,int lmac_id,u8 pf_req_flr);int rpm_stats_reset (void *rpmd,int lmac_id); +void rpm_x2p_reset (void *rpmd,bool enable); +int rpm_enadis_rx (void *rpmd,int lmac_id,bool enable);#endif /* RPM_H */
drivers/net/ethernet/marvell/octeontx2/af/rvu.c +1 -0
@@ -1157,6 +1157,7 @@ static int rvu_setup_hw_resources(struct rvu *rvu) }rvu_program_channels (rvu); +cgx_start_linkup (rvu); err =rvu_mcs_init (rvu);if (err) {
drivers/net/ethernet/marvell/octeontx2/af/rvu.h +1 -0
@@ -912,6 +912,7 @@ int rvu_cgx_prio_flow_ctrl_cfg(struct rvu *rvu, u16 pcifunc, u8 tx_pause, u8 rx_int rvu_cgx_cfg_pause_frm (struct rvu *rvu,u16 pcifunc,u8 tx_pause,u8 rx_pause);void rvu_mac_reset (struct rvu *rvu,u16 pcifunc);u32 rvu_cgx_get_lmac_fifolen (struct rvu *rvu,int cgx,int lmac); +void cgx_start_linkup (struct rvu *rvu);int npc_get_nixlf_mcam_index (struct npc_mcam *mcam,u16 pcifunc,int nixlf,int type); bool is_mcam_entry_enabled(struct rvu *rvu, struct npc_mcam *mcam, int blkaddr,
drivers/net/ethernet/marvell/octeontx2/af/rvu_cgx.c +30 -6
@@ -349,6 +349,7 @@ static void rvu_cgx_wq_destroy(struct rvu *rvu)int rvu_cgx_init (struct rvu *rvu) { +struct mac_ops *mac_ops;int cgx, err;void *cgxd;
@@ -375,6 +376,15 @@ int rvu_cgx_init(struct rvu *rvu)if (err)return err; +/* Clear X2P reset on all MAC blocks */ +for (cgx =0 ; cgx < rvu->cgx_cnt_max; cgx++) { + cgxd =rvu_cgx_pdata (cgx, rvu); +if (!cgxd) +continue ; + mac_ops =get_mac_ops (cgxd); + mac_ops->mac_x2p_reset (cgxd, false); + } +/* Register for CGX events */ err =cgx_lmac_event_handler_init (rvu);if (err)
@@ -382,10 +392,26 @@ int rvu_cgx_init(struct rvu *rvu)mutex_init (&rvu->cgx_cfg_lock); -/* Ensure event handler registration is completed, before -* we turn on the links -*/ -mb (); +return 0 ; +} + +void cgx_start_linkup (struct rvu *rvu) +{ +unsigned long lmac_bmap; +struct mac_ops *mac_ops; +int cgx, lmac, err; +void *cgxd; + +/* Enable receive on all LMACS */ +for (cgx =0 ; cgx <= rvu->cgx_cnt_max; cgx++) { + cgxd =rvu_cgx_pdata (cgx, rvu); +if (!cgxd) +continue ; + mac_ops =get_mac_ops (cgxd); + lmac_bmap =cgx_get_lmac_bmap (cgxd); +for_each_set_bit (lmac, &lmac_bmap, rvu->hw->lmac_per_cgx) + mac_ops->mac_enadis_rx (cgxd, lmac, true); + }/* Do link up for all CGX ports */ for (cgx =0 ; cgx <= rvu->cgx_cnt_max; cgx++) {
@@ -398,8 +424,6 @@ int rvu_cgx_init(struct rvu *rvu)"Link up process failed to start on cgx %d\n" , cgx); } - -return 0 ; }int rvu_cgx_exit (struct rvu *rvu)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 414/676 spi: atmel-quadspi: Fix register name in verbose logging function
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Csókás, Bence <[email protected]>
[ Upstream commit 2ac40e6d0ccdd93031f8b1af61b0fe5cdd704923 ]
atmel_qspi_reg_name() is used for pretty-printing register offsets for verbose logging of register accesses. However, due to a typo (likely a copy-paste error), QSPI_RD's offset prints as "MR", the name of the previous register. Fix this typo.
--- drivers/spi/atmel-quadspi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/spi/atmel-quadspi.c +1 -1
@@ -183,7 +183,7 @@ static const char *atmel_qspi_reg_name(u32 offset, char *tmp, size_t sz)case QSPI_MR :return "MR" ;case QSPI_RD : -return "MR" ; +return "RD" ;case QSPI_TD :return "TD" ;case QSPI_SR :
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 415/676 net: hsr: fix hsr_init_sk() vs network/transport headers.
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Dumazet <[email protected]>
[ Upstream commit 9cfb5e7f0ded2bfaabc270ceb5f91d13f0e805b9 ]
Following sequence in hsr_init_sk() is invalid :
skb_reset_mac_header(skb);
skb_reset_mac_len(skb);
skb_reset_network_header(skb);
skb_reset_transport_header(skb);It is invalid because skb_reset_mac_len() needs the correct network header, which should be after the mac header.
This patch moves the skb_reset_network_header() and skb_reset_transport_header() before
the call to dev_hard_header().
As a result skb->mac_len is no longer set to a value close to 65535.
--- net/hsr/hsr_device.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
net/hsr/hsr_device.c +2 -2
@@ -253,6 +253,8 @@ static struct sk_buff *hsr_init_skb(struct hsr_port *master) skb->dev = master->dev; skb->priority =TC_PRIO_CONTROL ; +skb_reset_network_header (skb); +skb_reset_transport_header (skb);if (dev_hard_header (skb, skb->dev,ETH_P_PRP , hsr->sup_multicast_addr, skb->dev->dev_addr, skb->len) <=0 )
@@ -260,8 +262,6 @@ static struct sk_buff *hsr_init_skb(struct hsr_port *master)skb_reset_mac_header (skb);skb_reset_mac_len (skb); -skb_reset_network_header (skb); -skb_reset_transport_header (skb);return skb; out:
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 416/676 bnxt_en: Reserve rings after PCIe AER recovery if NIC interface is down
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Saravanan Vajravel <[email protected]>
[ Upstream commit 5311598f7f3293683cdc761df71ae3469327332c ]
After successful PCIe AER recovery, FW will reset all resource reservations. If it is IF_UP, the driver will call bnxt_open() and all resources will be reserved again. It it is IF_DOWN, we should call bnxt_reserve_rings() so that we can reserve resources including RoCE resources to allow RoCE to resume after AER. Without this patch, RoCE fails to resume in this IF_DOWN scenario.
Later, if it becomes IF_UP, bnxt_open() will see that resources have been reserved and will not reserve again.
--- drivers/net/ethernet/broadcom/bnxt/bnxt.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-)
drivers/net/ethernet/broadcom/bnxt/bnxt.c +6 -2
@@ -14102,8 +14102,12 @@ static void bnxt_io_resume(struct pci_dev *pdev)rtnl_lock (); err =bnxt_hwrm_func_qcaps (bp); -if (!err &&netif_running (netdev)) - err =bnxt_open (netdev); +if (!err) { +if (netif_running (netdev)) + err =bnxt_open (netdev); +else + err =bnxt_reserve_rings (bp, true); + }bnxt_ulp_start (bp, err);if (!err) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 417/676 bnxt_en: Refactor bnxt_ptp_init()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michael Chan <[email protected]>
[ Upstream commit 1e9614cd956268e10a669c0593e7e54d03d0c087 ]
Instead of passing the 2nd parameter phc_cfg to bnxt_ptp_init(). Store it in bp->ptp_cfg so that the caller doesn't need to know what the value should be.
In the next patch, we'll need to call bnxt_ptp_init() in bnxt_resume() and this will make it easier.
Stable-dep-of: 3661c05c54e8 ("bnxt_en: Unregister PTP during PCI shutdown and suspend")
--- drivers/net/ethernet/broadcom/bnxt/bnxt.c | 6 +++--- drivers/net/ethernet/broadcom/bnxt/bnxt_ptp.c | 4 ++-- drivers/net/ethernet/broadcom/bnxt/bnxt_ptp.h | 3 ++- 3 files changed, 7 insertions(+), 6 deletions(-)
drivers/net/ethernet/broadcom/bnxt/bnxt.c +3 -3
@@ -7597,7 +7597,6 @@ static int __bnxt_hwrm_ptp_qcfg(struct bnxt *bp)struct hwrm_port_mac_ptp_qcfg_output *resp;struct hwrm_port_mac_ptp_qcfg_input *req;struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; -bool phc_cfg;u8 flags;int rc;
@@ -7640,8 +7639,9 @@ static int __bnxt_hwrm_ptp_qcfg(struct bnxt *bp) rc = -ENODEV ; goto exit; } - phc_cfg = (flags &PORT_MAC_PTP_QCFG_RESP_FLAGS_RTC_CONFIGURED ) !=0 ; - rc =bnxt_ptp_init (bp, phc_cfg); + ptp->rtc_configured = + (flags &PORT_MAC_PTP_QCFG_RESP_FLAGS_RTC_CONFIGURED ) !=0 ; + rc =bnxt_ptp_init (bp);if (rc)netdev_warn (bp->dev,"PTP initialization failed.\n" ); exit:
drivers/net/ethernet/broadcom/bnxt/bnxt_ptp.c +2 -2
@@ -922,7 +922,7 @@ static void bnxt_ptp_free(struct bnxt *bp) } } -int bnxt_ptp_init (struct bnxt *bp,bool phc_cfg) +int bnxt_ptp_init (struct bnxt *bp) {struct bnxt_ptp_cfg *ptp = bp->ptp_cfg;int rc;
@@ -944,7 +944,7 @@ int bnxt_ptp_init(struct bnxt *bp, bool phc_cfg)if (BNXT_PTP_USE_RTC (bp)) {bnxt_ptp_timecounter_init (bp, false); - rc =bnxt_ptp_init_rtc (bp, phc_cfg); + rc =bnxt_ptp_init_rtc (bp, ptp->rtc_configured);if (rc) goto out; }else {
drivers/net/ethernet/broadcom/bnxt/bnxt_ptp.h +2 -1
@@ -115,6 +115,7 @@ struct bnxt_ptp_cfg { BNXT_PTP_MSG_PDELAY_REQ | \ BNXT_PTP_MSG_PDELAY_RESP) u8 tx_tstamp_en:1; + u8 rtc_configured:1;int rx_filter;u32 tstamp_filters;
@@ -145,6 +146,6 @@ int bnxt_get_tx_ts_p5(struct bnxt *bp, struct sk_buff *skb);int bnxt_get_rx_ts_p5 (struct bnxt *bp,u64 *ts,u32 pkt_ts);void bnxt_ptp_rtc_timecounter_init (struct bnxt_ptp_cfg *ptp,u64 ns);int bnxt_ptp_init_rtc (struct bnxt *bp,bool phc_cfg); -int bnxt_ptp_init (struct bnxt *bp,bool phc_cfg); +int bnxt_ptp_init (struct bnxt *bp);void bnxt_ptp_clear (struct bnxt *bp);#endif
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 418/676 bnxt_en: Unregister PTP during PCI shutdown and suspend
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michael Chan <[email protected]>
[ Upstream commit 3661c05c54e8db7064aa96a0774654740974dffc ]
If we go through the PCI shutdown or suspend path, we shutdown the NIC but PTP remains registered. If the kernel continues to run for a little bit, the periodic PTP .do_aux_work() function may be called and it will read the PHC from the BAR register. Since the device has already been disabled, it will cause a PCIe completion timeout. Fix it by calling bnxt_ptp_clear() in the PCI shutdown/suspend handlers. bnxt_ptp_clear() will unregister from PTP and .do_aux_work() will be canceled.
In bnxt_resume(), we need to re-initialize PTP.
--- drivers/net/ethernet/broadcom/bnxt/bnxt.c | 6 ++++++ 1 file changed, 6 insertions(+)
drivers/net/ethernet/broadcom/bnxt/bnxt.c +6 -0
@@ -13857,6 +13857,7 @@ static void bnxt_shutdown(struct pci_dev *pdev)if (netif_running (dev))dev_close (dev); +bnxt_ptp_clear (bp);bnxt_clear_int_mode (bp);pci_disable_device (pdev);
@@ -13883,6 +13884,7 @@ static int bnxt_suspend(struct device *device) rc =bnxt_close (dev); }bnxt_hwrm_func_drv_unrgtr (bp); +bnxt_ptp_clear (bp);pci_disable_device (bp->pdev);bnxt_free_ctx_mem (bp);kfree (bp->ctx);
@@ -13926,6 +13928,10 @@ static int bnxt_resume(struct device *device) goto resume_exit; } +if (bnxt_ptp_init (bp)) { +kfree (bp->ptp_cfg); + bp->ptp_cfg =NULL ; + }bnxt_get_wol_settings (bp);if (netif_running (dev)) { rc =bnxt_open (dev);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 419/676 Bluetooth: MGMT: Fix slab-use-after-free Read in set_powered_sync
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Luiz Augusto von Dentz <[email protected]>
[ Upstream commit 0b882940665ca2849386ee459d4331aa2f8c4e7d ]
This fixes the following crash:
==================================================================
BUG: KASAN: slab-use-after-free in set_powered_sync+0x3a/0xc0 net/bluetooth/mgmt.c:1353 Read of size 8 at addr ffff888029b4dd18 by task kworker/u9:0/54 CPU: 1 UID: 0 PID: 54 Comm: kworker/u9:0 Not tainted 6.11.0-rc6-syzkaller-01155-gf723224742fc #0 Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 08/06/2024 Workqueue: hci0 hci_cmd_sync_work Call Trace: <TASK> __dump_stack lib/dump_stack.c:93 [inline] dump_stack_lvl+0x241/0x360 lib/dump_stack.c:119 print_address_description mm/kasan/report.c:377 [inline] print_report+0x169/0x550 mm/kasan/report.c:488 q kasan_report+0x143/0x180 mm/kasan/report.c:601 set_powered_sync+0x3a/0xc0 net/bluetooth/mgmt.c:1353 hci_cmd_sync_work+0x22b/0x400 net/bluetooth/hci_sync.c:328 process_one_work kernel/workqueue.c:3231 [inline] process_scheduled_works+0xa2c/0x1830 kernel/workqueue.c:3312 worker_thread+0x86d/0xd10 kernel/workqueue.c:3389 kthread+0x2f0/0x390 kernel/kthread.c:389 ret_from_fork+0x4b/0x80 arch/x86/kernel/process.c:147 ret_from_fork_asm+0x1a/0x30 arch/x86/entry/entry_64.S:244 </TASK> Allocated by task 5247: kasan_save_stack mm/kasan/common.c:47 [inline] kasan_save_track+0x3f/0x80 mm/kasan/common.c:68 poison_kmalloc_redzone mm/kasan/common.c:370 [inline] __kasan_kmalloc+0x98/0xb0 mm/kasan/common.c:387 kasan_kmalloc include/linux/kasan.h:211 [inline] __kmalloc_cache_noprof+0x19c/0x2c0 mm/slub.c:4193 kmalloc_noprof include/linux/slab.h:681 [inline] kzalloc_noprof include/linux/slab.h:807 [inline] mgmt_pending_new+0x65/0x250 net/bluetooth/mgmt_util.c:269 mgmt_pending_add+0x36/0x120 net/bluetooth/mgmt_util.c:296 set_powered+0x3cd/0x5e0 net/bluetooth/mgmt.c:1394 hci_mgmt_cmd+0xc47/0x11d0 net/bluetooth/hci_sock.c:1712 hci_sock_sendmsg+0x7b8/0x11c0 net/bluetooth/hci_sock.c:1832 sock_sendmsg_nosec net/socket.c:730 [inline] __sock_sendmsg+0x221/0x270 net/socket.c:745 sock_write_iter+0x2dd/0x400 net/socket.c:1160 new_sync_write fs/read_write.c:497 [inline] vfs_write+0xa72/0xc90 fs/read_write.c:590 ksys_write+0x1a0/0x2c0 fs/read_write.c:643 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0xf3/0x230 arch/x86/entry/common.c:83 entry_SYSCALL_64_after_hwframe+0x77/0x7f Freed by task 5246: kasan_save_stack mm/kasan/common.c:47 [inline] kasan_save_track+0x3f/0x80 mm/kasan/common.c:68 kasan_save_free_info+0x40/0x50 mm/kasan/generic.c:579 poison_slab_object+0xe0/0x150 mm/kasan/common.c:240 __kasan_slab_free+0x37/0x60 mm/kasan/common.c:256 kasan_slab_free include/linux/kasan.h:184 [inline] slab_free_hook mm/slub.c:2256 [inline] slab_free mm/slub.c:4477 [inline] kfree+0x149/0x360 mm/slub.c:4598 settings_rsp+0x2bc/0x390 net/bluetooth/mgmt.c:1443 mgmt_pending_foreach+0xd1/0x130 net/bluetooth/mgmt_util.c:259 __mgmt_power_off+0x112/0x420 net/bluetooth/mgmt.c:9455 hci_dev_close_sync+0x665/0x11a0 net/bluetooth/hci_sync.c:5191 hci_dev_do_close net/bluetooth/hci_core.c:483 [inline] hci_dev_close+0x112/0x210 net/bluetooth/hci_core.c:508 sock_do_ioctl+0x158/0x460 net/socket.c:1222 sock_ioctl+0x629/0x8e0 net/socket.c:1341 vfs_ioctl fs/ioctl.c:51 [inline] __do_sys_ioctl fs/ioctl.c:907 [inline] __se_sys_ioctl+0xfc/0x170 fs/ioctl.c:893 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0xf3/0x230 arch/x86/entry/common.c:83gv entry_SYSCALL_64_after_hwframe+0x77/0x7f
--- net/bluetooth/mgmt.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-)
net/bluetooth/mgmt.c +9 -2
@@ -1318,7 +1318,8 @@ static void mgmt_set_powered_complete(struct hci_dev *hdev, void *data, int err)struct mgmt_mode *cp;/* Make sure cmd still outstanding. */ -if (cmd !=pending_find (MGMT_OP_SET_POWERED , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_SET_POWERED , hdev))return ; cp = cmd->param;
@@ -1351,7 +1352,13 @@ static void mgmt_set_powered_complete(struct hci_dev *hdev, void *data, int err)static int set_powered_sync (struct hci_dev *hdev,void *data) {struct mgmt_pending_cmd *cmd = data; -struct mgmt_mode *cp = cmd->param; +struct mgmt_mode *cp; + +/* Make sure cmd still outstanding. */ +if (cmd !=pending_find (MGMT_OP_SET_POWERED , hdev)) +return -ECANCELED ; + + cp = cmd->param;BT_DBG ("%s" , hdev->name);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 420/676 Bluetooth: MGMT: Fix possible deadlocks
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Luiz Augusto von Dentz <[email protected]>
[ Upstream commit a66dfaf18fd61bb75ef8cee83db46b2aadf153d0 ]
This fixes possible deadlocks like the following caused by hci_cmd_sync_dequeue causing the destroy function to run:
INFO: task kworker/u19:0:143 blocked for more than 120 seconds.
Tainted: G W O 6.8.0-2024-03-19-intel-next-iLS-24ww14 #1
"echo 0 > /proc/sys/kernel/hung_task_timeout_secs" disables this message.
task:kworker/u19:0 state:D stack:0 pid:143 tgid:143 ppid:2 flags:0x00004000
Workqueue: hci0 hci_cmd_sync_work [bluetooth]
Call Trace:
<TASK>
__schedule+0x374/0xaf0
schedule+0x3c/0xf0
schedule_preempt_disabled+0x1c/0x30
__mutex_lock.constprop.0+0x3ef/0x7a0
__mutex_lock_slowpath+0x13/0x20
mutex_lock+0x3c/0x50
mgmt_set_connectable_complete+0xa4/0x150 [bluetooth]
? kfree+0x211/0x2a0
hci_cmd_sync_dequeue+0xae/0x130 [bluetooth]
? __pfx_cmd_complete_rsp+0x10/0x10 [bluetooth]
cmd_complete_rsp+0x26/0x80 [bluetooth]
mgmt_pending_foreach+0x4d/0x70 [bluetooth]
__mgmt_power_off+0x8d/0x180 [bluetooth]
? _raw_spin_unlock_irq+0x23/0x40
hci_dev_close_sync+0x445/0x5b0 [bluetooth]
hci_set_powered_sync+0x149/0x250 [bluetooth]
set_powered_sync+0x24/0x60 [bluetooth]
hci_cmd_sync_work+0x90/0x150 [bluetooth]
process_one_work+0x13e/0x300
worker_thread+0x2f7/0x420
? __pfx_worker_thread+0x10/0x10
kthread+0x107/0x140
? __pfx_kthread+0x10/0x10
ret_from_fork+0x3d/0x60
? __pfx_kthread+0x10/0x10
ret_from_fork_asm+0x1b/0x30
</TASK>--- net/bluetooth/mgmt.c | 27 ++++++++++++++++++--------- 1 file changed, 18 insertions(+), 9 deletions(-)
net/bluetooth/mgmt.c +18 -9
@@ -1510,7 +1510,8 @@ static void mgmt_set_discoverable_complete(struct hci_dev *hdev, void *data,bt_dev_dbg (hdev,"err %d" , err);/* Make sure cmd still outstanding. */ -if (cmd !=pending_find (MGMT_OP_SET_DISCOVERABLE , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_SET_DISCOVERABLE , hdev))return ;hci_dev_lock (hdev);
@@ -1684,7 +1685,8 @@ static void mgmt_set_connectable_complete(struct hci_dev *hdev, void *data,bt_dev_dbg (hdev,"err %d" , err);/* Make sure cmd still outstanding. */ -if (cmd !=pending_find (MGMT_OP_SET_CONNECTABLE , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_SET_CONNECTABLE , hdev))return ;hci_dev_lock (hdev);
@@ -1917,7 +1919,7 @@ static void set_ssp_complete(struct hci_dev *hdev, void *data, int err)bool changed;/* Make sure cmd still outstanding. */ -if (cmd !=pending_find (MGMT_OP_SET_SSP , hdev)) +if (err == -ECANCELED || cmd !=pending_find (MGMT_OP_SET_SSP , hdev))return ;if (err) {
@@ -3782,7 +3784,8 @@ static void set_name_complete(struct hci_dev *hdev, void *data, int err)bt_dev_dbg (hdev,"err %d" , err); -if (cmd !=pending_find (MGMT_OP_SET_LOCAL_NAME , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_SET_LOCAL_NAME , hdev))return ;if (status) {
@@ -3957,7 +3960,8 @@ static void set_default_phy_complete(struct hci_dev *hdev, void *data, int err)struct sk_buff *skb = cmd->skb;u8 status =mgmt_status (err); -if (cmd !=pending_find (MGMT_OP_SET_PHY_CONFIGURATION , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_SET_PHY_CONFIGURATION , hdev))return ;if (!status) {
@@ -5848,13 +5852,16 @@ static void start_discovery_complete(struct hci_dev *hdev, void *data, int err) {struct mgmt_pending_cmd *cmd = data; +bt_dev_dbg (hdev,"err %d" , err); + +if (err == -ECANCELED ) +return ; +if (cmd !=pending_find (MGMT_OP_START_DISCOVERY , hdev) && cmd !=pending_find (MGMT_OP_START_LIMITED_DISCOVERY , hdev) && cmd !=pending_find (MGMT_OP_START_SERVICE_DISCOVERY , hdev))return ; -bt_dev_dbg (hdev,"err %d" , err); -mgmt_cmd_complete (cmd->sk, cmd->index, cmd->opcode,mgmt_status (err), cmd->param,1 );mgmt_pending_remove (cmd);
@@ -6087,7 +6094,8 @@ static void stop_discovery_complete(struct hci_dev *hdev, void *data, int err) {struct mgmt_pending_cmd *cmd = data; -if (cmd !=pending_find (MGMT_OP_STOP_DISCOVERY , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_STOP_DISCOVERY , hdev))return ;bt_dev_dbg (hdev,"err %d" , err);
@@ -8032,7 +8040,8 @@ static void read_local_oob_ext_data_complete(struct hci_dev *hdev, void *data,u8 status =mgmt_status (err);u16 eir_len; -if (cmd !=pending_find (MGMT_OP_READ_LOCAL_OOB_EXT_DATA , hdev)) +if (err == -ECANCELED || + cmd !=pending_find (MGMT_OP_READ_LOCAL_OOB_EXT_DATA , hdev))return ;if (!status) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 421/676 llc: Improve setsockopt() handling of malformed user input
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michal Luczaj <[email protected]>
[ Upstream commit 1465036b10be4b8b00eb31c879e86de633ad74c1 ]
copy_from_sockptr() is used incorrectly: return value is the number of bytes that could not be copied. Since it's deprecated, switch to copy_safe_from_sockptr().
Note: Keeping the optlen != sizeof(int) check as copy_safe_from_sockptr() by itself would also accept optlen > sizeof(int). Which would allow a more lenient handling of inputs.
--- net/llc/af_llc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
net/llc/af_llc.c +1 -1
@@ -1099,7 +1099,7 @@ static int llc_ui_setsockopt(struct socket *sock, int level, int optname,lock_sock (sk);if (unlikely (level !=SOL_LLC || optlen !=sizeof (int ))) goto out; - rc =copy_from_sockptr (&opt, optval,sizeof (opt)); + rc =copy_safe_from_sockptr (&opt,sizeof (opt), optval, optlen);if (rc) goto out; rc = -EINVAL ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 422/676 rxrpc: Improve setsockopt() handling of malformed user input
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michal Luczaj <[email protected]>
[ Upstream commit 02020056647017e70509bb58c3096448117099e1 ]
copy_from_sockptr() does not return negative value on error; instead, it reports the number of bytes that failed to copy. Since it's deprecated, switch to copy_safe_from_sockptr().
Note: Keeping the optlen != sizeof(unsigned int) check as copy_safe_from_sockptr() by itself would also accept
optlen > sizeof(unsigned int). Which would allow a more lenient handling of inputs.
--- net/rxrpc/af_rxrpc.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
net/rxrpc/af_rxrpc.c +4 -3
@@ -661,9 +661,10 @@ static int rxrpc_setsockopt(struct socket *sock, int level, int optname, ret = -EISCONN ;if (rx->sk.sk_state !=RXRPC_UNBOUND ) goto error; - ret =copy_from_sockptr (&min_sec_level, optval, -sizeof (unsigned int )); -if (ret <0 ) + ret =copy_safe_from_sockptr (&min_sec_level, +sizeof (min_sec_level), + optval, optlen); +if (ret) goto error; ret = -EINVAL ;if (min_sec_level >RXRPC_SECURITY_MAX )
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 423/676 tcp: Fix use-after-free of nreq in reqsk_timer_handler().
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kuniyuki Iwashima <[email protected]>
[ Upstream commit c31e72d021db2714df03df6c42855a1db592716c ]
The cited commit replaced inet_csk_reqsk_queue_drop_and_put() with __inet_csk_reqsk_queue_drop() and reqsk_put() in reqsk_timer_handler().
Then, oreq should be passed to reqsk_put() instead of req; otherwise use-after-free of nreq could happen when reqsk is migrated but the retry attempt failed (e.g. due to timeout).
Let's pass oreq to reqsk_put().
--- net/ipv4/inet_connection_sock.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
net/ipv4/inet_connection_sock.c +1 -1
@@ -1124,7 +1124,7 @@ static void reqsk_timer_handler(struct timer_list *t) drop:__inet_csk_reqsk_queue_drop (sk_listener, oreq, true); -reqsk_put (req); +reqsk_put (oreq); } static bool reqsk_queue_hash_req(struct request_sock *req,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 424/676 ip6mr: fix tables suspicious RCU usage
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Paolo Abeni <[email protected]>
[ Upstream commit f1553c9894b4dbeb10a2ab15ab1aa113b3b4047c ]
Several places call ip6mr_get_table() with no RCU nor RTNL lock. Add RCU protection inside such helper and provide a lockless variant for the few callers that already acquired the relevant lock.
Note that some users additionally reference the table outside the RCU lock. That is actually safe as the table deletion can happen only after all table accesses are completed.
--- net/ipv6/ip6mr.c | 38 +++++++++++++++++++++++++++----------- 1 file changed, 27 insertions(+), 11 deletions(-)
net/ipv6/ip6mr.c +27 -11
@@ -125,7 +125,7 @@ static struct mr_table *ip6mr_mr_table_iter(struct net *net,return ret; } -static struct mr_table *ip6mr_get_table (struct net *net,u32 id) +static struct mr_table *__ip6mr_get_table (struct net *net,u32 id) {struct mr_table *mrt;
@@ -136,6 +136,16 @@ static struct mr_table *ip6mr_get_table(struct net *net, u32 id)return NULL ; } +static struct mr_table *ip6mr_get_table (struct net *net,u32 id) +{ +struct mr_table *mrt; + +rcu_read_lock (); + mrt =__ip6mr_get_table (net, id); +rcu_read_unlock (); +return mrt; +} +static int ip6mr_fib_lookup (struct net *net,struct flowi6 *flp6,struct mr_table **mrt) {
@@ -177,7 +187,7 @@ static int ip6mr_rule_action(struct fib_rule *rule, struct flowi *flp, arg->table =fib_rule_get_table (rule, arg); - mrt =ip6mr_get_table (rule->fr_net, arg->table); + mrt =__ip6mr_get_table (rule->fr_net, arg->table);if (!mrt)return -EAGAIN ; res->mrt = mrt;
@@ -304,6 +314,8 @@ static struct mr_table *ip6mr_get_table(struct net *net, u32 id)return net->ipv6.mrt6; } +#define __ip6mr_get_table ip6mr_get_table +static int ip6mr_fib_lookup (struct net *net,struct flowi6 *flp6,struct mr_table **mrt) {
@@ -382,7 +394,7 @@ static struct mr_table *ip6mr_new_table(struct net *net, u32 id) {struct mr_table *mrt; - mrt =ip6mr_get_table (net, id); + mrt =__ip6mr_get_table (net, id);if (mrt)return mrt;
@@ -411,13 +423,15 @@ static void *ip6mr_vif_seq_start(struct seq_file *seq, loff_t *pos)struct net *net =seq_file_net (seq);struct mr_table *mrt; - mrt =ip6mr_get_table (net,RT6_TABLE_DFLT ); -if (!mrt) +rcu_read_lock (); + mrt =__ip6mr_get_table (net,RT6_TABLE_DFLT ); +if (!mrt) { +rcu_read_unlock ();return ERR_PTR (-ENOENT ); + } iter->mrt = mrt; -rcu_read_lock ();return mr_vif_seq_start (seq, pos); }
@@ -2278,11 +2292,13 @@ int ip6mr_get_route(struct net *net, struct sk_buff *skb, struct rtmsg *rtm,struct mfc6_cache *cache;struct rt6_info *rt = (struct rt6_info *)skb_dst (skb); - mrt =ip6mr_get_table (net,RT6_TABLE_DFLT ); -if (!mrt) +rcu_read_lock (); + mrt =__ip6mr_get_table (net,RT6_TABLE_DFLT ); +if (!mrt) { +rcu_read_unlock ();return -ENOENT ; + } -rcu_read_lock (); cache =ip6mr_cache_find (mrt, &rt->rt6i_src.addr, &rt->rt6i_dst.addr);if (!cache && skb->dev) {int vif =ip6mr_find_vif (mrt, skb->dev);
@@ -2563,7 +2579,7 @@ static int ip6mr_rtm_getroute(struct sk_buff *in_skb, struct nlmsghdr *nlh, grp =nla_get_in6_addr (tb[RTA_DST ]); tableid = tb[RTA_TABLE ] ?nla_get_u32 (tb[RTA_TABLE ]) :0 ; - mrt =ip6mr_get_table (net, tableid ?:RT_TABLE_DEFAULT ); + mrt =__ip6mr_get_table (net, tableid ?:RT_TABLE_DEFAULT );if (!mrt) {NL_SET_ERR_MSG_MOD (extack,"MR table does not exist" );return -ENOENT ;
@@ -2608,7 +2624,7 @@ static int ip6mr_rtm_dumproute(struct sk_buff *skb, struct netlink_callback *cb)if (filter.table_id) {struct mr_table *mrt; - mrt =ip6mr_get_table (sock_net (skb->sk), filter.table_id); + mrt =__ip6mr_get_table (sock_net (skb->sk), filter.table_id);if (!mrt) {if (rtnl_msg_family (cb->nlh) !=RTNL_FAMILY_IP6MR )return skb->len;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 425/676 ipmr: fix tables suspicious RCU usage
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Paolo Abeni <[email protected]>
[ Upstream commit fc9c273d6daaa9866f349bbe8cae25c67764c456 ]
Similar to the previous patch, plumb the RCU lock inside the ipmr_get_table(), provided a lockless variant and apply the latter in the few spots were the lock is already held.
--- net/ipv4/ipmr.c | 42 +++++++++++++++++++++++++++++------------- 1 file changed, 29 insertions(+), 13 deletions(-)
net/ipv4/ipmr.c +29 -13
@@ -136,7 +136,7 @@ static struct mr_table *ipmr_mr_table_iter(struct net *net,return ret; } -static struct mr_table *ipmr_get_table (struct net *net,u32 id) +static struct mr_table *__ipmr_get_table (struct net *net,u32 id) {struct mr_table *mrt;
@@ -147,6 +147,16 @@ static struct mr_table *ipmr_get_table(struct net *net, u32 id)return NULL ; } +static struct mr_table *ipmr_get_table (struct net *net,u32 id) +{ +struct mr_table *mrt; + +rcu_read_lock (); + mrt =__ipmr_get_table (net, id); +rcu_read_unlock (); +return mrt; +} +static int ipmr_fib_lookup (struct net *net,struct flowi4 *flp4,struct mr_table **mrt) {
@@ -188,7 +198,7 @@ static int ipmr_rule_action(struct fib_rule *rule, struct flowi *flp, arg->table =fib_rule_get_table (rule, arg); - mrt =ipmr_get_table (rule->fr_net, arg->table); + mrt =__ipmr_get_table (rule->fr_net, arg->table);if (!mrt)return -EAGAIN ; res->mrt = mrt;
@@ -314,6 +324,8 @@ static struct mr_table *ipmr_get_table(struct net *net, u32 id)return net->ipv4.mrt; } +#define __ipmr_get_table ipmr_get_table +static int ipmr_fib_lookup (struct net *net,struct flowi4 *flp4,struct mr_table **mrt) {
@@ -402,7 +414,7 @@ static struct mr_table *ipmr_new_table(struct net *net, u32 id)if (id !=RT_TABLE_DEFAULT && id >=1000000000 )return ERR_PTR (-EINVAL ); - mrt =ipmr_get_table (net, id); + mrt =__ipmr_get_table (net, id);if (mrt)return mrt;
@@ -1373,7 +1385,7 @@ int ip_mroute_setsockopt(struct sock *sk, int optname, sockptr_t optval, goto out_unlock; } - mrt =ipmr_get_table (net,raw_sk (sk)->ipmr_table ? :RT_TABLE_DEFAULT ); + mrt =__ipmr_get_table (net,raw_sk (sk)->ipmr_table ? :RT_TABLE_DEFAULT );if (!mrt) { ret = -ENOENT ; goto out_unlock;
@@ -2261,11 +2273,13 @@ int ipmr_get_route(struct net *net, struct sk_buff *skb,struct mr_table *mrt;int err; - mrt =ipmr_get_table (net,RT_TABLE_DEFAULT ); -if (!mrt) +rcu_read_lock (); + mrt =__ipmr_get_table (net,RT_TABLE_DEFAULT ); +if (!mrt) { +rcu_read_unlock ();return -ENOENT ; + } -rcu_read_lock (); cache =ipmr_cache_find (mrt, saddr, daddr);if (!cache && skb->dev) {int vif =ipmr_find_vif (mrt, skb->dev);
@@ -2550,7 +2564,7 @@ static int ipmr_rtm_getroute(struct sk_buff *in_skb, struct nlmsghdr *nlh, grp = tb[RTA_DST ] ?nla_get_in_addr (tb[RTA_DST ]) :0 ; tableid = tb[RTA_TABLE ] ?nla_get_u32 (tb[RTA_TABLE ]) :0 ; - mrt =ipmr_get_table (net, tableid ? tableid :RT_TABLE_DEFAULT ); + mrt =__ipmr_get_table (net, tableid ? tableid :RT_TABLE_DEFAULT );if (!mrt) { err = -ENOENT ; goto errout_free;
@@ -2602,7 +2616,7 @@ static int ipmr_rtm_dumproute(struct sk_buff *skb, struct netlink_callback *cb)if (filter.table_id) {struct mr_table *mrt; - mrt =ipmr_get_table (sock_net (skb->sk), filter.table_id); + mrt =__ipmr_get_table (sock_net (skb->sk), filter.table_id);if (!mrt) {if (rtnl_msg_family (cb->nlh) !=RTNL_FAMILY_IPMR )return skb->len;
@@ -2710,7 +2724,7 @@ static int rtm_to_ipmr_mfcc(struct net *net, struct nlmsghdr *nlh,break ; } } - mrt =ipmr_get_table (net, tblid); + mrt =__ipmr_get_table (net, tblid);if (!mrt) { ret = -ENOENT ; goto out;
@@ -2918,13 +2932,15 @@ static void *ipmr_vif_seq_start(struct seq_file *seq, loff_t *pos)struct net *net =seq_file_net (seq);struct mr_table *mrt; - mrt =ipmr_get_table (net,RT_TABLE_DEFAULT ); -if (!mrt) +rcu_read_lock (); + mrt =__ipmr_get_table (net,RT_TABLE_DEFAULT ); +if (!mrt) { +rcu_read_unlock ();return ERR_PTR (-ENOENT ); + } iter->mrt = mrt; -rcu_read_lock ();return mr_vif_seq_start (seq, pos); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 426/676 iio: light: al3010: Fix an error handling path in al3010_probe()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Christophe JAILLET <[email protected]>
[ Upstream commit a4b7064d34186cf4970fe0333c3b27346cf8f819 ]
If i2c_smbus_write_byte_data() fails in al3010_init(), al3010_set_pwr(false) is not called.
In order to avoid such a situation, move the devm_add_action_or_reset() witch calls al3010_set_pwr(false) right after a successful al3010_set_pwr(true).
--- drivers/iio/light/al3010.c | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-)
drivers/iio/light/al3010.c +5 -6
@@ -87,7 +87,12 @@ static int al3010_init(struct al3010_data *data)int ret; ret =al3010_set_pwr (data->client, true); +if (ret <0 ) +return ret; + ret =devm_add_action_or_reset (&data->client->dev, + al3010_set_pwr_off, + data);if (ret <0 )return ret;
@@ -190,12 +195,6 @@ static int al3010_probe(struct i2c_client *client)return ret; } - ret =devm_add_action_or_reset (&client->dev, - al3010_set_pwr_off, - data); -if (ret <0 ) -return ret; -return devm_iio_device_register (&client->dev, indio_dev); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 427/676 usb: using mutex lock and supporting O_NONBLOCK flag in iowarrior_read()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jeongjun Park <[email protected]>
[ Upstream commit 44feafbaa66ec86232b123bb8437a6a262442025 ]
iowarrior_read() uses the iowarrior dev structure, but does not use any lock on the structure. This can cause various bugs including data-races, so it is more appropriate to use a mutex lock to safely protect the iowarrior dev structure. When using a mutex lock, you should split the branch to prevent blocking when the O_NONBLOCK flag is set.
In addition, it is unnecessary to check for NULL on the iowarrior dev structure obtained by reading file->private_data. Therefore, it is better to remove the check.
--- drivers/usb/misc/iowarrior.c | 46 ++++++++++++++++++++++++++++-------- 1 file changed, 36 insertions(+), 10 deletions(-)
drivers/usb/misc/iowarrior.c +36 -10
@@ -277,28 +277,45 @@ static ssize_t iowarrior_read(struct file *file, char __user *buffer,struct iowarrior *dev;int read_idx;int offset; +int retval; dev = file->private_data; +if (file->f_flags &O_NONBLOCK ) { + retval =mutex_trylock (&dev->mutex); +if (!retval) +return -EAGAIN ; + }else { + retval =mutex_lock_interruptible (&dev->mutex); +if (retval) +return -ERESTARTSYS ; + } +/* verify that the device wasn't unplugged */ -if (!dev || !dev->present) -return -ENODEV ; +if (!dev->present) { + retval = -ENODEV ; + goto exit; + }dev_dbg (&dev->interface->dev,"minor %d, count = %zd\n" , dev->minor, count);/* read count must be packet size (+ time stamp) */ if ((count != dev->report_size) - && (count != (dev->report_size +1 ))) -return -EINVAL ; + && (count != (dev->report_size +1 ))) { + retval = -EINVAL ; + goto exit; + }/* repeat until no buffer overrun in callback handler occur */ do { atomic_set(&dev->overflow_flag, 0); if ((read_idx = read_index(dev)) == -1) { /* queue empty */ - if (file->f_flags & O_NONBLOCK) - return -EAGAIN; + if (file->f_flags & O_NONBLOCK) { + retval = -EAGAIN; + goto exit; + } else { //next line will return when there is either new data, or the device is unplugged int r = wait_event_interruptible(dev->read_wait,
@@ -309,28 +326,37 @@ static ssize_t iowarrior_read(struct file *file, char __user *buffer, -1));if (r) {//we were interrupted by a signal -return -ERESTART ; + retval = -ERESTART ; + goto exit; }if (!dev->present) {//The device was unplugged -return -ENODEV ; + retval = -ENODEV ; + goto exit; }if (read_idx ==-1 ) {// Can this happen ??? -return 0 ; + retval =0 ; + goto exit; } } } offset = read_idx * (dev->report_size +1 );if (copy_to_user (buffer, dev->read_queue + offset, count)) { -return -EFAULT ; + retval = -EFAULT ; + goto exit; } }while (atomic_read (&dev->overflow_flag)); read_idx = ++read_idx ==MAX_INTERRUPT_BUFFER ?0 : read_idx;atomic_set (&dev->read_idx, read_idx); +mutex_unlock (&dev->mutex);return count; + +exit: +mutex_unlock (&dev->mutex); +return retval; }/*
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 428/676 usb: yurex: make waiting on yurex_write interruptible
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Oliver Neukum <[email protected]>
[ Upstream commit e0aa9614ab0fd35b404e4b16ebe879f9fc152591 ]
The IO yurex_write() needs to wait for in order to have a device ready for writing again can take a long time time. Consequently the sleep is done in an interruptible state. Therefore others waiting for yurex_write() itself to finish should use mutex_lock_interruptible.
Rule: add
--- drivers/usb/misc/iowarrior.c | 4 ---- drivers/usb/misc/yurex.c | 5 ++++- 2 files changed, 4 insertions(+), 5 deletions(-)
drivers/usb/misc/iowarrior.c +0 -4
@@ -912,7 +912,6 @@ static int iowarrior_probe(struct usb_interface *interface,static void iowarrior_disconnect (struct usb_interface *interface) {struct iowarrior *dev =usb_get_intfdata (interface); -int minor = dev->minor;usb_deregister_dev (interface, &iowarrior_class);
@@ -936,9 +935,6 @@ static void iowarrior_disconnect(struct usb_interface *interface)mutex_unlock (&dev->mutex);iowarrior_delete (dev); } - -dev_info (&interface->dev,"I/O-Warror #%d now disconnected\n" , - minor -IOWARRIOR_MINOR_BASE ); }/* usb specific object needed to register this driver with the usb subsystem */
drivers/usb/misc/yurex.c +4 -1
@@ -441,7 +441,10 @@ static ssize_t yurex_write(struct file *file, const char __user *user_buffer,if (count ==0 ) goto error; -mutex_lock (&dev->io_mutex); + retval =mutex_lock_interruptible (&dev->io_mutex); +if (retval <0 ) +return -EINTR ; +if (dev->disconnected) {/* already disconnected */ mutex_unlock (&dev->io_mutex); retval = -ENODEV ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 429/676 USB: chaoskey: fail open after removal
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Oliver Neukum <[email protected]>
[ Upstream commit 422dc0a4d12d0b80dd3aab3fe5943f665ba8f041 ]
chaoskey_open() takes the lock only to increase the counter of openings. That means that the mutual exclusion with chaoskey_disconnect() cannot prevent an increase of the counter and chaoskey_open() returning a success.
If that race is hit, chaoskey_disconnect() will happily free all resources associated with the device after it has dropped the lock, as it has read the counter as zero.
To prevent this race chaoskey_open() has to check the presence of the device under the lock. However, the current per device lock cannot be used, because it is a part of the data structure to be freed. Hence an additional global mutex is needed. The issue is as old as the driver.
Rule: add
--- drivers/usb/misc/chaoskey.c | 35 ++++++++++++++++++++++++----------- 1 file changed, 24 insertions(+), 11 deletions(-)
drivers/usb/misc/chaoskey.c +24 -11
@@ -27,6 +27,8 @@ static struct usb_class_driver chaoskey_class;static int chaoskey_rng_read (struct hwrng *rng,void *data,size_t max,bool wait); +static DEFINE_MUTEX (chaoskey_list_lock); + #define usb_dbg(usb_if, format, arg...) \ dev_dbg(&(usb_if)->dev, format, ## arg)
@@ -230,6 +232,7 @@ static void chaoskey_disconnect(struct usb_interface *interface)if (dev->hwrng_registered)hwrng_unregister (&dev->hwrng); +mutex_lock (&chaoskey_list_lock);usb_deregister_dev (interface, &chaoskey_class);usb_set_intfdata (interface,NULL );
@@ -244,6 +247,7 @@ static void chaoskey_disconnect(struct usb_interface *interface) }else mutex_unlock (&dev->lock); +mutex_unlock (&chaoskey_list_lock);usb_dbg (interface,"disconnect done" ); }
@@ -251,6 +255,7 @@ static int chaoskey_open(struct inode *inode, struct file *file) {struct chaoskey *dev;struct usb_interface *interface; +int rv =0 ;/* get the interface from minor number and driver information */ interface =usb_find_interface (&chaoskey_driver,iminor (inode));
@@ -266,18 +271,23 @@ static int chaoskey_open(struct inode *inode, struct file *file) } file->private_data = dev; +mutex_lock (&chaoskey_list_lock);mutex_lock (&dev->lock); - ++dev->open; +if (dev->present) + ++dev->open; +else + rv = -ENODEV ;mutex_unlock (&dev->lock); +mutex_unlock (&chaoskey_list_lock); -usb_dbg (interface,"open success" ); -return 0 ; +return rv; }static int chaoskey_release (struct inode *inode,struct file *file) {struct chaoskey *dev = file->private_data;struct usb_interface *interface; +int rv =0 ;if (dev ==NULL )return -ENODEV ;
@@ -286,14 +296,15 @@ static int chaoskey_release(struct inode *inode, struct file *file)usb_dbg (interface,"release" ); +mutex_lock (&chaoskey_list_lock);mutex_lock (&dev->lock);usb_dbg (interface,"open count at release is %d" , dev->open);if (dev->open <=0 ) {usb_dbg (interface,"invalid open count (%d)" , dev->open); -mutex_unlock (&dev->lock); -return -ENODEV ; + rv = -ENODEV ; + goto bail; } --dev->open;
@@ -302,13 +313,15 @@ static int chaoskey_release(struct inode *inode, struct file *file)if (dev->open ==0 ) {mutex_unlock (&dev->lock);chaoskey_free (dev); - }else -mutex_unlock (&dev->lock); - }else -mutex_unlock (&dev->lock); - + goto destruction; + } + } +bail: +mutex_unlock (&dev->lock); +destruction: +mutex_lock (&chaoskey_list_lock);usb_dbg (interface,"release success" ); -return 0 ; +return rv; }static void chaos_read_callback (struct urb *urb)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 430/676 USB: chaoskey: Fix possible deadlock chaoskey_list_lock
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Edward Adam Davis <[email protected]>
[ Upstream commit d73dc7b182be4238b75278bfae16afb4c5564a58 ]
[Syzbot reported two possible deadlocks]
The first possible deadlock is:
WARNING: possible recursive locking detected
6.12.0-rc1-syzkaller-00027-g4a9fe2a8ac53 #0 Not tainted
--------------------------------------------
syz-executor363/2651 is trying to acquire lock:ffffffff89b120e8 (chaoskey_list_lock){+.+.}-{3:3}, at: chaoskey_release+0x15d/0x2c0 drivers/usb/misc/chaoskey.c:322
but task is already holding lock:ffffffff89b120e8 (chaoskey_list_lock){+.+.}-{3:3}, at: chaoskey_release+0x7f/0x2c0 drivers/usb/misc/chaoskey.c:299
other info that might help us debug this:
Possible unsafe locking scenario:
CPU0
---- lock(chaoskey_list_lock);
lock(chaoskey_list_lock);
*** DEADLOCK ***
The second possible deadlock is:
WARNING: possible circular locking dependency detected 6.12.0-rc1-syzkaller-00027-g4a9fe2a8ac53 #0 Not tainted
------------------------------------------------------
kworker/0:2/804 is trying to acquire lock:ffffffff899dadb0 (minor_rwsem){++++}-{3:3}, at: usb_deregister_dev+0x7c/0x1e0 drivers/usb/core/file.c:186
but task is already holding lock:ffffffff89b120e8 (chaoskey_list_lock){+.+.}-{3:3}, at: chaoskey_disconnect+0xa8/0x2a0 drivers/usb/misc/chaoskey.c:235
which lock already depends on the new lock.
the existing dependency chain (in reverse order) is:
-> #1 (chaoskey_list_lock){+.+.}-{3:3}:
__mutex_lock_common kernel/locking/mutex.c:608 [inline]
__mutex_lock+0x175/0x9c0 kernel/locking/mutex.c:752
chaoskey_open+0xdd/0x220 drivers/usb/misc/chaoskey.c:274
usb_open+0x186/0x220 drivers/usb/core/file.c:47
chrdev_open+0x237/0x6a0 fs/char_dev.c:414
do_dentry_open+0x6cb/0x1390 fs/open.c:958
vfs_open+0x82/0x3f0 fs/open.c:1088
do_open fs/namei.c:3774 [inline]
path_openat+0x1e6a/0x2d60 fs/namei.c:3933
do_filp_open+0x1dc/0x430 fs/namei.c:3960
do_sys_openat2+0x17a/0x1e0 fs/open.c:1415
do_sys_open fs/open.c:1430 [inline]
__do_sys_openat fs/open.c:1446 [inline]
__se_sys_openat fs/open.c:1441 [inline]
__x64_sys_openat+0x175/0x210 fs/open.c:1441
do_syscall_x64 arch/x86/entry/common.c:52 [inline]
do_syscall_64+0xcd/0x250 arch/x86/entry/common.c:83
entry_SYSCALL_64_after_hwframe+0x77/0x7f-> #0 (minor_rwsem){++++}-{3:3}:
check_prev_add kernel/locking/lockdep.c:3161 [inline]
check_prevs_add kernel/locking/lockdep.c:3280 [inline]
validate_chain kernel/locking/lockdep.c:3904 [inline]
__lock_acquire+0x250b/0x3ce0 kernel/locking/lockdep.c:5202
lock_acquire.part.0+0x11b/0x380 kernel/locking/lockdep.c:5825
down_write+0x93/0x200 kernel/locking/rwsem.c:1577
usb_deregister_dev+0x7c/0x1e0 drivers/usb/core/file.c:186
chaoskey_disconnect+0xb7/0x2a0 drivers/usb/misc/chaoskey.c:236
usb_unbind_interface+0x1e8/0x970 drivers/usb/core/driver.c:461
device_remove drivers/base/dd.c:569 [inline]
device_remove+0x122/0x170 drivers/base/dd.c:561
__device_release_driver drivers/base/dd.c:1273 [inline]
device_release_driver_internal+0x44a/0x610 drivers/base/dd.c:1296
bus_remove_device+0x22f/0x420 drivers/base/bus.c:576
device_del+0x396/0x9f0 drivers/base/core.c:3864
usb_disable_device+0x36c/0x7f0 drivers/usb/core/message.c:1418
usb_disconnect+0x2e1/0x920 drivers/usb/core/hub.c:2304
hub_port_connect drivers/usb/core/hub.c:5361 [inline]
hub_port_connect_change drivers/usb/core/hub.c:5661 [inline]
port_event drivers/usb/core/hub.c:5821 [inline]
hub_event+0x1bed/0x4f40 drivers/usb/core/hub.c:5903
process_one_work+0x9c5/0x1ba0 kernel/workqueue.c:3229
process_scheduled_works kernel/workqueue.c:3310 [inline]
worker_thread+0x6c8/0xf00 kernel/workqueue.c:3391
kthread+0x2c1/0x3a0 kernel/kthread.c:389
ret_from_fork+0x45/0x80 arch/x86/kernel/process.c:147
ret_from_fork_asm+0x1a/0x30 arch/x86/entry/entry_64.S:244other info that might help us debug this:
Possible unsafe locking scenario:
CPU0 CPU1
---- ----
lock(chaoskey_list_lock);
lock(minor_rwsem);
lock(chaoskey_list_lock); lock(minor_rwsem);
*** DEADLOCK ***
[Analysis]
The first is AA lock, it because wrong logic, it need a unlock. The second is AB lock, it needs to rearrange the order of lock usage.
--- drivers/usb/misc/chaoskey.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/usb/misc/chaoskey.c +2 -2
@@ -232,10 +232,10 @@ static void chaoskey_disconnect(struct usb_interface *interface)if (dev->hwrng_registered)hwrng_unregister (&dev->hwrng); -mutex_lock (&chaoskey_list_lock);usb_deregister_dev (interface, &chaoskey_class);usb_set_intfdata (interface,NULL ); +mutex_lock (&chaoskey_list_lock);mutex_lock (&dev->lock); dev->present = false;
@@ -319,7 +319,7 @@ static int chaoskey_release(struct inode *inode, struct file *file) bail:mutex_unlock (&dev->lock); destruction: -mutex_lock (&chaoskey_list_lock); +mutex_unlock (&chaoskey_list_lock);usb_dbg (interface,"release success" );return rv; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 431/676 misc: apds990x: Fix missing pm_runtime_disable()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jinjie Ruan <[email protected]>
[ Upstream commit 3c5d8b819d27012264edd17e6ae7fffda382fe44 ]
The pm_runtime_disable() is missing in probe error path, so add it to fix it.
--- drivers/misc/apds990x.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-)
drivers/misc/apds990x.c +7 -5
@@ -1147,7 +1147,7 @@ static int apds990x_probe(struct i2c_client *client) err = chip->pdata->setup_resources ();if (err) { err = -EINVAL ; - goto fail3; + goto fail4; } }
@@ -1155,7 +1155,7 @@ static int apds990x_probe(struct i2c_client *client) apds990x_attribute_group);if (err <0 ) {dev_err (&chip->client->dev,"Sysfs registration failed\n" ); - goto fail4; + goto fail5; } err = request_threaded_irq(client->irq, NULL,
@@ -1166,15 +1166,17 @@ static int apds990x_probe(struct i2c_client *client)if (err) {dev_err (&client->dev,"could not get IRQ %d\n" , client->irq); - goto fail5; + goto fail6; }return err; -fail5: +fail6:sysfs_remove_group (&chip->client->dev.kobj, &apds990x_attribute_group[0 ]); -fail4: +fail5:if (chip->pdata && chip->pdata->release_resources) chip->pdata->release_resources (); +fail4: +pm_runtime_disable (&client->dev); fail3:regulator_bulk_disable (ARRAY_SIZE (chip->regs), chip->regs); fail2:
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 432/676 counter: stm32-timer-cnt: Add check for clk_enable()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiasheng Jiang <[email protected]>
[ Upstream commit 842c3755a6bfbfcafa4a1438078d2485a9eb1d87 ]
Add check for the return value of clk_enable() in order to catch the potential exception.
--- drivers/counter/stm32-timer-cnt.c | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-)
drivers/counter/stm32-timer-cnt.c +13 -3
@@ -195,11 +195,17 @@ static int stm32_count_enable_write(struct counter_device *counter, {struct stm32_timer_cnt *const priv =counter_priv (counter);u32 cr1; +int ret;if (enable) {regmap_read (priv->regmap,TIM_CR1 , &cr1); -if (!(cr1 &TIM_CR1_CEN )) -clk_enable (priv->clk); +if (!(cr1 &TIM_CR1_CEN )) { + ret =clk_enable (priv->clk); +if (ret) { +dev_err (counter->parent,"Cannot enable clock %d\n" , ret); +return ret; + } + }regmap_update_bits (priv->regmap,TIM_CR1 ,TIM_CR1_CEN ,TIM_CR1_CEN );
@@ -383,7 +389,11 @@ static int __maybe_unused stm32_timer_cnt_resume(struct device *dev)return ret;if (priv->enabled) { -clk_enable (priv->clk); + ret =clk_enable (priv->clk); +if (ret) { +dev_err (dev,"Cannot enable clock %d\n" , ret); +return ret; + }/* Restore registers that may have been lost */ regmap_write (priv->regmap,TIM_SMCR , priv->bak.smcr);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 433/676 counter: ti-ecap-capture: Add check for clk_enable()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiasheng Jiang <[email protected]>
[ Upstream commit 1437d9f1c56fce9c24e566508bce1d218dd5497a ]
Add check for the return value of clk_enable() in order to catch the potential exception.
--- drivers/counter/ti-ecap-capture.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-)
drivers/counter/ti-ecap-capture.c +6 -1
@@ -576,8 +576,13 @@ static int ecap_cnt_resume(struct device *dev) {struct counter_device *counter_dev =dev_get_drvdata (dev);struct ecap_cnt_dev *ecap_dev =counter_priv (counter_dev); +int ret; -clk_enable (ecap_dev->clk); + ret =clk_enable (ecap_dev->clk); +if (ret) { +dev_err (dev,"Cannot enable clock %d\n" , ret); +return ret; + }ecap_cnt_capture_set_evmode (counter_dev, ecap_dev->pm_ctx.ev_mode);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 434/676 firmware_loader: Fix possible resource leak in fw_log_firmware_info()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gaosheng Cui <[email protected]>
[ Upstream commit 369a9c046c2fdfe037f05b43b84c386bdbccc103 ]
The alg instance should be released under the exception path, otherwise there may be resource leak here.
To mitigate this, free the alg instance with crypto_free_shash when kmalloc fails.
--- drivers/base/firmware_loader/main.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-)
drivers/base/firmware_loader/main.c +2 -3
@@ -824,19 +824,18 @@ static void fw_log_firmware_info(const struct firmware *fw, const char *name, st shash->tfm = alg;if (crypto_shash_digest (shash, fw->data, fw->size, sha256buf) <0 ) - goto out_shash; + goto out_free;for (int i =0 ; i <SHA256_DIGEST_SIZE ; i++)sprintf (&outbuf[i *2 ],"%02x" , sha256buf[i]); outbuf[SHA256_BLOCK_SIZE ] =0 ;dev_dbg (device,"Loaded FW: %s, sha256: %s\n" , name, outbuf); -out_shash: -crypto_free_shash (alg); out_free:kfree (shash);kfree (outbuf);kfree (sha256buf); +crypto_free_shash (alg); }#else static void fw_log_firmware_info(const struct firmware *fw, const char *name,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 435/676 ALSA: hda/realtek: Update ALC256 depop procedure
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kailang Yang <[email protected]>
[ Upstream commit cc3d0b5dd989d3238d456f9fd385946379a9c13d ]
Old procedure has a chance to meet Headphone no output.
--- sound/pci/hda/patch_realtek.c | 42 ++++++++++++++++------------------- 1 file changed, 19 insertions(+), 23 deletions(-)
sound/pci/hda/patch_realtek.c +19 -23
@@ -3602,25 +3602,22 @@ static void alc256_init(struct hda_codec *codec) hp_pin_sense =snd_hda_jack_detect (codec, hp_pin); -if (hp_pin_sense) +if (hp_pin_sense) {msleep (2 ); +alc_update_coefex_idx (codec,0x57 ,0x04 ,0x0007 ,0x1 );/* Low power */ -alc_update_coefex_idx (codec,0x57 ,0x04 ,0x0007 ,0x1 );/* Low power */ - -snd_hda_codec_write (codec, hp_pin,0 , -AC_VERB_SET_AMP_GAIN_MUTE ,AMP_OUT_MUTE ); - -if (hp_pin_sense || spec->ultra_low_power) -msleep (85 ); - -snd_hda_codec_write (codec, hp_pin,0 , +snd_hda_codec_write (codec, hp_pin,0 ,AC_VERB_SET_PIN_WIDGET_CONTROL ,PIN_OUT ); -if (hp_pin_sense || spec->ultra_low_power) -msleep (100 ); +msleep (75 ); + +snd_hda_codec_write (codec, hp_pin,0 , +AC_VERB_SET_AMP_GAIN_MUTE ,AMP_OUT_UNMUTE ); +msleep (75 ); +alc_update_coefex_idx (codec,0x57 ,0x04 ,0x0007 ,0x4 );/* Hight power */ + }alc_update_coef_idx (codec,0x46 ,3 <<12 ,0 ); -alc_update_coefex_idx (codec,0x57 ,0x04 ,0x0007 ,0x4 );/* Hight power */ alc_update_coefex_idx (codec,0x53 ,0x02 ,0x8000 ,1 <<15 );/* Clear bit */ alc_update_coefex_idx (codec,0x53 ,0x02 ,0x8000 ,0 <<15 );/*
@@ -3644,29 +3641,28 @@ static void alc256_shutup(struct hda_codec *codec)alc_update_coefex_idx (codec,0x57 ,0x04 ,0x0007 ,0x1 );/* Low power */ hp_pin_sense =snd_hda_jack_detect (codec, hp_pin); -if (hp_pin_sense) +if (hp_pin_sense) {msleep (2 ); -snd_hda_codec_write (codec, hp_pin,0 , +snd_hda_codec_write (codec, hp_pin,0 ,AC_VERB_SET_AMP_GAIN_MUTE ,AMP_OUT_MUTE ); -if (hp_pin_sense || spec->ultra_low_power) -msleep (85 ); +msleep (75 );/* 3k pull low control for Headset jack. */ /* NOTE: call this before clearing the pin, otherwise codec stalls */ /* If disable 3k pulldown control for alc257, the Mic detection will not work correctly * when booting with headset plugged. So skip setting it for the codec alc257 */ -if (spec->en_3kpull_low) -alc_update_coef_idx (codec,0x46 ,0 ,3 <<12 ); +if (spec->en_3kpull_low) +alc_update_coef_idx (codec,0x46 ,0 ,3 <<12 ); -if (!spec->no_shutup_pins) -snd_hda_codec_write (codec, hp_pin,0 , +if (!spec->no_shutup_pins) +snd_hda_codec_write (codec, hp_pin,0 ,AC_VERB_SET_PIN_WIDGET_CONTROL ,0x0 ); -if (hp_pin_sense || spec->ultra_low_power) -msleep (100 ); +msleep (75 ); + }alc_auto_setup_eapd (codec, false);alc_shutup_pins (codec);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 436/676 drm/radeon: add helper rdev_to_drm(rdev)
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Wu Hoi Pok <[email protected]>
[ Upstream commit a6e23bec8ed184ed2a11080b28cdbd7a3024f0c0 ]
Add helper rdev_to_drm(rdev), similar to amdgpu, most function should access the "drm_device" with "rdev_to_drm(rdev)" instead, where amdgpu has "adev_to_drm(adev)". It also makes changing from "*drm_device" to "drm_device" in "radeon_devicce" later on easier.
Stable-dep-of: 7037bb04265e ("drm/radeon: Fix spurious unplug event on radeon HDMI")
--- drivers/gpu/drm/radeon/radeon.h | 5 +++++ 1 file changed, 5 insertions(+)
drivers/gpu/drm/radeon/radeon.h +5 -0
@@ -2478,6 +2478,11 @@ void r100_io_wreg(struct radeon_device *rdev, u32 reg, u32 v);u32 cik_mm_rdoorbell (struct radeon_device *rdev,u32 index);void cik_mm_wdoorbell (struct radeon_device *rdev,u32 index,u32 v); +static inline struct drm_device *rdev_to_drm (struct radeon_device *rdev) +{ +return rdev->ddev; +} +/* * Cast helper */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 437/676 drm/radeon: change rdev->ddev to rdev_to_drm(rdev)
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Wu Hoi Pok <[email protected]>
[ Upstream commit fb1b5e1dd53fc834e12f69749cbc8484382599c4 ]
This patch changes the way "drm_device" is accessed. It uses "rdev_to_drm(rdev)" instead of accessing the struct member directly.
Stable-dep-of: 7037bb04265e ("drm/radeon: Fix spurious unplug event on radeon HDMI")
--- drivers/gpu/drm/radeon/atombios_encoders.c | 2 +- drivers/gpu/drm/radeon/cik.c | 14 ++-- drivers/gpu/drm/radeon/dce6_afmt.c | 2 +- drivers/gpu/drm/radeon/evergreen.c | 12 ++-- drivers/gpu/drm/radeon/ni.c | 2 +- drivers/gpu/drm/radeon/r100.c | 24 +++---- drivers/gpu/drm/radeon/r300.c | 6 +- drivers/gpu/drm/radeon/r420.c | 6 +- drivers/gpu/drm/radeon/r520.c | 2 +- drivers/gpu/drm/radeon/r600.c | 12 ++-- drivers/gpu/drm/radeon/r600_cs.c | 2 +- drivers/gpu/drm/radeon/r600_dpm.c | 4 +- drivers/gpu/drm/radeon/r600_hdmi.c | 2 +- drivers/gpu/drm/radeon/radeon_acpi.c | 10 +-- drivers/gpu/drm/radeon/radeon_agp.c | 2 +- drivers/gpu/drm/radeon/radeon_atombios.c | 2 +- drivers/gpu/drm/radeon/radeon_audio.c | 4 +- drivers/gpu/drm/radeon/radeon_combios.c | 12 ++-- drivers/gpu/drm/radeon/radeon_device.c | 10 +-- drivers/gpu/drm/radeon/radeon_display.c | 74 +++++++++++----------- drivers/gpu/drm/radeon/radeon_fbdev.c | 26 ++++---- drivers/gpu/drm/radeon/radeon_fence.c | 8 +-- drivers/gpu/drm/radeon/radeon_gem.c | 2 +- drivers/gpu/drm/radeon/radeon_i2c.c | 2 +- drivers/gpu/drm/radeon/radeon_ib.c | 2 +- drivers/gpu/drm/radeon/radeon_irq_kms.c | 12 ++-- drivers/gpu/drm/radeon/radeon_object.c | 2 +- drivers/gpu/drm/radeon/radeon_pm.c | 20 +++--- drivers/gpu/drm/radeon/radeon_ring.c | 2 +- drivers/gpu/drm/radeon/radeon_ttm.c | 6 +- drivers/gpu/drm/radeon/rs400.c | 6 +- drivers/gpu/drm/radeon/rs600.c | 14 ++-- drivers/gpu/drm/radeon/rs690.c | 2 +- drivers/gpu/drm/radeon/rv515.c | 4 +- drivers/gpu/drm/radeon/rv770.c | 2 +- drivers/gpu/drm/radeon/si.c | 4 +- 36 files changed, 159 insertions(+), 159 deletions(-)
drivers/gpu/drm/radeon/atombios_encoders.c +1 -1
@@ -2178,7 +2178,7 @@ int radeon_atom_pick_dig_encoder(struct drm_encoder *encoder, int fe_idx)void radeon_atom_encoder_init (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_encoder *encoder;list_for_each_entry (encoder, &dev->mode_config.encoder_list, head) {
drivers/gpu/drm/radeon/cik.c +7 -7
@@ -7585,7 +7585,7 @@ int cik_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[0 ]) { -drm_handle_vblank (rdev->ddev,0 ); +drm_handle_vblank (rdev_to_drm (rdev),0 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -7615,7 +7615,7 @@ int cik_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[1 ]) { -drm_handle_vblank (rdev->ddev,1 ); +drm_handle_vblank (rdev_to_drm (rdev),1 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -7645,7 +7645,7 @@ int cik_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[2 ]) { -drm_handle_vblank (rdev->ddev,2 ); +drm_handle_vblank (rdev_to_drm (rdev),2 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -7675,7 +7675,7 @@ int cik_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[3 ]) { -drm_handle_vblank (rdev->ddev,3 ); +drm_handle_vblank (rdev_to_drm (rdev),3 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -7705,7 +7705,7 @@ int cik_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[4 ]) { -drm_handle_vblank (rdev->ddev,4 ); +drm_handle_vblank (rdev_to_drm (rdev),4 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -7735,7 +7735,7 @@ int cik_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[5 ]) { -drm_handle_vblank (rdev->ddev,5 ); +drm_handle_vblank (rdev_to_drm (rdev),5 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -8581,7 +8581,7 @@ int cik_init(struct radeon_device *rdev)/* Initialize surface registers */ radeon_surface_init (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* Fence driver */ radeon_fence_driver_init (rdev);
drivers/gpu/drm/radeon/dce6_afmt.c +1 -1
@@ -90,7 +90,7 @@ struct r600_audio_pin *dce6_audio_get_pin(struct radeon_device *rdev) pin = &rdev->audio.pin[i]; pin_count =0 ; -list_for_each_entry (encoder, &rdev->ddev->mode_config.encoder_list, head) { +list_for_each_entry (encoder, &rdev_to_drm (rdev)->mode_config.encoder_list, head) {if (radeon_encoder_is_digital (encoder)) { radeon_encoder =to_radeon_encoder (encoder); dig = radeon_encoder->enc_priv;
drivers/gpu/drm/radeon/evergreen.c +6 -6
@@ -1672,7 +1672,7 @@ void evergreen_pm_misc(struct radeon_device *rdev)*/ void evergreen_pm_prepare (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 tmp;
@@ -1697,7 +1697,7 @@ void evergreen_pm_prepare(struct radeon_device *rdev)*/ void evergreen_pm_finish (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 tmp;
@@ -1762,7 +1762,7 @@ void evergreen_hpd_set_polarity(struct radeon_device *rdev,*/ void evergreen_hpd_init (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned enabled =0 ; u32 tmp = DC_HPDx_CONNECTION_TIMER(0x9c4) |
@@ -1803,7 +1803,7 @@ void evergreen_hpd_init(struct radeon_device *rdev)*/ void evergreen_hpd_fini (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned disabled =0 ;
@@ -4756,7 +4756,7 @@ int evergreen_irq_process(struct radeon_device *rdev) event_name ="vblank" ;if (rdev->irq.crtc_vblank_int[crtc_idx]) { -drm_handle_vblank (rdev->ddev, crtc_idx); +drm_handle_vblank (rdev_to_drm (rdev), crtc_idx); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -5214,7 +5214,7 @@ int evergreen_init(struct radeon_device *rdev)/* Initialize surface registers */ radeon_surface_init (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* Fence driver */ radeon_fence_driver_init (rdev);/* initialize AGP */
drivers/gpu/drm/radeon/ni.c +1 -1
@@ -2373,7 +2373,7 @@ int cayman_init(struct radeon_device *rdev)/* Initialize surface registers */ radeon_surface_init (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* Fence driver */ radeon_fence_driver_init (rdev);/* initialize memory controller */
drivers/gpu/drm/radeon/r100.c +12 -12
@@ -458,7 +458,7 @@ void r100_pm_misc(struct radeon_device *rdev)*/ void r100_pm_prepare (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 tmp;
@@ -489,7 +489,7 @@ void r100_pm_prepare(struct radeon_device *rdev)*/ void r100_pm_finish (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 tmp;
@@ -602,7 +602,7 @@ void r100_hpd_set_polarity(struct radeon_device *rdev,*/ void r100_hpd_init (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned enable =0 ;
@@ -625,7 +625,7 @@ void r100_hpd_init(struct radeon_device *rdev)*/ void r100_hpd_fini (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned disable =0 ;
@@ -797,7 +797,7 @@ int r100_irq_process(struct radeon_device *rdev)/* Vertical blank interrupts */ if (status &RADEON_CRTC_VBLANK_STAT ) {if (rdev->irq.crtc_vblank_int[0 ]) { -drm_handle_vblank (rdev->ddev,0 ); +drm_handle_vblank (rdev_to_drm (rdev),0 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -806,7 +806,7 @@ int r100_irq_process(struct radeon_device *rdev) }if (status &RADEON_CRTC2_VBLANK_STAT ) {if (rdev->irq.crtc_vblank_int[1 ]) { -drm_handle_vblank (rdev->ddev,1 ); +drm_handle_vblank (rdev_to_drm (rdev),1 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -1490,7 +1490,7 @@ int r100_cs_packet_parse_vline(struct radeon_cs_parser *p) header =radeon_get_ib_value (p, h_idx); crtc_id =radeon_get_ib_value (p, h_idx +5 ); reg =R100_CP_PACKET0_GET_REG (header); - crtc =drm_crtc_find (p->rdev->ddev, p->filp, crtc_id); + crtc =drm_crtc_find (rdev_to_drm (p->rdev), p->filp, crtc_id);if (!crtc) {DRM_ERROR ("cannot find crtc %d\n" , crtc_id);return -ENOENT ;
@@ -3078,7 +3078,7 @@ DEFINE_SHOW_ATTRIBUTE(r100_debugfs_mc_info);void r100_debugfs_rbbm_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("r100_rbbm_info" ,0444 , root, rdev, &r100_debugfs_rbbm_info_fops);
@@ -3088,7 +3088,7 @@ void r100_debugfs_rbbm_init(struct radeon_device *rdev)void r100_debugfs_cp_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("r100_cp_ring_info" ,0444 , root, rdev, &r100_debugfs_cp_ring_info_fops);
@@ -3100,7 +3100,7 @@ void r100_debugfs_cp_init(struct radeon_device *rdev)void r100_debugfs_mc_info_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("r100_mc_info" ,0444 , root, rdev, &r100_debugfs_mc_info_fops);
@@ -3966,7 +3966,7 @@ int r100_resume(struct radeon_device *rdev) RREG32(R_0007C0_CP_STAT)); }/* post */ -radeon_combios_asic_init (rdev->ddev); +radeon_combios_asic_init (rdev_to_drm (rdev));/* Resume clock after posting */ r100_clock_startup (rdev);/* Initialize surface registers */
@@ -4075,7 +4075,7 @@ int r100_init(struct radeon_device *rdev)/* Set asic errata */ r100_errata (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize AGP */ if (rdev->flags &RADEON_IS_AGP ) { r =radeon_agp_init (rdev);
drivers/gpu/drm/radeon/r300.c +3 -3
@@ -615,7 +615,7 @@ DEFINE_SHOW_ATTRIBUTE(rv370_debugfs_pcie_gart_info);static void rv370_debugfs_pcie_gart_info_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("rv370_pcie_gart_info" ,0444 , root, rdev, &rv370_debugfs_pcie_gart_info_fops);
@@ -1451,7 +1451,7 @@ int r300_resume(struct radeon_device *rdev) RREG32(R_0007C0_CP_STAT)); }/* post */ -radeon_combios_asic_init (rdev->ddev); +radeon_combios_asic_init (rdev_to_drm (rdev));/* Resume clock after posting */ r300_clock_startup (rdev);/* Initialize surface registers */
@@ -1537,7 +1537,7 @@ int r300_init(struct radeon_device *rdev)/* Set asic errata */ r300_errata (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize AGP */ if (rdev->flags &RADEON_IS_AGP ) { r =radeon_agp_init (rdev);
drivers/gpu/drm/radeon/r420.c +3 -3
@@ -321,7 +321,7 @@ int r420_resume(struct radeon_device *rdev)if (rdev->is_atom_bios) {atom_asic_init (rdev->mode_info.atom_context); }else { -radeon_combios_asic_init (rdev->ddev); +radeon_combios_asic_init (rdev_to_drm (rdev)); }/* Resume clock after posting */ r420_clock_resume (rdev);
@@ -413,7 +413,7 @@ int r420_init(struct radeon_device *rdev)return -EINVAL ;/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize AGP */ if (rdev->flags &RADEON_IS_AGP ) { r =radeon_agp_init (rdev);
@@ -492,7 +492,7 @@ DEFINE_SHOW_ATTRIBUTE(r420_debugfs_pipes_info);void r420_debugfs_pipes_info_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("r420_pipes_info" ,0444 , root, rdev, &r420_debugfs_pipes_info_fops);
drivers/gpu/drm/radeon/r520.c +1 -1
@@ -287,7 +287,7 @@ int r520_init(struct radeon_device *rdev)atom_asic_init (rdev->mode_info.atom_context); }/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize AGP */ if (rdev->flags &RADEON_IS_AGP ) { r =radeon_agp_init (rdev);
drivers/gpu/drm/radeon/r600.c +6 -6
@@ -950,7 +950,7 @@ void r600_hpd_set_polarity(struct radeon_device *rdev,void r600_hpd_init (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned enable =0 ;
@@ -1017,7 +1017,7 @@ void r600_hpd_init(struct radeon_device *rdev)void r600_hpd_fini (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned disable =0 ;
@@ -3280,7 +3280,7 @@ int r600_init(struct radeon_device *rdev)/* Initialize surface registers */ radeon_surface_init (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* Fence driver */ radeon_fence_driver_init (rdev);if (rdev->flags &RADEON_IS_AGP ) {
@@ -4136,7 +4136,7 @@ int r600_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: D1 vblank - IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[0 ]) { -drm_handle_vblank (rdev->ddev,0 ); +drm_handle_vblank (rdev_to_drm (rdev),0 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -4166,7 +4166,7 @@ int r600_irq_process(struct radeon_device *rdev)DRM_DEBUG ("IH: D2 vblank - IH event w/o asserted irq bit?\n" );if (rdev->irq.crtc_vblank_int[1 ]) { -drm_handle_vblank (rdev->ddev,1 ); +drm_handle_vblank (rdev_to_drm (rdev),1 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -4358,7 +4358,7 @@ DEFINE_SHOW_ATTRIBUTE(r600_debugfs_mc_info);static void r600_debugfs_mc_info_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("r600_mc_info" ,0444 , root, rdev, &r600_debugfs_mc_info_fops);
drivers/gpu/drm/radeon/r600_cs.c +1 -1
@@ -884,7 +884,7 @@ int r600_cs_common_vline_parse(struct radeon_cs_parser *p, crtc_id =radeon_get_ib_value (p, h_idx +2 +7 +1 ); reg =R600_CP_PACKET0_GET_REG (header); - crtc =drm_crtc_find (p->rdev->ddev, p->filp, crtc_id); + crtc =drm_crtc_find (rdev_to_drm (p->rdev), p->filp, crtc_id);if (!crtc) {DRM_ERROR ("cannot find crtc %d\n" , crtc_id);return -ENOENT ;
drivers/gpu/drm/radeon/r600_dpm.c +2 -2
@@ -155,7 +155,7 @@ void r600_dpm_print_ps_status(struct radeon_device *rdev,u32 r600_dpm_get_vblank_time (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 vblank_in_pixels;
@@ -182,7 +182,7 @@ u32 r600_dpm_get_vblank_time(struct radeon_device *rdev)u32 r600_dpm_get_vrefresh (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 vrefresh =0 ;
drivers/gpu/drm/radeon/r600_hdmi.c +1 -1
@@ -116,7 +116,7 @@ void r600_audio_update_hdmi(struct work_struct *work) { struct radeon_device *rdev = container_of(work, struct radeon_device, audio_work); -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct r600_audio_pin audio_status =r600_audio_status (rdev);struct drm_encoder *encoder;bool changed = false;
drivers/gpu/drm/radeon/radeon_acpi.c +5 -5
@@ -405,11 +405,11 @@ static int radeon_atif_handler(struct radeon_device *rdev,if (req.pending &ATIF_DGPU_DISPLAY_EVENT ) {if ((rdev->flags &RADEON_IS_PX ) &&radeon_atpx_dgpu_req_power_for_displays ()) { -pm_runtime_get_sync (rdev->ddev->dev); +pm_runtime_get_sync (rdev_to_drm (rdev)->dev);/* Just fire off a uevent and let userspace tell us what to do */ -drm_helper_hpd_irq_event (rdev->ddev); -pm_runtime_mark_last_busy (rdev->ddev->dev); -pm_runtime_put_autosuspend (rdev->ddev->dev); +drm_helper_hpd_irq_event (rdev_to_drm (rdev)); +pm_runtime_mark_last_busy (rdev_to_drm (rdev)->dev); +pm_runtime_put_autosuspend (rdev_to_drm (rdev)->dev); } }/* TODO: check other events */
@@ -736,7 +736,7 @@ int radeon_acpi_init(struct radeon_device *rdev)struct radeon_encoder *target =NULL ;/* Find the encoder controlling the brightness */ -list_for_each_entry (tmp, &rdev->ddev->mode_config.encoder_list, +list_for_each_entry (tmp, &rdev_to_drm (rdev)->mode_config.encoder_list, head) {struct radeon_encoder *enc =to_radeon_encoder (tmp);
drivers/gpu/drm/radeon/radeon_agp.c +1 -1
@@ -161,7 +161,7 @@ struct radeon_agp_head *radeon_agp_head_init(struct drm_device *dev)static int radeon_agp_head_acquire (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct pci_dev *pdev =to_pci_dev (dev->dev);if (!rdev->agp)
drivers/gpu/drm/radeon/radeon_atombios.c +1 -1
@@ -186,7 +186,7 @@ void radeon_atombios_i2c_init(struct radeon_device *rdev)if (i2c.valid) {sprintf (stmp,"0x%x" , i2c.i2c_id); - rdev->i2c_bus[i] =radeon_i2c_create (rdev->ddev, &i2c, stmp); + rdev->i2c_bus[i] =radeon_i2c_create (rdev_to_drm (rdev), &i2c, stmp); } gpio = (ATOM_GPIO_I2C_ASSIGMENT *) ((u8 *)gpio +sizeof (ATOM_GPIO_I2C_ASSIGMENT ));
drivers/gpu/drm/radeon/radeon_audio.c +2 -2
@@ -195,7 +195,7 @@ static void radeon_audio_enable(struct radeon_device *rdev,return ;if (rdev->mode_info.mode_config_initialized) { -list_for_each_entry (encoder, &rdev->ddev->mode_config.encoder_list, head) { +list_for_each_entry (encoder, &rdev_to_drm (rdev)->mode_config.encoder_list, head) {if (radeon_encoder_is_digital (encoder)) { radeon_encoder =to_radeon_encoder (encoder); dig = radeon_encoder->enc_priv;
@@ -758,7 +758,7 @@ static int radeon_audio_component_get_eld(struct device *kdev, int port,if (!rdev->audio.enabled || !rdev->mode_info.mode_config_initialized)return 0 ; -list_for_each_entry (encoder, &rdev->ddev->mode_config.encoder_list, head) { +list_for_each_entry (encoder, &rdev_to_drm (rdev)->mode_config.encoder_list, head) {if (!radeon_encoder_is_digital (encoder))continue ; radeon_encoder =to_radeon_encoder (encoder);
drivers/gpu/drm/radeon/radeon_combios.c +6 -6
@@ -371,7 +371,7 @@ bool radeon_combios_check_hardcoded_edid(struct radeon_device *rdev)int edid_info, size;struct edid *edid;unsigned char *raw; - edid_info =combios_get_table_offset (rdev->ddev,COMBIOS_HARDCODED_EDID_TABLE ); + edid_info =combios_get_table_offset (rdev_to_drm (rdev),COMBIOS_HARDCODED_EDID_TABLE );if (!edid_info)return false;
@@ -641,7 +641,7 @@ static struct radeon_i2c_bus_rec combios_setup_i2c_bus(struct radeon_device *rdestatic struct radeon_i2c_bus_rec radeon_combios_get_i2c_info_from_table (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct radeon_i2c_bus_rec i2c;u16 offset;u8 id, blocks, clk, data;
@@ -669,7 +669,7 @@ static struct radeon_i2c_bus_rec radeon_combios_get_i2c_info_from_table(struct rvoid radeon_combios_i2c_init (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct radeon_i2c_bus_rec i2c;/* actual hw pads
@@ -811,7 +811,7 @@ bool radeon_combios_get_clock_info(struct drm_device *dev)bool radeon_combios_sideport_present (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);u16 igp_info;/* sideport is AMD only */
@@ -914,7 +914,7 @@ struct radeon_encoder_primary_dac *radeon_combios_get_primary_dac_info(structenum radeon_tv_std radeon_combios_get_tv_info (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);uint16_t tv_info;enum radeon_tv_std tv_std =TV_STD_NTSC ;
@@ -2636,7 +2636,7 @@ static const char *thermal_controller_names[] = {void radeon_combios_get_power_modes (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);u16 offset, misc, misc2 =0 ;u8 rev, tmp;int state_index =0 ;
drivers/gpu/drm/radeon/radeon_device.c +5 -5
@@ -760,7 +760,7 @@ bool radeon_boot_test_post_card(struct radeon_device *rdev)if (rdev->is_atom_bios)atom_asic_init (rdev->mode_info.atom_context);else -radeon_combios_asic_init (rdev->ddev); +radeon_combios_asic_init (rdev_to_drm (rdev));return true; }else {dev_err (rdev->dev,"Card not posted and no BIOS - ignoring\n" );
@@ -980,7 +980,7 @@ int radeon_atombios_init(struct radeon_device *rdev)return -ENOMEM ; rdev->mode_info.atom_card_info = atom_card_info; - atom_card_info->dev = rdev->ddev; + atom_card_info->dev =rdev_to_drm (rdev); atom_card_info->reg_read = cail_reg_read; atom_card_info->reg_write = cail_reg_write;/* needed for iio ops */
@@ -1005,7 +1005,7 @@ int radeon_atombios_init(struct radeon_device *rdev)mutex_init (&rdev->mode_info.atom_context->mutex);mutex_init (&rdev->mode_info.atom_context->scratch_mutex); -radeon_atom_initialize_bios_scratch_regs (rdev->ddev); +radeon_atom_initialize_bios_scratch_regs (rdev_to_drm (rdev));atom_allocate_fb_scratch (rdev->mode_info.atom_context);return 0 ; }
@@ -1049,7 +1049,7 @@ void radeon_atombios_fini(struct radeon_device *rdev)*/ int radeon_combios_init (struct radeon_device *rdev) { -radeon_combios_initialize_bios_scratch_regs (rdev->ddev); +radeon_combios_initialize_bios_scratch_regs (rdev_to_drm (rdev));return 0 ; }
@@ -1847,7 +1847,7 @@ int radeon_gpu_reset(struct radeon_device *rdev)downgrade_write (&rdev->exclusive_lock); -drm_helper_resume_force_mode (rdev->ddev); +drm_helper_resume_force_mode (rdev_to_drm (rdev));/* set the power state here in case we are a PX system or headless */ if ((rdev->pm.pm_method ==PM_METHOD_DPM ) && rdev->pm.dpm_enabled)
drivers/gpu/drm/radeon/radeon_display.c +37 -37
214 lines not on this page · raw message
drivers/gpu/drm/radeon/radeon_fbdev.c +13 -13
@@ -67,7 +67,7 @@ static int radeon_fbdev_create_pinned_object(struct drm_fb_helper *fb_helper,int height = mode_cmd->height;u32 cpp; - info =drm_get_format_info (rdev->ddev, mode_cmd); + info =drm_get_format_info (rdev_to_drm (rdev), mode_cmd); cpp = info->cpp[0 ];/* need to align pitch with crtc limits */
@@ -148,15 +148,15 @@ static int radeon_fbdev_fb_open(struct fb_info *info, int user)struct radeon_device *rdev = fb_helper->dev->dev_private;int ret; - ret =pm_runtime_get_sync (rdev->ddev->dev); + ret =pm_runtime_get_sync (rdev_to_drm (rdev)->dev);if (ret <0 && ret != -EACCES ) goto err_pm_runtime_mark_last_busy;return 0 ; err_pm_runtime_mark_last_busy: -pm_runtime_mark_last_busy (rdev->ddev->dev); -pm_runtime_put_autosuspend (rdev->ddev->dev); +pm_runtime_mark_last_busy (rdev_to_drm (rdev)->dev); +pm_runtime_put_autosuspend (rdev_to_drm (rdev)->dev);return ret; }
@@ -165,8 +165,8 @@ static int radeon_fbdev_fb_release(struct fb_info *info, int user)struct drm_fb_helper *fb_helper = info->par;struct radeon_device *rdev = fb_helper->dev->dev_private; -pm_runtime_mark_last_busy (rdev->ddev->dev); -pm_runtime_put_autosuspend (rdev->ddev->dev); +pm_runtime_mark_last_busy (rdev_to_drm (rdev)->dev); +pm_runtime_put_autosuspend (rdev_to_drm (rdev)->dev);return 0 ; }
@@ -236,7 +236,7 @@ static int radeon_fbdev_fb_helper_fb_probe(struct drm_fb_helper *fb_helper, ret = -ENOMEM ; goto err_radeon_fbdev_destroy_pinned_object; } - ret =radeon_framebuffer_init (rdev->ddev, fb, &mode_cmd, gobj); + ret =radeon_framebuffer_init (rdev_to_drm (rdev), fb, &mode_cmd, gobj);if (ret) {DRM_ERROR ("failed to initialize framebuffer %d\n" , ret); goto err_kfree;
@@ -374,12 +374,12 @@ void radeon_fbdev_setup(struct radeon_device *rdev) fb_helper =kzalloc (sizeof (*fb_helper),GFP_KERNEL );if (!fb_helper)return ; -drm_fb_helper_prepare (rdev->ddev, fb_helper, bpp_sel, &radeon_fbdev_fb_helper_funcs); +drm_fb_helper_prepare (rdev_to_drm (rdev), fb_helper, bpp_sel, &radeon_fbdev_fb_helper_funcs); - ret =drm_client_init (rdev->ddev, &fb_helper->client,"radeon-fbdev" , + ret =drm_client_init (rdev_to_drm (rdev), &fb_helper->client,"radeon-fbdev" , &radeon_fbdev_client_funcs);if (ret) { -drm_err (rdev->ddev,"Failed to register client: %d\n" , ret); +drm_err (rdev_to_drm (rdev),"Failed to register client: %d\n" , ret); goto err_drm_client_init; }
@@ -394,13 +394,13 @@ void radeon_fbdev_setup(struct radeon_device *rdev)void radeon_fbdev_set_suspend (struct radeon_device *rdev,int state) { -if (rdev->ddev->fb_helper) -drm_fb_helper_set_suspend (rdev->ddev->fb_helper, state); +if (rdev_to_drm (rdev)->fb_helper) +drm_fb_helper_set_suspend (rdev_to_drm (rdev)->fb_helper, state); }bool radeon_fbdev_robj_is_fb (struct radeon_device *rdev,struct radeon_bo *robj) { -struct drm_fb_helper *fb_helper = rdev->ddev->fb_helper; +struct drm_fb_helper *fb_helper =rdev_to_drm (rdev)->fb_helper;struct drm_gem_object *gobj;if (!fb_helper)
drivers/gpu/drm/radeon/radeon_fence.c +4 -4
@@ -151,7 +151,7 @@ int radeon_fence_emit(struct radeon_device *rdev, rdev->fence_context + ring, seq);radeon_fence_ring_emit (rdev, ring, *fence); -trace_radeon_fence_emit (rdev->ddev, ring, (*fence)->seq); +trace_radeon_fence_emit (rdev_to_drm (rdev), ring, (*fence)->seq);radeon_fence_schedule_check (rdev, ring);return 0 ; }
@@ -492,7 +492,7 @@ static long radeon_fence_wait_seq_timeout(struct radeon_device *rdev,if (!target_seq[i])continue ; -trace_radeon_fence_wait_begin (rdev->ddev, i, target_seq[i]); +trace_radeon_fence_wait_begin (rdev_to_drm (rdev), i, target_seq[i]);radeon_irq_kms_sw_irq_get (rdev, i); }
@@ -514,7 +514,7 @@ static long radeon_fence_wait_seq_timeout(struct radeon_device *rdev,continue ;radeon_irq_kms_sw_irq_put (rdev, i); -trace_radeon_fence_wait_end (rdev->ddev, i, target_seq[i]); +trace_radeon_fence_wait_end (rdev_to_drm (rdev), i, target_seq[i]); }return r;
@@ -1004,7 +1004,7 @@ DEFINE_DEBUGFS_ATTRIBUTE(radeon_debugfs_gpu_reset_fops,void radeon_debugfs_fence_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("radeon_gpu_reset" ,0444 , root, rdev, &radeon_debugfs_gpu_reset_fops);
drivers/gpu/drm/radeon/radeon_gem.c +1 -1
@@ -898,7 +898,7 @@ DEFINE_SHOW_ATTRIBUTE(radeon_debugfs_gem_info);void radeon_gem_debugfs_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("radeon_gem_info" ,0444 , root, rdev, &radeon_debugfs_gem_info_fops);
drivers/gpu/drm/radeon/radeon_i2c.c +1 -1
@@ -1012,7 +1012,7 @@ void radeon_i2c_add(struct radeon_device *rdev,struct radeon_i2c_bus_rec *rec, const char *name) { - struct drm_device *dev = rdev->ddev; + struct drm_device *dev = rdev_to_drm(rdev);int i;for (i =0 ; i <RADEON_MAX_I2C_BUS ; i++) {
drivers/gpu/drm/radeon/radeon_ib.c +1 -1
@@ -307,7 +307,7 @@ DEFINE_SHOW_ATTRIBUTE(radeon_debugfs_sa_info);static void radeon_debugfs_sa_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("radeon_sa_info" ,0444 , root, rdev, &radeon_debugfs_sa_info_fops);
drivers/gpu/drm/radeon/radeon_irq_kms.c +6 -6
@@ -80,7 +80,7 @@ static void radeon_hotplug_work_func(struct work_struct *work) { struct radeon_device *rdev = container_of(work, struct radeon_device, hotplug_work.work); -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_mode_config *mode_config = &dev->mode_config;struct drm_connector *connector;
@@ -101,7 +101,7 @@ static void radeon_dp_work_func(struct work_struct *work) { struct radeon_device *rdev = container_of(work, struct radeon_device, dp_work); -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_mode_config *mode_config = &dev->mode_config;struct drm_connector *connector;
@@ -197,7 +197,7 @@ static void radeon_driver_irq_uninstall_kms(struct drm_device *dev)static int radeon_irq_install (struct radeon_device *rdev,int irq) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);int ret;if (irq ==IRQ_NOTCONNECTED )
@@ -218,7 +218,7 @@ static int radeon_irq_install(struct radeon_device *rdev, int irq)static void radeon_irq_uninstall (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct pci_dev *pdev =to_pci_dev (dev->dev);radeon_driver_irq_uninstall_kms (dev);
@@ -322,9 +322,9 @@ int radeon_irq_kms_init(struct radeon_device *rdev)spin_lock_init (&rdev->irq.lock);/* Disable vblank irqs aggressively for power-saving */ - rdev->ddev->vblank_disable_immediate = true; +rdev_to_drm (rdev)->vblank_disable_immediate = true; - r =drm_vblank_init (rdev->ddev, rdev->num_crtc); + r =drm_vblank_init (rdev_to_drm (rdev), rdev->num_crtc);if (r) {return r; }
drivers/gpu/drm/radeon/radeon_object.c +1 -1
@@ -152,7 +152,7 @@ int radeon_bo_create(struct radeon_device *rdev, bo =kzalloc (sizeof (struct radeon_bo ),GFP_KERNEL );if (bo ==NULL )return -ENOMEM ; -drm_gem_private_object_init (rdev->ddev, &bo->tbo.base, size); +drm_gem_private_object_init (rdev_to_drm (rdev), &bo->tbo.base, size); bo->rdev = rdev; bo->surface_reg =-1 ;INIT_LIST_HEAD (&bo->list);
drivers/gpu/drm/radeon/radeon_pm.c +10 -10
@@ -281,7 +281,7 @@ static void radeon_pm_set_clocks(struct radeon_device *rdev)if (rdev->irq.installed) { i =0 ; -drm_for_each_crtc (crtc, rdev->ddev) { +drm_for_each_crtc (crtc,rdev_to_drm (rdev)) {if (rdev->pm.active_crtcs & (1 << i)) {/* This can fail if a modeset is in progress */ if (drm_crtc_vblank_get (crtc) ==0 )
@@ -298,7 +298,7 @@ static void radeon_pm_set_clocks(struct radeon_device *rdev)if (rdev->irq.installed) { i =0 ; -drm_for_each_crtc (crtc, rdev->ddev) { +drm_for_each_crtc (crtc,rdev_to_drm (rdev)) {if (rdev->pm.req_vblank & (1 << i)) { rdev->pm.req_vblank &= ~(1 << i);drm_crtc_vblank_put (crtc);
@@ -670,7 +670,7 @@ static ssize_t radeon_hwmon_show_temp(struct device *dev, char *buf) {struct radeon_device *rdev =dev_get_drvdata (dev); -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);int temp;/* Can't get temperature when the card is off */
@@ -714,7 +714,7 @@ static ssize_t radeon_hwmon_show_sclk(struct device *dev, struct device_attribute *attr, char *buf) { struct radeon_device *rdev = dev_get_drvdata(dev); -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);u32 sclk =0 ;/* Can't get clock frequency when the card is off */
@@ -739,7 +739,7 @@ static ssize_t radeon_hwmon_show_vddc(struct device *dev, struct device_attribute *attr, char *buf) { struct radeon_device *rdev = dev_get_drvdata(dev); -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);u16 vddc =0 ;/* Can't get vddc when the card is off */
@@ -1691,7 +1691,7 @@ void radeon_pm_fini(struct radeon_device *rdev)static void radeon_pm_compute_clocks_old (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;
@@ -1764,7 +1764,7 @@ static void radeon_pm_compute_clocks_old(struct radeon_device *rdev)static void radeon_pm_compute_clocks_dpm (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;struct radeon_connector *radeon_connector;
@@ -1825,7 +1825,7 @@ static bool radeon_pm_in_vbl(struct radeon_device *rdev)*/ for (crtc =0 ; (crtc < rdev->num_crtc) && in_vbl; crtc++) {if (rdev->pm.active_crtcs & (1 << crtc)) { - vbl_status = radeon_get_crtc_scanoutpos(rdev->ddev, + vbl_status = radeon_get_crtc_scanoutpos(rdev_to_drm(rdev), crtc, USE_REAL_VBLANKSTART, &vpos, &hpos, NULL, NULL,
@@ -1917,7 +1917,7 @@ static void radeon_dynpm_idle_work_handler(struct work_struct *work)static int radeon_debugfs_pm_info_show (struct seq_file *m,void *unused) {struct radeon_device *rdev = m->private; -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);if ((rdev->flags &RADEON_IS_PX ) && (ddev->switch_power_state !=DRM_SWITCH_POWER_ON )) {
@@ -1954,7 +1954,7 @@ DEFINE_SHOW_ATTRIBUTE(radeon_debugfs_pm_info);static void radeon_debugfs_pm_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("radeon_pm_info" ,0444 , root, rdev, &radeon_debugfs_pm_info_fops);
drivers/gpu/drm/radeon/radeon_ring.c +1 -1
@@ -548,7 +548,7 @@ static void radeon_debugfs_ring_init(struct radeon_device *rdev, struct radeon_r {#if defined(CONFIG_DEBUG_FS )const char *ring_name =radeon_debugfs_ring_idx_to_name (ring->idx); -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;if (ring_name) debugfs_create_file(ring_name, 0444, root, ring,
drivers/gpu/drm/radeon/radeon_ttm.c +3 -3
@@ -689,8 +689,8 @@ int radeon_ttm_init(struct radeon_device *rdev)/* No others user of address space so set it to 0 */ r =ttm_device_init (&rdev->mman.bdev, &radeon_bo_driver, rdev->dev, - rdev->ddev->anon_inode->i_mapping, - rdev->ddev->vma_offset_manager, +rdev_to_drm (rdev)->anon_inode->i_mapping, +rdev_to_drm (rdev)->vma_offset_manager, rdev->need_swiotlb,dma_addressing_limited (&rdev->pdev->dev));if (r) {
@@ -897,7 +897,7 @@ static const struct file_operations radeon_ttm_gtt_fops = {static void radeon_ttm_debugfs_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct drm_minor *minor = rdev->ddev->primary; +struct drm_minor *minor =rdev_to_drm (rdev)->primary;struct dentry *root = minor->debugfs_root; debugfs_create_file("radeon_vram", 0444, root, rdev,
drivers/gpu/drm/radeon/rs400.c +3 -3
@@ -378,7 +378,7 @@ DEFINE_SHOW_ATTRIBUTE(rs400_debugfs_gart_info);static void rs400_debugfs_pcie_gart_info_init (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("rs400_gart_info" ,0444 , root, rdev, &rs400_debugfs_gart_info_fops);
@@ -473,7 +473,7 @@ int rs400_resume(struct radeon_device *rdev) RREG32(R_0007C0_CP_STAT)); }/* post */ -radeon_combios_asic_init (rdev->ddev); +radeon_combios_asic_init (rdev_to_drm (rdev));/* Resume clock after posting */ r300_clock_startup (rdev);/* Initialize surface registers */
@@ -551,7 +551,7 @@ int rs400_init(struct radeon_device *rdev)return -EINVAL ;/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize memory controller */ rs400_mc_init (rdev);/* Fence driver */
drivers/gpu/drm/radeon/rs600.c +7 -7
@@ -322,7 +322,7 @@ void rs600_pm_misc(struct radeon_device *rdev)void rs600_pm_prepare (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 tmp;
@@ -340,7 +340,7 @@ void rs600_pm_prepare(struct radeon_device *rdev)void rs600_pm_finish (struct radeon_device *rdev) { -struct drm_device *ddev = rdev->ddev; +struct drm_device *ddev =rdev_to_drm (rdev);struct drm_crtc *crtc;struct radeon_crtc *radeon_crtc;u32 tmp;
@@ -409,7 +409,7 @@ void rs600_hpd_set_polarity(struct radeon_device *rdev,void rs600_hpd_init (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned enable =0 ;
@@ -436,7 +436,7 @@ void rs600_hpd_init(struct radeon_device *rdev)void rs600_hpd_fini (struct radeon_device *rdev) { -struct drm_device *dev = rdev->ddev; +struct drm_device *dev =rdev_to_drm (rdev);struct drm_connector *connector;unsigned disable =0 ;
@@ -798,7 +798,7 @@ int rs600_irq_process(struct radeon_device *rdev)/* Vertical blank interrupts */ if (G_007EDC_LB_D1_VBLANK_INTERRUPT (rdev->irq.stat_regs.r500.disp_int)) {if (rdev->irq.crtc_vblank_int[0 ]) { -drm_handle_vblank (rdev->ddev,0 ); +drm_handle_vblank (rdev_to_drm (rdev),0 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -807,7 +807,7 @@ int rs600_irq_process(struct radeon_device *rdev) }if (G_007EDC_LB_D2_VBLANK_INTERRUPT (rdev->irq.stat_regs.r500.disp_int)) {if (rdev->irq.crtc_vblank_int[1 ]) { -drm_handle_vblank (rdev->ddev,1 ); +drm_handle_vblank (rdev_to_drm (rdev),1 ); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -1134,7 +1134,7 @@ int rs600_init(struct radeon_device *rdev)return -EINVAL ;/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize memory controller */ rs600_mc_init (rdev);r100_debugfs_rbbm_init (rdev);
drivers/gpu/drm/radeon/rs690.c +1 -1
@@ -845,7 +845,7 @@ int rs690_init(struct radeon_device *rdev)return -EINVAL ;/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize memory controller */ rs690_mc_init (rdev);rv515_debugfs (rdev);
drivers/gpu/drm/radeon/rv515.c +2 -2
@@ -255,7 +255,7 @@ DEFINE_SHOW_ATTRIBUTE(rv515_debugfs_ga_info);void rv515_debugfs (struct radeon_device *rdev) {#if defined(CONFIG_DEBUG_FS ) -struct dentry *root = rdev->ddev->primary->debugfs_root; +struct dentry *root =rdev_to_drm (rdev)->primary->debugfs_root;debugfs_create_file ("rv515_pipes_info" ,0444 , root, rdev, &rv515_debugfs_pipes_info_fops);
@@ -636,7 +636,7 @@ int rv515_init(struct radeon_device *rdev)if (radeon_boot_test_post_card (rdev) == false)return -EINVAL ;/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* initialize AGP */ if (rdev->flags &RADEON_IS_AGP ) { r =radeon_agp_init (rdev);
drivers/gpu/drm/radeon/rv770.c +1 -1
@@ -1935,7 +1935,7 @@ int rv770_init(struct radeon_device *rdev)/* Initialize surface registers */ radeon_surface_init (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* Fence driver */ radeon_fence_driver_init (rdev);/* initialize AGP */
drivers/gpu/drm/radeon/si.c +2 -2
@@ -6296,7 +6296,7 @@ int si_irq_process(struct radeon_device *rdev) event_name ="vblank" ;if (rdev->irq.crtc_vblank_int[crtc_idx]) { -drm_handle_vblank (rdev->ddev, crtc_idx); +drm_handle_vblank (rdev_to_drm (rdev), crtc_idx); rdev->pm.vblank_sync = true;wake_up (&rdev->irq.vblank_queue); }
@@ -6858,7 +6858,7 @@ int si_init(struct radeon_device *rdev)/* Initialize surface registers */ radeon_surface_init (rdev);/* Initialize clocks */ -radeon_get_clock_info (rdev->ddev); +radeon_get_clock_info (rdev_to_drm (rdev));/* Fence driver */ radeon_fence_driver_init (rdev);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 438/676 drm/radeon: Fix spurious unplug event on radeon HDMI
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Steven 'Steve' Kendall <[email protected]>
[ Upstream commit 7037bb04265ef05c6ffad56d884b0df76f57b095 ]
On several HP models (tested on HP 3125 and HP Probook 455 G2), spurious unplug events are emitted upon login on Chrome OS. This is likely due to the way Chrome OS restarts graphics upon login, so it's possible it's an issue on other distributions but not as common, though I haven't reproduced the issue elsewhere.
Use logic from an earlier version of the merged change (see link below) which iterates over connectors and finds matching encoders, rather than the other way around. Also fixes an issue with screen mirroring on Chrome OS. I've deployed this patch on Fedora and did not observe any regression on these devices.
--- drivers/gpu/drm/radeon/radeon_audio.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-)
drivers/gpu/drm/radeon/radeon_audio.c +8 -4
@@ -758,16 +758,20 @@ static int radeon_audio_component_get_eld(struct device *kdev, int port,if (!rdev->audio.enabled || !rdev->mode_info.mode_config_initialized)return 0 ; -list_for_each_entry (encoder, &rdev_to_drm (rdev)->mode_config.encoder_list, head) { +list_for_each_entry (connector, &dev->mode_config.connector_list, head) { +const struct drm_connector_helper_funcs *connector_funcs = + connector->helper_private; + encoder = connector_funcs->best_encoder (connector); + +if (!encoder) +continue ; +if (!radeon_encoder_is_digital (encoder))continue ; radeon_encoder =to_radeon_encoder (encoder); dig = radeon_encoder->enc_priv;if (!dig->pin || dig->pin->id != port)continue ; - connector =radeon_get_connector_for_encoder (encoder); -if (!connector) -continue ; *enabled = true; ret =drm_eld_size (connector->eld);memcpy (buf, connector->eld,min (max_bytes, ret));
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 439/676 drm/amd/display: Fix null check for pipe_ctx->plane_state in hwss_setup_dpp
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zicheng Qu <[email protected]>
[ Upstream commit 2bc96c95070571c6c824e0d4c7783bee25a37876 ]
This commit addresses a null pointer dereference issue in hwss_setup_dpp(). The issue could occur when pipe_ctx->plane_state is null. The fix adds a check to ensure pipe_ctx->plane_state is not null before accessing. This prevents a null pointer dereference.
--- drivers/gpu/drm/amd/display/dc/core/dc_hw_sequencer.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/gpu/drm/amd/display/dc/core/dc_hw_sequencer.c +3 -0
@@ -727,6 +727,9 @@ void hwss_setup_dpp(union block_sequence_params *params)struct dpp *dpp = pipe_ctx->plane_res.dpp;struct dc_plane_state *plane_state = pipe_ctx->plane_state; +if (!plane_state) +return ; +if (dpp && dpp->funcs->dpp_setup) {// program the input csc dpp->funcs->dpp_setup(dpp,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 440/676 apparmor: fix Do simple duplicate message elimination
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: chao liu <[email protected]>
[ Upstream commit 9b897132424fe76bf6c61f22f9cf12af7f1d1e6a ]
Multiple profiles shared 'ent->caps', so some logs missed.
--- security/apparmor/capability.c | 2 ++ 1 file changed, 2 insertions(+)
security/apparmor/capability.c +2 -0
@@ -96,6 +96,8 @@ static int audit_caps(struct apparmor_audit_data *ad, struct aa_profile *profilereturn error; }else {aa_put_profile (ent->profile); +if (profile != ent->profile) +cap_clear (ent->caps); ent->profile =aa_get_profile (profile);cap_raise (ent->caps, cap); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 441/676 ASoC: amd: yc: Fix for enabling DMIC on acp6x via _DSD entry
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Venkata Prasad Potturu <[email protected]>
[ Upstream commit 4095cf872084ecfdfdb0e681f3e9ff9745acfa75 ]
Add condition check to register ACP PDM sound card by reading _WOV acpi entry.
--- sound/soc/amd/yc/acp6x-mach.c | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-)
sound/soc/amd/yc/acp6x-mach.c +17 -1
@@ -537,8 +537,14 @@ static int acp6x_probe(struct platform_device *pdev)struct acp6x_pdm *machine =NULL ;struct snd_soc_card *card;struct acpi_device *adev; +acpi_handle handle; +acpi_integer dmic_status;int ret; +bool is_dmic_enable, wov_en; +/* IF WOV entry not found, enable dmic based on AcpDmicConnected entry*/ + is_dmic_enable = false; + wov_en = true;/* check the parent device's firmware node has _DSD or not */ adev =ACPI_COMPANION (pdev->dev.parent);if (adev) {
@@ -546,9 +552,19 @@ static int acp6x_probe(struct platform_device *pdev)if (!acpi_dev_get_property (adev,"AcpDmicConnected" ,ACPI_TYPE_INTEGER , &obj) && obj->integer.value ==1 ) -platform_set_drvdata (pdev, &acp6x_card); + is_dmic_enable = true; } + handle =ACPI_HANDLE (pdev->dev.parent); + ret =acpi_evaluate_integer (handle,"_WOV" ,NULL , &dmic_status); +if (!ACPI_FAILURE (ret)) + wov_en = dmic_status; + +if (is_dmic_enable && wov_en) +platform_set_drvdata (pdev, &acp6x_card); +else +return 0 ; +/* check for any DMI overrides */ dmi_id =dmi_first_match (yc_acp_quirk_table);if (dmi_id)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 442/676 gfs2: Dont set GLF_LOCK in gfs2_dispose_glock_lru
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andreas Gruenbacher <[email protected]>
[ Upstream commit 927cfc90d27cb7732a62464f95fd9aa7edfa9b70 ]
In gfs2_dispose_glock_lru(), we want to skip glocks which are in the process of transitioning state (as indicated by the set GLF_LOCK flag), but we we don't need to set that flag for requesting a state transition.
Stable-dep-of: 1e86044402c4 ("gfs2: Remove and replace gfs2_glock_queue_work")
--- fs/gfs2/glock.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
fs/gfs2/glock.c +1 -2
@@ -2018,14 +2018,13 @@ __acquires(&lru_lock)atomic_inc (&lru_count);continue ; } -if (test_and_set_bit (GLF_LOCK , &gl->gl_flags)) { +if (test_bit (GLF_LOCK , &gl->gl_flags)) {spin_unlock (&gl->gl_lockref.lock); goto add_back_to_lru; } gl->gl_lockref.count++;if (demote_ok (gl))handle_callback (gl,LM_ST_UNLOCKED ,0 , false); -WARN_ON (!test_and_clear_bit (GLF_LOCK , &gl->gl_flags));__gfs2_glock_queue_work (gl,0 );spin_unlock (&gl->gl_lockref.lock);cond_resched_lock (&lru_lock);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 443/676 gfs2: Remove and replace gfs2_glock_queue_work
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andreas Gruenbacher <[email protected]>
[ Upstream commit 1e86044402c45b70a9b31beeaefb5cc732a7470c ]
There are no more callers of gfs2_glock_queue_work() left, so remove that helper. With that, we can now rename __gfs2_glock_queue_work() back to gfs2_glock_queue_work() to get rid of some unnecessary clutter.
--- fs/gfs2/glock.c | 35 +++++++++++++++-------------------- 1 file changed, 15 insertions(+), 20 deletions(-)
fs/gfs2/glock.c +15 -20
@@ -274,7 +274,7 @@ static void gfs2_glock_remove_from_lru(struct gfs2_glock *gl)* Enqueue the glock on the work queue. Passes one glock reference on to the * work queue. */ -static void __gfs2_glock_queue_work (struct gfs2_glock *gl,unsigned long delay) { +static void gfs2_glock_queue_work (struct gfs2_glock *gl,unsigned long delay) {if (!queue_delayed_work (glock_workqueue, &gl->gl_work, delay)) {/* * We are holding the lockref spinlock, and the work was still
@@ -287,12 +287,6 @@ static void __gfs2_glock_queue_work(struct gfs2_glock *gl, unsigned long delay) } } -static void gfs2_glock_queue_work (struct gfs2_glock *gl,unsigned long delay) { -spin_lock (&gl->gl_lockref.lock); -__gfs2_glock_queue_work (gl, delay); -spin_unlock (&gl->gl_lockref.lock); -} -static void __gfs2_glock_put (struct gfs2_glock *gl) {struct gfs2_sbd *sdp = gl->gl_name.ln_sbd;
@@ -337,7 +331,8 @@ void gfs2_glock_put_async(struct gfs2_glock *gl)if (lockref_put_or_lock (&gl->gl_lockref))return ; -__gfs2_glock_queue_work (gl,0 ); +GLOCK_BUG_ON (gl, gl->gl_lockref.count !=1 ); +gfs2_glock_queue_work (gl,0 );spin_unlock (&gl->gl_lockref.lock); }
@@ -814,7 +809,7 @@ __acquires(&gl->gl_lockref.lock)*/ clear_bit (GLF_LOCK , &gl->gl_flags);clear_bit (GLF_DEMOTE_IN_PROGRESS , &gl->gl_flags); -__gfs2_glock_queue_work (gl,GL_GLOCK_DFT_HOLD ); +gfs2_glock_queue_work (gl,GL_GLOCK_DFT_HOLD );return ; }else {clear_bit (GLF_INVALIDATE_IN_PROGRESS , &gl->gl_flags);
@@ -844,7 +839,7 @@ __acquires(&gl->gl_lockref.lock)/* Complete the operation now. */ finish_xmote (gl, target); -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 ); }/**
@@ -891,7 +886,7 @@ __acquires(&gl->gl_lockref.lock)clear_bit (GLF_LOCK , &gl->gl_flags);smp_mb__after_atomic (); gl->gl_lockref.count++; -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 );return ; out_unlock:
@@ -1124,12 +1119,12 @@ static void glock_work_func(struct work_struct *work) drop_refs--;if (gl->gl_name.ln_type !=LM_TYPE_INODE ) delay =0 ; -__gfs2_glock_queue_work (gl, delay); +gfs2_glock_queue_work (gl, delay); }/* * Drop the remaining glock references manually here. (Mind that -* __gfs2_glock_queue_work depends on the lockref spinlock begin held +* gfs2_glock_queue_work depends on the lockref spinlock begin held * here as well.) */ gl->gl_lockref.count -= drop_refs;
@@ -1616,7 +1611,7 @@ int gfs2_glock_nq(struct gfs2_holder *gh) test_and_clear_bit(GLF_FROZEN, &gl->gl_flags))) {set_bit (GLF_REPLY_PENDING , &gl->gl_flags); gl->gl_lockref.count++; -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 ); }run_queue (gl,1 );spin_unlock (&gl->gl_lockref.lock);
@@ -1681,7 +1676,7 @@ static void __gfs2_glock_dq(struct gfs2_holder *gh) !test_bit(GLF_DEMOTE, &gl->gl_flags) && gl->gl_name.ln_type == LM_TYPE_INODE) delay = gl->gl_hold_time; -__gfs2_glock_queue_work (gl, delay); +gfs2_glock_queue_work (gl, delay); } }
@@ -1905,7 +1900,7 @@ void gfs2_glock_cb(struct gfs2_glock *gl, unsigned int state) delay = gl->gl_hold_time; }handle_callback (gl, state, delay, true); -__gfs2_glock_queue_work (gl, delay); +gfs2_glock_queue_work (gl, delay);spin_unlock (&gl->gl_lockref.lock); }
@@ -1965,7 +1960,7 @@ void gfs2_glock_complete(struct gfs2_glock *gl, int ret) gl->gl_lockref.count++;set_bit (GLF_REPLY_PENDING , &gl->gl_flags); -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 );spin_unlock (&gl->gl_lockref.lock); }
@@ -2025,7 +2020,7 @@ __acquires(&lru_lock) gl->gl_lockref.count++;if (demote_ok (gl))handle_callback (gl,LM_ST_UNLOCKED ,0 , false); -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 );spin_unlock (&gl->gl_lockref.lock);cond_resched_lock (&lru_lock); }
@@ -2163,7 +2158,7 @@ static void thaw_glock(struct gfs2_glock *gl)spin_lock (&gl->gl_lockref.lock);set_bit (GLF_REPLY_PENDING , &gl->gl_flags); -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 );spin_unlock (&gl->gl_lockref.lock); }
@@ -2182,7 +2177,7 @@ static void clear_glock(struct gfs2_glock *gl) gl->gl_lockref.count++;if (gl->gl_state !=LM_ST_UNLOCKED )handle_callback (gl,LM_ST_UNLOCKED ,0 , false); -__gfs2_glock_queue_work (gl,0 ); +gfs2_glock_queue_work (gl,0 ); }spin_unlock (&gl->gl_lockref.lock); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 444/676 f2fs: fix fiemap failure issue when page size is 16KB
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Xiuhong Wang <[email protected]>
commit a7a7c1d423a6351a6541e95c797da5358e5ad1ea upstream.
After enable 16K page size, an infinite loop may occur in fiemap (fm_length=UINT64_MAX) on a file, such as the 16KB scratch.img during the remount operation in Android.
The condition for whether fiemap continues to map is to check whether the number of bytes corresponding to the next map.m_lblk exceeds blks_to_bytes(inode,max_inode_blocks(inode)) if there are HOLE. The latter does not take into account the maximum size of a file with 16KB page size, so the loop cannot be jumped out.
The following is the fail trace:
When f2fs_map_blocks reaches map.m_lblk=3936, it needs to go to the first direct node block, so the map is 3936 + 4090 = 8026, The next map is the second direct node block, that is, 8026 + 4090 = 12116,
The next map is the first indirect node block, that is, 12116 + 4090 * 4090 = 16740216,
The next map is the second indirect node block, that is, 16740216 + 4090 * 4090 = 33468316,
The next map is the first double indirect node block, that is, 33468316 + 4090 * 4090 * 4090 = 68451397316
Since map.m_lblk represents the address of a block, which is 32 bits, truncation will occur, that is, 68451397316 becomes 4026887876, and the number of bytes corresponding to the block number does not exceed blks_to_bytes(inode,max_inode_blocks(inode)), so the loop will not be jumped out.
The next time, it will be considered that it should still be a double indirect node block, that is,
4026887876 + 4090 * 4090 * 4090 = 72444816876, which will be truncated to 3725340140, and the loop will not be jumped out.
156.374871: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 0, start blkaddr = 0x8e00, len = 0x200, flags = 2,seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.374916: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 512, start blkaddr = 0x0, len = 0x0, flags = 0 , seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.374920: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 513, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0
......
156.385747: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 3935, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385752: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 3936, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385755: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 8026, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385758: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 12116, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385761: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 16740216, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385764: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 33468316, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385767: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 4026887876, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385770: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 3725340140, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385772: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 4026887876, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0 156.385775: f2fs_map_blocks: dev = (254,57), ino = 7449, file offset = 3725340140, start blkaddr = 0x0, len = 0x0, flags = 0, seg_type = 8, may_create = 0, multidevice = 0, flag = 1, err = 0
Commit a6a010f5def5 ("f2fs: Restrict max filesize for 16K f2fs") has set the maximum allowed file size to (U32_MAX + 1) * F2FS_BLKSIZE, so max_file_blocks should be used here to limit it, that is, maxbytes defined above. And the max_inode_blocks function is not called by other functions except here, so cleanup it.
--- fs/f2fs/data.c | 22 +--------------------- 1 file changed, 1 insertion(+), 21 deletions(-)
fs/f2fs/data.c +1 -21
@@ -1873,25 +1873,6 @@ static int f2fs_xattr_fiemap(struct inodreturn (err <0 ? err :0 ); } -static loff_t max_inode_blocks (struct inode *inode) -{ -loff_t result =ADDRS_PER_INODE (inode); -loff_t leaf_count =ADDRS_PER_BLOCK (inode); - -/* two direct node blocks */ - result += (leaf_count *2 ); - -/* two indirect node blocks */ - leaf_count *=NIDS_PER_BLOCK ; - result += (leaf_count *2 ); - -/* one double indirect node block */ - leaf_count *=NIDS_PER_BLOCK ; - result += leaf_count; - -return result; -} -int f2fs_fiemap (struct inode *inode,struct fiemap_extent_info *fieinfo,u64 start,u64 len) {
@@ -1964,8 +1945,7 @@ next:if (!compr_cluster && !(map.m_flags &F2FS_MAP_FLAGS )) { start_blk = next_pgofs; -if (blks_to_bytes (inode, start_blk) <blks_to_bytes (inode, -max_inode_blocks (inode))) +if (blks_to_bytes (inode, start_blk) < maxbytes) goto prep_next; flags |=FIEMAP_EXTENT_LAST ;
Greg Kroah-Hartman
maintainerPATCH 445/676 mailbox: mtk-cmdq: Move devm_mbox_controller_register() after devm_pm_runtime_enable()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jason-JH.Lin <[email protected]>
commit a8bd68e4329f9a0ad1b878733e0f80be6a971649 upstream.
When mtk-cmdq unbinds, a WARN_ON message with condition pm_runtime_get_sync() < 0 occurs.
According to the call tracei below:
cmdq_mbox_shutdown
mbox_free_channel
mbox_controller_unregister
__devm_mbox_controller_unregister
...
The root cause can be deduced to be calling pm_runtime_get_sync() after calling pm_runtime_disable() as observed below:
1. CMDQ driver uses devm_mbox_controller_register() in cmdq_probe() to bind the cmdq device to the mbox_controller, so devm_mbox_controller_unregister() will automatically unregister the device bound to the mailbox controller when the device-managed resource is removed. That means devm_mbox_controller_unregister() and cmdq_mbox_shoutdown() will be called after cmdq_remove().
2. CMDQ driver also uses devm_pm_runtime_enable() in cmdq_probe() after devm_mbox_controller_register(), so that devm_pm_runtime_disable() will be called after cmdq_remove(), but before devm_mbox_controller_unregister().
To fix this problem, cmdq_probe() needs to move devm_mbox_controller_register() after devm_pm_runtime_enable() to make devm_pm_runtime_disable() be called after devm_mbox_controller_unregister().
--- drivers/mailbox/mtk-cmdq-mailbox.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-)
drivers/mailbox/mtk-cmdq-mailbox.c +6 -6
@@ -623,12 +623,6 @@ static int cmdq_probe(struct platform_de cmdq->mbox.chans[i].con_priv = (void *)&cmdq->thread[i]; } - err =devm_mbox_controller_register (dev, &cmdq->mbox); -if (err <0 ) { -dev_err (dev,"failed to register mailbox: %d\n" , err); -return err; - } -platform_set_drvdata (pdev, cmdq);WARN_ON (clk_bulk_prepare (cmdq->pdata->gce_num, cmdq->clocks));
@@ -642,6 +636,12 @@ static int cmdq_probe(struct platform_dereturn err; } + err =devm_mbox_controller_register (dev, &cmdq->mbox); +if (err <0 ) { +dev_err (dev,"failed to register mailbox: %d\n" , err); +return err; + } +return 0 ; }
Greg Kroah-Hartman
maintainerPATCH 446/676 scsi: lpfc: Validate hdwq pointers before dereferencing in reset/errata paths
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Justin Tee <[email protected]>
commit 2be1d4f11944cd6283cb97268b3e17c4424945ca upstream.
When the HBA is undergoing a reset or is handling an errata event, NULL ptr dereference crashes may occur in routines such as lpfc_sli_flush_io_rings(), lpfc_dev_loss_tmo_callbk(), or lpfc_abort_handler().
Add NULL ptr checks before dereferencing hdwq pointers that may have been freed due to operations colliding with a reset or errata event handler.
--- drivers/scsi/lpfc/lpfc_hbadisc.c | 3 ++- drivers/scsi/lpfc/lpfc_scsi.c | 13 +++++++++++-- drivers/scsi/lpfc/lpfc_sli.c | 11 +++++++++++ 3 files changed, 24 insertions(+), 3 deletions(-)
drivers/scsi/lpfc/lpfc_hbadisc.c +2 -1
@@ -175,7 +175,8 @@ lpfc_dev_loss_tmo_callbk(struct fc_rport ndlp->nlp_state, ndlp->fc4_xpt_flags);/* Don't schedule a worker thread event if the vport is going down. */ -if (vport->load_flag &FC_UNLOADING ) { +if ((vport->load_flag &FC_UNLOADING ) || + !(phba->hba_flag &HBA_SETUP )) {spin_lock_irqsave (&ndlp->lock, iflags); ndlp->rport =NULL ;
drivers/scsi/lpfc/lpfc_scsi.c +11 -2
@@ -5546,11 +5546,20 @@ lpfc_abort_handler(struct scsi_cmnd *cmn iocb = &lpfc_cmd->cur_iocbq;if (phba->sli_rev ==LPFC_SLI_REV4 ) { - pring_s4 = phba->sli4_hba.hdwq[iocb->hba_wqidx].io_wq->pring; -if (!pring_s4) { +/* if the io_wq & pring are gone, the port was reset. */ +if (!phba->sli4_hba.hdwq[iocb->hba_wqidx].io_wq || + !phba->sli4_hba.hdwq[iocb->hba_wqidx].io_wq->pring) { +lpfc_printf_vlog (vport,KERN_WARNING ,LOG_FCP , +"2877 SCSI Layer I/O Abort Request " +"IO CMPL Status x%x ID %d LUN %llu " +"HBA_SETUP %d\n" ,FAILED , + cmnd->device->id, + (u64 )cmnd->device->lun, + (HBA_SETUP & phba->hba_flag)); ret =FAILED ; goto out_unlock_hba; } + pring_s4 = phba->sli4_hba.hdwq[iocb->hba_wqidx].io_wq->pring;spin_lock (&pring_s4->ring_lock); }/* the command is in process of being cancelled */
drivers/scsi/lpfc/lpfc_sli.c +11 -0
@@ -4684,6 +4684,17 @@ lpfc_sli_flush_io_rings(struct lpfc_hba/* Look on all the FCP Rings for the iotag */ if (phba->sli_rev >=LPFC_SLI_REV4 ) {for (i =0 ; i < phba->cfg_hdw_queue; i++) { +if (!phba->sli4_hba.hdwq || + !phba->sli4_hba.hdwq[i].io_wq) { +lpfc_printf_log (phba,KERN_ERR ,LOG_SLI , +"7777 hdwq's deleted %lx " +"%lx %x %x\n" , + (unsigned long )phba->pport->load_flag, + (unsigned long )phba->hba_flag, + phba->link_state, + phba->sli.sli_flag); +return ; + } pring = phba->sli4_hba.hdwq[i].io_wq->pring;spin_lock_irq (&pring->ring_lock);
Greg Kroah-Hartman
maintainerPATCH 447/676 nvme: fix metadata handling in nvme-passthrough
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Puranjay Mohan <[email protected]>
commit 7c2fd76048e95dd267055b5f5e0a48e6e7c81fd9 upstream.
On an NVMe namespace that does not support metadata, it is possible to send an IO command with metadata through io-passthru. This allows issues like [1] to trigger in the completion code path. nvme_map_user_request() doesn't check if the namespace supports metadata before sending it forward. It also allows admin commands with metadata to be processed as it ignores metadata when bdev == NULL and may report success.
Reject an IO command with metadata when the NVMe namespace doesn't support it and reject an admin command if it has metadata.
[1] https://lore.kernel.org/all/[email protected]/
--- drivers/nvme/host/ioctl.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
drivers/nvme/host/ioctl.c +7 -1
@@ -3,6 +3,7 @@* Copyright (c) 2011-2014, Intel Corporation. * Copyright (c) 2017-2021 Christoph Hellwig. */ +#include <linux/blk-integrity.h> #include <linux/ptrace.h> /* for force_successful_syscall_return */ #include <linux/nvme_ioctl.h> #include <linux/io_uring.h>
@@ -171,10 +172,15 @@ static int nvme_map_user_request(structstruct request_queue *q = req->q;struct nvme_ns *ns = q->queuedata;struct block_device *bdev = ns ? ns->disk->part0 :NULL ; +bool supports_metadata = bdev &&blk_get_integrity (bdev->bd_disk); +bool has_metadata = meta_buffer && meta_len;struct bio *bio =NULL ;void *meta =NULL ;int ret; +if (has_metadata && !supports_metadata) +return -EINVAL ; +if (ioucmd && (ioucmd->flags &IORING_URING_CMD_FIXED )) {struct iov_iter iter;
@@ -198,7 +204,7 @@ static int nvme_map_user_request(structif (bdev)bio_set_dev (bio, bdev); -if (bdev && meta_buffer && meta_len) { +if (has_metadata) { meta =nvme_add_user_metadata (req, meta_buffer, meta_len, meta_seed);if (IS_ERR (meta)) {
Greg Kroah-Hartman
maintainerPATCH 448/676 xfs: add bounds checking to xlog_recover_process_data
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: lei lu <[email protected]>
commit fb63435b7c7dc112b1ae1baea5486e0a6e27b196 upstream.
There is a lack of verification of the space occupied by fixed members of xlog_op_header in the xlog_recover_process_data.
We can create a crafted image to trigger an out of bounds read by following these steps:
1) Mount an image of xfs, and do some file operations to leave records
2) Before umounting, copy the image for subsequent steps to simulate abnormal exit. Because umount will ensure that tail_blk and head_blk are the same, which will result in the inability to enter xlog_recover_process_data
3) Write a tool to parse and modify the copied image in step 2
4) Make the end of the xlog_op_header entries only 1 byte away from xlog_rec_header->h_size
5) xlog_rec_header->h_num_logops++
6) Modify xlog_rec_header->h_crc
Fix:
Add a check to make sure there is sufficient space to access fixed members of xlog_op_header.
--- fs/xfs/xfs_log_recover.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
fs/xfs/xfs_log_recover.c +4 -1
@@ -2456,7 +2456,10 @@ xlog_recover_process_data( ohead = (struct xlog_op_header *)dp; dp +=sizeof (*ohead); -ASSERT (dp <= end); +if (dp > end) { +xfs_warn (log->l_mp,"%s: op header overrun" , __func__); +return -EFSCORRUPTED ; + }/* errors will abort recovery */ error = xlog_recover_process_ophdr(log, rhash, rhead, ohead,
Greg Kroah-Hartman
maintainerPATCH 449/676 xen: Fix the issue of resource not being properly released in xenbus_dev_probe()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Qiu-ji Chen <[email protected]>
commit afc545da381ba0c651b2658966ac737032676f01 upstream.
This patch fixes an issue in the function xenbus_dev_probe(). In the xenbus_dev_probe() function, within the if (err) branch at line 313, the program incorrectly returns err directly without releasing the resources allocated by err = drv->probe(dev, id). As the return value is non-zero, the upper layers assume the processing logic has failed. However, the probe operation was performed earlier without a corresponding remove operation. Since the probe actually allocates resources, failing to perform the remove operation could lead to problems.
To fix this issue, we followed the resource release logic of the xenbus_dev_remove() function by adding a new block fail_remove before the fail_put block. After entering the branch if (err) at line 313, the function will use a goto statement to jump to the fail_remove block, ensuring that the previously acquired resources are correctly released, thus preventing the reference count leak.
This bug was identified by an experimental static analysis tool developed by our team. The tool specializes in analyzing reference count operations and detecting potential issues where resources are not properly managed. In this case, the tool flagged the missing release operation as a potential problem, which led to the development of this patch.
Message-ID: <[email protected]>
--- drivers/xen/xenbus/xenbus_probe.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
drivers/xen/xenbus/xenbus_probe.c +7 -1
@@ -313,7 +313,7 @@ int xenbus_dev_probe(struct device *_devif (err) {dev_warn (&dev->dev,"watch_otherend on %s failed.\n" , dev->nodename); -return err; + goto fail_remove; } dev->spurious_threshold =1 ;
@@ -322,6 +322,12 @@ int xenbus_dev_probe(struct device *_dev dev->nodename);return 0 ; +fail_remove: +if (drv->remove) { +down (&dev->reclaim_sem); + drv->remove (dev); +up (&dev->reclaim_sem); + } fail_put:module_put (drv->driver.owner); fail:
Greg Kroah-Hartman
maintainerPATCH 450/676 ALSA: usb-audio: Fix out of bounds reads when finding clock sources
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Takashi Iwai <[email protected]>
commit a3dd4d63eeb452cfb064a13862fb376ab108f6a6 upstream.
The current USB-audio driver code doesn't check bLength of each descriptor at traversing for clock descriptors. That is, when a device provides a bogus descriptor with a shorter bLength, the driver might hit out-of-bounds reads.
For addressing it, this patch adds sanity checks to the validator functions for the clock descriptor traversal. When the descriptor length is shorter than expected, it's skipped in the loop.
For the clock source and clock multiplier descriptors, we can just check bLength against the sizeof() of each descriptor type. OTOH, the clock selector descriptor of UAC2 and UAC3 has an array of bNrInPins elements and two more fields at its tail, hence those have to be checked in addition to the sizeof() check.
--- sound/usb/clock.c | 24 +++++++++++++++++++++++- 1 file changed, 23 insertions(+), 1 deletion(-)
sound/usb/clock.c +23 -1
@@ -36,6 +36,12 @@ union uac23_clock_multiplier_desc {struct uac_clock_multiplier_descriptor v3; }; +/* check whether the descriptor bLength has the minimal length */ +#define DESC_LENGTH_CHECK (p, proto) \ + ((proto) == UAC_VERSION_3 ? \ + ((p)->v3.bLength >= sizeof((p)->v3)) : \ + ((p)->v2.bLength >= sizeof((p)->v2))) +#define GET_VAL (p, proto, field) \ ((proto) == UAC_VERSION_3 ? (p)->v3.field : (p)->v2.field)
@@ -58,6 +64,8 @@ static bool validate_clock_source(void * {union uac23_clock_source_desc *cs = p; +if (!DESC_LENGTH_CHECK (cs, proto)) +return false;return GET_VAL (cs, proto, bClockID) == id; }
@@ -65,13 +73,27 @@ static bool validate_clock_selector(void {union uac23_clock_selector_desc *cs = p; -return GET_VAL (cs, proto, bClockID) == id; +if (!DESC_LENGTH_CHECK (cs, proto)) +return false; +if (GET_VAL (cs, proto, bClockID) != id) +return false; +/* additional length check for baCSourceID array (in bNrInPins size) +* and two more fields (which sizes depend on the protocol) +*/ +if (proto ==UAC_VERSION_3 ) +return cs->v3.bLength >=sizeof (cs->v3) + cs->v3.bNrInPins + +4 /* bmControls */ +2 /* wCSelectorDescrStr */ ; +else +return cs->v2.bLength >=sizeof (cs->v2) + cs->v2.bNrInPins + +1 /* bmControls */ +1 /* iClockSelector */ ; }static bool validate_clock_multiplier (void *p,int id,int proto) {union uac23_clock_multiplier_desc *cs = p; +if (!DESC_LENGTH_CHECK (cs, proto)) +return false;return GET_VAL (cs, proto, bClockID) == id; }
Greg Kroah-Hartman
maintainerPATCH 451/676 usb: ehci-spear: fix call balance of sehci clk handling routines
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Vitalii Mordan <[email protected]>
commit 40c974826734836402abfd44efbf04f63a2cc1c1 upstream.
If the clock sehci->clk was not enabled in spear_ehci_hcd_drv_probe, it should not be disabled in any path.
Conversely, if it was enabled in spear_ehci_hcd_drv_probe, it must be disabled in all error paths to ensure proper cleanup.
Found by Linux Verification Center (linuxtesting.org) with Klever.
--- drivers/usb/host/ehci-spear.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/usb/host/ehci-spear.c +4 -3
@@ -105,7 +105,9 @@ static int spear_ehci_hcd_drv_probe(stru/* registers start at offset 0x0 */ hcd_to_ehci (hcd)->caps = hcd->regs; -clk_prepare_enable (sehci->clk); + retval =clk_prepare_enable (sehci->clk); +if (retval) + goto err_put_hcd; retval =usb_add_hcd (hcd, irq,IRQF_SHARED );if (retval) goto err_stop_ehci;
@@ -130,8 +132,7 @@ static void spear_ehci_hcd_drv_remove(stusb_remove_hcd (hcd); -if (sehci->clk) -clk_disable_unprepare (sehci->clk); +clk_disable_unprepare (sehci->clk);usb_put_hcd (hcd); }
Greg Kroah-Hartman
maintainerPATCH 452/676 closures: Change BUG_ON() to WARN_ON()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kent Overstreet <[email protected]>
commit 339b84ab6b1d66900c27bd999271cb2ae40ce812 upstream.
If a BUG_ON() can be hit in the wild, it shouldn't be a BUG_ON()
For reference, this has popped up once in the CI, and we'll need more info to debug it:
03240 ------------[ cut here ]------------
03240 kernel BUG at lib/closure.c:21!
03240 kernel BUG at lib/closure.c:21!
03240 Internal error: Oops - BUG: 00000000f2000800 [#1] SMP
03240 Modules linked in:
03240 CPU: 15 PID: 40534 Comm: kworker/u80:1 Not tainted 6.10.0-rc4-ktest-ga56da69799bd #25570 03240 Hardware name: linux,dummy-virt (DT)
03240 Workqueue: btree_update btree_interior_update_work
03240 pstate: 00001005 (nzcv daif -PAN -UAO -TCO -DIT +SSBS BTYPE=--)
03240 pc : closure_put+0x224/0x2a0
03240 lr : closure_put+0x24/0x2a0
03240 sp : ffff0000d12071c0
03240 x29: ffff0000d12071c0 x28: dfff800000000000 x27: ffff0000d1207360
03240 x26: 0000000000000040 x25: 0000000000000040 x24: 0000000000000040
03240 x23: ffff0000c1f20180 x22: 0000000000000000 x21: ffff0000c1f20168
03240 x20: 0000000040000000 x19: ffff0000c1f20140 x18: 0000000000000001
03240 x17: 0000000000003aa0 x16: 0000000000003ad0 x15: 1fffe0001c326974
03240 x14: 0000000000000a1e x13: 0000000000000000 x12: 1fffe000183e402d
03240 x11: ffff6000183e402d x10: dfff800000000000 x9 : ffff6000183e402e
03240 x8 : 0000000000000001 x7 : 00009fffe7c1bfd3 x6 : ffff0000c1f2016b
03240 x5 : ffff0000c1f20168 x4 : ffff6000183e402e x3 : ffff800081391954
03240 x2 : 0000000000000001 x1 : 0000000000000000 x0 : 00000000a8000000
03240 Call trace:
03240 closure_put+0x224/0x2a0 03240 bch2_check_for_deadlock+0x910/0x1028 03240 bch2_six_check_for_deadlock+0x1c/0x30 03240 six_lock_slowpath.isra.0+0x29c/0xed0 03240 six_lock_ip_waiter+0xa8/0xf8 03240 __bch2_btree_node_lock_write+0x14c/0x298 03240 bch2_trans_lock_write+0x6d4/0xb10 03240 __bch2_trans_commit+0x135c/0x5520 03240 btree_interior_update_work+0x1248/0x1c10 03240 process_scheduled_works+0x53c/0xd90 03240 worker_thread+0x370/0x8c8 03240 kthread+0x258/0x2e8 03240 ret_from_fork+0x10/0x20
03240 Code: aa1303e0 d63f0020 a94363f7 17ffff8c (d4210000) 03240 ---[ end trace 0000000000000000 ]---
03240 Kernel panic - not syncing: Oops - BUG: Fatal exception 03240 SMP: stopping secondary CPUs
03241 SMP: failed to stop secondary CPUs 13,15
03241 Kernel Offset: disabled
03241 CPU features: 0x00,00000003,80000008,4240500b
03241 Memory Limit: none
03241 ---[ end Kernel panic - not syncing: Oops - BUG: Fatal exception ]--- 03246 ========= FAILED TIMEOUT copygc_torture_no_checksum in 7200s
--- drivers/md/bcache/closure.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-)
drivers/md/bcache/closure.c +8 -2
@@ -17,10 +17,16 @@ static inline void closure_put_after_sub {int r = flags &CLOSURE_REMAINING_MASK ; -BUG_ON (flags &CLOSURE_GUARD_MASK ); -BUG_ON (!r && (flags & ~CLOSURE_DESTRUCTOR )); +if (WARN (flags &CLOSURE_GUARD_MASK , +"closure has guard bits set: %x (%u)" , + flags &CLOSURE_GUARD_MASK , (unsigned )__fls (r))) + r &= ~CLOSURE_GUARD_MASK ;if (!r) { +WARN (flags & ~CLOSURE_DESTRUCTOR , +"closure ref hit 0 with incorrect flags set: %x (%u)" , + flags & ~CLOSURE_DESTRUCTOR , (unsigned )__fls (flags)); +if (cl->fn && !(flags &CLOSURE_DESTRUCTOR )) {atomic_set (&cl->remaining,CLOSURE_REMAINING_INITIALIZER );
Greg Kroah-Hartman
maintainerPATCH 453/676 dm-cache: fix warnings about duplicate slab caches
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mikulas Patocka <[email protected]>
commit 346dbf1b1345476a6524512892cceb931bee3039 upstream.
The commit 4c39529663b9 adds a warning about duplicate cache names if CONFIG_DEBUG_VM is selected. These warnings are triggered by the dm-cache code.
The dm-cache code allocates a slab cache for each device. This commit changes it to allocate just one slab cache in the module init function.
--- drivers/md/dm-cache-background-tracker.c | 25 ++++++------------------- drivers/md/dm-cache-background-tracker.h | 8 ++++++++ drivers/md/dm-cache-target.c | 25 ++++++++++++++++++++----- 3 files changed, 34 insertions(+), 24 deletions(-)
drivers/md/dm-cache-background-tracker.c +6 -19
@@ -11,12 +11,6 @@#define DM_MSG_PREFIX "dm-background-tracker" -struct bt_work { -struct list_head list; -struct rb_node node; -struct policy_work work; -}; -struct background_tracker {unsigned int max_work;atomic_t pending_promotes;
@@ -26,10 +20,10 @@ struct background_tracker {struct list_head issued;struct list_head queued;struct rb_root pending; - -struct kmem_cache *work_cache; }; +struct kmem_cache *btracker_work_cache =NULL ; +struct background_tracker *btracker_create (unsigned int max_work) {struct background_tracker *b =kmalloc (sizeof (*b),GFP_KERNEL );
@@ -48,12 +42,6 @@ struct background_tracker *btracker_creaINIT_LIST_HEAD (&b->queued); b->pending =RB_ROOT ; - b->work_cache =KMEM_CACHE (bt_work,0 ); -if (!b->work_cache) { -DMERR ("couldn't create mempool for background work items" ); -kfree (b); - b =NULL ; - }return b; }
@@ -66,10 +54,9 @@ void btracker_destroy(struct background_BUG_ON (!list_empty (&b->issued)); list_for_each_entry_safe (w, tmp, &b->queued, list) {list_del (&w->list); -kmem_cache_free (b->work_cache, w); +kmem_cache_free (btracker_work_cache, w); } -kmem_cache_destroy (b->work_cache);kfree (b); }EXPORT_SYMBOL_GPL (btracker_destroy);
@@ -180,7 +167,7 @@ static struct bt_work *alloc_work(structif (max_work_reached (b))return NULL ; -return kmem_cache_alloc (b->work_cache,GFP_NOWAIT ); +return kmem_cache_alloc (btracker_work_cache,GFP_NOWAIT ); } int btracker_queue(struct background_tracker *b,
@@ -203,7 +190,7 @@ int btracker_queue(struct background_tra* There was a race, we'll just ignore this second * bit of work for the same oblock. */ -kmem_cache_free (b->work_cache, w); +kmem_cache_free (btracker_work_cache, w);return -EINVAL ; }
@@ -244,7 +231,7 @@ void btracker_complete(struct backgroundupdate_stats (b, &w->work,-1 );rb_erase (&w->node, &b->pending);list_del (&w->list); -kmem_cache_free (b->work_cache, w); +kmem_cache_free (btracker_work_cache, w); }EXPORT_SYMBOL_GPL (btracker_complete);
drivers/md/dm-cache-background-tracker.h +8 -0
@@ -26,6 +26,14 @@* protected with a spinlock. */ +struct bt_work { +struct list_head list; +struct rb_node node; +struct policy_work work; +}; + +extern struct kmem_cache *btracker_work_cache; +struct background_work ;struct background_tracker ;
drivers/md/dm-cache-target.c +20 -5
@@ -10,6 +10,7 @@#include "dm-bio-record.h" #include "dm-cache-metadata.h" #include "dm-io-tracker.h" +#include "dm-cache-background-tracker.h" #include <linux/dm-io.h> #include <linux/dm-kcopyd.h>
@@ -2267,7 +2268,7 @@ static int parse_cache_args(struct cache/*----------------------------------------------------------------*/ -static struct kmem_cache *migration_cache; +static struct kmem_cache *migration_cache =NULL ;#define NOT_CORE_OPTION 1
@@ -3455,22 +3456,36 @@ static int __init dm_cache_init(void)int r; migration_cache =KMEM_CACHE (dm_cache_migration,0 ); -if (!migration_cache) -return -ENOMEM ; +if (!migration_cache) { + r = -ENOMEM ; + goto err; + } + + btracker_work_cache =kmem_cache_create ("dm_cache_bt_work" , +sizeof (struct bt_work ), __alignof__(struct bt_work ),0 ,NULL ); +if (!btracker_work_cache) { + r = -ENOMEM ; + goto err; + } r =dm_register_target (&cache_target);if (r) { -kmem_cache_destroy (migration_cache); -return r; + goto err; }return 0 ; + +err: +kmem_cache_destroy (migration_cache); +kmem_cache_destroy (btracker_work_cache); +return r; } static void __exit dm_cache_exit(void) {dm_unregister_target (&cache_target);kmem_cache_destroy (migration_cache); +kmem_cache_destroy (btracker_work_cache); }module_init (dm_cache_init);
Greg Kroah-Hartman
maintainerPATCH 454/676 drm/amd/display: Add NULL check for clk_mgr and clk_mgr->funcs in dcn30_init_hw
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Srinivasan Shanmugam <[email protected]>
commit cba7fec864172dadd953daefdd26e01742b71a6a upstream.
This commit addresses a potential null pointer dereference issue in the dcn30_init_hw function. The issue could occur when dc->clk_mgr or dc->clk_mgr->funcs is null.
The fix adds a check to ensure dc->clk_mgr and dc->clk_mgr->funcs is not null before accessing its functions. This prevents a potential null pointer dereference.
Reported by smatch:drivers/gpu/drm/amd/amdgpu/../display/dc/hwss/dcn30/dcn30_hwseq.c:789 dcn30_init_hw() error: we previously assumed 'dc->clk_mgr' could be null (see line 628)
--- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c +4 -3
@@ -440,7 +440,7 @@ void dcn30_init_hw(struct dc *dc)int edp_num;uint32_t backlight =MAX_BACKLIGHT_LEVEL ; -if (dc->clk_mgr && dc->clk_mgr->funcs->init_clocks) +if (dc->clk_mgr && dc->clk_mgr->funcs && dc->clk_mgr->funcs->init_clocks) dc->clk_mgr->funcs->init_clocks (dc->clk_mgr);// Initialize the dccg
@@ -599,11 +599,12 @@ void dcn30_init_hw(struct dc *dc)if (!dcb->funcs->is_accelerated_mode (dcb) && dc->res_pool->hubbub->funcs->init_watermarks) dc->res_pool->hubbub->funcs->init_watermarks (dc->res_pool->hubbub); -if (dc->clk_mgr->funcs->notify_wm_ranges) +if (dc->clk_mgr && dc->clk_mgr->funcs && dc->clk_mgr->funcs->notify_wm_ranges) dc->clk_mgr->funcs->notify_wm_ranges (dc->clk_mgr);//if softmax is enabled then hardmax will be set by a different call -if (dc->clk_mgr->funcs->set_hard_max_memclk && !dc->clk_mgr->dc_mode_softmax_enabled) +if (dc->clk_mgr && dc->clk_mgr->funcs && dc->clk_mgr->funcs->set_hard_max_memclk && + !dc->clk_mgr->dc_mode_softmax_enabled) dc->clk_mgr->funcs->set_hard_max_memclk (dc->clk_mgr);if (dc->res_pool->hubbub->funcs->force_pstate_change_control)
Greg Kroah-Hartman
maintainerPATCH 455/676 drm/amd/display: Add NULL check for clk_mgr in dcn32_init_hw
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Srinivasan Shanmugam <[email protected]>
commit c395fd47d1565bd67671f45cca281b3acc2c31ef upstream.
This commit addresses a potential null pointer dereference issue in the dcn32_init_hw function. The issue could occur when dc->clk_mgr is null.
The fix adds a check to ensure dc->clk_mgr is not null before accessing its functions. This prevents a potential null pointer dereference.
Reported by smatch:drivers/gpu/drm/amd/amdgpu/../display/dc/hwss/dcn32/dcn32_hwseq.c:961 dcn32_init_hw() error: we previously assumed 'dc->clk_mgr' could be null (see line 782)
--- drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c +4 -3
@@ -773,7 +773,7 @@ void dcn32_init_hw(struct dc *dc)int edp_num;uint32_t backlight =MAX_BACKLIGHT_LEVEL ; -if (dc->clk_mgr && dc->clk_mgr->funcs->init_clocks) +if (dc->clk_mgr && dc->clk_mgr->funcs && dc->clk_mgr->funcs->init_clocks) dc->clk_mgr->funcs->init_clocks (dc->clk_mgr);// Initialize the dccg
@@ -950,10 +950,11 @@ void dcn32_init_hw(struct dc *dc)if (!dcb->funcs->is_accelerated_mode (dcb) && dc->res_pool->hubbub->funcs->init_watermarks) dc->res_pool->hubbub->funcs->init_watermarks (dc->res_pool->hubbub); -if (dc->clk_mgr->funcs->notify_wm_ranges) +if (dc->clk_mgr && dc->clk_mgr->funcs && dc->clk_mgr->funcs->notify_wm_ranges) dc->clk_mgr->funcs->notify_wm_ranges (dc->clk_mgr); -if (dc->clk_mgr->funcs->set_hard_max_memclk && !dc->clk_mgr->dc_mode_softmax_enabled) +if (dc->clk_mgr && dc->clk_mgr->funcs && dc->clk_mgr->funcs->set_hard_max_memclk && + !dc->clk_mgr->dc_mode_softmax_enabled) dc->clk_mgr->funcs->set_hard_max_memclk (dc->clk_mgr);if (dc->res_pool->hubbub->funcs->force_pstate_change_control)
Greg Kroah-Hartman
maintainerPATCH 456/676 drm/amd/display: Check null pointer before try to access it
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Rodrigo Siqueira <[email protected]>
commit 1b686053c06ffb9f4524b288110cf2a831ff7a25 upstream.
[why & how]
Change the order of the pipe_ctx->plane_state check to ensure that plane_state is not null before accessing it.
--- drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-)
drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +7 -3
@@ -1741,13 +1741,17 @@ static void dcn20_program_pipe( (pipe_ctx->plane_state && pipe_ctx->plane_state->update_flags.bits.hdr_mult)) hws->funcs.set_hdr_multiplier(pipe_ctx); -if (pipe_ctx->update_flags.bits.enable || - (pipe_ctx->plane_state && +if ((pipe_ctx->plane_state && pipe_ctx->plane_state->update_flags.bits.hdr_mult) || + pipe_ctx->update_flags.bits.enable) + hws->funcs.set_hdr_multiplier (pipe_ctx); + +if ((pipe_ctx->plane_state && pipe_ctx->plane_state->update_flags.bits.in_transfer_func_change) || (pipe_ctx->plane_state && pipe_ctx->plane_state->update_flags.bits.gamma_change) || (pipe_ctx->plane_state && - pipe_ctx->plane_state->update_flags.bits.lut_3d)) + pipe_ctx->plane_state->update_flags.bits.lut_3d) || + pipe_ctx->update_flags.bits.enable) hws->funcs.set_input_transfer_func (dc, pipe_ctx, pipe_ctx->plane_state);/* dcn10_translate_regamma_to_hw_format takes 750us to finish
Greg Kroah-Hartman
maintainerPATCH 457/676 drm/amd/display: Add NULL check for function pointer in dcn20_set_output_transfer_func
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Srinivasan Shanmugam <[email protected]>
commit 62ed6f0f198da04e884062264df308277628004f upstream.
This commit adds a null check for the set_output_gamma function pointer in the dcn20_set_output_transfer_func function. Previously, set_output_gamma was being checked for null at line 1030, but then it was being dereferenced without any null check at line 1048. This could potentially lead to a null pointer dereference error if set_output_gamma is null.
To fix this, we now ensure that set_output_gamma is not null before dereferencing it. We do this by adding a null check for set_output_gamma before the call to set_output_gamma at line 1048.
--- drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +2 -1
@@ -880,7 +880,8 @@ bool dcn20_set_output_transfer_func(stru/* * if above if is not executed then 'params' equal to 0 and set in bypass */ - mpc->funcs->set_output_gamma (mpc, mpcc_id, params); +if (mpc->funcs->set_output_gamma) + mpc->funcs->set_output_gamma (mpc, mpcc_id, params);return true; }
Greg Kroah-Hartman
maintainerPATCH 458/676 drm/amd/display: Check phantom_stream before it is used
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Hung <[email protected]>
commit 3718a619a8c0a53152e76bb6769b6c414e1e83f4 upstream.
dcn32_enable_phantom_stream can return null, so returned value must be checked before used.
This fixes 1 NULL_RETURNS issue reported by Coverity.
--- drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource.c +3 -0
@@ -1786,6 +1786,9 @@ void dcn32_add_phantom_pipes(struct dc *// be a valid candidate for SubVP (i.e. has a plane, stream, doesn't // already have phantom pipe assigned, etc.) by previous checks. phantom_stream =dcn32_enable_phantom_stream (dc, context, pipes, pipe_cnt, index); +if (!phantom_stream) +return ; +dcn32_enable_phantom_plane (dc, context, phantom_stream, index);for (i =0 ; i < dc->res_pool->pipe_count; i++) {
Greg Kroah-Hartman
maintainerPATCH 459/676 drm/amd/display: Add NULL pointer check for kzalloc
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hersen Wu <[email protected]>
commit 8e65a1b7118acf6af96449e1e66b7adbc9396912 upstream.
[Why & How]
Check return pointer of kzalloc before using it.
--- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c | 8 ++++++++ drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c | 8 ++++++++ drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c | 3 +++ drivers/gpu/drm/amd/display/dc/dcn31/dcn31_resource.c | 5 +++++ drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c | 5 +++++ drivers/gpu/drm/amd/display/dc/dcn315/dcn315_resource.c | 2 ++ drivers/gpu/drm/amd/display/dc/dcn316/dcn316_resource.c | 2 ++ drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource.c | 5 +++++ drivers/gpu/drm/amd/display/dc/dcn321/dcn321_resource.c | 2 ++ 9 files changed, 40 insertions(+)
drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c +8 -0
@@ -560,11 +560,19 @@ void dcn3_clk_mgr_construct(dce_clock_read_ss_info (clk_mgr); clk_mgr->base.bw_params =kzalloc (sizeof (*clk_mgr->base.bw_params),GFP_KERNEL ); +if (!clk_mgr->base.bw_params) { +BREAK_TO_DEBUGGER (); +return ; + }/* need physical address of table to give to PMFW */ clk_mgr->wm_range_table =dm_helpers_allocate_gpu_mem (clk_mgr->base.ctx,DC_MEM_ALLOC_TYPE_GART ,sizeof (WatermarksExternal_t), &clk_mgr->wm_range_table_addr); +if (!clk_mgr->wm_range_table) { +BREAK_TO_DEBUGGER (); +return ; + } }void dcn3_clk_mgr_destroy (struct clk_mgr_internal *clk_mgr)
drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c +8 -0
@@ -1022,11 +1022,19 @@ void dcn32_clk_mgr_construct( clk_mgr->smu_present = false; clk_mgr->base.bw_params =kzalloc (sizeof (*clk_mgr->base.bw_params),GFP_KERNEL ); +if (!clk_mgr->base.bw_params) { +BREAK_TO_DEBUGGER (); +return ; + }/* need physical address of table to give to PMFW */ clk_mgr->wm_range_table =dm_helpers_allocate_gpu_mem (clk_mgr->base.ctx,DC_MEM_ALLOC_TYPE_GART ,sizeof (WatermarksExternal_t), &clk_mgr->wm_range_table_addr); +if (!clk_mgr->wm_range_table) { +BREAK_TO_DEBUGGER (); +return ; + } }void dcn32_clk_mgr_destroy (struct clk_mgr_internal *clk_mgr)
drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c +3 -0
@@ -2045,6 +2045,9 @@ bool dcn30_validate_bandwidth(struct dcBW_VAL_TRACE_COUNT (); +if (!pipes) + goto validate_fail; +DC_FP_START (); out =dcn30_internal_validate_bw (dc, context, pipes, &pipe_cnt, &vlevel, fast_validate, true);DC_FP_END ();
drivers/gpu/drm/amd/display/dc/dcn31/dcn31_resource.c +5 -0
@@ -1308,6 +1308,8 @@ static struct hpo_dp_link_encoder *dcn31/* allocate HPO link encoder */ hpo_dp_enc31 =kzalloc (sizeof (struct dcn31_hpo_dp_link_encoder ),GFP_KERNEL ); +if (!hpo_dp_enc31) +return NULL ;/* out of memory */ hpo_dp_link_encoder31_construct(hpo_dp_enc31, ctx, inst, &hpo_dp_link_enc_regs[inst],
@@ -1764,6 +1766,9 @@ bool dcn31_validate_bandwidth(struct dcBW_VAL_TRACE_COUNT (); +if (!pipes) + goto validate_fail; +DC_FP_START (); out =dcn30_internal_validate_bw (dc, context, pipes, &pipe_cnt, &vlevel, fast_validate, true);DC_FP_END ();
drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c +5 -0
@@ -1381,6 +1381,8 @@ static struct hpo_dp_link_encoder *dcn31/* allocate HPO link encoder */ hpo_dp_enc31 =kzalloc (sizeof (struct dcn31_hpo_dp_link_encoder ),GFP_KERNEL ); +if (!hpo_dp_enc31) +return NULL ;/* out of memory */ hpo_dp_link_encoder31_construct(hpo_dp_enc31, ctx, inst, &hpo_dp_link_enc_regs[inst],
@@ -1741,6 +1743,9 @@ bool dcn314_validate_bandwidth(struct dcBW_VAL_TRACE_COUNT (); +if (!pipes) + goto validate_fail; +if (filter_modes_for_single_channel_workaround (dc, context)) goto validate_fail;
drivers/gpu/drm/amd/display/dc/dcn315/dcn315_resource.c +2 -0
@@ -1308,6 +1308,8 @@ static struct hpo_dp_link_encoder *dcn31/* allocate HPO link encoder */ hpo_dp_enc31 =kzalloc (sizeof (struct dcn31_hpo_dp_link_encoder ),GFP_KERNEL ); +if (!hpo_dp_enc31) +return NULL ;/* out of memory */ hpo_dp_link_encoder31_construct(hpo_dp_enc31, ctx, inst, &hpo_dp_link_enc_regs[inst],
drivers/gpu/drm/amd/display/dc/dcn316/dcn316_resource.c +2 -0
@@ -1305,6 +1305,8 @@ static struct hpo_dp_link_encoder *dcn31/* allocate HPO link encoder */ hpo_dp_enc31 =kzalloc (sizeof (struct dcn31_hpo_dp_link_encoder ),GFP_KERNEL ); +if (!hpo_dp_enc31) +return NULL ;/* out of memory */ hpo_dp_link_encoder31_construct(hpo_dp_enc31, ctx, inst, &hpo_dp_link_enc_regs[inst],
drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource.c +5 -0
@@ -1299,6 +1299,8 @@ static struct hpo_dp_link_encoder *dcn32/* allocate HPO link encoder */ hpo_dp_enc31 =kzalloc (sizeof (struct dcn31_hpo_dp_link_encoder ),GFP_KERNEL ); +if (!hpo_dp_enc31) +return NULL ;/* out of memory */ #undef REG_STRUCT#define REG_STRUCT hpo_dp_link_enc_regs
@@ -1845,6 +1847,9 @@ bool dcn32_validate_bandwidth(struct dcBW_VAL_TRACE_COUNT (); +if (!pipes) + goto validate_fail; +DC_FP_START (); out =dcn32_internal_validate_bw (dc, context, pipes, &pipe_cnt, &vlevel, fast_validate);DC_FP_END ();
drivers/gpu/drm/amd/display/dc/dcn321/dcn321_resource.c +2 -0
@@ -1285,6 +1285,8 @@ static struct hpo_dp_link_encoder *dcn32/* allocate HPO link encoder */ hpo_dp_enc31 =kzalloc (sizeof (struct dcn31_hpo_dp_link_encoder ),GFP_KERNEL ); +if (!hpo_dp_enc31) +return NULL ;/* out of memory */ #undef REG_STRUCT#define REG_STRUCT hpo_dp_link_enc_regs
Greg Kroah-Hartman
maintainerPATCH 460/676 dm-bufio: fix warnings about duplicate slab caches
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mikulas Patocka <[email protected]>
commit 42964e4b5e3ac95090bdd23ed7da2a941ccd902c upstream.
The commit 4c39529663b9 adds a warning about duplicate cache names if CONFIG_DEBUG_VM is selected. These warnings are triggered by the dm-bufio code. The dm-bufio code allocates a slab cache with each client. It is not possible to preallocate the caches in the module init function because the size of auxiliary per-buffer data is not known at this point.
So, this commit changes dm-bufio so that it appends a unique atomic value to the cache name, to avoid the warnings.
--- drivers/md/dm-bufio.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-)
drivers/md/dm-bufio.c +8 -4
@@ -2444,7 +2444,8 @@ struct dm_bufio_client *dm_bufio_client_int r;unsigned int num_locks;struct dm_bufio_client *c; -char slab_name[27 ]; +char slab_name[64 ]; +static atomic_t seqno =ATOMIC_INIT (0 );if (!block_size || block_size & ((1 <<SECTOR_SHIFT ) -1 )) {DMERR ("%s: block size not specified or is not multiple of 512b" , __func__);
@@ -2495,7 +2496,8 @@ struct dm_bufio_client *dm_bufio_client_ (block_size < PAGE_SIZE || !is_power_of_2(block_size))) {unsigned int align =min (1U <<__ffs (block_size), (unsigned int )PAGE_SIZE ); -snprintf (slab_name,sizeof (slab_name),"dm_bufio_cache-%u" , block_size); +snprintf (slab_name,sizeof (slab_name),"dm_bufio_cache-%u-%u" , + block_size,atomic_inc_return (&seqno)); c->slab_cache =kmem_cache_create (slab_name, block_size, align,SLAB_RECLAIM_ACCOUNT ,NULL );if (!c->slab_cache) {
@@ -2504,9 +2506,11 @@ struct dm_bufio_client *dm_bufio_client_ } }if (aux_size) -snprintf (slab_name,sizeof (slab_name),"dm_bufio_buffer-%u" , aux_size); +snprintf (slab_name,sizeof (slab_name),"dm_bufio_buffer-%u-%u" , + aux_size,atomic_inc_return (&seqno));else -snprintf (slab_name,sizeof (slab_name),"dm_bufio_buffer" ); +snprintf (slab_name,sizeof (slab_name),"dm_bufio_buffer-%u" , +atomic_inc_return (&seqno)); c->slab_buffer =kmem_cache_create (slab_name,sizeof (struct dm_buffer ) + aux_size,0 ,SLAB_RECLAIM_ACCOUNT ,NULL );if (!c->slab_buffer) {
Greg Kroah-Hartman
maintainerPATCH 461/676 perf/x86/intel: Hide Topdown metrics events if the feature is not enumerated
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kan Liang <[email protected]>
commit 556a7c039a52c21da33eaae9269984a1ef59189b upstream.
The below error is observed on Ice Lake VM.
$ perf stat Error: The sys_perf_event_open() syscall returned with 22 (Invalid argument) for event (slots). /bin/dmesg | grep -i perf may provide additional information.
In a virtualization env, the Topdown metrics and the slots event haven't been supported yet. The guest CPUID doesn't enumerate them. However, the current kernel unconditionally exposes the slots event and the Topdown metrics events to sysfs, which misleads the perf tool and triggers the error.
Hide the perf-metrics topdown events and the slots event if the perf-metrics feature is not enumerated.
The big core of a hybrid platform can also supports the perf-metrics feature. Fix the hybrid platform as well.
--- arch/x86/events/intel/core.c | 34 +++++++++++++++++++++++++++++++++- 1 file changed, 33 insertions(+), 1 deletion(-)
arch/x86/events/intel/core.c +33 -1
@@ -5559,8 +5559,22 @@ default_is_visible(struct kobject *kobj,return attr->mode; } +static umode_t +td_is_visible (struct kobject *kobj,struct attribute *attr,int i) +{ +/* +* Hide the perf metrics topdown events +* if the feature is not enumerated. +*/ +if (x86_pmu.num_topdown_events) +return x86_pmu.intel_cap.perf_metrics ? attr->mode :0 ; + +return attr->mode; +} +static struct attribute_group group_events_td = { .name ="events" , + .is_visible = td_is_visible, };static struct attribute_group group_events_mem = {
@@ -5762,9 +5776,27 @@ static umode_t hybrid_format_is_visible(return (cpu >=0 ) && (pmu->cpu_type & pmu_attr->pmu_type) ? attr->mode :0 ; } +static umode_t hybrid_td_is_visible (struct kobject *kobj, +struct attribute *attr,int i) +{ +struct device *dev =kobj_to_dev (kobj); +struct x86_hybrid_pmu *pmu = + container_of(dev_get_drvdata(dev), struct x86_hybrid_pmu, pmu); + +if (!is_attr_for_this_pmu (kobj, attr)) +return 0 ; + + +/* Only the big core supports perf metrics */ +if (pmu->cpu_type == hybrid_big) +return pmu->intel_cap.perf_metrics ? attr->mode :0 ; + +return attr->mode; +} +static struct attribute_group hybrid_group_events_td = { .name ="events" , - .is_visible = hybrid_events_is_visible, + .is_visible = hybrid_td_is_visible, };static struct attribute_group hybrid_group_events_mem = {
Greg Kroah-Hartman
maintainerPATCH 462/676 f2fs: fix null reference error when checking end of zone
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Daejun Park <[email protected]>
commit c82bc1ab2a8a5e73d9728e80c4c2ed87e8921a38 upstream.
This patch fixes a potentially null pointer being accessed by is_end_zone_blkaddr() that checks the last block of a zone when f2fs is mounted as a single device.
--- fs/f2fs/data.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
fs/f2fs/data.c +3 -1
@@ -924,6 +924,7 @@ alloc_new:#ifdef CONFIG_BLK_DEV_ZONED static bool is_end_zone_blkaddr (struct f2fs_sb_info *sbi,block_t blkaddr) { +struct block_device *bdev = sbi->sb->s_bdev;int devi =0 ;if (f2fs_is_multi_device (sbi)) {
@@ -934,8 +935,9 @@ static bool is_end_zone_blkaddr(struct freturn false; } blkaddr -=FDEV (devi).start_blk; + bdev =FDEV (devi).bdev; } -return bdev_zoned_model (FDEV (devi).bdev) ==BLK_ZONED_HM && +return bdev_is_zoned (bdev) &&f2fs_blkz_is_seq (sbi, devi, blkaddr) && (blkaddr % sbi->blocks_per_blkz == sbi->blocks_per_blkz -1 ); }
Greg Kroah-Hartman
maintainerPATCH 463/676 btrfs: do not BUG_ON() when freeing tree block after error
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Filipe Manana <[email protected]>
commit bb3868033a4cccff7be57e9145f2117cbdc91c11 upstream.
When freeing a tree block, at btrfs_free_tree_block(), if we fail to create a delayed reference we don't deal with the error and just do a BUG_ON(). The error most likely to happen is -ENOMEM, and we have a comment mentioning that only -ENOMEM can happen, but that is not true, because in case qgroups are enabled any error returned from btrfs_qgroup_trace_extent_post() (can be -EUCLEAN or anything returned from btrfs_search_slot() for example) can be propagated back to btrfs_free_tree_block().
So stop doing a BUG_ON() and return the error to the callers and make them abort the transaction to prevent leaking space. Syzbot was triggering this, likely due to memory allocation failure injection.
--- fs/btrfs/ctree.c | 51 ++++++++++++++++++++++++++++++++++++--------- fs/btrfs/extent-tree.c | 22 +++++++++++-------- fs/btrfs/extent-tree.h | 8 +++---- fs/btrfs/free-space-tree.c | 10 ++++++-- fs/btrfs/ioctl.c | 6 ++++- fs/btrfs/qgroup.c | 6 +++-- 6 files changed, 74 insertions(+), 29 deletions(-)
fs/btrfs/ctree.c +41 -10
@@ -617,10 +617,16 @@ static noinline int __btrfs_cow_block(statomic_inc (&cow->refs);rcu_assign_pointer (root->node, cow); -btrfs_free_tree_block (trans,btrfs_root_id (root), buf, - parent_start, last_ref); + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), buf, + parent_start, last_ref);free_extent_buffer (buf);add_root_to_dirty_list (root); +if (ret <0 ) { +btrfs_tree_unlock (cow); +free_extent_buffer (cow); +btrfs_abort_transaction (trans, ret); +return ret; + } }else {WARN_ON (trans->transid !=btrfs_header_generation (parent)); ret = btrfs_tree_mod_log_insert_key(parent, parent_slot,
@@ -645,8 +651,14 @@ static noinline int __btrfs_cow_block(streturn ret; } } -btrfs_free_tree_block (trans,btrfs_root_id (root), buf, - parent_start, last_ref); + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), buf, + parent_start, last_ref); +if (ret <0 ) { +btrfs_tree_unlock (cow); +free_extent_buffer (cow); +btrfs_abort_transaction (trans, ret); +return ret; + } }if (unlock_orig)btrfs_tree_unlock (buf);
@@ -1121,9 +1133,13 @@ static noinline int balance_level(structfree_extent_buffer (mid);root_sub_used (root, mid->len); -btrfs_free_tree_block (trans,btrfs_root_id (root), mid,0 ,1 ); + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), mid,0 ,1 );/* once for the root ptr */ free_extent_buffer_stale (mid); +if (ret <0 ) { +btrfs_abort_transaction (trans, ret); + goto out; + }return 0 ; } if (btrfs_header_nritems(mid) >
@@ -1191,10 +1207,14 @@ static noinline int balance_level(struct goto out; }root_sub_used (root, right->len); -btrfs_free_tree_block (trans,btrfs_root_id (root), right, + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), right,0 ,1 );free_extent_buffer_stale (right); right =NULL ; +if (ret <0 ) { +btrfs_abort_transaction (trans, ret); + goto out; + } }else {struct btrfs_disk_key right_key;btrfs_node_key (right, &right_key,0 );
@@ -1249,9 +1269,13 @@ static noinline int balance_level(struct goto out; }root_sub_used (root, mid->len); -btrfs_free_tree_block (trans,btrfs_root_id (root), mid,0 ,1 ); + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), mid,0 ,1 );free_extent_buffer_stale (mid); mid =NULL ; +if (ret <0 ) { +btrfs_abort_transaction (trans, ret); + goto out; + } }else {/* update the parent key to reflect our changes */ struct btrfs_disk_key mid_key;
@@ -3022,7 +3046,11 @@ static noinline int insert_new_root(stru old = root->node; ret =btrfs_tree_mod_log_insert_root (root->node, c, false);if (ret <0 ) { -btrfs_free_tree_block (trans,btrfs_root_id (root), c,0 ,1 ); +int ret2; + + ret2 =btrfs_free_tree_block (trans,btrfs_root_id (root), c,0 ,1 ); +if (ret2 <0 ) +btrfs_abort_transaction (trans, ret2);btrfs_tree_unlock (c);free_extent_buffer (c);return ret;
@@ -4587,9 +4615,12 @@ static noinline int btrfs_del_leaf(strucroot_sub_used (root, leaf->len);atomic_inc (&leaf->refs); -btrfs_free_tree_block (trans,btrfs_root_id (root), leaf,0 ,1 ); + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), leaf,0 ,1 );free_extent_buffer_stale (leaf); -return 0 ; +if (ret <0 ) +btrfs_abort_transaction (trans, ret); + +return ret; }/* * delete the item at the leaf level in path. If that empties
fs/btrfs/extent-tree.c +13 -9
@@ -3290,10 +3290,10 @@ out_delayed_unlock:return 0 ; } -void btrfs_free_tree_block (struct btrfs_trans_handle *trans, -u64 root_id, -struct extent_buffer *buf, -u64 parent,int last_ref) +int btrfs_free_tree_block (struct btrfs_trans_handle *trans, +u64 root_id, +struct extent_buffer *buf, +u64 parent,int last_ref) {struct btrfs_fs_info *fs_info = trans->fs_info;struct btrfs_ref generic_ref = {0 };
@@ -3307,7 +3307,8 @@ void btrfs_free_tree_block(struct btrfs_if (root_id !=BTRFS_TREE_LOG_OBJECTID ) {btrfs_ref_tree_mod (fs_info, &generic_ref); ret =btrfs_add_delayed_tree_ref (trans, &generic_ref,NULL ); -BUG_ON (ret);/* -ENOMEM */ +if (ret <0 ) +return ret; }if (last_ref &&btrfs_header_generation (buf) == trans->transid) {
@@ -3371,6 +3372,7 @@ out:*/ clear_bit (EXTENT_BUFFER_CORRUPT , &buf->bflags); } +return 0 ; }/* Can return -ENOMEM */
@@ -5474,7 +5476,7 @@ static noinline int walk_up_proc(struct struct walk_control *wc) {struct btrfs_fs_info *fs_info = root->fs_info; -int ret; +int ret =0 ;int level = wc->level;struct extent_buffer *eb = path->nodes[level];u64 parent =0 ;
@@ -5565,12 +5567,14 @@ static noinline int walk_up_proc(struct goto owner_mismatch; } -btrfs_free_tree_block (trans,btrfs_root_id (root), eb, parent, - wc->refs[level] ==1 ); + ret =btrfs_free_tree_block (trans,btrfs_root_id (root), eb, parent, + wc->refs[level] ==1 ); +if (ret <0 ) +btrfs_abort_transaction (trans, ret); out: wc->refs[level] =0 ; wc->flags[level] =0 ; -return 0 ; +return ret; owner_mismatch: btrfs_err_rl(fs_info, "unexpected tree owner, have %llu expect %llu",
fs/btrfs/extent-tree.h +4 -4
@@ -114,10 +114,10 @@ struct extent_buffer *btrfs_alloc_tree_b int level, u64 hint, u64 empty_size, enum btrfs_lock_nesting nest); -void btrfs_free_tree_block (struct btrfs_trans_handle *trans, -u64 root_id, -struct extent_buffer *buf, -u64 parent,int last_ref); +int btrfs_free_tree_block (struct btrfs_trans_handle *trans, +u64 root_id, +struct extent_buffer *buf, +u64 parent,int last_ref); int btrfs_alloc_reserved_file_extent(struct btrfs_trans_handle *trans, struct btrfs_root *root, u64 owner, u64 offset, u64 ram_bytes,
fs/btrfs/free-space-tree.c +7 -3
@@ -1289,10 +1289,14 @@ int btrfs_delete_free_space_tree(structbtrfs_tree_lock (free_space_root->node);btrfs_clear_buffer_dirty (trans, free_space_root->node);btrfs_tree_unlock (free_space_root->node); -btrfs_free_tree_block (trans,btrfs_root_id (free_space_root), - free_space_root->node,0 ,1 ); - + ret =btrfs_free_tree_block (trans,btrfs_root_id (free_space_root), + free_space_root->node,0 ,1 );btrfs_put_root (free_space_root); +if (ret <0 ) { +btrfs_abort_transaction (trans, ret); +btrfs_end_transaction (trans); +return ret; + }return btrfs_commit_transaction (trans);
fs/btrfs/ioctl.c +5 -1
@@ -707,6 +707,8 @@ static noinline int create_subvol(struct ret =btrfs_insert_root (trans, fs_info->tree_root, &key, root_item);if (ret) { +int ret2; +/* * Since we don't abort the transaction in this case, free the * tree block so that we don't leak space and leave the
@@ -717,7 +719,9 @@ static noinline int create_subvol(structbtrfs_tree_lock (leaf);btrfs_clear_buffer_dirty (trans, leaf);btrfs_tree_unlock (leaf); -btrfs_free_tree_block (trans, objectid, leaf,0 ,1 ); + ret2 =btrfs_free_tree_block (trans, objectid, leaf,0 ,1 ); +if (ret2 <0 ) +btrfs_abort_transaction (trans, ret2);free_extent_buffer (leaf); goto out; }
fs/btrfs/qgroup.c +4 -2
@@ -1320,9 +1320,11 @@ int btrfs_quota_disable(struct btrfs_fs_btrfs_tree_lock (quota_root->node);btrfs_clear_buffer_dirty (trans, quota_root->node);btrfs_tree_unlock (quota_root->node); -btrfs_free_tree_block (trans,btrfs_root_id (quota_root), - quota_root->node,0 ,1 ); + ret =btrfs_free_tree_block (trans,btrfs_root_id (quota_root), + quota_root->node,0 ,1 ); +if (ret <0 ) +btrfs_abort_transaction (trans, ret); out:btrfs_put_root (quota_root);
Greg Kroah-Hartman
maintainerPATCH 464/676 ALSA: usb-audio: Fix potential out-of-bound accesses for Extigy and Mbox devices
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Benoît Sevens <[email protected]>
commit b909df18ce2a998afef81d58bbd1a05dc0788c40 upstream.
A bogus device can provide a bNumConfigurations value that exceeds the initial value used in usb_get_configuration for allocating dev->config.
This can lead to out-of-bounds accesses later, e.g. in usb_destroy_configuration.
--- sound/usb/quirks.c | 27 +++++++++++++++++++++------ 1 file changed, 21 insertions(+), 6 deletions(-)
sound/usb/quirks.c +21 -6
@@ -555,6 +555,7 @@ int snd_usb_create_quirk(struct snd_usb_static int snd_usb_extigy_boot_quirk (struct usb_device *dev,struct usb_interface *intf) {struct usb_host_config *config = dev->actconfig; +struct usb_device_descriptor new_device_descriptor;int err; if (le16_to_cpu(get_cfg_desc(config)->wTotalLength) == EXTIGY_FIRMWARE_SIZE_OLD ||
@@ -566,10 +567,14 @@ static int snd_usb_extigy_boot_quirk(strif (err <0 )dev_dbg (&dev->dev,"error sending boot message: %d\n" , err); err =usb_get_descriptor (dev,USB_DT_DEVICE ,0 , - &dev->descriptor,sizeof (dev->descriptor)); - config = dev->actconfig; + &new_device_descriptor,sizeof (new_device_descriptor));if (err <0 )dev_dbg (&dev->dev,"error usb_get_descriptor: %d\n" , err); +if (new_device_descriptor.bNumConfigurations > dev->descriptor.bNumConfigurations) +dev_dbg (&dev->dev,"error too large bNumConfigurations: %d\n" , + new_device_descriptor.bNumConfigurations); +else +memcpy (&dev->descriptor, &new_device_descriptor,sizeof (dev->descriptor)); err =usb_reset_configuration (dev);if (err <0 )dev_dbg (&dev->dev,"error usb_reset_configuration: %d\n" , err);
@@ -901,6 +906,7 @@ static void mbox2_setup_48_24_magic(strustatic int snd_usb_mbox2_boot_quirk (struct usb_device *dev) {struct usb_host_config *config = dev->actconfig; +struct usb_device_descriptor new_device_descriptor;int err;u8 bootresponse[0x12 ];int fwsize;
@@ -936,10 +942,14 @@ static int snd_usb_mbox2_boot_quirk(strudev_dbg (&dev->dev,"device initialised!\n" ); err =usb_get_descriptor (dev,USB_DT_DEVICE ,0 , - &dev->descriptor,sizeof (dev->descriptor)); - config = dev->actconfig; + &new_device_descriptor,sizeof (new_device_descriptor));if (err <0 )dev_dbg (&dev->dev,"error usb_get_descriptor: %d\n" , err); +if (new_device_descriptor.bNumConfigurations > dev->descriptor.bNumConfigurations) +dev_dbg (&dev->dev,"error too large bNumConfigurations: %d\n" , + new_device_descriptor.bNumConfigurations); +else +memcpy (&dev->descriptor, &new_device_descriptor,sizeof (dev->descriptor)); err =usb_reset_configuration (dev);if (err <0 )
@@ -1253,6 +1263,7 @@ static void mbox3_setup_48_24_magic(strustatic int snd_usb_mbox3_boot_quirk (struct usb_device *dev) {struct usb_host_config *config = dev->actconfig; +struct usb_device_descriptor new_device_descriptor;int err;int descriptor_size;
@@ -1266,10 +1277,14 @@ static int snd_usb_mbox3_boot_quirk(strudev_dbg (&dev->dev,"device initialised!\n" ); err =usb_get_descriptor (dev,USB_DT_DEVICE ,0 , - &dev->descriptor,sizeof (dev->descriptor)); - config = dev->actconfig; + &new_device_descriptor,sizeof (new_device_descriptor));if (err <0 )dev_dbg (&dev->dev,"error usb_get_descriptor: %d\n" , err); +if (new_device_descriptor.bNumConfigurations > dev->descriptor.bNumConfigurations) +dev_dbg (&dev->dev,"error too large bNumConfigurations: %d\n" , + new_device_descriptor.bNumConfigurations); +else +memcpy (&dev->descriptor, &new_device_descriptor,sizeof (dev->descriptor)); err =usb_reset_configuration (dev);if (err <0 )
Greg Kroah-Hartman
maintainerPATCH 465/676 Revert "arm64: dts: mediatek: mt8195-cherry: Mark USB 3.0 on xhci1 as disabled"
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Chen-Yu Tsai <[email protected]>
This reverts commit 090386dbedbc2f099c44a0136eb8eb8713930072.
The hunk was applied to the wrong device node when the commit was backported to the 6.6 stable branch.
Revert it to re-do the backport correctly.
--- arch/arm64/boot/dts/mediatek/mt8195-cherry.dtsi | 1 - 1 file changed, 1 deletion(-)
arch/arm64/boot/dts/mediatek/mt8195-cherry.dtsi +0 -1
@@ -1312,7 +1312,6 @@ usb2-lpm-disable; vusb33-supply = <&mt6359_vusb_ldo_reg>; vbus-supply = <&usb_vbus>; - mediatek,u3p-dis-msk = <1>; }; #include <arm/cros-ec-keyboard.dtsi>
Greg Kroah-Hartman
maintainerPATCH 466/676 arm64: dts: mediatek: mt8195-cherry: Mark USB 3.0 on xhci1 as disabled
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Chen-Yu Tsai <[email protected]>
[ Upstream commit 09d385679487c58f0859c1ad4f404ba3df2f8830 ]
USB 3.0 on xhci1 is not used, as the controller shares the same PHY as pcie1. The latter is enabled to support the M.2 PCIe WLAN card on this design.
Mark USB 3.0 as disabled on this controller using the "mediatek,u3p-dis-msk" property.
--- arch/arm64/boot/dts/mediatek/mt8195-cherry.dtsi | 1 + 1 file changed, 1 insertion(+)
arch/arm64/boot/dts/mediatek/mt8195-cherry.dtsi +1 -0
@@ -1296,6 +1296,7 @@ vusb33-supply = <&mt6359_vusb_ldo_reg>; vbus-supply = <&usb_vbus>; + mediatek,u3p-dis-msk = <1>; }; &xhci2 {
Greg Kroah-Hartman
maintainerPATCH 467/676 ASoC: Intel: sst: Fix used of uninitialized ctx to log an error
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hans de Goede <[email protected]>
commit c1895ba181e560144601fafe46aeedbafdf4dbc4 upstream.
Fix the new "LPE0F28" code path using the uninitialized ctx variable to log an error.
--- sound/soc/intel/atom/sst/sst_acpi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
sound/soc/intel/atom/sst/sst_acpi.c +1 -1
@@ -308,7 +308,7 @@ static int sst_acpi_probe(struct platfor rsrc =platform_get_resource (pdev,IORESOURCE_MEM , pdata->res_info->acpi_lpe_res_index);if (!rsrc) { -dev_err (ctx->dev,"Invalid SHIM base\n" ); +dev_err (dev,"Invalid SHIM base\n" );return -EIO ; } rsrc->start -= pdata->res_info->shim_offset;
Greg Kroah-Hartman
maintainerPATCH 468/676 soc: qcom: socinfo: fix revision check in qcom_socinfo_probe()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Manikanta Mylavarapu <[email protected]>
commit 128fdbf36cddc2a901c4889ba1c89fa9f2643f2c upstream.
In success case, the revision holds a non-null pointer. The current logic incorrectly returns an error for a non-null pointer, whereas it should return an error for a null pointer.
The socinfo driver for IPQ9574 and IPQ5332 is currently broken, resulting in the following error message
qcom-socinfo qcom-socinfo: probe with driver qcom-socinfo failed with error -12
Add a null check for the revision to ensure it returns an error only in failure case (null pointer).
--- drivers/soc/qcom/socinfo.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/soc/qcom/socinfo.c +1 -1
@@ -757,7 +757,7 @@ static int qcom_socinfo_probe(struct pla qs->attr.revision =devm_kasprintf (&pdev->dev,GFP_KERNEL ,"%u.%u" ,SOCINFO_MAJOR (le32_to_cpu (info->ver)),SOCINFO_MINOR (le32_to_cpu (info->ver))); -if (!qs->attr.soc_id || qs->attr.revision) +if (!qs->attr.soc_id || !qs->attr.revision)return -ENOMEM ;if (offsetof(struct socinfo , serial_num) <= item_size) {
Greg Kroah-Hartman
maintainerPATCH 469/676 ext4: supress data-race warnings in ext4_free_inodes_{count,set}()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jeongjun Park <[email protected]>
commit 902cc179c931a033cd7f4242353aa2733bf8524c upstream.
find_group_other() and find_group_orlov() read *_lo, *_hi with ext4_free_inodes_count without additional locking. This can cause data-race warning, but since the lock is held for most writes and free inodes value is generally not a problem even if it is incorrect, it is more appropriate to use READ_ONCE()/WRITE_ONCE() than to add locking.
==================================================================
BUG: KCSAN: data-race in ext4_free_inodes_count / ext4_free_inodes_set
write to 0xffff88810404300e of 2 bytes by task 6254 on cpu 1:
ext4_free_inodes_set+0x1f/0x80 fs/ext4/super.c:405 __ext4_new_inode+0x15ca/0x2200 fs/ext4/ialloc.c:1216 ext4_symlink+0x242/0x5a0 fs/ext4/namei.c:3391 vfs_symlink+0xca/0x1d0 fs/namei.c:4615 do_symlinkat+0xe3/0x340 fs/namei.c:4641 __do_sys_symlinkat fs/namei.c:4657 [inline] __se_sys_symlinkat fs/namei.c:4654 [inline] __x64_sys_symlinkat+0x5e/0x70 fs/namei.c:4654 x64_sys_call+0x1dda/0x2d60 arch/x86/include/generated/asm/syscalls_64.h:267 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0x54/0x120 arch/x86/entry/common.c:83 entry_SYSCALL_64_after_hwframe+0x76/0x7e
read to 0xffff88810404300e of 2 bytes by task 6257 on cpu 0:
ext4_free_inodes_count+0x1c/0x80 fs/ext4/super.c:349 find_group_other fs/ext4/ialloc.c:594 [inline] __ext4_new_inode+0x6ec/0x2200 fs/ext4/ialloc.c:1017 ext4_symlink+0x242/0x5a0 fs/ext4/namei.c:3391 vfs_symlink+0xca/0x1d0 fs/namei.c:4615 do_symlinkat+0xe3/0x340 fs/namei.c:4641 __do_sys_symlinkat fs/namei.c:4657 [inline] __se_sys_symlinkat fs/namei.c:4654 [inline] __x64_sys_symlinkat+0x5e/0x70 fs/namei.c:4654 x64_sys_call+0x1dda/0x2d60 arch/x86/include/generated/asm/syscalls_64.h:267 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0x54/0x120 arch/x86/entry/common.c:83 entry_SYSCALL_64_after_hwframe+0x76/0x7e
--- fs/ext4/super.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
fs/ext4/super.c +4 -4
@@ -346,9 +346,9 @@ __u32 ext4_free_group_clusters(struct su__u32 ext4_free_inodes_count (struct super_block *sb,struct ext4_group_desc *bg) { -return le16_to_cpu (bg->bg_free_inodes_count_lo) | +return le16_to_cpu (READ_ONCE (bg->bg_free_inodes_count_lo)) | (EXT4_DESC_SIZE (sb) >=EXT4_MIN_DESC_SIZE_64BIT ? - (__u32 )le16_to_cpu (bg->bg_free_inodes_count_hi) <<16 :0 ); + (__u32 )le16_to_cpu (READ_ONCE (bg->bg_free_inodes_count_hi)) <<16 :0 ); } __u32 ext4_used_dirs_count(struct super_block *sb,
@@ -402,9 +402,9 @@ void ext4_free_group_clusters_set(structvoid ext4_free_inodes_set (struct super_block *sb,struct ext4_group_desc *bg,__u32 count) { - bg->bg_free_inodes_count_lo =cpu_to_le16 ((__u16 )count); +WRITE_ONCE (bg->bg_free_inodes_count_lo,cpu_to_le16 ((__u16 )count));if (EXT4_DESC_SIZE (sb) >=EXT4_MIN_DESC_SIZE_64BIT ) - bg->bg_free_inodes_count_hi =cpu_to_le16 (count >>16 ); +WRITE_ONCE (bg->bg_free_inodes_count_hi,cpu_to_le16 (count >>16 )); } void ext4_used_dirs_set(struct super_block *sb,
Greg Kroah-Hartman
maintainerPATCH 470/676 ext4: fix FS_IOC_GETFSMAP handling
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Theodore Ts'o <[email protected]>
commit 4a622e4d477bb12ad5ed4abbc7ad1365de1fa347 upstream.
The original implementation ext4's FS_IOC_GETFSMAP handling only worked when the range of queried blocks included at least one free (unallocated) block range. This is because how the metadata blocks were emitted was as a side effect of ext4_mballoc_query_range() calling ext4_getfsmap_datadev_helper(), and that function was only called when a free block range was identified. As a result, this caused generic/365 to fail.
Fix this by creating a new function ext4_getfsmap_meta_helper() which gets called so that blocks before the first free block range in a block group can get properly reported.
--- fs/ext4/fsmap.c | 54 +++++++++++++++++++++++++++++++++++++++++++++++++++++- fs/ext4/mballoc.c | 18 ++++++++++++++---- fs/ext4/mballoc.h | 1 + 3 files changed, 68 insertions(+), 5 deletions(-)
fs/ext4/fsmap.c +53 -1
@@ -185,6 +185,56 @@ static inline ext4_fsblk_t ext4_fsmap_nereturn fmr->fmr_physical + fmr->fmr_length; } +static int ext4_getfsmap_meta_helper (struct super_block *sb, +ext4_group_t agno,ext4_grpblk_t start, +ext4_grpblk_t len,void *priv) +{ +struct ext4_getfsmap_info *info = priv; +struct ext4_fsmap *p; +struct ext4_fsmap *tmp; +struct ext4_sb_info *sbi =EXT4_SB (sb); +ext4_fsblk_t fsb, fs_start, fs_end; +int error; + + fs_start = fsb = (EXT4_C2B (sbi, start) + +ext4_group_first_block_no (sb, agno)); + fs_end = fs_start +EXT4_C2B (sbi, len); + +/* Return relevant extents from the meta_list */ +list_for_each_entry_safe (p, tmp, &info->gfi_meta_list, fmr_list) { +if (p->fmr_physical < info->gfi_next_fsblk) { +list_del (&p->fmr_list); +kfree (p); +continue ; + } +if (p->fmr_physical <= fs_start || + p->fmr_physical + p->fmr_length <= fs_end) { +/* Emit the retained free extent record if present */ +if (info->gfi_lastfree.fmr_owner) { + error =ext4_getfsmap_helper (sb, info, + &info->gfi_lastfree); +if (error) +return error; + info->gfi_lastfree.fmr_owner =0 ; + } + error =ext4_getfsmap_helper (sb, info, p); +if (error) +return error; + fsb = p->fmr_physical + p->fmr_length; +if (info->gfi_next_fsblk < fsb) + info->gfi_next_fsblk = fsb; +list_del (&p->fmr_list); +kfree (p); +continue ; + } + } +if (info->gfi_next_fsblk < fsb) + info->gfi_next_fsblk = fsb; + +return 0 ; +} + +/* Transform a blockgroup's free record into a fsmap */ static int ext4_getfsmap_datadev_helper(struct super_block *sb, ext4_group_t agno, ext4_grpblk_t start,
@@ -539,6 +589,7 @@ static int ext4_getfsmap_datadev(struct error =ext4_mballoc_query_range (sb, info->gfi_agno,EXT4_B2C (sbi, info->gfi_low.fmr_physical),EXT4_B2C (sbi, info->gfi_high.fmr_physical), + ext4_getfsmap_meta_helper, ext4_getfsmap_datadev_helper, info);if (error) goto err;
@@ -560,7 +611,8 @@ static int ext4_getfsmap_datadev(struct/* Report any gaps at the end of the bg */ info->gfi_last = true; - error =ext4_getfsmap_datadev_helper (sb, end_ag, last_cluster,0 , info); + error =ext4_getfsmap_datadev_helper (sb, end_ag, last_cluster +1 , +0 , info);if (error) goto err;
fs/ext4/mballoc.c +14 -4
@@ -7155,13 +7155,14 @@ intext4_mballoc_query_range ( struct super_block *sb, ext4_group_t group, - ext4_grpblk_t start, + ext4_grpblk_t first, ext4_grpblk_t end, + ext4_mballoc_query_range_fn meta_formatter, ext4_mballoc_query_range_fn formatter, void *priv) { void *bitmap; -ext4_grpblk_t next; +ext4_grpblk_t start, next;struct ext4_buddy e4b;int error;
@@ -7172,10 +7173,19 @@ ext4_mballoc_query_range(ext4_lock_group (sb, group); - start =max (e4b.bd_info->bb_first_free, start); + start =max (e4b.bd_info->bb_first_free, first);if (end >=EXT4_CLUSTERS_PER_GROUP (sb)) end =EXT4_CLUSTERS_PER_GROUP (sb) -1 ; - +if (meta_formatter && start != first) { +if (start > end) + start = end; +ext4_unlock_group (sb, group); + error =meta_formatter (sb, group, first, start - first, + priv); +if (error) + goto out_unload; +ext4_lock_group (sb, group); + }while (start <= end) { start =mb_find_next_zero_bit (bitmap, end +1 , start);if (start > end)
fs/ext4/mballoc.h +1 -0
@@ -260,6 +260,7 @@ ext4_mballoc_query_range(ext4_group_t agno, ext4_grpblk_t start, ext4_grpblk_t end, + ext4_mballoc_query_range_fn meta_formatter, ext4_mballoc_query_range_fn formatter, void *priv);
Greg Kroah-Hartman
maintainerPATCH 471/676 jfs: xattr: check invalid xattr size more strictly
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Artem Sadovnikov <[email protected]>
commit d9f9d96136cba8fedd647d2c024342ce090133c2 upstream.
Commit 7c55b78818cf ("jfs: xattr: fix buffer overflow for invalid xattr") also addresses this issue but it only fixes it for positive values, while ea_size is an integer type and can take negative values, e.g. in case of a corrupted filesystem. This still breaks validation and would overflow because of implicit conversion from int to size_t in print_hex_dump().
Fix this issue by clamping the ea_size value instead.
Found by Linux Verification Center (linuxtesting.org) with Syzkaller.
--- fs/jfs/xattr.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
fs/jfs/xattr.c +1 -1
@@ -559,7 +559,7 @@ static int ea_get(struct inode *inode, s size_check:if (EALIST_SIZE (ea_buf->xattr) != ea_size) { -int size =min_t (int,EALIST_SIZE (ea_buf->xattr), ea_size); +int size =clamp_t (int, ea_size,0 ,EALIST_SIZE (ea_buf->xattr));printk (KERN_ERR "ea_get: invalid extended attribute\n" ); print_hex_dump(KERN_ERR, "", DUMP_PREFIX_ADDRESS, 16, 1,
Greg Kroah-Hartman
maintainerPATCH 472/676 ASoC: amd: yc: Add a quirk for microfone on Lenovo ThinkPad P14s Gen 5 21MES00B00
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ilya Zverev <[email protected]>
commit b682aa788e5f9f1ddacdfbb453e49fd3f4e83721 upstream.
New ThinkPads need new quirk entries. Ilya has tested this one. Laptop product id is 21MES00B00, though the shorthand 21ME works.
--- sound/soc/amd/yc/acp6x-mach.c | 7 +++++++ 1 file changed, 7 insertions(+)
sound/soc/amd/yc/acp6x-mach.c +7 -0
@@ -245,6 +245,13 @@ static const struct dmi_system_id yc_acp .driver_data = &acp6x_card, .matches = {DMI_MATCH (DMI_BOARD_VENDOR ,"LENOVO" ), + DMI_MATCH(DMI_PRODUCT_NAME, "21ME"), + } + }, + { + .driver_data = &acp6x_card, + .matches = { +DMI_MATCH (DMI_BOARD_VENDOR ,"LENOVO" ), DMI_MATCH(DMI_PRODUCT_NAME, "82QF"), } },
Greg Kroah-Hartman
maintainerPATCH 473/676 ASoC: codecs: Fix atomicity violation in snd_soc_component_get_drvdata()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Qiu-ji Chen <[email protected]>
commit 1157733344651ca505e259d6554591ff156922fa upstream.
An atomicity violation occurs when the validity of the variables da7219->clk_src and da7219->mclk_rate is being assessed. Since the entire assessment is not protected by a lock, the da7219 variable might still be in flux during the assessment, rendering this check invalid.
To fix this issue, we recommend adding a lock before the block if ((da7219->clk_src == clk_id) && (da7219->mclk_rate == freq)) so that the legitimacy check for da7219->clk_src and da7219->mclk_rate is protected by the lock, ensuring the validity of the check.
This possible bug is found by an experimental static analysis tool developed by our team. This tool analyzes the locking APIs to extract function pairs that can be concurrently executed, and then analyzes the instructions in the paired functions to identify possible concurrency bugs including data races and atomicity violations.
--- sound/soc/codecs/da7219.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-)
sound/soc/codecs/da7219.c +6 -3
@@ -1167,17 +1167,20 @@ static int da7219_set_dai_sysclk(structstruct da7219_priv *da7219 =snd_soc_component_get_drvdata (component);int ret =0 ; -if ((da7219->clk_src == clk_id) && (da7219->mclk_rate == freq)) +mutex_lock (&da7219->pll_lock); + +if ((da7219->clk_src == clk_id) && (da7219->mclk_rate == freq)) { +mutex_unlock (&da7219->pll_lock);return 0 ; + }if ((freq <2000000 ) || (freq >54000000 )) { +mutex_unlock (&da7219->pll_lock);dev_err (codec_dai->dev,"Unsupported MCLK value %d\n" , freq);return -EINVAL ; } -mutex_lock (&da7219->pll_lock); -switch (clk_id) {case DA7219_CLKSRC_MCLK_SQR : snd_soc_component_update_bits(component, DA7219_PLL_CTRL,
Greg Kroah-Hartman
maintainerPATCH 474/676 perf/x86/intel/pt: Fix buffer full but size is 0 case
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Adrian Hunter <[email protected]>
commit 5b590160d2cf776b304eb054afafea2bd55e3620 upstream.
If the trace data buffer becomes full, a truncated flag [T] is reported in PERF_RECORD_AUX. In some cases, the size reported is 0, even though data must have been added to make the buffer full.
That happens when the buffer fills up from empty to full before the Intel PT driver has updated the buffer position. Then the driver calculates the new buffer position before calculating the data size. If the old and new positions are the same, the data size is reported as 0, even though it is really the whole buffer size.
Fix by detecting when the buffer position is wrapped, and adjust the data size calculation accordingly.
Example
Use a very small buffer size (8K) and observe the size of truncated [T] data. Before the fix, it is possible to see records of 0 size.
Before:
$ perf record -m,8K -e intel_pt// uname
Linux
[ perf record: Woken up 2 times to write data ]
[ perf record: Captured and wrote 0.105 MB perf.data ]
$ perf script -D --no-itrace | grep AUX | grep -F '[T]'
Warning:
AUX data lost 2 times out of 3! 5 19462712368111 0x19710 [0x40]: PERF_RECORD_AUX offset: 0 size: 0 flags: 0x1 [T]
5 19462712700046 0x19ba8 [0x40]: PERF_RECORD_AUX offset: 0x170 size: 0xe90 flags: 0x1 [T]After:
$ perf record -m,8K -e intel_pt// uname
Linux
[ perf record: Woken up 3 times to write data ]
[ perf record: Captured and wrote 0.040 MB perf.data ]
$ perf script -D --no-itrace | grep AUX | grep -F '[T]'
Warning:
AUX data lost 2 times out of 3! 1 113720802995 0x4948 [0x40]: PERF_RECORD_AUX offset: 0 size: 0x2000 flags: 0x1 [T]
1 113720979812 0x6b10 [0x40]: PERF_RECORD_AUX offset: 0x2000 size: 0x2000 flags: 0x1 [T]--- arch/x86/events/intel/pt.c | 11 ++++++++--- arch/x86/events/intel/pt.h | 2 ++ 2 files changed, 10 insertions(+), 3 deletions(-)
arch/x86/events/intel/pt.c +8 -3
@@ -827,11 +827,13 @@ static void pt_buffer_advance(struct pt_ buf->cur_idx++;if (buf->cur_idx == buf->cur->last) { -if (buf->cur == buf->last) +if (buf->cur == buf->last) { buf->cur = buf->first; -else + buf->wrapped = true; + }else { buf->cur = list_entry(buf->cur->list.next, struct topa, list); + } buf->cur_idx =0 ; } }
@@ -845,8 +847,11 @@ static void pt_buffer_advance(struct pt_static void pt_update_head (struct pt *pt) {struct pt_buffer *buf =perf_get_aux (&pt->handle); +bool wrapped = buf->wrapped;u64 topa_idx, base, old; + buf->wrapped = false; +if (buf->single) {local_set (&buf->data_size, buf->output_off);return ;
@@ -864,7 +869,7 @@ static void pt_update_head(struct pt *pt }else { old = (local64_xchg (&buf->head, base) & ((buf->nr_pages <<PAGE_SHIFT ) -1 )); -if (base < old) +if (base < old || (base == old && wrapped)) base += buf->nr_pages <<PAGE_SHIFT ;local_add (base - old, &buf->data_size);
arch/x86/events/intel/pt.h +2 -0
@@ -65,6 +65,7 @@ struct pt_pmu {* @head: logical write offset inside the buffer * @snapshot: if this is for a snapshot/overwrite counter * @single: use Single Range Output instead of ToPA +* @wrapped: buffer advance wrapped back to the first topa table * @stop_pos: STOP topa entry index * @intr_pos: INT topa entry index * @stop_te: STOP topa entry pointer
@@ -82,6 +83,7 @@ struct pt_buffer {local64_t head;bool snapshot;bool single; +bool wrapped;long stop_pos, intr_pos;struct topa_entry *stop_te, *intr_te;void **data_pages;
Greg Kroah-Hartman
maintainerPATCH 475/676 crypto: x86/aegis128 - access 32-bit arguments as 32-bit
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Biggers <[email protected]>
commit 3b2f2d22fb424e9bebda4dbf6676cbfc7f9f62cd upstream.
Fix the AEGIS assembly code to access 'unsigned int' arguments as 32-bit values instead of 64-bit, since the upper bits of the corresponding 64-bit registers are not guaranteed to be zero.
Note: there haven't been any reports of this bug actually causing incorrect behavior. Neither gcc nor clang guarantee zero-extension to 64 bits, but zero-extension is likely to happen in practice because most instructions that operate on 32-bit registers zero-extend to 64 bits.
--- arch/x86/crypto/aegis128-aesni-asm.S | 29 +++++++++++++++-------------- 1 file changed, 15 insertions(+), 14 deletions(-)
arch/x86/crypto/aegis128-aesni-asm.S +15 -14
@@ -21,7 +21,7 @@ #define T1 %xmm7 #define STATEP %rdi -#define LEN %rsi +#define LEN %esi #define SRC %rdx #define DST %rcx
@@ -76,32 +76,32 @@ SYM_FUNC_START_LOCAL(__load_partial) xor %r9d, %r9d pxor MSG, MSG - mov LEN, %r8 + mov LEN, %r8d and $0x1, %r8 jz .Lld_partial_1 - mov LEN, %r8 + mov LEN, %r8d and $0x1E, %r8 add SRC, %r8 mov (%r8), %r9b .Lld_partial_1: - mov LEN, %r8 + mov LEN, %r8d and $0x2, %r8 jz .Lld_partial_2 - mov LEN, %r8 + mov LEN, %r8d and $0x1C, %r8 add SRC, %r8 shl $0x10, %r9 mov (%r8), %r9w .Lld_partial_2: - mov LEN, %r8 + mov LEN, %r8d and $0x4, %r8 jz .Lld_partial_4 - mov LEN, %r8 + mov LEN, %r8d and $0x18, %r8 add SRC, %r8 shl $32, %r9
@@ -111,11 +111,11 @@ SYM_FUNC_START_LOCAL(__load_partial) .Lld_partial_4: movq %r9, MSG - mov LEN, %r8 + mov LEN, %r8d and $0x8, %r8 jz .Lld_partial_8 - mov LEN, %r8 + mov LEN, %r8d and $0x10, %r8 add SRC, %r8 pslldq $8, MSG
@@ -139,7 +139,7 @@ SYM_FUNC_END(__load_partial) * %r10 */ SYM_FUNC_START_LOCAL(__store_partial) - mov LEN, %r8 + mov LEN, %r8d mov DST, %r9 movq T0, %r10
@@ -677,7 +677,7 @@ SYM_TYPED_FUNC_START(crypto_aegis128_aes call __store_partial /* mask with byte count: */ - movq LEN, T0 + movd LEN, T0 punpcklbw T0, T0 punpcklbw T0, T0 punpcklbw T0, T0
@@ -702,7 +702,8 @@ SYM_FUNC_END(crypto_aegis128_aesni_dec_t /* * void crypto_aegis128_aesni_final(void *state, void *tag_xor, - * u64 assoclen, u64 cryptlen); + * unsigned int assoclen, + * unsigned int cryptlen); */ SYM_FUNC_START(crypto_aegis128_aesni_final) FRAME_BEGIN
@@ -715,8 +716,8 @@ SYM_FUNC_START(crypto_aegis128_aesni_fin movdqu 0x40(STATEP), STATE4 /* prepare length block: */ - movq %rdx, MSG - movq %rcx, T0 + movd %edx, MSG + movd %ecx, T0 pslldq $8, T0 pxor T0, MSG psllq $3, MSG /* multiply by 8 (to get bit count) */
Greg Kroah-Hartman
maintainerPATCH 476/676 KVM: x86/mmu: Skip the "try unsync" path iff the old SPTE was a leaf SPTE
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sean Christopherson <[email protected]>
commit 2867eb782cf7f64c2ac427596133b6f9c3f64b7a upstream.
Apply make_spte()'s optimization to skip trying to unsync shadow pages if and only if the old SPTE was a leaf SPTE, as non-leaf SPTEs in direct MMUs are always writable, i.e. could trigger a false positive and incorrectly lead to KVM creating a SPTE without write-protecting or marking shadow pages unsync.
This bug only affects the TDP MMU, as the shadow MMU only overwrites a shadow-present SPTE when synchronizing SPTEs (and only 4KiB SPTEs can be unsync). Specifically, mmu_set_spte() drops any non-leaf SPTEs *before* calling make_spte(), whereas the TDP MMU can do a direct replacement of a page table with the leaf SPTE.
Opportunistically update the comment to explain why skipping the unsync stuff is safe, as opposed to simply saying "it's someone else's problem".
Message-ID: <[email protected]>
--- arch/x86/kvm/mmu/spte.c | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-)
arch/x86/kvm/mmu/spte.c +13 -5
@@ -206,12 +206,20 @@ bool make_spte(struct kvm_vcpu *vcpu, st spte |=PT_WRITABLE_MASK | shadow_mmu_writable_mask;/* -* Optimization: for pte sync, if spte was writable the hash -* lookup is unnecessary (and expensive). Write protection -* is responsibility of kvm_mmu_get_page / kvm_mmu_sync_roots. -* Same reasoning can be applied to dirty page accounting. +* When overwriting an existing leaf SPTE, and the old SPTE was +* writable, skip trying to unsync shadow pages as any relevant +* shadow pages must already be unsync, i.e. the hash lookup is +* unnecessary (and expensive). +* +* The same reasoning applies to dirty page/folio accounting; +* KVM will mark the folio dirty using the old SPTE, thus +* there's no need to immediately mark the new SPTE as dirty. +* +* Note, both cases rely on KVM not changing PFNs without first +* zapping the old SPTE, which is guaranteed by both the shadow +* MMU and the TDP MMU. */ -if (is_writable_pte (old_spte)) +if (is_last_spte (old_spte, level) &&is_writable_pte (old_spte)) goto out;/*
Greg Kroah-Hartman
maintainerPATCH 477/676 powerpc/pseries: Fix KVM guest detection for disabling hardlockup detector
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gautam Menghani <[email protected]>
commit 44e5d21e6d3fd2a1fed7f0327cf72e99397e2eaf upstream.
As per the kernel documentation[1], hardlockup detector should be disabled in KVM guests as it may give false positives. On PPC, hardlockup detector is enabled inside KVM guests because disable_hardlockup_detector() is marked as early_initcall and it relies on kvm_guest static key (is_kvm_guest()) which is initialized later during boot by check_kvm_guest(), which is a core_initcall. check_kvm_guest() is also called in pSeries_smp_probe(), which is called before initcalls, but it is skipped if KVM guest does not have doorbell support or if the guest is launched with SMT=1.
Call check_kvm_guest() in disable_hardlockup_detector() so that is_kvm_guest() check goes through fine and hardlockup detector can be disabled inside the KVM guest.
[1]: Documentation/admin-guide/sysctl/kernel.rst
--- arch/powerpc/kernel/setup_64.c | 1 + 1 file changed, 1 insertion(+)
arch/powerpc/kernel/setup_64.c +1 -0
@@ -924,6 +924,7 @@ static int __init disable_hardlockup_dethardlockup_detector_disable ();#else if (firmware_has_feature (FW_FEATURE_LPAR )) { +check_kvm_guest ();if (is_kvm_guest ())hardlockup_detector_disable (); }
Greg Kroah-Hartman
maintainerPATCH 478/676 KVM: arm64: vgic-v3: Sanitise guest writes to GICR_INVLPIR
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Marc Zyngier <[email protected]>
commit d561491ba927cb5634094ff311795e9d618e9b86 upstream.
Make sure we filter out non-LPI invalidation when handling writes to GICR_INVLPIR.
--- arch/arm64/kvm/vgic/vgic-mmio-v3.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-)
arch/arm64/kvm/vgic/vgic-mmio-v3.c +6 -1
@@ -555,6 +555,7 @@ static void vgic_mmio_write_invlpi(struc unsigned long val) {struct vgic_irq *irq; +u32 intid;/* * If the guest wrote only to the upper 32bit part of the
@@ -566,9 +567,13 @@ static void vgic_mmio_write_invlpi(strucif ((addr &4 ) || !vgic_lpis_enabled (vcpu))return ; + intid =lower_32_bits (val); +if (intid <VGIC_MIN_LPI ) +return ; +vgic_set_rdist_busy (vcpu, true); - irq =vgic_get_irq (vcpu->kvm,NULL ,lower_32_bits (val)); + irq =vgic_get_irq (vcpu->kvm,NULL , intid);if (irq) {vgic_its_inv_lpi (vcpu->kvm, irq);vgic_put_irq (vcpu->kvm, irq);
Greg Kroah-Hartman
maintainerPATCH 479/676 KVM: arm64: Ignore PMCNTENSET_EL0 while checking for overflow status
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Raghavendra Rao Ananta <[email protected]>
commit 54bbee190d42166209185d89070c58a343bf514b upstream.
DDI0487K.a D13.3.1 describes the PMU overflow condition, which evaluates to true if any counter's global enable (PMCR_EL0.E), overflow flag (PMOVSSET_EL0[n]), and interrupt enable (PMINTENSET_EL1[n]) are all 1. Of note, this does not require a counter to be enabled
(i.e. PMCNTENSET_EL0[n] = 1) to generate an overflow.
Align kvm_pmu_overflow_status() with the reality of the architecture and stop using PMCNTENSET_EL0 as part of the overflow condition. The bug was discovered while running an SBSA PMU test [*], which only sets PMCR.E, PMOVSSET<0>, PMINTENSET<0>, and expects an overflow interrupt.
--- arch/arm64/kvm/pmu-emul.c | 1 - 1 file changed, 1 deletion(-)
arch/arm64/kvm/pmu-emul.c +0 -1
@@ -326,7 +326,6 @@ static u64 kvm_pmu_overflow_status(strucif ((__vcpu_sys_reg (vcpu,PMCR_EL0 ) &ARMV8_PMU_PMCR_E )) { reg =__vcpu_sys_reg (vcpu,PMOVSSET_EL0 ); - reg &=__vcpu_sys_reg (vcpu,PMCNTENSET_EL0 ); reg &=__vcpu_sys_reg (vcpu,PMINTENSET_EL1 ); }
Greg Kroah-Hartman
maintainerPATCH 480/676 KVM: arm64: vgic-its: Clear ITE when DISCARD frees an ITE
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kunkun Jiang <[email protected]>
commit 7602ffd1d5e8927fadd5187cb4aed2fdc9c47143 upstream.
When DISCARD frees an ITE, it does not invalidate the corresponding ITE. In the scenario of continuous saves and restores, there may be a situation where an ITE is not saved but is restored. This is unreasonable and may cause restore to fail. This patch clears the corresponding ITE when DISCARD frees an ITE.
--- arch/arm64/kvm/vgic/vgic-its.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
arch/arm64/kvm/vgic/vgic-its.c +5 -1
@@ -855,6 +855,9 @@ static int vgic_its_cmd_handle_discard(s ite =find_ite (its, device_id, event_id);if (ite &&its_is_collection_mapped (ite->collection)) { +struct its_device *device =find_its_device (its, device_id); +int ite_esz =vgic_its_get_abi (its)->ite_esz; +gpa_t gpa = device->itt_addr + ite->event_id * ite_esz;/* * Though the spec talks about removing the pending state, we * don't bother here since we clear the ITTE anyway and the
@@ -863,7 +866,8 @@ static int vgic_its_cmd_handle_discard(svgic_its_invalidate_cache (kvm);its_free_ite (kvm, ite); -return 0 ; + +return vgic_its_write_entry_lock (its, gpa,0 , ite_esz); }return E_ITS_DISCARD_UNMAPPED_INTERRUPT ;
Greg Kroah-Hartman
maintainerPATCH 481/676 KVM: arm64: Get rid of userspace_irqchip_in_use
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Raghavendra Rao Ananta <[email protected]>
commit 38d7aacca09230fdb98a34194fec2af597e8e20d upstream.
Improper use of userspace_irqchip_in_use led to syzbot hitting the following WARN_ON() in kvm_timer_update_irq():
WARNING: CPU: 0 PID: 3281 at arch/arm64/kvm/arch_timer.c:459 kvm_timer_update_irq+0x21c/0x394 Call trace: kvm_timer_update_irq+0x21c/0x394 arch/arm64/kvm/arch_timer.c:459 kvm_timer_vcpu_reset+0x158/0x684 arch/arm64/kvm/arch_timer.c:968 kvm_reset_vcpu+0x3b4/0x560 arch/arm64/kvm/reset.c:264 kvm_vcpu_set_target arch/arm64/kvm/arm.c:1553 [inline] kvm_arch_vcpu_ioctl_vcpu_init arch/arm64/kvm/arm.c:1573 [inline] kvm_arch_vcpu_ioctl+0x112c/0x1b3c arch/arm64/kvm/arm.c:1695 kvm_vcpu_ioctl+0x4ec/0xf74 virt/kvm/kvm_main.c:4658 vfs_ioctl fs/ioctl.c:51 [inline] __do_sys_ioctl fs/ioctl.c:907 [inline] __se_sys_ioctl fs/ioctl.c:893 [inline] __arm64_sys_ioctl+0x108/0x184 fs/ioctl.c:893 __invoke_syscall arch/arm64/kernel/syscall.c:35 [inline] invoke_syscall+0x78/0x1b8 arch/arm64/kernel/syscall.c:49 el0_svc_common+0xe8/0x1b0 arch/arm64/kernel/syscall.c:132 do_el0_svc+0x40/0x50 arch/arm64/kernel/syscall.c:151 el0_svc+0x54/0x14c arch/arm64/kernel/entry-common.c:712 el0t_64_sync_handler+0x84/0xfc arch/arm64/kernel/entry-common.c:730 el0t_64_sync+0x190/0x194 arch/arm64/kernel/entry.S:598
The following sequence led to the scenario:
- Userspace creates a VM and a vCPU.
- The vCPU is initialized with KVM_ARM_VCPU_PMU_V3 during KVM_ARM_VCPU_INIT.
- Without any other setup, such as vGIC or vPMU, userspace issues KVM_RUN on the vCPU. Since the vPMU is requested, but not setup, kvm_arm_pmu_v3_enable() fails in kvm_arch_vcpu_run_pid_change(). As a result, KVM_RUN returns after enabling the timer, but before incrementing 'userspace_irqchip_in_use':
kvm_arch_vcpu_run_pid_change()
ret = kvm_arm_pmu_v3_enable()
if (!vcpu->arch.pmu.created)
return -EINVAL;
if (ret)
return ret;
[...]
if (!irqchip_in_kernel(kvm))
static_branch_inc(&userspace_irqchip_in_use);
- Userspace ignores the error and issues KVM_ARM_VCPU_INIT again.
Since the timer is already enabled, control moves through the
following flow, ultimately hitting the WARN_ON():
kvm_timer_vcpu_reset()
if (timer->enabled)
kvm_timer_update_irq()
if (!userspace_irqchip())
ret = kvm_vgic_inject_irq()
ret = vgic_lazy_init()
if (unlikely(!vgic_initialized(kvm)))
if (kvm->arch.vgic.vgic_model !=
KVM_DEV_TYPE_ARM_VGIC_V2)
return -EBUSY;
WARN_ON(ret);Theoretically, since userspace_irqchip_in_use's functionality can be simply replaced by '!irqchip_in_kernel()', get rid of the static key to avoid the mismanagement, which also helps with the syzbot issue.
--- arch/arm64/include/asm/kvm_host.h | 2 -- arch/arm64/kvm/arch_timer.c | 3 +-- arch/arm64/kvm/arm.c | 18 +++--------------- 3 files changed, 4 insertions(+), 19 deletions(-)
arch/arm64/include/asm/kvm_host.h +0 -2
@@ -72,8 +72,6 @@ enum kvm_mode kvm_get_mode(void);static inline enum kvm_mode kvm_get_mode (void ) {return KVM_MODE_NONE ; };#endif -DECLARE_STATIC_KEY_FALSE (userspace_irqchip_in_use); -extern unsigned int __ro_after_init kvm_sve_max_vl;int __init kvm_arm_init_sve (void );
arch/arm64/kvm/arch_timer.c +1 -2
@@ -206,8 +206,7 @@ void get_timer_map(struct kvm_vcpu *vcpustatic inline bool userspace_irqchip (struct kvm *kvm) { -return static_branch_unlikely (&userspace_irqchip_in_use) && -unlikely (!irqchip_in_kernel (kvm)); +return unlikely (!irqchip_in_kernel (kvm)); }static void soft_timer_start (struct hrtimer *hrt,u64 ns)
arch/arm64/kvm/arm.c +3 -15
@@ -57,7 +57,6 @@ DECLARE_KVM_NVHE_PER_CPU(struct kvm_cpu_static bool vgic_present, kvm_arm_initialised; static DEFINE_PER_CPU(unsigned char, kvm_hyp_initialized); -DEFINE_STATIC_KEY_FALSE (userspace_irqchip_in_use);bool is_kvm_arm_initialised (void ) {
@@ -401,9 +400,6 @@ void kvm_arch_vcpu_postcreate(struct kvmvoid kvm_arch_vcpu_destroy (struct kvm_vcpu *vcpu) { -if (vcpu_has_run_once (vcpu) &&unlikely (!irqchip_in_kernel (vcpu->kvm))) -static_branch_dec (&userspace_irqchip_in_use); -kvm_mmu_free_memory_cache (&vcpu->arch.mmu_page_cache);kvm_timer_vcpu_terminate (vcpu);kvm_pmu_vcpu_destroy (vcpu);
@@ -627,14 +623,6 @@ int kvm_arch_vcpu_run_pid_change(structreturn ret; } -if (!irqchip_in_kernel (kvm)) { -/* -* Tell the rest of the code that there are userspace irqchip -* VMs in the wild. -*/ -static_branch_inc (&userspace_irqchip_in_use); - } -/* * Initialize traps for protected VMs. * NOTE: Move to run in EL2 directly, rather than via a hypercall, once
@@ -856,7 +844,7 @@ static bool kvm_vcpu_exit_request(struct* state gets updated in kvm_timer_update_run and * kvm_pmu_update_run below). */ -if (static_branch_unlikely (&userspace_irqchip_in_use)) { +if (unlikely (!irqchip_in_kernel (vcpu->kvm))) {if (kvm_timer_should_notify_user (vcpu) ||kvm_pmu_should_notify_user (vcpu)) { *ret = -EINTR ;
@@ -975,7 +963,7 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_v vcpu->mode =OUTSIDE_GUEST_MODE ;isb ();/* Ensure work in x_flush_hwstate is committed */ kvm_pmu_sync_hwstate (vcpu); -if (static_branch_unlikely (&userspace_irqchip_in_use)) +if (unlikely (!irqchip_in_kernel (vcpu->kvm)))kvm_timer_sync_user (vcpu);kvm_vgic_sync_hwstate (vcpu);local_irq_enable ();
@@ -1021,7 +1009,7 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_v* we don't want vtimer interrupts to race with syncing the * timer virtual interrupt state. */ -if (static_branch_unlikely (&userspace_irqchip_in_use)) +if (unlikely (!irqchip_in_kernel (vcpu->kvm)))kvm_timer_sync_user (vcpu);kvm_arch_vcpu_ctxsync_fp (vcpu);
Greg Kroah-Hartman
maintainerPATCH 482/676 KVM: arm64: vgic-its: Add a data length check in vgic_its_save_*
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jing Zhang <[email protected]>
commit 7fe28d7e68f92cc3d0668b8f2fbdf5c303ac3022 upstream.
In all the vgic_its_save_*() functinos, they do not check whether the data length is 8 bytes before calling vgic_write_guest_lock. This patch adds the check. To prevent the kernel from being blown up when the fault occurs, KVM_BUG_ON() is used. And the other BUG_ON()s are replaced together.
--- arch/arm64/kvm/vgic/vgic-its.c | 20 ++++++++------------ arch/arm64/kvm/vgic/vgic.h | 23 +++++++++++++++++++++++ 2 files changed, 31 insertions(+), 12 deletions(-)
arch/arm64/kvm/vgic/vgic-its.c +8 -12
@@ -2211,7 +2211,6 @@ static int scan_its_table(struct vgic_itstatic int vgic_its_save_ite (struct vgic_its *its,struct its_device *dev,struct its_ite *ite,gpa_t gpa,int ite_esz) { -struct kvm *kvm = its->dev->kvm;u32 next_offset;u64 val;
@@ -2220,7 +2219,8 @@ static int vgic_its_save_ite(struct vgic ((u64 )ite->irq->intid <<KVM_ITS_ITE_PINTID_SHIFT ) | ite->collection->collection_id; val =cpu_to_le64 (val); -return vgic_write_guest_lock (kvm, gpa, &val, ite_esz); + +return vgic_its_write_entry_lock (its, gpa, val, ite_esz); }/**
@@ -2361,7 +2361,6 @@ static int vgic_its_restore_itt(struct vstatic int vgic_its_save_dte (struct vgic_its *its,struct its_device *dev,gpa_t ptr,int dte_esz) { -struct kvm *kvm = its->dev->kvm;u64 val, itt_addr_field;u32 next_offset;
@@ -2372,7 +2371,8 @@ static int vgic_its_save_dte(struct vgic (itt_addr_field <<KVM_ITS_DTE_ITTADDR_SHIFT ) | (dev->num_eventid_bits - 1)); val =cpu_to_le64 (val); -return vgic_write_guest_lock (kvm, ptr, &val, dte_esz); + +return vgic_its_write_entry_lock (its, ptr, val, dte_esz); }/**
@@ -2559,7 +2559,8 @@ static int vgic_its_save_cte(struct vgic ((u64 )collection->target_addr <<KVM_ITS_CTE_RDBASE_SHIFT ) | collection->collection_id); val =cpu_to_le64 (val); -return vgic_write_guest_lock (its->dev->kvm, gpa, &val, esz); + +return vgic_its_write_entry_lock (its, gpa, val, esz); }/*
@@ -2575,8 +2576,7 @@ static int vgic_its_restore_cte(struct vu64 val;int ret; -BUG_ON (esz >sizeof (val)); - ret =kvm_read_guest_lock (kvm, gpa, &val, esz); + ret =vgic_its_read_entry_lock (its, gpa, &val, esz);if (ret)return ret; val =le64_to_cpu (val);
@@ -2614,7 +2614,6 @@ static int vgic_its_save_collection_tablu64 baser = its->baser_coll_table;gpa_t gpa =GITS_BASER_ADDR_48_to_52 (baser);struct its_collection *collection; -u64 val;size_t max_size, filled =0 ;int ret, cte_esz = abi->cte_esz;
@@ -2638,10 +2637,7 @@ static int vgic_its_save_collection_tabl* table is not fully filled, add a last dummy element * with valid bit unset */ - val =0 ; -BUG_ON (cte_esz >sizeof (val)); - ret =vgic_write_guest_lock (its->dev->kvm, gpa, &val, cte_esz); -return ret; +return vgic_its_write_entry_lock (its, gpa,0 , cte_esz); }/**
arch/arm64/kvm/vgic/vgic.h +23 -0
@@ -145,6 +145,29 @@ static inline int vgic_write_guest_lock(return ret; } +static inline int vgic_its_read_entry_lock (struct vgic_its *its,gpa_t eaddr, +u64 *eval,unsigned long esize) +{ +struct kvm *kvm = its->dev->kvm; + +if (KVM_BUG_ON (esize !=sizeof (*eval), kvm)) +return -EINVAL ; + +return kvm_read_guest_lock (kvm, eaddr, eval, esize); + +} + +static inline int vgic_its_write_entry_lock (struct vgic_its *its,gpa_t eaddr, +u64 eval,unsigned long esize) +{ +struct kvm *kvm = its->dev->kvm; + +if (KVM_BUG_ON (esize !=sizeof (eval), kvm)) +return -EINVAL ; + +return vgic_write_guest_lock (kvm, eaddr, &eval, esize); +} +/* * This struct provides an intermediate representation of the fields contained * in the GICH_VMCR and ICH_VMCR registers, such that code exporting the GIC
Greg Kroah-Hartman
maintainerPATCH 483/676 KVM: arm64: vgic-its: Clear DTE when MAPD unmaps a device
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kunkun Jiang <[email protected]>
commit e9649129d33dca561305fc590a7c4ba8c3e5675a upstream.
vgic_its_save_device_tables will traverse its->device_list to save DTE for each device. vgic_its_restore_device_tables will traverse each entry of device table and check if it is valid. Restore if valid.
But when MAPD unmaps a device, it does not invalidate the corresponding DTE. In the scenario of continuous saves and restores, there may be a situation where a device's DTE is not saved but is restored. This is unreasonable and may cause restore to fail. This patch clears the corresponding DTE when MAPD unmaps a device.
--- arch/arm64/kvm/vgic/vgic-its.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
arch/arm64/kvm/vgic/vgic-its.c +4 -2
@@ -1215,9 +1215,11 @@ static int vgic_its_cmd_handle_mapd(strubool valid =its_cmd_get_validbit (its_cmd);u8 num_eventid_bits =its_cmd_get_size (its_cmd);gpa_t itt_addr =its_cmd_get_ittaddr (its_cmd); +int dte_esz =vgic_its_get_abi (its)->dte_esz;struct its_device *device; +gpa_t gpa; -if (!vgic_its_check_id (its, its->baser_device_table, device_id,NULL )) +if (!vgic_its_check_id (its, its->baser_device_table, device_id, &gpa))return E_ITS_MAPD_DEVICE_OOR ;if (valid && num_eventid_bits >VITS_TYPER_IDBITS )
@@ -1238,7 +1240,7 @@ static int vgic_its_cmd_handle_mapd(stru* is an error, so we are done in any case. */ if (!valid) -return 0 ; +return vgic_its_write_entry_lock (its, gpa,0 , dte_esz); device =vgic_its_alloc_device (its, device_id, itt_addr, num_eventid_bits);
Greg Kroah-Hartman
maintainerPATCH 484/676 PCI: Fix use-after-free of slot->bus on hot remove
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Lukas Wunner <[email protected]>
commit c7acef99642b763ba585f4a43af999fcdbcc3dc4 upstream.
Dennis reports a boot crash on recent Lenovo laptops with a USB4 dock.
Since commit 0fc70886569c ("thunderbolt: Reset USB4 v2 host router") and commit 59a54c5f3dbd ("thunderbolt: Reset topology created by the boot firmware"), USB4 v2 and v1 Host Routers are reset on probe of the thunderbolt driver.
The reset clears the Presence Detect State and Data Link Layer Link Active bits at the USB4 Host Router's Root Port and thus causes hot removal of the dock.
The crash occurs when pciehp is unbound from one of the dock's Downstream
Ports: pciehp creates a pci_slot on bind and destroys it on unbind. The pci_slot contains a pointer to the pci_bus below the Downstream Port, but a reference on that pci_bus is never acquired. The pci_bus is destroyed before the pci_slot, so a use-after-free ensues when pci_slot_release() accesses slot->bus.
In principle this should not happen because pci_stop_bus_device() unbinds pciehp (and therefore destroys the pci_slot) before the pci_bus is destroyed by pci_remove_bus_device().
However the stacktrace provided by Dennis shows that pciehp is unbound from pci_remove_bus_device() instead of pci_stop_bus_device(). To understand the significance of this, one needs to know that the PCI core uses a two step process to remove a portion of the hierarchy: It first unbinds all drivers in the sub-hierarchy in pci_stop_bus_device() and then actually removes the devices in pci_remove_bus_device(). There is no precaution to prevent driver binding in-between pci_stop_bus_device() and pci_remove_bus_device().
In Dennis' case, it seems removal of the hierarchy by pciehp races with driver binding by pci_bus_add_devices(). pciehp is bound to the Downstream Port after pci_stop_bus_device() has run, so it is unbound by pci_remove_bus_device() instead of pci_stop_bus_device(). Because the pci_bus has already been destroyed at that point, accesses to it result in a use-after-free.
One might conclude that driver binding needs to be prevented after pci_stop_bus_device() has run. However it seems risky that pci_slot points to pci_bus without holding a reference. Solely relying on correct ordering of driver unbind versus pci_bus destruction is certainly not defensive programming.
If pci_slot has a need to access data in pci_bus, it ought to acquire a reference. Amend pci_create_slot() accordingly. Dennis reports that the crash is not reproducible with this change.
Abridged stacktrace:
pcieport 0000:00:07.0: PME: Signaling with IRQ 156
pcieport 0000:00:07.0: pciehp: Slot #12 AttnBtn- PwrCtrl- MRL- AttnInd- PwrInd- HotPlug+ Surprise+ Interlock- NoCompl+ IbPresDis- LLActRep+ pci_bus 0000:20: dev 00, created physical slot 12
pcieport 0000:00:07.0: pciehp: Slot(12): Card not present
...
pcieport 0000:21:02.0: pciehp: pcie_disable_notification: SLOTCTRL d8 write cmd 0
Oops: general protection fault, probably for non-canonical address 0x6b6b6b6b6b6b6b6b: 0000 [#1] PREEMPT SMP NOPTI CPU: 13 UID: 0 PID: 134 Comm: irq/156-pciehp Not tainted 6.11.0-devel+ #1 RIP: 0010:dev_driver_string+0x12/0x40 pci_destroy_slot pciehp_remove pcie_port_remove_service device_release_driver_internal bus_remove_device device_del device_unregister remove_iter device_for_each_child pcie_portdrv_remove pci_device_remove device_release_driver_internal bus_remove_device device_del pci_remove_bus_device (recursive invocation) pci_remove_bus_device pciehp_unconfigure_device pciehp_disable_slot pciehp_handle_presence_or_link_change pciehp_ist
--- drivers/pci/slot.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/pci/slot.c +3 -1
@@ -79,6 +79,7 @@ static void pci_slot_release(struct kobjup_read (&pci_bus_sem);list_del (&slot->list); +pci_bus_put (slot->bus);kfree (slot); }
@@ -261,7 +262,7 @@ placeholder: goto err; } - slot->bus = parent; + slot->bus =pci_bus_get (parent); slot->number = slot_nr; slot->kobj.kset = pci_slots_kset;
@@ -269,6 +270,7 @@ placeholder: slot_name =make_slot_name (name);if (!slot_name) { err = -ENOMEM ; +pci_bus_put (slot->bus);kfree (slot); goto err; }
Greg Kroah-Hartman
maintainerPATCH 485/676 fsnotify: fix sending inotify event with unexpected filename
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Amir Goldstein <[email protected]>
commit aa52c54da40d9eee3ba87c05cdcb0cd07c04fa13 upstream.
We got a report that adding a fanotify filsystem watch prevents tail -f from receiving events.
Reproducer:
1. Create 3 windows / login sessions. Become root in each session.
2. Choose a mounted filesystem that is pretty quiet; I picked /boot.
3. In the first window, run: fsnotifywait -S -m /boot
4. In the second window, run: echo data >> /boot/foo
5. In the third window, run: tail -f /boot/foo
6. Go back to the second window and run: echo more data >> /boot/foo
7. Observe that the tail command doesn't show the new data.
8. In the first window, hit control-C to interrupt fsnotifywait.
9. In the second window, run: echo still more data >> /boot/foo
10. Observe that the tail command in the third window has now printed the missing data.
When stracing tail, we observed that when fanotify filesystem mark is set, tail does get the inotify event, but the event is receieved with the filename:
read(4, "\1\0\0\0\2\0\0\0\0\0\0\0\20\0\0\0foo\0\0\0\0\0\0\0\0\0\0\0\0\0",
50) = 32
This is unexpected, because tail is watching the file itself and not its parent and is inconsistent with the inotify event received by tail when fanotify filesystem mark is not set:
read(4, "\1\0\0\0\2\0\0\0\0\0\0\0\0\0\0\0", 50) = 16
The inteference between different fsnotify groups was caused by the fact that the mark on the sb requires the filename, so the filename is passed to fsnotify(). Later on, fsnotify_handle_event() tries to take care of not passing the filename to groups (such as inotify) that are interested in the filename only when the parent is watching.
But the logic was incorrect for the case that no group is watching the parent, some groups are watching the sb and some watching the inode.
--- fs/notify/fsnotify.c | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-)
fs/notify/fsnotify.c +13 -10
@@ -310,16 +310,19 @@ static int fsnotify_handle_event(structif (!inode_mark)return 0 ; -if (mask &FS_EVENT_ON_CHILD ) { -/* -* Some events can be sent on both parent dir and child marks -* (e.g. FS_ATTRIB). If both parent dir and child are -* watching, report the event once to parent dir with name (if -* interested) and once to child without name (if interested). -* The child watcher is expecting an event without a file name -* and without the FS_EVENT_ON_CHILD flag. -*/ - mask &= ~FS_EVENT_ON_CHILD ; +/* +* Some events can be sent on both parent dir and child marks (e.g. +* FS_ATTRIB). If both parent dir and child are watching, report the +* event once to parent dir with name (if interested) and once to child +* without name (if interested). +* +* In any case regardless whether the parent is watching or not, the +* child watcher is expecting an event without the FS_EVENT_ON_CHILD +* flag. The file name is expected if and only if this is a directory +* event. +*/ + mask &= ~FS_EVENT_ON_CHILD ; +if (!(mask &ALL_FSNOTIFY_DIRENT_EVENTS )) { dir =NULL ; name =NULL ; }
Greg Kroah-Hartman
maintainerPATCH 486/676 comedi: Flush partial mappings in error case
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jann Horn <[email protected]>
commit ce8f9fb651fac95dd41f69afe54d935420b945bd upstream.
If some remap_pfn_range() calls succeeded before one failed, we still have buffer pages mapped into the userspace page tables when we drop the buffer reference with comedi_buf_map_put(bm). The userspace mappings are only cleaned up later in the mmap error path.
Fix it by explicitly flushing all mappings in our VMA on the error path.
See commit 79a61cc3fc04 ("mm: avoid leaving partial pfn mappings around in error case").
--- drivers/comedi/comedi_fops.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
drivers/comedi/comedi_fops.c +12 -0
@@ -2407,6 +2407,18 @@ static int comedi_mmap(struct file *file start +=PAGE_SIZE ; } + +#ifdef CONFIG_MMU +/* +* Leaving behind a partial mapping of a buffer we're about to +* drop is unsafe, see remap_pfn_range_notrack(). +* We need to zap the range here ourselves instead of relying +* on the automatic zapping in remap_pfn_range() because we call +* remap_pfn_range() in a loop. +*/ +if (retval) +zap_vma_ptes (vma, vma->vm_start, size); +#endif }if (retval ==0 ) {
Greg Kroah-Hartman
maintainerPATCH 487/676 apparmor: test: Fix memory leak for aa_unpack_strdup()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jinjie Ruan <[email protected]>
commit 7290f59231910ccba427d441a6e8b8c6f6112448 upstream.
The string allocated by kmemdup() in aa_unpack_strdup() is not freed and cause following memory leaks, free them to fix it.
unreferenced object 0xffffff80c6af8a50 (size 8): comm "kunit_try_catch", pid 225, jiffies 4294894407 hex dump (first 8 bytes): 74 65 73 74 69 6e 67 00 testing. backtrace (crc 5eab668b): [<0000000001e3714d>] kmemleak_alloc+0x34/0x40 [<000000006e6c7776>] __kmalloc_node_track_caller_noprof+0x300/0x3e0 [<000000006870467c>] kmemdup_noprof+0x34/0x60 [<000000001176bb03>] aa_unpack_strdup+0xd0/0x18c [<000000008ecde918>] policy_unpack_test_unpack_strdup_with_null_name+0xf8/0x3ec [<0000000032ef8f77>] kunit_try_run_case+0x13c/0x3ac [<00000000f3edea23>] kunit_generic_run_threadfn_adapter+0x80/0xec [<00000000adf936cf>] kthread+0x2e8/0x374 [<0000000041bb1628>] ret_from_fork+0x10/0x20 unreferenced object 0xffffff80c2a29090 (size 8): comm "kunit_try_catch", pid 227, jiffies 4294894409 hex dump (first 8 bytes): 74 65 73 74 69 6e 67 00 testing. backtrace (crc 5eab668b): [<0000000001e3714d>] kmemleak_alloc+0x34/0x40 [<000000006e6c7776>] __kmalloc_node_track_caller_noprof+0x300/0x3e0 [<000000006870467c>] kmemdup_noprof+0x34/0x60 [<000000001176bb03>] aa_unpack_strdup+0xd0/0x18c [<0000000046a45c1a>] policy_unpack_test_unpack_strdup_with_name+0xd0/0x3c4 [<0000000032ef8f77>] kunit_try_run_case+0x13c/0x3ac [<00000000f3edea23>] kunit_generic_run_threadfn_adapter+0x80/0xec [<00000000adf936cf>] kthread+0x2e8/0x374 [<0000000041bb1628>] ret_from_fork+0x10/0x20
--- security/apparmor/policy_unpack_test.c | 6 ++++++ 1 file changed, 6 insertions(+)
security/apparmor/policy_unpack_test.c +6 -0
@@ -281,6 +281,8 @@ static void policy_unpack_test_unpack_st ((uintptr_t )puf->e->start <= (uintptr_t )string) && ((uintptr_t)string <= (uintptr_t)puf->e->end));KUNIT_EXPECT_STREQ (test, string,TEST_STRING_DATA ); + +kfree (string); }static void policy_unpack_test_unpack_strdup_with_name (struct kunit *test)
@@ -296,6 +298,8 @@ static void policy_unpack_test_unpack_st ((uintptr_t )puf->e->start <= (uintptr_t )string) && ((uintptr_t)string <= (uintptr_t)puf->e->end));KUNIT_EXPECT_STREQ (test, string,TEST_STRING_DATA ); + +kfree (string); }static void policy_unpack_test_unpack_strdup_out_of_bounds (struct kunit *test)
@@ -313,6 +317,8 @@ static void policy_unpack_test_unpack_stKUNIT_EXPECT_EQ (test, size,0 );KUNIT_EXPECT_NULL (test, string);KUNIT_EXPECT_PTR_EQ (test, puf->e->pos, start); + +kfree (string); }static void policy_unpack_test_unpack_nameX_with_null_name (struct kunit *test)
Greg Kroah-Hartman
maintainerPATCH 488/676 tty: ldsic: fix tty_ldisc_autoload sysctls proc_handler
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nicolas Bouchinet <[email protected]>
commit 635a9fca54f4f4148be1ae1c7c6bd37af80f5773 upstream.
Commit 7c0cca7c847e ("tty: ldisc: add sysctl to prevent autoloading of ldiscs") introduces the tty_ldisc_autoload sysctl with the wrong proc_handler. .extra1 and .extra2 parameters are set to avoid other values thant SYSCTL_ZERO or SYSCTL_ONE to be set but proc_dointvec do not uses them.
This commit fixes this by using proc_dointvec_minmax instead of proc_dointvec.
--- drivers/tty/tty_io.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/tty/tty_io.c +1 -1
@@ -3607,7 +3607,7 @@ static struct ctl_table tty_table[] = { .data = &tty_ldisc_autoload, .maxlen = sizeof(tty_ldisc_autoload), .mode = 0644, - .proc_handler = proc_dointvec, + .proc_handler = proc_dointvec_minmax, .extra1 = SYSCTL_ZERO, .extra2 = SYSCTL_ONE, },
Greg Kroah-Hartman
maintainerPATCH 489/676 locking/lockdep: Avoid creating new name string literals in lockdep_set_subclass()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ahmed Ehab <[email protected]>
commit d7fe143cb115076fed0126ad8cf5ba6c3e575e43 upstream.
Syzbot reports a problem that a warning will be triggered while searching a lock class in look_up_lock_class().
The cause of the issue is that a new name is created and used by lockdep_set_subclass() instead of using the existing one. This results in a lock instance has a different name pointer than previous registered one stored in lock class, and WARN_ONCE() is triggered because of that in look_up_lock_class().
To fix this, change lockdep_set_subclass() to use the existing name instead of a new one. Hence, no new name will be created by lockdep_set_subclass(). Hence, the warning is avoided.
[boqun: Reword the commit log to state the correct issue]
--- include/linux/lockdep.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
include/linux/lockdep.h +1 -1
@@ -230,7 +230,7 @@ static inline void lockdep_init_map(stru (lock)->dep_map.lock_type)#define lockdep_set_subclass (lock, sub) \ - lockdep_init_map_type(&(lock)->dep_map, #lock, (lock)->dep_map.key, sub,\ + lockdep_init_map_type(&(lock)->dep_map, (lock)->dep_map.name, (lock)->dep_map.key, sub,\ (lock)->dep_map.wait_type_inner, \ (lock)->dep_map.wait_type_outer, \ (lock)->dep_map.lock_type)
Greg Kroah-Hartman
maintainerPATCH 490/676 tools/nolibc: s390: include std.h
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Thomas Weißschuh <[email protected]>
commit 711b5875814b2a0e9a5aaf7a85ba7c80f5a389b1 upstream.
arch-s390.h uses types from std.h, but does not include it. Depending on the inclusion order the compilation can fail. Include std.h explicitly to avoid these errors.
--- tools/include/nolibc/arch-s390.h | 1 + 1 file changed, 1 insertion(+)
tools/include/nolibc/arch-s390.h +1 -0
@@ -10,6 +10,7 @@#include "compiler.h" #include "crt.h" +#include "std.h" /* Syscalls for s390: * - registers are 64-bit
Signature · 1 line
2.47.1
Greg Kroah-Hartman
maintainerPATCH 491/676 pinctrl: qcom: spmi: fix debugfs drive strength
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johan Hovold <[email protected]>
commit 6bc0ebfb1d920f13c522545f114cdabb49e9408a upstream.
Commit 723e8462a4fe ("pinctrl: qcom: spmi-gpio: Fix the GPIO strength mapping") fixed a long-standing issue in the Qualcomm SPMI PMIC gpio driver which had the 'low' and 'high' drive strength settings switched but failed to update the debugfs interface which still gets this wrong.
Fix the debugfs code so that the exported values match the hardware settings.
Note that this probably means that most devicetrees that try to describe the firmware settings got this wrong if the settings were derived from debugfs. Before the above mentioned commit the settings would have actually matched the firmware settings even if they were described incorrectly, but now they are inverted.
--- drivers/pinctrl/qcom/pinctrl-spmi-gpio.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/pinctrl/qcom/pinctrl-spmi-gpio.c +1 -1
@@ -667,7 +667,7 @@ static void pmic_gpio_config_dbg_show(st "push-pull", "open-drain", "open-source" };static const char *const strengths[] = { -"no" ,"high" ,"medium" ,"low" +"no" ,"low" ,"medium" ,"high" }; pad = pctldev->desc->pins[pin].drv_data;
Greg Kroah-Hartman
maintainerPATCH 492/676 dt-bindings: iio: dac: ad3552r: fix maximum spi speed
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Angelo Dureghello <[email protected]>
commit d1d1c117f39b2057d1e978f26a8bd9631ddb193b upstream.
Fix maximum SPI clock speed, as per datasheet (Rev. B, page 6).
--- Documentation/devicetree/bindings/iio/dac/adi,ad3552r.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
Documentation/devicetree/bindings/iio/dac/adi,ad3552r.yaml +1 -1
@@ -26,7 +26,7 @@ properties: maxItems: 1 spi-max-frequency: - maximum: 30000000 + maximum: 66000000 reset-gpios: maxItems: 1
Greg Kroah-Hartman
maintainerPATCH 493/676 exfat: fix uninit-value in __exfat_get_dentry_set
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Namjae Jeon <[email protected]>
commit 02dffe9ab092fc4c8800aee68cb7eafd37a980c4 upstream.
There is no check if stream size and start_clu are invalid. If start_clu is EOF cluster and stream size is 4096, It will cause uninit value access. because ei->hint_femp.eidx could be 128(if cluster size is 4K) and wrong hint will allocate next cluster. and this cluster will be same with the cluster that is allocated by exfat_extend_valid_size(). The previous patch will check invalid start_clu, but for clarity, initialize hint_femp.eidx to zero.
--- fs/exfat/namei.c | 1 + 1 file changed, 1 insertion(+)
fs/exfat/namei.c +1 -0
@@ -377,6 +377,7 @@ static int exfat_find_empty_entry(structif (ei->start_clu ==EXFAT_EOF_CLUSTER ) { ei->start_clu = clu.dir; p_dir->dir = clu.dir; + hint_femp.eidx =0 ; }/* append to the FAT chain */
Greg Kroah-Hartman
maintainerPATCH 494/676 Bluetooth: Fix type of len in rfcomm_sock_getsockopt{,_old}()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andrej Shadura <[email protected]>
commit 5fe6caa62b07fd39cd6a28acc8f92ba2955e11a6 upstream.
Commit 9bf4e919ccad worked around an issue introduced after an innocuous optimisation change in LLVM main:
Quoted 11 lines
len is defined as an 'int' because it is assigned from '
__userint *optlen'. However, it is clamped against the result ofsizeof(), which has a type of 'size_t' ('unsigned long' for 64-bit platforms). This is done withmin_t()becausemin()requires compatible types, which results in both len and the result ofsizeof()being casted to 'unsigned int', meaning len changes signs and the result ofsizeof()is truncated. From there, len is passed tocopy_to_user(), which has a third parameter type of 'unsigned long', so it is widened and changes signs again. This excessive casting in combination with the KCSAN instrumentation causes LLVM to fail to eliminate the__bad_copy_from()call, failing the build.
The same issue occurs in rfcomm in functions rfcomm_sock_getsockopt and rfcomm_sock_getsockopt_old.
Change the type of len to size_t in both rfcomm_sock_getsockopt and rfcomm_sock_getsockopt_old and replace min_t() with min().
Improves: 9bf4e919ccad ("Bluetooth: Fix type of len in {l2cap,sco}_sock_getsockopt_old()")
--- net/bluetooth/rfcomm/sock.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-)
net/bluetooth/rfcomm/sock.c +6 -4
@@ -729,7 +729,8 @@ static int rfcomm_sock_getsockopt_old(ststruct sock *l2cap_sk;struct l2cap_conn *conn;struct rfcomm_conninfo cinfo; -int len, err =0 ; +int err =0 ; +size_t len;u32 opt;BT_DBG ("sk %p" , sk);
@@ -783,7 +784,7 @@ static int rfcomm_sock_getsockopt_old(st cinfo.hci_handle = conn->hcon->handle;memcpy (cinfo.dev_class, conn->hcon->dev_class,3 ); - len = min_t(unsigned int, len, sizeof(cinfo)); + len =min (len,sizeof (cinfo));if (copy_to_user (optval, (char *) &cinfo, len)) err = -EFAULT ;
@@ -802,7 +803,8 @@ static int rfcomm_sock_getsockopt(struct {struct sock *sk = sock->sk;struct bt_security sec; -int len, err =0 ; +int err =0 ; +size_t len;BT_DBG ("sk %p" , sk);
@@ -827,7 +829,7 @@ static int rfcomm_sock_getsockopt(struct sec.level =rfcomm_pi (sk)->sec_level; sec.key_size =0 ; - len = min_t(unsigned int, len, sizeof(sec)); + len =min (len,sizeof (sec));if (copy_to_user (optval, (char *) &sec, len)) err = -EFAULT ;
Greg Kroah-Hartman
maintainerPATCH 495/676 Compiler Attributes: disable __counted_by for clang < 19.1.3
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jan Hendrik Farr <[email protected]>
commit f06e108a3dc53c0f5234d18de0bd224753db5019 upstream.
This patch disables __counted_by for clang versions < 19.1.3 because of the two issues listed below. It does this by introducing CONFIG_CC_HAS_COUNTED_BY.
1. clang < 19.1.2 has a bug that can lead to __bdos returning 0:
https://github.com/llvm/llvm-project/pull/110497
2. clang < 19.1.3 has a bug that can lead to __bdos being off by 4:
https://github.com/llvm/llvm-project/pull/112636
--- drivers/misc/lkdtm/bugs.c | 4 ++-- include/linux/compiler_attributes.h | 13 ------------- include/linux/compiler_types.h | 19 +++++++++++++++++++ init/Kconfig | 9 +++++++++ 4 files changed, 30 insertions(+), 15 deletions(-)
drivers/misc/lkdtm/bugs.c +2 -2
@@ -388,8 +388,8 @@ static void lkdtm_FAM_BOUNDS(void)pr_err ("FAIL: survived access of invalid flexible array member index!\n" ); -if (!__has_attribute (__counted_by__)) -pr_warn ("This is expected since this %s was built a compiler supporting __counted_by\n" , +if (!IS_ENABLED (CONFIG_CC_HAS_COUNTED_BY )) +pr_warn ("This is expected since this %s was built with a compiler that does not support __counted_by\n" , lkdtm_kernel_info);else if (IS_ENABLED (CONFIG_UBSAN_BOUNDS ))pr_expected_config (CONFIG_UBSAN_TRAP );
include/linux/compiler_attributes.h +0 -13
@@ -95,19 +95,6 @@#endif /* -* Optional: only supported since gcc >= 14 -* Optional: only supported since clang >= 18 -* -* gcc: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=108896 -* clang: https://reviews.llvm.org/D148381 -*/ -#if __has_attribute (__counted_by__) -# define __counted_by (member) __attribute__((__counted_by__(member))) -#else -# define __counted_by (member) -#endif - -/* * Optional: not supported by gcc * Optional: only supported since clang >= 14.0 *
include/linux/compiler_types.h +19 -0
@@ -295,6 +295,25 @@ struct ftrace_likely_data {#define __no_sanitize_or_inline __always_inline#endif +/* +* Optional: only supported since gcc >= 15 +* Optional: only supported since clang >= 18 +* +* gcc: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=108896 +* clang: https://github.com/llvm/llvm-project/pull/76348 +* +* __bdos on clang < 19.1.2 can erroneously return 0: +* https://github.com/llvm/llvm-project/pull/110497 +* +* __bdos on clang < 19.1.3 can be off by 4: +* https://github.com/llvm/llvm-project/pull/112636 +*/ +#ifdef CONFIG_CC_HAS_COUNTED_BY +# define __counted_by (member) __attribute__((__counted_by__(member))) +#else +# define __counted_by (member) +#endif +/* Section for code which can't be instrumented at all */ #define __noinstr_section (section) \ noinline notrace __attribute((__section__(section))) \
init/Kconfig +9 -0
@@ -107,6 +107,15 @@ config CC_HAS_ASM_INLINE config CC_HAS_NO_PROFILE_FN_ATTR def_bool $(success,echo '__attribute__((no_profile_instrument_function)) int x();' | $(CC) -x c - -c -o /dev/null -Werror) +config CC_HAS_COUNTED_BY + # TODO: when gcc 15 is released remove the build test and add + # a gcc version check + def_bool $(success,echo 'struct flex { int count; int array[] __attribute__((__counted_by__(count))); };' | $(CC) $(CLANG_FLAGS) -x c - -c -o /dev/null -Werror) + # clang needs to be at least 19.1.3 to avoid __bdos miscalculations + # https://github.com/llvm/llvm-project/pull/110497 + # https://github.com/llvm/llvm-project/pull/112636 + depends on !(CC_IS_CLANG && CLANG_VERSION < 190103) + config PAHOLE_VERSION int default $(shell,$(srctree)/scripts/pahole-version.sh $(PAHOLE))
Greg Kroah-Hartman
maintainerPATCH 496/676 usb: xhci: Fix TD invalidation under pending Set TR Dequeue
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michal Pecio <[email protected]>
commit 484c3bab2d5dfa13ff659a51a06e9a393141eefc upstream.
xhci_invalidate_cancelled_tds() may not work correctly if the hardware is modifying endpoint or stream contexts at the same time by executing a Set TR Dequeue command. And even if it worked, it would be unable to queue Set TR Dequeue for the next stream, failing to clear xHC cache.
On stream endpoints, a chain of Set TR Dequeue commands may take some time to execute and we may want to cancel more TDs during this time. Currently this leads to Stop Endpoint completion handler calling this function without testing for SET_DEQ_PENDING, which will trigger the aforementioned problems when it happens.
On all endpoints, a halt condition causes Reset Endpoint to be queued and an error status given to the class driver, which may unlink more URBs in response. Stop Endpoint is queued and its handler may execute concurrently with Set TR Dequeue queued by Reset Endpoint handler.
(Reset Endpoint handler calls this function too, but there seems to be no possibility of it running concurrently with Set TR Dequeue).
Fix xhci_invalidate_cancelled_tds() to work correctly under a pending Set TR Dequeue. Bail out of the function when SET_DEQ_PENDING is set, then make the completion handler call the function again and also call xhci_giveback_invalidated_tds(), which needs to be called next.
This seems to fix another potential bug, where the handler would call xhci_invalidate_cancelled_tds(), which may clear some deferred TDs if a sanity check fails, and the TDs wouldn't be given back promptly.
Said sanity check seems to be wrong and prone to false positives when the endpoint halts, but fixing it is beyond the scope of this change, besides ensuring that cleared TDs are given back properly.
--- drivers/usb/host/xhci-ring.c | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-)
drivers/usb/host/xhci-ring.c +13 -5
@@ -994,6 +994,13 @@ static int xhci_invalidate_cancelled_tdsunsigned int slot_id = ep->vdev->slot_id;int err; +/* +* This is not going to work if the hardware is changing its dequeue +* pointers as we look at them. Completion handler will call us later. +*/ +if (ep->ep_state &SET_DEQ_PENDING ) +return 0 ; + xhci = ep->xhci;list_for_each_entry_safe (td, tmp_td, &ep->cancelled_td_list, cancelled_td_list) {
@@ -1354,7 +1361,6 @@ static void xhci_handle_cmd_set_deq(strustruct xhci_ep_ctx *ep_ctx;struct xhci_slot_ctx *slot_ctx;struct xhci_td *td, *tmp_td; -bool deferred = false; ep_index =TRB_TO_EP_INDEX (le32_to_cpu (trb->generic.field[3 ])); stream_id =TRB_TO_STREAM_ID (le32_to_cpu (trb->generic.field[2 ]));
@@ -1455,8 +1461,6 @@ static void xhci_handle_cmd_set_deq(struxhci_dbg (ep->xhci,"%s: Giveback cancelled URB %p TD\n" , __func__, td->urb);xhci_td_cleanup (ep->xhci, td, ep_ring, td->status); - }else if (td->cancel_status ==TD_CLEARING_CACHE_DEFERRED ) { - deferred = true; }else {xhci_dbg (ep->xhci,"%s: Keep cancelled URB %p TD as cancel_status is %d\n" , __func__, td->urb, td->cancel_status);
@@ -1467,11 +1471,15 @@ cleanup: ep->queued_deq_seg =NULL ; ep->queued_deq_ptr =NULL ; -if (deferred) { -/* We have more streams to clear */ +/* Check for deferred or newly cancelled TDs */ +if (!list_empty (&ep->cancelled_td_list)) {xhci_dbg (ep->xhci,"%s: Pending TDs to clear, continuing with invalidation\n" , __func__);xhci_invalidate_cancelled_tds (ep); +/* Try to restart the endpoint if all is done */ +ring_doorbell_for_active_rings (xhci, slot_id, ep_index); +/* Start giving back any TDs invalidated above */ +xhci_giveback_invalidated_tds (ep); }else {/* Restart any rings with pending URBs */ xhci_dbg (ep->xhci,"%s: All TDs cleared, ring doorbell\n" , __func__);
Greg Kroah-Hartman
maintainerPATCH 497/676 ARM: dts: omap36xx: declare 1GHz OPP as turbo again
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andreas Kemnade <[email protected]>
commit 96a64e9730c2c76cfa5c510583a0fbf40d62886b upstream.
Operating stable without reduced chip life at 1Ghz needs several technologies working: The technologies involve
- SmartReflex
- DVFS
As this cannot directly specified in the OPP table as dependecies in the devicetree yet, use the turbo flag again to mark this OPP as something special to have some kind of opt-in.
So revert commit5f1bf7ae8481 ("ARM: dts: omap36xx: Remove turbo mode for 1GHz variants")
Practical reasoning:
At least the GTA04A5 (DM3730) has become unstable with that OPP enabled. Furthermore nothing enforces the availability of said technologies, even in the kernel configuration, so allow users to rather opt-in.
--- arch/arm/boot/dts/ti/omap/omap36xx.dtsi | 1 + 1 file changed, 1 insertion(+)
arch/arm/boot/dts/ti/omap/omap36xx.dtsi +1 -0
@@ -72,6 +72,7 @@ <1375000 1375000 1375000>; /* only on am/dm37x with speed-binned bit set */ opp-supported-hw = <0xffffffff 2>; + turbo-mode; }; };
Greg Kroah-Hartman
maintainerPATCH 498/676 wifi: ath12k: fix warning when unbinding
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jose Ignacio Tornos Martinez <[email protected]>
commit ca68ce0d9f4bcd032fd1334441175ae399642a06 upstream.
If there is an error during some initialization related to firmware, the buffers dp->tx_ring[i].tx_status are released.
However this is released again when the device is unbinded (ath12k_pci), and we get:
WARNING: CPU: 0 PID: 2098 at mm/slub.c:4689 free_large_kmalloc+0x4d/0x80 Call Trace:
free_large_kmallocath12k_dp_freeath12k_core_deinitath12k_pci_remove
...
The issue is always reproducible from a VM because the MSI addressing initialization is failing.
In order to fix the issue, just set the buffers to NULL after releasing in order to avoid the double free.
--- drivers/net/wireless/ath/ath12k/dp.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/net/wireless/ath/ath12k/dp.c +3 -1
@@ -1249,8 +1249,10 @@ void ath12k_dp_free(struct ath12k_base *ath12k_dp_rx_reo_cmd_list_cleanup (ab); -for (i =0 ; i < ab->hw_params->max_tx_ring; i++) +for (i =0 ; i < ab->hw_params->max_tx_ring; i++) {kfree (dp->tx_ring[i].tx_status); + dp->tx_ring[i].tx_status =NULL ; + }ath12k_dp_rx_free (ab);/* Deinit any SOC level resource */
Greg Kroah-Hartman
maintainerPATCH 499/676 wifi: rtlwifi: Drastically reduce the attempts to read efuse in case of failures
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Guilherme G. Piccoli <[email protected]>
commit 5c1b544563005a00591a3aa86ecff62ed4d11be3 upstream.
Syzkaller reported a hung task with uevent_show() on stack trace. That specific issue was addressed by another commit [0], but even with that fix applied (for example, running v6.12-rc5) we face another type of hung task that comes from the same reproducer [1]. By investigating that, we could narrow it to the following path:
(a) Syzkaller emulates a Realtek USB WiFi adapter using raw-gadget and dummy_hcd infrastructure.
(b) During the probe of rtl8192cu, the driver ends-up performing an efuse read procedure (which is related to EEPROM load IIUC), and here lies the
issue: the function read_efuse() calls read_efuse_byte() many times, as loop iterations depending on the efuse size (in our example, 512 in total).
This procedure for reading efuse bytes relies in a loop that performs an I/O read up to *10k* times in case of failures. We measured the time of the loop inside read_efuse_byte() alone, and in this reproducer (which involves the dummy_hcd emulation layer), it takes 15 seconds each. As a consequence, we have the driver stuck in its probe routine for big time, exposing a stack trace like below if we attempt to reboot the system, for example:
task:kworker/0:3 state:D stack:0 pid:662 tgid:662 ppid:2 flags:0x00004000
Workqueue: usb_hub_wq hub_event Call Trace: __schedule+0xe22/0xeb6 schedule_timeout+0xe7/0x132 __wait_for_common+0xb5/0x12e usb_start_wait_urb+0xc5/0x1ef ? usb_alloc_urb+0x95/0xa4 usb_control_msg+0xff/0x184 _usbctrl_vendorreq_sync+0xa0/0x161 _usb_read_sync+0xb3/0xc5 read_efuse_byte+0x13c/0x146 read_efuse+0x351/0x5f0 efuse_read_all_map+0x42/0x52 rtl_efuse_shadow_map_update+0x60/0xef rtl_get_hwinfo+0x5d/0x1c2 rtl92cu_read_eeprom_info+0x10a/0x8d5 ? rtl92c_read_chip_version+0x14f/0x17e rtl_usb_probe+0x323/0x851 usb_probe_interface+0x278/0x34b really_probe+0x202/0x4a4 __driver_probe_device+0x166/0x1b2 driver_probe_device+0x2f/0xd8 [...]
We propose hereby to drastically reduce the attempts of doing the I/O reads in case of failures, restricted to USB devices (given that they're inherently slower than PCIe ones). By retrying up to 10 times (instead of 10000), we got reponsiveness in the reproducer, while seems reasonable to believe that there's no sane USB device implementation in the field requiring this amount of retries at every I/O read in order to properly work. Based on that assumption, it'd be good to have it backported to stable but maybe not since driver implementation (the 10k number comes from day 0), perhaps up to 6.x series makes sense.
[0] Commit 15fffc6a5624 ("driver core: Fix uevent_show() vs driver detach race")
[1] A note about that: this syzkaller report presents multiple reproducers that differs by the type of emulated USB device. For this specific case, check the entry from 2024/08/08 06:23 in the list of crashes; the C repro is available at https://syzkaller.appspot.com/text?tag=ReproC&x=1521fc83980000.
--- drivers/net/wireless/realtek/rtlwifi/efuse.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-)
drivers/net/wireless/realtek/rtlwifi/efuse.c +10 -1
@@ -162,10 +162,19 @@ void efuse_write_1byte(struct ieee80211_void read_efuse_byte (struct ieee80211_hw *hw,u16 _offset,u8 *pbuf) {struct rtl_priv *rtlpriv =rtl_priv (hw); +u16 max_attempts =10000 ;u32 value32;u8 readbyte;u16 retry; +/* +* In case of USB devices, transfer speeds are limited, hence +* efuse I/O reads could be (way) slower. So, decrease (a lot) +* the read attempts in case of failures. +*/ +if (rtlpriv->rtlhal.interface ==INTF_USB ) + max_attempts =10 ; +rtl_write_byte (rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL ] +1 , (_offset &0xff )); readbyte =rtl_read_byte (rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL ] +2 );
@@ -178,7 +187,7 @@ void read_efuse_byte(struct ieee80211_hw retry =0 ; value32 =rtl_read_dword (rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL ]); -while (!(((value32 >>24 ) &0xff ) &0x80 ) && (retry <10000 )) { +while (!(((value32 >>24 ) &0xff ) &0x80 ) && (retry < max_attempts)) { value32 =rtl_read_dword (rtlpriv, rtlpriv->cfg->maps[EFUSE_CTRL ]); retry++;
Greg Kroah-Hartman
maintainerPATCH 500/676 wifi: ath12k: fix crash when unbinding
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jose Ignacio Tornos Martinez <[email protected]>
commit 1304446f67863385dc4c914b6e0194f6664ee764 upstream.
If there is an error during some initialization related to firmware, the function ath12k_dp_cc_cleanup is called to release resources. However this is released again when the device is unbinded (ath12k_pci), and we get:
BUG: kernel NULL pointer dereference, address: 0000000000000020 at RIP: 0010:ath12k_dp_cc_cleanup.part.0+0xb6/0x500 [ath12k] Call Trace:
ath12k_dp_cc_cleanupath12k_dp_freeath12k_core_deinitath12k_pci_remove
...
The issue is always reproducible from a VM because the MSI addressing initialization is failing.
In order to fix the issue, just set to NULL the released structure in ath12k_dp_cc_cleanup at the end.
--- drivers/net/wireless/ath/ath12k/dp.c | 1 + 1 file changed, 1 insertion(+)
drivers/net/wireless/ath/ath12k/dp.c +1 -0
@@ -1214,6 +1214,7 @@ static void ath12k_dp_cc_cleanup(struct }kfree (dp->spt_info); + dp->spt_info =NULL ; }static void ath12k_dp_reoq_lut_cleanup (struct ath12k_base *ab)
Greg Kroah-Hartman
maintainerPATCH 501/676 wifi: brcmfmac: release root node in all execution paths
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Javier Carrasco <[email protected]>
commit 2e19a3b590ebf2e351fc9d0e7c323430e65b6b6d upstream.
The fixed patch introduced an additional condition to enter the scope where the 'root' device_node is released (!settings->board_type, currently 'err'), which avoid decrementing the refcount with a call to of_node_put() if that second condition is not satisfied.
Move the call to of_node_put() to the point where 'root' is no longer required to avoid leaking the resource if err is not zero.
--- drivers/net/wireless/broadcom/brcm80211/brcmfmac/of.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
drivers/net/wireless/broadcom/brcm80211/brcmfmac/of.c +1 -2
@@ -109,9 +109,8 @@ void brcmf_of_probe(struct device *dev, }strreplace (board_type,'/' ,'-' ); settings->board_type = board_type; - -of_node_put (root); } +of_node_put (root);if (!np || !of_device_is_compatible (np,"brcm,bcm4329-fmac" ))return ;
Greg Kroah-Hartman
maintainerPATCH 502/676 Revert "usb: gadget: composite: fix OS descriptors w_value logic"
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michal Vrastil <[email protected]>
commit 51cdd69d6a857f527d6d0697a2e1f0fa8bca1005 upstream.
This reverts commit ec6ce7075ef879b91a8710829016005dc8170f17.
Fix installation of WinUSB driver using OS descriptors. Without the fix the drivers are not installed correctly and the property 'DeviceInterfaceGUID' is missing on host side.
The original change was based on the assumption that the interface number is in the high byte of wValue but it is in the low byte, instead. Unfortunately, the fix is based on MS documentation which is also wrong.
The actual USB request for OS descriptors (using USB analyzer) looks like:
Offset 0 1 2 3 4 5 6 7 0x000 C1 A1 02 00 05 00 0A 00
C1: bmRequestType (device to host, vendor, interface)
A1: nas magic number
0002: wValue (2: nas interface)
0005: wIndex (5: get extended property i.e. nas interface GUID) 008E: wLength (142)
The fix was tested on Windows 10 and Windows 11.
--- drivers/usb/gadget/composite.c | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-)
drivers/usb/gadget/composite.c +15 -3
@@ -2111,8 +2111,20 @@ unknown:memset (buf,0 , w_length); buf[5 ] =0x01 ;switch (ctrl->bRequestType &USB_RECIP_MASK ) { +/* +* The Microsoft CompatID OS Descriptor Spec(w_index = 0x4) and +* Extended Prop OS Desc Spec(w_index = 0x5) state that the +* HighByte of wValue is the InterfaceNumber and the LowByte is +* the PageNumber. This high/low byte ordering is incorrectly +* documented in the Spec. USB analyzer output on the below +* request packets show the high/low byte inverted i.e LowByte +* is the InterfaceNumber and the HighByte is the PageNumber. +* Since we dont support >64KB CompatID/ExtendedProp descriptors, +* PageNumber is set to 0. Hence verify that the HighByte is 0 +* for below two cases. +*/ case USB_RECIP_DEVICE : -if (w_index !=0x4 || (w_value &0xff )) +if (w_index !=0x4 || (w_value >>8 ))break ; buf[6 ] = w_index;/* Number of ext compat interfaces */
@@ -2128,9 +2140,9 @@ unknown: }break ;case USB_RECIP_INTERFACE : -if (w_index !=0x5 || (w_value &0xff )) +if (w_index !=0x5 || (w_value >>8 ))break ; - interface = w_value >>8 ; + interface = w_value &0xFF ;if (interface >=MAX_CONFIG_INTERFACES || !os_desc_cfg->interface[interface])break ;
Greg Kroah-Hartman
maintainerPATCH 503/676 serial: sh-sci: Clean sci_ports[0] after at earlycon exit
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Claudiu Beznea <[email protected]>
commit 3791ea69a4858b81e0277f695ca40f5aae40f312 upstream.
The early_console_setup() function initializes the sci_ports[0].port with an object of type struct uart_port obtained from the object of type struct earlycon_device received as argument by the early_console_setup().
It may happen that later, when the rest of the serial ports are probed, the serial port that was used as earlycon (e.g., port A) to be mapped to a different position in sci_ports[] and the slot 0 to be used by a different serial port (e.g., port B), as follows:
sci_ports[0] = port A
sci_ports[X] = port B
In this case, the new port mapped at index zero will have associated data that was used for earlycon.
In case this happens, after Linux boot, any access to the serial port that maps on sci_ports[0] (port A) will block the serial port that was used as earlycon (port B).
To fix this, add early_console_exit() that clean the sci_ports[0] at earlycon exit time.
--- drivers/tty/serial/sh-sci.c | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+)
drivers/tty/serial/sh-sci.c +28 -0
@@ -3505,6 +3505,32 @@ sh_early_platform_init_buffer("earlyprin#ifdef CONFIG_SERIAL_SH_SCI_EARLYCON static struct plat_sci_port port_cfg__initdata ; +static int early_console_exit (struct console *co) +{ +struct sci_port *sci_port = &sci_ports[0 ]; +struct uart_port *port = &sci_port->port; +unsigned long flags; +int locked =1 ; + +if (port->sysrq) + locked =0 ; +else if (oops_in_progress) + locked =uart_port_trylock_irqsave (port, &flags); +else +uart_port_lock_irqsave (port, &flags); + +/* +* Clean the slot used by earlycon. A new SCI device might +* map to this slot. +*/ +memset (sci_ports,0 ,sizeof (*sci_port)); + +if (locked) +uart_port_unlock_irqrestore (port, flags); + +return 0 ; +} +static int __init early_console_setup (struct earlycon_device *device,int type) {
@@ -3523,6 +3549,8 @@ static int __init early_console_setup(st SCSCR_RE | SCSCR_TE | port_cfg.scscr); device->con->write = serial_console_write; + device->con->exit = early_console_exit; +return 0 ; } static int __init sci_early_console_setup(struct earlycon_device *device,
Greg Kroah-Hartman
maintainerPATCH 504/676 Revert "serial: sh-sci: Clean sci_ports[0] after at earlycon exit"
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Greg Kroah-Hartman <[email protected]>
commit 718632467d88e98816fa01ab12681ef1c2aa56f8 upstream.
This reverts commit 3791ea69a4858b81e0277f695ca40f5aae40f312.
It was reported to cause boot-time issues, so revert it for now.
--- drivers/tty/serial/sh-sci.c | 28 ---------------------------- 1 file changed, 28 deletions(-)
drivers/tty/serial/sh-sci.c +0 -28
@@ -3505,32 +3505,6 @@ sh_early_platform_init_buffer("earlyprin#ifdef CONFIG_SERIAL_SH_SCI_EARLYCON static struct plat_sci_port port_cfg__initdata ; -static int early_console_exit (struct console *co) -{ -struct sci_port *sci_port = &sci_ports[0 ]; -struct uart_port *port = &sci_port->port; -unsigned long flags; -int locked =1 ; - -if (port->sysrq) - locked =0 ; -else if (oops_in_progress) - locked =uart_port_trylock_irqsave (port, &flags); -else -uart_port_lock_irqsave (port, &flags); - -/* -* Clean the slot used by earlycon. A new SCI device might -* map to this slot. -*/ -memset (sci_ports,0 ,sizeof (*sci_port)); - -if (locked) -uart_port_unlock_irqrestore (port, flags); - -return 0 ; -} -static int __init early_console_setup (struct earlycon_device *device,int type) {
@@ -3549,8 +3523,6 @@ static int __init early_console_setup(st SCSCR_RE | SCSCR_TE | port_cfg.scscr); device->con->write = serial_console_write; - device->con->exit = early_console_exit; -return 0 ; } static int __init sci_early_console_setup(struct earlycon_device *device,
Greg Kroah-Hartman
maintainerPATCH 505/676 gpio: exar: set value when external pull-up or pull-down is present
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sai Kumar Cholleti <[email protected]>
commit 72cef64180de04a7b055b4773c138d78f4ebdb77 upstream.
Setting GPIO direction = high, sometimes results in GPIO value = 0.
If a GPIO is pulled high, the following construction results in the value being 0 when the desired value is 1:
$ echo "high" > /sys/class/gpio/gpio336/direction $ cat /sys/class/gpio/gpio336/value 0
Before the GPIO direction is changed from an input to an output, exar_set_value() is called with value = 1, but since the GPIO is an input when exar_set_value() is called, _regmap_update_bits() reads a 1 due to an external pull-up. regmap_set_bits() sets force_write = false, so the value (1) is not written. When the direction is then changed, the GPIO becomes an output with the value of 0 (the hardware default).
regmap_write_bits() sets force_write = true, so the value is always written by exar_set_value() and an external pull-up doesn't affect the outcome of setting direction = high.
The same can happen when a GPIO is pulled low, but the scenario is a little more complicated.
$ echo high > /sys/class/gpio/gpio351/direction $ cat /sys/class/gpio/gpio351/value 1
$ echo in > /sys/class/gpio/gpio351/direction $ cat /sys/class/gpio/gpio351/value 0
$ echo low > /sys/class/gpio/gpio351/direction $ cat /sys/class/gpio/gpio351/value 1
--- drivers/gpio/gpio-exar.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-)
drivers/gpio/gpio-exar.c +6 -4
@@ -99,11 +99,13 @@ static void exar_set_value(struct gpio_cstruct exar_gpio_chip *exar_gpio =gpiochip_get_data (chip);unsigned int addr =exar_offset_to_lvl_addr (exar_gpio, offset);unsigned int bit =exar_offset_to_bit (exar_gpio, offset); +unsigned int bit_value = value ?BIT (bit) :0 ; -if (value) -regmap_set_bits (exar_gpio->regmap, addr,BIT (bit)); -else -regmap_clear_bits (exar_gpio->regmap, addr,BIT (bit)); +/* +* regmap_write_bits() forces value to be written when an external +* pull up/down might otherwise indicate value was already set. +*/ +regmap_write_bits (exar_gpio->regmap, addr,BIT (bit), bit_value); } static int exar_direction_output(struct gpio_chip *chip, unsigned int offset,
Greg Kroah-Hartman
maintainerPATCH 506/676 netfilter: ipset: add missing range check in bitmap_ip_uadt
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jeongjun Park <[email protected]>
commit 35f56c554eb1b56b77b3cf197a6b00922d49033d upstream.
When tb[IPSET_ATTR_IP_TO] is not present but tb[IPSET_ATTR_CIDR] exists, the values of ip and ip_to are slightly swapped. Therefore, the range check for ip should be done later, but this part is missing and it seems that the vulnerability occurs.
So we should add missing range checks and remove unnecessary range checks.
--- net/netfilter/ipset/ip_set_bitmap_ip.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-)
net/netfilter/ipset/ip_set_bitmap_ip.c +2 -5
@@ -163,11 +163,8 @@ bitmap_ip_uadt(struct ip_set *set, struc ret =ip_set_get_hostipaddr4 (tb[IPSET_ATTR_IP_TO ], &ip_to);if (ret)return ret; -if (ip > ip_to) { +if (ip > ip_to)swap (ip, ip_to); -if (ip < map->first_ip) -return -IPSET_ERR_BITMAP_RANGE ; - } }else if (tb[IPSET_ATTR_CIDR ]) {u8 cidr =nla_get_u8 (tb[IPSET_ATTR_CIDR ]);
@@ -178,7 +175,7 @@ bitmap_ip_uadt(struct ip_set *set, struc ip_to = ip; } -if (ip_to > map->last_ip) +if (ip < map->first_ip || ip_to > map->last_ip)return -IPSET_ERR_BITMAP_RANGE ;for (; !before (ip_to, ip); ip += map->hosts) {
Greg Kroah-Hartman
maintainerPATCH 507/676 spi: Fix acpi deferred irq probe
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Stanislaw Gruszka <[email protected]>
commit d24cfee7f63d6b44d45a67c5662bd1cc48e8b3ca upstream.
When probing spi device take care of deferred probe of ACPI irq gpio similar like for OF/DT case.
Quoted 1 line
From practical standpoint this fixes issue with vsc-tp driver on
Dell XP 9340 laptop, which try to request interrupt with spi->irq equal to -EPROBE_DEFER and fail to probe with the following error:
vsc-tp spi-INTC10D0:00: probe with driver vsc-tp failed with error -22
--- drivers/spi/spi.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-)
drivers/spi/spi.c +10 -3
@@ -426,6 +426,16 @@ static int spi_probe(struct device *dev) spi->irq =0 ; } +if (has_acpi_companion (dev) && spi->irq <0 ) { +struct acpi_device *adev =to_acpi_device_node (dev->fwnode); + + spi->irq =acpi_dev_gpio_irq_get (adev,0 ); +if (spi->irq == -EPROBE_DEFER ) +return -EPROBE_DEFER ; +if (spi->irq <0 ) + spi->irq =0 ; + } + ret =dev_pm_domain_attach (dev, true);if (ret)return ret;
@@ -2706,9 +2716,6 @@ static acpi_status acpi_register_spi_devacpi_set_modalias (adev,acpi_device_hid (adev), spi->modalias,sizeof (spi->modalias)); -if (spi->irq <0 ) - spi->irq =acpi_dev_gpio_irq_get (adev,0 ); -acpi_device_set_enumerated (adev); adev->power.flags.ignore_parent = true;
Greg Kroah-Hartman
maintainerPATCH 508/676 mtd: spi-nor: core: replace dummy buswidth from addr to data
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Cheng Ming Lin <[email protected]>
commit 98d1fb94ce75f39febd456d6d3cbbe58b6678795 upstream.
The default dummy cycle for Macronix SPI NOR flash in Octal Output Read Mode(1-1-8) is 20.
Currently, the dummy buswidth is set according to the address bus width. In the 1-1-8 mode, this means the dummy buswidth is 1. When converting dummy cycles to bytes, this results in 20 x 1 / 8 = 2 bytes, causing the host to read data 4 cycles too early.
Since the protocol data buswidth is always greater than or equal to the address buswidth. Setting the dummy buswidth to match the data buswidth increases the likelihood that the dummy cycle-to-byte conversion will be divisible, preventing the host from reading data prematurely.
--- drivers/mtd/spi-nor/core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/mtd/spi-nor/core.c +1 -1
@@ -89,7 +89,7 @@ void spi_nor_spimem_setup_op(const struc op->addr.buswidth =spi_nor_get_protocol_addr_nbits (proto);if (op->dummy.nbytes) - op->dummy.buswidth =spi_nor_get_protocol_addr_nbits (proto); + op->dummy.buswidth =spi_nor_get_protocol_data_nbits (proto);if (op->data.nbytes) op->data.buswidth =spi_nor_get_protocol_data_nbits (proto);
Greg Kroah-Hartman
maintainerPATCH 509/676 cpufreq: mediatek-hw: Fix wrong return value in mtk_cpufreq_get_cpu_power()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jinjie Ruan <[email protected]>
commit 172bf5ed04cb6c9e66d58de003938ed5c8756570 upstream.
mtk_cpufreq_get_cpu_power() return 0 if the policy is NULL. Then in em_create_perf_table(), the later zero check for power is not invalid as power is uninitialized. As Lukasz suggested, it must return -EINVAL when the 'policy' is not found. So return -EINVAL to fix it.
--- drivers/cpufreq/mediatek-cpufreq-hw.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/mediatek-cpufreq-hw.c +1 -1
@@ -62,7 +62,7 @@ mtk_cpufreq_get_cpu_power(struct device policy =cpufreq_cpu_get_raw (cpu_dev->id);if (!policy) -return 0 ; +return -EINVAL ; data = policy->driver_data;
Greg Kroah-Hartman
maintainerPATCH 510/676 cifs: support mounting with alternate password to allow password rotation
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Meetakshi Setiya <[email protected]>
commit b9aef1b13a0a92aa7058ba235afb24b5b89153ca upstream.
Fixes the case for example where the password specified on mount is a recently expired password, but password2 is valid. Without this patch this mount scenario would fail.
This patch introduces the following changes to support password rotation on mount:
1. If an existing session is not found and the new session setup results in EACCES, EKEYEXPIRED or EKEYREVOKED, swap password and password2 (if available), and retry the mount.
2. To match the new mount with an existing session, add conditions to check if a) password and password2 of the new mount and the existing session are the same, or b) password of the new mount is the same as the password2 of the existing session, and password2 of the new mount is the same as the password of the existing session.
3. If an existing session is found, but needs reconnect, retry the session setup after swapping password and password2 (if available), in case the previous attempt results in EACCES, EKEYEXPIRED or EKEYREVOKED.
--- fs/smb/client/connect.c | 57 ++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 50 insertions(+), 7 deletions(-)
fs/smb/client/connect.c +50 -7
@@ -1908,11 +1908,35 @@ static int match_session(struct cifs_ses CIFS_MAX_USERNAME_LEN))return 0 ;if ((ctx->username &&strlen (ctx->username) !=0 ) && - ses->password !=NULL && -strncmp (ses->password, - ctx->password ? ctx->password :"" , -CIFS_MAX_PASSWORD_LEN )) -return 0 ; + ses->password !=NULL ) { + +/* New mount can only share sessions with an existing mount if: +* 1. Both password and password2 match, or +* 2. password2 of the old mount matches password of the new mount +* and password of the old mount matches password2 of the new +* mount +*/ +if (ses->password2 !=NULL && ctx->password2 !=NULL ) { +if (!((strncmp (ses->password, ctx->password ? + ctx->password :"" ,CIFS_MAX_PASSWORD_LEN ) ==0 && +strncmp (ses->password2, ctx->password2, +CIFS_MAX_PASSWORD_LEN ) ==0 ) || + (strncmp (ses->password, ctx->password2, +CIFS_MAX_PASSWORD_LEN ) ==0 && +strncmp (ses->password2, ctx->password ? + ctx->password :"" ,CIFS_MAX_PASSWORD_LEN ) ==0 ))) +return 0 ; + + }else if ((ses->password2 ==NULL && ctx->password2 !=NULL ) || + (ses->password2 !=NULL && ctx->password2 ==NULL )) { +return 0 ; + + }else { +if (strncmp (ses->password, ctx->password ? + ctx->password :"" ,CIFS_MAX_PASSWORD_LEN )) +return 0 ; + } + } }if (strcmp (ctx->local_nls->charset, ses->local_nls->charset))
@@ -2256,6 +2280,7 @@ struct cifs_ses * cifs_get_smb_ses(struct TCP_Server_Info *server, struct smb3_fs_context *ctx) { int rc = 0; +int retries =0 ;unsigned int xid;struct cifs_ses *ses;struct sockaddr_in *addr = (struct sockaddr_in *)&server->dstaddr;
@@ -2274,6 +2299,8 @@ cifs_get_smb_ses(struct TCP_Server_Infocifs_dbg (FYI ,"Session needs reconnect\n" );mutex_lock (&ses->session_mutex); + +retry_old_session: rc =cifs_negotiate_protocol (xid, ses, server);if (rc) {mutex_unlock (&ses->session_mutex);
@@ -2286,6 +2313,13 @@ cifs_get_smb_ses(struct TCP_Server_Info rc =cifs_setup_session (xid, ses, server, ctx->local_nls);if (rc) { +if (((rc == -EACCES ) || (rc == -EKEYEXPIRED ) || + (rc == -EKEYREVOKED )) && !retries && ses->password2) { + retries++; +cifs_dbg (FYI ,"Session reconnect failed, retrying with alternate password\n" ); +swap (ses->password, ses->password2); + goto retry_old_session; + }mutex_unlock (&ses->session_mutex);/* problem -- put our reference */ cifs_put_smb_ses (ses);
@@ -2361,6 +2395,7 @@ cifs_get_smb_ses(struct TCP_Server_Info ses->chans_need_reconnect =1 ;spin_unlock (&ses->chan_lock); +retry_new_session:mutex_lock (&ses->session_mutex); rc =cifs_negotiate_protocol (xid, ses, server);if (!rc)
@@ -2373,8 +2408,16 @@ cifs_get_smb_ses(struct TCP_Server_Info sizeof(ses->smb3signingkey));spin_unlock (&ses->chan_lock); -if (rc) - goto get_ses_fail; +if (rc) { +if (((rc == -EACCES ) || (rc == -EKEYEXPIRED ) || + (rc == -EKEYREVOKED )) && !retries && ses->password2) { + retries++; +cifs_dbg (FYI ,"Session setup failed, retrying with alternate password\n" ); +swap (ses->password, ses->password2); + goto retry_new_session; + }else + goto get_ses_fail; + }/* * success, put it on the list and add it as first channel
Greg Kroah-Hartman
maintainerPATCH 511/676 parisc/ftrace: Fix function graph tracing disablement
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Josh Poimboeuf <[email protected]>
commit a5f05a138a8cac035bf9da9b6ed0e532bc7942c8 upstream.
Due to an apparent copy-paste bug, the parisc implementation of ftrace_disable_ftrace_graph_caller() doesn't actually do anything. It enables the (already-enabled) static key rather than disabling it.
The result is that after function graph tracing has been "disabled", any subsequent (non-graph) function tracing will inadvertently also enable the slow fgraph return address hijacking.
--- arch/parisc/kernel/ftrace.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/parisc/kernel/ftrace.c +1 -1
@@ -87,7 +87,7 @@ int ftrace_enable_ftrace_graph_caller(voint ftrace_disable_ftrace_graph_caller (void ) { -static_key_enable (&ftrace_graph_enable.key); +static_key_disable (&ftrace_graph_enable.key);return 0 ; }#endif
Greg Kroah-Hartman
maintainerPATCH 512/676 ksmbd: fix use-after-free in SMB request handling
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Yunseong Kim <[email protected]>
commit 9a8c5d89d327ff58e9b2517f8a6afb4181d32c6e upstream.
A race condition exists between SMB request handling in ksmbd_conn_handler_loop() and the freeing of ksmbd_conn in the workqueue handler handle_ksmbd_work(). This leads to a UAF.
- KASAN: slab-use-after-free Read in handle_ksmbd_work
- KASAN: slab-use-after-free in rtlock_slowlock_locked
This race condition arises as follows:
- ksmbd_conn_handler_loop() waits for conn->r_count to reach zero:
wait_event(conn->r_count_q, atomic_read(&conn->r_count) == 0);
- Meanwhile, handle_ksmbd_work() decrements conn->r_count using atomic_dec_return(&conn->r_count), and if it reaches zero, calls ksmbd_conn_free(), which frees conn.
- However, after handle_ksmbd_work() decrements conn->r_count, it may still access conn->r_count_q in the following line:
waitqueue_active(&conn->r_count_q) or wake_up(&conn->r_count_q) This results in a UAF, as conn has already been freed.
The discovery of this UAF can be referenced in the following PR for syzkaller's support for SMB requests.
--- fs/smb/server/server.c | 4 ++++ 1 file changed, 4 insertions(+)
fs/smb/server/server.c +4 -0
@@ -276,8 +276,12 @@ static void handle_ksmbd_work(struct work_struct *wk)* disconnection. waitqueue_active is safe because it * uses atomic operation for condition. */ +atomic_inc (&conn->refcnt);if (!atomic_dec_return (&conn->r_count) &&waitqueue_active (&conn->r_count_q))wake_up (&conn->r_count_q); + +if (atomic_dec_and_test (&conn->refcnt)) +kfree (conn); }/**
Signature · 1 line
2.47.1
Greg Kroah-Hartman
maintainerPATCH 513/676 smb: client: fix NULL ptr deref in crypto_aead_setkey()
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Paulo Alcantara <[email protected]>
commit 4bdec0d1f658f7c98749bd2c5a486e6cfa8565d2 upstream.
Neither SMB3.0 or SMB3.02 supports encryption negotiate context, so when SMB2_GLOBAL_CAP_ENCRYPTION flag is set in the negotiate response, the client uses AES-128-CCM as the default cipher. See MS-SMB2 3.3.5.4.
Commit b0abcd65ec54 ("smb: client: fix UAF in async decryption") added a @server->cipher_type check to conditionally call smb3_crypto_aead_allocate(), but that check would always be false as @server->cipher_type is unset for SMB3.02.
Fix the following KASAN splat by setting @server->cipher_type for SMB3.02 as well.
mount.cifs //srv/share /mnt -o vers=3.02,seal,...
BUG: KASAN: null-ptr-deref in crypto_aead_setkey+0x2c/0x130 Read of size 8 at addr 0000000000000020 by task mount.cifs/1095 CPU: 1 UID: 0 PID: 1095 Comm: mount.cifs Not tainted 6.12.0 #1 Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS 1.16.3-3.fc41 04/01/2014 Call Trace: <TASK> dump_stack_lvl+0x5d/0x80 ? crypto_aead_setkey+0x2c/0x130 kasan_report+0xda/0x110 ? crypto_aead_setkey+0x2c/0x130 crypto_aead_setkey+0x2c/0x130 crypt_message+0x258/0xec0 [cifs] ? __asan_memset+0x23/0x50 ? __pfx_crypt_message+0x10/0x10 [cifs] ? mark_lock+0xb0/0x6a0 ? hlock_class+0x32/0xb0 ? mark_lock+0xb0/0x6a0 smb3_init_transform_rq+0x352/0x3f0 [cifs] ? lock_acquire.part.0+0xf4/0x2a0 smb_send_rqst+0x144/0x230 [cifs] ? __pfx_smb_send_rqst+0x10/0x10 [cifs] ? hlock_class+0x32/0xb0 ? smb2_setup_request+0x225/0x3a0 [cifs] ? __pfx_cifs_compound_last_callback+0x10/0x10 [cifs] compound_send_recv+0x59b/0x1140 [cifs] ? __pfx_compound_send_recv+0x10/0x10 [cifs] ? __create_object+0x5e/0x90 ? hlock_class+0x32/0xb0 ? do_raw_spin_unlock+0x9a/0xf0 cifs_send_recv+0x23/0x30 [cifs] SMB2_tcon+0x3ec/0xb30 [cifs] ? __pfx_SMB2_tcon+0x10/0x10 [cifs] ? lock_acquire.part.0+0xf4/0x2a0 ? __pfx_lock_release+0x10/0x10 ? do_raw_spin_trylock+0xc6/0x120 ? lock_acquire+0x3f/0x90 ? _get_xid+0x16/0xd0 [cifs] ? __pfx_SMB2_tcon+0x10/0x10 [cifs] ? cifs_get_smb_ses+0xcdd/0x10a0 [cifs] cifs_get_smb_ses+0xcdd/0x10a0 [cifs] ? __pfx_cifs_get_smb_ses+0x10/0x10 [cifs] ? cifs_get_tcp_session+0xaa0/0xca0 [cifs] cifs_mount_get_session+0x8a/0x210 [cifs] dfs_mount_share+0x1b0/0x11d0 [cifs] ? __pfx___lock_acquire+0x10/0x10 ? __pfx_dfs_mount_share+0x10/0x10 [cifs] ? lock_acquire.part.0+0xf4/0x2a0 ? find_held_lock+0x8a/0xa0 ? hlock_class+0x32/0xb0 ? lock_release+0x203/0x5d0 cifs_mount+0xb3/0x3d0 [cifs] ? do_raw_spin_trylock+0xc6/0x120 ? __pfx_cifs_mount+0x10/0x10 [cifs] ? lock_acquire+0x3f/0x90 ? find_nls+0x16/0xa0 ? smb3_update_mnt_flags+0x372/0x3b0 [cifs] cifs_smb3_do_mount+0x1e2/0xc80 [cifs] ? __pfx_vfs_parse_fs_string+0x10/0x10 ? __pfx_cifs_smb3_do_mount+0x10/0x10 [cifs] smb3_get_tree+0x1bf/0x330 [cifs] vfs_get_tree+0x4a/0x160 path_mount+0x3c1/0xfb0 ? kasan_quarantine_put+0xc7/0x1d0 ? __pfx_path_mount+0x10/0x10 ? kmem_cache_free+0x118/0x3e0 ? user_path_at+0x74/0xa0 __x64_sys_mount+0x1a6/0x1e0 ? __pfx___x64_sys_mount+0x10/0x10 ? mark_held_locks+0x1a/0x90 do_syscall_64+0xbb/0x1d0 entry_SYSCALL_64_after_hwframe+0x77/0x7f
--- fs/smb/client/smb2pdu.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
fs/smb/client/smb2pdu.c +3 -1
@@ -1228,7 +1228,9 @@ SMB2_negotiate(const unsigned int xid,* SMB3.0 supports only 1 cipher and doesn't have a encryption neg context * Set the cipher type manually. */ -if (server->dialect ==SMB30_PROT_ID && (server->capabilities &SMB2_GLOBAL_CAP_ENCRYPTION )) +if ((server->dialect ==SMB30_PROT_ID || + server->dialect ==SMB302_PROT_ID ) && + (server->capabilities &SMB2_GLOBAL_CAP_ENCRYPTION )) server->cipher_type =SMB2_ENCRYPTION_AES128_CCM ; security_blob = smb2_get_data_area_len(&blob_offset, &blob_length,
Greg Kroah-Hartman
maintainerPATCH 514/676 platform/chrome: cros_ec_typec: fix missing fwnode reference decrement
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Javier Carrasco <[email protected]>
commit 9c41f371457bd9a24874e3c7934d9745e87fbc58 upstream.
The device_for_each_child_node() macro requires explicit calls to fwnode_handle_put() upon early exits (return, break, goto) to decrement the fwnode's refcount, and avoid levaing a node reference behind.
Add the missing fwnode_handle_put() after the common label for all error paths.
--- drivers/platform/chrome/cros_ec_typec.c | 1 + 1 file changed, 1 insertion(+)
drivers/platform/chrome/cros_ec_typec.c +1 -0
@@ -390,6 +390,7 @@ static int cros_typec_init_ports(structreturn 0 ; unregister_ports: +fwnode_handle_put (fwnode);cros_unregister_ports (typec);return ret; }
Greg Kroah-Hartman
maintainerPATCH 515/676 ubi: wl: Put source PEB into correct list if trying locking LEB failed
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zhihao Cheng <[email protected]>
commit d610020f030bec819f42de327c2bd5437d2766b3 upstream.
During wear-leveing work, the source PEB will be moved into scrub list when source LEB cannot be locked in ubi_eba_copy_leb(), which is wrong for non-scrub type source PEB. The problem could bring extra and ineffective wear-leveing jobs, which makes more or less negative effects for the life time of flash. Specifically, the process is divided 2 steps:
1. wear_leveling_worker // generate false scrub type PEB ubi_eba_copy_leb // MOVE_RETRY is returned leb_write_trylock // trylock failed
scrubbing = 1;
e1 is put into ubi->scrub
2. wear_leveling_worker // schedule false scrub type PEB for wl scrubbing = 1
e1 = rb_entry(rb_first(&ubi->scrub))
The problem can be reproduced easily by running fsstress on a small UBIFS partition(<64M, simulated by nandsim) for 5~10mins (CONFIG_MTD_UBI_FASTMAP=y,CONFIG_MTD_UBI_WL_THRESHOLD=50). Following message is shown:
ubi0: scrubbed PEB 66 (LEB 0:10), data moved to PEB 165
Since scrub type source PEB has set variable scrubbing as '1', and variable scrubbing is checked before variable keep, so the problem can be fixed by setting keep variable as 1 directly if the source LEB cannot be locked.
--- drivers/mtd/ubi/wl.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-)
drivers/mtd/ubi/wl.c +8 -1
@@ -834,7 +834,14 @@ static int wear_leveling_worker(struct u goto out_not_moved; }if (err ==MOVE_RETRY ) { - scrubbing =1 ; +/* +* For source PEB: +* 1. The scrubbing is set for scrub type PEB, it will +* be put back into ubi->scrub list. +* 2. Non-scrub type PEB will be put back into ubi->used +* list. +*/ + keep =1 ; dst_leb_clean =1 ; goto out_not_moved; }
Greg Kroah-Hartman
maintainerPATCH 516/676 um: ubd: Do not use drvdata in release
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tiwei Bie <[email protected]>
commit 5bee35e5389f450a7eea7318deb9073e9414d3b1 upstream.
The drvdata is not available in release. Let's just use container_of() to get the ubd instance. Otherwise, removing a ubd device will result in a crash:
RIP: 0033:blk_mq_free_tag_set+0x1f/0xba RSP: 00000000e2083bf0 EFLAGS: 00010246 RAX: 000000006021463a RBX: 0000000000000348 RCX: 0000000062604d00 RDX: 0000000004208060 RSI: 00000000605241a0 RDI: 0000000000000348 RBP: 00000000e2083c10 R08: 0000000062414010 R09: 00000000601603f7 R10: 000000000000133a R11: 000000006038c4bd R12: 0000000000000000 R13: 0000000060213a5c R14: 0000000062405d20 R15: 00000000604f7aa0 Kernel panic - not syncing: Segfault with no mm CPU: 0 PID: 17 Comm: kworker/0:1 Not tainted 6.8.0-rc3-00107-gba3f67c11638 #1 Workqueue: events mc_work_proc Stack: 00000000 604f7ef0 62c5d000 62405d20 e2083c30 6002c776 6002c755 600e47ff e2083c60 6025ffe3 04208060 603d36e0 Call Trace: [<6002c776>] ubd_device_release+0x21/0x55 [<6002c755>] ? ubd_device_release+0x0/0x55 [<600e47ff>] ? kfree+0x0/0x100 [<6025ffe3>] device_release+0x70/0xba [<60381d6a>] kobject_put+0xb5/0xe2 [<6026027b>] put_device+0x19/0x1c [<6026a036>] platform_device_put+0x26/0x29 [<6026ac5a>] platform_device_unregister+0x2c/0x2e [<6002c52e>] ubd_remove+0xb8/0xd6 [<6002bb74>] ? mconsole_reply+0x0/0x50 [<6002b926>] mconsole_remove+0x160/0x1cc [<6002bbbc>] ? mconsole_reply+0x48/0x50 [<6003379c>] ? um_set_signals+0x3b/0x43 [<60061c55>] ? update_min_vruntime+0x14/0x70 [<6006251f>] ? dequeue_task_fair+0x164/0x235 [<600620aa>] ? update_cfs_group+0x0/0x40 [<603a0e77>] ? __schedule+0x0/0x3ed [<60033761>] ? um_set_signals+0x0/0x43 [<6002af6a>] mc_work_proc+0x77/0x91 [<600520b4>] process_scheduled_works+0x1af/0x2c3 [<6004ede3>] ? assign_work+0x0/0x58 [<600527a1>] worker_thread+0x2f7/0x37a [<6004ee3b>] ? set_pf_worker+0x0/0x64 [<6005765d>] ? arch_local_irq_save+0x0/0x2d [<60058e07>] ? kthread_exit+0x0/0x3a [<600524aa>] ? worker_thread+0x0/0x37a [<60058f9f>] kthread+0x130/0x135 [<6002068e>] new_thread_handler+0x85/0xb6
--- arch/um/drivers/ubd_kern.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/um/drivers/ubd_kern.c +1 -1
@@ -799,7 +799,7 @@ static int ubd_open_dev(struct ubd *ubd_static void ubd_device_release (struct device *dev) { -struct ubd *ubd_dev =dev_get_drvdata (dev); + struct ubd *ubd_dev = container_of(dev, struct ubd, pdev.dev);blk_mq_free_tag_set (&ubd_dev->tag_set); *ubd_dev = ((struct ubd )DEFAULT_UBD );
Greg Kroah-Hartman
maintainerPATCH 517/676 um: net: Do not use drvdata in release
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tiwei Bie <[email protected]>
commit d1db692a9be3b4bd3473b64fcae996afaffe8438 upstream.
The drvdata is not available in release. Let's just use container_of() to get the uml_net instance. Otherwise, removing a network device will result in a crash:
RIP: 0033:net_device_release+0x10/0x6f RSP: 00000000e20c7c40 EFLAGS: 00010206 RAX: 000000006002e4e7 RBX: 00000000600f1baf RCX: 00000000624074e0 RDX: 0000000062778000 RSI: 0000000060551c80 RDI: 00000000627af028 RBP: 00000000e20c7c50 R08: 00000000603ad594 R09: 00000000e20c7b70 R10: 000000000000135a R11: 00000000603ad422 R12: 0000000000000000 R13: 0000000062c7af00 R14: 0000000062406d60 R15: 00000000627700b6 Kernel panic - not syncing: Segfault with no mm CPU: 0 UID: 0 PID: 29 Comm: kworker/0:2 Not tainted 6.12.0-rc6-g59b723cd2adb #1 Workqueue: events mc_work_proc Stack: 627af028 62c7af00 e20c7c80 60276fcd 62778000 603f5820 627af028 00000000 e20c7cb0 603a2bcd 627af000 62770010 Call Trace: [<60276fcd>] device_release+0x70/0xba [<603a2bcd>] kobject_put+0xba/0xe7 [<60277265>] put_device+0x19/0x1c [<60281266>] platform_device_put+0x26/0x29 [<60281e5f>] platform_device_unregister+0x2c/0x2e [<6002ec9c>] net_remove+0x63/0x69 [<60031316>] ? mconsole_reply+0x0/0x50 [<600310c8>] mconsole_remove+0x160/0x1cc [<60087d40>] ? __remove_hrtimer+0x38/0x74 [<60087ff8>] ? hrtimer_try_to_cancel+0x8c/0x98 [<6006b3cf>] ? dl_server_stop+0x3f/0x48 [<6006b390>] ? dl_server_stop+0x0/0x48 [<600672e8>] ? dequeue_entities+0x327/0x390 [<60038fa6>] ? um_set_signals+0x0/0x43 [<6003070c>] mc_work_proc+0x77/0x91 [<60057664>] process_scheduled_works+0x1b3/0x2dd [<60055f32>] ? assign_work+0x0/0x58 [<60057f0a>] worker_thread+0x1e9/0x293 [<6005406f>] ? set_pf_worker+0x0/0x64 [<6005d65d>] ? arch_local_irq_save+0x0/0x2d [<6005d748>] ? kthread_exit+0x0/0x3a [<60057d21>] ? worker_thread+0x0/0x293 [<6005dbf1>] kthread+0x126/0x12b [<600219c5>] new_thread_handler+0x85/0xb6
--- arch/um/drivers/net_kern.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/um/drivers/net_kern.c +1 -1
@@ -336,7 +336,7 @@ static struct platform_driver uml_net_drstatic void net_device_release (struct device *dev) { -struct uml_net *device =dev_get_drvdata (dev); + struct uml_net *device = container_of(dev, struct uml_net, pdev.dev);struct net_device *netdev = device->dev;struct uml_net_private *lp =netdev_priv (netdev);
Greg Kroah-Hartman
maintainerPATCH 518/676 dt-bindings: serial: rs485: Fix rs485-rts-delay property
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michal Simek <[email protected]>
commit 12b3642b6c242061d3ba84e6e3050c3141ded14c upstream.
Code expects array only with 2 items which should be checked. But also item checking is not working as it should likely because of incorrect items description.
--- Documentation/devicetree/bindings/serial/rs485.yaml | 19 +++++++++---------- 1 file changed, 9 insertions(+), 10 deletions(-)
Documentation/devicetree/bindings/serial/rs485.yaml +9 -10
@@ -18,16 +18,15 @@ properties: description: prop-encoded-array <a b> $ref: /schemas/types.yaml#/definitions/uint32-array items: - items: - - description: Delay between rts signal and beginning of data sent in - milliseconds. It corresponds to the delay before sending data. - default: 0 - maximum: 100 - - description: Delay between end of data sent and rts signal in milliseconds. - It corresponds to the delay after sending data and actual release - of the line. - default: 0 - maximum: 100 + - description: Delay between rts signal and beginning of data sent in + milliseconds. It corresponds to the delay before sending data. + default: 0 + maximum: 100 + - description: Delay between end of data sent and rts signal in milliseconds. + It corresponds to the delay after sending data and actual release + of the line. + default: 0 + maximum: 100 rs485-rts-active-high: description: drive RTS high when sending (this is the default).
Greg Kroah-Hartman
maintainerPATCH 519/676 serial: 8250_fintek: Add support for F81216E
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Filip Brozovic <[email protected]>
commit 166105c9030a30ba08574a9998afc7b60bc72dd7 upstream.
The F81216E is a LPC/eSPI to 4 UART Super I/O and is mostly compatible with the F81216H, but does not support RS-485 auto-direction delays on any port.
--- drivers/tty/serial/8250/8250_fintek.c | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-)
drivers/tty/serial/8250/8250_fintek.c +13 -1
@@ -21,6 +21,7 @@#define CHIP_ID_F81866 0x1010#define CHIP_ID_F81966 0x0215#define CHIP_ID_F81216AD 0x1602 +#define CHIP_ID_F81216E 0x1617#define CHIP_ID_F81216H 0x0501#define CHIP_ID_F81216 0x0802#define VENDOR_ID1 0x23
@@ -158,6 +159,7 @@ static int fintek_8250_check_id(struct fcase CHIP_ID_F81866 :case CHIP_ID_F81966 :case CHIP_ID_F81216AD : +case CHIP_ID_F81216E :case CHIP_ID_F81216H :case CHIP_ID_F81216 :break ;
@@ -181,6 +183,7 @@ static int fintek_8250_get_ldn_range(strreturn 0 ;case CHIP_ID_F81216AD : +case CHIP_ID_F81216E :case CHIP_ID_F81216H :case CHIP_ID_F81216 : *min =F81216_LDN_LOW ;
@@ -250,6 +253,7 @@ static void fintek_8250_set_irq_mode(strbreak ;case CHIP_ID_F81216AD : +case CHIP_ID_F81216E :case CHIP_ID_F81216H :case CHIP_ID_F81216 : sio_write_mask_reg(pdata, FINTEK_IRQ_MODE, IRQ_SHARE,
@@ -263,7 +267,8 @@ static void fintek_8250_set_irq_mode(strstatic void fintek_8250_set_max_fifo (struct fintek_8250 *pdata) {switch (pdata->pid) { -case CHIP_ID_F81216H :/* 128Bytes FIFO */ +case CHIP_ID_F81216E :/* 128Bytes FIFO */ +case CHIP_ID_F81216H :case CHIP_ID_F81966 :case CHIP_ID_F81866 : sio_write_mask_reg(pdata, FIFO_CTRL,
@@ -297,6 +302,7 @@ static void fintek_8250_set_termios(stru goto exit;switch (pdata->pid) { +case CHIP_ID_F81216E :case CHIP_ID_F81216H : reg =RS485 ;break ;
@@ -346,6 +352,7 @@ static void fintek_8250_set_termios_handstruct fintek_8250 *pdata = uart->port.private_data;switch (pdata->pid) { +case CHIP_ID_F81216E :case CHIP_ID_F81216H :case CHIP_ID_F81966 :case CHIP_ID_F81866 :
@@ -438,6 +445,11 @@ static void fintek_8250_set_rs485_handle uart->port.rs485_supported = fintek_8250_rs485_supported;break ; +case CHIP_ID_F81216E :/* F81216E does not support RS485 delays */ + uart->port.rs485_config = fintek_8250_rs485_config; + uart->port.rs485_supported = fintek_8250_rs485_supported; +break ; +default :/* No RS485 Auto direction functional */ break ; }
Greg Kroah-Hartman
maintainerPATCH 520/676 serial: 8250: omap: Move pm_runtime_get_sync
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bin Liu <[email protected]>
commit bcc7ba668818dcadd2f1db66b39ed860a63ecf97 upstream.
Currently in omap_8250_shutdown, the dma->rx_running flag is set to zero in omap_8250_rx_dma_flush. Next pm_runtime_get_sync is called, which is a runtime resume call stack which can re-set the flag. When the call omap_8250_shutdown returns, the flag is expected to be UN-SET, but this is not the case. This is causing issues the next time UART is re-opened and omap_8250_rx_dma is called. Fix by moving pm_runtime_get_sync before the omap_8250_rx_dma_flush.
--- drivers/tty/serial/8250/8250_omap.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/tty/serial/8250/8250_omap.c +2 -2
@@ -766,12 +766,12 @@ static void omap_8250_shutdown(struct uastruct uart_8250_port *up =up_to_u8250p (port);struct omap8250_priv *priv = port->private_data; +pm_runtime_get_sync (port->dev); +flush_work (&priv->qos_work);if (up->dma)omap_8250_rx_dma_flush (up); -pm_runtime_get_sync (port->dev); -serial_out (up,UART_OMAP_WER ,0 );if (priv->habit &UART_HAS_EFR2 )serial_out (up,UART_OMAP_EFR2 ,0x0 );
Greg Kroah-Hartman
maintainerPATCH 521/676 um: vector: Do not use drvdata in release
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tiwei Bie <[email protected]>
commit 51b39d741970742a5c41136241a9c48ac607cf82 upstream.
The drvdata is not available in release. Let's just use container_of() to get the vector_device instance. Otherwise, removing a vector device will result in a crash:
RIP: 0033:vector_device_release+0xf/0x50 RSP: 00000000e187bc40 EFLAGS: 00010202 RAX: 0000000060028f61 RBX: 00000000600f1baf RCX: 00000000620074e0 RDX: 000000006220b9c0 RSI: 0000000060551c80 RDI: 0000000000000000 RBP: 00000000e187bc50 R08: 00000000603ad594 R09: 00000000e187bb70 R10: 000000000000135a R11: 00000000603ad422 R12: 00000000623ae028 R13: 000000006287a200 R14: 0000000062006d30 R15: 00000000623700b6 Kernel panic - not syncing: Segfault with no mm CPU: 0 UID: 0 PID: 16 Comm: kworker/0:1 Not tainted 6.12.0-rc6-g59b723cd2adb #1 Workqueue: events mc_work_proc Stack: 60028f61 623ae028 e187bc80 60276fcd 6220b9c0 603f5820 623ae028 00000000 e187bcb0 603a2bcd 623ae000 62370010 Call Trace: [<60028f61>] ? vector_device_release+0x0/0x50 [<60276fcd>] device_release+0x70/0xba [<603a2bcd>] kobject_put+0xba/0xe7 [<60277265>] put_device+0x19/0x1c [<60281266>] platform_device_put+0x26/0x29 [<60281e5f>] platform_device_unregister+0x2c/0x2e [<60029422>] vector_remove+0x52/0x58 [<60031316>] ? mconsole_reply+0x0/0x50 [<600310c8>] mconsole_remove+0x160/0x1cc [<603b19f4>] ? strlen+0x0/0x15 [<60066611>] ? __dequeue_entity+0x1a9/0x206 [<600666a7>] ? set_next_entity+0x39/0x63 [<6006666e>] ? set_next_entity+0x0/0x63 [<60038fa6>] ? um_set_signals+0x0/0x43 [<6003070c>] mc_work_proc+0x77/0x91 [<60057664>] process_scheduled_works+0x1b3/0x2dd [<60055f32>] ? assign_work+0x0/0x58 [<60057f0a>] worker_thread+0x1e9/0x293 [<6005406f>] ? set_pf_worker+0x0/0x64 [<6005d65d>] ? arch_local_irq_save+0x0/0x2d [<6005d748>] ? kthread_exit+0x0/0x3a [<60057d21>] ? worker_thread+0x0/0x293 [<6005dbf1>] kthread+0x126/0x12b [<600219c5>] new_thread_handler+0x85/0xb6
--- arch/um/drivers/vector_kern.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
arch/um/drivers/vector_kern.c +2 -1
@@ -823,7 +823,8 @@ static struct platform_driver uml_net_drstatic void vector_device_release (struct device *dev) { -struct vector_device *device =dev_get_drvdata (dev); +struct vector_device *device = + container_of(dev, struct vector_device, pdev.dev);struct net_device *netdev = device->dev;list_del (&device->list);
Greg Kroah-Hartman
maintainerPATCH 522/676 sh: cpuinfo: Fix a warning for CONFIG_CPUMASK_OFFSTACK
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Huacai Chen <[email protected]>
commit 3c891f7c6a4e90bb1199497552f24b26e46383bc upstream.
When CONFIG_CPUMASK_OFFSTACK and CONFIG_DEBUG_PER_CPU_MAPS are selected, cpu_max_bits_warn() generates a runtime warning similar as below when showing /proc/cpuinfo. Fix this by using nr_cpu_ids (the runtime limit) instead of NR_CPUS to iterate CPUs.
[ 3.052463] ------------[ cut here ]------------ [ 3.059679] WARNING: CPU: 3 PID: 1 at include/linux/cpumask.h:108 show_cpuinfo+0x5e8/0x5f0 [ 3.070072] Modules linked in: efivarfs autofs4 [ 3.076257] CPU: 0 PID: 1 Comm: systemd Not tainted 5.19-rc5+ #1052 [ 3.099465] Stack : 9000000100157b08 9000000000f18530 9000000000cf846c 9000000100154000 [ 3.109127] 9000000100157a50 0000000000000000 9000000100157a58 9000000000ef7430 [ 3.118774] 90000001001578e8 0000000000000040 0000000000000020 ffffffffffffffff [ 3.128412] 0000000000aaaaaa 1ab25f00eec96a37 900000010021de80 900000000101c890 [ 3.138056] 0000000000000000 0000000000000000 0000000000000000 0000000000aaaaaa [ 3.147711] ffff8000339dc220 0000000000000001 0000000006ab4000 0000000000000000 [ 3.157364] 900000000101c998 0000000000000004 9000000000ef7430 0000000000000000 [ 3.167012] 0000000000000009 000000000000006c 0000000000000000 0000000000000000 [ 3.176641] 9000000000d3de08 9000000001639390 90000000002086d8 00007ffff0080286 [ 3.186260] 00000000000000b0 0000000000000004 0000000000000000 0000000000071c1c [ 3.195868] ... [ 3.199917] Call Trace: [ 3.203941] [<90000000002086d8>] show_stack+0x38/0x14c [ 3.210666] [<9000000000cf846c>] dump_stack_lvl+0x60/0x88 [ 3.217625] [<900000000023d268>] __warn+0xd0/0x100 [ 3.223958] [<9000000000cf3c90>] warn_slowpath_fmt+0x7c/0xcc [ 3.231150] [<9000000000210220>] show_cpuinfo+0x5e8/0x5f0 [ 3.238080] [<90000000004f578c>] seq_read_iter+0x354/0x4b4 [ 3.245098] [<90000000004c2e90>] new_sync_read+0x17c/0x1c4 [ 3.252114] [<90000000004c5174>] vfs_read+0x138/0x1d0 [ 3.258694] [<90000000004c55f8>] ksys_read+0x70/0x100 [ 3.265265] [<9000000000cfde9c>] do_syscall+0x7c/0x94 [ 3.271820] [<9000000000202fe4>] handle_syscall+0xc4/0x160 [ 3.281824] ---[ end trace 8b484262b4b8c24c ]---
--- arch/sh/kernel/cpu/proc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/sh/kernel/cpu/proc.c +1 -1
@@ -132,7 +132,7 @@ static int show_cpuinfo(struct seq_filestatic void *c_start (struct seq_file *m,loff_t *pos) { -return *pos <NR_CPUS ? cpu_data + *pos :NULL ; +return *pos < nr_cpu_ids ? cpu_data + *pos :NULL ; }static void *c_next (struct seq_file *m,void *v,loff_t *pos) {
Greg Kroah-Hartman
maintainerPATCH 523/676 iio: gts: Fix uninitialized symbol ret
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zicheng Qu <[email protected]>
commit e2fb2f89faf87b681038475d093214f4cbe12ebb upstream.
Initialize the variable ret at the time of declaration to prevent it from being returned without a defined value. Fixes smatch warning:drivers/iio/industrialio-gts-helper.c:256 gain_to_scaletables() error:
uninitialized symbol 'ret'.
--- drivers/iio/industrialio-gts-helper.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/iio/industrialio-gts-helper.c +1 -1
@@ -167,7 +167,7 @@ static int iio_gts_gain_cmp(const void *a, const void *b)static int gain_to_scaletables (struct iio_gts *gts,int **gains,int **scales) { -int ret, i, j, new_idx, time_idx; +int i, j, new_idx, time_idx, ret =0 ;int *all_gains;size_t gain_bytes;
Signature · 1 line
2.47.1
Greg Kroah-Hartman
maintainerPATCH 524/676 ublk: fix ublk_ch_mmap() for 64K page size
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ming Lei <[email protected]>
commit d369735e02ef122d19d4c3d093028da0eb400636 upstream.
In ublk_ch_mmap(), queue id is calculated in the following way:
(vma->vm_pgoff << PAGE_SHIFT) / `max_cmd_buf_size`
'max_cmd_buf_size' is equal to
UBLK_MAX_QUEUE_DEPTH * sizeof(struct ublksrv_io_desc)
and UBLK_MAX_QUEUE_DEPTH is 4096 and part of UAPI, so 'max_cmd_buf_size' is always page aligned in 4K page size kernel. However, it isn't true in 64K page size kernel.
Fixes the issue by always rounding up 'max_cmd_buf_size' with PAGE_SIZE.
--- drivers/block/ublk_drv.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-)
drivers/block/ublk_drv.c +12 -3
@@ -713,12 +713,21 @@ static inline char *ublk_queue_cmd_buf(sreturn ublk_get_queue (ub, q_id)->io_cmd_buf; } +static inline int __ublk_queue_cmd_buf_size (int depth) +{ +return round_up (depth *sizeof (struct ublksrv_io_desc ),PAGE_SIZE ); +} +static inline int ublk_queue_cmd_buf_size (struct ublk_device *ub,int q_id) {struct ublk_queue *ubq =ublk_get_queue (ub, q_id); -return round_up (ubq->q_depth *sizeof (struct ublksrv_io_desc ), -PAGE_SIZE ); +return __ublk_queue_cmd_buf_size (ubq->q_depth); +} + +static int ublk_max_cmd_buf_size (void ) +{ +return __ublk_queue_cmd_buf_size (UBLK_MAX_QUEUE_DEPTH ); } static inline bool ublk_queue_can_use_recovery_reissue(
@@ -1387,7 +1396,7 @@ static int ublk_ch_mmap(struct file *fil {struct ublk_device *ub = filp->private_data;size_t sz = vma->vm_end - vma->vm_start; -unsigned max_sz =UBLK_MAX_QUEUE_DEPTH *sizeof (struct ublksrv_io_desc ); +unsigned max_sz =ublk_max_cmd_buf_size ();unsigned long pfn, end, phys_off = vma->vm_pgoff <<PAGE_SHIFT ;int q_id, ret =0 ;
Greg Kroah-Hartman
maintainerPATCH 525/676 arm64: tls: Fix context-switching of tpidrro_el0 when kpti is enabled
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Will Deacon <[email protected]>
commit 67ab51cbdfee02ef07fb9d7d14cc0bf6cb5a5e5c upstream.
Commit 18011eac28c7 ("arm64: tls: Avoid unconditional zeroing of tpidrro_el0 for native tasks") tried to optimise the context switching of tpidrro_el0 by eliding the clearing of the register when switching to a native task with kpti enabled, on the erroneous assumption that the kpti trampoline entry code would already have taken care of the write.
Although the kpti trampoline does zero the register on entry from a native task, the check in tls_thread_switch() is on the *next* task and so we can end up leaving a stale, non-zero value in the register if the previous task was 32-bit.
Drop the broken optimisation and zero tpidrro_el0 unconditionally when switching to a native 64-bit task.
--- arch/arm64/kernel/process.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/arm64/kernel/process.c +1 -1
@@ -429,7 +429,7 @@ static void tls_thread_switch(struct tasif (is_compat_thread (task_thread_info (next)))write_sysreg (next->thread.uw.tp_value, tpidrro_el0); -else if (!arm64_kernel_unmapped_at_el0 ()) +else write_sysreg (0 , tpidrro_el0);write_sysreg (*task_user_tls (next), tpidr_el0);
Greg Kroah-Hartman
maintainerPATCH 526/676 block: fix missing dispatching request when queue is started or unquiesced
In reply to Greg Kroah-Hartman6.6-stable review patch. If anyone has any objections, please let me know.
------------------
From: Muchun Song <[email protected]>
commit 2003ee8a9aa14d766b06088156978d53c2e9be3d upstream.
Supposing the following scenario with a virtio_blk driver.
CPU0 CPU1 CPU2
blk_mq_try_issue_directly()
__blk_mq_issue_directly()
q->mq_ops->queue_rq()
virtio_queue_rq()
blk_mq_stop_hw_queue()
virtblk_done()
blk_mq_try_issue_directly()
if (blk_mq_hctx_stopped()) blk_mq_request_bypass_insert() blk_mq_run_hw_queue()
blk_mq_run_hw_queue() blk_mq_run_hw_queue()
blk_mq_insert_request() return
After CPU0 has marked the queue as stopped, CPU1 will see the queue is stopped. But before CPU1 puts the request on the dispatch list, CPU2 receives the interrupt of completion of request, so it will run the hardware queue and marks the queue as non-stopped. Meanwhile, CPU1 also runs the same hardware queue. After both CPU1 and CPU2 complete blk_mq_run_hw_queue(), CPU1 just puts the request to the same hardware queue and returns. It misses dispatching a request. Fix it by running the hardware queue explicitly. And blk_mq_request_issue_directly() should handle a similar situation. Fix it as well.
--- block/blk-mq.c | 2 ++ 1 file changed, 2 insertions(+)
block/blk-mq.c +2 -0
@@ -2668,6 +2668,7 @@ static void blk_mq_try_issue_directly(stif (blk_mq_hctx_stopped (hctx) ||blk_queue_quiesced (rq->q)) {blk_mq_insert_request (rq,0 ); +blk_mq_run_hw_queue (hctx, false);return ; }
@@ -2698,6 +2699,7 @@ static blk_status_t blk_mq_request_issueif (blk_mq_hctx_stopped (hctx) ||blk_queue_quiesced (rq->q)) {blk_mq_insert_request (rq,0 ); +blk_mq_run_hw_queue (hctx, false);return BLK_STS_OK ; }