5.15.165-rc1 review
Subsystems (3)
Greg Kroah-Hartman
maintainerPATCH 142/484 RDMA/hns: Fix insufficient extend DB for VFs.
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Chengchang Tang <[email protected]>
[ Upstream commit 0b8e658f70ffd5dc7cda3872fd524d657d4796b7 ]
VFs and its PF will share the memory of the extend DB. Currently, the number of extend DB allocated by driver is only enough for PF. This leads to a probability of DB loss and some other problems in scenarios where both PF and VFs use a large number of QPs.
--- drivers/infiniband/hw/hns/hns_roce_hw_v2.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
drivers/infiniband/hw/hns/hns_roce_hw_v2.c +4 -2
@@ -2598,14 +2598,16 @@ static int set_llm_cfg_to_hw(struct hns_roce_dev *hr_dev,static struct hns_roce_link_table *alloc_link_table_buf (struct hns_roce_dev *hr_dev) { +u16 total_sl = hr_dev->caps.sl_num * hr_dev->func_num;struct hns_roce_v2_priv *priv = hr_dev->priv;struct hns_roce_link_table *link_tbl;u32 pg_shift, size, min_size; link_tbl = &priv->ext_llm; pg_shift = hr_dev->caps.llm_buf_pg_sz +PAGE_SHIFT ; - size = hr_dev->caps.num_qps *HNS_ROCE_V2_EXT_LLM_ENTRY_SZ ; - min_size =HNS_ROCE_EXT_LLM_MIN_PAGES (hr_dev->caps.sl_num) << pg_shift; + size = hr_dev->caps.num_qps * hr_dev->func_num * +HNS_ROCE_V2_EXT_LLM_ENTRY_SZ ; + min_size =HNS_ROCE_EXT_LLM_MIN_PAGES (total_sl) << pg_shift;/* Alloc data table */ size =max (size, min_size);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 143/484 bnxt_re: Fix imm_data endianness
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jack Wang <[email protected]>
[ Upstream commit 95b087f87b780daafad1dbb2c84e81b729d5d33f ]
When map a device between servers with MLX and BCM RoCE nics, RTRS server complain about unknown imm type, and can't map the device,
After more debug, it seems bnxt_re wrongly handle the imm_data, this patch fixed the compat issue with MLX for us.
In off list discussion, Selvin confirmed HW is working in little endian format and all data needs to be converted to LE while providing.
This patch fix the endianness for imm_data
--- drivers/infiniband/hw/bnxt_re/ib_verbs.c | 8 ++++---- drivers/infiniband/hw/bnxt_re/qplib_fp.h | 6 +++--- 2 files changed, 7 insertions(+), 7 deletions(-)
drivers/infiniband/hw/bnxt_re/ib_verbs.c +4 -4
@@ -2354,7 +2354,7 @@ static int bnxt_re_build_send_wqe(struct bnxt_re_qp *qp,break ;case IB_WR_SEND_WITH_IMM : wqe->type =BNXT_QPLIB_SWQE_TYPE_SEND_WITH_IMM ; - wqe->send.imm_data = wr->ex.imm_data; + wqe->send.imm_data =be32_to_cpu (wr->ex.imm_data);break ;case IB_WR_SEND_WITH_INV : wqe->type =BNXT_QPLIB_SWQE_TYPE_SEND_WITH_INV ;
@@ -2384,7 +2384,7 @@ static int bnxt_re_build_rdma_wqe(const struct ib_send_wr *wr,break ;case IB_WR_RDMA_WRITE_WITH_IMM : wqe->type =BNXT_QPLIB_SWQE_TYPE_RDMA_WRITE_WITH_IMM ; - wqe->rdma.imm_data = wr->ex.imm_data; + wqe->rdma.imm_data =be32_to_cpu (wr->ex.imm_data);break ;case IB_WR_RDMA_READ : wqe->type =BNXT_QPLIB_SWQE_TYPE_RDMA_READ ;
@@ -3334,7 +3334,7 @@ static void bnxt_re_process_res_shadow_qp_wc(struct bnxt_re_qp *gsi_sqp, wc->byte_len = orig_cqe->length; wc->qp = &gsi_qp->ib_qp; - wc->ex.imm_data = orig_cqe->immdata; + wc->ex.imm_data =cpu_to_be32 (le32_to_cpu (orig_cqe->immdata)); wc->src_qp = orig_cqe->src_qp;memcpy (wc->smac, orig_cqe->smac,ETH_ALEN );if (bnxt_re_is_vlan_pkt (orig_cqe, &vlan_id, &sl)) {
@@ -3470,7 +3470,7 @@ int bnxt_re_poll_cq(struct ib_cq *ib_cq, int num_entries, struct ib_wc *wc) (unsigned long )(cqe->qp_handle), struct bnxt_re_qp, qplib_qp); wc->qp = &qp->ib_qp; - wc->ex.imm_data = cqe->immdata; + wc->ex.imm_data =cpu_to_be32 (le32_to_cpu (cqe->immdata)); wc->src_qp = cqe->src_qp;memcpy (wc->smac, cqe->smac,ETH_ALEN ); wc->port_num =1 ;
drivers/infiniband/hw/bnxt_re/qplib_fp.h +3 -3
@@ -164,7 +164,7 @@ struct bnxt_qplib_swqe {/* Send, with imm, inval key */ struct {union { -__be32 imm_data; +u32 imm_data;u32 inv_key; };u32 q_key;
@@ -182,7 +182,7 @@ struct bnxt_qplib_swqe {/* RDMA write, with imm, read */ struct {union { -__be32 imm_data; +u32 imm_data;u32 inv_key; };u64 remote_va;
@@ -374,7 +374,7 @@ struct bnxt_qplib_cqe {u16 cfa_meta;u64 wr_id;union { -__be32 immdata; +__le32 immdata;u32 invrkey; };u64 qp_handle;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 144/484 netfilter: ctnetlink: use helper function to calculate expect ID
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pablo Neira Ayuso <[email protected]>
[ Upstream commit 782161895eb4ac45cf7cfa8db375bd4766cb8299 ]
Delete expectation path is missing a call to the nf_expect_get_id() helper function to calculate the expectation ID, otherwise LSB of the expectation object address is leaked to userspace.
--- net/netfilter/nf_conntrack_netlink.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
net/netfilter/nf_conntrack_netlink.c +2 -1
@@ -3426,7 +3426,8 @@ static int ctnetlink_del_expect(struct sk_buff *skb,if (cda[CTA_EXPECT_ID ]) {__be32 id =nla_get_be32 (cda[CTA_EXPECT_ID ]); -if (ntohl (id) != (u32 )(unsigned long )exp) { + +if (id !=nf_expect_get_id (exp)) {nf_ct_expect_put (exp);return -ENOENT ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 145/484 netfilter: nft_set_pipapo: constify lookup fn args where possible
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Florian Westphal <[email protected]>
[ Upstream commit f04df573faf90bb828a2241b650598c02c074323 ]
Those get called from packet path, content must not be modified. No functional changes intended.
Stable-dep-of: 791a615b7ad2 ("netfilter: nf_set_pipapo: fix initial map fill")
--- net/netfilter/nft_set_pipapo.c | 18 +++++---- net/netfilter/nft_set_pipapo.h | 6 +-- net/netfilter/nft_set_pipapo_avx2.c | 59 +++++++++++++++++------------ 3 files changed, 48 insertions(+), 35 deletions(-)
net/netfilter/nft_set_pipapo.c +10 -8
@@ -360,7 +360,7 @@* Return: -1 on no match, bit position on 'match_only', 0 otherwise. */ int pipapo_refill (unsigned long *map,int len,int rules,unsigned long *dst, -union nft_pipapo_map_bucket *mt,bool match_only) +const union nft_pipapo_map_bucket *mt,bool match_only) {unsigned long bitset;int k, ret =-1 ;
@@ -412,9 +412,9 @@ bool nft_pipapo_lookup(const struct net *net, const struct nft_set *set,struct nft_pipapo_scratch *scratch;unsigned long *res_map, *fill_map;u8 genmask =nft_genmask_cur (net); +const struct nft_pipapo_match *m; +const struct nft_pipapo_field *f;const u8 *rp = (const u8 *)key; -struct nft_pipapo_match *m; -struct nft_pipapo_field *f;bool map_index;int i;
@@ -517,11 +517,13 @@ static struct nft_pipapo_elem *pipapo_get(const struct net *net, {struct nft_pipapo_elem *ret =ERR_PTR (-ENOENT );struct nft_pipapo *priv =nft_set_priv (set); -struct nft_pipapo_match *m = priv->clone;unsigned long *res_map, *fill_map =NULL ; -struct nft_pipapo_field *f; +const struct nft_pipapo_match *m; +const struct nft_pipapo_field *f;int i; + m = priv->clone; + res_map =kmalloc_array (m->bsize_max,sizeof (*res_map),GFP_ATOMIC );if (!res_map) { ret =ERR_PTR (-ENOMEM );
@@ -1591,7 +1593,7 @@ static void pipapo_gc(const struct nft_set *_set, struct nft_pipapo_match *m)while ((rules_f0 =pipapo_rules_same_key (m->f, first_rule))) {union nft_pipapo_map_bucket rulemap[NFT_PIPAPO_MAX_FIELDS ]; -struct nft_pipapo_field *f; +const struct nft_pipapo_field *f;int i, start, rules_fx; start = first_rule;
@@ -2037,8 +2039,8 @@ static void nft_pipapo_walk(const struct nft_ctx *ctx, struct nft_set *set, {struct nft_pipapo *priv =nft_set_priv (set);struct net *net =read_pnet (&set->net); -struct nft_pipapo_match *m; -struct nft_pipapo_field *f; +const struct nft_pipapo_match *m; +const struct nft_pipapo_field *f;int i, r;rcu_read_lock ();
net/netfilter/nft_set_pipapo.h +3 -3
@@ -185,7 +185,7 @@ struct nft_pipapo_elem { };int pipapo_refill (unsigned long *map,int len,int rules,unsigned long *dst, -union nft_pipapo_map_bucket *mt,bool match_only); +const union nft_pipapo_map_bucket *mt,bool match_only);/** * pipapo_and_field_buckets_4bit() - Intersect 4-bit buckets
@@ -193,7 +193,7 @@ int pipapo_refill(unsigned long *map, int len, int rules, unsigned long *dst,* @dst: Area to store result * @data: Input data selecting table buckets */ -static inline void pipapo_and_field_buckets_4bit (struct nft_pipapo_field *f, +static inline void pipapo_and_field_buckets_4bit (const struct nft_pipapo_field *f,unsigned long *dst,const u8 *data) {
@@ -221,7 +221,7 @@ static inline void pipapo_and_field_buckets_4bit(struct nft_pipapo_field *f,* @dst: Area to store result * @data: Input data selecting table buckets */ -static inline void pipapo_and_field_buckets_8bit (struct nft_pipapo_field *f, +static inline void pipapo_and_field_buckets_8bit (const struct nft_pipapo_field *f,unsigned long *dst,const u8 *data) {
net/netfilter/nft_set_pipapo_avx2.c +35 -24
132 lines not on this page · raw message
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 146/484 netfilter: nf_set_pipapo: fix initial map fill
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Florian Westphal <[email protected]>
[ Upstream commit 791a615b7ad2258c560f91852be54b0480837c93 ]
The initial buffer has to be inited to all-ones, but it must restrict it to the size of the first field, not the total field size.
After each round in the map search step, the result and the fill map are swapped, so if we have a set where f->bsize of the first element is smaller than m->bsize_max, those one-bits are leaked into future rounds result map.
This makes pipapo find an incorrect matching results for sets where first field size is not the largest.
Followup patch adds a test case to nft_concat_range.sh selftest script.
Thanks to Stefano Brivio for pointing out that we need to zero out the remainder explicitly, only correcting memset() argument isn't enough.
--- net/netfilter/nft_set_pipapo.c | 4 ++-- net/netfilter/nft_set_pipapo.h | 21 +++++++++++++++++++++ net/netfilter/nft_set_pipapo_avx2.c | 10 ++++++---- 3 files changed, 29 insertions(+), 6 deletions(-)
net/netfilter/nft_set_pipapo.c +2 -2
@@ -432,7 +432,7 @@ bool nft_pipapo_lookup(const struct net *net, const struct nft_set *set, res_map = scratch->map + (map_index ? m->bsize_max :0 ); fill_map = scratch->map + (map_index ?0 : m->bsize_max); -memset (res_map,0xff , m->bsize_max *sizeof (*res_map)); +pipapo_resmap_init (m, res_map);nft_pipapo_for_each_field (f, i, m) {bool last = i == m->field_count -1 ;
@@ -536,7 +536,7 @@ static struct nft_pipapo_elem *pipapo_get(const struct net *net, goto out; } -memset (res_map,0xff , m->bsize_max *sizeof (*res_map)); +pipapo_resmap_init (m, res_map);nft_pipapo_for_each_field (f, i, m) {bool last = i == m->field_count -1 ;
net/netfilter/nft_set_pipapo.h +21 -0
@@ -285,4 +285,25 @@ static u64 pipapo_estimate_size(const struct nft_set_desc *desc) return size; } +/** +* pipapo_resmap_init() - Initialise result map before first use +* @m: Matching data, including mapping table +* @res_map: Result map +* +* Initialize all bits covered by the first field to one, so that after +* the first step, only the matching bits of the first bit group remain. +* +* If other fields have a large bitmap, set remainder of res_map to 0. +*/ +static inline void pipapo_resmap_init (const struct nft_pipapo_match *m,unsigned long *res_map) +{ +const struct nft_pipapo_field *f = m->f; +int i; + +for (i =0 ; i < f->bsize; i++) + res_map[i] =ULONG_MAX ; + +for (i = f->bsize; i < m->bsize_max; i++) + res_map[i] =0ul ; +}#endif /* _NFT_SET_PIPAPO_H */
net/netfilter/nft_set_pipapo_avx2.c +6 -4
@@ -1036,6 +1036,7 @@ static int nft_pipapo_avx2_lookup_8b_16(unsigned long *map, unsigned long *fill,/** * nft_pipapo_avx2_lookup_slow() - Fallback function for uncommon field sizes +* @mdata: Matching data, including mapping table * @map: Previous match result, used as initial bitmap * @fill: Destination bitmap to be filled with current match result * @f: Field, containing lookup and mapping tables
@@ -1051,7 +1052,8 @@ static int nft_pipapo_avx2_lookup_8b_16(unsigned long *map, unsigned long *fill,* Return: -1 on no match, rule index of match if @last, otherwise first long * word index to be checked next (i.e. first filled word). */ -static int nft_pipapo_avx2_lookup_slow (unsigned long *map,unsigned long *fill, +static int nft_pipapo_avx2_lookup_slow (const struct nft_pipapo_match *mdata, +unsigned long *map,unsigned long *fill,const struct nft_pipapo_field *f,int offset,const u8 *pkt,bool first,bool last)
@@ -1062,7 +1064,7 @@ static int nft_pipapo_avx2_lookup_slow(unsigned long *map, unsigned long *fill, lt += offset *NFT_PIPAPO_LONGS_PER_M256 ;if (first) -memset (map,0xff , bsize *sizeof (*map)); +pipapo_resmap_init (mdata, map);for (i = offset; i < bsize; i++) {if (f->bb ==8 )
@@ -1188,7 +1190,7 @@ bool nft_pipapo_avx2_lookup(const struct net *net, const struct nft_set *set, }else if (f->groups ==16 ) {NFT_SET_PIPAPO_AVX2_LOOKUP (8 ,16 ); }else { - ret =nft_pipapo_avx2_lookup_slow (res, fill, f, + ret =nft_pipapo_avx2_lookup_slow (m, res, fill, f, ret, rp, first, last); }
@@ -1204,7 +1206,7 @@ bool nft_pipapo_avx2_lookup(const struct net *net, const struct nft_set *set, }else if (f->groups ==32 ) {NFT_SET_PIPAPO_AVX2_LOOKUP (4 ,32 ); }else { - ret =nft_pipapo_avx2_lookup_slow (res, fill, f, + ret =nft_pipapo_avx2_lookup_slow (m, res, fill, f, ret, rp, first, last); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 147/484 net: dsa: mv88e6xxx: Limit chip-wide frame size config to CPU ports
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Martin Willi <[email protected]>
[ Upstream commit 66b6095c264e1b4e0a441c6329861806504e06c6 ]
Marvell chips not supporting per-port jumbo frame size configurations use a chip-wide frame size configuration. In the commit referenced with the Fixes tag, the setting is applied just for the last port changing its MTU.
While configuring CPU ports accounts for tagger overhead, user ports do not. When setting the MTU for a user port, the chip-wide setting is reduced to not include the tagger overhead, resulting in an potentially insufficient maximum frame size for the CPU port. Specifically, sending full-size frames from the CPU port on a MV88E6097 having a user port MTU of 1500 bytes results in dropped frames.
As, by design, the CPU port MTU is adjusted for any user port change, apply the chip-wide setting only for CPU ports.
--- drivers/net/dsa/mv88e6xxx/chip.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/net/dsa/mv88e6xxx/chip.c +2 -1
@@ -3104,7 +3104,8 @@ static int mv88e6xxx_change_mtu(struct dsa_switch *ds, int port, int new_mtu)mv88e6xxx_reg_lock (chip);if (chip->info->ops->port_set_jumbo_size) ret = chip->info->ops->port_set_jumbo_size (chip, port, new_mtu); -else if (chip->info->ops->set_max_frame_size) +else if (chip->info->ops->set_max_frame_size && +dsa_is_cpu_port (ds, port)) ret = chip->info->ops->set_max_frame_size (chip, new_mtu);mv88e6xxx_reg_unlock (chip);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 148/484 net: dsa: b53: Limit chip-wide jumbo frame config to CPU ports
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Martin Willi <[email protected]>
[ Upstream commit c5118072e228e7e4385fc5ac46b2e31cf6c4f2d3 ]
Broadcom switches supported by the b53 driver use a chip-wide jumbo frame configuration. In the commit referenced with the Fixes tag, the setting is applied just for the last port changing its MTU.
While configuring CPU ports accounts for tagger overhead, user ports do not. When setting the MTU for a user port, the chip-wide setting is reduced to not include the tagger overhead, resulting in an potentially insufficient chip-wide maximum frame size for the CPU port.
As, by design, the CPU port MTU is adjusted for any user port change, apply the chip-wide setting only for CPU ports. This aligns the driver to the behavior of other switch drivers.
--- drivers/net/dsa/b53/b53_common.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/net/dsa/b53/b53_common.c +3 -0
@@ -2223,6 +2223,9 @@ static int b53_change_mtu(struct dsa_switch *ds, int port, int mtu)if (is5325 (dev) ||is5365 (dev))return -EOPNOTSUPP ; +if (!dsa_is_cpu_port (ds, port)) +return 0 ; + enable_jumbo = (mtu >=JMS_MIN_SIZE ); allow_10_100 = (dev->chip_id ==BCM583XX_DEVICE_ID );
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 149/484 fs/ntfs3: Use ALIGN kernel macro
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 97a6815e50619377704e6566fb2b77c1aa4e2647 ]
This way code will be more readable.
Stable-dep-of: 25610ff98d4a ("fs/ntfs3: Fix transform resident to nonresident for compressed files")
--- fs/ntfs3/fsntfs.c | 2 +- fs/ntfs3/ntfs.h | 1 - fs/ntfs3/ntfs_fs.h | 2 ++ 3 files changed, 3 insertions(+), 2 deletions(-)
fs/ntfs3/fsntfs.c +1 -1
@@ -475,7 +475,7 @@ static int ntfs_extend_mft(struct ntfs_sb_info *sbi)struct ATTRIB *attr;struct wnd_bitmap *wnd = &sbi->mft.bitmap; - new_mft_total = (wnd->nbits +MFT_INCREASE_CHUNK +127 ) & (CLST )~127 ; + new_mft_total =ALIGN (wnd->nbits +NTFS_MFT_INCREASE_STEP ,128 ); new_mft_bytes = (u64 )new_mft_total << sbi->record_bits;/* Step 1: Resize $MFT::DATA. */
fs/ntfs3/ntfs.h +0 -1
@@ -84,7 +84,6 @@ typedef u32 CLST;#define COMPRESSION_UNIT 4#define COMPRESS_MAX_CLUSTER 0x1000 -#define MFT_INCREASE_CHUNK 1024enum RECORD_NUM {MFT_REC_MFT =0 ,
fs/ntfs3/ntfs_fs.h +2 -0
@@ -198,6 +198,8 @@ struct ntfs_index {/* Minimum MFT zone. */ #define NTFS_MIN_MFT_ZONE 100 +/* Step to increase the MFT. */ +#define NTFS_MFT_INCREASE_STEP 1024/* Ntfs file system in-core superblock data. */ struct ntfs_sb_info {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 150/484 fs/ntfs3: Merge synonym COMPRESSION_UNIT and NTFS_LZNT_CUNIT
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 487f8d482a7e51a640b8f955a398f906a4f83951 ]
COMPRESSION_UNIT and NTFS_LZNT_CUNIT mean the same thing (1u<<NTFS_LZNT_CUNIT) determines the size for compression (in clusters).
COMPRESS_MAX_CLUSTER is not used in the code.
Stable-dep-of: 25610ff98d4a ("fs/ntfs3: Fix transform resident to nonresident for compressed files")
--- fs/ntfs3/attrib.c | 2 +- fs/ntfs3/frecord.c | 2 +- fs/ntfs3/fslog.c | 2 +- fs/ntfs3/inode.c | 2 +- fs/ntfs3/ntfs.h | 3 --- 5 files changed, 4 insertions(+), 7 deletions(-)
fs/ntfs3/attrib.c +1 -1
@@ -265,7 +265,7 @@ int attr_make_nonresident(struct ntfs_inode *ni, struct ATTRIB *attr, align = sbi->cluster_size;if (is_attr_compressed (attr)) - align <<=COMPRESSION_UNIT ; + align <<=NTFS_LZNT_CUNIT ; len = (rsize + align -1 ) >> sbi->cluster_bits;run_init (run);
fs/ntfs3/frecord.c +1 -1
@@ -1453,7 +1453,7 @@ int ni_insert_nonresident(struct ntfs_inode *ni, enum ATTR_TYPE type,if (is_ext) {if (flags &ATTR_FLAG_COMPRESSED ) - attr->nres.c_unit =COMPRESSION_UNIT ; + attr->nres.c_unit =NTFS_LZNT_CUNIT ; attr->nres.total_size = attr->nres.alloc_size; }
fs/ntfs3/fslog.c +1 -1
@@ -2999,7 +2999,7 @@ static struct ATTRIB *attr_create_nonres_log(struct ntfs_sb_info *sbi,if (is_ext) { attr->name_off =SIZEOF_NONRESIDENT_EX_LE ;if (is_attr_compressed (attr)) - attr->nres.c_unit =COMPRESSION_UNIT ; + attr->nres.c_unit =NTFS_LZNT_CUNIT ; attr->nres.run_off =cpu_to_le16 (SIZEOF_NONRESIDENT_EX + name_size);
fs/ntfs3/inode.c +1 -1
@@ -1465,7 +1465,7 @@ struct inode *ntfs_create_inode(struct user_namespace *mnt_userns, attr->size =cpu_to_le32 (SIZEOF_NONRESIDENT_EX +8 ); attr->name_off =SIZEOF_NONRESIDENT_EX_LE ; attr->flags =ATTR_FLAG_COMPRESSED ; - attr->nres.c_unit =COMPRESSION_UNIT ; + attr->nres.c_unit =NTFS_LZNT_CUNIT ; asize =SIZEOF_NONRESIDENT_EX +8 ; }else { attr->size =cpu_to_le32 (SIZEOF_NONRESIDENT +8 );
fs/ntfs3/ntfs.h +0 -3
@@ -82,9 +82,6 @@ typedef u32 CLST;#define RESIDENT_LCN ((CLST)-2)#define COMPRESSED_LCN ((CLST)-3) -#define COMPRESSION_UNIT 4 -#define COMPRESS_MAX_CLUSTER 0x1000 -enum RECORD_NUM {MFT_REC_MFT =0 ,MFT_REC_MIRR =1 ,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 151/484 fs/ntfs3: Fix transform resident to nonresident for compressed files
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 25610ff98d4a34e6a85cbe4fd8671be6b0829f8f ]
Сorrected calculation of required space len (in clusters) for attribute data storage in case of compression.
--- fs/ntfs3/attrib.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-)
fs/ntfs3/attrib.c +8 -5
@@ -242,7 +242,7 @@ int attr_make_nonresident(struct ntfs_inode *ni, struct ATTRIB *attr,struct ntfs_sb_info *sbi;struct ATTRIB *attr_s;struct MFT_REC *rec; -u32 used, asize, rsize, aoff, align; +u32 used, asize, rsize, aoff;bool is_data;CLST len, alen;char *next;
@@ -263,10 +263,13 @@ int attr_make_nonresident(struct ntfs_inode *ni, struct ATTRIB *attr, rsize =le32_to_cpu (attr->res.data_size); is_data = attr->type ==ATTR_DATA && !attr->name_len; - align = sbi->cluster_size; -if (is_attr_compressed (attr)) - align <<=NTFS_LZNT_CUNIT ; - len = (rsize + align -1 ) >> sbi->cluster_bits; +/* len - how many clusters required to store 'rsize' bytes */ +if (is_attr_compressed (attr)) { +u8 shift = sbi->cluster_bits +NTFS_LZNT_CUNIT ; + len = ((rsize + (1u << shift) -1 ) >> shift) <<NTFS_LZNT_CUNIT ; + }else { + len =bytes_to_cluster (sbi, rsize); + }run_init (run);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 152/484 fs/ntfs3: Missed NI_FLAG_UPDATE_PARENT setting
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 1c308ace1fd6de93bd0b7e1a5e8963ab27e2c016 ]
--- fs/ntfs3/attrib.c | 1 + 1 file changed, 1 insertion(+)
fs/ntfs3/attrib.c +1 -0
@@ -1565,6 +1565,7 @@ int attr_allocate_frame(struct ntfs_inode *ni, CLST frame, size_t compr_size, attr_b->nres.total_size =cpu_to_le64 (total_size);inode_set_bytes (&ni->vfs_inode, total_size); + ni->ni_flags |=NI_FLAG_UPDATE_PARENT ; mi_b->dirty = true;mark_inode_dirty (&ni->vfs_inode);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 153/484 fs/ntfs3: Fix getting file type
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 24c5100aceedcd47af89aaa404d4c96cd2837523 ]
An additional condition causes the mft record to be read from disk and get the file type dt_type.
--- fs/ntfs3/dir.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
fs/ntfs3/dir.c +2 -1
@@ -326,7 +326,8 @@ static inline int ntfs_filldir(struct ntfs_sb_info *sbi, struct ntfs_inode *ni,* It does additional locks/reads just to get the type of name. * Should we use additional mount option to enable branch below? */ -if ((fname->dup.fa &FILE_ATTRIBUTE_REPARSE_POINT ) && +if (((fname->dup.fa &FILE_ATTRIBUTE_REPARSE_POINT ) || + fname->dup.ea_size) && ino != ni->mi.rno) {struct inode *inode =ntfs_iget5 (sbi->sb, &e->ref,NULL );if (!IS_ERR_OR_NULL (inode)) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 154/484 pinctrl: rockchip: update rk3308 iomux routes
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dmitry Yashin <[email protected]>
[ Upstream commit a8f2548548584549ea29d43431781d67c4afa42b ]
Some of the rk3308 iomux routes in rk3308_mux_route_data belong to the rk3308b SoC. Remove them and correct i2c3 routes.
--- drivers/pinctrl/pinctrl-rockchip.c | 17 ++--------------- 1 file changed, 2 insertions(+), 15 deletions(-)
drivers/pinctrl/pinctrl-rockchip.c +2 -15
@@ -748,9 +748,8 @@ static struct rockchip_mux_route_data rk3308_mux_route_data[] = {RK_MUXROUTE_SAME (0 ,RK_PC3 ,1 ,0x314 ,BIT (16 +0 ) |BIT (0 )),/* rtc_clk */ RK_MUXROUTE_SAME (1 ,RK_PC6 ,2 ,0x314 ,BIT (16 +2 ) |BIT (16 +3 )),/* uart2_rxm0 */ RK_MUXROUTE_SAME (4 ,RK_PD2 ,2 ,0x314 ,BIT (16 +2 ) |BIT (16 +3 ) |BIT (2 )),/* uart2_rxm1 */ -RK_MUXROUTE_SAME (0 ,RK_PB7 ,2 ,0x608 ,BIT (16 +8 ) |BIT (16 +9 )),/* i2c3_sdam0 */ -RK_MUXROUTE_SAME (3 ,RK_PB4 ,2 ,0x608 ,BIT (16 +8 ) |BIT (16 +9 ) |BIT (8 )),/* i2c3_sdam1 */ -RK_MUXROUTE_SAME (2 ,RK_PA0 ,3 ,0x608 ,BIT (16 +8 ) |BIT (16 +9 ) |BIT (9 )),/* i2c3_sdam2 */ +RK_MUXROUTE_SAME (0 ,RK_PB7 ,2 ,0x314 ,BIT (16 +4 )),/* i2c3_sdam0 */ +RK_MUXROUTE_SAME (3 ,RK_PB4 ,2 ,0x314 ,BIT (16 +4 ) |BIT (4 )),/* i2c3_sdam1 */ RK_MUXROUTE_SAME (1 ,RK_PA3 ,2 ,0x308 ,BIT (16 +3 )),/* i2s-8ch-1-sclktxm0 */ RK_MUXROUTE_SAME (1 ,RK_PA4 ,2 ,0x308 ,BIT (16 +3 )),/* i2s-8ch-1-sclkrxm0 */ RK_MUXROUTE_SAME(1, RK_PB5, 2, 0x308, BIT(16 + 3) | BIT(3)), /* i2s-8ch-1-sclktxm1 */
@@ -759,18 +758,6 @@ static struct rockchip_mux_route_data rk3308_mux_route_data[] = {RK_MUXROUTE_SAME (1 ,RK_PB6 ,4 ,0x308 ,BIT (16 +12 ) |BIT (16 +13 ) |BIT (12 )),/* pdm-clkm1 */ RK_MUXROUTE_SAME (2 ,RK_PA6 ,2 ,0x308 ,BIT (16 +12 ) |BIT (16 +13 ) |BIT (13 )),/* pdm-clkm2 */ RK_MUXROUTE_SAME(2, RK_PA4, 3, 0x600, BIT(16 + 2) | BIT(2)), /* pdm-clkm-m2 */ -RK_MUXROUTE_SAME (3 ,RK_PB2 ,3 ,0x314 ,BIT (16 +9 )),/* spi1_miso */ -RK_MUXROUTE_SAME (2 ,RK_PA4 ,2 ,0x314 ,BIT (16 +9 ) |BIT (9 )),/* spi1_miso_m1 */ -RK_MUXROUTE_SAME (0 ,RK_PB3 ,3 ,0x314 ,BIT (16 +10 ) |BIT (16 +11 )),/* owire_m0 */ -RK_MUXROUTE_SAME (1 ,RK_PC6 ,7 ,0x314 ,BIT (16 +10 ) |BIT (16 +11 ) |BIT (10 )),/* owire_m1 */ -RK_MUXROUTE_SAME (2 ,RK_PA2 ,5 ,0x314 ,BIT (16 +10 ) |BIT (16 +11 ) |BIT (11 )),/* owire_m2 */ -RK_MUXROUTE_SAME (0 ,RK_PB3 ,2 ,0x314 ,BIT (16 +12 ) |BIT (16 +13 )),/* can_rxd_m0 */ -RK_MUXROUTE_SAME (1 ,RK_PC6 ,5 ,0x314 ,BIT (16 +12 ) |BIT (16 +13 ) |BIT (12 )),/* can_rxd_m1 */ -RK_MUXROUTE_SAME (2 ,RK_PA2 ,4 ,0x314 ,BIT (16 +12 ) |BIT (16 +13 ) |BIT (13 )),/* can_rxd_m2 */ -RK_MUXROUTE_SAME (1 ,RK_PC4 ,3 ,0x314 ,BIT (16 +14 )),/* mac_rxd0_m0 */ -RK_MUXROUTE_SAME (4 ,RK_PA2 ,2 ,0x314 ,BIT (16 +14 ) |BIT (14 )),/* mac_rxd0_m1 */ -RK_MUXROUTE_SAME (3 ,RK_PB4 ,4 ,0x314 ,BIT (16 +15 )),/* uart3_rx */ - RK_MUXROUTE_SAME(0, RK_PC1, 3, 0x314, BIT(16 + 15) | BIT(15)), /* uart3_rx_m1 */ }; static struct rockchip_mux_route_data rk3328_mux_route_data[] = {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 155/484 pinctrl: core: fix possible memory leak when pinctrl_enable() fails
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Yang Yingliang <[email protected]>
[ Upstream commit ae1cf4759972c5fe665ee4c5e0c29de66fe3cf4a ]
In devm_pinctrl_register(), if pinctrl_enable() fails in pinctrl_register(), the "pctldev" has not been added to dev resources, so devm_pinctrl_dev_release() can not be called, it leads memory leak.
Introduce pinctrl_uninit_controller(), call it in the error path to free memory.
--- drivers/pinctrl/core.c | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-)
drivers/pinctrl/core.c +11 -1
@@ -2062,6 +2062,14 @@ pinctrl_init_controller(struct pinctrl_desc *pctldesc, struct device *dev,return ERR_PTR (ret); } +static void pinctrl_uninit_controller (struct pinctrl_dev *pctldev,struct pinctrl_desc *pctldesc) +{ +pinctrl_free_pindescs (pctldev, pctldesc->pins, + pctldesc->npins); +mutex_destroy (&pctldev->mutex); +kfree (pctldev); +} +static int pinctrl_claim_hogs (struct pinctrl_dev *pctldev) { pctldev->p =create_pinctrl (pctldev->dev, pctldev);
@@ -2142,8 +2150,10 @@ struct pinctrl_dev *pinctrl_register(struct pinctrl_desc *pctldesc,return pctldev; error =pinctrl_enable (pctldev); -if (error) +if (error) { +pinctrl_uninit_controller (pctldev, pctldesc);return ERR_PTR (error); + }return pctldev; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 156/484 pinctrl: single: fix possible memory leak when pinctrl_enable() fails
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Yang Yingliang <[email protected]>
[ Upstream commit 8f773bfbdd428819328a2d185976cfc6ae811cd3 ]
This driver calls pinctrl_register_and_init() which is not devm_ managed, it will leads memory leak if pinctrl_enable() fails. Replace it with devm_pinctrl_register_and_init(). And call pcs_free_resources() if pinctrl_enable() fails.
--- drivers/pinctrl/pinctrl-single.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/pinctrl/pinctrl-single.c +4 -3
@@ -1328,7 +1328,6 @@ static void pcs_irq_free(struct pcs_device *pcs)static void pcs_free_resources (struct pcs_device *pcs) {pcs_irq_free (pcs); -pinctrl_unregister (pcs->pctl);#if IS_BUILTIN (CONFIG_PINCTRL_SINGLE )if (pcs->missing_nr_pinctrl_cells)
@@ -1885,7 +1884,7 @@ static int pcs_probe(struct platform_device *pdev)if (ret <0 ) goto free; - ret =pinctrl_register_and_init (&pcs->desc, pcs->dev, pcs, &pcs->pctl); + ret =devm_pinctrl_register_and_init (pcs->dev, &pcs->desc, pcs, &pcs->pctl);if (ret) {dev_err (pcs->dev,"could not register single pinctrl driver\n" ); goto free;
@@ -1918,8 +1917,10 @@ static int pcs_probe(struct platform_device *pdev)dev_info (pcs->dev,"%i pins, size %u\n" , pcs->desc.npins, pcs->size); -return pinctrl_enable (pcs->pctl); +if (pinctrl_enable (pcs->pctl)) + goto free; +return 0 ; free:pcs_free_resources (pcs);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 157/484 pinctrl: ti: ti-iodelay: Drop if block with always false condition
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Uwe Kleine-König <[email protected]>
[ Upstream commit 88b3f108502bc45e6ebd005702add46759f3f45a ]
ti_iodelay_remove() is only called after ti_iodelay_probe() completed successfully. In this case platform_set_drvdata() was called with a non-NULL argument and so platform_get_drvdata() won't return NULL.
Simplify by removing the if block with the always false condition.
Stable-dep-of: 9b401f4a7170 ("pinctrl: ti: ti-iodelay: fix possible memory leak when pinctrl_enable() fails")
--- drivers/pinctrl/ti/pinctrl-ti-iodelay.c | 3 --- 1 file changed, 3 deletions(-)
drivers/pinctrl/ti/pinctrl-ti-iodelay.c +0 -3
@@ -908,9 +908,6 @@ static int ti_iodelay_remove(struct platform_device *pdev) {struct ti_iodelay_device *iod =platform_get_drvdata (pdev); -if (!iod) -return 0 ; -if (iod->pctl)pinctrl_unregister (iod->pctl);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 158/484 pinctrl: ti: ti-iodelay: fix possible memory leak when pinctrl_enable() fails
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Yang Yingliang <[email protected]>
[ Upstream commit 9b401f4a7170125365160c9af267a41ff6b39001 ]
This driver calls pinctrl_register_and_init() which is not devm_ managed, it will leads memory leak if pinctrl_enable() fails. Replace it with devm_pinctrl_register_and_init(). And add missing of_node_put() in the error path.
--- drivers/pinctrl/ti/pinctrl-ti-iodelay.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-)
drivers/pinctrl/ti/pinctrl-ti-iodelay.c +6 -5
@@ -883,7 +883,7 @@ static int ti_iodelay_probe(struct platform_device *pdev) iod->desc.name =dev_name (dev); iod->desc.owner =THIS_MODULE ; - ret =pinctrl_register_and_init (&iod->desc, dev, iod, &iod->pctl); + ret =devm_pinctrl_register_and_init (dev, &iod->desc, iod, &iod->pctl);if (ret) {dev_err (dev,"Failed to register pinctrl\n" ); goto exit_out;
@@ -891,7 +891,11 @@ static int ti_iodelay_probe(struct platform_device *pdev)platform_set_drvdata (pdev, iod); -return pinctrl_enable (iod->pctl); + ret =pinctrl_enable (iod->pctl); +if (ret) + goto exit_out; + +return 0 ; exit_out:of_node_put (np);
@@ -908,9 +912,6 @@ static int ti_iodelay_remove(struct platform_device *pdev) {struct ti_iodelay_device *iod =platform_get_drvdata (pdev); -if (iod->pctl) -pinctrl_unregister (iod->pctl); -ti_iodelay_pinconf_deinit_dev (iod);/* Expect other allocations to be freed by devm */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 159/484 pinctrl: freescale: mxs: Fix refcount of child
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Peng Fan <[email protected]>
[ Upstream commit 7f500f2011c0bbb6e1cacab74b4c99222e60248e ]
of_get_next_child() will increase refcount of the returned node, need use of_node_put() on it when done.
Per current implementation, 'child' will be override by for_each_child_of_node(np, child), so use of_get_child_count to avoid refcount leakage.
--- drivers/pinctrl/freescale/pinctrl-mxs.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/pinctrl/freescale/pinctrl-mxs.c +2 -2
@@ -405,8 +405,8 @@ static int mxs_pinctrl_probe_dt(struct platform_device *pdev,int ret;u32 val; - child =of_get_next_child (np,NULL ); -if (!child) { + val =of_get_child_count (np); +if (val ==0 ) {dev_err (&pdev->dev,"no group is defined\n" );return -ENOENT ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 160/484 fs/ntfs3: Replace inode_trylock with inode_lock
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 69505fe98f198ee813898cbcaf6770949636430b ]
The issue was detected due to xfstest 465 failing.
--- fs/ntfs3/file.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-)
fs/ntfs3/file.c +1 -4
@@ -398,10 +398,7 @@ static int ntfs_file_mmap(struct file *file, struct vm_area_struct *vma) }if (ni->i_valid < to) { -if (!inode_trylock (inode)) { - err = -EAGAIN ; - goto out; - } +inode_lock (inode); err =ntfs_extend_initialized_size (file, ni, ni->i_valid, to);inode_unlock (inode);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 161/484 fs/ntfs3: Fix field-spanning write in INDEX_HDR
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 2f3e176fee66ac86ae387787bf06457b101d9f7a ]
Fields flags and res[3] replaced with one 4 byte flags.
--- fs/ntfs3/index.c | 4 ++-- fs/ntfs3/ntfs.h | 9 +++++---- 2 files changed, 7 insertions(+), 6 deletions(-)
fs/ntfs3/index.c +2 -2
@@ -979,7 +979,7 @@ static struct indx_node *indx_new(struct ntfs_index *indx, hdr->used =cpu_to_le32 (eo +sizeof (struct NTFS_DE ) +sizeof (u64));de_set_vbn_le (e, *sub_vbn); - hdr->flags =1 ; + hdr->flags =NTFS_INDEX_HDR_HAS_SUBNODES ; }else { e->size =cpu_to_le16 (sizeof (struct NTFS_DE )); hdr->used =cpu_to_le32 (eo +sizeof (struct NTFS_DE ));
@@ -1684,7 +1684,7 @@ static int indx_insert_into_root(struct ntfs_index *indx, struct ntfs_inode *ni, e->size =cpu_to_le16 (sizeof (struct NTFS_DE ) +sizeof (u64)); e->flags =NTFS_IE_HAS_SUBNODES |NTFS_IE_LAST ; - hdr->flags =1 ; + hdr->flags =NTFS_INDEX_HDR_HAS_SUBNODES ; hdr->used = hdr->total =cpu_to_le32 (new_root_size - offsetof(struct INDEX_ROOT , ihdr));
fs/ntfs3/ntfs.h +5 -4
@@ -686,14 +686,15 @@ static inline bool de_has_vcn_ex(const struct NTFS_DE *e) offsetof(struct ATTR_FILE_NAME, name) + \ NTFS_NAME_LEN * sizeof(short), 8) +#define NTFS_INDEX_HDR_HAS_SUBNODES cpu_to_le32(1) +struct INDEX_HDR {__le32 de_off;// 0x00: The offset from the start of this structure // to the first NTFS_DE. __le32 used;// 0x04: The size of this structure plus all // entries (quad-word aligned). __le32 total;// 0x08: The allocated size of for this structure plus all entries. -u8 flags;// 0x0C: 0x00 = Small directory, 0x01 = Large directory. -u8 res[3 ]; +__le32 flags;// 0x0C: 0x00 = Small directory, 0x01 = Large directory. // // de_off + used <= total
@@ -740,7 +741,7 @@ static inline struct NTFS_DE *hdr_next_de(const struct INDEX_HDR *hdr,static inline bool hdr_has_subnode (const struct INDEX_HDR *hdr) { -return hdr->flags &1 ; +return hdr->flags &NTFS_INDEX_HDR_HAS_SUBNODES ; }struct INDEX_BUFFER {
@@ -760,7 +761,7 @@ static inline bool ib_is_empty(const struct INDEX_BUFFER *ib)static inline bool ib_is_leaf (const struct INDEX_BUFFER *ib) { -return !(ib->ihdr.flags &1 ); +return !(ib->ihdr.flags &NTFS_INDEX_HDR_HAS_SUBNODES ); }/* Index root structure ( 0x90 ). */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 162/484 fs/proc/task_mmu: indicate PM_FILE for PMD-mapped file THP
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: David Hildenbrand <[email protected]>
[ Upstream commit 3f9f022e975d930709848a86a1c79775b0585202 ]
Patch series "fs/proc: move page_mapcount() to fs/proc/internal.h".
With all other page_mapcount() users in the tree gone, move page_mapcount() to fs/proc/internal.h, rename it and extend the documentation to prevent future (ab)use.
... of course, I find some issues while working on that code that I sort first ;)
We'll now only end up calling page_mapcount() [now folio_precise_page_mapcount()] on pages mapped via present page table entries. Except for /proc/kpagecount, that still does questionable things, but we'll leave that legacy interface as is for now.
Did a quick sanity check. Likely we would want some better selfestest for /proc/$/pagemap + smaps. I'll see if I can find some time to write some more.
This patch (of 6):
Looks like we never taught pagemap_pmd_range() about the existence of PMD-mapped file THPs. Seems to date back to the times when we first added support for non-anon THPs in the form of shmem THP.
--- fs/proc/task_mmu.c | 2 ++ 1 file changed, 2 insertions(+)
fs/proc/task_mmu.c +2 -0
@@ -1471,6 +1471,8 @@ static int pagemap_pmd_range(pmd_t *pmdp, unsigned long addr, unsigned long end, }#endif +if (page && !PageAnon (page)) + flags |=PM_FILE ;if (page && !migration &&page_mapcount (page) ==1 ) flags |=PM_MMAP_EXCLUSIVE ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 163/484 nilfs2: avoid undefined behavior in nilfs_cnt32_ge macro
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ryusuke Konishi <[email protected]>
[ Upstream commit 0f3819e8c483771a59cf9d3190cd68a7a990083c ]
According to the C standard 3.4.3p3, the result of signed integer overflow is undefined. The macro nilfs_cnt32_ge(), which compares two sequence numbers, uses signed integer subtraction that can overflow, and therefore the result of the calculation may differ from what is expected due to undefined behavior in different environments.
Similar to an earlier change to the jiffies-related comparison macros in commit 5a581b367b5d ("jiffies: Avoid undefined behavior from signed overflow"), avoid this potential issue by changing the definition of the macro to perform the subtraction as unsigned integers, then cast the result to a signed integer for comparison.
--- fs/nilfs2/segment.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
fs/nilfs2/segment.c +1 -1
@@ -136,7 +136,7 @@ static void nilfs_dispose_list(struct the_nilfs *, struct list_head *, int);#define nilfs_cnt32_ge (a, b) \ (typecheck(__u32, a) && typecheck(__u32, b) && \ - ((__s32)(a) - (__s32)(b) >= 0)) + ((__s32)((a) - (b)) >= 0))static int nilfs_prepare_segment_lock (struct super_block *sb,struct nilfs_transaction_info *ti)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 164/484 rtc: interface: Add RTC offset to alarm after fix-up
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Csókás, Bence <[email protected]>
[ Upstream commit 463927a8902a9f22c3633960119410f57d4c8920 ]
rtc_add_offset() is called by __rtc_read_time() and __rtc_read_alarm() to add the RTC's offset to the raw read-outs from the device drivers. However, in the latter case, a fix-up algorithm is run if the RTC device does not report a full struct rtc_time alarm value. In that case, the offset was forgot to be added.
--- drivers/rtc/interface.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-)
drivers/rtc/interface.c +5 -4
@@ -274,10 +274,9 @@ int __rtc_read_alarm(struct rtc_device *rtc, struct rtc_wkalrm *alarm)return err;/* full-function RTCs won't have such missing fields */ -if (rtc_valid_tm (&alarm->time) ==0 ) { -rtc_add_offset (rtc, &alarm->time); -return 0 ; - } + err =rtc_valid_tm (&alarm->time); +if (!err) + goto done;/* get the "after" timestamp, to detect wrapped fields */ err =rtc_read_time (rtc, &now);
@@ -379,6 +378,8 @@ int __rtc_read_alarm(struct rtc_device *rtc, struct rtc_wkalrm *alarm)if (err)dev_warn (&rtc->dev,"invalid alarm value: %ptR\n" , &alarm->time); +else +rtc_add_offset (rtc, &alarm->time);return err; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 165/484 fs/ntfs3: Missed error return
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Konstantin Komarov <[email protected]>
[ Upstream commit 2cbbd96820255fff4f0ad1533197370c9ccc570b ]
--- fs/ntfs3/bitmap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
fs/ntfs3/bitmap.c +1 -1
@@ -1363,7 +1363,7 @@ int wnd_extend(struct wnd_bitmap *wnd, size_t new_bits) err =ntfs_vbo_to_lbo (sbi, &wnd->run, vbo, &lbo, &bytes);if (err) -break ; +return err; bh =ntfs_bread (sb, lbo >> sb->s_blocksize_bits);if (!bh)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 166/484 s390/dasd: fix error checks in dasd_copy_pair_store()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Carlos López <[email protected]>
[ Upstream commit 8e64d2356cbc800b4cd0e3e614797f76bcf0cdb8 ]
dasd_add_busid() can return an error via ERR_PTR() if an allocation fails. However, two callsites in dasd_copy_pair_store() do not check the result, potentially resulting in a NULL pointer dereference. Fix this by checking the result with IS_ERR() and returning the error up the stack.
--- drivers/s390/block/dasd_devmap.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-)
drivers/s390/block/dasd_devmap.c +8 -2
@@ -2141,13 +2141,19 @@ static ssize_t dasd_copy_pair_store(struct device *dev,/* allocate primary devmap if needed */ prim_devmap =dasd_find_busid (prim_busid); -if (IS_ERR (prim_devmap)) +if (IS_ERR (prim_devmap)) { prim_devmap =dasd_add_busid (prim_busid,DASD_FEATURE_DEFAULT ); +if (IS_ERR (prim_devmap)) +return PTR_ERR (prim_devmap); + }/* allocate secondary devmap if needed */ sec_devmap =dasd_find_busid (sec_busid); -if (IS_ERR (sec_devmap)) +if (IS_ERR (sec_devmap)) { sec_devmap =dasd_add_busid (sec_busid,DASD_FEATURE_DEFAULT ); +if (IS_ERR (sec_devmap)) +return PTR_ERR (sec_devmap); + }/* setting copy relation is only allowed for offline secondary */ if (sec_devmap->device)
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 167/484 landlock: Dont lose track of restrictions on cred_transfer
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jann Horn <[email protected]>
commit 39705a6c29f8a2b93cf5b99528a55366c50014d1 upstream.
When a process' cred struct is replaced, this _almost_ always invokes the cred_prepare LSM hook; but in one special case (when KEYCTL_SESSION_TO_PARENT updates the parent's credentials), the cred_transfer LSM hook is used instead. Landlock only implements the cred_prepare hook, not cred_transfer, so KEYCTL_SESSION_TO_PARENT causes all information on Landlock restrictions to be lost.
This basically means that a process with the ability to use the fork() and keyctl() syscalls can get rid of all Landlock restrictions on itself.
Fix it by adding a cred_transfer hook that does the same thing as the existing cred_prepare hook. (Implemented by having hook_cred_prepare() call hook_cred_transfer() so that the two functions are less likely to accidentally diverge in the future.)
--- security/landlock/cred.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-)
security/landlock/cred.c +9 -2
@@ -14,8 +14,8 @@#include "ruleset.h" #include "setup.h" -static int hook_cred_prepare (struct cred *const new, -const struct cred *const old,const gfp_t gfp) +static void hook_cred_transfer (struct cred *const new, +const struct cred *const old) {struct landlock_ruleset *const old_dom =landlock_cred (old)->domain;
@@ -23,6 +23,12 @@ static int hook_cred_prepare(struct credlandlock_get_ruleset (old_dom);landlock_cred (new)->domain = old_dom; } +} + +static int hook_cred_prepare (struct cred *const new, +const struct cred *const old,const gfp_t gfp) +{ +hook_cred_transfer (new, old);return 0 ; }
@@ -36,6 +42,7 @@ static void hook_cred_free(struct cred * static struct security_hook_list landlock_hooks[] __lsm_ro_after_init = {LSM_HOOK_INIT (cred_prepare, hook_cred_prepare), +LSM_HOOK_INIT (cred_transfer, hook_cred_transfer),LSM_HOOK_INIT (cred_free, hook_cred_free), };
Greg Kroah-Hartman
maintainerPATCH 168/484 mm/hugetlb: fix possible recursive locking detected warning
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Miaohe Lin <[email protected]>
commit 667574e873b5f77a220b2a93329689f36fb56d5d upstream.
When tries to demote 1G hugetlb folios, a lockdep warning is observed:
============================================
WARNING: possible recursive locking detected 6.10.0-rc6-00452-ga4d0275fa660-dirty #79 Not tainted
--------------------------------------------
bash/710 is trying to acquire lock:ffffffff8f0a7850 (&h->resize_lock){+.+.}-{3:3}, at: demote_store+0x244/0x460
but task is already holding lock:ffffffff8f0a6f48 (&h->resize_lock){+.+.}-{3:3}, at: demote_store+0xae/0x460
other info that might help us debug this:
Possible unsafe locking scenario:
CPU0
---- lock(&h->resize_lock);
lock(&h->resize_lock);
*** DEADLOCK ***
May be due to missing lock nesting notation
4 locks held by bash/710:
#0: ffff8f118439c3f0 (sb_writers#5){.+.+}-{0:0}, at: ksys_write+0x64/0xe0 #1: ffff8f11893b9e88 (&of->mutex#2){+.+.}-{3:3}, at: kernfs_fop_write_iter+0xf8/0x1d0 #2: ffff8f1183dc4428 (kn->active#98){.+.+}-{0:0}, at: kernfs_fop_write_iter+0x100/0x1d0 #3: ffffffff8f0a6f48 (&h->resize_lock){+.+.}-{3:3}, at: demote_store+0xae/0x460
stack backtrace: CPU: 3 PID: 710 Comm: bash Not tainted 6.10.0-rc6-00452-ga4d0275fa660-dirty #79 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.14.0-0-g155821a1990b-prebuilt.qemu.org 04/01/2014 Call Trace: <TASK> dump_stack_lvl+0x68/0xa0 __lock_acquire+0x10f2/0x1ca0 lock_acquire+0xbe/0x2d0 __mutex_lock+0x6d/0x400 demote_store+0x244/0x460 kernfs_fop_write_iter+0x12c/0x1d0 vfs_write+0x380/0x540 ksys_write+0x64/0xe0 do_syscall_64+0xb9/0x1d0 entry_SYSCALL_64_after_hwframe+0x77/0x7f RIP: 0033:0x7fa61db14887 RSP: 002b:00007ffc56c48358 EFLAGS: 00000246 ORIG_RAX: 0000000000000001 RAX: ffffffffffffffda RBX: 0000000000000002 RCX: 00007fa61db14887 RDX: 0000000000000002 RSI: 000055a030050220 RDI: 0000000000000001 RBP: 000055a030050220 R08: 00007fa61dbd1460 R09: 000000007fffffff R10: 0000000000000000 R11: 0000000000000246 R12: 0000000000000002 R13: 00007fa61dc1b780 R14: 00007fa61dc17600 R15: 00007fa61dc16a00 </TASK>
Lockdep considers this an AA deadlock because the different resize_lock mutexes reside in the same lockdep class, but this is a false positive. Place them in distinct classes to avoid these warnings.
--- include/linux/hugetlb.h | 1 + mm/hugetlb.c | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-)
include/linux/hugetlb.h +1 -0
@@ -600,6 +600,7 @@ HPAGEFLAG(VmemmapOptimized, vmemmap_opti/* Defines one hugetlb page size */ struct hstate {struct mutex resize_lock; +struct lock_class_key resize_key;int next_nid_to_alloc;int next_nid_to_free;unsigned int order;
mm/hugetlb.c +1 -1
@@ -3717,7 +3717,7 @@ void __init hugetlb_add_hstate(unsignedBUG_ON (hugetlb_max_hstate >=HUGE_MAX_HSTATE );BUG_ON (order ==0 ); h = &hstates[hugetlb_max_hstate++]; -mutex_init (&h->resize_lock); +__mutex_init (&h->resize_lock,"resize mutex" , &h->resize_key); h->order = order; h->mask = ~(huge_page_size (h) -1 );for (i =0 ; i <MAX_NUMNODES ; ++i)
Greg Kroah-Hartman
maintainerPATCH 169/484 mm: mmap_lock: replace get_memcg_path_buf() with on-stack buffer
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tetsuo Handa <[email protected]>
commit 7d6be67cfdd4a53cea7147313ca13c531e3a470f upstream.
Commit 2b5067a8143e ("mm: mmap_lock: add tracepoints around lock acquisition") introduced TRACE_MMAP_LOCK_EVENT() macro using preempt_disable() in order to let get_mm_memcg_path() return a percpu buffer exclusively used by normal, softirq, irq and NMI contexts respectively.
Commit 832b50725373 ("mm: mmap_lock: use local locks instead of disabling preemption") replaced preempt_disable() with local_lock(&memcg_paths.lock) based on an argument that preempt_disable() has to be avoided because get_mm_memcg_path() might sleep if PREEMPT_RT=y.
But syzbot started reporting
inconsistent {HARDIRQ-ON-W} -> {IN-HARDIRQ-W} usage.
and
inconsistent {SOFTIRQ-ON-W} -> {IN-SOFTIRQ-W} usage.
messages, for local_lock() does not disable IRQ.
We could replace local_lock() with local_lock_irqsave() in order to suppress these messages. But this patch instead replaces percpu buffers with on-stack buffer, for the size of each buffer returned by get_memcg_path_buf() is only 256 bytes which is tolerable for allocating from current thread's kernel stack memory.
--- mm/mmap_lock.c | 175 ++++++--------------------------------------------------- 1 file changed, 20 insertions(+), 155 deletions(-)
mm/mmap_lock.c +20 -155
@@ -19,14 +19,7 @@ EXPORT_TRACEPOINT_SYMBOL(mmap_lock_relea#ifdef CONFIG_MEMCG -/* -* Our various events all share the same buffer (because we don't want or need -* to allocate a set of buffers *per event type*), so we need to protect against -* concurrent _reg() and _unreg() calls, and count how many _reg() calls have -* been made. -*/ -static DEFINE_MUTEX (reg_lock); -static int reg_refcount;/* Protected by reg_lock. */ +static atomic_t reg_refcount;/* * Size of the buffer for memcg path names. Ignoring stack trace support,
@@ -34,136 +27,22 @@ static int reg_refcount; /* Protected by*/ #define MEMCG_PATH_BUF_SIZE MAX_FILTER_STR_VAL -/* -* How many contexts our trace events might be called in: normal, softirq, irq, -* and NMI. -*/ -#define CONTEXT_COUNT 4 - -struct memcg_path { -local_lock_t lock; -char __rcu *buf; -local_t buf_idx; -}; -static DEFINE_PER_CPU(struct memcg_path, memcg_paths) = { - .lock =INIT_LOCAL_LOCK (lock), - .buf_idx =LOCAL_INIT (0 ), -}; - -static char **tmp_bufs; - -/* Called with reg_lock held. */ -static void free_memcg_path_bufs (void ) -{ -struct memcg_path *memcg_path; -int cpu; -char **old = tmp_bufs; - -for_each_possible_cpu (cpu) { - memcg_path =per_cpu_ptr (&memcg_paths, cpu); - *(old++) =rcu_dereference_protected (memcg_path->buf, -lockdep_is_held (®_lock)); -rcu_assign_pointer (memcg_path->buf,NULL ); - } - -/* Wait for inflight memcg_path_buf users to finish. */ -synchronize_rcu (); - - old = tmp_bufs; -for_each_possible_cpu (cpu) { -kfree (*(old++)); - } - -kfree (tmp_bufs); - tmp_bufs =NULL ; -} -int trace_mmap_lock_reg (void ) { -int cpu; -char *new; - -mutex_lock (®_lock); - -/* If the refcount is going 0->1, proceed with allocating buffers. */ -if (reg_refcount++) - goto out; - - tmp_bufs =kmalloc_array (num_possible_cpus (),sizeof (*tmp_bufs), -GFP_KERNEL ); -if (tmp_bufs ==NULL ) - goto out_fail; - -for_each_possible_cpu (cpu) { - new =kmalloc (MEMCG_PATH_BUF_SIZE *CONTEXT_COUNT ,GFP_KERNEL ); -if (new ==NULL ) - goto out_fail_free; -rcu_assign_pointer (per_cpu_ptr (&memcg_paths, cpu)->buf, new); -/* Don't need to wait for inflights, they'd have gotten NULL. */ - } - -out: -mutex_unlock (®_lock); +atomic_inc (®_refcount);return 0 ; - -out_fail_free: -free_memcg_path_bufs (); -out_fail: -/* Since we failed, undo the earlier ref increment. */ - --reg_refcount; - -mutex_unlock (®_lock); -return -ENOMEM ; }void trace_mmap_lock_unreg (void ) { -mutex_lock (®_lock); - -/* If the refcount is going 1->0, proceed with freeing buffers. */ -if (--reg_refcount) - goto out; - -free_memcg_path_bufs (); - -out: -mutex_unlock (®_lock); -} - -static inline char *get_memcg_path_buf (void ) -{ -struct memcg_path *memcg_path =this_cpu_ptr (&memcg_paths); -char *buf; -int idx; - -rcu_read_lock (); - buf =rcu_dereference (memcg_path->buf); -if (buf ==NULL ) { -rcu_read_unlock (); -return NULL ; - } - idx =local_add_return (MEMCG_PATH_BUF_SIZE , &memcg_path->buf_idx) - -MEMCG_PATH_BUF_SIZE ; -return &buf[idx]; +atomic_dec (®_refcount); } -static inline void put_memcg_path_buf (void ) -{ -local_sub (MEMCG_PATH_BUF_SIZE , &this_cpu_ptr (&memcg_paths)->buf_idx); -rcu_read_unlock (); -} - -#define TRACE_MMAP_LOCK_EVENT (type, mm, ...) \ - do { \ - const char *memcg_path; \ - local_lock(&memcg_paths.lock); \ - memcg_path = get_mm_memcg_path(mm); \ - trace_mmap_lock_##type(mm, \ - memcg_path != NULL ? memcg_path : "", \ - ##__VA_ARGS__); \ - if (likely(memcg_path != NULL)) \ - put_memcg_path_buf(); \ - local_unlock(&memcg_paths.lock); \ +#define TRACE_MMAP_LOCK_EVENT (type, mm, ...) \ + do { \ + char buf[MEMCG_PATH_BUF_SIZE]; \ + get_mm_memcg_path(mm, buf, sizeof(buf)); \ + trace_mmap_lock_##type(mm, buf, ##__VA_ARGS__); \ } while (0)#else /* !CONFIG_MEMCG */
@@ -185,37 +64,23 @@ void trace_mmap_lock_unreg(void)#ifdef CONFIG_TRACING #ifdef CONFIG_MEMCG /* -* Write the given mm_struct's memcg path to a percpu buffer, and return a -* pointer to it. If the path cannot be determined, or no buffer was available -* (because the trace event is being unregistered), NULL is returned. -* -* Note: buffers are allocated per-cpu to avoid locking, so preemption must be -* disabled by the caller before calling us, and re-enabled only after the -* caller is done with the pointer. -* -* The caller must call put_memcg_path_buf() once the buffer is no longer -* needed. This must be done while preemption is still disabled. +* Write the given mm_struct's memcg path to a buffer. If the path cannot be +* determined or the trace event is being unregistered, empty string is written. */ -static const char *get_mm_memcg_path (struct mm_struct *mm) +static void get_mm_memcg_path (struct mm_struct *mm,char *buf,size_t buflen) { -char *buf =NULL ; -struct mem_cgroup *memcg =get_mem_cgroup_from_mm (mm); +struct mem_cgroup *memcg; + buf[0 ] ='\0' ; +/* No need to get path if no trace event is registered. */ +if (!atomic_read (®_refcount)) +return ; + memcg =get_mem_cgroup_from_mm (mm);if (memcg ==NULL ) - goto out; -if (unlikely (memcg->css.cgroup ==NULL )) - goto out_put; - - buf =get_memcg_path_buf (); -if (buf ==NULL ) - goto out_put; - -cgroup_path (memcg->css.cgroup, buf,MEMCG_PATH_BUF_SIZE ); - -out_put: +return ; +if (memcg->css.cgroup) +cgroup_path (memcg->css.cgroup, buf, buflen);css_put (&memcg->css); -out: -return buf; }#endif /* CONFIG_MEMCG */
Greg Kroah-Hartman
maintainerPATCH 170/484 dt-bindings: thermal: correct thermal zone node name limit
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Krzysztof Kozlowski <[email protected]>
commit 97e32381d0fc6c2602a767b0c46e15eb2b75971d upstream.
Linux kernel uses thermal zone node name during registering thermal zones and has a hard-coded limit of 20 characters, including terminating NUL byte. The bindings expect node names to finish with '-thermal' which is eight bytes long, thus we have only 11 characters for the reset of the node name (thus 10 for the pattern after leading fixed character).
--- Documentation/devicetree/bindings/thermal/thermal-zones.yaml | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
Documentation/devicetree/bindings/thermal/thermal-zones.yaml +4 -1
@@ -49,7 +49,10 @@ properties: to take when the temperature crosses those thresholds. patternProperties: - "^[a-zA-Z][a-zA-Z0-9\\-]{1,12}-thermal$": + # Node name is limited in size due to Linux kernel requirements - 19 + # characters in total (see THERMAL_NAME_LENGTH, including terminating NUL + # byte): + "^[a-zA-Z][a-zA-Z0-9\\-]{1,10}-thermal$": type: object description: Each thermal zone node contains information about how frequently it
Greg Kroah-Hartman
maintainerPATCH 171/484 tick/broadcast: Make takeover of broadcast hrtimer reliable
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Yu Liao <[email protected]>
commit f7d43dd206e7e18c182f200e67a8db8c209907fa upstream.
Running the LTP hotplug stress test on a aarch64 machine results in rcu_sched stall warnings when the broadcast hrtimer was owned by the un-plugged CPU. The issue is the following:
CPU1 (owns the broadcast hrtimer) CPU2
tick_broadcast_enter() // shutdown local timer device broadcast_shutdown_local() ... tick_broadcast_exit() clockevents_switch_state(dev, CLOCK_EVT_STATE_ONESHOT) // timer device is not programmed cpumask_set_cpu(cpu, tick_broadcast_force_mask) initiates offlining of CPU1
take_cpu_down()
/*
* CPU1 shuts down and does not
* send broadcast IPI anymore
*/
takedown_cpu() hotplug_cpu__broadcast_tick_pull() // move broadcast hrtimer to this CPU clockevents_program_event() bc_set_next() hrtimer_start() /* * timer device is not programmed * because only the first expiring * timer will trigger clockevent * device reprogramming */
What happens is that CPU2 exits broadcast mode with force bit set, then the local timer device is not reprogrammed and CPU2 expects to receive the expired event by the broadcast IPI. But this does not happen because CPU1 is offlined by CPU2. CPU switches the clockevent device to ONESHOT state, but does not reprogram the device.
The subsequent reprogramming of the hrtimer broadcast device does not program the clockevent device of CPU2 either because the pending expiry time is already in the past and the CPU expects the event to be delivered. As a consequence all CPUs which wait for a broadcast event to be delivered are stuck forever.
Fix this issue by reprogramming the local timer device if the broadcast force bit of the CPU is set so that the broadcast hrtimer is delivered.
[ tglx: Massage comment and change log. Add Fixes tag ]
--- kernel/time/tick-broadcast.c | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+)
kernel/time/tick-broadcast.c +23 -0
@@ -1137,6 +1137,7 @@ void tick_broadcast_switch_to_oneshot(vo#ifdef CONFIG_HOTPLUG_CPU void hotplug_cpu__broadcast_tick_pull (int deadcpu) { +struct tick_device *td =this_cpu_ptr (&tick_cpu_device);struct clock_event_device *bc;unsigned long flags;
@@ -1144,6 +1145,28 @@ void hotplug_cpu__broadcast_tick_pull(in bc = tick_broadcast_device.evtdev;if (bc &&broadcast_needs_cpu (bc, deadcpu)) { +/* +* If the broadcast force bit of the current CPU is set, +* then the current CPU has not yet reprogrammed the local +* timer device to avoid a ping-pong race. See +* ___tick_broadcast_oneshot_control(). +* +* If the broadcast device is hrtimer based then +* programming the broadcast event below does not have any +* effect because the local clockevent device is not +* running and not programmed because the broadcast event +* is not earlier than the pending event of the local clock +* event device. As a consequence all CPUs waiting for a +* broadcast event are stuck forever. +* +* Detect this condition and reprogram the cpu local timer +* device to avoid the starvation. +*/ +if (tick_check_broadcast_expired ()) { +cpumask_clear_cpu (smp_processor_id (), tick_broadcast_force_mask); +tick_program_event (td->evtdev->next_event,1 ); + } +/* This moves the broadcast assignment to this CPU: */ clockevents_program_event (bc, bc->next_event,1 ); }
Greg Kroah-Hartman
maintainerPATCH 172/484 net: netconsole: Disable target before netpoll cleanup
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Breno Leitao <[email protected]>
commit 97d9fba9a812cada5484667a46e14a4c976ca330 upstream.
Currently, netconsole cleans up the netpoll structure before disabling the target. This approach can lead to race conditions, as message senders (write_ext_msg() and write_msg()) check if the target is enabled before using netpoll. The sender can validate that the target is enabled, but, the netpoll might be de-allocated already, causing undesired behaviours.
This patch reverses the order of operations:
1. Disable the target
2. Clean up the netpoll structure
This change eliminates the potential race condition, ensuring that no messages are sent through a partially cleaned-up netpoll structure.
--- drivers/net/netconsole.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/net/netconsole.c +1 -1
@@ -716,6 +716,7 @@ restart:/* rtnl_lock already held * we might sleep in __netpoll_cleanup() */ + nt->enabled = false;spin_unlock_irqrestore (&target_list_lock, flags);__netpoll_cleanup (&nt->np);
@@ -723,7 +724,6 @@ restart:spin_lock_irqsave (&target_list_lock, flags);dev_put (nt->np.dev); nt->np.dev =NULL ; - nt->enabled = false; stopped = true;netconsole_target_put (nt); goto restart;
Greg Kroah-Hartman
maintainerPATCH 173/484 af_packet: Handle outgoing VLAN packets without hardware offloading
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Chengen Du <[email protected]>
commit 79eecf631c14e7f4057186570ac20e2cfac3802e upstream.
The issue initially stems from libpcap. The ethertype will be overwritten as the VLAN TPID if the network interface lacks hardware VLAN offloading. In the outbound packet path, if hardware VLAN offloading is unavailable, the VLAN tag is inserted into the payload but then cleared from the sk_buff struct. Consequently, this can lead to a false negative when checking for the presence of a VLAN tag, causing the packet sniffing outcome to lack VLAN tag information (i.e., TCI-TPID). As a result, the packet capturing tool may be unable to parse packets as expected.
The TCI-TPID is missing because the prb_fill_vlan_info() function does not modify the tp_vlan_tci/tp_vlan_tpid values, as the information is in the payload and not in the sk_buff struct. The skb_vlan_tag_present() function only checks vlan_all in the sk_buff struct. In cooked mode, the L2 header is stripped, preventing the packet capturing tool from determining the correct TCI-TPID value. Additionally, the protocol in SLL is incorrect, which means the packet capturing tool cannot parse the L3 header correctly.
--- net/packet/af_packet.c | 86 +++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 84 insertions(+), 2 deletions(-)
net/packet/af_packet.c +84 -2
@@ -505,6 +505,61 @@ static void *packet_current_frame(structreturn packet_lookup_frame (po, rb, rb->head, status); } +static u16 vlan_get_tci (struct sk_buff *skb,struct net_device *dev) +{ +u8 *skb_orig_data = skb->data; +int skb_orig_len = skb->len; +struct vlan_hdr vhdr, *vh; +unsigned int header_len; + +if (!dev) +return 0 ; + +/* In the SOCK_DGRAM scenario, skb data starts at the network +* protocol, which is after the VLAN headers. The outer VLAN +* header is at the hard_header_len offset in non-variable +* length link layer headers. If it's a VLAN device, the +* min_header_len should be used to exclude the VLAN header +* size. +*/ +if (dev->min_header_len == dev->hard_header_len) + header_len = dev->hard_header_len; +else if (is_vlan_dev (dev)) + header_len = dev->min_header_len; +else +return 0 ; + +skb_push (skb, skb->data -skb_mac_header (skb)); + vh =skb_header_pointer (skb, header_len,sizeof (vhdr), &vhdr); +if (skb_orig_data != skb->data) { + skb->data = skb_orig_data; + skb->len = skb_orig_len; + } +if (unlikely (!vh)) +return 0 ; + +return ntohs (vh->h_vlan_TCI); +} + +static __be16 vlan_get_protocol_dgram (struct sk_buff *skb) +{ +__be16 proto = skb->protocol; + +if (unlikely (eth_type_vlan (proto))) { +u8 *skb_orig_data = skb->data; +int skb_orig_len = skb->len; + +skb_push (skb, skb->data -skb_mac_header (skb)); + proto =__vlan_get_protocol (skb, proto,NULL ); +if (skb_orig_data != skb->data) { + skb->data = skb_orig_data; + skb->len = skb_orig_len; + } + } + +return proto; +} +static void prb_del_retire_blk_timer (struct tpacket_kbdq_core *pkc) {del_timer_sync (&pkc->retire_blk_timer);
@@ -974,10 +1029,16 @@ static void prb_clear_rxhash(struct tpacstatic void prb_fill_vlan_info (struct tpacket_kbdq_core *pkc,struct tpacket3_hdr *ppd) { + struct packet_sock *po = container_of(pkc, struct packet_sock, rx_ring.prb_bdqc); +if (skb_vlan_tag_present (pkc->skb)) { ppd->hv1.tp_vlan_tci =skb_vlan_tag_get (pkc->skb); ppd->hv1.tp_vlan_tpid =ntohs (pkc->skb->vlan_proto); ppd->tp_status =TP_STATUS_VLAN_VALID |TP_STATUS_VLAN_TPID_VALID ; + }else if (unlikely (po->sk.sk_type ==SOCK_DGRAM &ð_type_vlan (pkc->skb->protocol))) { + ppd->hv1.tp_vlan_tci =vlan_get_tci (pkc->skb, pkc->skb->dev); + ppd->hv1.tp_vlan_tpid =ntohs (pkc->skb->protocol); + ppd->tp_status =TP_STATUS_VLAN_VALID |TP_STATUS_VLAN_TPID_VALID ; }else { ppd->hv1.tp_vlan_tci =0 ; ppd->hv1.tp_vlan_tpid =0 ;
@@ -2393,6 +2454,10 @@ static int tpacket_rcv(struct sk_buff *s h.h2->tp_vlan_tci =skb_vlan_tag_get (skb); h.h2->tp_vlan_tpid =ntohs (skb->vlan_proto); status |=TP_STATUS_VLAN_VALID |TP_STATUS_VLAN_TPID_VALID ; + }else if (unlikely (sk->sk_type ==SOCK_DGRAM &ð_type_vlan (skb->protocol))) { + h.h2->tp_vlan_tci =vlan_get_tci (skb, skb->dev); + h.h2->tp_vlan_tpid =ntohs (skb->protocol); + status |=TP_STATUS_VLAN_VALID |TP_STATUS_VLAN_TPID_VALID ; }else { h.h2->tp_vlan_tci =0 ; h.h2->tp_vlan_tpid =0 ;
@@ -2422,7 +2487,8 @@ static int tpacket_rcv(struct sk_buff *s sll->sll_halen =dev_parse_header (skb, sll->sll_addr); sll->sll_family =AF_PACKET ; sll->sll_hatype = dev->type; - sll->sll_protocol = skb->protocol; + sll->sll_protocol = (sk->sk_type ==SOCK_DGRAM ) ? +vlan_get_protocol_dgram (skb) : skb->protocol; sll->sll_pkttype = skb->pkt_type;if (unlikely (packet_sock_flag (po,PACKET_SOCK_ORIGDEV ))) sll->sll_ifindex = orig_dev->ifindex;
@@ -3447,7 +3513,8 @@ static int packet_recvmsg(struct socket/* Original length was stored in sockaddr_ll fields */ origlen =PACKET_SKB_CB (skb)->sa.origlen; sll->sll_family =AF_PACKET ; - sll->sll_protocol = skb->protocol; + sll->sll_protocol = (sock->type ==SOCK_DGRAM ) ? +vlan_get_protocol_dgram (skb) : skb->protocol; }sock_recv_ts_and_drops (msg, sk, skb);
@@ -3502,6 +3569,21 @@ static int packet_recvmsg(struct socket aux.tp_vlan_tci =skb_vlan_tag_get (skb); aux.tp_vlan_tpid =ntohs (skb->vlan_proto); aux.tp_status |=TP_STATUS_VLAN_VALID |TP_STATUS_VLAN_TPID_VALID ; + }else if (unlikely (sock->type ==SOCK_DGRAM &ð_type_vlan (skb->protocol))) { +struct sockaddr_ll *sll = &PACKET_SKB_CB (skb)->sa.ll; +struct net_device *dev; + +rcu_read_lock (); + dev =dev_get_by_index_rcu (sock_net (sk), sll->sll_ifindex); +if (dev) { + aux.tp_vlan_tci =vlan_get_tci (skb, dev); + aux.tp_vlan_tpid =ntohs (skb->protocol); + aux.tp_status |=TP_STATUS_VLAN_VALID |TP_STATUS_VLAN_TPID_VALID ; + }else { + aux.tp_vlan_tci =0 ; + aux.tp_vlan_tpid =0 ; + } +rcu_read_unlock (); }else { aux.tp_vlan_tci =0 ; aux.tp_vlan_tpid =0 ;
Greg Kroah-Hartman
maintainerPATCH 174/484 ipv6: take care of scope when choosing the src addr
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nicolas Dichtel <[email protected]>
commit abb9a68d2c64dd9b128ae1f2e635e4d805e7ce64 upstream.
When the source address is selected, the scope must be checked. For example, if a loopback address is assigned to the vrf device, it must not be chosen for packets sent outside.
--- net/ipv6/addrconf.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
net/ipv6/addrconf.c +2 -1
@@ -1831,7 +1831,8 @@ int ipv6_dev_get_saddr(struct net *net, master, &dst, scores, hiscore_idx); -if (scores[hiscore_idx].ifa) +if (scores[hiscore_idx].ifa && + scores[hiscore_idx].scopedist >=0 ) goto out; }
Greg Kroah-Hartman
maintainerPATCH 175/484 sched/fair: set_load_weight() must also call reweight_task() for SCHED_IDLE tasks
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tejun Heo <[email protected]>
commit d329605287020c3d1c3b0dadc63d8208e7251382 upstream.
When a task's weight is being changed, set_load_weight() is called with @update_load set. As weight changes aren't trivial for the fair class, set_load_weight() calls fair.c::reweight_task() for fair class tasks.
However, set_load_weight() first tests task_has_idle_policy() on entry and skips calling reweight_task() for SCHED_IDLE tasks. This is buggy as SCHED_IDLE tasks are just fair tasks with a very low weight and they would incorrectly skip load, vlag and position updates.
Fix it by updating reweight_task() to take struct load_weight as idle weight can't be expressed with prio and making set_load_weight() call reweight_task() for SCHED_IDLE tasks too when @update_load is set.
--- kernel/sched/core.c | 23 ++++++++++------------- kernel/sched/fair.c | 7 +++---- kernel/sched/sched.h | 2 +- 3 files changed, 14 insertions(+), 18 deletions(-)
kernel/sched/core.c +10 -13
@@ -1203,27 +1203,24 @@ int tg_nop(struct task_group *tg, void *static void set_load_weight (struct task_struct *p,bool update_load) {int prio = p->static_prio -MAX_RT_PRIO ; -struct load_weight *load = &p->se.load; +struct load_weight lw; -/* -* SCHED_IDLE tasks get minimal weight: -*/ if (task_has_idle_policy (p)) { - load->weight =scale_load (WEIGHT_IDLEPRIO ); - load->inv_weight =WMULT_IDLEPRIO ; -return ; + lw.weight =scale_load (WEIGHT_IDLEPRIO ); + lw.inv_weight =WMULT_IDLEPRIO ; + }else { + lw.weight =scale_load (sched_prio_to_weight[prio]); + lw.inv_weight = sched_prio_to_wmult[prio]; }/* * SCHED_OTHER tasks have to update their load when changing their * weight */ -if (update_load && p->sched_class == &fair_sched_class) { -reweight_task (p, prio); - }else { - load->weight =scale_load (sched_prio_to_weight[prio]); - load->inv_weight = sched_prio_to_wmult[prio]; - } +if (update_load && p->sched_class == &fair_sched_class) +reweight_task (p, &lw); +else + p->se.load = lw; }#ifdef CONFIG_UCLAMP_TASK
kernel/sched/fair.c +3 -4
@@ -3121,15 +3121,14 @@ static void reweight_entity(struct cfs_r } -void reweight_task (struct task_struct *p,int prio) +void reweight_task (struct task_struct *p,const struct load_weight *lw) {struct sched_entity *se = &p->se;struct cfs_rq *cfs_rq =cfs_rq_of (se);struct load_weight *load = &se->load; -unsigned long weight =scale_load (sched_prio_to_weight[prio]); -reweight_entity (cfs_rq, se, weight); - load->inv_weight = sched_prio_to_wmult[prio]; +reweight_entity (cfs_rq, se, lw->weight); + load->inv_weight = lw->inv_weight; }#ifdef CONFIG_FAIR_GROUP_SCHED
kernel/sched/sched.h +1 -1
@@ -2322,7 +2322,7 @@ extern void init_sched_dl_class(void);extern void init_sched_rt_class (void );extern void init_sched_fair_class (void ); -extern void reweight_task (struct task_struct *p,int prio); +extern void reweight_task (struct task_struct *p,const struct load_weight *lw);extern void resched_curr (struct rq *rq);extern void resched_cpu (int cpu);
Greg Kroah-Hartman
maintainerPATCH 176/484 fuse: verify {g,u}id mount options correctly
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Sandeen <[email protected]>
commit 525bd65aa759ec320af1dc06e114ed69733e9e23 upstream.
As was done in0200679fc795 ("tmpfs: verify {g,u}id mount options correctly") we need to validate that the requested uid and/or gid is representable in the filesystem's idmapping.
Cribbing from the above commit log,
The contract for {g,u}id mount options and {g,u}id values in general set from userspace has always been that they are translated according to the caller's idmapping. In so far, fuse has been doing the correct thing. But since fuse is mountable in unprivileged contexts it is also necessary to verify that the resulting {k,g}uid is representable in the namespace of the superblock.
--- fs/fuse/inode.c | 24 ++++++++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-)
fs/fuse/inode.c +20 -4
@@ -686,6 +686,8 @@ static int fuse_parse_param(struct fs_costruct fs_parse_result result;struct fuse_fs_context *ctx = fsc->fs_private;int opt; +kuid_t kuid; +kgid_t kgid;if (fsc->purpose ==FS_CONTEXT_FOR_RECONFIGURE ) {/*
@@ -730,16 +732,30 @@ static int fuse_parse_param(struct fs_cobreak ;case OPT_USER_ID : - ctx->user_id =make_kuid (fsc->user_ns, result.uint_32); -if (!uid_valid (ctx->user_id)) + kuid =make_kuid (fsc->user_ns, result.uint_32); +if (!uid_valid (kuid))return invalfc (fsc,"Invalid user_id" ); +/* +* The requested uid must be representable in the +* filesystem's idmapping. +*/ +if (!kuid_has_mapping (fsc->user_ns, kuid)) +return invalfc (fsc,"Invalid user_id" ); + ctx->user_id = kuid; ctx->user_id_present = true;break ;case OPT_GROUP_ID : - ctx->group_id =make_kgid (fsc->user_ns, result.uint_32); -if (!gid_valid (ctx->group_id)) + kgid =make_kgid (fsc->user_ns, result.uint_32);; +if (!gid_valid (kgid)) +return invalfc (fsc,"Invalid group_id" ); +/* +* The requested gid must be representable in the +* filesystem's idmapping. +*/ +if (!kgid_has_mapping (fsc->user_ns, kgid))return invalfc (fsc,"Invalid group_id" ); + ctx->group_id = kgid; ctx->group_id_present = true;break ;
Greg Kroah-Hartman
maintainerPATCH 177/484 char: tpm: Fix possible memory leak in tpm_bios_measurements_open()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Joe Hattori <[email protected]>
commit 5d8e2971e817bb64225fc0b6327a78752f58a9aa upstream.
In tpm_bios_measurements_open(), get_device() is called on the device embedded in struct tpm_chip. In the error path, however, put_device() is not called. This results in a reference count leak, which prevents the device from being properly released. This commit makes sure to call put_device() when the seq_open() call fails.
--- drivers/char/tpm/eventlog/common.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/char/tpm/eventlog/common.c +2 -0
@@ -47,6 +47,8 @@ static int tpm_bios_measurements_open(stif (!err) { seq = file->private_data; seq->private = chip; + }else { +put_device (&chip->dev); }return err;
Greg Kroah-Hartman
maintainerPATCH 178/484 media: venus: fix use after free in vdec_close
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dikshita Agarwal <[email protected]>
commit a0157b5aa34eb43ec4c5510f9c260bbb03be937e upstream.
There appears to be a possible use after free with vdec_close(). The firmware will add buffer release work to the work queue through HFI callbacks as a normal part of decoding. Randomly closing the decoder device from userspace during normal decoding can incur a read after free for inst.
Fix it by cancelling the work in vdec_close.
--- drivers/media/platform/qcom/venus/vdec.c | 1 + 1 file changed, 1 insertion(+)
drivers/media/platform/qcom/venus/vdec.c +1 -0
@@ -1632,6 +1632,7 @@ static int vdec_close(struct file *file)vdec_pm_get (inst); +cancel_work_sync (&inst->delayed_process_work);v4l2_m2m_ctx_release (inst->m2m_ctx);v4l2_m2m_release (inst->m2m_dev);vdec_ctrl_deinit (inst);
Greg Kroah-Hartman
maintainerPATCH 179/484 ata: libata-scsi: Honor the D_SENSE bit for CK_COND=1 and no error
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Igor Pylypiv <[email protected]>
commit 28ab9769117ca944cb6eb537af5599aa436287a4 upstream.
SAT-5 revision 8 specification removed the text about the ANSI INCITS 431-2007 compliance which was requiring SCSI/ATA Translation (SAT) to return descriptor format sense data for the ATA PASS-THROUGH commands regardless of the setting of the D_SENSE bit.
Let's honor the D_SENSE bit for ATA PASS-THROUGH commands while generating the "ATA PASS-THROUGH INFORMATION AVAILABLE" sense data.
SAT-5 revision 7
================
12.2.2.8 Fixed format sense data
Table 212 shows the fields returned in the fixed format sense data (see SPC-5) for ATA PASS-THROUGH commands. SATLs compliant with ANSI INCITS 431-2007, SCSI/ATA Translation (SAT) return descriptor format sense data for the ATA PASS-THROUGH commands regardless of the setting of the D_SENSE bit.
SAT-5 revision 8
================
12.2.2.8 Fixed format sense data
Table 211 shows the fields returned in the fixed format sense data (see SPC-5) for ATA PASS-THROUGH commands.
--- drivers/ata/libata-scsi.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-)
drivers/ata/libata-scsi.c +2 -5
@@ -872,11 +872,8 @@ static void ata_gen_passthru_sense(struc &sense_key, &asc, &ascq, verbose);ata_scsi_set_sense (qc->dev, cmd, sense_key, asc, ascq); }else { -/* -* ATA PASS-THROUGH INFORMATION AVAILABLE -* Always in descriptor format sense. -*/ -scsi_build_sense (cmd,1 ,RECOVERED_ERROR ,0 ,0x1D ); +/* ATA PASS-THROUGH INFORMATION AVAILABLE */ +ata_scsi_set_sense (qc->dev, cmd,RECOVERED_ERROR ,0 ,0x1D ); }if ((cmd->sense_buffer[0 ] &0x7f ) >=0x72 ) {
Re: [PATCH 5.15 179/484] ata: libata-scsi: Honor the D_SENSE bit for CK_COND=1 and no error
Quoted 56 lines · Greg Kroah-Hartman
5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Igor Pylypiv <[email protected]>
commit
28ab9769117ca944cb6eb537af5599aa436287a4upstream.SAT-5 revision 8 specification removed the text about the ANSI INCITS 431-2007 compliance which was requiring SCSI/ATA Translation (SAT) to return descriptor format sense data for the ATA PASS-THROUGH commands regardless of the setting of the
D_SENSEbit.Let's honor the
D_SENSEbit for ATA PASS-THROUGH commands while generating the "ATA PASS-THROUGH INFORMATION AVAILABLE" sense data.SAT-5 revision 7
================12.2.2.8 Fixed format sense data
Table 212 shows the fields returned in the fixed format sense data (see SPC-5) for ATA PASS-THROUGH commands. SATLs compliant with ANSI INCITS 431-2007, SCSI/ATA Translation (SAT) return descriptor format sense data for the ATA PASS-THROUGH commands regardless of the setting of the
D_SENSEbit.SAT-5 revision 8
================12.2.2.8 Fixed format sense data
Table 211 shows the fields returned in the fixed format sense data (see SPC-5) for ATA PASS-THROUGH commands.
Cc [email protected] # 4.19+Reported-by Niklas Cassel <[email protected]>Reviewed-by Niklas Cassel <[email protected]>Signed-off-by Igor Pylypiv <[email protected]>Reviewed-by Hannes Reinecke <[email protected]>Signed-off-by Niklas Cassel <[email protected]>Signed-off-by Greg Kroah-Hartman <[email protected]>--- drivers/ata/libata-scsi.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-)drivers/ata/libata-scsi.c +0
-0@@ -872,11 +872,8 @@ static void ata_gen_passthru_sense(struc &sense_key, &asc, &ascq, verbose);ata_scsi_set_sense (qc->dev, cmd, sense_key, asc, ascq); }else {
drivers/ata/libata-scsi.c static void ata_gen_passthru_sense(struc · line 879
Quoted 10 lines
drivers/ata/libata-scsi.c +2
-5-/* -* ATA PASS-THROUGH INFORMATION AVAILABLE -* Always in descriptor format sense. -*/ -scsi_build_sense (cmd,1 ,RECOVERED_ERROR ,0 ,0x1D ); +/* ATA PASS-THROUGH INFORMATION AVAILABLE */ +ata_scsi_set_sense (qc->dev, cmd,RECOVERED_ERROR ,0 ,0x1D ); }if ((cmd->sense_buffer[0 ] &0x7f ) >=0x72 ) {
Hello Greg,
This commit unfortunately breaks hdparm, hddtemp and udisks, and I have just sent a PR to Linus that reverts this commit, see:
https://lore.kernel.org/linux-ide/[email protected]/T/#u
and
https://git.kernel.org/pub/scm/linux/kernel/git/libata/linux.git/commit/?h=ata-6.11-rc4
So it might be a good idea to not include this patch in v5.15.x in the first place, so that we avoid having a v5.15.x release that will be broken until the revert gets backported (in v5.15.x+1).
Kind regards,
Niklas
Greg Kroah-Hartman
maintainerRe: [PATCH 5.15 179/484] ata: libata-scsi: Honor the D_SENSE bit for CK_COND=1 and no error
Quoted 76 lines · Niklas Cassel
Quoted 56 lines · Greg Kroah-Hartman
5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Igor Pylypiv <[email protected]>
commit
28ab9769117ca944cb6eb537af5599aa436287a4upstream.SAT-5 revision 8 specification removed the text about the ANSI INCITS 431-2007 compliance which was requiring SCSI/ATA Translation (SAT) to return descriptor format sense data for the ATA PASS-THROUGH commands regardless of the setting of the
D_SENSEbit.Let's honor the
D_SENSEbit for ATA PASS-THROUGH commands while generating the "ATA PASS-THROUGH INFORMATION AVAILABLE" sense data.SAT-5 revision 7
================12.2.2.8 Fixed format sense data
Table 212 shows the fields returned in the fixed format sense data (see SPC-5) for ATA PASS-THROUGH commands. SATLs compliant with ANSI INCITS 431-2007, SCSI/ATA Translation (SAT) return descriptor format sense data for the ATA PASS-THROUGH commands regardless of the setting of the
D_SENSEbit.SAT-5 revision 8
================12.2.2.8 Fixed format sense data
Table 211 shows the fields returned in the fixed format sense data (see SPC-5) for ATA PASS-THROUGH commands.
Cc [email protected] # 4.19+Reported-by Niklas Cassel <[email protected]>Reviewed-by Niklas Cassel <[email protected]>Signed-off-by Igor Pylypiv <[email protected]>Reviewed-by Hannes Reinecke <[email protected]>Signed-off-by Niklas Cassel <[email protected]>Signed-off-by Greg Kroah-Hartman <[email protected]>--- drivers/ata/libata-scsi.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-)drivers/ata/libata-scsi.c +0
-0@@ -872,11 +872,8 @@ static void ata_gen_passthru_sense(struc &sense_key, &asc, &ascq, verbose);ata_scsi_set_sense (qc->dev, cmd, sense_key, asc, ascq); }else {drivers/ata/libata-scsi.c static void ata_gen_passthru_sense(struc · line 879
Quoted 10 lines
drivers/ata/libata-scsi.c +2
-5-/* -* ATA PASS-THROUGH INFORMATION AVAILABLE -* Always in descriptor format sense. -*/ -scsi_build_sense (cmd,1 ,RECOVERED_ERROR ,0 ,0x1D ); +/* ATA PASS-THROUGH INFORMATION AVAILABLE */ +ata_scsi_set_sense (qc->dev, cmd,RECOVERED_ERROR ,0 ,0x1D ); }if ((cmd->sense_buffer[0 ] &0x7f ) >=0x72 ) {Hello Greg,
This commit unfortunately breaks hdparm, hddtemp and udisks, and I have just sent a PR to Linus that reverts this commit, see:
https://lore.kernel.org/linux-ide/[email protected]/T/#u
and
https://git.kernel.org/pub/scm/linux/kernel/git/libata/linux.git/commit/?h=ata-6.11-rc4
Quoted 3 lines
So it might be a good idea to not include this patch in v5.15.x in the first place, so that we avoid having a v5.15.x release that will be broken until the revert gets backported (in v5.15.x+1).
I've taken the revert now, thanks!
greg k-h
Greg Kroah-Hartman
maintainerPATCH 180/484 hfs: fix to initialize fields of hfs_inode_info after hfs_alloc_inode()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Chao Yu <[email protected]>
commit 26a2ed107929a855155429b11e1293b83e6b2a8b upstream.
Syzbot reports uninitialized value access issue as below:
loop0: detected capacity change from 0 to 64
=====================================================
BUG: KMSAN: uninit-value in hfs_revalidate_dentry+0x307/0x3f0 fs/hfs/sysdep.c:30 hfs_revalidate_dentry+0x307/0x3f0 fs/hfs/sysdep.c:30 d_revalidate fs/namei.c:862 [inline] lookup_fast+0x89e/0x8e0 fs/namei.c:1649 walk_component fs/namei.c:2001 [inline] link_path_walk+0x817/0x1480 fs/namei.c:2332 path_lookupat+0xd9/0x6f0 fs/namei.c:2485 filename_lookup+0x22e/0x740 fs/namei.c:2515 user_path_at_empty+0x8b/0x390 fs/namei.c:2924 user_path_at include/linux/namei.h:57 [inline] do_mount fs/namespace.c:3689 [inline] __do_sys_mount fs/namespace.c:3898 [inline] __se_sys_mount+0x66b/0x810 fs/namespace.c:3875 __x64_sys_mount+0xe4/0x140 fs/namespace.c:3875 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0xcf/0x1e0 arch/x86/entry/common.c:83 entry_SYSCALL_64_after_hwframe+0x63/0x6b BUG: KMSAN: uninit-value in hfs_ext_read_extent fs/hfs/extent.c:196 [inline] BUG: KMSAN: uninit-value in hfs_get_block+0x92d/0x1620 fs/hfs/extent.c:366 hfs_ext_read_extent fs/hfs/extent.c:196 [inline] hfs_get_block+0x92d/0x1620 fs/hfs/extent.c:366 block_read_full_folio+0x4ff/0x11b0 fs/buffer.c:2271 hfs_read_folio+0x55/0x60 fs/hfs/inode.c:39 filemap_read_folio+0x148/0x4f0 mm/filemap.c:2426 do_read_cache_folio+0x7c8/0xd90 mm/filemap.c:3553 do_read_cache_page mm/filemap.c:3595 [inline] read_cache_page+0xfb/0x2f0 mm/filemap.c:3604 read_mapping_page include/linux/pagemap.h:755 [inline] hfs_btree_open+0x928/0x1ae0 fs/hfs/btree.c:78 hfs_mdb_get+0x260c/0x3000 fs/hfs/mdb.c:204 hfs_fill_super+0x1fb1/0x2790 fs/hfs/super.c:406 mount_bdev+0x628/0x920 fs/super.c:1359 hfs_mount+0xcd/0xe0 fs/hfs/super.c:456 legacy_get_tree+0x167/0x2e0 fs/fs_context.c:610 vfs_get_tree+0xdc/0x5d0 fs/super.c:1489 do_new_mount+0x7a9/0x16f0 fs/namespace.c:3145 path_mount+0xf98/0x26a0 fs/namespace.c:3475 do_mount fs/namespace.c:3488 [inline] __do_sys_mount fs/namespace.c:3697 [inline] __se_sys_mount+0x919/0x9e0 fs/namespace.c:3674 __ia32_sys_mount+0x15b/0x1b0 fs/namespace.c:3674 do_syscall_32_irqs_on arch/x86/entry/common.c:112 [inline] __do_fast_syscall_32+0xa2/0x100 arch/x86/entry/common.c:178 do_fast_syscall_32+0x37/0x80 arch/x86/entry/common.c:203 do_SYSENTER_32+0x1f/0x30 arch/x86/entry/common.c:246 entry_SYSENTER_compat_after_hwframe+0x70/0x82
Uninit was created at:
__alloc_pages+0x9a6/0xe00 mm/page_alloc.c:4590 __alloc_pages_node include/linux/gfp.h:238 [inline] alloc_pages_node include/linux/gfp.h:261 [inline] alloc_slab_page mm/slub.c:2190 [inline] allocate_slab mm/slub.c:2354 [inline] new_slab+0x2d7/0x1400 mm/slub.c:2407 ___slab_alloc+0x16b5/0x3970 mm/slub.c:3540 __slab_alloc mm/slub.c:3625 [inline] __slab_alloc_node mm/slub.c:3678 [inline] slab_alloc_node mm/slub.c:3850 [inline] kmem_cache_alloc_lru+0x64d/0xb30 mm/slub.c:3879 alloc_inode_sb include/linux/fs.h:3018 [inline] hfs_alloc_inode+0x5a/0xc0 fs/hfs/super.c:165 alloc_inode+0x83/0x440 fs/inode.c:260 new_inode_pseudo fs/inode.c:1005 [inline] new_inode+0x38/0x4f0 fs/inode.c:1031 hfs_new_inode+0x61/0x1010 fs/hfs/inode.c:186 hfs_mkdir+0x54/0x250 fs/hfs/dir.c:228 vfs_mkdir+0x49a/0x700 fs/namei.c:4126 do_mkdirat+0x529/0x810 fs/namei.c:4149 __do_sys_mkdirat fs/namei.c:4164 [inline] __se_sys_mkdirat fs/namei.c:4162 [inline] __x64_sys_mkdirat+0xc8/0x120 fs/namei.c:4162 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0xcf/0x1e0 arch/x86/entry/common.c:83 entry_SYSCALL_64_after_hwframe+0x63/0x6b
It missed to initialize .tz_secondswest, .cached_start and .cached_blocks fields in struct hfs_inode_info after hfs_alloc_inode(), fix it.
--- fs/hfs/inode.c | 3 +++ 1 file changed, 3 insertions(+)
fs/hfs/inode.c +3 -0
@@ -202,6 +202,7 @@ struct inode *hfs_new_inode(struct inodeHFS_I (inode)->flags =0 ;HFS_I (inode)->rsrc_inode =NULL ;HFS_I (inode)->fs_blocks =0 ; +HFS_I (inode)->tz_secondswest = sys_tz.tz_minuteswest *60 ;if (S_ISDIR (mode)) { inode->i_size =2 ;HFS_SB (sb)->folder_count++;
@@ -277,6 +278,8 @@ void hfs_inode_read_fork(struct inode *ifor (count =0 , i =0 ; i <3 ; i++) count +=be16_to_cpu (ext[i].count);HFS_I (inode)->first_blocks = count; +HFS_I (inode)->cached_start =0 ; +HFS_I (inode)->cached_blocks =0 ; inode->i_size =HFS_I (inode)->phys_size = log_size;HFS_I (inode)->fs_blocks = (log_size + sb->s_blocksize -1 ) >> sb->s_blocksize_bits;
Greg Kroah-Hartman
maintainerPATCH 181/484 ext2: Verify bitmap and itable block numbers before using them
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jan Kara <[email protected]>
commit 322a6aff03937aa1ece33b4e46c298eafaf9ac41 upstream.
Verify bitmap block numbers and inode table blocks are sane before using them for checking bits in the block bitmap.
--- fs/ext2/balloc.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-)
fs/ext2/balloc.c +9 -2
@@ -79,26 +79,33 @@ static int ext2_valid_block_bitmap(strucext2_grpblk_t next_zero_bit;ext2_fsblk_t bitmap_blk;ext2_fsblk_t group_first_block; +ext2_grpblk_t max_bit; group_first_block =ext2_group_first_block_no (sb, block_group); + max_bit =ext2_group_last_block_no (sb, block_group) - group_first_block;/* check whether block bitmap block number is set */ bitmap_blk =le32_to_cpu (desc->bg_block_bitmap); offset = bitmap_blk - group_first_block; -if (!ext2_test_bit (offset, bh->b_data)) +if (offset <0 || offset > max_bit || + !ext2_test_bit (offset, bh->b_data))/* bad block bitmap */ goto err_out;/* check whether the inode bitmap block number is set */ bitmap_blk =le32_to_cpu (desc->bg_inode_bitmap); offset = bitmap_blk - group_first_block; -if (!ext2_test_bit (offset, bh->b_data)) +if (offset <0 || offset > max_bit || + !ext2_test_bit (offset, bh->b_data))/* bad block bitmap */ goto err_out;/* check whether the inode table block number is set */ bitmap_blk =le32_to_cpu (desc->bg_inode_table); offset = bitmap_blk - group_first_block; +if (offset <0 || offset > max_bit || + offset +EXT2_SB (sb)->s_itb_per_group -1 > max_bit) + goto err_out; next_zero_bit =ext2_find_next_zero_bit (bh->b_data, offset +EXT2_SB (sb)->s_itb_per_group, offset);
Greg Kroah-Hartman
maintainerPATCH 182/484 drm/gma500: fix null pointer dereference in cdv_intel_lvds_get_modes
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ma Ke <[email protected]>
commit cb520c3f366c77e8d69e4e2e2781a8ce48d98e79 upstream.
In cdv_intel_lvds_get_modes(), the return value of drm_mode_duplicate() is assigned to mode, which will lead to a NULL pointer dereference on failure of drm_mode_duplicate(). Add a check to avoid npd.
--- drivers/gpu/drm/gma500/cdv_intel_lvds.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/gpu/drm/gma500/cdv_intel_lvds.c +3 -0
@@ -310,6 +310,9 @@ static int cdv_intel_lvds_get_modes(struif (mode_dev->panel_fixed_mode !=NULL ) {struct drm_display_mode *mode =drm_mode_duplicate (dev, mode_dev->panel_fixed_mode); +if (!mode) +return 0 ; +drm_mode_probed_add (connector, mode);return 1 ; }
Greg Kroah-Hartman
maintainerPATCH 183/484 drm/gma500: fix null pointer dereference in psb_intel_lvds_get_modes
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ma Ke <[email protected]>
commit 2df7aac81070987b0f052985856aa325a38debf6 upstream.
In psb_intel_lvds_get_modes(), the return value of drm_mode_duplicate() is assigned to mode, which will lead to a possible NULL pointer dereference on failure of drm_mode_duplicate(). Add a check to avoid npd.
--- drivers/gpu/drm/gma500/psb_intel_lvds.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/gpu/drm/gma500/psb_intel_lvds.c +3 -0
@@ -508,6 +508,9 @@ static int psb_intel_lvds_get_modes(struif (mode_dev->panel_fixed_mode !=NULL ) {struct drm_display_mode *mode =drm_mode_duplicate (dev, mode_dev->panel_fixed_mode); +if (!mode) +return 0 ; +drm_mode_probed_add (connector, mode);return 1 ; }
Greg Kroah-Hartman
maintainerPATCH 184/484 scsi: qla2xxx: Fix optrom version displayed in FDMI
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Shreyas Deodhar <[email protected]>
commit 348744f27a35e087acc9378bf53537fbfb072775 upstream.
Bios version was popluated for FDMI response. Systems with EFI would show optrom version as 0. EFI version is populated here and BIOS version is already displayed under FDMI_HBA_BOOT_BIOS_NAME.
--- drivers/scsi/qla2xxx/qla_gs.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/qla2xxx/qla_gs.c +1 -1
@@ -1709,7 +1709,7 @@ qla2x00_hba_attributes(scsi_qla_host_t * eiter->type =cpu_to_be16 (FDMI_HBA_OPTION_ROM_VERSION ); alen =scnprintf ( eiter->a.orom_version,sizeof (eiter->a.orom_version), -"%d.%02d" , ha->bios_revision[1 ], ha->bios_revision[0 ]); +"%d.%02d" , ha->efi_revision[1 ], ha->efi_revision[0 ]); alen +=FDMI_ATTR_ALIGNMENT (alen); alen +=FDMI_ATTR_TYPELEN (eiter); eiter->len =cpu_to_be16 (alen);
Greg Kroah-Hartman
maintainerPATCH 185/484 drm/amd/display: Check for NULL pointer
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sung Joon Kim <[email protected]>
commit 4ab68e168ae1695f7c04fae98930740aaf7c50fa upstream.
[why & how]
Need to make sure plane_state is initialized
before accessing its members.
--- drivers/gpu/drm/amd/display/dc/core/dc_surface.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/gpu/drm/amd/display/dc/core/dc_surface.c +2 -1
@@ -154,7 +154,8 @@ const struct dc_plane_status *dc_plane_gif (pipe_ctx->plane_state != plane_state)continue ; - pipe_ctx->plane_state->status.is_flip_pending = false; +if (pipe_ctx->plane_state) + pipe_ctx->plane_state->status.is_flip_pending = false;break ; }
Greg Kroah-Hartman
maintainerPATCH 186/484 sched/fair: Use all little CPUs for CPU-bound workloads
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pierre Gondois <[email protected]>
commit 3af7524b14198f5159a86692d57a9f28ec9375ce upstream.
Running N CPU-bound tasks on an N CPUs platform:
- with asymmetric CPU capacity
- not being a DynamIq system (i.e. having a PKG level sched domain without the SD_SHARE_PKG_RESOURCES flag set)
.. might result in a task placement where two tasks run on a big CPU and none on a little CPU. This placement could be more optimal by using all CPUs.
Testing platform:
Juno-r2:
- 2 big CPUs (1-2), maximum capacity of 1024
- 4 little CPUs (0,3-5), maximum capacity of 383
Testing workload ([1]):
Spawn 6 CPU-bound tasks. During the first 100ms (step 1), each tasks is affine to a CPU, except for:
- one little CPU which is left idle.
- one big CPU which has 2 tasks affine.
After the 100ms (step 2), remove the cpumask affinity.
Behavior before the patch:
During step 2, the load balancer running from the idle CPU tags sched domains as:
- little CPUs: 'group_has_spare'. Cf. group_has_capacity() and group_is_overloaded(), 3 CPU-bound tasks run on a 4 CPUs sched-domain, and the idle CPU provides enough spare capacity regarding the imbalance_pct
- big CPUs: 'group_overloaded'. Indeed, 3 tasks run on a 2 CPUs sched-domain, so the following path is used:
group_is_overloaded()
\-if (sgs->sum_nr_running <= sgs->group_weight) return true;
The following path which would change the migration type to 'migrate_task' is not taken:
calculate_imbalance()
\-if (env->idle != CPU_NOT_IDLE && env->imbalance == 0)
as the local group has some spare capacity, so the imbalance is not 0.
The migration type requested is 'migrate_util' and the busiest runqueue is the big CPU's runqueue having 2 tasks (each having a utilization of 512). The idle little CPU cannot pull one of these task as its capacity is too small for the task. The following path is used:
detach_tasks()
\-case migrate_util:
\-if (util > env->imbalance) goto next;After the patch:
As the number of failed balancing attempts grows (with 'nr_balance_failed'), progressively make it easier to migrate a big task to the idling little CPU. A similar mechanism is used for the 'migrate_load' migration type.
Improvement:
Running the testing workload [1] with the step 2 representing a ~10s load for a big CPU:
Before patch: ~19.3s
After patch: ~18s (-6.7%)
Similar issue reported at:
https://lore.kernel.org/lkml/[email protected]/
--- kernel/sched/fair.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
kernel/sched/fair.c +1 -1
@@ -8241,7 +8241,7 @@ static int detach_tasks(struct lb_env *ecase migrate_util: util =task_util_est (p); -if (util > env->imbalance) +if (shr_bound (util, env->sd->nr_balance_failed) > env->imbalance) goto next; env->imbalance -= util;
Greg Kroah-Hartman
maintainerPATCH 187/484 apparmor: use kvfree_sensitive to free data->data
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Fedor Pchelkin <[email protected]>
commit 2bc73505a5cd2a18a7a542022722f136c19e3b87 upstream.
Inside unpack_profile() data->data is allocated using kvmemdup() so it should be freed with the corresponding kvfree_sensitive().
Also add missing data->data release for rhashtable insertion failure path in unpack_profile().
Found by Linux Verification Center (linuxtesting.org).
--- security/apparmor/policy.c | 2 +- security/apparmor/policy_unpack.c | 1 + 2 files changed, 2 insertions(+), 1 deletion(-)
security/apparmor/policy.c +1 -1
@@ -187,7 +187,7 @@ static void aa_free_data(void *ptr, void {struct aa_data *data = ptr; -kfree_sensitive (data->data); +kvfree_sensitive (data->data, data->size);kfree_sensitive (data->key);kfree_sensitive (data); }
security/apparmor/policy_unpack.c +1 -0
@@ -915,6 +915,7 @@ static struct aa_profile *unpack_profileif (rhashtable_insert_fast (profile->data, &data->head, profile->data->p)) { +kvfree_sensitive (data->data, data->size);kfree_sensitive (data->key);kfree_sensitive (data); info ="failed to insert data to table" ;
Greg Kroah-Hartman
maintainerPATCH 188/484 task_work: s/task_work_cancel()/task_work_cancel_func()/
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Frederic Weisbecker <[email protected]>
commit 68cbd415dd4b9c5b9df69f0f091879e56bf5907a upstream.
A proper task_work_cancel() API that actually cancels a callback and not *any* callback pointing to a given function is going to be needed for perf events event freeing. Do the appropriate rename to prepare for that.
--- include/linux/task_work.h | 2 +- kernel/irq/manage.c | 2 +- kernel/task_work.c | 10 +++++----- security/keys/keyctl.c | 2 +- 4 files changed, 8 insertions(+), 8 deletions(-)
include/linux/task_work.h +1 -1
@@ -24,7 +24,7 @@ int task_work_add(struct task_struct *tastruct callback_head *task_work_cancel_match (struct task_struct *task,bool (*match)(struct callback_head *,void *data),void *data); -struct callback_head *task_work_cancel (struct task_struct *,task_work_func_t ); +struct callback_head *task_work_cancel_func (struct task_struct *,task_work_func_t );void task_work_run (void );static inline void exit_task_work (struct task_struct *task)
kernel/irq/manage.c +1 -1
@@ -1330,7 +1330,7 @@ static int irq_thread(void *data)* synchronize_hardirq(). So neither IRQTF_RUNTHREAD nor the * oneshot mask bit can be set. */ -task_work_cancel (current, irq_thread_dtor); +task_work_cancel_func (current, irq_thread_dtor);return 0 ; }
kernel/task_work.c +5 -5
@@ -104,9 +104,9 @@ static bool task_work_func_match(struct }/** -* task_work_cancel - cancel a pending work added by task_work_add() -* @task: the task which should execute the work -* @func: identifies the work to remove +* task_work_cancel_func - cancel a pending work matching a function added by task_work_add() +* @task: the task which should execute the func's work +* @func: identifies the func to match with a work to remove * * Find the last queued pending work with ->func == @func and remove * it from queue.
@@ -115,7 +115,7 @@ static bool task_work_func_match(struct* The found work or NULL if not found. */ struct callback_head * -task_work_cancel (struct task_struct *task,task_work_func_t func) +task_work_cancel_func (struct task_struct *task,task_work_func_t func) {return task_work_cancel_match (task, task_work_func_match, func); }
@@ -152,7 +152,7 @@ void task_work_run(void)if (!work)break ;/* -* Synchronize with task_work_cancel(). It can not remove +* Synchronize with task_work_cancel_match(). It can not remove * the first entry == work, cmpxchg(task_works) must fail. * But it can remove another entry from the ->next list. */
security/keys/keyctl.c +1 -1
@@ -1694,7 +1694,7 @@ long keyctl_session_to_parent(void) goto unlock;/* cancel an already pending keyring replacement */ - oldwork =task_work_cancel (parent, key_change_session_keyring); + oldwork =task_work_cancel_func (parent, key_change_session_keyring);/* the replacement session keyring is applied just prior to userspace * restarting */
Greg Kroah-Hartman
maintainerPATCH 189/484 task_work: Introduce task_work_cancel() again
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Frederic Weisbecker <[email protected]>
commit f409530e4db9dd11b88cb7703c97c8f326ff6566 upstream.
Re-introduce task_work_cancel(), this time to cancel an actual callback and not *any* callback pointing to a given function. This is going to be needed for perf events event freeing.
--- include/linux/task_work.h | 1 + kernel/task_work.c | 24 ++++++++++++++++++++++++ 2 files changed, 25 insertions(+)
include/linux/task_work.h +1 -0
@@ -25,6 +25,7 @@ int task_work_add(struct task_struct *tastruct callback_head *task_work_cancel_match (struct task_struct *task,bool (*match)(struct callback_head *,void *data),void *data);struct callback_head *task_work_cancel_func (struct task_struct *,task_work_func_t ); +bool task_work_cancel (struct task_struct *task,struct callback_head *cb);void task_work_run (void );static inline void exit_task_work (struct task_struct *task)
kernel/task_work.c +24 -0
@@ -120,6 +120,30 @@ task_work_cancel_func(struct task_structreturn task_work_cancel_match (task, task_work_func_match, func); } +static bool task_work_match (struct callback_head *cb,void *data) +{ +return cb == data; +} + +/** +* task_work_cancel - cancel a pending work added by task_work_add() +* @task: the task which should execute the work +* @cb: the callback to remove if queued +* +* Remove a callback from a task's queue if queued. +* +* RETURNS: +* True if the callback was queued and got cancelled, false otherwise. +*/ +bool task_work_cancel (struct task_struct *task,struct callback_head *cb) +{ +struct callback_head *ret; + + ret =task_work_cancel_match (task, task_work_match, cb); + +return ret == cb; +} +/** * task_work_run - execute the works added by task_work_add() *
Greg Kroah-Hartman
maintainerPATCH 190/484 udf: Avoid using corrupted block bitmap buffer
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jan Kara <[email protected]>
commit a90d4471146de21745980cba51ce88e7926bcc4f upstream.
When the filesystem block bitmap is corrupted, we detect the corruption while loading the bitmap and fail the allocation with error. However the next allocation from the same bitmap will notice the bitmap buffer is already loaded and tries to allocate from the bitmap with mixed results (depending on the exact nature of the bitmap corruption). Fix the problem by using BH_verified bit to indicate whether the bitmap is valid or not.
--- fs/udf/balloc.c | 15 +++++++++++++-- fs/udf/super.c | 3 ++- 2 files changed, 15 insertions(+), 3 deletions(-)
fs/udf/balloc.c +13 -2
@@ -68,8 +68,12 @@ static int read_block_bitmap(struct supe }for (i =0 ; i < count; i++) -if (udf_test_bit (i + off, bh->b_data)) +if (udf_test_bit (i + off, bh->b_data)) { + bitmap->s_block_bitmap[bitmap_nr] = +ERR_PTR (-EFSCORRUPTED ); +brelse (bh);return -EFSCORRUPTED ; + }return 0 ; }
@@ -85,8 +89,15 @@ static int __load_block_bitmap(struct su block_group, nr_groups); } -if (bitmap->s_block_bitmap[block_group]) +if (bitmap->s_block_bitmap[block_group]) { +/* +* The bitmap failed verification in the past. No point in +* trying again. +*/ +if (IS_ERR (bitmap->s_block_bitmap[block_group])) +return PTR_ERR (bitmap->s_block_bitmap[block_group]);return block_group; + } retval =read_block_bitmap (sb, bitmap, block_group, block_group);if (retval <0 )
fs/udf/super.c +2 -1
@@ -266,7 +266,8 @@ static void udf_sb_free_bitmap(struct udint nr_groups = bitmap->s_nr_groups;for (i =0 ; i < nr_groups; i++) -brelse (bitmap->s_block_bitmap[i]); +if (!IS_ERR_OR_NULL (bitmap->s_block_bitmap[i])) +brelse (bitmap->s_block_bitmap[i]);kvfree (bitmap); }
Greg Kroah-Hartman
maintainerPATCH 191/484 m68k: amiga: Turn off Warp1260 interrupts during boot
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Paolo Pisati <[email protected]>
commit 1d8491d3e726984343dd8c3cdbe2f2b47cfdd928 upstream.
On an Amiga 1200 equipped with a Warp1260 accelerator, an interrupt storm coming from the accelerator board causes the machine to crash in local_irq_enable() or auto_irq_enable(). Disabling interrupts for the Warp1260 in amiga_parse_bootinfo() fixes the problem.
--- arch/m68k/amiga/config.c | 9 +++++++++ include/uapi/linux/zorro_ids.h | 3 +++ 2 files changed, 12 insertions(+)
arch/m68k/amiga/config.c +9 -0
@@ -179,6 +179,15 @@ int __init amiga_parse_bootinfo(const st dev->slotsize =be16_to_cpu (cd->cd_SlotSize); dev->boardaddr =be32_to_cpu (cd->cd_BoardAddr); dev->boardsize =be32_to_cpu (cd->cd_BoardSize); + +/* CS-LAB Warp 1260 workaround */ +if (be16_to_cpu (dev->rom.er_Manufacturer) ==ZORRO_MANUF (ZORRO_PROD_CSLAB_WARP_1260 ) && + dev->rom.er_Product ==ZORRO_PROD (ZORRO_PROD_CSLAB_WARP_1260 )) { + +/* turn off all interrupts */ +pr_info ("Warp 1260 card detected: applying interrupt storm workaround\n" ); + *(uint32_t *)(dev->boardaddr +0x1000 ) =0xfff ; + } }else pr_warn ("amiga_parse_bootinfo: too many AutoConfig devices\n" );#endif /* CONFIG_ZORRO */
include/uapi/linux/zorro_ids.h +3 -0
@@ -449,6 +449,9 @@#define ZORRO_PROD_VMC_ISDN_BLASTER_Z2 ZORRO_ID(VMC, 0x01, 0)#define ZORRO_PROD_VMC_HYPERCOM_4 ZORRO_ID(VMC, 0x02, 0) +#define ZORRO_MANUF_CSLAB 0x1400 +#define ZORRO_PROD_CSLAB_WARP_1260 ZORRO_ID(CSLAB, 0x65, 0) +#define ZORRO_MANUF_INFORMATION 0x157C#define ZORRO_PROD_INFORMATION_ISDN_ENGINE_I ZORRO_ID(INFORMATION, 0x64, 0)
Greg Kroah-Hartman
maintainerPATCH 192/484 ext4: check dot and dotdot of dx_root before making dir indexed
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Baokun Li <[email protected]>
commit 50ea741def587a64e08879ce6c6a30131f7111e7 upstream.
Syzbot reports a issue as follows:
============================================
BUG: unable to handle page fault for address: ffffed11022e24fe PGD 23ffee067 P4D 23ffee067 PUD 0 Oops: Oops: 0000 [#1] PREEMPT SMP KASAN PTI CPU: 0 PID: 5079 Comm: syz-executor306 Not tainted 6.10.0-rc5-g55027e689933 #0 Call Trace: <TASK> make_indexed_dir+0xdaf/0x13c0 fs/ext4/namei.c:2341 ext4_add_entry+0x222a/0x25d0 fs/ext4/namei.c:2451 ext4_rename fs/ext4/namei.c:3936 [inline] ext4_rename2+0x26e5/0x4370 fs/ext4/namei.c:4214
[...]
============================================
The immediate cause of this problem is that there is only one valid dentry for the block to be split during do_split, so split==0 results in out of bounds accesses to the map triggering the issue.
do_split
unsigned split
dx_make_map
count = 1
split = count/2 = 0;
continued = hash2 == map[split - 1].hash;
---> map[4294967295]The maximum length of a filename is 255 and the minimum block size is 1024, so it is always guaranteed that the number of entries is greater than or equal to 2 when do_split() is called.
But syzbot's crafted image has no dot and dotdot in dir, and the dentry distribution in dirblock is as follows:
bus dentry1 hole dentry2 free
|xx--|xx-------------|...............|xx-------------|...............| 0 12 (8+248)=256 268 256 524 (8+256)=264 788 236 1024
So when renaming dentry1 increases its name_len length by 1, neither hole nor free is sufficient to hold the new dentry, and make_indexed_dir() is called.
In make_indexed_dir() it is assumed that the first two entries of the dirblock must be dot and dotdot, so bus and dentry1 are left in dx_root because they are treated as dot and dotdot, and only dentry2 is moved to the new leaf block. That's why count is equal to 1.
Therefore add the ext4_check_dx_root() helper function to add more sanity checks to dot and dotdot before starting the conversion to avoid the above issue.
--- fs/ext4/namei.c | 56 +++++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 51 insertions(+), 5 deletions(-)
fs/ext4/namei.c +51 -5
@@ -2218,6 +2218,52 @@ static int add_dirent_to_buf(handle_t *hreturn err ? err : err2; } +static bool ext4_check_dx_root (struct inode *dir,struct dx_root *root) +{ +struct fake_dirent *fde; +const char *error_msg; +unsigned int rlen; +unsigned int blocksize = dir->i_sb->s_blocksize; +char *blockend = (char *)root + dir->i_sb->s_blocksize; + + fde = &root->dot; +if (unlikely (fde->name_len !=1 )) { + error_msg ="invalid name_len for '.'" ; + goto corrupted; + } +if (unlikely (strncmp (root->dot_name,"." , fde->name_len))) { + error_msg ="invalid name for '.'" ; + goto corrupted; + } + rlen =ext4_rec_len_from_disk (fde->rec_len, blocksize); +if (unlikely ((char *)fde + rlen >= blockend)) { + error_msg ="invalid rec_len for '.'" ; + goto corrupted; + } + + fde = &root->dotdot; +if (unlikely (fde->name_len !=2 )) { + error_msg ="invalid name_len for '..'" ; + goto corrupted; + } +if (unlikely (strncmp (root->dotdot_name,".." , fde->name_len))) { + error_msg ="invalid name for '..'" ; + goto corrupted; + } + rlen =ext4_rec_len_from_disk (fde->rec_len, blocksize); +if (unlikely ((char *)fde + rlen >= blockend)) { + error_msg ="invalid rec_len for '..'" ; + goto corrupted; + } + +return true; + +corrupted: +EXT4_ERROR_INODE (dir,"Corrupt dir, %s, running e2fsck is recommended" , + error_msg); +return false; +} +/* * This converts a one block unindexed directory to a 3 block indexed * directory, and adds the dentry to the indexed directory.
@@ -2252,17 +2298,17 @@ static int make_indexed_dir(handle_t *habrelse (bh);return retval; } + root = (struct dx_root *) bh->b_data; +if (!ext4_check_dx_root (dir, root)) { +brelse (bh); +return -EFSCORRUPTED ; + }/* The 0th block becomes the root, move the dirents out */ fde = &root->dotdot; de = (struct ext4_dir_entry_2 *)((char *)fde +ext4_rec_len_from_disk (fde->rec_len, blocksize)); -if ((char *) de >= (((char *) root) + blocksize)) { -EXT4_ERROR_INODE (dir,"invalid rec_len for '..'" ); -brelse (bh); -return -EFSCORRUPTED ; - } len = ((char *) root) + (blocksize - csum_size) - (char *) de;/* Allocate new block for the 0th block's dirents */
Greg Kroah-Hartman
maintainerPATCH 193/484 ext4: make sure the first directory block is not a hole
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Baokun Li <[email protected]>
commit f9ca51596bbfd0f9c386dd1c613c394c78d9e5e6 upstream.
The syzbot constructs a directory that has no dirblock but is non-inline, i.e. the first directory block is a hole. And no errors are reported when creating files in this directory in the following flow.
ext4_mknod
...
ext4_add_entry
// Read block 0
ext4_read_dirblock(dir, block, DIRENT)
bh = ext4_bread(NULL, inode, block, 0)
if (!bh && (type == INDEX || type == DIRENT_HTREE))
// The first directory block is a hole
// But type == DIRENT, so no error is reported.After that, we get a directory block without '.' and '..' but with a valid dentry. This may cause some code that relies on dot or dotdot (such as make_indexed_dir()) to crash.
Therefore when ext4_read_dirblock() finds that the first directory block is a hole report that the filesystem is corrupted and return an error to avoid loading corrupted data from disk causing something bad.
--- fs/ext4/namei.c | 17 ++++++----------- 1 file changed, 6 insertions(+), 11 deletions(-)
fs/ext4/namei.c +6 -11
@@ -151,10 +151,11 @@ static struct buffer_head *__ext4_read_dreturn bh; } -if (!bh && (type ==INDEX || type ==DIRENT_HTREE )) { +/* The first directory block must not be a hole. */ +if (!bh && (type ==INDEX || type ==DIRENT_HTREE || block ==0 )) {ext4_error_inode (inode, func, line, block, -"Directory hole found for htree %s block" , - (type ==INDEX ) ?"index" :"leaf" ); +"Directory hole found for htree %s block %u" , + (type ==INDEX ) ?"index" :"leaf" , block);return ERR_PTR (-EFSCORRUPTED ); }if (!bh)
@@ -3133,10 +3134,7 @@ bool ext4_empty_dir(struct inode *inode)EXT4_ERROR_INODE (inode,"invalid size" );return false; } -/* The first directory block must not be a hole, -* so treat it as DIRENT_HTREE -*/ - bh =ext4_read_dirblock (inode,0 ,DIRENT_HTREE ); + bh =ext4_read_dirblock (inode,0 ,EITHER );if (IS_ERR (bh))return false;
@@ -3594,10 +3592,7 @@ static struct buffer_head *ext4_get_firsstruct ext4_dir_entry_2 *de;unsigned int offset; -/* The first directory block must not be a hole, so -* treat it as DIRENT_HTREE -*/ - bh =ext4_read_dirblock (inode,0 ,DIRENT_HTREE ); + bh =ext4_read_dirblock (inode,0 ,EITHER );if (IS_ERR (bh)) { *retval =PTR_ERR (bh);return NULL ;
Greg Kroah-Hartman
maintainerPATCH 194/484 io_uring: tighten task exit cancellations
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pavel Begunkov <[email protected]>
commit f8b632e89a101dae349a7b212c1771d7925f441b upstream.
io_uring_cancel_generic() should retry if any state changes like a request is completed, however in case of a task exit it only goes for another loop and avoids schedule() if any tracked (i.e. REQ_F_INFLIGHT) request got completed.
Let's assume we have a non-tracked request executing in iowq and a tracked request linked to it. Let's also assume io_uring_cancel_generic() fails to find and cancel the request, i.e. via io_run_local_work(), which may happen as io-wq has gaps. Next, the request logically completes, io-wq still hold a ref but queues it for completion via tw, which happens in io_uring_try_cancel_requests(). After, right before prepare_to_wait() io-wq puts the request, grabs the linked one and tries executes it, e.g. arms polling. Finally the cancellation loop calls prepare_to_wait(), there are no tw to run, no tracked request was completed, so the tctx_inflight() check passes and the task is put to indefinite sleep.
--- io_uring/io_uring.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
io_uring/io_uring.c +4 -1
@@ -9856,8 +9856,11 @@ static void io_uring_cancel_generic(boolatomic_inc (&tctx->in_idle); do { io_uring_drop_tctx_refs(current); + if (!tctx_inflight(tctx, !cancel_all)) + break; + /* read completions before cancelations */ - inflight = tctx_inflight(tctx, !cancel_all); + inflight = tctx_inflight(tctx, false); if (!inflight) break;
Greg Kroah-Hartman
maintainerPATCH 195/484 selftests/landlock: Add cred_transfer test
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mickaël Salaün <[email protected]>
commit cc374782b6ca0fd634482391da977542443d3368 upstream.
Check that keyctl(KEYCTL_SESSION_TO_PARENT) preserves the parent's restrictions.
--- tools/testing/selftests/landlock/base_test.c | 74 +++++++++++++++++++++++++++ tools/testing/selftests/landlock/config | 5 + 2 files changed, 77 insertions(+), 2 deletions(-)
tools/testing/selftests/landlock/base_test.c +74 -0
@@ -9,6 +9,7 @@#define _GNU_SOURCE#include <errno.h> #include <fcntl.h> +#include <linux/keyctl.h> #include <linux/landlock.h> #include <string.h> #include <sys/prctl.h>
@@ -356,4 +357,77 @@ TEST(ruleset_fd_transfer)ASSERT_EQ (EXIT_SUCCESS ,WEXITSTATUS (status)); } +TEST (cred_transfer) +{ +struct landlock_ruleset_attr ruleset_attr = { + .handled_access_fs =LANDLOCK_ACCESS_FS_READ_DIR , + }; +int ruleset_fd, dir_fd; +pid_t child; +int status; + +drop_caps (_metadata); + + dir_fd =open ("/" ,O_RDONLY |O_DIRECTORY |O_CLOEXEC ); +EXPECT_LE (0 , dir_fd); +EXPECT_EQ (0 ,close (dir_fd)); + +/* Denies opening directories. */ + ruleset_fd = +landlock_create_ruleset (&ruleset_attr,sizeof (ruleset_attr),0 ); +ASSERT_LE (0 , ruleset_fd); +EXPECT_EQ (0 ,prctl (PR_SET_NO_NEW_PRIVS ,1 ,0 ,0 ,0 )); +ASSERT_EQ (0 ,landlock_restrict_self (ruleset_fd,0 )); +EXPECT_EQ (0 ,close (ruleset_fd)); + +/* Checks ruleset enforcement. */ +EXPECT_EQ (-1 ,open ("/" ,O_RDONLY |O_DIRECTORY |O_CLOEXEC )); +EXPECT_EQ (EACCES , errno); + +/* Needed for KEYCTL_SESSION_TO_PARENT permission checks */ +EXPECT_NE (-1 ,syscall (__NR_keyctl,KEYCTL_JOIN_SESSION_KEYRING ,NULL ,0 , + 0, 0)) + { +TH_LOG ("Failed to join session keyring: %s" ,strerror (errno)); + } + + child =fork (); +ASSERT_LE (0 , child); +if (child ==0 ) { +/* Checks ruleset enforcement. */ +EXPECT_EQ (-1 ,open ("/" ,O_RDONLY |O_DIRECTORY |O_CLOEXEC )); +EXPECT_EQ (EACCES , errno); + +/* +* KEYCTL_SESSION_TO_PARENT is a no-op unless we have a +* different session keyring in the child, so make that happen. +*/ +EXPECT_NE (-1 ,syscall (__NR_keyctl,KEYCTL_JOIN_SESSION_KEYRING , +NULL ,0 ,0 ,0 )); + +/* +* KEYCTL_SESSION_TO_PARENT installs credentials on the parent +* that never go through the cred_prepare hook, this path uses +* cred_transfer instead. +*/ +EXPECT_EQ (0 ,syscall (__NR_keyctl,KEYCTL_SESSION_TO_PARENT ,0 , +0 ,0 ,0 )); + +/* Re-checks ruleset enforcement. */ +EXPECT_EQ (-1 ,open ("/" ,O_RDONLY |O_DIRECTORY |O_CLOEXEC )); +EXPECT_EQ (EACCES , errno); + +_exit (_metadata->passed ?EXIT_SUCCESS :EXIT_FAILURE ); +return ; + } + +EXPECT_EQ (child,waitpid (child, &status,0 )); +EXPECT_EQ (1 ,WIFEXITED (status)); +EXPECT_EQ (EXIT_SUCCESS ,WEXITSTATUS (status)); + +/* Re-checks ruleset enforcement. */ +EXPECT_EQ (-1 ,open ("/" ,O_RDONLY |O_DIRECTORY |O_CLOEXEC )); +EXPECT_EQ (EACCES , errno); +} +TEST_HARNESS_MAIN
tools/testing/selftests/landlock/config +3 -2
@@ -1,7 +1,8 @@ +CONFIG_KEYS=y CONFIG_OVERLAY_FS=y +CONFIG_SECURITY=y CONFIG_SECURITY_LANDLOCK=y CONFIG_SECURITY_PATH=y -CONFIG_SECURITY=y CONFIG_SHMEM=y -CONFIG_TMPFS_XATTR=y CONFIG_TMPFS=y +CONFIG_TMPFS_XATTR=y
Greg Kroah-Hartman
maintainerPATCH 196/484 wifi: mwifiex: Fix interface type change
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Rafael Beims <[email protected]>
commit a17b9f590f6ec2b9f1b12b1db3bf1d181de6b272 upstream.
When changing the interface type we also need to update the bss_num, the driver private data is searched based on a unique (bss_type, bss_num) tuple, therefore every time bss_type changes, bss_num must also change.
This fixes for example an issue in which, after the mode changed, a wireless scan on the changed interface would not finish, leading to repeated -EBUSY messages to userspace when other scan requests were sent.
--- drivers/net/wireless/marvell/mwifiex/cfg80211.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/net/wireless/marvell/mwifiex/cfg80211.c +2 -0
@@ -930,6 +930,8 @@ mwifiex_init_new_priv_params(struct mwifreturn -EOPNOTSUPP ; } + priv->bss_num =mwifiex_get_unused_bss_num (adapter, priv->bss_type); +spin_lock_irqsave (&adapter->main_proc_lock, flags); adapter->main_locked = false;spin_unlock_irqrestore (&adapter->main_proc_lock, flags);
Greg Kroah-Hartman
maintainerPATCH 197/484 leds: ss4200: Convert PCIBIOS_* return codes to errnos
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ilpo Järvinen <[email protected]>
commit ce068e83976140badb19c7f1307926b4b562fac4 upstream.
ich7_lpc_probe() uses pci_read_config_dword() that returns PCIBIOS_* codes. The error handling code assumes incorrectly it's a normal errno and checks for < 0. The return code is returned from the probe function as is but probe functions should return normal errnos.
Remove < 0 from the check and convert PCIBIOS_* returns code using pcibios_err_to_errno() into normal errno before returning it.
--- drivers/leds/leds-ss4200.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/leds/leds-ss4200.c +5 -2
@@ -356,8 +356,10 @@ static int ich7_lpc_probe(struct pci_dev nas_gpio_pci_dev = dev; status =pci_read_config_dword (dev,PMBASE , &g_pm_io_base); -if (status) +if (status) { + status =pcibios_err_to_errno (status); goto out; + } g_pm_io_base &=0x00000ff80 ; status =pci_read_config_dword (dev,GPIO_CTRL , &gc);
@@ -369,8 +371,9 @@ static int ich7_lpc_probe(struct pci_dev } status =pci_read_config_dword (dev,GPIO_BASE , &nas_gpio_io_base); -if (0 > status) { +if (status) {dev_info (&dev->dev,"Unable to read GPIOBASE.\n" ); + status =pcibios_err_to_errno (status); goto out; }dev_dbg (&dev->dev,": GPIOBASE = 0x%08x\n" , nas_gpio_io_base);
Greg Kroah-Hartman
maintainerPATCH 198/484 jbd2: make jbd2_journal_get_max_txn_bufs() internal
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jan Kara <[email protected]>
commit 4aa99c71e42ad60178c1154ec24e3df9c684fb67 upstream.
There's no reason to have jbd2_journal_get_max_txn_bufs() public function. Currently all users are internal and can use journal->j_max_transaction_buffers instead. This saves some unnecessary recomputations of the limit as a bonus which becomes important as this function gets more complex in the following patch.
--- fs/jbd2/commit.c | 2 +- fs/jbd2/journal.c | 5 +++++ include/linux/jbd2.h | 5 ----- 3 files changed, 6 insertions(+), 6 deletions(-)
fs/jbd2/commit.c +1 -1
@@ -800,7 +800,7 @@ start_journal_io:if (first_block < journal->j_tail) freed += journal->j_last - journal->j_first;/* Update tail only if we free significant amount of space */ -if (freed <jbd2_journal_get_max_txn_bufs (journal)) +if (freed < journal->j_max_transaction_buffers) update_tail =0 ; }J_ASSERT (commit_transaction->t_state ==T_COMMIT );
fs/jbd2/journal.c +5 -0
@@ -1529,6 +1529,11 @@ static void journal_fail_superblock(jour journal->j_sb_buffer =NULL ; } +static int jbd2_journal_get_max_txn_bufs (journal_t *journal) +{ +return (journal->j_total_len - journal->j_fc_wbufsize) /4 ; +} +/* * Given a journal_t structure, initialise the various fields for * startup of a new journaling session. We use this both when creating
include/linux/jbd2.h +0 -5
@@ -1669,11 +1669,6 @@ int jbd2_wait_inode_data(journal_t *jourint jbd2_fc_wait_bufs (journal_t *journal,int num_blks);int jbd2_fc_release_bufs (journal_t *journal); -static inline int jbd2_journal_get_max_txn_bufs (journal_t *journal) -{ -return (journal->j_total_len - journal->j_fc_wbufsize) /4 ; -} -/* * is_journal_abort *
Greg Kroah-Hartman
maintainerPATCH 199/484 media: uvcvideo: Fix integer overflow calculating timestamp
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ricardo Ribalda <[email protected]>
commit 8676a5e796fa18f55897ca36a94b2adf7f73ebd1 upstream.
The function uvc_video_clock_update() supports a single SOF overflow. Or in other words, the maximum difference between the first ant the last timestamp can be 4096 ticks or 4.096 seconds.
This results in a maximum value for y2 of: 0x12FBECA00, that overflows 32bits.
y2 = (u32)ktime_to_ns(ktime_sub(last->host_time, first->host_time)) + y1;
Extend the size of y2 to u64 to support all its values.
Without this patch:
# yavta -s 1920x1080 -f YUYV -t 1/5 -c /dev/video0 Device /dev/v4l/by-id/usb-Shine-Optics_Integrated_Camera_0001-video-index0 opened. Device `Integrated Camera: Integrated C' on `usb-0000:00:14.0-6' (driver 'uvcvideo') supports video, capture, without mplanes. Video format set: YUYV (56595559) 1920x1080 (stride 3840) field none buffer size 4147200 Video format: YUYV (56595559) 1920x1080 (stride 3840) field none buffer size 4147200 Current frame rate: 1/5 Setting frame rate to: 1/5 Frame rate set: 1/5 8 buffers requested. length: 4147200 offset: 0 timestamp type/source: mono/SoE Buffer 0/0 mapped at address 0x7947ea94c000. length: 4147200 offset: 4149248 timestamp type/source: mono/SoE Buffer 1/0 mapped at address 0x7947ea557000. length: 4147200 offset: 8298496 timestamp type/source: mono/SoE Buffer 2/0 mapped at address 0x7947ea162000. length: 4147200 offset: 12447744 timestamp type/source: mono/SoE Buffer 3/0 mapped at address 0x7947e9d6d000. length: 4147200 offset: 16596992 timestamp type/source: mono/SoE Buffer 4/0 mapped at address 0x7947e9978000. length: 4147200 offset: 20746240 timestamp type/source: mono/SoE Buffer 5/0 mapped at address 0x7947e9583000. length: 4147200 offset: 24895488 timestamp type/source: mono/SoE Buffer 6/0 mapped at address 0x7947e918e000. length: 4147200 offset: 29044736 timestamp type/source: mono/SoE Buffer 7/0 mapped at address 0x7947e8d99000. 0 (0) [-] none 0 4147200 B 507.554210 508.874282 242.836 fps ts mono/SoE 1 (1) [-] none 2 4147200 B 508.886298 509.074289 0.751 fps ts mono/SoE 2 (2) [-] none 3 4147200 B 509.076362 509.274307 5.261 fps ts mono/SoE 3 (3) [-] none 4 4147200 B 509.276371 509.474336 5.000 fps ts mono/SoE 4 (4) [-] none 5 4147200 B 509.476394 509.674394 4.999 fps ts mono/SoE 5 (5) [-] none 6 4147200 B 509.676506 509.874345 4.997 fps ts mono/SoE 6 (6) [-] none 7 4147200 B 509.876430 510.074370 5.002 fps ts mono/SoE 7 (7) [-] none 8 4147200 B 510.076434 510.274365 5.000 fps ts mono/SoE 8 (0) [-] none 9 4147200 B 510.276421 510.474333 5.000 fps ts mono/SoE 9 (1) [-] none 10 4147200 B 510.476391 510.674429 5.001 fps ts mono/SoE 10 (2) [-] none 11 4147200 B 510.676434 510.874283 4.999 fps ts mono/SoE 11 (3) [-] none 12 4147200 B 510.886264 511.074349 4.766 fps ts mono/SoE 12 (4) [-] none 13 4147200 B 511.070577 511.274304 5.426 fps ts mono/SoE 13 (5) [-] none 14 4147200 B 511.286249 511.474301 4.637 fps ts mono/SoE 14 (6) [-] none 15 4147200 B 511.470542 511.674251 5.426 fps ts mono/SoE 15 (7) [-] none 16 4147200 B 511.672651 511.874337 4.948 fps ts mono/SoE 16 (0) [-] none 17 4147200 B 511.873988 512.074462 4.967 fps ts mono/SoE 17 (1) [-] none 18 4147200 B 512.075982 512.278296 4.951 fps ts mono/SoE 18 (2) [-] none 19 4147200 B 512.282631 512.482423 4.839 fps ts mono/SoE 19 (3) [-] none 20 4147200 B 518.986637 512.686333 0.149 fps ts mono/SoE 20 (4) [-] none 21 4147200 B 518.342709 512.886386 -1.553 fps ts mono/SoE 21 (5) [-] none 22 4147200 B 517.909812 513.090360 -2.310 fps ts mono/SoE 22 (6) [-] none 23 4147200 B 517.590775 513.294454 -3.134 fps ts mono/SoE 23 (7) [-] none 24 4147200 B 513.298465 513.494335 -0.233 fps ts mono/SoE 24 (0) [-] none 25 4147200 B 513.510273 513.698375 4.721 fps ts mono/SoE 25 (1) [-] none 26 4147200 B 513.698904 513.902327 5.301 fps ts mono/SoE 26 (2) [-] none 27 4147200 B 513.895971 514.102348 5.074 fps ts mono/SoE 27 (3) [-] none 28 4147200 B 514.099091 514.306337 4.923 fps ts mono/SoE 28 (4) [-] none 29 4147200 B 514.310348 514.510567 4.734 fps ts mono/SoE 29 (5) [-] none 30 4147200 B 514.509295 514.710367 5.026 fps ts mono/SoE 30 (6) [-] none 31 4147200 B 521.532513 514.914398 0.142 fps ts mono/SoE 31 (7) [-] none 32 4147200 B 520.885277 515.118385 -1.545 fps ts mono/SoE 32 (0) [-] none 33 4147200 B 520.411140 515.318336 -2.109 fps ts mono/SoE 33 (1) [-] none 34 4147200 B 515.325425 515.522278 -0.197 fps ts mono/SoE 34 (2) [-] none 35 4147200 B 515.538276 515.726423 4.698 fps ts mono/SoE 35 (3) [-] none 36 4147200 B 515.720767 515.930373 5.480 fps ts mono/SoE
--- drivers/media/usb/uvc/uvc_video.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-)
drivers/media/usb/uvc/uvc_video.c +5 -5
@@ -697,11 +697,11 @@ void uvc_video_clock_update(struct uvc_sunsigned long flags;u64 timestamp;u32 delta_stc; -u32 y1, y2; +u32 y1;u32 x1, x2;u32 mean;u32 sof; -u64 y; +u64 y, y2;if (!uvc_hw_timestamps_param)return ;
@@ -741,7 +741,7 @@ void uvc_video_clock_update(struct uvc_s sof = y; uvc_dbg(stream->dev, CLOCK, - "%s: PTS %u y %llu.%06llu SOF %u.%06llu (x1 %u x2 %u y1 %u y2 %u SOF offset %u)\n", + "%s: PTS %u y %llu.%06llu SOF %u.%06llu (x1 %u x2 %u y1 %u y2 %llu SOF offset %u)\n", stream->dev->name, buf->pts, y >> 16, div_u64((y & 0xffff) * 1000000, 65536), sof >> 16, div_u64(((u64)sof & 0xffff) * 1000000LLU, 65536),
@@ -756,7 +756,7 @@ void uvc_video_clock_update(struct uvc_s goto done; y1 =NSEC_PER_SEC ; - y2 = (u32 )ktime_to_ns (ktime_sub (last->host_time, first->host_time)) + y1; + y2 =ktime_to_ns (ktime_sub (last->host_time, first->host_time)) + y1;/* Interpolated and host SOF timestamps can wrap around at slightly * different times. Handle this by adding or removing 2048 to or from
@@ -776,7 +776,7 @@ void uvc_video_clock_update(struct uvc_s timestamp =ktime_to_ns (first->host_time) + y - y1; uvc_dbg(stream->dev, CLOCK, - "%s: SOF %u.%06llu y %llu ts %llu buf ts %llu (x1 %u/%u/%u x2 %u/%u/%u y1 %u y2 %u)\n", + "%s: SOF %u.%06llu y %llu ts %llu buf ts %llu (x1 %u/%u/%u x2 %u/%u/%u y1 %u y2 %llu)\n", stream->dev->name, sof >> 16, div_u64(((u64)sof & 0xffff) * 1000000LLU, 65536), y, timestamp, vbuf->vb2_buf.timestamp,
Greg Kroah-Hartman
maintainerPATCH 200/484 KVM: VMX: Split out the non-virtualization part of vmx_interrupt_blocked()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sean Christopherson <[email protected]>
commit 322a569c4b4188a0da2812f9e952780ce09b74ba upstream.
Move the non-VMX chunk of the "interrupt blocked" checks to a separate helper so that KVM can reuse the code to detect if interrupts are blocked for L2, e.g. to determine if a virtual interrupt _for L2_ is a valid wake event. If L1 disables HLT-exiting for L2, nested APICv is enabled, and L2 HLTs, then L2 virtual interrupts are valid wake events, but if and only if interrupts are unblocked for L2.
--- arch/x86/kvm/vmx/vmx.c | 11 ++++++++--- arch/x86/kvm/vmx/vmx.h | 1 + 2 files changed, 9 insertions(+), 3 deletions(-)
arch/x86/kvm/vmx/vmx.c +8 -3
@@ -4706,14 +4706,19 @@ static int vmx_nmi_allowed(struct kvm_vcreturn !vmx_nmi_blocked (vcpu); } +bool __vmx_interrupt_blocked (struct kvm_vcpu *vcpu) +{ +return !(vmx_get_rflags (vcpu) &X86_EFLAGS_IF ) || + (vmcs_read32 (GUEST_INTERRUPTIBILITY_INFO ) & + (GUEST_INTR_STATE_STI |GUEST_INTR_STATE_MOV_SS )); +} +bool vmx_interrupt_blocked (struct kvm_vcpu *vcpu) {if (is_guest_mode (vcpu) &&nested_exit_on_intr (vcpu))return false; -return !(vmx_get_rflags (vcpu) &X86_EFLAGS_IF ) || - (vmcs_read32 (GUEST_INTERRUPTIBILITY_INFO ) & - (GUEST_INTR_STATE_STI |GUEST_INTR_STATE_MOV_SS )); +return __vmx_interrupt_blocked (vcpu); }static int vmx_interrupt_allowed (struct kvm_vcpu *vcpu,bool for_injection)
arch/x86/kvm/vmx/vmx.h +1 -0
@@ -388,6 +388,7 @@ u64 construct_eptp(struct kvm_vcpu *vcpubool vmx_guest_inject_ac (struct kvm_vcpu *vcpu);void vmx_update_exception_bitmap (struct kvm_vcpu *vcpu);bool vmx_nmi_blocked (struct kvm_vcpu *vcpu); +bool __vmx_interrupt_blocked (struct kvm_vcpu *vcpu);bool vmx_interrupt_blocked (struct kvm_vcpu *vcpu);bool vmx_get_nmi_mask (struct kvm_vcpu *vcpu);void vmx_set_nmi_mask (struct kvm_vcpu *vcpu,bool masked);
Greg Kroah-Hartman
maintainerPATCH 201/484 ALSA: usb-audio: Fix microphone sound on HD webcam.
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: wangdicheng <[email protected]>
commit 74dba240881820b46b9b1c62ef4de3bfff47fbd4 upstream.
I own an external usb Webcam, HD webcam, which had low mic volume and inconsistent sound quality. Video works as expected.
(snip)
[ 95.473820][ 1] [ T73] usb 5-2.2: new high-speed USB device number 7 using xhci_hcd [ 95.773974][ 1] [ T73] usb 5-2.2: New USB device found, idVendor=1bcf, idProduct=2281, bcdDevice= 0.05 [ 95.783445][ 1] [ T73] usb 5-2.2: New USB device strings: Mfr=1, Product=2, SerialNumber=3 [ 95.791872][ 1] [ T73] usb 5-2.2: Product: HD webcam [ 95.797001][ 1] [ T73] usb 5-2.2: Manufacturer: Sunplus IT Co [ 95.802996][ 1] [ T73] usb 5-2.2: SerialNumber: 20200513 [ 96.092610][ 2] [ T3680] usb 5-2.2: Warning! Unlikely big volume range (=4096), cval->res is probably wrong. [ 96.102436][ 2] [ T3680] usb 5-2.2: [5] FU [Mic Capture Volume] ch = 1, val = 0/4096/1
Set up quirk cval->res to 16 for 256 levels,
Set GET_SAMPLE_RATE quirk flag to stop trying to get the sample rate. Confirmed that happened anyway later due to the backoff mechanism, After 3 failures.
All audio stream on device interfaces share the same values, apart from wMaxPacketSize and tSamFreq :
bLength 9
bDescriptorType 4
bInterfaceNumber 3
bAlternateSetting 4
bNumEndpoints 1
bInterfaceClass 1 AudioInterface Descriptor:
bLength 9 bDescriptorType 4 bInterfaceNumber 3 bAlternateSetting 4 bNumEndpoints 1 bInterfaceClass 1 Audio bInterfaceSubClass 2 Streaming bInterfaceProtocol 0 iInterface 0
AudioStreaming Interface Descriptor:
bLength 7
bDescriptorType 36
bDescriptorSubtype 1 (AS_GENERAL)
bTerminalLink 3
bDelay 1 frames
wFormatTag 0x0001 PCM
AudioStreaming Interface Descriptor:
bLength 11
bDescriptorType 36
bDescriptorSubtype 2 (FORMAT_TYPE)
bFormatType 1 (FORMAT_TYPE_I)
bNrChannels 1
bSubframeSize 2
bBitResolution 16
bSamFreqType 1 Discrete
tSamFreq[ 0] 48000
Endpoint Descriptor:
bLength 9
bDescriptorType 5
bEndpointAddress 0x86 EP 6 IN
bmAttributes 5
Transfer Type Isochronous
Synch Type Asynchronous
Usage Type Data
wMaxPacketSize 0x0064 1x 100 bytes
bInterval 4
bRefresh 0
bSynchAddress 0
AudioStreaming Endpoint Descriptor:
bLength 7
bDescriptorType 37
bDescriptorSubtype 1 (EP_GENERAL)
bmAttributes 0x01
Sampling Frequency
bLockDelayUnits 0 Undefined
wLockDelay 0x0000
(snip)
Testing patch provides consistent good sound recording quality and volume range.
(snip)
[ 95.473820][ 1] [ T73] usb 5-2.2: new high-speed USB device number 7 using xhci_hcd [ 95.773974][ 1] [ T73] usb 5-2.2: New USB device found, idVendor=1bcf, idProduct=2281, bcdDevice= 0.05 [ 95.783445][ 1] [ T73] usb 5-2.2: New USB device strings: Mfr=1, Product=2, SerialNumber=3 [ 95.791872][ 1] [ T73] usb 5-2.2: Product: HD webcam [ 95.797001][ 1] [ T73] usb 5-2.2: Manufacturer: Sunplus IT Co [ 95.802996][ 1] [ T73] usb 5-2.2: SerialNumber: 20200513 [ 96.110630][ 3] [ T3680] usbcore: registered new interface driver snd-usb-audio [ 96.114329][ 7] [ T3677] usb 5-2.2: Found UVC 1.00 device HD webcam (1bcf:2281) [ 96.167555][ 7] [ T3677] usbcore: registered new interface driver uvcvideo
--- sound/usb/mixer.c | 7 +++++++ sound/usb/quirks.c | 2 ++ 2 files changed, 9 insertions(+)
sound/usb/mixer.c +7 -0
@@ -1212,6 +1212,13 @@ static void volume_control_quirks(struct cval->res =16 ; }break ; +case USB_ID (0x1bcf ,0x2281 ):/* HD Webcam */ +if (!strcmp (kctl->id.name,"Mic Capture Volume" )) { +usb_audio_info (chip, +"set resolution quirk: cval->res = 16\n" ); + cval->res =16 ; + } +break ; } }
sound/usb/quirks.c +2 -0
@@ -1904,6 +1904,8 @@ static const struct usb_audio_quirk_flag QUIRK_FLAG_ALIGN_TRANSFER),DEVICE_FLG (0x534d ,0x2109 ,/* MacroSilicon MS2109 */ QUIRK_FLAG_ALIGN_TRANSFER ), +DEVICE_FLG (0x1bcf ,0x2281 ,/* HD Webcam */ +QUIRK_FLAG_GET_SAMPLE_RATE ),/* Vendor matches */ VENDOR_FLG(0x045e, /* MS Lifecam */
Greg Kroah-Hartman
maintainerPATCH 202/484 ALSA: usb-audio: Move HD Webcam quirk to the right place
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Takashi Iwai <[email protected]>
commit 7010d9464f7ca3ee2d75095ea2e642a9009a41ff upstream.
The quirk_flags_table[] is sorted in the USB ID order, while the last fix was put at a wrong position. Adjust the entry at the right position.
--- sound/usb/quirks.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
sound/usb/quirks.c +2 -2
@@ -1850,6 +1850,8 @@ static const struct usb_audio_quirk_flag QUIRK_FLAG_GET_SAMPLE_RATE),DEVICE_FLG (0x19f7 ,0x0035 ,/* RODE NT-USB+ */ QUIRK_FLAG_GET_SAMPLE_RATE ), +DEVICE_FLG (0x1bcf ,0x2281 ,/* HD Webcam */ +QUIRK_FLAG_GET_SAMPLE_RATE ),DEVICE_FLG (0x1bcf ,0x2283 ,/* NexiGo N930AF FHD Webcam */ QUIRK_FLAG_GET_SAMPLE_RATE ), DEVICE_FLG(0x2040, 0x7200, /* Hauppauge HVR-950Q */
@@ -1904,8 +1906,6 @@ static const struct usb_audio_quirk_flag QUIRK_FLAG_ALIGN_TRANSFER),DEVICE_FLG (0x534d ,0x2109 ,/* MacroSilicon MS2109 */ QUIRK_FLAG_ALIGN_TRANSFER ), -DEVICE_FLG (0x1bcf ,0x2281 ,/* HD Webcam */ -QUIRK_FLAG_GET_SAMPLE_RATE ),/* Vendor matches */ VENDOR_FLG(0x045e, /* MS Lifecam */
Greg Kroah-Hartman
maintainerPATCH 203/484 ALSA: usb-audio: Add a quirk for Sonix HD USB Camera
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: wangdicheng <[email protected]>
commit 21451dfd853e7d8e6e3fbd7ef1fbdb2f2ead12f5 upstream.
Sonix HD USB Camera does not support reading the sample rate which leads to many lines of "cannot get freq at ep 0x84".
This patch adds the USB ID to quirks.c and avoids those error messages.
(snip)
[1.789698] usb 3-3: new high-speed USB device number 2 using xhci_hcd [1.984121] usb 3-3: New USB device found, idVendor=0c45, idProduct=6340, bcdDevice= 0.00 [1.984124] usb 3-3: New USB device strings: Mfr=2, Product=1, SerialNumber=0 [1.984127] usb 3-3: Product: USB 2.0 Camera [1.984128] usb 3-3: Manufacturer: Sonix Technology Co., Ltd. [5.440957] usb 3-3: 3:1: cannot get freq at ep 0x84 [12.130679] usb 3-3: 3:1: cannot get freq at ep 0x84 [12.175065] usb 3-3: 3:1: cannot get freq at ep 0x84
--- sound/usb/quirks.c | 2 ++ 1 file changed, 2 insertions(+)
sound/usb/quirks.c +2 -0
@@ -1810,6 +1810,8 @@ static const struct usb_audio_quirk_flag QUIRK_FLAG_CTL_MSG_DELAY_1M),DEVICE_FLG (0x0b0e ,0x0349 ,/* Jabra 550a */ QUIRK_FLAG_CTL_MSG_DELAY_1M ), +DEVICE_FLG (0x0c45 ,0x6340 ,/* Sonix HD USB Camera */ +QUIRK_FLAG_GET_SAMPLE_RATE ),DEVICE_FLG (0x0ecb ,0x205c ,/* JBL Quantum610 Wireless */ QUIRK_FLAG_FIXED_RATE ), DEVICE_FLG(0x0ecb, 0x2069, /* JBL Quantum810 Wireless */
Greg Kroah-Hartman
maintainerPATCH 204/484 tools/memory-model: Fix bug in lock.cat
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alan Stern <[email protected]>
commit 4c830eef806679dc243e191f962c488dd9d00708 upstream.
Andrea reported that the following innocuous litmus test:
C T
{}
P0(spinlock_t *x)
{
int r0;
spin_lock(x);
spin_unlock(x);
r0 = spin_is_locked(x);
}gives rise to a nonsensical empty result with no executions:
$ herd7 -conf linux-kernel.cfg T.litmus Test T Required States 0 Ok Witnesses Positive: 0 Negative: 0 Condition forall (true) Observation T Never 0 0 Time T 0.00 Hash=6fa204e139ddddf2cb6fa963bad117c0
The problem is caused by a bug in the lock.cat part of the LKMM. Its computation of the rf relation for RU (read-unlocked) events is faulty; it implicitly assumes that every RU event must read from either a UL (unlock) event in another thread or from the lock's initial state. Neither is true in the litmus test above, so the computation yields no possible executions.
The lock.cat code tries to make up for this deficiency by allowing RU events outside of critical sections to read from the last po-previous UL event. But it does this incorrectly, trying to keep these rfi links separate from the rfe links that might also be needed, and passing only the latter to herd7's cross() macro.
The problem is fixed by merging the two sets of possible rf links for RU events and using them all in the call to cross().
--- tools/memory-model/lock.cat | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-)
tools/memory-model/lock.cat +10 -10
@@ -102,19 +102,19 @@ let rf-lf = rfe-lf | rfi-lf * within one of the lock's critical sections returns False. *) -(* rfi for RU events: an RU may read from the last po-previous UL *) -let rfi-ru = ([UL] ; po-loc ; [RU]) \ ([UL] ; po-loc ; [LKW] ; po-loc) - -(* rfe for RU events: an RU may read from an external UL or the initial write *) -let all-possible-rfe-ru = - let possible-rfe-ru r = +(* + * rf for RU events: an RU may read from an external UL or the initial write, + * or from the last po-previous UL + *) +let all-possible-rf-ru = + let possible-rf-ru r = let pair-to-relation p = p ++ 0 - in map pair-to-relation (((UL | IW) * {r}) & loc & ext) - in map possible-rfe-ru RU + in map pair-to-relation ((((UL | IW) * {r}) & loc & ext) | + (((UL * {r}) & po-loc) \ ([UL] ; po-loc ; [LKW] ; po-loc))) + in map possible-rf-ru RU (* Generate all rf relations for RU events *) -with rfe-ru from cross(all-possible-rfe-ru) -let rf-ru = rfe-ru | rfi-ru +with rf-ru from cross(all-possible-rf-ru) (* Final rf relation *) let rf = rf | rf-lf | rf-ru
Greg Kroah-Hartman
maintainerPATCH 205/484 hwrng: amd - Convert PCIBIOS_* return codes to errnos
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ilpo Järvinen <[email protected]>
commit 14cba6ace79627a57fb9058582b03f0ed3832390 upstream.
amd_rng_mod_init() uses pci_read_config_dword() that returns PCIBIOS_* codes. The return code is then returned as is but amd_rng_mod_init() is a module_init() function that should return normal errnos.
Convert PCIBIOS_* returns code using pcibios_err_to_errno() into normal errno before returning it.
--- drivers/char/hw_random/amd-rng.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/char/hw_random/amd-rng.c +3 -1
@@ -142,8 +142,10 @@ static int __init amd_rng_mod_init(void) found: err =pci_read_config_dword (pdev,0x58 , &pmbase); -if (err) +if (err) { + err =pcibios_err_to_errno (err); goto put_dev; + } pmbase &=0x0000FF00 ;if (pmbase ==0 ) {
Greg Kroah-Hartman
maintainerPATCH 206/484 PCI: hv: Return zero, not garbage, when reading PCI_INTERRUPT_PIN
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Wei Liu <[email protected]>
commit fea93a3e5d5e6a09eb153866d2ce60ea3287a70d upstream.
The intent of the code snippet is to always return 0 for both PCI_INTERRUPT_LINE and PCI_INTERRUPT_PIN.
The check misses PCI_INTERRUPT_PIN. This patch fixes that.
This is discovered by this call in VFIO:
pci_read_config_byte(vdev->pdev, PCI_INTERRUPT_PIN, &pin);
The old code does not set *val to 0 because it misses the check for PCI_INTERRUPT_PIN. Garbage is returned in that case.
--- drivers/pci/controller/pci-hyperv.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/pci/controller/pci-hyperv.c +2 -2
@@ -707,8 +707,8 @@ static void _hv_pcifront_read_config(str PCI_CAPABILITY_LIST) {/* ROM BARs are unimplemented */ *val =0 ; - } else if (where >= PCI_INTERRUPT_LINE && where + size <= - PCI_INTERRUPT_PIN) { + } else if ((where >= PCI_INTERRUPT_LINE && where + size <= PCI_INTERRUPT_PIN) || + (where >= PCI_INTERRUPT_PIN && where + size <= PCI_MIN_GNT)) {/* * Interrupt Line and Interrupt PIN are hard-wired to zero * because this front-end only supports message-signaled
Greg Kroah-Hartman
maintainerPATCH 207/484 PCI: dw-rockchip: Fix initial PERST# GPIO value
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Niklas Cassel <[email protected]>
commit 28b8d7793b8573563b3d45321376f36168d77b1e upstream.
PERST# is active low according to the PCIe specification.
However, the existing pcie-dw-rockchip.c driver does:
gpiod_set_value(..., 0); msleep(100); gpiod_set_value(..., 1);
when asserting + deasserting PERST#.
This is of course wrong, but because all the device trees for this compatible string have also incorrectly marked this GPIO as ACTIVE_HIGH:
$ git grep -B 10 reset-gpios arch/arm64/boot/dts/rockchip/rk3568* $ git grep -B 10 reset-gpios arch/arm64/boot/dts/rockchip/rk3588*
The actual toggling of PERST# is correct, and we cannot change it anyway, since that would break device tree compatibility.
However, this driver does request the GPIO to be initialized as GPIOD_OUT_HIGH, which does cause a silly sequence where PERST# gets toggled back and forth for no good reason.
Fix this by requesting the GPIO to be initialized as GPIOD_OUT_LOW (which for this driver means PERST# asserted).
This will avoid an unnecessary signal change where PERST# gets deasserted (by devm_gpiod_get_optional()) and then gets asserted (by rockchip_pcie_start_link()) just a few instructions later.
Before patch, debug prints on EP side, when booting RC:
[ 845.606810] pci: PERST# asserted by host! [ 852.483985] pci: PERST# de-asserted by host! [ 852.503041] pci: PERST# asserted by host! [ 852.610318] pci: PERST# de-asserted by host!
After patch, debug prints on EP side, when booting RC:
[ 125.107921] pci: PERST# asserted by host! [ 132.111429] pci: PERST# de-asserted by host!
This extra, very short, PERST# assertion + deassertion has been reported to cause issues with certain WLAN controllers, e.g. RTL8822CE.
--- drivers/pci/controller/dwc/pcie-dw-rockchip.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/pci/controller/dwc/pcie-dw-rockchip.c +1 -1
@@ -148,7 +148,7 @@ static int rockchip_pcie_resource_get(streturn PTR_ERR (rockchip->apb_base); rockchip->rst_gpio =devm_gpiod_get_optional (&pdev->dev,"reset" , -GPIOD_OUT_HIGH ); +GPIOD_OUT_LOW );if (IS_ERR (rockchip->rst_gpio))return PTR_ERR (rockchip->rst_gpio);
Greg Kroah-Hartman
maintainerPATCH 208/484 PCI: rockchip: Use GPIOD_OUT_LOW flag while requesting ep_gpio
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Manivannan Sadhasivam <[email protected]>
commit 840b7a5edf88fe678c60dee88a135647c0ea4375 upstream.
Rockchip platforms use 'GPIO_ACTIVE_HIGH' flag in the devicetree definition for ep_gpio. This means, whatever the logical value set by the driver for the ep_gpio, physical line will output the same logic level.
For instance,
gpiod_set_value_cansleep(rockchip->ep_gpio, 0); --> Level low gpiod_set_value_cansleep(rockchip->ep_gpio, 1); --> Level high
But while requesting the ep_gpio, GPIOD_OUT_HIGH flag is currently used. Now, this also causes the physical line to output 'high' creating trouble for endpoint devices during host reboot.
When host reboot happens, the ep_gpio will initially output 'low' due to the GPIO getting reset to its POR value. Then during host controller probe, it will output 'high' due to GPIOD_OUT_HIGH flag. Then during rockchip_pcie_host_init_port(), it will first output 'low' and then 'high' indicating the completion of controller initialization.
On the endpoint side, each output 'low' of ep_gpio is accounted for PERST# assert and 'high' for PERST# deassert. With the above mentioned flow during host reboot, endpoint will witness below state changes for PERST#:
(1) PERST# assert - GPIO POR state
(2) PERST# deassert - GPIOD_OUT_HIGH while requesting GPIO
(3) PERST# assert - rockchip_pcie_host_init_port()
(4) PERST# deassert - rockchip_pcie_host_init_port()
Now the time interval between (2) and (3) is very short as both happen during the driver probe(), and this results in a race in the endpoint. Because, before completing the PERST# deassertion in (2), endpoint got another PERST# assert in (3).
A proper way to fix this issue is to change the GPIOD_OUT_HIGH flag in (2) to GPIOD_OUT_LOW. Because the usual convention is to request the GPIO with a state corresponding to its 'initial/default' value and let the driver change the state of the GPIO when required.
As per that, the ep_gpio should be requested with GPIOD_OUT_LOW as it corresponds to the POR value of '0' (PERST# assert in the endpoint). Then the driver can change the state of the ep_gpio later in rockchip_pcie_host_init_port() as per the initialization sequence.
This fixes the firmware crash issue in Qcom based modems connected to Rockpro64 based board.
--- drivers/pci/controller/pcie-rockchip.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/pci/controller/pcie-rockchip.c +1 -1
@@ -120,7 +120,7 @@ int rockchip_pcie_parse_dt(struct rockchif (rockchip->is_rc) { rockchip->ep_gpio =devm_gpiod_get_optional (dev,"ep" , -GPIOD_OUT_HIGH ); +GPIOD_OUT_LOW );if (IS_ERR (rockchip->ep_gpio))return dev_err_probe (dev,PTR_ERR (rockchip->ep_gpio),"failed to get ep GPIO\n" );
Greg Kroah-Hartman
maintainerPATCH 209/484 binder: fix hang of unregistered readers
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Carlos Llamas <[email protected]>
commit 31643d84b8c3d9c846aa0e20bc033e46c68c7e7d upstream.
With the introduction of binder_available_for_proc_work_ilocked() in commit 1b77e9dcc3da ("ANDROID: binder: remove proc waitqueue") a binder thread can only "wait_for_proc_work" after its thread->looper has been marked as BINDER_LOOPER_STATE_{ENTERED|REGISTERED}.
This means an unregistered reader risks waiting indefinitely for work since it never gets added to the proc->waiting_threads. If there are no further references to its waitqueue either the task will hang. The same applies to readers using the (e)poll interface.
I couldn't find the rationale behind this restriction. So this patch restores the previous behavior of allowing unregistered threads to "wait_for_proc_work". Note that an error message for this scenario, which had previously become unreachable, is now re-enabled.
--- drivers/android/binder.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-)
drivers/android/binder.c +1 -3
@@ -542,9 +542,7 @@ static bool binder_has_work(struct bindestatic bool binder_available_for_proc_work_ilocked (struct binder_thread *thread) {return !thread->transaction_stack && -binder_worklist_empty_ilocked (&thread->todo) && - (thread->looper & (BINDER_LOOPER_STATE_ENTERED | -BINDER_LOOPER_STATE_REGISTERED )); +binder_worklist_empty_ilocked (&thread->todo); } static void binder_wakeup_poll_threads_ilocked(struct binder_proc *proc,
Greg Kroah-Hartman
maintainerPATCH 210/484 dev/parport: fix the array out-of-bounds risk
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: tuhaowen <[email protected]>
commit ab11dac93d2d568d151b1918d7b84c2d02bacbd5 upstream.
Fixed array out-of-bounds issues caused by sprintf by replacing it with snprintf for safer data copying, ensuring the destination buffer is not overflowed.
Below is the stack trace I encountered during the actual issue:
[ 66.575408s] [pid:5118,cpu4,QThread,4]Kernel panic - not syncing: stack-protector:
Kernel stack is corrupted in: do_hardware_base_addr+0xcc/0xd0 [parport] [ 66.575408s] [pid:5118,cpu4,QThread,5]CPU: 4 PID: 5118 Comm:
QThread Tainted: G S W O 5.10.97-arm64-desktop #7100.57021.2
[ 66.575439s] [pid:5118,cpu4,QThread,6]TGID: 5087 Comm: EFileApp
[ 66.575439s] [pid:5118,cpu4,QThread,7]Hardware name: HUAWEI HUAWEI QingYun PGUX-W515x-B081/SP1PANGUXM, BIOS 1.00.07 04/29/2024
[ 66.575439s] [pid:5118,cpu4,QThread,8]Call trace:
[ 66.575469s] [pid:5118,cpu4,QThread,9] dump_backtrace+0x0/0x1c0
[ 66.575469s] [pid:5118,cpu4,QThread,0] show_stack+0x14/0x20
[ 66.575469s] [pid:5118,cpu4,QThread,1] dump_stack+0xd4/0x10c
[ 66.575500s] [pid:5118,cpu4,QThread,2] panic+0x1d8/0x3bc
[ 66.575500s] [pid:5118,cpu4,QThread,3] __stack_chk_fail+0x2c/0x38
[ 66.575500s] [pid:5118,cpu4,QThread,4] do_hardware_base_addr+0xcc/0xd0 [parport]
--- drivers/parport/procfs.c | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-)
drivers/parport/procfs.c +12 -12
@@ -51,12 +51,12 @@ static int do_active_device(struct ctl_tfor (dev = port->devices; dev ; dev = dev->next) {if (dev == port->cad) { - len +=sprintf (buffer,"%s\n" , dev->name); + len +=snprintf (buffer,sizeof (buffer),"%s\n" , dev->name); } }if (!len) { - len +=sprintf (buffer,"%s\n" ,"none" ); + len +=snprintf (buffer,sizeof (buffer),"%s\n" ,"none" ); }if (len > *lenp)
@@ -87,19 +87,19 @@ static int do_autoprobe(struct ctl_table }if ((str = info->class_name) !=NULL ) - len +=sprintf (buffer + len,"CLASS:%s;\n" , str); + len +=snprintf (buffer + len,sizeof (buffer) - len,"CLASS:%s;\n" , str);if ((str = info->model) !=NULL ) - len +=sprintf (buffer + len,"MODEL:%s;\n" , str); + len +=snprintf (buffer + len,sizeof (buffer) - len,"MODEL:%s;\n" , str);if ((str = info->mfr) !=NULL ) - len +=sprintf (buffer + len,"MANUFACTURER:%s;\n" , str); + len +=snprintf (buffer + len,sizeof (buffer) - len,"MANUFACTURER:%s;\n" , str);if ((str = info->description) !=NULL ) - len +=sprintf (buffer + len,"DESCRIPTION:%s;\n" , str); + len +=snprintf (buffer + len,sizeof (buffer) - len,"DESCRIPTION:%s;\n" , str);if ((str = info->cmdset) !=NULL ) - len +=sprintf (buffer + len,"COMMAND SET:%s;\n" , str); + len +=snprintf (buffer + len,sizeof (buffer) - len,"COMMAND SET:%s;\n" , str);if (len > *lenp) len = *lenp;
@@ -117,7 +117,7 @@ static int do_hardware_base_addr(struct void *result, size_t *lenp, loff_t *ppos) { struct parport *port = (struct parport *)table->extra1; -char buffer[20 ]; +char buffer[64 ];int len =0 ;if (*ppos) {
@@ -128,7 +128,7 @@ static int do_hardware_base_addr(structif (write)/* permissions prevent this anyway */ return -EACCES ; - len +=sprintf (buffer,"%lu\t%lu\n" , port->base, port->base_hi); + len +=snprintf (buffer,sizeof (buffer),"%lu\t%lu\n" , port->base, port->base_hi);if (len > *lenp) len = *lenp;
@@ -155,7 +155,7 @@ static int do_hardware_irq(struct ctl_taif (write)/* permissions prevent this anyway */ return -EACCES ; - len +=sprintf (buffer,"%d\n" , port->irq); + len +=snprintf (buffer,sizeof (buffer),"%d\n" , port->irq);if (len > *lenp) len = *lenp;
@@ -182,7 +182,7 @@ static int do_hardware_dma(struct ctl_taif (write)/* permissions prevent this anyway */ return -EACCES ; - len +=sprintf (buffer,"%d\n" , port->dma); + len +=snprintf (buffer,sizeof (buffer),"%d\n" , port->dma);if (len > *lenp) len = *lenp;
@@ -213,7 +213,7 @@ static int do_hardware_modes(struct ctl_#define printmode (x) \ do { \ if (port->modes & PARPORT_MODE_##x) \ - len += sprintf(buffer + len, "%s%s", f++ ? "," : "", #x); \ + len += snprintf(buffer + len, sizeof(buffer) - len, "%s%s", f++ ? "," : "", #x); \ } while (0)int f =0 ;printmode (PCSPP );
Greg Kroah-Hartman
maintainerPATCH 211/484 fs/ntfs3: Update log->page_{mask,bits} if log->page_size changed
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Huacai Chen <[email protected]>
commit 2fef55d8f78383c8e6d6d4c014b9597375132696 upstream.
If an NTFS file system is mounted to another system with different PAGE_SIZE from the original system, log->page_size will change in log_replay(), but log->page_{mask,bits} don't change correspondingly. This will cause a panic because "u32 bytes = log->page_size - page_off" will get a negative value in the later read_log_page().
--- fs/ntfs3/fslog.c | 3 +++ 1 file changed, 3 insertions(+)
fs/ntfs3/fslog.c +3 -0
@@ -3935,6 +3935,9 @@ init_log_instance: goto out; } + log->page_mask = log->page_size -1 ; + log->page_bits =blksize_bits (log->page_size); +/* If the file size has shrunk then we won't mount it. */ if (l_size <le64_to_cpu (ra2->l_size)) { err = -EINVAL ;
Greg Kroah-Hartman
maintainerPATCH 212/484 scsi: qla2xxx: Return ENOBUFS if sg_cnt is more than one for ELS cmds
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Saurav Kashyap <[email protected]>
commit ce2065c4cc4f05635413f63f6dc038d7d4842e31 upstream.
Firmware only supports single DSDs in ELS Pass-through IOCB (0x53h), sg cnt is decided by the SCSI ML. User is not aware of the cause of an acutal error.
Return the appropriate return code that will be decoded by API and application and proper error message will be displayed to user.
--- drivers/scsi/qla2xxx/qla_bsg.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/qla2xxx/qla_bsg.c +1 -1
@@ -324,7 +324,7 @@ qla2x00_process_els(struct bsg_job *bsg_"request_sg_cnt=%x reply_sg_cnt=%x.\n" , bsg_job->request_payload.sg_cnt, bsg_job->reply_payload.sg_cnt); - rval = -EPERM ; + rval = -ENOBUFS ; goto done; }
Greg Kroah-Hartman
maintainerPATCH 213/484 clk: davinci: da8xx-cfgchip: Initialize clk_init_data before use
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bastien Curutchet <[email protected]>
commit a83b22754e351f13fb46596c85f667dc33da71ec upstream.
The flag attribute of the struct clk_init_data isn't initialized before the devm_clk_hw_register() call. This can lead to unexpected behavior during registration.
Initialize the entire clk_init_data to zero at declaration.
--- drivers/clk/davinci/da8xx-cfgchip.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/clk/davinci/da8xx-cfgchip.c +2 -2
@@ -505,7 +505,7 @@ da8xx_cfgchip_register_usb0_clk48(structconst char *const parent_names[] = {"usb_refclkin" ,"pll0_auxclk" };struct clk *fck_clk;struct da8xx_usb0_clk48 *usb0; -struct clk_init_data init; +struct clk_init_data init = {};int ret; fck_clk =devm_clk_get (dev,"fck" );
@@ -580,7 +580,7 @@ da8xx_cfgchip_register_usb1_clk48(struct {const char *const parent_names[] = {"usb0_clk48" ,"usb_refclkin" };struct da8xx_usb1_clk48 *usb1; -struct clk_init_data init; +struct clk_init_data init = {};int ret; usb1 =devm_kzalloc (dev,sizeof (*usb1),GFP_KERNEL );
Greg Kroah-Hartman
maintainerPATCH 214/484 ubi: eba: properly rollback inside self_check_eba
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Fedor Pchelkin <[email protected]>
commit 745d9f4a31defec731119ee8aad8ba9f2536dd9a upstream.
In case of a memory allocation failure in the volumes loop we can only process the already allocated scan_eba and fm_eba array elements on the error path - others are still uninitialized.
Found by Linux Verification Center (linuxtesting.org).
--- drivers/mtd/ubi/eba.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/mtd/ubi/eba.c +2 -1
@@ -1560,6 +1560,7 @@ int self_check_eba(struct ubi_device *ub GFP_KERNEL);if (!fm_eba[i]) { ret = -ENOMEM ; +kfree (scan_eba[i]); goto out_free; }
@@ -1595,7 +1596,7 @@ int self_check_eba(struct ubi_device *ub } out_free: -for (i =0 ; i < num_volumes; i++) { +while (--i >=0 ) {if (!ubi->volumes[i])continue ;
Greg Kroah-Hartman
maintainerPATCH 215/484 decompress_bunzip2: fix rare decompression failure
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ross Lagerwall <[email protected]>
commit bf6acd5d16057d7accbbb1bf7dc6d8c56eeb4ecc upstream.
The decompression code parses a huffman tree and counts the number of symbols for a given bit length. In rare cases, there may be >= 256 symbols with a given bit length, causing the unsigned char to overflow. This causes a decompression failure later when the code tries and fails to find the bit length for a given symbol.
Since the maximum number of symbols is 258, use unsigned short instead.
--- lib/decompress_bunzip2.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
lib/decompress_bunzip2.c +2 -1
@@ -232,7 +232,8 @@ static int INIT get_next_block(struct buRUNB) */ symCount = symTotal+2 ;for (j =0 ; j < groupCount; j++) { -unsigned char length[MAX_SYMBOLS ], temp[MAX_HUFCODE_BITS +1 ]; +unsigned char length[MAX_SYMBOLS ]; +unsigned short temp[MAX_HUFCODE_BITS +1 ];int minLen, maxLen, pp;/* Read Huffman code lengths for each symbol. They're stored in a way similar to mtf; record a starting
Greg Kroah-Hartman
maintainerPATCH 216/484 kbuild: Fix -S -c in x86 stack protector scripts
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nathan Chancellor <[email protected]>
commit 3415b10a03945b0da4a635e146750dfe5ce0f448 upstream.
After a recent change in clang to stop consuming all instances of '-S' and '-c' [1], the stack protector scripts break due to the kernel's use of -Werror=unused-command-line-argument to catch cases where flags are not being properly consumed by the compiler driver:
$ echo | clang -o - -x c - -S -c -Werror=unused-command-line-argument clang: error: argument unused during compilation: '-c' [-Werror,-Wunused-command-line-argument]
This results in CONFIG_STACKPROTECTOR getting disabled because CONFIG_CC_HAS_SANE_STACKPROTECTOR is no longer set.
'-c' and '-S' both instruct the compiler to stop at different stages of the pipeline ('-S' after compiling, '-c' after assembling), so having them present together in the same command makes little sense. In this case, the test wants to stop before assembling because it is looking at the textual assembly output of the compiler for either '%fs' or '%gs', so remove '-c' from the list of arguments to resolve the error.
All versions of GCC continue to work after this change, along with versions of clang that do or do not contain the change mentioned above.
--- scripts/gcc-x86_32-has-stack-protector.sh | 2 +- scripts/gcc-x86_64-has-stack-protector.sh | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-)
scripts/gcc-x86_32-has-stack-protector.sh +1 -1
@@ -5,4 +5,4 @@ # -mstack-protector-guard-reg, added by # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81708 -echo "int foo(void) { char X[200]; return 3; }" | $* -S -x c -c -m32 -O0 -fstack-protector -mstack-protector-guard-reg=fs -mstack-protector-guard-symbol=__stack_chk_guard - -o - 2> /dev/null | grep -q "%fs" +echo "int foo(void) { char X[200]; return 3; }" | $* -S -x c -m32 -O0 -fstack-protector -mstack-protector-guard-reg=fs -mstack-protector-guard-symbol=__stack_chk_guard - -o - 2> /dev/null | grep -q "%fs"
scripts/gcc-x86_64-has-stack-protector.sh +1 -1
@@ -1,4 +1,4 @@ #!/bin/sh # SPDX-License-Identifier: GPL-2.0 -echo "int foo(void) { char X[200]; return 3; }" | $* -S -x c -c -m64 -O0 -mcmodel=kernel -fno-PIE -fstack-protector - -o - 2> /dev/null | grep -q "%gs" +echo "int foo(void) { char X[200]; return 3; }" | $* -S -x c -m64 -O0 -mcmodel=kernel -fno-PIE -fstack-protector - -o - 2> /dev/null | grep -q "%gs"
Greg Kroah-Hartman
maintainerPATCH 217/484 kobject_uevent: Fix OOB access within zap_modalias_env()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zijun Hu <[email protected]>
commit dd6e9894b451e7c85cceb8e9dc5432679a70e7dc upstream.
zap_modalias_env() wrongly calculates size of memory block to move, so will cause OOB memory access issue if variable MODALIAS is not the last one within its @env parameter, fixed by correcting size to memmove.
--- lib/kobject_uevent.c | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-)
lib/kobject_uevent.c +16 -1
@@ -432,8 +432,23 @@ static void zap_modalias_env(struct kobj len =strlen (env->envp[i]) +1 ;if (i != env->envp_idx -1 ) { +/* @env->envp[] contains pointers to @env->buf[] +* with @env->buflen chars, and we are removing +* variable MODALIAS here pointed by @env->envp[i] +* with length @len as shown below: +* +* 0 @env->buf[] @env->buflen +* --------------------------------------------- +* ^ ^ ^ ^ +* | |-> @len <-| target block | +* @env->envp[0] @env->envp[i] @env->envp[i + 1] +* +* so the "target block" indicated above is moved +* backward by @len, and its right size is +* @env->buflen - (@env->envp[i + 1] - @env->envp[0]). +*/ memmove (env->envp[i], env->envp[i +1 ], - env->buflen - len); + env->buflen - (env->envp[i +1 ] - env->envp[0 ]));for (j = i; j < env->envp_idx -1 ; j++) env->envp[j] = env->envp[j +1 ] - len;
Greg Kroah-Hartman
maintainerPATCH 218/484 gve: Fix an edge case for TSO skb validity check
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bailey Forrest <[email protected]>
commit 36e3b949e35964e22b9a57f960660fc599038dd4 upstream.
The NIC requires each TSO segment to not span more than 10 descriptors. NIC further requires each descriptor to not exceed 16KB - 1 (GVE_TX_MAX_BUF_SIZE_DQO).
The descriptors for an skb are generated by gve_tx_add_skb_no_copy_dqo() for DQO RDA queue format. gve_tx_add_skb_no_copy_dqo() loops through each skb frag and generates a descriptor for the entire frag if the frag size is not greater than GVE_TX_MAX_BUF_SIZE_DQO. If the frag size is greater than GVE_TX_MAX_BUF_SIZE_DQO, it is split into descriptor(s) of size GVE_TX_MAX_BUF_SIZE_DQO and a descriptor is generated for the remainder (frag size % GVE_TX_MAX_BUF_SIZE_DQO).
gve_can_send_tso() checks if the descriptors thus generated for an skb would meet the requirement that each TSO-segment not span more than 10 descriptors. However, the current code misses an edge case when a TSO segment spans multiple descriptors within a large frag. This change fixes the edge case.
gve_can_send_tso() relies on the assumption that max gso size (9728) is less than GVE_TX_MAX_BUF_SIZE_DQO and therefore within an skb fragment a TSO segment can never span more than 2 descriptors.
--- drivers/net/ethernet/google/gve/gve_tx_dqo.c | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-)
drivers/net/ethernet/google/gve/gve_tx_dqo.c +21 -1
@@ -606,22 +606,42 @@ static bool gve_can_send_tso(const strucconst struct skb_shared_info *shinfo =skb_shinfo (skb);const int gso_size = shinfo->gso_size;int cur_seg_num_bufs; +int prev_frag_size;int cur_seg_size;int i; cur_seg_size =skb_headlen (skb) - header_len; + prev_frag_size =skb_headlen (skb); cur_seg_num_bufs = cur_seg_size >0 ;for (i =0 ; i < shinfo->nr_frags; i++) {if (cur_seg_size >= gso_size) { cur_seg_size %= gso_size; cur_seg_num_bufs = cur_seg_size >0 ; + +if (prev_frag_size >GVE_TX_MAX_BUF_SIZE_DQO ) { +int prev_frag_remain = prev_frag_size % +GVE_TX_MAX_BUF_SIZE_DQO ; + +/* If the last descriptor of the previous frag +* is less than cur_seg_size, the segment will +* span two descriptors in the previous frag. +* Since max gso size (9728) is less than +* GVE_TX_MAX_BUF_SIZE_DQO, it is impossible +* for the segment to span more than two +* descriptors. +*/ +if (prev_frag_remain && + cur_seg_size > prev_frag_remain) + cur_seg_num_bufs++; + } }if (unlikely (++cur_seg_num_bufs > max_bufs_per_seg))return false; - cur_seg_size +=skb_frag_size (&shinfo->frags[i]); + prev_frag_size =skb_frag_size (&shinfo->frags[i]); + cur_seg_size += prev_frag_size; }return true;
Greg Kroah-Hartman
maintainerPATCH 219/484 devres: Fix devm_krealloc() wasting memory
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zijun Hu <[email protected]>
commit c884e3249f753dcef7a2b2023541ac1dc46b318e upstream.
Driver API devm_krealloc() calls alloc_dr() with wrong argument @total_new_size, so causes more memory to be allocated than required fix this memory waste by using @new_size as the argument for alloc_dr().
--- drivers/base/devres.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
drivers/base/devres.c +4 -1
@@ -890,9 +890,12 @@ void *devm_krealloc(struct device *dev,/* * Otherwise: allocate new, larger chunk. We need to allocate before * taking the lock as most probably the caller uses GFP_KERNEL. +* alloc_dr() will call check_dr_size() to reserve extra memory +* for struct devres automatically, so size @new_size user request +* is delivered to it directly as devm_kmalloc() does. */ new_dr =alloc_dr (devm_kmalloc_release, - total_new_size, gfp,dev_to_node (dev)); + new_size, gfp,dev_to_node (dev));if (!new_dr)return NULL ;
Greg Kroah-Hartman
maintainerPATCH 220/484 devres: Fix memory leakage caused by driver API devm_free_percpu()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zijun Hu <[email protected]>
commit bd50a974097bb82d52a458bd3ee39fb723129a0c upstream.
It will cause memory leakage when use driver API devm_free_percpu() to free memory allocated by devm_alloc_percpu(), fixed by using devres_release() instead of devres_destroy() within devm_free_percpu().
--- drivers/base/devres.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/base/devres.c +5 -1
@@ -1219,7 +1219,11 @@ EXPORT_SYMBOL_GPL(__devm_alloc_percpu);*/ void devm_free_percpu (struct device *dev,void __percpu *pdata) { -WARN_ON (devres_destroy (dev, devm_percpu_release, devm_percpu_match, +/* +* Use devres_release() to prevent memory leakage as +* devm_free_pages() does. +*/ +WARN_ON (devres_release (dev, devm_percpu_release, devm_percpu_match, (__force void *)pdata)); }EXPORT_SYMBOL_GPL (devm_free_percpu);
Greg Kroah-Hartman
maintainerPATCH 221/484 mm/numa_balancing: teach mpol_to_str about the balancing mode
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tvrtko Ursulin <[email protected]>
commit af649773fb25250cd22625af021fb6275c56a3ee upstream.
Since balancing mode was added in bda420b98505 ("numa balancing: migrate on fault among multiple bound nodes"), it was possible to set this mode but it wouldn't be shown in /proc/<pid>/numa_maps since there was no support for it in the mpol_to_str() helper.
Furthermore, because the balancing mode sets the MPOL_F_MORON flag, it would be displayed as 'default' due a workaround introduced a few years earlier in 8790c71a18e5 ("mm/mempolicy.c: fix mempolicy printing in numa_maps").
To tidy this up we implement two changes:
Replace the MPOL_F_MORON check by pointer comparison against the preferred_node_policy array. By doing this we generalise the current special casing and replace the incorrect 'default' with the correct 'bind' for the mode.
Secondly, we add a string representation and corresponding handling for the MPOL_F_NUMA_BALANCING flag.
With the two changes together we start showing the balancing flag when it is set and therefore complete the fix.
Representation format chosen is to separate multiple flags with vertical bars, following what existed long time ago in kernel 2.6.25. But as between then and now there wasn't a way to display multiple flags, this patch does not change the format in practice.
Some /proc/<pid>/numa_maps output examples:
555559580000 bind=balancing:0-1,3 file=...
555585800000 bind=balancing|static:0,2 file=...
555635240000 prefer=relative:0 file=
References: 8790c71a18e5 ("mm/mempolicy.c: fix mempolicy printing in numa_maps")
--- mm/mempolicy.c | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-)
mm/mempolicy.c +14 -4
@@ -2921,8 +2921,9 @@ out:* @pol: pointer to mempolicy to be formatted * * Convert @pol into a string. If @buffer is too short, truncate the string. -* Recommend a @maxlen of at least 32 for the longest mode, "interleave", the -* longest flag, "relative", and to display at least a few node ids. +* Recommend a @maxlen of at least 51 for the longest mode, "weighted +* interleave", plus the longest flag flags, "relative|balancing", and to +* display at least a few node ids. */ void mpol_to_str (char *buffer,int maxlen,struct mempolicy *pol) {
@@ -2931,7 +2932,10 @@ void mpol_to_str(char *buffer, int maxleunsigned short mode =MPOL_DEFAULT ;unsigned short flags =0 ; -if (pol && pol != &default_policy && !(pol->flags &MPOL_F_MORON )) { +if (pol && + pol != &default_policy && + !(pol >= &preferred_node_policy[0 ] && + pol <= &preferred_node_policy[ARRAY_SIZE (preferred_node_policy) -1 ])) { mode = pol->mode; flags = pol->flags; }
@@ -2958,12 +2962,18 @@ void mpol_to_str(char *buffer, int maxle p +=snprintf (p, buffer + maxlen - p,"=" );/* -* Currently, the only defined flags are mutually exclusive +* Static and relative are mutually exclusive. */ if (flags &MPOL_F_STATIC_NODES ) p +=snprintf (p, buffer + maxlen - p,"static" );else if (flags &MPOL_F_RELATIVE_NODES ) p +=snprintf (p, buffer + maxlen - p,"relative" ); + +if (flags &MPOL_F_NUMA_BALANCING ) { +if (!is_power_of_2 (flags &MPOL_MODE_FLAGS )) + p +=snprintf (p, buffer + maxlen - p,"|" ); + p +=snprintf (p, buffer + maxlen - p,"balancing" ); + } }if (!nodes_empty (nodes))
Greg Kroah-Hartman
maintainerPATCH 222/484 rtc: cmos: Fix return value of nvmem callbacks
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Joy Chakraborty <[email protected]>
commit 1c184baccf0d5e2ef4cc1562261d0e48508a1c2b upstream.
Read/write callbacks registered with nvmem core expect 0 to be returned on success and a negative value to be returned on failure.
cmos_nvram_read()/cmos_nvram_write() currently return the number of bytes read or written, fix to return 0 on success and -EIO incase number of bytes requested was not read or written.
--- drivers/rtc/rtc-cmos.c | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-)
drivers/rtc/rtc-cmos.c +4 -6
@@ -643,11 +643,10 @@ static int cmos_nvram_read(void *priv, u size_t count) {unsigned char *buf = val; -int retval; off +=NVRAM_OFFSET ;spin_lock_irq (&rtc_lock); -for (retval =0 ; count; count--, off++, retval++) { +for (; count; count--, off++) {if (off <128 ) *buf++ =CMOS_READ (off);else if (can_bank2)
@@ -657,7 +656,7 @@ static int cmos_nvram_read(void *priv, u }spin_unlock_irq (&rtc_lock); -return retval; +return count ? -EIO :0 ; } static int cmos_nvram_write(void *priv, unsigned int off, void *val,
@@ -665,7 +664,6 @@ static int cmos_nvram_write(void *priv, {struct cmos_rtc *cmos = priv;unsigned char *buf = val; -int retval;/* NOTE: on at least PCs and Ataris, the boot firmware uses a * checksum on part of the NVRAM data. That's currently ignored
@@ -674,7 +672,7 @@ static int cmos_nvram_write(void *priv,*/ off +=NVRAM_OFFSET ;spin_lock_irq (&rtc_lock); -for (retval =0 ; count; count--, off++, retval++) { +for (; count; count--, off++) {/* don't trash RTC registers */ if (off == cmos->day_alrm || off == cmos->mon_alrm
@@ -689,7 +687,7 @@ static int cmos_nvram_write(void *priv, }spin_unlock_irq (&rtc_lock); -return retval; +return count ? -EIO :0 ; }/*----------------------------------------------------------------*/
Greg Kroah-Hartman
maintainerPATCH 223/484 scsi: qla2xxx: During vport delete send async logout explicitly
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Manish Rangankar <[email protected]>
commit 76f480d7c717368f29a3870f7d64471ce0ff8fb2 upstream.
During vport delete, it is observed that during unload we hit a crash because of stale entries in outstanding command array. For all these stale I/O entries, eh_abort was issued and aborted (fast_fail_io = 2009h) but I/Os could not complete while vport delete is in process of deleting.
BUG: kernel NULL pointer dereference, address: 000000000000001c #PF: supervisor read access in kernel mode #PF: error_code(0x0000) - not-present page PGD 0 P4D 0 Oops: 0000 [#1] PREEMPT SMP NOPTI Workqueue: qla2xxx_wq qla_do_work [qla2xxx] RIP: 0010:dma_direct_unmap_sg+0x51/0x1e0 RSP: 0018:ffffa1e1e150fc68 EFLAGS: 00010046 RAX: 0000000000000000 RBX: 0000000000000021 RCX: 0000000000000001 RDX: 0000000000000021 RSI: 0000000000000000 RDI: ffff8ce208a7a0d0 RBP: ffff8ce208a7a0d0 R08: 0000000000000000 R09: ffff8ce378aac9c8 R10: ffff8ce378aac8a0 R11: ffffa1e1e150f9d8 R12: 0000000000000000 R13: 0000000000000000 R14: ffff8ce378aac9c8 R15: 0000000000000000 FS: 0000000000000000(0000) GS:ffff8d217f000000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 000000000000001c CR3: 0000002089acc000 CR4: 0000000000350ee0 Call Trace: <TASK> qla2xxx_qpair_sp_free_dma+0x417/0x4e0 ? qla2xxx_qpair_sp_compl+0x10d/0x1a0 ? qla2x00_status_entry+0x768/0x2830 ? newidle_balance+0x2f0/0x430 ? dequeue_entity+0x100/0x3c0 ? qla24xx_process_response_queue+0x6a1/0x19e0 ? __schedule+0x2d5/0x1140 ? qla_do_work+0x47/0x60 ? process_one_work+0x267/0x440 ? process_one_work+0x440/0x440 ? worker_thread+0x2d/0x3d0 ? process_one_work+0x440/0x440 ? kthread+0x156/0x180 ? set_kthread_struct+0x50/0x50 ? ret_from_fork+0x22/0x30 </TASK>
Send out async logout explicitly for all the ports during vport delete.
--- drivers/scsi/qla2xxx/qla_mid.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/qla2xxx/qla_mid.c +1 -1
@@ -180,7 +180,7 @@ qla24xx_disable_vp(scsi_qla_host_t *vha)atomic_set (&vha->loop_state,LOOP_DOWN );atomic_set (&vha->loop_down_timer,LOOP_DOWN_TIME );list_for_each_entry (fcport, &vha->vp_fcports, list) - fcport->logout_on_delete =0 ; + fcport->logout_on_delete =1 ;if (!vha->hw->flags.edif_enabled)qla2x00_wait_for_sess_deletion (vha);
Greg Kroah-Hartman
maintainerPATCH 224/484 scsi: qla2xxx: Unable to act on RSCN for port online
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Quinn Tran <[email protected]>
commit c3d98b12eef8db436e32f1a8c5478be57dc15621 upstream.
The device does not come online when the target port is online. There were multiple RSCNs indicating multiple devices were affected. Driver is in the process of finishing a fabric scan. A new RSCN (device up) arrived at the tail end of the last fabric scan. Driver mistakenly thinks the new RSCN is being taken care of by the previous fabric scan, where this notification is cleared and not acted on. The laser needs to be blinked again to get the device to show up.
To prevent driver from accidentally clearing the RSCN notification, each RSCN is given a generation value. A fabric scan will scan for that generation(s). Any new RSCN arrive after the scan start will have a new generation value. This will trigger another scan to get latest data. The RSCN notification flag will be cleared when the scan is associate to that generation.
--- drivers/scsi/qla2xxx/qla_def.h | 3 +++ drivers/scsi/qla2xxx/qla_gs.c | 33 ++++++++++++++++++++++++++++++--- drivers/scsi/qla2xxx/qla_init.c | 24 +++++++++++++++++++----- drivers/scsi/qla2xxx/qla_inline.h | 8 ++++++++ 4 files changed, 60 insertions(+), 8 deletions(-)
drivers/scsi/qla2xxx/qla_def.h +3 -0
@@ -3264,6 +3264,8 @@ struct fab_scan_rp {struct fab_scan {struct fab_scan_rp *l;u32 size; +u32 rscn_gen_start; +u32 rscn_gen_end;u16 scan_retry;#define MAX_SCAN_RETRIES 5enum scan_flags_t scan_flags;
@@ -4971,6 +4973,7 @@ typedef struct scsi_qla_host {/* Counter to detect races between ELS and RSCN events */ atomic_t generation_tick; +atomic_t rscn_gen;/* Time when global fcport update has been scheduled */ int total_fcport_update_gen;/* List of pending LOGOs, protected by tgt_mutex */
drivers/scsi/qla2xxx/qla_gs.c +30 -3
@@ -3464,6 +3464,29 @@ static int qla2x00_is_a_vp(scsi_qla_hostreturn rc; } +static bool qla_ok_to_clear_rscn (scsi_qla_host_t *vha,fc_port_t *fcport) +{ +u32 rscn_gen; + + rscn_gen =atomic_read (&vha->rscn_gen); +ql_dbg (ql_dbg_disc + ql_dbg_verbose, vha,0x2017 , +"%s %d %8phC rscn_gen %x start %x end %x current %x\n" , + __func__, __LINE__, fcport->port_name, fcport->rscn_gen, + vha->scan.rscn_gen_start, vha->scan.rscn_gen_end, rscn_gen); + +if (val_is_in_range (fcport->rscn_gen, vha->scan.rscn_gen_start, + vha->scan.rscn_gen_end)) +/* rscn came in before fabric scan */ +return true; + +if (val_is_in_range (fcport->rscn_gen, vha->scan.rscn_gen_end, rscn_gen)) +/* rscn came in after fabric scan */ +return false; + +/* rare: fcport's scan_needed + rscn_gen must be stale */ +return true; +} +void qla24xx_async_gnnft_done (scsi_qla_host_t *vha,srb_t *sp) {fc_port_t *fcport;
@@ -3577,10 +3600,10 @@ void qla24xx_async_gnnft_done(scsi_qla_h (fcport->scan_needed && fcport->port_type != FCT_INITIATOR && fcport->port_type != FCT_NVME_INITIATOR)) { + fcport->scan_needed =0 ;qlt_schedule_sess_for_deletion (fcport); } fcport->d_id.b24 = rp->id.b24; - fcport->scan_needed =0 ;break ; }
@@ -3621,7 +3644,9 @@ login_logout: do_delete = true; } - fcport->scan_needed =0 ; +if (qla_ok_to_clear_rscn (vha, fcport)) + fcport->scan_needed =0 ; + if (((qla_dual_mode_enabled(vha) || qla_ini_mode_enabled(vha)) && atomic_read(&fcport->state) == FCS_ONLINE) ||
@@ -3651,7 +3676,9 @@ login_logout: fcport->port_name, fcport->loop_id, fcport->login_retry); } - fcport->scan_needed =0 ; + +if (qla_ok_to_clear_rscn (vha, fcport)) + fcport->scan_needed =0 ;qla24xx_fcport_handle_login (vha, fcport); } }
drivers/scsi/qla2xxx/qla_init.c +19 -5
@@ -1845,10 +1845,18 @@ int qla24xx_post_newsess_work(struct scsreturn qla2x00_post_work (vha, e); } +static void qla_rscn_gen_tick (scsi_qla_host_t *vha,u32 *ret_rscn_gen) +{ + *ret_rscn_gen =atomic_inc_return (&vha->rscn_gen); +/* memory barrier */ +wmb (); +} +void qla2x00_handle_rscn (scsi_qla_host_t *vha,struct event_arg *ea) {fc_port_t *fcport;unsigned long flags; +u32 rscn_gen;switch (ea->id.b.rsvd_1) {case RSCN_PORT_ADDR :
@@ -1877,15 +1885,16 @@ void qla2x00_handle_rscn(scsi_qla_host_t* Otherwise we're already in the middle of a relogin */ fcport->scan_needed =1 ; - fcport->rscn_gen++; +qla_rscn_gen_tick (vha, &fcport->rscn_gen); } }else { fcport->scan_needed =1 ; - fcport->rscn_gen++; +qla_rscn_gen_tick (vha, &fcport->rscn_gen); } }break ;case RSCN_AREA_ADDR : +qla_rscn_gen_tick (vha, &rscn_gen);list_for_each_entry (fcport, &vha->vp_fcports, list) {if (fcport->flags &FCF_FCP2_DEVICE &&atomic_read (&fcport->state) ==FCS_ONLINE )
@@ -1893,11 +1902,12 @@ void qla2x00_handle_rscn(scsi_qla_host_tif ((ea->id.b24 &0xffff00 ) == (fcport->d_id.b24 &0xffff00 )) { fcport->scan_needed =1 ; - fcport->rscn_gen++; + fcport->rscn_gen = rscn_gen; } }break ;case RSCN_DOM_ADDR : +qla_rscn_gen_tick (vha, &rscn_gen);list_for_each_entry (fcport, &vha->vp_fcports, list) {if (fcport->flags &FCF_FCP2_DEVICE &&atomic_read (&fcport->state) ==FCS_ONLINE )
@@ -1905,19 +1915,20 @@ void qla2x00_handle_rscn(scsi_qla_host_tif ((ea->id.b24 &0xff0000 ) == (fcport->d_id.b24 &0xff0000 )) { fcport->scan_needed =1 ; - fcport->rscn_gen++; + fcport->rscn_gen = rscn_gen; } }break ;case RSCN_FAB_ADDR :default : +qla_rscn_gen_tick (vha, &rscn_gen);list_for_each_entry (fcport, &vha->vp_fcports, list) {if (fcport->flags &FCF_FCP2_DEVICE &&atomic_read (&fcport->state) ==FCS_ONLINE )continue ; fcport->scan_needed =1 ; - fcport->rscn_gen++; + fcport->rscn_gen = rscn_gen; }break ; }
@@ -1926,6 +1937,7 @@ void qla2x00_handle_rscn(scsi_qla_host_tif (vha->scan.scan_flags ==0 ) {ql_dbg (ql_dbg_disc, vha,0xffff ,"%s: schedule\n" , __func__); vha->scan.scan_flags |=SF_QUEUED ; + vha->scan.rscn_gen_start =atomic_read (&vha->rscn_gen);schedule_delayed_work (&vha->scan.scan_work,5 ); }spin_unlock_irqrestore (&vha->work_lock, flags);
@@ -6423,6 +6435,8 @@ qla2x00_configure_fabric(scsi_qla_host_tqlt_do_generation_tick (vha, &discovery_gen);if (USE_ASYNC_SCAN (ha)) { +/* start of scan begins here */ + vha->scan.rscn_gen_end =atomic_read (&vha->rscn_gen); rval =qla24xx_async_gpnft (vha,FC4_TYPE_FCP_SCSI ,NULL );if (rval)
drivers/scsi/qla2xxx/qla_inline.h +8 -0
@@ -631,3 +631,11 @@ static inline int qla_mapq_alloc_qp_cpu_ }return 0 ; } + +static inline bool val_is_in_range (u32 val,u32 start,u32 end) +{ +if (val >= start && val <= end) +return true; +else +return false; +}
Greg Kroah-Hartman
maintainerPATCH 225/484 scsi: qla2xxx: Fix for possible memory corruption
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Shreyas Deodhar <[email protected]>
commit c03d740152f78e86945a75b2ad541bf972fab92a upstream.
Init Control Block is dereferenced incorrectly. Correctly dereference ICB
--- drivers/scsi/qla2xxx/qla_os.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/qla2xxx/qla_os.c +1 -1
@@ -4634,7 +4634,7 @@ static void qla2x00_number_of_exch(scsi_qla_host_t *vha, u32 *ret_cnt, u16 max_cnt) {u32 temp; -struct init_cb_81xx *icb = (struct init_cb_81xx *)&vha->hw->init_cb; +struct init_cb_81xx *icb = (struct init_cb_81xx *)vha->hw->init_cb; *ret_cnt =FW_DEF_EXCHANGES_CNT ;if (max_cnt > vha->hw->max_exchg)
Greg Kroah-Hartman
maintainerPATCH 226/484 scsi: qla2xxx: Use QP lock to search for bsg
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Quinn Tran <[email protected]>
commit c449b4198701d828e40d60a2abd30970b74a1d75 upstream.
On bsg timeout, hardware_lock is used as part of search for the srb. Instead, qpair lock should be used to iterate through different qpair.
--- drivers/scsi/qla2xxx/qla_bsg.c | 96 ++++++++++++++++++++++++----------------- 1 file changed, 57 insertions(+), 39 deletions(-)
drivers/scsi/qla2xxx/qla_bsg.c +57 -39
@@ -2966,17 +2966,61 @@ skip_chip_chk:return ret; } -int -qla24xx_bsg_timeout (struct bsg_job *bsg_job) +static bool qla_bsg_found (struct qla_qpair *qpair,struct bsg_job *bsg_job) { +bool found = false;struct fc_bsg_reply *bsg_reply = bsg_job->reply;scsi_qla_host_t *vha =shost_priv (fc_bsg_to_shost (bsg_job));struct qla_hw_data *ha = vha->hw; -srb_t *sp; -int cnt, que; +srb_t *sp =NULL ; +int cnt;unsigned long flags;struct req_que *req; +spin_lock_irqsave (qpair->qp_lock_ptr, flags); + req = qpair->req; + +for (cnt =1 ; cnt < req->num_outstanding_cmds; cnt++) { + sp = req->outstanding_cmds[cnt]; +if (sp && + (sp->type ==SRB_CT_CMD || + sp->type ==SRB_ELS_CMD_HST || + sp->type ==SRB_ELS_CMD_HST_NOLOGIN ) && + sp->u.bsg_job == bsg_job) { + req->outstanding_cmds[cnt] =NULL ; +spin_unlock_irqrestore (qpair->qp_lock_ptr, flags); + +if (!ha->flags.eeh_busy && ha->isp_ops->abort_command (sp)) { +ql_log (ql_log_warn, vha,0x7089 , +"mbx abort_command failed.\n" ); + bsg_reply->result = -EIO ; + }else { +ql_dbg (ql_dbg_user, vha,0x708a , +"mbx abort_command success.\n" ); + bsg_reply->result =0 ; + } +/* ref: INIT */ +kref_put (&sp->cmd_kref, qla2x00_sp_release); + + found = true; + goto done; + } + } +spin_unlock_irqrestore (qpair->qp_lock_ptr, flags); + +done: +return found; +} + +int +qla24xx_bsg_timeout (struct bsg_job *bsg_job) +{ +struct fc_bsg_reply *bsg_reply = bsg_job->reply; +scsi_qla_host_t *vha =shost_priv (fc_bsg_to_shost (bsg_job)); +struct qla_hw_data *ha = vha->hw; +int i; +struct qla_qpair *qpair; +ql_log (ql_log_info, vha,0x708b ,"%s CMD timeout. bsg ptr %p.\n" , __func__, bsg_job);
@@ -2986,47 +3030,21 @@ qla24xx_bsg_timeout(struct bsg_job *bsg_qla_pci_set_eeh_busy (vha); } +if (qla_bsg_found (ha->base_qpair, bsg_job)) + goto done; +/* find the bsg job from the active list of commands */ -spin_lock_irqsave (&ha->hardware_lock, flags); -for (que =0 ; que < ha->max_req_queues; que++) { - req = ha->req_q_map[que]; -if (!req) +for (i =0 ; i < ha->max_qpairs; i++) { + qpair = vha->hw->queue_pair_map[i]; +if (!qpair)continue ; - -for (cnt =1 ; cnt < req->num_outstanding_cmds; cnt++) { - sp = req->outstanding_cmds[cnt]; -if (sp && - (sp->type ==SRB_CT_CMD || - sp->type ==SRB_ELS_CMD_HST || - sp->type ==SRB_ELS_CMD_HST_NOLOGIN || - sp->type ==SRB_FXIOCB_BCMD ) && - sp->u.bsg_job == bsg_job) { - req->outstanding_cmds[cnt] =NULL ; -spin_unlock_irqrestore (&ha->hardware_lock, flags); - -if (!ha->flags.eeh_busy && ha->isp_ops->abort_command (sp)) { -ql_log (ql_log_warn, vha,0x7089 , -"mbx abort_command failed.\n" ); - bsg_reply->result = -EIO ; - }else { -ql_dbg (ql_dbg_user, vha,0x708a , -"mbx abort_command success.\n" ); - bsg_reply->result =0 ; - } -spin_lock_irqsave (&ha->hardware_lock, flags); - goto done; - - } - } +if (qla_bsg_found (qpair, bsg_job)) + goto done; } -spin_unlock_irqrestore (&ha->hardware_lock, flags); +ql_log (ql_log_info, vha,0x708b ,"SRB not found to abort.\n" ); bsg_reply->result = -ENXIO ; -return 0 ; done: -spin_unlock_irqrestore (&ha->hardware_lock, flags); -/* ref: INIT */ -kref_put (&sp->cmd_kref, qla2x00_sp_release);return 0 ; }
Greg Kroah-Hartman
maintainerPATCH 227/484 scsi: qla2xxx: Fix flash read failure
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Quinn Tran <[email protected]>
commit 29e222085d8907ccff18ecd931bdd4c6b1f11b92 upstream.
Link up failure is observed as a result of flash read failure. Current code does not check flash read return code where it relies on FW checksum to detect the problem.
Add check of flash read failure to detect the problem sooner.
--- drivers/scsi/qla2xxx/qla_init.c | 63 ++++++++++++++++++----- drivers/scsi/qla2xxx/qla_sup.c | 108 +++++++++++++++++++++++++++------------- 2 files changed, 125 insertions(+), 46 deletions(-)
drivers/scsi/qla2xxx/qla_init.c +50 -13
@@ -8296,15 +8296,21 @@ qla28xx_get_aux_images(struct qla27xx_image_status pri_aux_image_status, sec_aux_image_status;bool valid_pri_image = false, valid_sec_image = false;bool active_pri_image = false, active_sec_image = false; +int rc;if (!ha->flt_region_aux_img_status_pri) {ql_dbg (ql_dbg_init, vha,0x018a ,"Primary aux image not addressed\n" ); goto check_sec_image; } -qla24xx_read_flash_data (vha, (uint32_t *)&pri_aux_image_status, + rc =qla24xx_read_flash_data (vha, (uint32_t *)&pri_aux_image_status, ha->flt_region_aux_img_status_pri,sizeof (pri_aux_image_status) >>2 ); +if (rc) { +ql_log (ql_log_info, vha,0x01a1 , +"Unable to read Primary aux image(%x).\n" , rc); + goto check_sec_image; + }qla27xx_print_image (vha,"Primary aux image" , &pri_aux_image_status);if (qla28xx_check_aux_image_status_signature (&pri_aux_image_status)) {
@@ -8335,9 +8341,15 @@ check_sec_image: goto check_valid_image; } -qla24xx_read_flash_data (vha, (uint32_t *)&sec_aux_image_status, + rc =qla24xx_read_flash_data (vha, (uint32_t *)&sec_aux_image_status, ha->flt_region_aux_img_status_sec,sizeof (sec_aux_image_status) >>2 ); +if (rc) { +ql_log (ql_log_info, vha,0x01a2 , +"Unable to read Secondary aux image(%x).\n" , rc); + goto check_valid_image; + } +qla27xx_print_image (vha,"Secondary aux image" , &sec_aux_image_status);if (qla28xx_check_aux_image_status_signature (&sec_aux_image_status)) {
@@ -8394,6 +8406,7 @@ qla27xx_get_active_image(struct scsi_qlastruct qla27xx_image_status pri_image_status, sec_image_status;bool valid_pri_image = false, valid_sec_image = false;bool active_pri_image = false, active_sec_image = false; +int rc;if (!ha->flt_region_img_status_pri) {ql_dbg (ql_dbg_init, vha,0x018a ,"Primary image not addressed\n" );
@@ -8435,8 +8448,14 @@ check_sec_image: goto check_valid_image; } -qla24xx_read_flash_data (vha, (uint32_t *)(&sec_image_status), + rc =qla24xx_read_flash_data (vha, (uint32_t *)(&sec_image_status), ha->flt_region_img_status_sec,sizeof (sec_image_status) >>2 ); +if (rc) { +ql_log (ql_log_info, vha,0x01a3 , +"Unable to read Secondary image status(%x).\n" , rc); + goto check_valid_image; + } +qla27xx_print_image (vha,"Secondary image" , &sec_image_status);if (qla27xx_check_image_status_signature (&sec_image_status)) {
@@ -8508,11 +8527,10 @@ qla24xx_load_risc_flash(scsi_qla_host_t "FW: Loading firmware from flash (%x).\n", faddr); dcode = (uint32_t *)req->ring; -qla24xx_read_flash_data (vha, dcode, faddr,8 ); -if (qla24xx_risc_firmware_invalid (dcode)) { + rval =qla24xx_read_flash_data (vha, dcode, faddr,8 ); +if (rval ||qla24xx_risc_firmware_invalid (dcode)) {ql_log (ql_log_fatal, vha,0x008c , -"Unable to verify the integrity of flash firmware " -"image.\n" ); +"Unable to verify the integrity of flash firmware image (rval %x).\n" , rval);ql_log (ql_log_fatal, vha,0x008d ,"Firmware data: %08x %08x %08x %08x.\n" , dcode[0 ], dcode[1 ], dcode[2 ], dcode[3 ]);
@@ -8526,7 +8544,12 @@ qla24xx_load_risc_flash(scsi_qla_host_tfor (j =0 ; j < segments; j++) {ql_dbg (ql_dbg_init, vha,0x008d ,"-> Loading segment %u...\n" , j); -qla24xx_read_flash_data (vha, dcode, faddr,10 ); + rval =qla24xx_read_flash_data (vha, dcode, faddr,10 ); +if (rval) { +ql_log (ql_log_fatal, vha,0x016a , +"-> Unable to read segment addr + size .\n" ); +return QLA_FUNCTION_FAILED ; + } risc_addr =be32_to_cpu ((__force __be32 )dcode[2 ]); risc_size =be32_to_cpu ((__force __be32 )dcode[3 ]);if (!*srisc_addr) {
@@ -8542,7 +8565,13 @@ qla24xx_load_risc_flash(scsi_qla_host_tql_dbg (ql_dbg_init, vha,0x008e ,"-> Loading fragment %u: %#x <- %#x (%#lx dwords)...\n" , fragment, risc_addr, faddr, dlen); -qla24xx_read_flash_data (vha, dcode, faddr, dlen); + rval =qla24xx_read_flash_data (vha, dcode, faddr, dlen); +if (rval) { +ql_log (ql_log_fatal, vha,0x016b , +"-> Unable to read fragment(faddr %#x dlen %#lx).\n" , + faddr, dlen); +return QLA_FUNCTION_FAILED ; + }for (i =0 ; i < dlen; i++) dcode[i] =swab32 (dcode[i]);
@@ -8571,7 +8600,14 @@ qla24xx_load_risc_flash(scsi_qla_host_t fwdt->length =0 ; dcode = (uint32_t *)req->ring; -qla24xx_read_flash_data (vha, dcode, faddr,7 ); + + rval =qla24xx_read_flash_data (vha, dcode, faddr,7 ); +if (rval) { +ql_log (ql_log_fatal, vha,0x016c , +"-> Unable to read template size.\n" ); + goto failed; + } + risc_size =be32_to_cpu ((__force __be32 )dcode[2 ]); ql_dbg(ql_dbg_init, vha, 0x0161, "-> fwdt%u template array at %#x (%#x dwords)\n",
@@ -8597,11 +8633,12 @@ qla24xx_load_risc_flash(scsi_qla_host_t } dcode = fwdt->template; -qla24xx_read_flash_data (vha, dcode, faddr, risc_size); + rval =qla24xx_read_flash_data (vha, dcode, faddr, risc_size); -if (!qla27xx_fwdt_template_valid (dcode)) { +if (rval || !qla27xx_fwdt_template_valid (dcode)) {ql_log (ql_log_warn, vha,0x0165 , -"-> fwdt%u failed template validate\n" , j); +"-> fwdt%u failed template validate (rval %x)\n" , + j, rval); goto failed; }
drivers/scsi/qla2xxx/qla_sup.c +75 -33
188 lines not on this page · raw message
Greg Kroah-Hartman
maintainerPATCH 228/484 scsi: qla2xxx: Complete command early within lock
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Shreyas Deodhar <[email protected]>
commit 4475afa2646d3fec176fc4d011d3879b26cb26e3 upstream.
A crash was observed while performing NPIV and FW reset,
BUG: kernel NULL pointer dereference, address: 000000000000001c #PF: supervisor read access in kernel mode #PF: error_code(0x0000) - not-present page PGD 0 P4D 0 Oops: 0000 1 PREEMPT_RT SMP NOPTI RIP: 0010:dma_direct_unmap_sg+0x51/0x1e0 RSP: 0018:ffffc90026f47b88 EFLAGS: 00010246 RAX: 0000000000000000 RBX: 0000000000000021 RCX: 0000000000000002 RDX: 0000000000000021 RSI: 0000000000000000 RDI: ffff8881041130d0 RBP: ffff8881041130d0 R08: 0000000000000000 R09: 0000000000000034 R10: ffffc90026f47c48 R11: 0000000000000031 R12: 0000000000000000 R13: 0000000000000000 R14: ffff8881565e4a20 R15: 0000000000000000 FS: 00007f4c69ed3d00(0000) GS:ffff889faac80000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 000000000000001c CR3: 0000000288a50002 CR4: 00000000007706e0 DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 PKRU: 55555554 Call Trace: <TASK> ? __die_body+0x1a/0x60 ? page_fault_oops+0x16f/0x4a0 ? do_user_addr_fault+0x174/0x7f0 ? exc_page_fault+0x69/0x1a0 ? asm_exc_page_fault+0x22/0x30 ? dma_direct_unmap_sg+0x51/0x1e0 ? preempt_count_sub+0x96/0xe0 qla2xxx_qpair_sp_free_dma+0x29f/0x3b0 [qla2xxx] qla2xxx_qpair_sp_compl+0x60/0x80 [qla2xxx] __qla2x00_abort_all_cmds+0xa2/0x450 [qla2xxx]
The command completion was done early while aborting the commands in driver unload path but outside lock to avoid the WARN_ON condition of performing dma_free_attr within the lock. However this caused race condition while command completion via multiple paths causing system crash.
Hence complete the command early in unload path but within the lock to avoid race condition.
--- drivers/scsi/qla2xxx/qla_os.c | 5 ----- 1 file changed, 5 deletions(-)
drivers/scsi/qla2xxx/qla_os.c +0 -5
@@ -1861,14 +1861,9 @@ __qla2x00_abort_all_cmds(struct qla_qpaifor (cnt =1 ; cnt < req->num_outstanding_cmds; cnt++) { sp = req->outstanding_cmds[cnt];if (sp) { -/* -* perform lockless completion during driver unload -*/ if (qla2x00_chip_is_down (vha)) { req->outstanding_cmds[cnt] =NULL ; -spin_unlock_irqrestore (qp->qp_lock_ptr, flags); sp->done (sp, res); -spin_lock_irqsave (qp->qp_lock_ptr, flags);continue ; }
Greg Kroah-Hartman
maintainerPATCH 229/484 scsi: qla2xxx: validate nvme_local_port correctly
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nilesh Javali <[email protected]>
commit eb1d4ce2609584eeb7694866f34d4b213caa3af9 upstream.
The driver load failed with error message,
qla2xxx [0000:04:00.0]-ffff:0: register_localport failed: ret=ffffffef
and with a kernel crash,
BUG: unable to handle kernel NULL pointer dereference at 0000000000000070 Workqueue: events_unbound qla_register_fcport_fn [qla2xxx] RIP: 0010:nvme_fc_register_remoteport+0x16/0x430 [nvme_fc] RSP: 0018:ffffaaa040eb3d98 EFLAGS: 00010282 RAX: 0000000000000000 RBX: ffff9dfb46b78c00 RCX: 0000000000000000 RDX: ffff9dfb46b78da8 RSI: ffffaaa040eb3e08 RDI: 0000000000000000 RBP: ffff9dfb612a0a58 R08: ffffffffaf1d6270 R09: 3a34303a30303030 R10: 34303a303030305b R11: 2078787832616c71 R12: ffff9dfb46b78dd4 R13: ffff9dfb46b78c24 R14: ffff9dfb41525300 R15: ffff9dfb46b78da8 FS: 0000000000000000(0000) GS:ffff9dfc67c00000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000000000070 CR3: 000000018da10004 CR4: 00000000000206f0 Call Trace: qla_nvme_register_remote+0xeb/0x1f0 [qla2xxx] ? qla2x00_dfs_create_rport+0x231/0x270 [qla2xxx] qla2x00_update_fcport+0x2a1/0x3c0 [qla2xxx] qla_register_fcport_fn+0x54/0xc0 [qla2xxx]
Exit the qla_nvme_register_remote() function when qla_nvme_register_hba() fails and correctly validate nvme_local_port.
--- drivers/scsi/qla2xxx/qla_nvme.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
drivers/scsi/qla2xxx/qla_nvme.c +4 -1
@@ -27,7 +27,10 @@ int qla_nvme_register_remote(struct scsireturn 0 ; } -if (!vha->nvme_local_port &&qla_nvme_register_hba (vha)) +if (qla_nvme_register_hba (vha)) +return 0 ; + +if (!vha->nvme_local_port)return 0 ; if (!(fcport->nvme_prli_service_param &
Greg Kroah-Hartman
maintainerPATCH 230/484 perf: Fix event leak upon exit
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Frederic Weisbecker <[email protected]>
commit 2fd5ad3f310de22836cdacae919dd99d758a1f1b upstream.
When a task is scheduled out, pending sigtrap deliveries are deferred to the target task upon resume to userspace via task_work.
However failures while adding an event's callback to the task_work engine are ignored. And since the last call for events exit happen after task work is eventually closed, there is a small window during which pending sigtrap can be queued though ignored, leaking the event refcount addition such as in the following scenario:
TASK A
-----
do_exit()
exit_task_work(tsk);
<IRQ>
perf_event_overflow()
event->pending_sigtrap = pending_id;
irq_work_queue(&event->pending_irq);
</IRQ>
=========> PREEMPTION: TASK A -> TASK B
event_sched_out()
event->pending_sigtrap = 0;
atomic_long_inc_not_zero(&event->refcount)
// FAILS: task work has exited
task_work_add(&event->pending_task)
[...]
<IRQ WORK>
perf_pending_irq()
// early return: event->oncpu = -1
</IRQ WORK>
[...]
=========> TASK B -> TASK A
perf_event_exit_task(tsk)
perf_event_exit_event()
free_event()
WARN(atomic_long_cmpxchg(&event->refcount, 1, 0) != 1)
// leak event due to unexpected refcount == 2As a result the event is never released while the task exits.
Fix this with appropriate task_work_add()'s error handling.
--- kernel/events/core.c | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-)
kernel/events/core.c +5 -8
@@ -2395,18 +2395,15 @@ event_sched_out(struct perf_event *event }if (event->pending_sigtrap) { -bool dec = true; - event->pending_sigtrap =0 ;if (state !=PERF_EVENT_STATE_OFF && - !event->pending_work) { - event->pending_work =1 ; - dec = false; + !event->pending_work && + !task_work_add (current, &event->pending_task,TWA_RESUME )) {WARN_ON_ONCE (!atomic_long_inc_not_zero (&event->refcount)); -task_work_add (current, &event->pending_task,TWA_RESUME ); - } -if (dec) + event->pending_work =1 ; + }else {local_dec (&event->ctx->nr_pending); + } }perf_event_set_state (event, state);
Greg Kroah-Hartman
maintainerPATCH 231/484 perf: Fix event leak upon exec and file release
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Frederic Weisbecker <[email protected]>
commit 3a5465418f5fd970e86a86c7f4075be262682840 upstream.
The perf pending task work is never waited upon the matching event release. In the case of a child event, released via free_event() directly, this can potentially result in a leaked event, such as in the following scenario that doesn't even require a weak IRQ work implementation to trigger:
schedule()
prepare_task_switch()
=======> <NMI>
perf_event_overflow()
event->pending_sigtrap = ...
irq_work_queue(&event->pending_irq)
<======= </NMI>
perf_event_task_sched_out()
event_sched_out()
event->pending_sigtrap = 0;
atomic_long_inc_not_zero(&event->refcount)
task_work_add(&event->pending_task)
finish_lock_switch()
=======> <IRQ>
perf_pending_irq()
//do nothing, rely on pending task work<======= </IRQ>
begin_new_exec()
perf_event_exit_task()
perf_event_exit_event()
// If is child event
free_event()
WARN(atomic_long_cmpxchg(&event->refcount, 1, 0) != 1)
// event is leakedSimilar scenarios can also happen with perf_event_remove_on_exec() or simply against concurrent perf_event_release().
Fix this with synchonizing against the possibly remaining pending task work while freeing the event, just like is done with remaining pending IRQ work. This means that the pending task callback neither need nor should hold a reference to the event, preventing it from ever beeing freed.
--- include/linux/perf_event.h | 1 + kernel/events/core.c | 38 ++++++++++++++++++++++++++++++++++---- 2 files changed, 35 insertions(+), 4 deletions(-)
include/linux/perf_event.h +1 -0
@@ -732,6 +732,7 @@ struct perf_event {struct irq_work pending_irq;struct callback_head pending_task;unsigned int pending_work; +struct rcuwait pending_work_wait;atomic_t event_limit;
kernel/events/core.c +34 -4
@@ -2399,7 +2399,6 @@ event_sched_out(struct perf_event *eventif (state !=PERF_EVENT_STATE_OFF && !event->pending_work && !task_work_add (current, &event->pending_task,TWA_RESUME )) { -WARN_ON_ONCE (!atomic_long_inc_not_zero (&event->refcount)); event->pending_work =1 ; }else {local_dec (&event->ctx->nr_pending);
@@ -5098,9 +5097,35 @@ static bool exclusive_event_installable(static void perf_addr_filters_splice (struct perf_event *event,struct list_head *head); +static void perf_pending_task_sync (struct perf_event *event) +{ +struct callback_head *head = &event->pending_task; + +if (!event->pending_work) +return ; +/* +* If the task is queued to the current task's queue, we +* obviously can't wait for it to complete. Simply cancel it. +*/ +if (task_work_cancel (current, head)) { + event->pending_work =0 ; +local_dec (&event->ctx->nr_pending); +return ; + } + +/* +* All accesses related to the event are within the same +* non-preemptible section in perf_pending_task(). The RCU +* grace period before the event is freed will make sure all +* those accesses are complete by then. +*/ +rcuwait_wait_event (&event->pending_work_wait, !event->pending_work,TASK_UNINTERRUPTIBLE ); +} +static void _free_event (struct perf_event *event) {irq_work_sync (&event->pending_irq); +perf_pending_task_sync (event);unaccount_event (event);
@@ -6731,23 +6756,27 @@ static void perf_pending_task(struct calint rctx;/* +* All accesses to the event must belong to the same implicit RCU read-side +* critical section as the ->pending_work reset. See comment in +* perf_pending_task_sync(). +*/ +preempt_disable_notrace (); +/* * If we 'fail' here, that's OK, it means recursion is already disabled * and we won't recurse 'further'. */ -preempt_disable_notrace (); rctx =perf_swevent_get_recursion_context ();if (event->pending_work) { event->pending_work =0 ;perf_sigtrap (event);local_dec (&event->ctx->nr_pending); +rcuwait_wake_up (&event->pending_work_wait); }if (rctx >=0 )perf_swevent_put_recursion_context (rctx);preempt_enable_notrace (); - -put_event (event); }/*
@@ -11785,6 +11814,7 @@ perf_event_alloc(struct perf_event_attrinit_waitqueue_head (&event->waitq);init_irq_work (&event->pending_irq, perf_pending_irq);init_task_work (&event->pending_task, perf_pending_task); +rcuwait_init (&event->pending_work_wait);mutex_init (&event->mmap_mutex);raw_spin_lock_init (&event->addr_filters.lock);
Greg Kroah-Hartman
maintainerPATCH 232/484 perf/x86/intel/uncore: Fix the bits of the CHA extended umask for SPR
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kan Liang <[email protected]>
commit a5a6ff3d639d088d4af7e2935e1ee0d8b4e817d4 upstream.
The perf stat errors out with UNC_CHA_TOR_INSERTS.IA_HIT_CXL_ACC_LOCAL event.
$perf stat -e uncore_cha_55/event=0x35,umask=0x10c0008101/ -a -- ls
event syntax error: '..0x35,umask=0x10c0008101/'
\___ Bad event or PMU
The definition of the CHA umask is config:8-15,32-55, which is 32bit. However, the umask of the event is bigger than 32bit.
This is an error in the original uncore spec.
Add a new umask_ext5 for the new CHA umask range.
--- arch/x86/events/intel/uncore_snbep.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
arch/x86/events/intel/uncore_snbep.c +4 -2
@@ -459,6 +459,7 @@#define SPR_RAW_EVENT_MASK_EXT 0xffffff/* SPR CHA */ +#define SPR_CHA_EVENT_MASK_EXT 0xffffffff#define SPR_CHA_PMON_CTL_TID_EN (1 << 16)#define SPR_CHA_PMON_EVENT_MASK (SNBEP_PMON_RAW_EVENT_MASK | \ SPR_CHA_PMON_CTL_TID_EN)
@@ -475,6 +476,7 @@ DEFINE_UNCORE_FORMAT_ATTR(umask_ext, umaDEFINE_UNCORE_FORMAT_ATTR (umask_ext2, umask,"config:8-15,32-57" );DEFINE_UNCORE_FORMAT_ATTR (umask_ext3, umask,"config:8-15,32-39" );DEFINE_UNCORE_FORMAT_ATTR (umask_ext4, umask,"config:8-15,32-55" ); +DEFINE_UNCORE_FORMAT_ATTR (umask_ext5, umask,"config:8-15,32-63" );DEFINE_UNCORE_FORMAT_ATTR (qor, qor,"config:16" );DEFINE_UNCORE_FORMAT_ATTR (edge, edge,"config:18" );DEFINE_UNCORE_FORMAT_ATTR (tid_en, tid_en,"config:19" );
@@ -5648,7 +5650,7 @@ static struct intel_uncore_ops spr_uncorstatic struct attribute *spr_uncore_cha_formats_attr[] = { &format_attr_event.attr, - &format_attr_umask_ext4.attr, + &format_attr_umask_ext5.attr, &format_attr_tid_en2.attr, &format_attr_edge.attr, &format_attr_inv.attr,
@@ -5684,7 +5686,7 @@ ATTRIBUTE_GROUPS(uncore_alias);static struct intel_uncore_type spr_uncore_chabox = { .name ="cha" , .event_mask =SPR_CHA_PMON_EVENT_MASK , - .event_mask_ext =SPR_RAW_EVENT_MASK_EXT , + .event_mask_ext =SPR_CHA_EVENT_MASK_EXT , .num_shared_regs =1 , .constraints = skx_uncore_chabox_constraints, .ops = &spr_uncore_chabox_ops,
Greg Kroah-Hartman
maintainerPATCH 233/484 perf/x86/intel/pt: Fix topa_entry base length
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Marco Cavenati <[email protected]>
commit 5638bd722a44bbe97c1a7b3fae5b9efddb3e70ff upstream.
topa_entry->base needs to store a pfn. It obviously needs to be large enough to store the largest possible x86 pfn which is MAXPHYADDR-PAGE_SIZE (52-12). So it is 4 bits too small.
Increase the size of topa_entry->base from 36 bits to 40 bits.
Note, systems where physical addresses can be 256TiB or more are affected.
[ Adrian: Amend commit message as suggested by Dave Hansen ]
--- arch/x86/events/intel/pt.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/x86/events/intel/pt.h +2 -2
@@ -33,8 +33,8 @@ struct topa_entry { u64 rsvd2 : 1; u64 size : 4; u64 rsvd3 : 2; - u64 base : 36; - u64 rsvd4 : 16; + u64 base : 40; + u64 rsvd4 : 12; };/* TSC to Core Crystal Clock Ratio */
Greg Kroah-Hartman
maintainerPATCH 234/484 perf/x86/intel/pt: Fix a topa_entry base address calculation
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Adrian Hunter <[email protected]>
commit ad97196379d0b8cb24ef3d5006978a6554e6467f upstream.
topa_entry->base is a bit-field. Bit-fields are not promoted to a 64-bit type, even if the underlying type is 64-bit, and so, if necessary, must be cast to a larger type when calculations are done.
Fix a topa_entry->base address calculation by adding a cast.
Without the cast, the address was limited to 36-bits i.e. 64GiB.
The address calculation is used on systems that do not support Multiple Entry ToPA (only Broadwell), and affects physical addresses on or above 64GiB. Instead of writing to the correct address, the address comprising the first 36 bits would be written to.
Intel PT snapshot and sampling modes are not affected.
--- arch/x86/events/intel/pt.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/x86/events/intel/pt.c +1 -1
@@ -861,7 +861,7 @@ static void pt_update_head(struct pt *pt*/ static void *pt_buffer_region (struct pt_buffer *buf) { -return phys_to_virt (TOPA_ENTRY (buf->cur, buf->cur_idx)->base <<TOPA_SHIFT ); +return phys_to_virt ((phys_addr_t )TOPA_ENTRY (buf->cur, buf->cur_idx)->base <<TOPA_SHIFT ); }/**
Greg Kroah-Hartman
maintainerPATCH 235/484 drm/i915/gt: Do not consider preemption during execlists_dequeue for gen8
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nitin Gote <[email protected]>
commit 65564157ae64cec0f527583f96e32f484f730f92 upstream.
We're seeing a GPU hang issue on a CHV platform, which was caused by commit bac24f59f454 ("drm/i915/execlists: Enable coarse preemption boundaries for Gen8").
The Gen8 platform only supports timeslicing and doesn't have a preemption mechanism, as its engines do not have a preemption timer.
Commit 751f82b353a6 ("drm/i915/gt: Only disable preemption on Gen8 render engines") addressed this issue only for render engines. This patch extends that fix by ensuring that preemption is not considered for all engines on Gen8 platforms.
v4:
- Use the correct Fixes tag (Rodrigo Vivi)
- Reworded commit log (Andi Shyti)
v3:
- Inside need_preempt(), condition of can_preempt() is not required as simplified can_preempt() is enough. (Chris Wilson)
v2: Simplify can_preempt() function (Tvrtko Ursulin)
--- drivers/gpu/drm/i915/gt/intel_execlists_submission.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-)
drivers/gpu/drm/i915/gt/intel_execlists_submission.c +1 -5
@@ -3231,11 +3231,7 @@ static void remove_from_engine(struct i9static bool can_preempt (struct intel_engine_cs *engine) { -if (GRAPHICS_VER (engine->i915) >8 ) -return true; - -/* GPGPU on bdw requires extra w/a; not implemented */ -return engine->class !=RENDER_CLASS ; +return GRAPHICS_VER (engine->i915) >8 ; }static void kick_execlists (const struct i915_request *rq,int prio)
Greg Kroah-Hartman
maintainerPATCH 236/484 drm/amdgpu/sdma5.2: Update wptr registers as well as doorbell
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Deucher <[email protected]>
commit a03ebf116303e5d13ba9a2b65726b106cb1e96f6 upstream.
We seem to have a case where SDMA will sometimes miss a doorbell if GFX is entering the powergating state when the doorbell comes in. To workaround this, we can update the wptr via MMIO, however, this is only safe because we disallow gfxoff in begin_ring() for SDMA 5.2 and then allow it again in end_ring().
Enable this workaround while we are root causing the issue with the HW team.
--- drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c +12 -0
@@ -298,6 +298,14 @@ static void sdma_v5_2_ring_set_wptr(struDRM_DEBUG ("calling WDOORBELL64(0x%08x, 0x%016llx)\n" , ring->doorbell_index, ring->wptr <<2 );WDOORBELL64 (ring->doorbell_index, ring->wptr <<2 ); +/* SDMA seems to miss doorbells sometimes when powergating kicks in. +* Updating the wptr directly will wake it. This is only safe because +* we disallow gfxoff in begin_use() and then allow it again in end_use(). +*/ +WREG32 (sdma_v5_2_get_reg_offset (adev, ring->me, mmSDMA0_GFX_RB_WPTR), +lower_32_bits (ring->wptr <<2 )); +WREG32 (sdma_v5_2_get_reg_offset (adev, ring->me, mmSDMA0_GFX_RB_WPTR_HI), +upper_32_bits (ring->wptr <<2 )); }else {DRM_DEBUG ("Not using doorbell -- " "mmSDMA%i_GFX_RB_WPTR == 0x%08x "
@@ -1675,6 +1683,10 @@ static void sdma_v5_2_ring_begin_use(str* but it shouldn't hurt for other parts since * this GFXOFF will be disallowed anyway when SDMA is * active, this just makes it explicit. +* sdma_v5_2_ring_set_wptr() takes advantage of this +* to update the wptr because sometimes SDMA seems to miss +* doorbells when entering PG. If you remove this, update +* sdma_v5_2_ring_set_wptr() as well! */ amdgpu_gfx_off_ctrl (adev, false); }
Greg Kroah-Hartman
maintainerPATCH 237/484 drm/i915/dp: Reset intel_dp->link_trained before retraining the link
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Imre Deak <[email protected]>
commit d13e2a6e95e6b87f571c837c71a3d05691def9bb upstream.
Regularly retraining a link during an atomic commit happens with the given pipe/link already disabled and hence intel_dp->link_trained being false. Ensure this also for retraining a DP SST link via direct calls to the link training functions (vs. an actual commit as for DP MST). So far nothing depended on this, however the next patch will depend on link_trained==false for changing the LTTPR mode to non-transparent.
--- drivers/gpu/drm/i915/display/intel_dp.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/gpu/drm/i915/display/intel_dp.c +2 -0
@@ -3627,6 +3627,8 @@ int intel_dp_retrain_link(struct intel_e !intel_dp_mst_is_master_trans(crtc_state))continue ; + intel_dp->link_trained = false; +intel_dp_check_frl_training (intel_dp);intel_dp_pcon_dsc_configure (intel_dp, crtc_state);intel_dp_start_link_train (intel_dp, crtc_state);
Greg Kroah-Hartman
maintainerPATCH 238/484 rtc: isl1208: Fix return value of nvmem callbacks
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Joy Chakraborty <[email protected]>
commit 70f1ae5f0e7f44edf842444044615da7b59838c1 upstream.
Read/write callbacks registered with nvmem core expect 0 to be returned on success and a negative value to be returned on failure.
isl1208_nvmem_read()/isl1208_nvmem_write() currently return the number of bytes read/written on success, fix to return 0 on success and negative on failure.
--- drivers/rtc/rtc-isl1208.c | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-)
drivers/rtc/rtc-isl1208.c +4 -7
@@ -743,14 +743,13 @@ static int isl1208_nvmem_read(void *priv {struct isl1208_state *isl1208 = priv;struct i2c_client *client =to_i2c_client (isl1208->rtc->dev.parent); -int ret;/* nvmem sanitizes offset/count for us, but count==0 is possible */ if (!count)return count; - ret =isl1208_i2c_read_regs (client,ISL1208_REG_USR1 + off, buf, + +return isl1208_i2c_read_regs (client,ISL1208_REG_USR1 + off, buf, count); -return ret ==0 ? count : ret; } static int isl1208_nvmem_write(void *priv, unsigned int off, void *buf,
@@ -758,15 +757,13 @@ static int isl1208_nvmem_write(void *pri {struct isl1208_state *isl1208 = priv;struct i2c_client *client =to_i2c_client (isl1208->rtc->dev.parent); -int ret;/* nvmem sanitizes off/count for us, but count==0 is possible */ if (!count)return count; - ret =isl1208_i2c_set_regs (client,ISL1208_REG_USR1 + off, buf, - count); -return ret ==0 ? count : ret; +return isl1208_i2c_set_regs (client,ISL1208_REG_USR1 + off, buf, + count); }static const struct nvmem_config isl1208_nvmem_config = {
Greg Kroah-Hartman
maintainerPATCH 239/484 watchdog/perf: properly initialize the turbo mode timestamp and rearm counter
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Thomas Gleixner <[email protected]>
commit f944ffcbc2e1c759764850261670586ddf3bdabb upstream.
For systems on which the performance counter can expire early due to turbo modes the watchdog handler has a safety net in place which validates that since the last watchdog event there has at least 4/5th of the watchdog period elapsed.
This works reliably only after the first watchdog event because the per CPU variable which holds the timestamp of the last event is never initialized.
So a first spurious event will validate against a timestamp of 0 which results in a delta which is likely to be way over the 4/5 threshold of the period. As this might happen before the first watchdog hrtimer event increments the watchdog counter, this can lead to false positives.
Fix this by initializing the timestamp before enabling the hardware event. Reset the rearm counter as well, as that might be non zero after the watchdog was disabled and reenabled.
--- kernel/watchdog_hld.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)
kernel/watchdog_hld.c +8 -3
@@ -91,11 +91,15 @@ static bool watchdog_check_timestamp(voi__this_cpu_write (last_timestamp, now);return true; } -#else -static inline bool watchdog_check_timestamp (void ) + +static void watchdog_init_timestamp (void ) { -return true; +__this_cpu_write (nmi_rearmed,0 ); +__this_cpu_write (last_timestamp,ktime_get_mono_fast_ns ()); } +#else +static inline bool watchdog_check_timestamp (void ) {return true; } +static inline void watchdog_init_timestamp (void ) { }#endif static struct perf_event_attr wd_hw_attr = {
@@ -196,6 +200,7 @@ void hardlockup_detector_perf_enable(voiif (!atomic_fetch_inc (&watchdog_cpus))pr_info ("Enabled. Permanently consumes one hw-PMU counter.\n" ); +watchdog_init_timestamp ();perf_event_enable (this_cpu_read (watchdog_ev)); }
Greg Kroah-Hartman
maintainerPATCH 240/484 platform: mips: cpu_hwmon: Disable driver on unsupported hardware
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit f4d430db17b4ef4e9c3c352a04b2fe3c93011978 upstream.
cpu_hwmon is unsupported on CPUs without loongson_chiptemp register and csr.
--- drivers/platform/mips/cpu_hwmon.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/platform/mips/cpu_hwmon.c +3 -0
@@ -139,6 +139,9 @@ static int __init loongson_hwmon_init(vo csr_temp_enable =csr_readl (LOONGSON_CSR_FEATURES ) &LOONGSON_CSRF_TEMP ; +if (!csr_temp_enable && !loongson_chiptemp[0 ]) +return -ENODEV ; + nr_packages = loongson_sysconf.nr_cpus / loongson_sysconf.cores_per_package;
Greg Kroah-Hartman
maintainerPATCH 241/484 RDMA/iwcm: Fix a use-after-free related to destroying CM IDs
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bart Van Assche <[email protected]>
commit aee2424246f9f1dadc33faa78990c1e2eb7826e4 upstream.
iw_conn_req_handler() associates a new struct rdma_id_private (conn_id) with an existing struct iw_cm_id (cm_id) as follows:
conn_id->cm_id.iw = cm_id;
cm_id->context = conn_id;
cm_id->cm_handler = cma_iw_handler;rdma_destroy_id() frees both the cm_id and the struct rdma_id_private. Make sure that cm_work_handler() does not trigger a use-after-free by only freeing of the struct rdma_id_private after all pending work has finished.
--- drivers/infiniband/core/iwcm.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-)
drivers/infiniband/core/iwcm.c +7 -4
@@ -369,8 +369,10 @@ EXPORT_SYMBOL(iw_cm_disconnect);* * Clean up all resources associated with the connection and release * the initial reference taken by iw_create_cm_id. +* +* Returns true if and only if the last cm_id_priv reference has been dropped. */ -static void destroy_cm_id (struct iw_cm_id *cm_id) +static bool destroy_cm_id (struct iw_cm_id *cm_id) {struct iwcm_id_private *cm_id_priv;struct ib_qp *qp;
@@ -440,7 +442,7 @@ static void destroy_cm_id(struct iw_cm_iiwpm_remove_mapping (&cm_id->local_addr,RDMA_NL_IWCM ); } - (void )iwcm_deref_id (cm_id_priv); +return iwcm_deref_id (cm_id_priv); }/*
@@ -451,7 +453,8 @@ static void destroy_cm_id(struct iw_cm_i*/ void iw_destroy_cm_id (struct iw_cm_id *cm_id) { -destroy_cm_id (cm_id); +if (!destroy_cm_id (cm_id)) +flush_workqueue (iwcm_wq); }EXPORT_SYMBOL (iw_destroy_cm_id);
@@ -1035,7 +1038,7 @@ static void cm_work_handler(struct work_if (!test_bit (IWCM_F_DROP_EVENTS , &cm_id_priv->flags)) { ret =process_event (cm_id_priv, &levent);if (ret) -destroy_cm_id (&cm_id_priv->id); +WARN_ON_ONCE (destroy_cm_id (&cm_id_priv->id)); }else pr_debug ("dropping event %d\n" , levent.event);if (iwcm_deref_id (cm_id_priv))
Greg Kroah-Hartman
maintainerPATCH 242/484 selftests/sigaltstack: Fix ppc64 GCC build
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Michael Ellerman <[email protected]>
commit 17c743b9da9e0d073ff19fd5313f521744514939 upstream.
Building the sigaltstack test with GCC on 64-bit powerpc errors with:
gcc -Wall sas.c -o /home/michael/linux/.build/kselftest/sigaltstack/sas
In file included from sas.c:23:
current_stack_pointer.h:22:2: error: #error "implement current_stack_pointer equivalent"
22 | #error "implement current_stack_pointer equivalent"
| ^~~~~
sas.c: In function ‘my_usr1’:
sas.c:50:13: error: ‘sp’ undeclared (first use in this function); did you mean ‘p’?
50 | if (sp < (unsigned long)sstack ||
| ^~This happens because GCC doesn't define __ppc__ for 64-bit builds, only 32-bit builds. Instead use __powerpc__ to detect powerpc builds, which is defined by clang and GCC for 64-bit and 32-bit builds.
--- tools/testing/selftests/sigaltstack/current_stack_pointer.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
tools/testing/selftests/sigaltstack/current_stack_pointer.h +1 -1
@@ -8,7 +8,7 @@ register unsigned long sp asm("sp"); registerunsigned long sp asm("esp" );#elif __loongarch64 registerunsigned long sp asm("$sp" ); -#elif __ppc__ +#elif __powerpc__ registerunsigned long sp asm("r1" );#elif __s390x__ registerunsigned long sp asm("%15" );
Greg Kroah-Hartman
maintainerPATCH 243/484 rbd: dont assume rbd_is_lock_owner() for exclusive mappings
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ilya Dryomov <[email protected]>
commit 3ceccb14f5576e02b81cc8b105ab81f224bd87f6 upstream.
Expanding on the previous commit, assuming that rbd_is_lock_owner() always returns true (i.e. that we are either in RBD_LOCK_STATE_LOCKED or RBD_LOCK_STATE_QUIESCING) if the mapping is exclusive is wrong too. In case ceph_cls_set_cookie() fails, the lock would be temporarily released even if the mapping is exclusive, meaning that we can end up even in RBD_LOCK_STATE_UNLOCKED.
IOW, exclusive mappings are really "just" about disabling automatic lock transitions (as documented in the man page), not about grabbing the lock and holding on to it whatever it takes.
--- drivers/block/rbd.c | 5 ----- 1 file changed, 5 deletions(-)
drivers/block/rbd.c +0 -5
@@ -6592,11 +6592,6 @@ static int rbd_add_acquire_lock(struct rif (ret)return ret; -/* -* The lock may have been released by now, unless automatic lock -* transitions are disabled. -*/ -rbd_assert (!rbd_dev->opts->exclusive ||rbd_is_lock_owner (rbd_dev));return 0 ; }
Greg Kroah-Hartman
maintainerPATCH 244/484 remoteproc: stm32_rproc: Fix mailbox interrupts queuing
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gwenael Treuveur <[email protected]>
commit c3281abea67c9c0dc6219bbc41d1feae05a16da3 upstream.
Manage interrupt coming from coprocessor also when state is ATTACHED.
--- drivers/remoteproc/stm32_rproc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/remoteproc/stm32_rproc.c +1 -1
@@ -293,7 +293,7 @@ static void stm32_rproc_mb_vq_work(strucmutex_lock (&rproc->lock); -if (rproc->state !=RPROC_RUNNING ) +if (rproc->state !=RPROC_RUNNING && rproc->state !=RPROC_ATTACHED ) goto unlock_mutex;if (rproc_vq_interrupt (rproc, mb->vq_id) ==IRQ_NONE )
Greg Kroah-Hartman
maintainerPATCH 245/484 remoteproc: imx_rproc: Skip over memory region when node value is NULL
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Aleksandr Mishin <[email protected]>
commit 2fa26ca8b786888673689ccc9da6094150939982 upstream.
In imx_rproc_addr_init() "nph = of_count_phandle_with_args()" just counts number of phandles. But phandles may be empty. So of_parse_phandle() in the parsing loop (0 < a < nph) may return NULL which is later dereferenced. Adjust this issue by adding NULL-return check.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
--- drivers/remoteproc/imx_rproc.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/remoteproc/imx_rproc.c +2 -0
@@ -588,6 +588,8 @@ static int imx_rproc_addr_init(struct imstruct resource res; node =of_parse_phandle (np,"memory-region" , a); +if (!node) +continue ;/* Not map vdevbuffer, vdevring region */ if (!strncmp (node->name,"vdev" ,strlen ("vdev" ))) {of_node_put (node);
Greg Kroah-Hartman
maintainerPATCH 246/484 MIPS: ip30: ip30-console: Add missing include
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit 8de4ed75bd14ed197119ac509c6902a8561e0c1c upstream.
Include linux/processor.h to fix build error:
arch/mips/sgi-ip30/ip30-console.c: In function ‘prom_putchar’:arch/mips/sgi-ip30/ip30-console.c:21:17: error: implicit declaration of function ‘cpu_relax’ [-Werror=implicit-function-declaration]
21 | cpu_relax();
--- arch/mips/sgi-ip30/ip30-console.c | 1 + 1 file changed, 1 insertion(+)
arch/mips/sgi-ip30/ip30-console.c +1 -0
@@ -1,6 +1,7 @@// SPDX-License-Identifier: GPL-2.0 #include <linux/io.h> +#include <linux/processor.h> #include <asm/sn/ioc3.h>
Greg Kroah-Hartman
maintainerPATCH 247/484 MIPS: dts: loongson: Fix GMAC phy node
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit 813c18d1ca1987afaf47e035152e1baa1375b1b2 upstream.
phy-mode should be rgmii-id to match hardware configuration.
Also there should be a phy-handle to reference phy node.
--- arch/mips/boot/dts/loongson/loongson64-2k1000.dtsi | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
arch/mips/boot/dts/loongson/loongson64-2k1000.dtsi +4 -2
@@ -125,7 +125,8 @@ <13 IRQ_TYPE_LEVEL_LOW>; interrupt-names = "macirq", "eth_lpi"; interrupt-parent = <&liointc0>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; + phy-handle = <&phy1>; mdio { #address-cells = <1>; #size-cells = <0>;
@@ -148,7 +149,8 @@ <15 IRQ_TYPE_LEVEL_LOW>; interrupt-names = "macirq", "eth_lpi"; interrupt-parent = <&liointc0>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; + phy-handle = <&phy1>; mdio { #address-cells = <1>; #size-cells = <0>;
Greg Kroah-Hartman
maintainerPATCH 248/484 MIPS: Loongson64: env: Hook up Loongsson-2K
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit 77543269ff23c75bebfb8e6e9a1177b350908ea7 upstream.
Somehow those enablement bits were left over when we were adding initial Loongson-2K support.
Set up basic information and select proper builtin DTB for Loongson-2K.
--- arch/mips/include/asm/mach-loongson64/boot_param.h | 2 ++ arch/mips/loongson64/env.c | 8 ++++++++ 2 files changed, 10 insertions(+)
arch/mips/include/asm/mach-loongson64/boot_param.h +2 -0
@@ -42,12 +42,14 @@ enum loongson_cpu_type { Legacy_1B =0x5 , Legacy_2G =0x6 , Legacy_2H =0x7 , + Legacy_2K =0x8 , Loongson_1A =0x100 , Loongson_1B =0x101 , Loongson_2E =0x200 , Loongson_2F =0x201 , Loongson_2G =0x202 , Loongson_2H =0x203 , + Loongson_2K =0x204 , Loongson_3A =0x300 , Loongson_3B =0x301 };
arch/mips/loongson64/env.c +8 -0
@@ -88,6 +88,12 @@ void __init prom_lefi_init_env(void) cpu_clock_freq = ecpu->cpu_clock_freq; loongson_sysconf.cputype = ecpu->cputype;switch (ecpu->cputype) { +case Legacy_2K: +case Loongson_2K: + smp_group[0 ] =0x900000001fe11000 ; + loongson_sysconf.cores_per_node =2 ; + loongson_sysconf.cores_per_package =2 ; +break ;case Legacy_3A:case Loongson_3A: loongson_sysconf.cores_per_node =4 ;
@@ -221,6 +227,8 @@ void __init prom_lefi_init_env(void)default :break ; } + }else if ((read_c0_prid () &PRID_IMP_MASK ) ==PRID_IMP_LOONGSON_64R ) { + loongson_fdt_blob = __dtb_loongson64_2core_2k1000_begin; }else if ((read_c0_prid () &PRID_IMP_MASK ) ==PRID_IMP_LOONGSON_64G ) {if (loongson_sysconf.bridgetype ==LS7A ) loongson_fdt_blob = __dtb_loongson64g_4core_ls7a_begin;
Greg Kroah-Hartman
maintainerPATCH 249/484 MIPS: Loongson64: Remove memory node for builtin-dtb
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit b81656c37acf1e682dde02f3e07987784b0f3634 upstream.
Builtin DTBS should never contain memory node as memory is going to be managed by LEFI interface.
Remove memory node to prevent confliction.
--- arch/mips/boot/dts/loongson/loongson64-2k1000.dtsi | 8 -------- 1 file changed, 8 deletions(-)
arch/mips/boot/dts/loongson/loongson64-2k1000.dtsi +0 -8
@@ -23,14 +23,6 @@ }; }; - memory@200000 { - compatible = "memory"; - device_type = "memory"; - reg = <0x00000000 0x00200000 0x00000000 0x0ee00000>, /* 238 MB at 2 MB */ - <0x00000000 0x20000000 0x00000000 0x1f000000>, /* 496 MB at 512 MB */ - <0x00000001 0x10000000 0x00000001 0xb0000000>; /* 6912 MB at 4352MB */ - }; - cpu_clk: cpu_clk { #clock-cells = <0>; compatible = "fixed-clock";
Greg Kroah-Hartman
maintainerPATCH 250/484 MIPS: Loongson64: reset: Prioritise firmware service
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit 4e7ca0b57f3bc09ba3e4ab86bf6b7c35134bfd04 upstream.
We should always use firmware's poweroff & reboot service if it's available as firmware may need to perform more task than platform's syscon etc.
However _machine_restart & poweroff hooks are registered at low priority, which means platform reboot driver can override them.
Register firmware based reboot/poweroff implementation with register_sys_off_handler with appropriate priority so that they will be prioritised. Remove _machine_halt hook as it's deemed to be unnecessary.
--- arch/mips/loongson64/reset.c | 38 ++++++++++++++++---------------------- 1 file changed, 16 insertions(+), 22 deletions(-)
arch/mips/loongson64/reset.c +16 -22
@@ -11,6 +11,7 @@#include <linux/init.h> #include <linux/kexec.h> #include <linux/pm.h> +#include <linux/reboot.h> #include <linux/slab.h> #include <asm/bootinfo.h>
@@ -21,36 +22,21 @@#include <loongson.h> #include <boot_param.h> -static void loongson_restart (char *command) +static int firmware_restart (struct sys_off_data *unusedd) {void (*fw_restart)(void ) = (void *)loongson_sysconf.restart_addr;fw_restart (); -while (1 ) { -if (cpu_wait) -cpu_wait (); - } +return NOTIFY_DONE ; } -static void loongson_poweroff (void ) +static int firmware_poweroff (struct sys_off_data *unused) {void (*fw_poweroff)(void ) = (void *)loongson_sysconf.poweroff_addr;fw_poweroff (); -while (1 ) { -if (cpu_wait) -cpu_wait (); - } -} - -static void loongson_halt (void ) -{ -pr_notice ("\n\n** You can safely turn off the power now **\n\n" ); -while (1 ) { -if (cpu_wait) -cpu_wait (); - } +return NOTIFY_DONE ; }#ifdef CONFIG_KEXEC
@@ -154,9 +140,17 @@ static void loongson_crash_shutdown(strustatic int __init mips_reboot_setup (void ) { - _machine_restart = loongson_restart; - _machine_halt = loongson_halt; - pm_power_off = loongson_poweroff; +if (loongson_sysconf.restart_addr) { +register_sys_off_handler (SYS_OFF_MODE_RESTART , +SYS_OFF_PRIO_FIRMWARE , + firmware_restart,NULL ); + } + +if (loongson_sysconf.poweroff_addr) { +register_sys_off_handler (SYS_OFF_MODE_POWER_OFF , +SYS_OFF_PRIO_FIRMWARE , + firmware_poweroff,NULL ); + }#ifdef CONFIG_KEXEC kexec_argv =kmalloc (KEXEC_ARGV_SIZE ,GFP_KERNEL );
Greg Kroah-Hartman
maintainerPATCH 251/484 MIPS: Loongson64: Test register availability before use
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiaxun Yang <[email protected]>
commit c04366b1207a036b7de02dfcc1ac7138d3343c9b upstream.
Some global register address variable may be missing on specific CPU type, test them before use them.
--- arch/mips/loongson64/smp.c | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-)
arch/mips/loongson64/smp.c +21 -2
@@ -479,12 +479,25 @@ static void loongson3_smp_finish(void)static void __init loongson3_smp_setup (void ) {int i =0 , num =0 ;/* i: physical id, num: logical id */ +int max_cpus =0 ;init_cpu_possible (cpu_none_mask); +for (i =0 ; i <ARRAY_SIZE (smp_group); i++) { +if (!smp_group[i]) +break ; + max_cpus += loongson_sysconf.cores_per_node; + } + +if (max_cpus < loongson_sysconf.nr_cpus) { +pr_err ("SMP Groups are less than the number of CPUs\n" ); + loongson_sysconf.nr_cpus = max_cpus ? max_cpus :1 ; + } +/* For unified kernel, NR_CPUS is the maximum possible value, * loongson_sysconf.nr_cpus is the really present value */ + i =0 ;while (i < loongson_sysconf.nr_cpus) {if (loongson_sysconf.reserved_cpus_mask & (1 <<i)) {/* Reserved physical CPU cores */
@@ -505,14 +518,14 @@ static void __init loongson3_smp_setup(v __cpu_logical_map[num] =-1 ; num++; } -csr_ipi_probe ();ipi_set0_regs_init ();ipi_clear0_regs_init ();ipi_status0_regs_init ();ipi_en0_regs_init ();ipi_mailbox_buf_init (); -ipi_write_enable (0 ); +if (smp_group[0 ]) +ipi_write_enable (0 );cpu_set_core (&cpu_data[0 ],cpu_logical_map (0 ) % loongson_sysconf.cores_per_package);
@@ -830,6 +843,9 @@ static int loongson3_disable_clock(unsiguint64_t core_id =cpu_core (&cpu_data[cpu]);uint64_t package_id = cpu_data[cpu].package; +if (!loongson_chipcfg[package_id] || !loongson_freqctrl[package_id]) +return 0 ; +if ((read_c0_prid () &PRID_REV_MASK ) ==PRID_REV_LOONGSON3A_R1 ) {LOONGSON_CHIPCFG (package_id) &= ~(1 << (12 + core_id)); }else {
@@ -844,6 +860,9 @@ static int loongson3_enable_clock(unsignuint64_t core_id =cpu_core (&cpu_data[cpu]);uint64_t package_id = cpu_data[cpu].package; +if (!loongson_chipcfg[package_id] || !loongson_freqctrl[package_id]) +return 0 ; +if ((read_c0_prid () &PRID_REV_MASK ) ==PRID_REV_LOONGSON3A_R1 ) {LOONGSON_CHIPCFG (package_id) |=1 << (12 + core_id); }else {
Greg Kroah-Hartman
maintainerPATCH 252/484 drm/panfrost: Mark simple_ondemand governor as softdep
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dragan Simic <[email protected]>
commit 80f4e62730a91572b7fdc657f7bb747e107ae308 upstream.
Panfrost DRM driver uses devfreq to perform DVFS, while using simple_ondemand devfreq governor by default. This causes driver initialization to fail on boot when simple_ondemand governor isn't built into the kernel statically, as a result of the missing module dependency and, consequently, the required governor module not being included in the initial ramdisk. Thus, let's mark simple_ondemand governor as a softdep for Panfrost, to have its kernel module included in the initial ramdisk.
This is a rather longstanding issue that has forced distributions to build devfreq governors statically into their kernels, [1][2] or has forced users to introduce some unnecessary workarounds. [3]
For future reference, not having support for the simple_ondemand governor in the initial ramdisk produces errors in the kernel log similar to these below, which were taken from a Pine64 RockPro64:
panfrost ff9a0000.gpu: [drm:panfrost_devfreq_init [panfrost]] *ERROR* Couldn't initialize GPU devfreq panfrost ff9a0000.gpu: Fatal error during GPU init
panfrost: probe of ff9a0000.gpu failed with error -22
Having simple_ondemand marked as a softdep for Panfrost may not resolve this issue for all Linux distributions. In particular, it will remain unresolved for the distributions whose utilities for the initial ramdisk generation do not handle the available softdep information [4] properly yet. However, some Linux distributions already handle softdeps properly while generating their initial ramdisks, [5] and this is a prerequisite step in the right direction for the distributions that don't handle them properly yet.
[1] https://gitlab.manjaro.org/manjaro-arm/packages/core/linux/-/blob/linux61/config?ref_type=heads#L8180
[2] https://salsa.debian.org/kernel-team/linux/-/merge_requests/1066
[3] https://forum.pine64.org/showthread.php?tid=15458
[4] https://git.kernel.org/pub/scm/utils/kernel/kmod/kmod.git/commit/?id=49d8e0b59052999de577ab732b719cfbeb89504d
[5] https://github.com/archlinux/mkinitcpio/commit/97ac4d37aae084a050be512f6d8f4489054668ad
--- drivers/gpu/drm/panfrost/panfrost_drv.c | 1 + 1 file changed, 1 insertion(+)
drivers/gpu/drm/panfrost/panfrost_drv.c +1 -0
@@ -687,3 +687,4 @@ module_platform_driver(panfrost_driver);MODULE_AUTHOR ("Panfrost Project Developers" );MODULE_DESCRIPTION ("Panfrost DRM Driver" );MODULE_LICENSE ("GPL v2" ); +MODULE_SOFTDEP ("pre: governor_simpleondemand" );
Greg Kroah-Hartman
maintainerPATCH 253/484 rbd: rename RBD_LOCK_STATE_RELEASING and releasing_wait
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ilya Dryomov <[email protected]>
commit f5c466a0fdb2d9f3650d2e3911b0735f17ba00cf upstream.
... to RBD_LOCK_STATE_QUIESCING and quiescing_wait to recognize that this state and the associated completion are backing rbd_quiesce_lock(), which isn't specific to releasing the lock.
While exclusive lock does get quiesced before it's released, it also gets quiesced before an attempt to update the cookie is made and there the lock is not released as long as ceph_cls_set_cookie() succeeds.
--- drivers/block/rbd.c | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-)
drivers/block/rbd.c +10 -10
@@ -362,7 +362,7 @@ enum rbd_watch_state {enum rbd_lock_state {RBD_LOCK_STATE_UNLOCKED ,RBD_LOCK_STATE_LOCKED , -RBD_LOCK_STATE_RELEASING , +RBD_LOCK_STATE_QUIESCING , };/* WatchNotify::ClientId */
@@ -422,7 +422,7 @@ struct rbd_device {struct list_head running_list;struct completion acquire_wait;int acquire_err; -struct completion releasing_wait; +struct completion quiescing_wait;spinlock_t object_map_lock;u8 *object_map;
@@ -525,7 +525,7 @@ static bool __rbd_is_lock_owner(struct rlockdep_assert_held (&rbd_dev->lock_rwsem);return rbd_dev->lock_state ==RBD_LOCK_STATE_LOCKED || - rbd_dev->lock_state ==RBD_LOCK_STATE_RELEASING ; + rbd_dev->lock_state ==RBD_LOCK_STATE_QUIESCING ; }static bool rbd_is_lock_owner (struct rbd_device *rbd_dev)
@@ -3460,12 +3460,12 @@ static void rbd_lock_del_request(structspin_lock (&rbd_dev->lock_lists_lock);if (!list_empty (&img_req->lock_item)) {list_del_init (&img_req->lock_item); - need_wakeup = (rbd_dev->lock_state ==RBD_LOCK_STATE_RELEASING && + need_wakeup = (rbd_dev->lock_state ==RBD_LOCK_STATE_QUIESCING &&list_empty (&rbd_dev->running_list)); }spin_unlock (&rbd_dev->lock_lists_lock);if (need_wakeup) -complete (&rbd_dev->releasing_wait); +complete (&rbd_dev->quiescing_wait); }static int rbd_img_exclusive_lock (struct rbd_img_request *img_req)
@@ -4183,16 +4183,16 @@ static bool rbd_quiesce_lock(struct rbd_/* * Ensure that all in-flight IO is flushed. */ - rbd_dev->lock_state =RBD_LOCK_STATE_RELEASING ; -rbd_assert (!completion_done (&rbd_dev->releasing_wait)); + rbd_dev->lock_state =RBD_LOCK_STATE_QUIESCING ; +rbd_assert (!completion_done (&rbd_dev->quiescing_wait));if (list_empty (&rbd_dev->running_list))return true;up_write (&rbd_dev->lock_rwsem); -wait_for_completion (&rbd_dev->releasing_wait); +wait_for_completion (&rbd_dev->quiescing_wait);down_write (&rbd_dev->lock_rwsem); -if (rbd_dev->lock_state !=RBD_LOCK_STATE_RELEASING ) +if (rbd_dev->lock_state !=RBD_LOCK_STATE_QUIESCING )return false;rbd_assert (list_empty (&rbd_dev->running_list));
@@ -5387,7 +5387,7 @@ static struct rbd_device *__rbd_dev_creaINIT_LIST_HEAD (&rbd_dev->acquiring_list);INIT_LIST_HEAD (&rbd_dev->running_list);init_completion (&rbd_dev->acquire_wait); -init_completion (&rbd_dev->releasing_wait); +init_completion (&rbd_dev->quiescing_wait);spin_lock_init (&rbd_dev->object_map_lock);
Greg Kroah-Hartman
maintainerPATCH 254/484 rbd: dont assume RBD_LOCK_STATE_LOCKED for exclusive mappings
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ilya Dryomov <[email protected]>
commit 2237ceb71f89837ac47c5dce2aaa2c2b3a337a3c upstream.
Every time a watch is reestablished after getting lost, we need to update the cookie which involves quiescing exclusive lock. For this, we transition from RBD_LOCK_STATE_LOCKED to RBD_LOCK_STATE_QUIESCING roughly for the duration of rbd_reacquire_lock() call. If the mapping is exclusive and I/O happens to arrive in this time window, it's failed with EROFS (later translated to EIO) based on the wrong assumption in rbd_img_exclusive_lock() -- "lock got released?" check there stopped making sense with commit a2b1da09793d ("rbd: lock should be quiesced on reacquire").
To make it worse, any such I/O is added to the acquiring list before EROFS is returned and this sets up for violating rbd_lock_del_request() precondition that the request is either on the running list or not on any list at all -- see commit ded080c86b3f ("rbd: don't move requests to the running list on errors"). rbd_lock_del_request() ends up processing these requests as if they were on the running list which screws up quiescing_wait completion counter and ultimately leads to
rbd_assert(!completion_done(&rbd_dev->quiescing_wait));
being triggered on the next watch error.
--- drivers/block/rbd.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-)
drivers/block/rbd.c +5 -5
@@ -3459,6 +3459,7 @@ static void rbd_lock_del_request(structlockdep_assert_held (&rbd_dev->lock_rwsem);spin_lock (&rbd_dev->lock_lists_lock);if (!list_empty (&img_req->lock_item)) { +rbd_assert (!list_empty (&rbd_dev->running_list));list_del_init (&img_req->lock_item); need_wakeup = (rbd_dev->lock_state ==RBD_LOCK_STATE_QUIESCING &&list_empty (&rbd_dev->running_list));
@@ -3478,11 +3479,6 @@ static int rbd_img_exclusive_lock(structif (rbd_lock_add_request (img_req))return 1 ; -if (rbd_dev->opts->exclusive) { -WARN_ON (1 );/* lock got released? */ -return -EROFS ; - } -/* * Note the use of mod_delayed_work() in rbd_acquire_lock() * and cancel_delayed_work() in wake_lock_waiters().
@@ -4603,6 +4599,10 @@ static void rbd_reacquire_lock(struct rbrbd_warn (rbd_dev,"failed to update lock cookie: %d" , ret); +if (rbd_dev->opts->exclusive) +rbd_warn (rbd_dev, +"temporarily releasing lock on exclusive mapping" ); +/* * Lock cookie cannot be updated on older OSDs, so do * a manual release and queue an acquire.
Greg Kroah-Hartman
maintainerPATCH 255/484 Bluetooth: btusb: Add RTL8852BE device 0489:e125 to device tables
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hilda Wu <[email protected]>
commit 295ef07a9dae6182ad4b689aa8c6a7dbba21474c upstream.
Add the support ID 0489:e125 to usb_device_id table for Realtek RTL8852B chip.
The device info from /sys/kernel/debug/usb/devices as below.
T: Bus=01 Lev=01 Prnt=01 Port=07 Cnt=03 Dev#= 5 Spd=12 MxCh= 0 D: Ver= 1.00 Cls=e0(wlcon) Sub=01 Prot=01 MxPS=64 #Cfgs= 1 P: Vendor=0489 ProdID=e125 Rev= 0.00 S: Manufacturer=Realtek S: Product=Bluetooth Radio S: SerialNumber=00e04c000001 C:* #Ifs= 2 Cfg#= 1 Atr=e0 MxPwr=500mA I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=1ms E: Ad=02(O) Atr=02(Bulk) MxPS= 64 Ivl=0ms E: Ad=82(I) Atr=02(Bulk) MxPS= 64 Ivl=0ms I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms
--- drivers/bluetooth/btusb.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/bluetooth/btusb.c +2 -0
@@ -559,6 +559,8 @@ static const struct usb_device_id blackl BTUSB_WIDEBAND_SPEECH }, { USB_DEVICE(0x0cb5, 0xc547), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH }, + { USB_DEVICE(0x0489, 0xe125), .driver_info = BTUSB_REALTEK | + BTUSB_WIDEBAND_SPEECH }, /* Silicon Wave based devices */ { USB_DEVICE(0x0c10, 0x0000), .driver_info = BTUSB_SWAVE },
Greg Kroah-Hartman
maintainerPATCH 256/484 Bluetooth: btusb: Add Realtek RTL8852BE support ID 0x13d3:0x3591
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: WangYuli <[email protected]>
commit 473a89b4ed7fd52a419340f7c540d5c8fc96fc75 upstream.
Add the support ID(0x13d3, 0x3591) to usb_device_id table for Realtek RTL8852BE.
The device table is as follows:
T: Bus=01 Lev=02 Prnt=03 Port=00 Cnt=01 Dev#= 5 Spd=12 MxCh= 0 D: Ver= 1.00 Cls=e0(wlcon) Sub=01 Prot=01 MxPS=64 #Cfgs= 1 P: Vendor=13d3 ProdID=3591 Rev= 0.00 S: Manufacturer=Realtek S: Product=Bluetooth Radio S: SerialNumber=00e04c000001 C:* #Ifs= 2 Cfg#= 1 Atr=e0 MxPwr=500mA I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=1ms E: Ad=02(O) Atr=02(Bulk) MxPS= 64 Ivl=0ms E: Ad=82(I) Atr=02(Bulk) MxPS= 64 Ivl=0ms I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms
--- drivers/bluetooth/btusb.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/bluetooth/btusb.c +2 -0
@@ -559,6 +559,8 @@ static const struct usb_device_id blackl BTUSB_WIDEBAND_SPEECH }, { USB_DEVICE(0x0cb5, 0xc547), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH }, + { USB_DEVICE(0x13d3, 0x3591), .driver_info = BTUSB_REALTEK | + BTUSB_WIDEBAND_SPEECH }, { USB_DEVICE(0x0489, 0xe125), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH },
Greg Kroah-Hartman
maintainerPATCH 257/484 nilfs2: handle inconsistent state in nilfs_btnode_create_block()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ryusuke Konishi <[email protected]>
commit 4811f7af6090e8f5a398fbdd766f903ef6c0d787 upstream.
Syzbot reported that a buffer state inconsistency was detected in nilfs_btnode_create_block(), triggering a kernel bug.
It is not appropriate to treat this inconsistency as a bug; it can occur if the argument block address (the buffer index of the newly created block) is a virtual block number and has been reallocated due to corruption of the bitmap used to manage its allocation state.
So, modify nilfs_btnode_create_block() and its callers to treat it as a possible filesystem error, rather than triggering a kernel bug.
--- fs/nilfs2/btnode.c | 25 ++++++++++++++++++++----- fs/nilfs2/btree.c | 4 ++-- 2 files changed, 22 insertions(+), 7 deletions(-)
fs/nilfs2/btnode.c +20 -5
@@ -51,12 +51,21 @@ nilfs_btnode_create_block(struct address bh =nilfs_grab_buffer (inode, btnc, blocknr,BIT (BH_NILFS_Node));if (unlikely (!bh)) -return NULL ; +return ERR_PTR (-ENOMEM );if (unlikely (buffer_mapped (bh) ||buffer_uptodate (bh) ||buffer_dirty (bh))) { -brelse (bh); -BUG (); +/* +* The block buffer at the specified new address was already +* in use. This can happen if it is a virtual block number +* and has been reallocated due to corruption of the bitmap +* used to manage its allocation state (if not, the buffer +* clearing of an abandoned b-tree node is missing somewhere). +*/ +nilfs_error (inode->i_sb, +"state inconsistency probably due to duplicate use of b-tree node block address %llu (ino=%lu)" , + (unsigned long long )blocknr, inode->i_ino); + goto failed; }memset (bh->b_data,0 ,i_blocksize (inode)); bh->b_bdev = inode->i_sb->s_bdev;
@@ -67,6 +76,12 @@ nilfs_btnode_create_block(struct addressunlock_page (bh->b_page);put_page (bh->b_page);return bh; + +failed: +unlock_page (bh->b_page); +put_page (bh->b_page); +brelse (bh); +return ERR_PTR (-EIO ); } int nilfs_btnode_submit_block(struct address_space *btnc, __u64 blocknr,
@@ -217,8 +232,8 @@ retry: } nbh =nilfs_btnode_create_block (btnc, newkey); -if (!nbh) -return -ENOMEM ; +if (IS_ERR (nbh)) +return PTR_ERR (nbh);BUG_ON (nbh == obh); ctxt->newbh = nbh;
fs/nilfs2/btree.c +2 -2
@@ -63,8 +63,8 @@ static int nilfs_btree_get_new_block(construct buffer_head *bh; bh =nilfs_btnode_create_block (btnc, ptr); -if (!bh) -return -ENOMEM ; +if (IS_ERR (bh)) +return PTR_ERR (bh);set_buffer_nilfs_volatile (bh); *bhp = bh;
Greg Kroah-Hartman
maintainerPATCH 258/484 io_uring/io-wq: limit retrying worker initialisation
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pavel Begunkov <[email protected]>
commit 0453aad676ff99787124b9b3af4a5f59fbe808e2 upstream.
If io-wq worker creation fails, we retry it by queueing up a task_work. tasK_work is needed because it should be done from the user process context. The problem is that retries are not limited, and if queueing a task_work is the reason for the failure, we might get into an infinite loop.
It doesn't seem to happen now but it would with the following patch executing task_work in the freezer's loop. For now, arbitrarily limit the number of attempts to create a worker.
--- io_uring/io-wq.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-)
io_uring/io-wq.c +7 -3
@@ -19,6 +19,7 @@#include "io-wq.h" #define WORKER_IDLE_TIMEOUT (5 * HZ) +#define WORKER_INIT_LIMIT 3enum {IO_WORKER_F_UP =1 ,/* up and active */
@@ -54,6 +55,7 @@ struct io_worker {unsigned long create_state;struct callback_head create_work;int create_index; +int init_retries;union {struct rcu_head rcu;
@@ -732,7 +734,7 @@ static bool io_wq_work_match_all(structreturn true; } -static inline bool io_should_retry_thread (long err) +static inline bool io_should_retry_thread (struct io_worker *worker,long err) {/* * Prevent perpetual task_work retry, if the task (or its group) is
@@ -740,6 +742,8 @@ static inline bool io_should_retry_threa*/ if (fatal_signal_pending (current))return false; +if (worker->init_retries++ >=WORKER_INIT_LIMIT ) +return false;switch (err) {case -EAGAIN :
@@ -766,7 +770,7 @@ static void create_worker_cont(struct caio_init_new_worker (wqe, worker, tsk);io_worker_release (worker);return ; - }else if (!io_should_retry_thread (PTR_ERR (tsk))) { + }else if (!io_should_retry_thread (worker,PTR_ERR (tsk))) {struct io_wqe_acct *acct =io_wqe_get_acct (worker);atomic_dec (&acct->nr_running);
@@ -831,7 +835,7 @@ fail: tsk =create_io_thread (io_wqe_worker, worker, wqe->node);if (!IS_ERR (tsk)) {io_init_new_worker (wqe, worker, tsk); - }else if (!io_should_retry_thread (PTR_ERR (tsk))) { + }else if (!io_should_retry_thread (worker,PTR_ERR (tsk))) {kfree (worker); goto fail; }else {
Greg Kroah-Hartman
maintainerPATCH 259/484 kernel: rerun task_work while freezing in get_signal()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pavel Begunkov <[email protected]>
commit 943ad0b62e3c21f324c4884caa6cb4a871bca05c upstream.
io_uring can asynchronously add a task_work while the task is getting freezed. TIF_NOTIFY_SIGNAL will prevent the task from sleeping in do_freezer_trap(), and since the get_signal()'s relock loop doesn't retry task_work, the task will spin there not being able to sleep until the freezing is cancelled / the task is killed / etc.
Run task_works in the freezer path. Keep the patch small and simple so it can be easily back ported, but we might need to do some cleaning after and look if there are other places with similar problems.
--- include/linux/sched/signal.h | 6 ++++++ kernel/signal.c | 8 ++++++++ 2 files changed, 14 insertions(+)
include/linux/sched/signal.h +6 -0
@@ -347,6 +347,12 @@ extern void sigqueue_free(struct sigqueuextern int send_sigqueue (struct sigqueue *,struct pid *,enum pid_type );extern int do_sigaction (int ,struct k_sigaction *,struct k_sigaction *); +static inline void clear_notify_signal (void ) +{ +clear_thread_flag (TIF_NOTIFY_SIGNAL ); +smp_mb__after_atomic (); +} +static inline int restart_syscall (void ) {set_tsk_thread_flag (current,TIF_SIGPENDING );
kernel/signal.c +8 -0
@@ -2579,6 +2579,14 @@ static void do_freezer_trap(void)spin_unlock_irq (¤t->sighand->siglock);cgroup_enter_frozen ();freezable_schedule (); + +/* +* We could've been woken by task_work, run it to clear +* TIF_NOTIFY_SIGNAL. The caller will retry if necessary. +*/ +clear_notify_signal (); +if (unlikely (READ_ONCE (current->task_works))) +task_work_run (); }static int ptrace_signal (int signr,kernel_siginfo_t *info)
Greg Kroah-Hartman
maintainerPATCH 260/484 kdb: address -Wformat-security warnings
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
[ Upstream commit 70867efacf4370b6c7cdfc7a5b11300e9ef7de64 ]
When -Wformat-security is not disabled, using a string pointer as a format causes a warning:
kernel/debug/kdb/kdb_io.c: In function 'kdb_read':kernel/debug/kdb/kdb_io.c:365:36: error: format not a string literal and no format arguments [-Werror=format-security]
365 | kdb_printf(kdb_prompt_str);
| ^~~~~~~~~~~~~~
kernel/debug/kdb/kdb_io.c: In function 'kdb_getstr':
kernel/debug/kdb/kdb_io.c:456:20: error: format not a string literal and no format arguments [-Werror=format-security]
456 | kdb_printf(kdb_prompt_str);
| ^~~~~~~~~~~~~~Use an explcit "%s" format instead.
--- kernel/debug/kdb/kdb_io.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
kernel/debug/kdb/kdb_io.c +2 -2
@@ -358,7 +358,7 @@ static char *kdb_read(char *buffer, size_t bufsize)if (i >= dtab_count)kdb_printf ("..." );kdb_printf ("\n" ); -kdb_printf (kdb_prompt_str); +kdb_printf ("%s" , kdb_prompt_str);kdb_printf ("%s" , buffer);if (cp != lastchar)kdb_position_cursor (kdb_prompt_str, buffer, cp);
@@ -450,7 +450,7 @@ char *kdb_getstr(char *buffer, size_t bufsize, const char *prompt) {if (prompt && kdb_prompt_str != prompt)strscpy (kdb_prompt_str, prompt,CMD_BUFLEN ); -kdb_printf (kdb_prompt_str); +kdb_printf ("%s" , kdb_prompt_str); kdb_nextline =1 ;/* Prompt and input resets line number */ return kdb_read (buffer, bufsize); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 261/484 kdb: Use the passed prompt in kdb_position_cursor()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Douglas Anderson <[email protected]>
[ Upstream commit e2e821095949cde46256034975a90f88626a2a73 ]
The function kdb_position_cursor() takes in a "prompt" parameter but never uses it. This doesn't _really_ matter since all current callers of the function pass the same value and it's a global variable, but it's a bit ugly. Let's clean it up.
Found by code inspection. This patch is expected to functionally be a no-op.
--- kernel/debug/kdb/kdb_io.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
kernel/debug/kdb/kdb_io.c +1 -1
@@ -194,7 +194,7 @@ char kdb_getchar(void)*/ static void kdb_position_cursor (char *prompt,char *buffer,char *cp) { -kdb_printf ("\r%s" , kdb_prompt_str); +kdb_printf ("\r%s" , prompt);if (cp > buffer)kdb_printf ("%.*s" , (int )(cp - buffer), buffer); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 262/484 jfs: Fix array-index-out-of-bounds in diFree
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jeongjun Park <[email protected]>
[ Upstream commit f73f969b2eb39ad8056f6c7f3a295fa2f85e313a ]
--- fs/jfs/jfs_imap.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
fs/jfs/jfs_imap.c +4 -1
@@ -290,7 +290,7 @@ int diSync(struct inode *ipimap)int diRead (struct inode *ip) {struct jfs_sb_info *sbi =JFS_SBI (ip->i_sb); -int iagno, ino, extno, rc; +int iagno, ino, extno, rc, agno;struct inode *ipimap;struct dinode *dp;struct iag *iagp;
@@ -339,8 +339,11 @@ int diRead(struct inode *ip)/* get the ag for the iag */ agstart =le64_to_cpu (iagp->agstart); + agno =BLKTOAG (agstart,JFS_SBI (ip->i_sb));release_metapage (mp); +if (agno >=MAXAG || agno <0 ) +return -EIO ; rel_inode = (ino & (INOSPERPAGE -1 )); pageno = blkno >> sbi->l2nbperpage;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 263/484 dmaengine: ti: k3-udma: Fix BCHAN count with UHC and HC channels
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Vignesh Raghavendra <[email protected]>
[ Upstream commit 372f8b3621294173f539b32976e41e6e12f5decf ]
Unlike other channel counts in CAPx registers, BCDMA BCHAN CNT doesn't include UHC and HC BC channels. So include them explicitly to arrive at total BC channel in the instance.
--- drivers/dma/ti/k3-udma.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/dma/ti/k3-udma.c +3 -1
@@ -4415,7 +4415,9 @@ static int udma_get_mmrs(struct platform_device *pdev, struct udma_dev *ud) ud->rchan_cnt =UDMA_CAP2_RCHAN_CNT (cap2);break ;case DMA_TYPE_BCDMA : - ud->bchan_cnt =BCDMA_CAP2_BCHAN_CNT (cap2); + ud->bchan_cnt =BCDMA_CAP2_BCHAN_CNT (cap2) + +BCDMA_CAP3_HBCHAN_CNT (cap3) + +BCDMA_CAP3_UBCHAN_CNT (cap3); ud->tchan_cnt =BCDMA_CAP2_TCHAN_CNT (cap2); ud->rchan_cnt =BCDMA_CAP2_RCHAN_CNT (cap2); ud->rflow_cnt = ud->rchan_cnt;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 264/484 phy: cadence-torrent: Check return value on register read
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ma Ke <[email protected]>
[ Upstream commit 967969cf594ed3c1678a9918d6e9bb2d1591cbe9 ]
cdns_torrent_dp_set_power_state() does not consider that ret might be overwritten. Add return value check of regmap_read_poll_timeout() after register read in cdns_torrent_dp_set_power_state().
--- drivers/phy/cadence/phy-cadence-torrent.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/phy/cadence/phy-cadence-torrent.c +3 -0
@@ -1056,6 +1056,9 @@ static int cdns_torrent_dp_set_power_state(struct cdns_torrent_phy *cdns_phy, ret =regmap_read_poll_timeout (regmap,PHY_PMA_XCVR_POWER_STATE_ACK , read_val, (read_val & mask) == value,0 ,POLL_TIMEOUT_US ); +if (ret) +return ret; +cdns_torrent_dp_write (regmap,PHY_PMA_XCVR_POWER_STATE_REQ ,0x00000000 );ndelay (100 );
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 265/484 um: time-travel: fix time-travel-start option
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johannes Berg <[email protected]>
[ Upstream commit 7d0a8a490aa3a2a82de8826aaf1dfa38575cb77a ]
We need to have the = as part of the option so that the value can be parsed properly. Also document that it must be given in nanoseconds, not seconds.
--- arch/um/kernel/time.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/um/kernel/time.c +2 -2
@@ -874,9 +874,9 @@ int setup_time_travel_start(char *str) return 1; } -__setup ("time-travel-start" , setup_time_travel_start); +__setup ("time-travel-start=" , setup_time_travel_start);__uml_help (setup_time_travel_start, -"time-travel-start=<seconds>\n" +"time-travel-start=<nanoseconds>\n" "Configure the UML instance's wall clock to start at this value rather than\n" "the host's wall clock at the time of UML boot.\n" );#endif
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 266/484 um: time-travel: fix signal blocking race/hang
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johannes Berg <[email protected]>
[ Upstream commit 2cf3a3c4b84def5406b830452b1cb8bbfffe0ebe ]
When signals are hard-blocked in order to do time-travel socket processing, we set signals_blocked and then handle SIGIO signals by setting the SIGIO bit in signals_pending. When unblocking, we first set signals_blocked to 0, and then handle all pending signals. We have to set it first, so that we can again properly block/unblock inside the unblock, if the time-travel handlers need to be processed.
Unfortunately, this is racy. We can get into this situation:
// signals_pending = SIGIO_MASK
unblock_signals_hard()
signals_blocked = 0;
if (signals_pending && signals_enabled) {
block_signals();
unblock_signals()
...
sig_handler_common(SIGIO, NULL, NULL);
sigio_handler()
...
sigio_reg_handler()
irq_do_timetravel_handler()
reg->timetravel_handler() ==
vu_req_interrupt_comm_handler()
vu_req_read_message()
vhost_user_recv_req()
vhost_user_recv()
vhost_user_recv_header()
// reads 12 bytes header of
// 20 bytes message
<-- receive SIGIO here <--
sig_handler()
int enabled = signals_enabled; // 1
if ((signals_blocked || !enabled) && (sig == SIGIO)) {
if (!signals_blocked && time_travel_mode == TT_MODE_EXTERNAL)
sigio_run_timetravel_handlers()
_sigio_handler()
sigio_reg_handler()
... as above ...
vhost_user_recv_header()
// reads 8 bytes that were message payload
// as if it were header - but aborts since
// it then gets -EAGAIN
...
--> end signal handler -->
// continue in vhost_user_recv()
// full_read() for 8 bytes payload busy loops
// entire process hangs hereConceptually, to fix this, we need to ensure that the signal handler cannot run while we hard-unblock signals. The thing that makes this more complex is that we can be doing hard-block/unblock while unblocking. Introduce a new signals_blocked_pending variable that we can keep at non-zero as long as pending signals are being processed, then we only need to ensure it's decremented safely and the signal handler will only increment it if it's already non-zero (or signals_blocked is set, of course.)
Note also that only the outermost call to hard-unblock is allowed to decrement signals_blocked_pending, since it could otherwise reach zero in an inner call, and leave the same race happening if the timetravel_handler loops, but that's basically required of it.
--- arch/um/os-Linux/signal.c | 118 +++++++++++++++++++++++++++++++------- 1 file changed, 98 insertions(+), 20 deletions(-)
arch/um/os-Linux/signal.c +98 -20
@@ -8,6 +8,7 @@#include <stdlib.h> #include <stdarg.h> +#include <stdbool.h> #include <errno.h> #include <signal.h> #include <string.h>
@@ -65,9 +66,7 @@ static void sig_handler_common(int sig, struct siginfo *si, mcontext_t *mc)int signals_enabled;#ifdef UML_CONFIG_UML_TIME_TRAVEL_SUPPORT -static int signals_blocked; -#else -#define signals_blocked 0 +static int signals_blocked, signals_blocked_pending;#endif static unsigned int signals_pending;static unsigned int signals_active =0 ;
@@ -76,14 +75,27 @@ void sig_handler(int sig, struct siginfo *si, mcontext_t *mc) {int enabled = signals_enabled; -if ((signals_blocked || !enabled) && (sig ==SIGIO )) { +#ifdef UML_CONFIG_UML_TIME_TRAVEL_SUPPORT +if ((signals_blocked || +__atomic_load_n (&signals_blocked_pending, __ATOMIC_SEQ_CST)) && + (sig ==SIGIO )) { +/* increment so unblock will do another round */ +__atomic_add_fetch (&signals_blocked_pending,1 , + __ATOMIC_SEQ_CST); +return ; + } +#endif + +if (!enabled && (sig ==SIGIO )) {/* * In TT_MODE_EXTERNAL, need to still call time-travel -* handlers unless signals are also blocked for the -* external time message processing. This will mark -* signals_pending by itself (only if necessary.) +* handlers. This will mark signals_pending by itself +* (only if necessary.) +* Note we won't get here if signals are hard-blocked +* (which is handled above), in that case the hard- +* unblock will handle things. */ -if (!signals_blocked && time_travel_mode ==TT_MODE_EXTERNAL ) +if (time_travel_mode ==TT_MODE_EXTERNAL )sigio_run_timetravel_handlers ();else signals_pending |=SIGIO_MASK ;
@@ -380,33 +392,99 @@ int um_set_signals_trace(int enable)#ifdef UML_CONFIG_UML_TIME_TRAVEL_SUPPORT void mark_sigio_pending (void ) { +/* +* It would seem that this should be atomic so +* it isn't a read-modify-write with a signal +* that could happen in the middle, losing the +* value set by the signal. +* +* However, this function is only called when in +* time-travel=ext simulation mode, in which case +* the only signal ever pending is SIGIO, which +* is blocked while this can be called, and the +* timer signal (SIGALRM) cannot happen. +*/ signals_pending |=SIGIO_MASK ; }void block_signals_hard (void ) { -if (signals_blocked) -return ; - signals_blocked =1 ; + signals_blocked++;barrier (); }void unblock_signals_hard (void ) { +static bool unblocking; +if (!signals_blocked) +panic ("unblocking signals while not blocked" ); + +if (--signals_blocked)return ; -/* Must be set to 0 before we check the pending bits etc. */ - signals_blocked =0 ; +/* +* Must be set to 0 before we check pending so the +* SIGIO handler will run as normal unless we're still +* going to process signals_blocked_pending. +*/ barrier (); -if (signals_pending && signals_enabled) { -/* this is a bit inefficient, but that's not really important */ -block_signals (); -unblock_signals (); - }else if (signals_pending &SIGIO_MASK ) { -/* we need to run time-travel handlers even if not enabled */ -sigio_run_timetravel_handlers (); +/* +* Note that block_signals_hard()/unblock_signals_hard() can be called +* within the unblock_signals()/sigio_run_timetravel_handlers() below. +* This would still be prone to race conditions since it's actually a +* call _within_ e.g. vu_req_read_message(), where we observed this +* issue, which loops. Thus, if the inner call handles the recorded +* pending signals, we can get out of the inner call with the real +* signal hander no longer blocked, and still have a race. Thus don't +* handle unblocking in the inner call, if it happens, but only in +* the outermost call - 'unblocking' serves as an ownership for the +* signals_blocked_pending decrement. +*/ +if (unblocking) +return ; + unblocking = true; + +while (__atomic_load_n (&signals_blocked_pending, __ATOMIC_SEQ_CST)) { +if (signals_enabled) { +/* signals are enabled so we can touch this */ + signals_pending |=SIGIO_MASK ; +/* +* this is a bit inefficient, but that's +* not really important +*/ +block_signals (); +unblock_signals (); + }else { +/* +* we need to run time-travel handlers even +* if not enabled +*/ +sigio_run_timetravel_handlers (); + } + +/* +* The decrement of signals_blocked_pending must be atomic so +* that the signal handler will either happen before or after +* the decrement, not during a read-modify-write: +* - If it happens before, it can increment it and we'll +* decrement it and do another round in the loop. +* - If it happens after it'll see 0 for both signals_blocked +* and signals_blocked_pending and thus run the handler as +* usual (subject to signals_enabled, but that's unrelated.) +* +* Note that a call to unblock_signals_hard() within the calls +* to unblock_signals() or sigio_run_timetravel_handlers() above +* will do nothing due to the 'unblocking' state, so this cannot +* underflow as the only one decrementing will be the outermost +* one. +*/ +if (__atomic_sub_fetch (&signals_blocked_pending,1 , + __ATOMIC_SEQ_CST) <0 ) +panic ("signals_blocked_pending underflow" ); } + + unblocking = false; }#endif
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 267/484 libbpf: Fix no-args func prototype BTF dumping syntax
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andrii Nakryiko <[email protected]>
[ Upstream commit 189f1a976e426011e6a5588f1d3ceedf71fe2965 ]
For all these years libbpf's BTF dumper has been emitting not strictly valid syntax for function prototypes that have no input arguments.
Instead of int (*blah)() we should emit int (*blah)(void).
This is not normally a problem, but it manifests when we get kfuncs in vmlinux.h that have no input arguments. Due to compiler internal specifics, we get no BTF information for such kfuncs, if they are not declared with proper (void).
The fix is trivial. We also need to adjust a few ancient tests that happily assumed () is correct.
--- tools/lib/bpf/btf_dump.c | 8 +++++--- .../selftests/bpf/progs/btf_dump_test_case_multidim.c | 4 ++-- .../selftests/bpf/progs/btf_dump_test_case_syntax.c | 4 ++-- 3 files changed, 9 insertions(+), 7 deletions(-)
tools/lib/bpf/btf_dump.c +5 -3
@@ -1458,10 +1458,12 @@ static void btf_dump_emit_type_chain(struct btf_dump *d,* Clang for BPF target generates func_proto with no * args as a func_proto with a single void arg (e.g., * `int (*f)(void)` vs just `int (*f)()`). We are -* going to pretend there are no args for such case. +* going to emit valid empty args (void) syntax for +* such case. Similarly and conveniently, valid +* no args case can be special-cased here as well. */ -if (vlen ==1 && p->type ==0 ) { -btf_dump_printf (d,")" ); +if (vlen ==0 || (vlen ==1 && p->type ==0 )) { +btf_dump_printf (d,"void)" );return ; }
tools/testing/selftests/bpf/progs/btf_dump_test_case_multidim.c +2 -2
@@ -14,9 +14,9 @@ typedef int *ptr_arr_t[6];typedef int *ptr_multiarr_t [7 ][8 ][9 ][10 ]; -typedef int * (*fn_ptr_arr_t [11 ])(); +typedef int * (*fn_ptr_arr_t [11 ])(void ); -typedef int * (*fn_ptr_multiarr_t [12 ][13 ])(); +typedef int * (*fn_ptr_multiarr_t [12 ][13 ])(void );struct root_struct {arr_t _1;
tools/testing/selftests/bpf/progs/btf_dump_test_case_syntax.c +2 -2
@@ -67,7 +67,7 @@ typedef void (*printf_fn_t)(const char *, ...);* `int -> char *` function and returns pointer to a char. Equivalent: * typedef char * (*fn_input_t)(int); * typedef char * (*fn_output_outer_t)(fn_input_t); -* typedef const fn_output_outer_t (* fn_output_inner_t)(); +* typedef const fn_output_outer_t (* fn_output_inner_t)(void); * typedef const fn_output_inner_t fn_ptr_arr2_t[5]; */ /* ----- START-EXPECTED-OUTPUT ----- */
@@ -94,7 +94,7 @@ typedef void (* (*signal_t)(int, void (*)(int)))(int);typedef char * (*fn_ptr_arr1_t [10 ])(int **); -typedef char * (* (*const fn_ptr_arr2_t [5 ])())(char * (*)(int )); +typedef char * (* (*const fn_ptr_arr2_t [5 ])(void ))(char * (*)(int ));struct struct_w_typedefs {int_t a;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 268/484 dma: fix call order in dmam_free_coherent
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Lance Richardson <[email protected]>
[ Upstream commit 28e8b7406d3a1f5329a03aa25a43aa28e087cb20 ]
dmam_free_coherent() frees a DMA allocation, which makes the freed vaddr available for reuse, then calls devres_destroy() to remove and free the data structure used to track the DMA allocation. Between the two calls, it is possible for a concurrent task to make an allocation with the same vaddr and add it to the devres list.
If this happens, there will be two entries in the devres list with the same vaddr and devres_destroy() can free the wrong entry, triggering the WARN_ON() in dmam_match.
Fix by destroying the devres entry before freeing the DMA allocation.
Tested:
kokonut //net/encryption
http://sponge2/b9145fe6-0f72-4325-ac2f-a84d81075b03
--- kernel/dma/mapping.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
kernel/dma/mapping.c +1 -1
@@ -62,8 +62,8 @@ void dmam_free_coherent(struct device *dev, size_t size, void *vaddr, {struct dma_devres match_data = { size, vaddr, dma_handle }; -dma_free_coherent (dev, size, vaddr, dma_handle);WARN_ON (devres_destroy (dev, dmam_release, dmam_match, &match_data)); +dma_free_coherent (dev, size, vaddr, dma_handle); }EXPORT_SYMBOL (dmam_free_coherent);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 269/484 bpf, events: Use prog to emit ksymbol event for main program
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hou Tao <[email protected]>
[ Upstream commit 0be9ae5486cd9e767138c13638820d240713f5f1 ]
Since commit 0108a4e9f358 ("bpf: ensure main program has an extable"), prog->aux->func[0]->kallsyms is left as uninitialized. For BPF programs with subprogs, the symbol for the main program is missing just as shown in the output of perf script below:
ffffffff81284b69 qp_trie_lookup_elem+0xb9 ([kernel.kallsyms]) ffffffffc0011125 bpf_prog_a4a0eb0651e6af8b_lookup_qp_trie+0x5d (bpf...) ffffffff8127bc2b bpf_for_each_array_elem+0x7b ([kernel.kallsyms]) ffffffffc00110a1 +0x25 ()
ffffffff8121a89a trace_call_bpf+0xca ([kernel.kallsyms])
Fix it by always using prog instead prog->aux->func[0] to emit ksymbol event for the main program. After the fix, the output of perf script will be correct:
ffffffff81284b96 qp_trie_lookup_elem+0xe6 ([kernel.kallsyms]) ffffffffc001382d bpf_prog_a4a0eb0651e6af8b_lookup_qp_trie+0x5d (bpf...) ffffffff8127bc2b bpf_for_each_array_elem+0x7b ([kernel.kallsyms]) ffffffffc0013779 bpf_prog_245c55ab25cfcf40_qp_trie_lookup+0x25 (bpf...) ffffffff8121a89a trace_call_bpf+0xca ([kernel.kallsyms])
--- kernel/events/core.c | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-)
kernel/events/core.c +12 -14
@@ -9194,21 +9194,19 @@ static void perf_event_bpf_emit_ksymbolsbool unregister = type ==PERF_BPF_EVENT_PROG_UNLOAD ;int i; -if (prog->aux->func_cnt ==0 ) { -perf_event_ksymbol (PERF_RECORD_KSYMBOL_TYPE_BPF , - (u64 )(unsigned long )prog->bpf_func, - prog->jited_len, unregister, - prog->aux->ksym.name); - }else { -for (i =0 ; i < prog->aux->func_cnt; i++) { -struct bpf_prog *subprog = prog->aux->func[i]; +perf_event_ksymbol (PERF_RECORD_KSYMBOL_TYPE_BPF , + (u64 )(unsigned long )prog->bpf_func, + prog->jited_len, unregister, + prog->aux->ksym.name); -perf_event_ksymbol ( -PERF_RECORD_KSYMBOL_TYPE_BPF , - (u64 )(unsigned long )subprog->bpf_func, - subprog->jited_len, unregister, - subprog->aux->ksym.name); - } +for (i =1 ; i < prog->aux->func_cnt; i++) { +struct bpf_prog *subprog = prog->aux->func[i]; + +perf_event_ksymbol ( +PERF_RECORD_KSYMBOL_TYPE_BPF , + (u64 )(unsigned long )subprog->bpf_func, + subprog->jited_len, unregister, + subprog->aux->ksym.name); } }
Greg Kroah-Hartman
maintainerPATCH 270/484 MIPS: SMP-CPS: Fix address for GCR_ACCESS register for CM3 and later
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gregory CLEMENT <[email protected]>
[ Upstream commit a263e5f309f32301e1f3ad113293f4e68a82a646 ]
When the CM block migrated from CM2.5 to CM3.0, the address offset for the Global CSR Access Privilege register was modified. We saw this in the "MIPS64 I6500 Multiprocessing System Programmer's Guide," it is stated that "the Global CSR Access Privilege register is located at offset 0x0120" in section 5.4. It is at least the same for I6400.
This fix allows to use the VP cores in SMP mode if the reset values were modified by the bootloader.
Based on the work of Vladimir Kondratiev <[email protected]> and the feedback from Jiaxun Yang <[email protected]>.
--- arch/mips/include/asm/mips-cm.h | 4 ++++ arch/mips/kernel/smp-cps.c | 5 ++++- 2 files changed, 8 insertions(+), 1 deletion(-)
arch/mips/include/asm/mips-cm.h +4 -0
@@ -228,6 +228,10 @@ GCR_ACCESSOR_RO(32, 0x0d0, gic_status) GCR_ACCESSOR_RO(32, 0x0f0, cpc_status)#define CM_GCR_CPC_STATUS_EX BIT(0) +/* GCR_ACCESS - Controls core/IOCU access to GCRs */ +GCR_ACCESSOR_RW(32, 0x120, access_cm3) +#define CM_GCR_ACCESS_ACCESSEN GENMASK(7, 0) +/* GCR_L2_CONFIG - Indicates L2 cache configuration when Config5.L2C=1 */ GCR_ACCESSOR_RW(32, 0x130, l2_config)#define CM_GCR_L2_CONFIG_BYPASS BIT(20)
arch/mips/kernel/smp-cps.c +4 -1
@@ -230,7 +230,10 @@ static void boot_core(unsigned int core, unsigned int vpe_id)write_gcr_co_reset_ext_base (CM_GCR_Cx_RESET_EXT_BASE_UEB);/* Ensure the core can access the GCRs */ -set_gcr_access (1 << core); +if (mips_cm_revision () <CM_REV_CM3 ) +set_gcr_access (1 << core); +else +set_gcr_access_cm3 (1 << core);if (mips_cpc_present ()) {/* Reset the core */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 271/484 ipv4: Fix incorrect source address in Record Route option
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ido Schimmel <[email protected]>
[ Upstream commit cc73bbab4b1fb8a4f53a24645871dafa5f81266a ]
The Record Route IP option records the addresses of the routers that routed the packet. In the case of forwarded packets, the kernel performs a route lookup via fib_lookup() and fills in the preferred source address of the matched route.
The lookup is performed with the DS field of the forwarded packet, but using the RT_TOS() macro which only masks one of the two ECN bits. If the packet is ECT(0) or CE, the matched route might be different than the route via which the packet was forwarded as the input path masks both of the ECN bits, resulting in the wrong address being filled in the Record Route option.
Fix by masking both of the ECN bits.
--- net/ipv4/route.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
net/ipv4/route.c +1 -1
@@ -1282,7 +1282,7 @@ void ip_rt_get_source(u8 *addr, struct sk_buff *skb, struct rtable *rt)struct flowi4 fl4 = { .daddr = iph->daddr, .saddr = iph->saddr, - .flowi4_tos =RT_TOS (iph->tos), + .flowi4_tos = iph->tos &IPTOS_RT_MASK , .flowi4_oif = rt->dst.dev->ifindex, .flowi4_iif = skb->dev->ifindex, .flowi4_mark = skb->mark,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 272/484 net: bonding: correctly annotate RCU in bond_should_notify_peers()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johannes Berg <[email protected]>
[ Upstream commit 3ba359c0cd6eb5ea772125a7aededb4a2d516684 ]
RCU use in bond_should_notify_peers() looks wrong, since it does rcu_dereference(), leaves the critical section, and uses the pointer after that.
Luckily, it's called either inside a nested RCU critical section or with the RTNL held.
Annotate it with rcu_dereference_rtnl() instead, and remove the inner RCU critical section.
--- drivers/net/bonding/bond_main.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-)
drivers/net/bonding/bond_main.c +2 -5
@@ -1087,13 +1087,10 @@ static struct slave *bond_find_best_slave(struct bonding *bond)return bestslave; } +/* must be called in RCU critical section or with RTNL held */ static bool bond_should_notify_peers(struct bonding *bond) { - struct slave *slave; - - rcu_read_lock(); - slave = rcu_dereference(bond->curr_active_slave); - rcu_read_unlock(); + struct slave *slave = rcu_dereference_rtnl(bond->curr_active_slave); if (!slave || !bond->send_peer_notif || bond->send_peer_notif %
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 273/484 netfilter: nft_set_pipapo_avx2: disable softinterrupts
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Florian Westphal <[email protected]>
[ Upstream commit a16909ae9982e931841c456061cb57fbaec9c59e ]
We need to disable softinterrupts, else we get following problem:
1. pipapo_avx2 called from process context; fpu usable
2. preempt_disable() called, pcpu scratchmap in use
3. softirq handles rx or tx, we re-enter pipapo_avx2
4. fpu busy, fallback to generic non-avx version
5. fallback reuses scratch map and index, which are in use by the preempted process
Handle this same way as generic version by first disabling softinterrupts while the scratchmap is in use.
--- net/netfilter/nft_set_pipapo_avx2.c | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-)
net/netfilter/nft_set_pipapo_avx2.c +10 -2
@@ -1141,8 +1141,14 @@ bool nft_pipapo_avx2_lookup(const struct net *net, const struct nft_set *set,bool map_index;int i, ret =0 ; -if (unlikely (!irq_fpu_usable ())) -return nft_pipapo_lookup (net, set, key, ext); +local_bh_disable (); + +if (unlikely (!irq_fpu_usable ())) { +bool fallback_res =nft_pipapo_lookup (net, set, key, ext); + +local_bh_enable (); +return fallback_res; + } m =rcu_dereference (priv->match);
@@ -1157,6 +1163,7 @@ bool nft_pipapo_avx2_lookup(const struct net *net, const struct nft_set *set, scratch = *raw_cpu_ptr (m->scratch);if (unlikely (!scratch)) {kernel_fpu_end (); +local_bh_enable ();return false; }
@@ -1237,6 +1244,7 @@ bool nft_pipapo_avx2_lookup(const struct net *net, const struct nft_set *set,if (i %2 ) scratch->map_index = !map_index;kernel_fpu_end (); +local_bh_enable ();return ret >=0 ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 274/484 tipc: Return non-zero value from tipc_udp_addr2str() on error
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Shigeru Yoshida <[email protected]>
[ Upstream commit fa96c6baef1b5385e2f0c0677b32b3839e716076 ]
tipc_udp_addr2str() should return non-zero value if the UDP media address is invalid. Otherwise, a buffer overflow access can occur in tipc_media_addr_printf(). Fix this by returning 1 on an invalid UDP media address.
--- net/tipc/udp_media.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
net/tipc/udp_media.c +4 -1
@@ -135,8 +135,11 @@ static int tipc_udp_addr2str(struct tipc_media_addr *a, char *buf, int size)snprintf (buf, size,"%pI4:%u" , &ua->ipv4,ntohs (ua->port)); else if (ntohs(ua->proto) == ETH_P_IPV6) snprintf(buf, size, "%pI6:%u", &ua->ipv6, ntohs(ua->port)); - else + else {pr_err ("Invalid UDP media address\n" ); +return 1 ; + } +return 0 ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 275/484 net: stmmac: Correct byte order of perfect_match
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Simon Horman <[email protected]>
[ Upstream commit e9dbebae2e3c338122716914fe105458f41e3a4a ]
The perfect_match parameter of the update_vlan_hash operation is __le16, and is correctly converted from host byte-order in the lone caller, stmmac_vlan_update().
However, the implementations of this caller, dwxgmac2_update_vlan_hash() and dwxgmac2_update_vlan_hash(), both treat this parameter as host byte order, using the following pattern:
u32 value = ... ... writel(value | perfect_match, ...);
This is not correct because both:
1) value is host byte order; and
2) writel expects a host byte order value as it's first argument
I believe that this will break on big endian systems. And I expect it has gone unnoticed by only being exercised on little endian systems.
The approach taken by this patch is to update the callback, and it's caller to simply use a host byte order value.
Flagged by Sparse.
Compile tested only.
--- drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c | 2 +- drivers/net/ethernet/stmicro/stmmac/dwxgmac2_core.c | 2 +- drivers/net/ethernet/stmicro/stmmac/hwif.h | 2 +- drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 4 ++-- 4 files changed, 5 insertions(+), 5 deletions(-)
drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c +1 -1
@@ -972,7 +972,7 @@ static void dwmac4_set_mac_loopback(void __iomem *ioaddr, bool enable) }static void dwmac4_update_vlan_hash (struct mac_device_info *hw,u32 hash, -__le16 perfect_match,bool is_double) +u16 perfect_match,bool is_double) {void __iomem *ioaddr = hw->pcsr;u32 value;
drivers/net/ethernet/stmicro/stmmac/dwxgmac2_core.c +1 -1
@@ -582,7 +582,7 @@ static int dwxgmac2_rss_configure(struct mac_device_info *hw, }static void dwxgmac2_update_vlan_hash (struct mac_device_info *hw,u32 hash, -__le16 perfect_match,bool is_double) +u16 perfect_match,bool is_double) {void __iomem *ioaddr = hw->pcsr;
drivers/net/ethernet/stmicro/stmmac/hwif.h +1 -1
@@ -370,7 +370,7 @@ struct stmmac_ops { struct stmmac_rss *cfg, u32 num_rxq);/* VLAN */ void (*update_vlan_hash)(struct mac_device_info *hw,u32 hash, -__le16 perfect_match,bool is_double); +u16 perfect_match,bool is_double);void (*enable_vlan)(struct mac_device_info *hw,u32 type); int (*add_hw_vlan_rx_fltr)(struct net_device *dev, struct mac_device_info *hw,
drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +2 -2
@@ -6237,7 +6237,7 @@ static u32 stmmac_vid_crc32_le(__le16 vid_le)static int stmmac_vlan_update (struct stmmac_priv *priv,bool is_double) {u32 crc, hash =0 ; -__le16 pmatch =0 ; +u16 pmatch =0 ;int count =0 ;u16 vid =0 ;
@@ -6252,7 +6252,7 @@ static int stmmac_vlan_update(struct stmmac_priv *priv, bool is_double)if (count >2 )/* VID = 0 always passes filter */ return -EOPNOTSUPP ; - pmatch =cpu_to_le16 (vid); + pmatch = vid; hash =0 ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 276/484 net: nexthop: Initialize all fields in dumped nexthops
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Petr Machata <[email protected]>
[ Upstream commit 6d745cd0e9720282cd291d36b9db528aea18add2 ]
struct nexthop_grp contains two reserved fields that are not initialized by nla_put_nh_group(), and carry garbage. This can be observed e.g. with strace (edited for clarity):
# ip nexthop add id 1 dev lo
# ip nexthop add id 101 group 1
# strace -e recvmsg ip nexthop get id 101
...
recvmsg(... [{nla_len=12, nla_type=NHA_GROUP},
[{id=1, weight=0, resvd1=0x69, resvd2=0x67}]] ...) = 52The fields are reserved and therefore not currently used. But as they are, they leak kernel memory, and the fact they are not just zero complicates repurposing of the fields for new ends. Initialize the full structure.
--- net/ipv4/nexthop.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
net/ipv4/nexthop.c +4 -3
@@ -675,9 +675,10 @@ static int nla_put_nh_group(struct sk_buff *skb, struct nh_group *nhg) p =nla_data (nla);for (i =0 ; i < nhg->num_nh; ++i) { - p->id = nhg->nh_entries[i].nh->id; - p->weight = nhg->nh_entries[i].weight -1 ; - p +=1 ; + *p++ = (struct nexthop_grp ) { + .id = nhg->nh_entries[i].nh->id, + .weight = nhg->nh_entries[i].weight -1 , + }; }if (nhg->resilient &&nla_put_nh_group_res (skb, nhg))
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 277/484 bpf: Fix a segment issue when downgrading gso_size
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Fred Li <[email protected]>
[ Upstream commit fa5ef655615a01533035c6139248c5b33aa27028 ]
Linearize the skb when downgrading gso_size because it may trigger a BUG_ON() later when the skb is segmented as described in [1,2].
--- net/core/filter.c | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-)
net/core/filter.c +11 -4
@@ -3507,13 +3507,20 @@ static int bpf_skb_net_grow(struct sk_buff *skb, u32 off, u32 len_diff,if (skb_is_gso (skb)) {struct skb_shared_info *shinfo =skb_shinfo (skb); -/* Due to header grow, MSS needs to be downgraded. */ -if (!(flags &BPF_F_ADJ_ROOM_FIXED_GSO )) -skb_decrease_gso_size (shinfo, len_diff); -/* Header must be checked, and gso_segs recomputed. */ shinfo->gso_type |= gso_type; shinfo->gso_segs =0 ; + +/* Due to header growth, MSS needs to be downgraded. +* There is a BUG_ON() when segmenting the frag_list with +* head_frag true, so linearize the skb after downgrading +* the MSS. +*/ +if (!(flags &BPF_F_ADJ_ROOM_FIXED_GSO )) { +skb_decrease_gso_size (shinfo, len_diff); +if (shinfo->frag_list) +return skb_linearize (skb); + } }return 0 ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 278/484 mISDN: Fix a use after free in hfcmulti_tx()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dan Carpenter <[email protected]>
[ Upstream commit 61ab751451f5ebd0b98e02276a44e23a10110402 ]
Don't dereference *sp after calling dev_kfree_skb(*sp).
--- drivers/isdn/hardware/mISDN/hfcmulti.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/isdn/hardware/mISDN/hfcmulti.c +4 -3
@@ -1931,7 +1931,7 @@ hfcmulti_dtmf(struct hfc_multi *hc)static void hfcmulti_tx (struct hfc_multi *hc,int ch) { -int i, ii, temp, len =0 ; +int i, ii, temp, tmp_len, len =0 ;int Zspace, z1, z2;/* must be int for calculation */ int Fspace, f1, f2;u_char *d;
@@ -2152,14 +2152,15 @@ hfcmulti_tx(struct hfc_multi *hc, int ch)HFC_wait_nodebug (hc); } + tmp_len = (*sp)->len;dev_kfree_skb (*sp);/* check for next frame */ if (bch &&get_next_bframe (bch)) { - len = (*sp)->len; + len = tmp_len; goto next_frame; }if (dch &&get_next_dframe (dch)) { - len = (*sp)->len; + len = tmp_len; goto next_frame; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 279/484 apparmor: Fix null pointer deref when receiving skb during sock creation
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Xiao Liang <[email protected]>
[ Upstream commit fce09ea314505a52f2436397608fa0a5d0934fb1 ]
The panic below is observed when receiving ICMP packets with secmark set while an ICMP raw socket is being created. SK_CTX(sk)->label is updated in apparmor_socket_post_create(), but the packet is delivered to the socket before that, causing the null pointer dereference. Drop the packet if label context is not set.
BUG: kernel NULL pointer dereference, address: 000000000000004c
#PF: supervisor read access in kernel mode
#PF: error_code(0x0000) - not-present page
PGD 0 P4D 0
Oops: 0000 [#1] PREEMPT SMP NOPTI
CPU: 0 PID: 407 Comm: a.out Not tainted 6.4.12-arch1-1 #1 3e6fa2753a2d75925c34ecb78e22e85a65d083df
Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 05/28/2020
RIP: 0010:aa_label_next_confined+0xb/0x40
Code: 00 00 48 89 ef e8 d5 25 0c 00 e9 66 ff ff ff 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 66 0f 1f 00 0f 1f 44 00 00 89 f0 <8b> 77 4c 39 c6 7e 1f 48 63 d0 48 8d 14 d7 eb 0b 83 c0 01 48 83 c2
RSP: 0018:ffffa92940003b08 EFLAGS: 00010246
RAX: 0000000000000000 RBX: 0000000000000000 RCX: 000000000000000e
RDX: ffffa92940003be8 RSI: 0000000000000000 RDI: 0000000000000000
RBP: ffff8b57471e7800 R08: ffff8b574c642400 R09: 0000000000000002
R10: ffffffffbd820eeb R11: ffffffffbeb7ff00 R12: ffff8b574c642400
R13: 0000000000000001 R14: 0000000000000001 R15: 0000000000000000
FS: 00007fb092ea7640(0000) GS:ffff8b577bc00000(0000) knlGS:0000000000000000
CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
CR2: 000000000000004c CR3: 00000001020f2005 CR4: 00000000007706f0
PKRU: 55555554
Call Trace:
<IRQ>
? __die+0x23/0x70
? page_fault_oops+0x171/0x4e0
? exc_page_fault+0x7f/0x180
? asm_exc_page_fault+0x26/0x30
? aa_label_next_confined+0xb/0x40
apparmor_secmark_check+0xec/0x330
security_sock_rcv_skb+0x35/0x50
sk_filter_trim_cap+0x47/0x250
sock_queue_rcv_skb_reason+0x20/0x60
raw_rcv+0x13c/0x210
raw_local_deliver+0x1f3/0x250
ip_protocol_deliver_rcu+0x4f/0x2f0
ip_local_deliver_finish+0x76/0xa0
__netif_receive_skb_one_core+0x89/0xa0
netif_receive_skb+0x119/0x170
? __netdev_alloc_skb+0x3d/0x140
vmxnet3_rq_rx_complete+0xb23/0x1010 [vmxnet3 56a84f9c97178c57a43a24ec073b45a9d6f01f3a]
vmxnet3_poll_rx_only+0x36/0xb0 [vmxnet3 56a84f9c97178c57a43a24ec073b45a9d6f01f3a]
__napi_poll+0x28/0x1b0
net_rx_action+0x2a4/0x380
__do_softirq+0xd1/0x2c8
__irq_exit_rcu+0xbb/0xf0
common_interrupt+0x86/0xa0
</IRQ>
<TASK>
asm_common_interrupt+0x26/0x40
RIP: 0010:apparmor_socket_post_create+0xb/0x200
Code: 08 48 85 ff 75 a1 eb b1 0f 1f 80 00 00 00 00 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 f3 0f 1e fa 0f 1f 44 00 00 41 54 <55> 48 89 fd 53 45 85 c0 0f 84 b2 00 00 00 48 8b 1d 80 56 3f 02 48
RSP: 0018:ffffa92940ce7e50 EFLAGS: 00000286
RAX: ffffffffbc756440 RBX: 0000000000000000 RCX: 0000000000000001
RDX: 0000000000000003 RSI: 0000000000000002 RDI: ffff8b574eaab740
RBP: 0000000000000001 R08: 0000000000000000 R09: 0000000000000000
R10: ffff8b57444cec70 R11: 0000000000000000 R12: 0000000000000003
R13: 0000000000000002 R14: ffff8b574eaab740 R15: ffffffffbd8e4748
? __pfx_apparmor_socket_post_create+0x10/0x10
security_socket_post_create+0x4b/0x80
__sock_create+0x176/0x1f0
__sys_socket+0x89/0x100
__x64_sys_socket+0x17/0x20
do_syscall_64+0x5d/0x90
? do_syscall_64+0x6c/0x90
? do_syscall_64+0x6c/0x90
? do_syscall_64+0x6c/0x90
entry_SYSCALL_64_after_hwframe+0x72/0xdc--- security/apparmor/lsm.c | 7 +++++++ 1 file changed, 7 insertions(+)
security/apparmor/lsm.c +7 -0
@@ -1057,6 +1057,13 @@ static int apparmor_socket_sock_rcv_skb(struct sock *sk, struct sk_buff *skb)if (!skb->secmark)return 0 ; +/* +* If reach here before socket_post_create hook is called, in which +* case label is null, drop the packet. +*/ +if (!ctx->label) +return -EACCES ; +return apparmor_secmark_check (ctx->label,OP_RECVMSG ,AA_MAY_RECEIVE , skb->secmark, sk); }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 280/484 powerpc: fix a file leak in kvm_vcpu_ioctl_enable_cap()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Al Viro <[email protected]>
[ Upstream commit b4cf5fc01ce83e5c0bcf3dbb9f929428646b9098 ]
missing fdput() on one of the failure exits
--- arch/powerpc/kvm/powerpc.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
arch/powerpc/kvm/powerpc.c +3 -1
@@ -1963,8 +1963,10 @@ static int kvm_vcpu_ioctl_enable_cap(struct kvm_vcpu *vcpu,break ; r = -ENXIO ; -if (!xive_enabled ()) +if (!xive_enabled ()) { +fdput (f);break ; + } r = -EPERM ; dev =kvm_device_from_filp (f.file);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 281/484 lirc: rc_dev_get_from_fd(): fix file leak
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Al Viro <[email protected]>
[ Upstream commit bba1f6758a9ec90c1adac5dcf78f8a15f1bad65b ]
missing fdput() on a failure exit
--- drivers/media/rc/lirc_dev.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/media/rc/lirc_dev.c +3 -1
@@ -841,8 +841,10 @@ struct rc_dev *rc_dev_get_from_fd(int fd, bool write)return ERR_PTR (-EINVAL ); } -if (write && !(f.file->f_mode &FMODE_WRITE )) +if (write && !(f.file->f_mode &FMODE_WRITE )) { +fdput (f);return ERR_PTR (-EPERM ); + } fh = f.file->private_data; dev = fh->rc;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 282/484 spi: spidev: Make probe to fail early if a spidev compatible is used
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Javier Martinez Canillas <[email protected]>
[ Upstream commit fffc84fd87d963a2ea77a125b8a6f5a3c9f3192d ]
Some Device Trees don't use a real device name in the compatible string for SPI devices nodes, abusing the fact that the spidev driver name is used to match as a fallback when a SPI device ID table is not defined.
But since commit 6840615f85f6 ("spi: spidev: Add SPI ID table") a table for SPI device IDs was added to the driver breaking the assumption that these DTs were relying on.
There has been a warning message for some time since commit 956b200a846e ("spi: spidev: Warn loudly if instantiated from DT as "spidev""), making quite clear that this case is not really supported by the spidev driver.
Since these devices won't match anyways after the mentioned commit, there is no point to continue if an spidev compatible is used. Let's just make the driver probe to fail early.
Stable-dep-of: fc28d1c1fe3b ("spi: spidev: add correct compatible for Rohm BH2228FV")
--- drivers/spi/spidev.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/spi/spidev.c +4 -3
@@ -760,9 +760,10 @@ static int spidev_probe(struct spi_device *spi)* compatible string, it is a Linux implementation thing * rather than a description of the hardware. */ -WARN (spi->dev.of_node && -of_device_is_compatible (spi->dev.of_node,"spidev" ), -"%pOF: buggy DT: spidev listed directly in DT\n" , spi->dev.of_node); +if (spi->dev.of_node &&of_device_is_compatible (spi->dev.of_node,"spidev" )) { +dev_err (&spi->dev,"spidev listed directly in DT is not supported\n" ); +return -EINVAL ; + }spidev_probe_acpi (spi);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 283/484 spi: spidev: Replace ACPI specific code by device_get_match_data()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andy Shevchenko <[email protected]>
[ Upstream commit 2a7f669dd8f6561d227e724ca2614c25732f4799 ]
Instead of calling the ACPI specific APIs, use device_get_match_data().
Stable-dep-of: fc28d1c1fe3b ("spi: spidev: add correct compatible for Rohm BH2228FV")
--- drivers/spi/spidev.c | 47 ++++++++++++++++++-------------------------- 1 file changed, 19 insertions(+), 28 deletions(-)
drivers/spi/spidev.c +19 -28
@@ -8,19 +8,20 @@*/ #include <linux/init.h> -#include <linux/module.h> #include <linux/ioctl.h> #include <linux/fs.h> #include <linux/device.h> #include <linux/err.h> #include <linux/list.h> #include <linux/errno.h> +#include <linux/mod_devicetable.h> +#include <linux/module.h> #include <linux/mutex.h> +#include <linux/property.h> #include <linux/slab.h> #include <linux/compat.h> #include <linux/of.h> #include <linux/of_device.h> -#include <linux/acpi.h> #include <linux/spi/spi.h> #include <linux/spi/spidev.h>
@@ -710,10 +711,12 @@ static const struct of_device_id spidev_dt_ids[] = {MODULE_DEVICE_TABLE (of, spidev_dt_ids);#endif -#ifdef CONFIG_ACPI -/* Dummy SPI devices not to be used in production systems */ -#define SPIDEV_ACPI_DUMMY 1 +static int spidev_acpi_check (struct device *dev) +{ +dev_warn (dev,"do not use this driver in production systems!\n" ); +return 0 ; +}static const struct acpi_device_id spidev_acpi_ids[] = {/*
@@ -722,35 +725,18 @@ static const struct acpi_device_id spidev_acpi_ids[] = {* description of the connected peripheral and they should also use * a proper driver instead of poking directly to the SPI bus. */ - { "SPT0001", SPIDEV_ACPI_DUMMY }, - { "SPT0002", SPIDEV_ACPI_DUMMY }, - { "SPT0003", SPIDEV_ACPI_DUMMY }, + { "SPT0001", (kernel_ulong_t)&spidev_acpi_check }, + { "SPT0002", (kernel_ulong_t)&spidev_acpi_check }, + { "SPT0003", (kernel_ulong_t)&spidev_acpi_check }, {}, };MODULE_DEVICE_TABLE (acpi, spidev_acpi_ids); -static void spidev_probe_acpi(struct spi_device *spi) -{ - const struct acpi_device_id *id; - - if (!has_acpi_companion(&spi->dev)) - return; - - id = acpi_match_device(spidev_acpi_ids, &spi->dev); - if (WARN_ON(!id)) - return; - - if (id->driver_data == SPIDEV_ACPI_DUMMY) - dev_warn(&spi->dev, "do not use this driver in production systems!\n"); -} -#else -static inline void spidev_probe_acpi(struct spi_device *spi) {} -#endif -/*-------------------------------------------------------------------------*/ static int spidev_probe (struct spi_device *spi) { +int (*match)(struct device *dev);struct spidev_data *spidev;int status;unsigned long minor;
@@ -765,7 +751,12 @@ static int spidev_probe(struct spi_device *spi)return -EINVAL ; } -spidev_probe_acpi (spi); + match =device_get_match_data (&spi->dev); +if (match) { + status =match (&spi->dev); +if (status) +return status; + }/* Allocate driver data */ spidev =kzalloc (sizeof (*spidev),GFP_KERNEL );
@@ -837,7 +828,7 @@ static struct spi_driver spidev_spi_driver = { .driver = { .name = "spidev", .of_match_table = of_match_ptr(spidev_dt_ids), - .acpi_match_table = ACPI_PTR(spidev_acpi_ids), + .acpi_match_table = spidev_acpi_ids, }, .probe = spidev_probe, .remove = spidev_remove,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 284/484 spi: spidev: Replace OF specific code by device property API
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andy Shevchenko <[email protected]>
[ Upstream commit 88a285192084edab6657e819f7f130f9cfcb0579 ]
Instead of calling the OF specific APIs, use device property ones.
It also prevents misusing PRP0001 in ACPI when trying to instantiate spidev directly. We only support special SPI test devices there.
Stable-dep-of: fc28d1c1fe3b ("spi: spidev: add correct compatible for Rohm BH2228FV")
--- drivers/spi/spidev.c | 45 ++++++++++++++++++++++---------------------- 1 file changed, 22 insertions(+), 23 deletions(-)
drivers/spi/spidev.c +22 -23
@@ -20,8 +20,6 @@#include <linux/property.h> #include <linux/slab.h> #include <linux/compat.h> -#include <linux/of.h> -#include <linux/of_device.h> #include <linux/spi/spi.h> #include <linux/spi/spidev.h>
@@ -696,20 +694,31 @@ static const struct spi_device_id spidev_spi_ids[] = { };MODULE_DEVICE_TABLE (spi, spidev_spi_ids); -#ifdef CONFIG_OF +/* +* spidev should never be referenced in DT without a specific compatible string, +* it is a Linux implementation thing rather than a description of the hardware. +*/ +static int spidev_of_check (struct device *dev) +{ +if (device_property_match_string (dev,"compatible" ,"spidev" ) <0 ) +return 0 ; + +dev_err (dev,"spidev listed directly in DT is not supported\n" ); +return -EINVAL ; +} +static const struct of_device_id spidev_dt_ids[] = { - { .compatible ="rohm,dh2228fv" }, - { .compatible ="lineartechnology,ltc2488" }, - { .compatible ="semtech,sx1301" }, - { .compatible ="lwn,bk4" }, - { .compatible ="dh,dhcom-board" }, - { .compatible ="menlo,m53cpld" }, - { .compatible ="cisco,spi-petra" }, - { .compatible ="micron,spi-authenta" }, + { .compatible ="rohm,dh2228fv" , .data = &spidev_of_check }, + { .compatible ="lineartechnology,ltc2488" , .data = &spidev_of_check }, + { .compatible ="semtech,sx1301" , .data = &spidev_of_check }, + { .compatible ="lwn,bk4" , .data = &spidev_of_check }, + { .compatible ="dh,dhcom-board" , .data = &spidev_of_check }, + { .compatible ="menlo,m53cpld" , .data = &spidev_of_check }, + { .compatible ="cisco,spi-petra" , .data = &spidev_of_check }, + { .compatible ="micron,spi-authenta" , .data = &spidev_of_check }, {}, };MODULE_DEVICE_TABLE (of, spidev_dt_ids); -#endif /* Dummy SPI devices not to be used in production systems */ static int spidev_acpi_check (struct device *dev)
@@ -741,16 +750,6 @@ static int spidev_probe(struct spi_device *spi)int status;unsigned long minor; -/* -* spidev should never be referenced in DT without a specific -* compatible string, it is a Linux implementation thing -* rather than a description of the hardware. -*/ -if (spi->dev.of_node &&of_device_is_compatible (spi->dev.of_node,"spidev" )) { -dev_err (&spi->dev,"spidev listed directly in DT is not supported\n" ); -return -EINVAL ; - } - match =device_get_match_data (&spi->dev);if (match) { status =match (&spi->dev);
@@ -827,7 +826,7 @@ static int spidev_remove(struct spi_device *spi)static struct spi_driver spidev_spi_driver = { .driver = { .name ="spidev" , - .of_match_table =of_match_ptr (spidev_dt_ids), + .of_match_table = spidev_dt_ids, .acpi_match_table = spidev_acpi_ids, }, .probe = spidev_probe,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 285/484 spidev: Add Silicon Labs EM3581 device compatible
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Vincent Tremblay <[email protected]>
[ Upstream commit c67d90e058550403a3e6f9b05bfcdcfa12b1815c ]
Add compatible string for Silicon Labs EM3581 device.
Stable-dep-of: fc28d1c1fe3b ("spi: spidev: add correct compatible for Rohm BH2228FV")
--- drivers/spi/spidev.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/spi/spidev.c +2 -0
@@ -690,6 +690,7 @@ static const struct spi_device_id spidev_spi_ids[] = { { .name = "m53cpld" }, { .name = "spi-petra" }, { .name = "spi-authenta" }, + { .name = "em3581" }, {}, };MODULE_DEVICE_TABLE (spi, spidev_spi_ids);
@@ -716,6 +717,7 @@ static const struct of_device_id spidev_dt_ids[] = { { .compatible = "menlo,m53cpld", .data = &spidev_of_check }, { .compatible = "cisco,spi-petra", .data = &spidev_of_check }, { .compatible = "micron,spi-authenta", .data = &spidev_of_check }, + { .compatible = "silabs,em3581", .data = &spidev_of_check }, {}, };MODULE_DEVICE_TABLE (of, spidev_dt_ids);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 286/484 spi: spidev: order compatibles alphabetically
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Krzysztof Kozlowski <[email protected]>
[ Upstream commit be5852457b7e85ad13b1bded9c97bed5ee1715a3 ]
Bring some order to reduce possibilities of conflicts.
Stable-dep-of: fc28d1c1fe3b ("spi: spidev: add correct compatible for Rohm BH2228FV")
--- drivers/spi/spidev.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
drivers/spi/spidev.c +4 -4
@@ -709,14 +709,14 @@ static int spidev_of_check(struct device *dev) }static const struct of_device_id spidev_dt_ids[] = { - { .compatible ="rohm,dh2228fv" , .data = &spidev_of_check }, + { .compatible ="cisco,spi-petra" , .data = &spidev_of_check }, + { .compatible ="dh,dhcom-board" , .data = &spidev_of_check }, { .compatible ="lineartechnology,ltc2488" , .data = &spidev_of_check }, - { .compatible ="semtech,sx1301" , .data = &spidev_of_check }, { .compatible ="lwn,bk4" , .data = &spidev_of_check }, - { .compatible ="dh,dhcom-board" , .data = &spidev_of_check }, { .compatible ="menlo,m53cpld" , .data = &spidev_of_check }, - { .compatible ="cisco,spi-petra" , .data = &spidev_of_check }, { .compatible ="micron,spi-authenta" , .data = &spidev_of_check }, + { .compatible ="rohm,dh2228fv" , .data = &spidev_of_check }, + { .compatible ="semtech,sx1301" , .data = &spidev_of_check }, { .compatible ="silabs,em3581" , .data = &spidev_of_check }, {}, };
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 287/484 spi: spidev: add correct compatible for Rohm BH2228FV
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Conor Dooley <[email protected]>
[ Upstream commit fc28d1c1fe3b3e2fbc50834c8f73dda72f6af9fc ]
When Maxime originally added the BH2228FV to the spidev driver, he spelt it incorrectly - the d should have been a b. Add the correctly spelt compatible to the driver. Although the majority of users of this compatible are abusers, there is at least one board that validly uses the incorrect spelt compatible, so keep it in the driver to avoid breaking the few real users it has.
--- drivers/spi/spidev.c | 1 + 1 file changed, 1 insertion(+)
drivers/spi/spidev.c +1 -0
@@ -715,6 +715,7 @@ static const struct of_device_id spidev_dt_ids[] = { { .compatible = "lwn,bk4", .data = &spidev_of_check }, { .compatible = "menlo,m53cpld", .data = &spidev_of_check }, { .compatible = "micron,spi-authenta", .data = &spidev_of_check }, + { .compatible = "rohm,bh2228fv", .data = &spidev_of_check }, { .compatible = "rohm,dh2228fv", .data = &spidev_of_check }, { .compatible = "semtech,sx1301", .data = &spidev_of_check }, { .compatible = "silabs,em3581", .data = &spidev_of_check },
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 288/484 ASoC: Intel: use soc_intel_is_byt_cr() only when IOSF_MBI is reachable
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pierre-Louis Bossart <[email protected]>
[ Upstream commit 9931f7d5d251882a147cc5811060097df43e79f5 ]
the Intel kbuild bot reports a link failure when IOSF_MBI is built-in but the Merrifield driver is configured as a module. The soc-intel-quirks.h is included for Merrifield platforms, but IOSF_MBI is not selected for that platform.
ld.lld: error: undefined symbol: iosf_mbi_read
Quoted 2 lines
Quoted 2 lines
Quoted 2 lines
referenced by
atom.c
sound/soc/sof/intel/atom.o:(atom_machine_select) in archive vmlinux.a
This patch forces the use of the fallback static inline when IOSF_MBI is not reachable.
--- sound/soc/intel/common/soc-intel-quirks.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
sound/soc/intel/common/soc-intel-quirks.h +1 -1
@@ -11,7 +11,7 @@#include <linux/platform_data/x86/soc.h> -#if IS_ENABLED (CONFIG_X86 ) +#if IS_REACHABLE (CONFIG_IOSF_MBI )#include <linux/dmi.h> #include <asm/iosf_mbi.h>
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 289/484 ceph: fix incorrect kmalloc size of pagevec mempool
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: ethanwu <[email protected]>
[ Upstream commit 03230edb0bd831662a7c08b6fef66b2a9a817774 ]
The kmalloc size of pagevec mempool is incorrectly calculated.
It misses the size of page pointer and only accounts the number for the array.
--- fs/ceph/super.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
fs/ceph/super.c +2 -1
@@ -783,7 +783,8 @@ static int __init init_caches(void)if (!ceph_mds_request_cachep) goto bad_mds_req; - ceph_wb_pagevec_pool =mempool_create_kmalloc_pool (10 ,CEPH_MAX_WRITE_SIZE >>PAGE_SHIFT ); + ceph_wb_pagevec_pool =mempool_create_kmalloc_pool (10 , + (CEPH_MAX_WRITE_SIZE >>PAGE_SHIFT ) *sizeof (struct page *));if (!ceph_wb_pagevec_pool) goto bad_pagevec_pool;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 290/484 s390/pci: Rework MSI descriptor walk
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Thomas Gleixner <[email protected]>
[ Upstream commit 2ca5e908d0f4cde61d9d3595e8314adca5d914a1 ]
Replace the about to vanish iterators and make use of the filtering.
Stable-dep-of: ab42fcb511fd ("s390/pci: Allow allocation of more than 1 MSI interrupt")
--- arch/s390/pci/pci_irq.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-)
arch/s390/pci/pci_irq.c +2 -4
@@ -303,7 +303,7 @@ int arch_setup_msi_irqs(struct pci_dev *pdev, int nvec, int type)/* Request MSI interrupts */ hwirq = bit; -for_each_pci_msi_entry (msi, pdev) { +msi_for_each_desc (msi, &pdev->dev,MSI_DESC_NOTASSOCIATED ) { rc = -EIO ;if (hwirq - bit >= msi_vecs)break ;
@@ -362,9 +362,7 @@ void arch_teardown_msi_irqs(struct pci_dev *pdev)return ;/* Release MSI interrupts */ -for_each_pci_msi_entry (msi, pdev) { -if (!msi->irq) -continue ; +msi_for_each_desc (msi, &pdev->dev,MSI_DESC_ASSOCIATED ) {irq_set_msi_desc (msi->irq,NULL );irq_free_desc (msi->irq); msi->msg.address_lo =0 ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 291/484 s390/pci: Refactor arch_setup_msi_irqs()
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gerd Bayer <[email protected]>
[ Upstream commit 5fd11b96b43708f2f6e3964412c301c1bd20ec0f ]
Factor out adapter interrupt allocation from arch_setup_msi_irqs() in preparation for enabling registration of multiple MSIs. Code movement only, no change of functionality intended.
Stable-dep-of: ab42fcb511fd ("s390/pci: Allow allocation of more than 1 MSI interrupt")
--- arch/s390/pci/pci_irq.c | 54 ++++++++++++++++++++++++----------------- 1 file changed, 32 insertions(+), 22 deletions(-)
arch/s390/pci/pci_irq.c +32 -22
@@ -262,33 +262,20 @@ static void zpci_floating_irq_handler(struct airq_struct *airq, bool floating) } } -int arch_setup_msi_irqs (struct pci_dev *pdev,int nvec,int type) +static int __alloc_airq (struct zpci_dev *zdev,int msi_vecs, +unsigned long *bit) { -struct zpci_dev *zdev =to_zpci (pdev); -unsigned int hwirq, msi_vecs, cpu; -unsigned long bit; -struct msi_desc *msi; -struct msi_msg msg; -int cpu_addr; -int rc, irq; - - zdev->aisb =-1UL ; - zdev->msi_first_bit =-1U ; -if (type ==PCI_CAP_ID_MSI && nvec >1 ) -return 1 ; - msi_vecs = min_t(unsigned int, nvec, zdev->max_msi); -if (irq_delivery ==DIRECTED ) {/* Allocate cpu vector bits */ - bit =airq_iv_alloc (zpci_ibv[0 ], msi_vecs); -if (bit ==-1UL ) + *bit =airq_iv_alloc (zpci_ibv[0 ], msi_vecs); +if (*bit ==-1UL )return -EIO ; }else {/* Allocate adapter summary indicator bit */ - bit =airq_iv_alloc_bit (zpci_sbv); -if (bit ==-1UL ) + *bit =airq_iv_alloc_bit (zpci_sbv); +if (*bit ==-1UL )return -EIO ; - zdev->aisb = bit; + zdev->aisb = *bit;/* Create adapter interrupt vector */ zdev->aibv =airq_iv_create (msi_vecs,AIRQ_IV_DATA |AIRQ_IV_BITLOCK );
@@ -296,10 +283,33 @@ int arch_setup_msi_irqs(struct pci_dev *pdev, int nvec, int type)return -ENOMEM ;/* Wire up shortcut pointer */ - zpci_ibv[bit] = zdev->aibv; + zpci_ibv[*bit] = zdev->aibv;/* Each function has its own interrupt vector */ - bit =0 ; + *bit =0 ; } +return 0 ; +} + +int arch_setup_msi_irqs (struct pci_dev *pdev,int nvec,int type) +{ +struct zpci_dev *zdev =to_zpci (pdev); +unsigned int hwirq, msi_vecs, cpu; +struct msi_desc *msi; +struct msi_msg msg; +unsigned long bit; +int cpu_addr; +int rc, irq; + + zdev->aisb =-1UL ; + zdev->msi_first_bit =-1U ; + +if (type ==PCI_CAP_ID_MSI && nvec >1 ) +return 1 ; + msi_vecs = min_t(unsigned int, nvec, zdev->max_msi); + + rc =__alloc_airq (zdev, msi_vecs, &bit); +if (rc <0 ) +return rc;/* Request MSI interrupts */ hwirq = bit;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 292/484 s390/pci: Allow allocation of more than 1 MSI interrupt
In reply to Greg Kroah-Hartman5.15-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gerd Bayer <[email protected]>
[ Upstream commit ab42fcb511fd9d241bbab7cc3ca04e34e9fc0666 ]
On a PCI adapter that provides up to 8 MSI interrupt sources the s390 implementation of PCI interrupts rejected to accommodate them, although the underlying hardware is able to support that.
For MSI-X it is sufficient to allocate a single irq_desc per msi_desc, but for MSI multiple irq descriptors are attached to and controlled by a single msi descriptor. Add the appropriate loops to maintain multiple irq descriptors and tie/untie them to/from the appropriate AIBV bit, if a device driver allocates more than 1 MSI interrupt.
Common PCI code passes on requests to allocate a number of interrupt vectors based on the device drivers' demand and the PCI functions' capabilities. However, the root-complex of s390 systems support just a limited number of interrupt vectors per PCI function. Produce a kernel log message to inform about any architecture-specific capping that might be done.
With this change, we had a PCI adapter successfully raising interrupts to its device driver via all 8 sources.
--- arch/s390/pci/pci_irq.c | 62 ++++++++++++++++++++++++++++------------- 1 file changed, 42 insertions(+), 20 deletions(-)
arch/s390/pci/pci_irq.c +42 -20
@@ -292,8 +292,8 @@ static int __alloc_airq(struct zpci_dev *zdev, int msi_vecs,int arch_setup_msi_irqs (struct pci_dev *pdev,int nvec,int type) { +unsigned int hwirq, msi_vecs, irqs_per_msi, i, cpu;struct zpci_dev *zdev =to_zpci (pdev); -unsigned int hwirq, msi_vecs, cpu;struct msi_desc *msi;struct msi_msg msg;unsigned long bit;
@@ -303,30 +303,46 @@ int arch_setup_msi_irqs(struct pci_dev *pdev, int nvec, int type) zdev->aisb =-1UL ; zdev->msi_first_bit =-1U ; -if (type ==PCI_CAP_ID_MSI && nvec >1 ) -return 1 ; msi_vecs = min_t(unsigned int, nvec, zdev->max_msi); +if (msi_vecs < nvec) { +pr_info ("%s requested %d irqs, allocate system limit of %d" , +pci_name (pdev), nvec, zdev->max_msi); + } rc =__alloc_airq (zdev, msi_vecs, &bit);if (rc <0 )return rc; -/* Request MSI interrupts */ +/* +* Request MSI interrupts: +* When using MSI, nvec_used interrupt sources and their irq +* descriptors are controlled through one msi descriptor. +* Thus the outer loop over msi descriptors shall run only once, +* while two inner loops iterate over the interrupt vectors. +* When using MSI-X, each interrupt vector/irq descriptor +* is bound to exactly one msi descriptor (nvec_used is one). +* So the inner loops are executed once, while the outer iterates +* over the MSI-X descriptors. +*/ hwirq = bit;msi_for_each_desc (msi, &pdev->dev,MSI_DESC_NOTASSOCIATED ) { - rc = -EIO ;if (hwirq - bit >= msi_vecs)break ; - irq =__irq_alloc_descs (-1 ,0 ,1 ,0 ,THIS_MODULE , - (irq_delivery ==DIRECTED ) ? - msi->affinity :NULL ); + irqs_per_msi = min_t(unsigned int, msi_vecs, msi->nvec_used); + irq =__irq_alloc_descs (-1 ,0 , irqs_per_msi,0 ,THIS_MODULE , + (irq_delivery ==DIRECTED ) ? + msi->affinity :NULL );if (irq <0 )return -ENOMEM ; - rc =irq_set_msi_desc (irq, msi); -if (rc) -return rc; -irq_set_chip_and_handler (irq, &zpci_irq_chip, - handle_percpu_irq); + +for (i =0 ; i < irqs_per_msi; i++) { + rc =irq_set_msi_desc_off (irq, i, msi); +if (rc) +return rc; +irq_set_chip_and_handler (irq + i, &zpci_irq_chip, + handle_percpu_irq); + } + msg.data = hwirq - bit;if (irq_delivery ==DIRECTED ) {if (msi->affinity)
@@ -339,31 +355,35 @@ int arch_setup_msi_irqs(struct pci_dev *pdev, int nvec, int type) msg.address_lo |= (cpu_addr <<8 );for_each_possible_cpu (cpu) { -airq_iv_set_data (zpci_ibv[cpu], hwirq, irq); +for (i =0 ; i < irqs_per_msi; i++) +airq_iv_set_data (zpci_ibv[cpu], + hwirq + i, irq + i); } }else { msg.address_lo = zdev->msi_addr &0xffffffff ; -airq_iv_set_data (zdev->aibv, hwirq, irq); +for (i =0 ; i < irqs_per_msi; i++) +airq_iv_set_data (zdev->aibv, hwirq + i, irq + i); } msg.address_hi = zdev->msi_addr >>32 ;pci_write_msi_msg (irq, &msg); - hwirq++; + hwirq += irqs_per_msi; } zdev->msi_first_bit = bit; - zdev->msi_nr_irqs = msi_vecs; + zdev->msi_nr_irqs = hwirq - bit; rc =zpci_set_irq (zdev);if (rc)return rc; -return (msi_vecs == nvec) ?0 : msi_vecs; +return (zdev->msi_nr_irqs == nvec) ?0 : zdev->msi_nr_irqs; }void arch_teardown_msi_irqs (struct pci_dev *pdev) {struct zpci_dev *zdev =to_zpci (pdev);struct msi_desc *msi; +unsigned int i;int rc;/* Disable interrupts */
@@ -373,8 +393,10 @@ void arch_teardown_msi_irqs(struct pci_dev *pdev)/* Release MSI interrupts */ msi_for_each_desc (msi, &pdev->dev,MSI_DESC_ASSOCIATED ) { -irq_set_msi_desc (msi->irq,NULL ); -irq_free_desc (msi->irq); +for (i =0 ; i < msi->nvec_used; i++) { +irq_set_msi_desc (msi->irq + i,NULL ); +irq_free_desc (msi->irq + i); + } msi->msg.address_lo =0 ; msi->msg.address_hi =0 ; msi->msg.data =0 ;
Signature · 1 line
2.43.0