1 |
commit: 5f8b01a12b5f1581cc8d5cfbc354ebd06cc2dc02 |
2 |
Author: Mike Pagano <mpagano <AT> gentoo <DOT> org> |
3 |
AuthorDate: Mon Mar 28 10:58:00 2022 +0000 |
4 |
Commit: Mike Pagano <mpagano <AT> gentoo <DOT> org> |
5 |
CommitDate: Mon Mar 28 10:58:00 2022 +0000 |
6 |
URL: https://gitweb.gentoo.org/proj/linux-patches.git/commit/?id=5f8b01a1 |
7 |
|
8 |
Linux patch 5.10.109 |
9 |
|
10 |
Signed-off-by: Mike Pagano <mpagano <AT> gentoo.org> |
11 |
|
12 |
0000_README | 4 + |
13 |
1108_linux-5.10.109.patch | 1481 +++++++++++++++++++++++++++++++++++++++++++++ |
14 |
2 files changed, 1485 insertions(+) |
15 |
|
16 |
diff --git a/0000_README b/0000_README |
17 |
index bf9e37df..e51b86fc 100644 |
18 |
--- a/0000_README |
19 |
+++ b/0000_README |
20 |
@@ -475,6 +475,10 @@ Patch: 1107_linux-5.10.108.patch |
21 |
From: http://www.kernel.org |
22 |
Desc: Linux 5.10.108 |
23 |
|
24 |
+Patch: 1108_linux-5.10.109.patch |
25 |
+From: http://www.kernel.org |
26 |
+Desc: Linux 5.10.109 |
27 |
+ |
28 |
Patch: 1500_XATTR_USER_PREFIX.patch |
29 |
From: https://bugs.gentoo.org/show_bug.cgi?id=470644 |
30 |
Desc: Support for namespace user.pax.* on tmpfs. |
31 |
|
32 |
diff --git a/1108_linux-5.10.109.patch b/1108_linux-5.10.109.patch |
33 |
new file mode 100644 |
34 |
index 00000000..4f325e08 |
35 |
--- /dev/null |
36 |
+++ b/1108_linux-5.10.109.patch |
37 |
@@ -0,0 +1,1481 @@ |
38 |
+diff --git a/Makefile b/Makefile |
39 |
+index 08b3066fe6e53..3b462df1134b6 100644 |
40 |
+--- a/Makefile |
41 |
++++ b/Makefile |
42 |
+@@ -1,7 +1,7 @@ |
43 |
+ # SPDX-License-Identifier: GPL-2.0 |
44 |
+ VERSION = 5 |
45 |
+ PATCHLEVEL = 10 |
46 |
+-SUBLEVEL = 108 |
47 |
++SUBLEVEL = 109 |
48 |
+ EXTRAVERSION = |
49 |
+ NAME = Dare mighty things |
50 |
+ |
51 |
+diff --git a/arch/nds32/include/asm/uaccess.h b/arch/nds32/include/asm/uaccess.h |
52 |
+index 010ba5f1d7dd6..54500e81efe59 100644 |
53 |
+--- a/arch/nds32/include/asm/uaccess.h |
54 |
++++ b/arch/nds32/include/asm/uaccess.h |
55 |
+@@ -70,9 +70,7 @@ static inline void set_fs(mm_segment_t fs) |
56 |
+ * versions are void (ie, don't return a value as such). |
57 |
+ */ |
58 |
+ |
59 |
+-#define get_user __get_user \ |
60 |
+- |
61 |
+-#define __get_user(x, ptr) \ |
62 |
++#define get_user(x, ptr) \ |
63 |
+ ({ \ |
64 |
+ long __gu_err = 0; \ |
65 |
+ __get_user_check((x), (ptr), __gu_err); \ |
66 |
+@@ -85,6 +83,14 @@ static inline void set_fs(mm_segment_t fs) |
67 |
+ (void)0; \ |
68 |
+ }) |
69 |
+ |
70 |
++#define __get_user(x, ptr) \ |
71 |
++({ \ |
72 |
++ long __gu_err = 0; \ |
73 |
++ const __typeof__(*(ptr)) __user *__p = (ptr); \ |
74 |
++ __get_user_err((x), __p, (__gu_err)); \ |
75 |
++ __gu_err; \ |
76 |
++}) |
77 |
++ |
78 |
+ #define __get_user_check(x, ptr, err) \ |
79 |
+ ({ \ |
80 |
+ const __typeof__(*(ptr)) __user *__p = (ptr); \ |
81 |
+@@ -165,12 +171,18 @@ do { \ |
82 |
+ : "r"(addr), "i"(-EFAULT) \ |
83 |
+ : "cc") |
84 |
+ |
85 |
+-#define put_user __put_user \ |
86 |
++#define put_user(x, ptr) \ |
87 |
++({ \ |
88 |
++ long __pu_err = 0; \ |
89 |
++ __put_user_check((x), (ptr), __pu_err); \ |
90 |
++ __pu_err; \ |
91 |
++}) |
92 |
+ |
93 |
+ #define __put_user(x, ptr) \ |
94 |
+ ({ \ |
95 |
+ long __pu_err = 0; \ |
96 |
+- __put_user_err((x), (ptr), __pu_err); \ |
97 |
++ __typeof__(*(ptr)) __user *__p = (ptr); \ |
98 |
++ __put_user_err((x), __p, __pu_err); \ |
99 |
+ __pu_err; \ |
100 |
+ }) |
101 |
+ |
102 |
+diff --git a/arch/x86/kernel/acpi/boot.c b/arch/x86/kernel/acpi/boot.c |
103 |
+index 14cd3186dc77d..55562a9b7f92e 100644 |
104 |
+--- a/arch/x86/kernel/acpi/boot.c |
105 |
++++ b/arch/x86/kernel/acpi/boot.c |
106 |
+@@ -1340,6 +1340,17 @@ static int __init disable_acpi_pci(const struct dmi_system_id *d) |
107 |
+ return 0; |
108 |
+ } |
109 |
+ |
110 |
++static int __init disable_acpi_xsdt(const struct dmi_system_id *d) |
111 |
++{ |
112 |
++ if (!acpi_force) { |
113 |
++ pr_notice("%s detected: force use of acpi=rsdt\n", d->ident); |
114 |
++ acpi_gbl_do_not_use_xsdt = TRUE; |
115 |
++ } else { |
116 |
++ pr_notice("Warning: DMI blacklist says broken, but acpi XSDT forced\n"); |
117 |
++ } |
118 |
++ return 0; |
119 |
++} |
120 |
++ |
121 |
+ static int __init dmi_disable_acpi(const struct dmi_system_id *d) |
122 |
+ { |
123 |
+ if (!acpi_force) { |
124 |
+@@ -1464,6 +1475,19 @@ static const struct dmi_system_id acpi_dmi_table[] __initconst = { |
125 |
+ DMI_MATCH(DMI_PRODUCT_NAME, "TravelMate 360"), |
126 |
+ }, |
127 |
+ }, |
128 |
++ /* |
129 |
++ * Boxes that need ACPI XSDT use disabled due to corrupted tables |
130 |
++ */ |
131 |
++ { |
132 |
++ .callback = disable_acpi_xsdt, |
133 |
++ .ident = "Advantech DAC-BJ01", |
134 |
++ .matches = { |
135 |
++ DMI_MATCH(DMI_SYS_VENDOR, "NEC"), |
136 |
++ DMI_MATCH(DMI_PRODUCT_NAME, "Bearlake CRB Board"), |
137 |
++ DMI_MATCH(DMI_BIOS_VERSION, "V1.12"), |
138 |
++ DMI_MATCH(DMI_BIOS_DATE, "02/01/2011"), |
139 |
++ }, |
140 |
++ }, |
141 |
+ {} |
142 |
+ }; |
143 |
+ |
144 |
+diff --git a/drivers/acpi/battery.c b/drivers/acpi/battery.c |
145 |
+index 2376f57b3617a..be743d177bcbf 100644 |
146 |
+--- a/drivers/acpi/battery.c |
147 |
++++ b/drivers/acpi/battery.c |
148 |
+@@ -66,6 +66,10 @@ MODULE_PARM_DESC(cache_time, "cache time in milliseconds"); |
149 |
+ |
150 |
+ static const struct acpi_device_id battery_device_ids[] = { |
151 |
+ {"PNP0C0A", 0}, |
152 |
++ |
153 |
++ /* Microsoft Surface Go 3 */ |
154 |
++ {"MSHW0146", 0}, |
155 |
++ |
156 |
+ {"", 0}, |
157 |
+ }; |
158 |
+ |
159 |
+@@ -1171,6 +1175,14 @@ static const struct dmi_system_id bat_dmi_table[] __initconst = { |
160 |
+ DMI_MATCH(DMI_PRODUCT_VERSION, "ThinkPad"), |
161 |
+ }, |
162 |
+ }, |
163 |
++ { |
164 |
++ /* Microsoft Surface Go 3 */ |
165 |
++ .callback = battery_notification_delay_quirk, |
166 |
++ .matches = { |
167 |
++ DMI_MATCH(DMI_SYS_VENDOR, "Microsoft Corporation"), |
168 |
++ DMI_MATCH(DMI_PRODUCT_NAME, "Surface Go 3"), |
169 |
++ }, |
170 |
++ }, |
171 |
+ {}, |
172 |
+ }; |
173 |
+ |
174 |
+diff --git a/drivers/acpi/video_detect.c b/drivers/acpi/video_detect.c |
175 |
+index 33474fd969913..7b9793cb55c50 100644 |
176 |
+--- a/drivers/acpi/video_detect.c |
177 |
++++ b/drivers/acpi/video_detect.c |
178 |
+@@ -409,6 +409,81 @@ static const struct dmi_system_id video_detect_dmi_table[] = { |
179 |
+ DMI_MATCH(DMI_PRODUCT_NAME, "GA503"), |
180 |
+ }, |
181 |
+ }, |
182 |
++ /* |
183 |
++ * Clevo NL5xRU and NL5xNU/TUXEDO Aura 15 Gen1 and Gen2 have both a |
184 |
++ * working native and video interface. However the default detection |
185 |
++ * mechanism first registers the video interface before unregistering |
186 |
++ * it again and switching to the native interface during boot. This |
187 |
++ * results in a dangling SBIOS request for backlight change for some |
188 |
++ * reason, causing the backlight to switch to ~2% once per boot on the |
189 |
++ * first power cord connect or disconnect event. Setting the native |
190 |
++ * interface explicitly circumvents this buggy behaviour, by avoiding |
191 |
++ * the unregistering process. |
192 |
++ */ |
193 |
++ { |
194 |
++ .callback = video_detect_force_native, |
195 |
++ .ident = "Clevo NL5xRU", |
196 |
++ .matches = { |
197 |
++ DMI_MATCH(DMI_SYS_VENDOR, "TUXEDO"), |
198 |
++ DMI_MATCH(DMI_BOARD_NAME, "NL5xRU"), |
199 |
++ }, |
200 |
++ }, |
201 |
++ { |
202 |
++ .callback = video_detect_force_native, |
203 |
++ .ident = "Clevo NL5xRU", |
204 |
++ .matches = { |
205 |
++ DMI_MATCH(DMI_SYS_VENDOR, "SchenkerTechnologiesGmbH"), |
206 |
++ DMI_MATCH(DMI_BOARD_NAME, "NL5xRU"), |
207 |
++ }, |
208 |
++ }, |
209 |
++ { |
210 |
++ .callback = video_detect_force_native, |
211 |
++ .ident = "Clevo NL5xRU", |
212 |
++ .matches = { |
213 |
++ DMI_MATCH(DMI_SYS_VENDOR, "Notebook"), |
214 |
++ DMI_MATCH(DMI_BOARD_NAME, "NL5xRU"), |
215 |
++ }, |
216 |
++ }, |
217 |
++ { |
218 |
++ .callback = video_detect_force_native, |
219 |
++ .ident = "Clevo NL5xRU", |
220 |
++ .matches = { |
221 |
++ DMI_MATCH(DMI_SYS_VENDOR, "TUXEDO"), |
222 |
++ DMI_MATCH(DMI_BOARD_NAME, "AURA1501"), |
223 |
++ }, |
224 |
++ }, |
225 |
++ { |
226 |
++ .callback = video_detect_force_native, |
227 |
++ .ident = "Clevo NL5xRU", |
228 |
++ .matches = { |
229 |
++ DMI_MATCH(DMI_SYS_VENDOR, "TUXEDO"), |
230 |
++ DMI_MATCH(DMI_BOARD_NAME, "EDUBOOK1502"), |
231 |
++ }, |
232 |
++ }, |
233 |
++ { |
234 |
++ .callback = video_detect_force_native, |
235 |
++ .ident = "Clevo NL5xNU", |
236 |
++ .matches = { |
237 |
++ DMI_MATCH(DMI_SYS_VENDOR, "TUXEDO"), |
238 |
++ DMI_MATCH(DMI_BOARD_NAME, "NL5xNU"), |
239 |
++ }, |
240 |
++ }, |
241 |
++ { |
242 |
++ .callback = video_detect_force_native, |
243 |
++ .ident = "Clevo NL5xNU", |
244 |
++ .matches = { |
245 |
++ DMI_MATCH(DMI_SYS_VENDOR, "SchenkerTechnologiesGmbH"), |
246 |
++ DMI_MATCH(DMI_BOARD_NAME, "NL5xNU"), |
247 |
++ }, |
248 |
++ }, |
249 |
++ { |
250 |
++ .callback = video_detect_force_native, |
251 |
++ .ident = "Clevo NL5xNU", |
252 |
++ .matches = { |
253 |
++ DMI_MATCH(DMI_SYS_VENDOR, "Notebook"), |
254 |
++ DMI_MATCH(DMI_BOARD_NAME, "NL5xNU"), |
255 |
++ }, |
256 |
++ }, |
257 |
+ |
258 |
+ /* |
259 |
+ * Desktops which falsely report a backlight and which our heuristics |
260 |
+diff --git a/drivers/char/tpm/tpm-dev-common.c b/drivers/char/tpm/tpm-dev-common.c |
261 |
+index 1784530b8387b..b99e1941c52c9 100644 |
262 |
+--- a/drivers/char/tpm/tpm-dev-common.c |
263 |
++++ b/drivers/char/tpm/tpm-dev-common.c |
264 |
+@@ -70,7 +70,13 @@ static void tpm_dev_async_work(struct work_struct *work) |
265 |
+ ret = tpm_dev_transmit(priv->chip, priv->space, priv->data_buffer, |
266 |
+ sizeof(priv->data_buffer)); |
267 |
+ tpm_put_ops(priv->chip); |
268 |
+- if (ret > 0) { |
269 |
++ |
270 |
++ /* |
271 |
++ * If ret is > 0 then tpm_dev_transmit returned the size of the |
272 |
++ * response. If ret is < 0 then tpm_dev_transmit failed and |
273 |
++ * returned an error code. |
274 |
++ */ |
275 |
++ if (ret != 0) { |
276 |
+ priv->response_length = ret; |
277 |
+ mod_timer(&priv->user_read_timer, jiffies + (120 * HZ)); |
278 |
+ } |
279 |
+diff --git a/drivers/char/tpm/tpm2-space.c b/drivers/char/tpm/tpm2-space.c |
280 |
+index 97e916856cf3e..d2225020e4d2c 100644 |
281 |
+--- a/drivers/char/tpm/tpm2-space.c |
282 |
++++ b/drivers/char/tpm/tpm2-space.c |
283 |
+@@ -58,12 +58,12 @@ int tpm2_init_space(struct tpm_space *space, unsigned int buf_size) |
284 |
+ |
285 |
+ void tpm2_del_space(struct tpm_chip *chip, struct tpm_space *space) |
286 |
+ { |
287 |
+- mutex_lock(&chip->tpm_mutex); |
288 |
+- if (!tpm_chip_start(chip)) { |
289 |
++ |
290 |
++ if (tpm_try_get_ops(chip) == 0) { |
291 |
+ tpm2_flush_sessions(chip, space); |
292 |
+- tpm_chip_stop(chip); |
293 |
++ tpm_put_ops(chip); |
294 |
+ } |
295 |
+- mutex_unlock(&chip->tpm_mutex); |
296 |
++ |
297 |
+ kfree(space->context_buf); |
298 |
+ kfree(space->session_buf); |
299 |
+ } |
300 |
+diff --git a/drivers/crypto/qat/qat_common/qat_crypto.c b/drivers/crypto/qat/qat_common/qat_crypto.c |
301 |
+index ab621b7dbd203..9210af8a1f58c 100644 |
302 |
+--- a/drivers/crypto/qat/qat_common/qat_crypto.c |
303 |
++++ b/drivers/crypto/qat/qat_common/qat_crypto.c |
304 |
+@@ -126,6 +126,14 @@ int qat_crypto_dev_config(struct adf_accel_dev *accel_dev) |
305 |
+ goto err; |
306 |
+ if (adf_cfg_section_add(accel_dev, "Accelerator0")) |
307 |
+ goto err; |
308 |
++ |
309 |
++ /* Temporarily set the number of crypto instances to zero to avoid |
310 |
++ * registering the crypto algorithms. |
311 |
++ * This will be removed when the algorithms will support the |
312 |
++ * CRYPTO_TFM_REQ_MAY_BACKLOG flag |
313 |
++ */ |
314 |
++ instances = 0; |
315 |
++ |
316 |
+ for (i = 0; i < instances; i++) { |
317 |
+ val = i; |
318 |
+ snprintf(key, sizeof(key), ADF_CY "%d" ADF_RING_BANK_NUM, i); |
319 |
+diff --git a/drivers/net/ethernet/apm/xgene/xgene_enet_main.c b/drivers/net/ethernet/apm/xgene/xgene_enet_main.c |
320 |
+index 5f1fc6582d74a..78c7cbc372b05 100644 |
321 |
+--- a/drivers/net/ethernet/apm/xgene/xgene_enet_main.c |
322 |
++++ b/drivers/net/ethernet/apm/xgene/xgene_enet_main.c |
323 |
+@@ -696,6 +696,12 @@ static int xgene_enet_rx_frame(struct xgene_enet_desc_ring *rx_ring, |
324 |
+ buf_pool->rx_skb[skb_index] = NULL; |
325 |
+ |
326 |
+ datalen = xgene_enet_get_data_len(le64_to_cpu(raw_desc->m1)); |
327 |
++ |
328 |
++ /* strip off CRC as HW isn't doing this */ |
329 |
++ nv = GET_VAL(NV, le64_to_cpu(raw_desc->m0)); |
330 |
++ if (!nv) |
331 |
++ datalen -= 4; |
332 |
++ |
333 |
+ skb_put(skb, datalen); |
334 |
+ prefetch(skb->data - NET_IP_ALIGN); |
335 |
+ skb->protocol = eth_type_trans(skb, ndev); |
336 |
+@@ -717,12 +723,8 @@ static int xgene_enet_rx_frame(struct xgene_enet_desc_ring *rx_ring, |
337 |
+ } |
338 |
+ } |
339 |
+ |
340 |
+- nv = GET_VAL(NV, le64_to_cpu(raw_desc->m0)); |
341 |
+- if (!nv) { |
342 |
+- /* strip off CRC as HW isn't doing this */ |
343 |
+- datalen -= 4; |
344 |
++ if (!nv) |
345 |
+ goto skip_jumbo; |
346 |
+- } |
347 |
+ |
348 |
+ slots = page_pool->slots - 1; |
349 |
+ head = page_pool->head; |
350 |
+diff --git a/drivers/net/wireless/ath/regd.c b/drivers/net/wireless/ath/regd.c |
351 |
+index bee9110b91f38..20f4f8ea9f894 100644 |
352 |
+--- a/drivers/net/wireless/ath/regd.c |
353 |
++++ b/drivers/net/wireless/ath/regd.c |
354 |
+@@ -666,14 +666,14 @@ ath_regd_init_wiphy(struct ath_regulatory *reg, |
355 |
+ |
356 |
+ /* |
357 |
+ * Some users have reported their EEPROM programmed with |
358 |
+- * 0x8000 or 0x0 set, this is not a supported regulatory |
359 |
+- * domain but since we have more than one user with it we |
360 |
+- * need a solution for them. We default to 0x64, which is |
361 |
+- * the default Atheros world regulatory domain. |
362 |
++ * 0x8000 set, this is not a supported regulatory domain |
363 |
++ * but since we have more than one user with it we need |
364 |
++ * a solution for them. We default to 0x64, which is the |
365 |
++ * default Atheros world regulatory domain. |
366 |
+ */ |
367 |
+ static void ath_regd_sanitize(struct ath_regulatory *reg) |
368 |
+ { |
369 |
+- if (reg->current_rd != COUNTRY_ERD_FLAG && reg->current_rd != 0) |
370 |
++ if (reg->current_rd != COUNTRY_ERD_FLAG) |
371 |
+ return; |
372 |
+ printk(KERN_DEBUG "ath: EEPROM regdomain sanitized\n"); |
373 |
+ reg->current_rd = 0x64; |
374 |
+diff --git a/drivers/net/wireless/ath/wcn36xx/main.c b/drivers/net/wireless/ath/wcn36xx/main.c |
375 |
+index 9aaf6f7473333..37e6e49de3366 100644 |
376 |
+--- a/drivers/net/wireless/ath/wcn36xx/main.c |
377 |
++++ b/drivers/net/wireless/ath/wcn36xx/main.c |
378 |
+@@ -1362,6 +1362,9 @@ static int wcn36xx_platform_get_resources(struct wcn36xx *wcn, |
379 |
+ if (iris_node) { |
380 |
+ if (of_device_is_compatible(iris_node, "qcom,wcn3620")) |
381 |
+ wcn->rf_id = RF_IRIS_WCN3620; |
382 |
++ if (of_device_is_compatible(iris_node, "qcom,wcn3660") || |
383 |
++ of_device_is_compatible(iris_node, "qcom,wcn3660b")) |
384 |
++ wcn->rf_id = RF_IRIS_WCN3660; |
385 |
+ if (of_device_is_compatible(iris_node, "qcom,wcn3680")) |
386 |
+ wcn->rf_id = RF_IRIS_WCN3680; |
387 |
+ of_node_put(iris_node); |
388 |
+diff --git a/drivers/net/wireless/ath/wcn36xx/wcn36xx.h b/drivers/net/wireless/ath/wcn36xx/wcn36xx.h |
389 |
+index 5c40d0bdee245..82be08265c06c 100644 |
390 |
+--- a/drivers/net/wireless/ath/wcn36xx/wcn36xx.h |
391 |
++++ b/drivers/net/wireless/ath/wcn36xx/wcn36xx.h |
392 |
+@@ -96,6 +96,7 @@ enum wcn36xx_ampdu_state { |
393 |
+ |
394 |
+ #define RF_UNKNOWN 0x0000 |
395 |
+ #define RF_IRIS_WCN3620 0x3620 |
396 |
++#define RF_IRIS_WCN3660 0x3660 |
397 |
+ #define RF_IRIS_WCN3680 0x3680 |
398 |
+ |
399 |
+ static inline void buff_to_be(u32 *buf, size_t len) |
400 |
+diff --git a/drivers/nfc/st21nfca/se.c b/drivers/nfc/st21nfca/se.c |
401 |
+index c8bdf078d1115..0841e0e370a03 100644 |
402 |
+--- a/drivers/nfc/st21nfca/se.c |
403 |
++++ b/drivers/nfc/st21nfca/se.c |
404 |
+@@ -320,6 +320,11 @@ int st21nfca_connectivity_event_received(struct nfc_hci_dev *hdev, u8 host, |
405 |
+ return -ENOMEM; |
406 |
+ |
407 |
+ transaction->aid_len = skb->data[1]; |
408 |
++ |
409 |
++ /* Checking if the length of the AID is valid */ |
410 |
++ if (transaction->aid_len > sizeof(transaction->aid)) |
411 |
++ return -EINVAL; |
412 |
++ |
413 |
+ memcpy(transaction->aid, &skb->data[2], |
414 |
+ transaction->aid_len); |
415 |
+ |
416 |
+@@ -329,6 +334,11 @@ int st21nfca_connectivity_event_received(struct nfc_hci_dev *hdev, u8 host, |
417 |
+ return -EPROTO; |
418 |
+ |
419 |
+ transaction->params_len = skb->data[transaction->aid_len + 3]; |
420 |
++ |
421 |
++ /* Total size is allocated (skb->len - 2) minus fixed array members */ |
422 |
++ if (transaction->params_len > ((skb->len - 2) - sizeof(struct nfc_evt_transaction))) |
423 |
++ return -EINVAL; |
424 |
++ |
425 |
+ memcpy(transaction->params, skb->data + |
426 |
+ transaction->aid_len + 4, transaction->params_len); |
427 |
+ |
428 |
+diff --git a/drivers/staging/fbtft/fb_st7789v.c b/drivers/staging/fbtft/fb_st7789v.c |
429 |
+index 3a280cc1892ca..0a2dbed9ffc74 100644 |
430 |
+--- a/drivers/staging/fbtft/fb_st7789v.c |
431 |
++++ b/drivers/staging/fbtft/fb_st7789v.c |
432 |
+@@ -82,6 +82,8 @@ enum st7789v_command { |
433 |
+ */ |
434 |
+ static int init_display(struct fbtft_par *par) |
435 |
+ { |
436 |
++ par->fbtftops.reset(par); |
437 |
++ |
438 |
+ /* turn off sleep mode */ |
439 |
+ write_reg(par, MIPI_DCS_EXIT_SLEEP_MODE); |
440 |
+ mdelay(120); |
441 |
+diff --git a/fs/exfat/super.c b/fs/exfat/super.c |
442 |
+index cd04c912f02e0..ba70ed1c98049 100644 |
443 |
+--- a/fs/exfat/super.c |
444 |
++++ b/fs/exfat/super.c |
445 |
+@@ -690,7 +690,7 @@ static int exfat_fill_super(struct super_block *sb, struct fs_context *fc) |
446 |
+ if (!sb->s_root) { |
447 |
+ exfat_err(sb, "failed to get the root dentry"); |
448 |
+ err = -ENOMEM; |
449 |
+- goto put_inode; |
450 |
++ goto free_table; |
451 |
+ } |
452 |
+ |
453 |
+ return 0; |
454 |
+diff --git a/include/sound/pcm.h b/include/sound/pcm.h |
455 |
+index 2336bf9243e18..ab966563e852e 100644 |
456 |
+--- a/include/sound/pcm.h |
457 |
++++ b/include/sound/pcm.h |
458 |
+@@ -398,6 +398,7 @@ struct snd_pcm_runtime { |
459 |
+ wait_queue_head_t tsleep; /* transfer sleep */ |
460 |
+ struct fasync_struct *fasync; |
461 |
+ bool stop_operating; /* sync_stop will be called */ |
462 |
++ struct mutex buffer_mutex; /* protect for buffer changes */ |
463 |
+ |
464 |
+ /* -- private section -- */ |
465 |
+ void *private_data; |
466 |
+diff --git a/kernel/cgroup/cgroup-internal.h b/kernel/cgroup/cgroup-internal.h |
467 |
+index bfbeabc17a9df..6e36e854b5124 100644 |
468 |
+--- a/kernel/cgroup/cgroup-internal.h |
469 |
++++ b/kernel/cgroup/cgroup-internal.h |
470 |
+@@ -65,6 +65,25 @@ static inline struct cgroup_fs_context *cgroup_fc2context(struct fs_context *fc) |
471 |
+ return container_of(kfc, struct cgroup_fs_context, kfc); |
472 |
+ } |
473 |
+ |
474 |
++struct cgroup_pidlist; |
475 |
++ |
476 |
++struct cgroup_file_ctx { |
477 |
++ struct cgroup_namespace *ns; |
478 |
++ |
479 |
++ struct { |
480 |
++ void *trigger; |
481 |
++ } psi; |
482 |
++ |
483 |
++ struct { |
484 |
++ bool started; |
485 |
++ struct css_task_iter iter; |
486 |
++ } procs; |
487 |
++ |
488 |
++ struct { |
489 |
++ struct cgroup_pidlist *pidlist; |
490 |
++ } procs1; |
491 |
++}; |
492 |
++ |
493 |
+ /* |
494 |
+ * A cgroup can be associated with multiple css_sets as different tasks may |
495 |
+ * belong to different cgroups on different hierarchies. In the other |
496 |
+diff --git a/kernel/cgroup/cgroup-v1.c b/kernel/cgroup/cgroup-v1.c |
497 |
+index 69fba563c810e..8f0ea12d7cee2 100644 |
498 |
+--- a/kernel/cgroup/cgroup-v1.c |
499 |
++++ b/kernel/cgroup/cgroup-v1.c |
500 |
+@@ -393,6 +393,7 @@ static void *cgroup_pidlist_start(struct seq_file *s, loff_t *pos) |
501 |
+ * next pid to display, if any |
502 |
+ */ |
503 |
+ struct kernfs_open_file *of = s->private; |
504 |
++ struct cgroup_file_ctx *ctx = of->priv; |
505 |
+ struct cgroup *cgrp = seq_css(s)->cgroup; |
506 |
+ struct cgroup_pidlist *l; |
507 |
+ enum cgroup_filetype type = seq_cft(s)->private; |
508 |
+@@ -402,25 +403,24 @@ static void *cgroup_pidlist_start(struct seq_file *s, loff_t *pos) |
509 |
+ mutex_lock(&cgrp->pidlist_mutex); |
510 |
+ |
511 |
+ /* |
512 |
+- * !NULL @of->priv indicates that this isn't the first start() |
513 |
+- * after open. If the matching pidlist is around, we can use that. |
514 |
+- * Look for it. Note that @of->priv can't be used directly. It |
515 |
+- * could already have been destroyed. |
516 |
++ * !NULL @ctx->procs1.pidlist indicates that this isn't the first |
517 |
++ * start() after open. If the matching pidlist is around, we can use |
518 |
++ * that. Look for it. Note that @ctx->procs1.pidlist can't be used |
519 |
++ * directly. It could already have been destroyed. |
520 |
+ */ |
521 |
+- if (of->priv) |
522 |
+- of->priv = cgroup_pidlist_find(cgrp, type); |
523 |
++ if (ctx->procs1.pidlist) |
524 |
++ ctx->procs1.pidlist = cgroup_pidlist_find(cgrp, type); |
525 |
+ |
526 |
+ /* |
527 |
+ * Either this is the first start() after open or the matching |
528 |
+ * pidlist has been destroyed inbetween. Create a new one. |
529 |
+ */ |
530 |
+- if (!of->priv) { |
531 |
+- ret = pidlist_array_load(cgrp, type, |
532 |
+- (struct cgroup_pidlist **)&of->priv); |
533 |
++ if (!ctx->procs1.pidlist) { |
534 |
++ ret = pidlist_array_load(cgrp, type, &ctx->procs1.pidlist); |
535 |
+ if (ret) |
536 |
+ return ERR_PTR(ret); |
537 |
+ } |
538 |
+- l = of->priv; |
539 |
++ l = ctx->procs1.pidlist; |
540 |
+ |
541 |
+ if (pid) { |
542 |
+ int end = l->length; |
543 |
+@@ -448,7 +448,8 @@ static void *cgroup_pidlist_start(struct seq_file *s, loff_t *pos) |
544 |
+ static void cgroup_pidlist_stop(struct seq_file *s, void *v) |
545 |
+ { |
546 |
+ struct kernfs_open_file *of = s->private; |
547 |
+- struct cgroup_pidlist *l = of->priv; |
548 |
++ struct cgroup_file_ctx *ctx = of->priv; |
549 |
++ struct cgroup_pidlist *l = ctx->procs1.pidlist; |
550 |
+ |
551 |
+ if (l) |
552 |
+ mod_delayed_work(cgroup_pidlist_destroy_wq, &l->destroy_dwork, |
553 |
+@@ -459,7 +460,8 @@ static void cgroup_pidlist_stop(struct seq_file *s, void *v) |
554 |
+ static void *cgroup_pidlist_next(struct seq_file *s, void *v, loff_t *pos) |
555 |
+ { |
556 |
+ struct kernfs_open_file *of = s->private; |
557 |
+- struct cgroup_pidlist *l = of->priv; |
558 |
++ struct cgroup_file_ctx *ctx = of->priv; |
559 |
++ struct cgroup_pidlist *l = ctx->procs1.pidlist; |
560 |
+ pid_t *p = v; |
561 |
+ pid_t *end = l->list + l->length; |
562 |
+ /* |
563 |
+@@ -542,6 +544,7 @@ static ssize_t cgroup_release_agent_write(struct kernfs_open_file *of, |
564 |
+ char *buf, size_t nbytes, loff_t off) |
565 |
+ { |
566 |
+ struct cgroup *cgrp; |
567 |
++ struct cgroup_file_ctx *ctx; |
568 |
+ |
569 |
+ BUILD_BUG_ON(sizeof(cgrp->root->release_agent_path) < PATH_MAX); |
570 |
+ |
571 |
+@@ -549,8 +552,9 @@ static ssize_t cgroup_release_agent_write(struct kernfs_open_file *of, |
572 |
+ * Release agent gets called with all capabilities, |
573 |
+ * require capabilities to set release agent. |
574 |
+ */ |
575 |
+- if ((of->file->f_cred->user_ns != &init_user_ns) || |
576 |
+- !capable(CAP_SYS_ADMIN)) |
577 |
++ ctx = of->priv; |
578 |
++ if ((ctx->ns->user_ns != &init_user_ns) || |
579 |
++ !file_ns_capable(of->file, &init_user_ns, CAP_SYS_ADMIN)) |
580 |
+ return -EPERM; |
581 |
+ |
582 |
+ cgrp = cgroup_kn_lock_live(of->kn, false); |
583 |
+diff --git a/kernel/cgroup/cgroup.c b/kernel/cgroup/cgroup.c |
584 |
+index 4927289a91a97..3f8447a5393e9 100644 |
585 |
+--- a/kernel/cgroup/cgroup.c |
586 |
++++ b/kernel/cgroup/cgroup.c |
587 |
+@@ -3590,6 +3590,7 @@ static int cgroup_cpu_pressure_show(struct seq_file *seq, void *v) |
588 |
+ static ssize_t cgroup_pressure_write(struct kernfs_open_file *of, char *buf, |
589 |
+ size_t nbytes, enum psi_res res) |
590 |
+ { |
591 |
++ struct cgroup_file_ctx *ctx = of->priv; |
592 |
+ struct psi_trigger *new; |
593 |
+ struct cgroup *cgrp; |
594 |
+ struct psi_group *psi; |
595 |
+@@ -3602,7 +3603,7 @@ static ssize_t cgroup_pressure_write(struct kernfs_open_file *of, char *buf, |
596 |
+ cgroup_kn_unlock(of->kn); |
597 |
+ |
598 |
+ /* Allow only one trigger per file descriptor */ |
599 |
+- if (of->priv) { |
600 |
++ if (ctx->psi.trigger) { |
601 |
+ cgroup_put(cgrp); |
602 |
+ return -EBUSY; |
603 |
+ } |
604 |
+@@ -3614,7 +3615,7 @@ static ssize_t cgroup_pressure_write(struct kernfs_open_file *of, char *buf, |
605 |
+ return PTR_ERR(new); |
606 |
+ } |
607 |
+ |
608 |
+- smp_store_release(&of->priv, new); |
609 |
++ smp_store_release(&ctx->psi.trigger, new); |
610 |
+ cgroup_put(cgrp); |
611 |
+ |
612 |
+ return nbytes; |
613 |
+@@ -3644,12 +3645,15 @@ static ssize_t cgroup_cpu_pressure_write(struct kernfs_open_file *of, |
614 |
+ static __poll_t cgroup_pressure_poll(struct kernfs_open_file *of, |
615 |
+ poll_table *pt) |
616 |
+ { |
617 |
+- return psi_trigger_poll(&of->priv, of->file, pt); |
618 |
++ struct cgroup_file_ctx *ctx = of->priv; |
619 |
++ return psi_trigger_poll(&ctx->psi.trigger, of->file, pt); |
620 |
+ } |
621 |
+ |
622 |
+ static void cgroup_pressure_release(struct kernfs_open_file *of) |
623 |
+ { |
624 |
+- psi_trigger_destroy(of->priv); |
625 |
++ struct cgroup_file_ctx *ctx = of->priv; |
626 |
++ |
627 |
++ psi_trigger_destroy(ctx->psi.trigger); |
628 |
+ } |
629 |
+ #endif /* CONFIG_PSI */ |
630 |
+ |
631 |
+@@ -3690,24 +3694,43 @@ static ssize_t cgroup_freeze_write(struct kernfs_open_file *of, |
632 |
+ static int cgroup_file_open(struct kernfs_open_file *of) |
633 |
+ { |
634 |
+ struct cftype *cft = of->kn->priv; |
635 |
++ struct cgroup_file_ctx *ctx; |
636 |
++ int ret; |
637 |
+ |
638 |
+- if (cft->open) |
639 |
+- return cft->open(of); |
640 |
+- return 0; |
641 |
++ ctx = kzalloc(sizeof(*ctx), GFP_KERNEL); |
642 |
++ if (!ctx) |
643 |
++ return -ENOMEM; |
644 |
++ |
645 |
++ ctx->ns = current->nsproxy->cgroup_ns; |
646 |
++ get_cgroup_ns(ctx->ns); |
647 |
++ of->priv = ctx; |
648 |
++ |
649 |
++ if (!cft->open) |
650 |
++ return 0; |
651 |
++ |
652 |
++ ret = cft->open(of); |
653 |
++ if (ret) { |
654 |
++ put_cgroup_ns(ctx->ns); |
655 |
++ kfree(ctx); |
656 |
++ } |
657 |
++ return ret; |
658 |
+ } |
659 |
+ |
660 |
+ static void cgroup_file_release(struct kernfs_open_file *of) |
661 |
+ { |
662 |
+ struct cftype *cft = of->kn->priv; |
663 |
++ struct cgroup_file_ctx *ctx = of->priv; |
664 |
+ |
665 |
+ if (cft->release) |
666 |
+ cft->release(of); |
667 |
++ put_cgroup_ns(ctx->ns); |
668 |
++ kfree(ctx); |
669 |
+ } |
670 |
+ |
671 |
+ static ssize_t cgroup_file_write(struct kernfs_open_file *of, char *buf, |
672 |
+ size_t nbytes, loff_t off) |
673 |
+ { |
674 |
+- struct cgroup_namespace *ns = current->nsproxy->cgroup_ns; |
675 |
++ struct cgroup_file_ctx *ctx = of->priv; |
676 |
+ struct cgroup *cgrp = of->kn->parent->priv; |
677 |
+ struct cftype *cft = of->kn->priv; |
678 |
+ struct cgroup_subsys_state *css; |
679 |
+@@ -3724,7 +3747,7 @@ static ssize_t cgroup_file_write(struct kernfs_open_file *of, char *buf, |
680 |
+ */ |
681 |
+ if ((cgrp->root->flags & CGRP_ROOT_NS_DELEGATE) && |
682 |
+ !(cft->flags & CFTYPE_NS_DELEGATABLE) && |
683 |
+- ns != &init_cgroup_ns && ns->root_cset->dfl_cgrp == cgrp) |
684 |
++ ctx->ns != &init_cgroup_ns && ctx->ns->root_cset->dfl_cgrp == cgrp) |
685 |
+ return -EPERM; |
686 |
+ |
687 |
+ if (cft->write) |
688 |
+@@ -4625,21 +4648,21 @@ void css_task_iter_end(struct css_task_iter *it) |
689 |
+ |
690 |
+ static void cgroup_procs_release(struct kernfs_open_file *of) |
691 |
+ { |
692 |
+- if (of->priv) { |
693 |
+- css_task_iter_end(of->priv); |
694 |
+- kfree(of->priv); |
695 |
+- } |
696 |
++ struct cgroup_file_ctx *ctx = of->priv; |
697 |
++ |
698 |
++ if (ctx->procs.started) |
699 |
++ css_task_iter_end(&ctx->procs.iter); |
700 |
+ } |
701 |
+ |
702 |
+ static void *cgroup_procs_next(struct seq_file *s, void *v, loff_t *pos) |
703 |
+ { |
704 |
+ struct kernfs_open_file *of = s->private; |
705 |
+- struct css_task_iter *it = of->priv; |
706 |
++ struct cgroup_file_ctx *ctx = of->priv; |
707 |
+ |
708 |
+ if (pos) |
709 |
+ (*pos)++; |
710 |
+ |
711 |
+- return css_task_iter_next(it); |
712 |
++ return css_task_iter_next(&ctx->procs.iter); |
713 |
+ } |
714 |
+ |
715 |
+ static void *__cgroup_procs_start(struct seq_file *s, loff_t *pos, |
716 |
+@@ -4647,21 +4670,18 @@ static void *__cgroup_procs_start(struct seq_file *s, loff_t *pos, |
717 |
+ { |
718 |
+ struct kernfs_open_file *of = s->private; |
719 |
+ struct cgroup *cgrp = seq_css(s)->cgroup; |
720 |
+- struct css_task_iter *it = of->priv; |
721 |
++ struct cgroup_file_ctx *ctx = of->priv; |
722 |
++ struct css_task_iter *it = &ctx->procs.iter; |
723 |
+ |
724 |
+ /* |
725 |
+ * When a seq_file is seeked, it's always traversed sequentially |
726 |
+ * from position 0, so we can simply keep iterating on !0 *pos. |
727 |
+ */ |
728 |
+- if (!it) { |
729 |
++ if (!ctx->procs.started) { |
730 |
+ if (WARN_ON_ONCE((*pos))) |
731 |
+ return ERR_PTR(-EINVAL); |
732 |
+- |
733 |
+- it = kzalloc(sizeof(*it), GFP_KERNEL); |
734 |
+- if (!it) |
735 |
+- return ERR_PTR(-ENOMEM); |
736 |
+- of->priv = it; |
737 |
+ css_task_iter_start(&cgrp->self, iter_flags, it); |
738 |
++ ctx->procs.started = true; |
739 |
+ } else if (!(*pos)) { |
740 |
+ css_task_iter_end(it); |
741 |
+ css_task_iter_start(&cgrp->self, iter_flags, it); |
742 |
+@@ -4712,9 +4732,9 @@ static int cgroup_may_write(const struct cgroup *cgrp, struct super_block *sb) |
743 |
+ |
744 |
+ static int cgroup_procs_write_permission(struct cgroup *src_cgrp, |
745 |
+ struct cgroup *dst_cgrp, |
746 |
+- struct super_block *sb) |
747 |
++ struct super_block *sb, |
748 |
++ struct cgroup_namespace *ns) |
749 |
+ { |
750 |
+- struct cgroup_namespace *ns = current->nsproxy->cgroup_ns; |
751 |
+ struct cgroup *com_cgrp = src_cgrp; |
752 |
+ int ret; |
753 |
+ |
754 |
+@@ -4743,11 +4763,12 @@ static int cgroup_procs_write_permission(struct cgroup *src_cgrp, |
755 |
+ |
756 |
+ static int cgroup_attach_permissions(struct cgroup *src_cgrp, |
757 |
+ struct cgroup *dst_cgrp, |
758 |
+- struct super_block *sb, bool threadgroup) |
759 |
++ struct super_block *sb, bool threadgroup, |
760 |
++ struct cgroup_namespace *ns) |
761 |
+ { |
762 |
+ int ret = 0; |
763 |
+ |
764 |
+- ret = cgroup_procs_write_permission(src_cgrp, dst_cgrp, sb); |
765 |
++ ret = cgroup_procs_write_permission(src_cgrp, dst_cgrp, sb, ns); |
766 |
+ if (ret) |
767 |
+ return ret; |
768 |
+ |
769 |
+@@ -4764,6 +4785,7 @@ static int cgroup_attach_permissions(struct cgroup *src_cgrp, |
770 |
+ static ssize_t cgroup_procs_write(struct kernfs_open_file *of, |
771 |
+ char *buf, size_t nbytes, loff_t off) |
772 |
+ { |
773 |
++ struct cgroup_file_ctx *ctx = of->priv; |
774 |
+ struct cgroup *src_cgrp, *dst_cgrp; |
775 |
+ struct task_struct *task; |
776 |
+ ssize_t ret; |
777 |
+@@ -4784,7 +4806,8 @@ static ssize_t cgroup_procs_write(struct kernfs_open_file *of, |
778 |
+ spin_unlock_irq(&css_set_lock); |
779 |
+ |
780 |
+ ret = cgroup_attach_permissions(src_cgrp, dst_cgrp, |
781 |
+- of->file->f_path.dentry->d_sb, true); |
782 |
++ of->file->f_path.dentry->d_sb, true, |
783 |
++ ctx->ns); |
784 |
+ if (ret) |
785 |
+ goto out_finish; |
786 |
+ |
787 |
+@@ -4806,6 +4829,7 @@ static void *cgroup_threads_start(struct seq_file *s, loff_t *pos) |
788 |
+ static ssize_t cgroup_threads_write(struct kernfs_open_file *of, |
789 |
+ char *buf, size_t nbytes, loff_t off) |
790 |
+ { |
791 |
++ struct cgroup_file_ctx *ctx = of->priv; |
792 |
+ struct cgroup *src_cgrp, *dst_cgrp; |
793 |
+ struct task_struct *task; |
794 |
+ ssize_t ret; |
795 |
+@@ -4829,7 +4853,8 @@ static ssize_t cgroup_threads_write(struct kernfs_open_file *of, |
796 |
+ |
797 |
+ /* thread migrations follow the cgroup.procs delegation rule */ |
798 |
+ ret = cgroup_attach_permissions(src_cgrp, dst_cgrp, |
799 |
+- of->file->f_path.dentry->d_sb, false); |
800 |
++ of->file->f_path.dentry->d_sb, false, |
801 |
++ ctx->ns); |
802 |
+ if (ret) |
803 |
+ goto out_finish; |
804 |
+ |
805 |
+@@ -6009,7 +6034,8 @@ static int cgroup_css_set_fork(struct kernel_clone_args *kargs) |
806 |
+ goto err; |
807 |
+ |
808 |
+ ret = cgroup_attach_permissions(cset->dfl_cgrp, dst_cgrp, sb, |
809 |
+- !(kargs->flags & CLONE_THREAD)); |
810 |
++ !(kargs->flags & CLONE_THREAD), |
811 |
++ current->nsproxy->cgroup_ns); |
812 |
+ if (ret) |
813 |
+ goto err; |
814 |
+ |
815 |
+diff --git a/kernel/rcu/tree_plugin.h b/kernel/rcu/tree_plugin.h |
816 |
+index 658427c33b937..f5ba0740f9b50 100644 |
817 |
+--- a/kernel/rcu/tree_plugin.h |
818 |
++++ b/kernel/rcu/tree_plugin.h |
819 |
+@@ -531,16 +531,17 @@ rcu_preempt_deferred_qs_irqrestore(struct task_struct *t, unsigned long flags) |
820 |
+ raw_spin_unlock_irqrestore_rcu_node(rnp, flags); |
821 |
+ } |
822 |
+ |
823 |
+- /* Unboost if we were boosted. */ |
824 |
+- if (IS_ENABLED(CONFIG_RCU_BOOST) && drop_boost_mutex) |
825 |
+- rt_mutex_futex_unlock(&rnp->boost_mtx); |
826 |
+- |
827 |
+ /* |
828 |
+ * If this was the last task on the expedited lists, |
829 |
+ * then we need to report up the rcu_node hierarchy. |
830 |
+ */ |
831 |
+ if (!empty_exp && empty_exp_now) |
832 |
+ rcu_report_exp_rnp(rnp, true); |
833 |
++ |
834 |
++ /* Unboost if we were boosted. */ |
835 |
++ if (IS_ENABLED(CONFIG_RCU_BOOST) && drop_boost_mutex) |
836 |
++ rt_mutex_futex_unlock(&rnp->boost_mtx); |
837 |
++ |
838 |
+ } else { |
839 |
+ local_irq_restore(flags); |
840 |
+ } |
841 |
+diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c |
842 |
+index d6f2126f46184..2aa39ce7093df 100644 |
843 |
+--- a/net/ipv6/ip6_output.c |
844 |
++++ b/net/ipv6/ip6_output.c |
845 |
+@@ -1500,8 +1500,8 @@ static int __ip6_append_data(struct sock *sk, |
846 |
+ sizeof(struct frag_hdr) : 0) + |
847 |
+ rt->rt6i_nfheader_len; |
848 |
+ |
849 |
+- if (mtu < fragheaderlen || |
850 |
+- ((mtu - fragheaderlen) & ~7) + fragheaderlen < sizeof(struct frag_hdr)) |
851 |
++ if (mtu <= fragheaderlen || |
852 |
++ ((mtu - fragheaderlen) & ~7) + fragheaderlen <= sizeof(struct frag_hdr)) |
853 |
+ goto emsgsize; |
854 |
+ |
855 |
+ maxfraglen = ((mtu - fragheaderlen) & ~7) + fragheaderlen - |
856 |
+diff --git a/net/llc/af_llc.c b/net/llc/af_llc.c |
857 |
+index ac5cadd02cfa8..99a37c411323e 100644 |
858 |
+--- a/net/llc/af_llc.c |
859 |
++++ b/net/llc/af_llc.c |
860 |
+@@ -276,6 +276,7 @@ static int llc_ui_autobind(struct socket *sock, struct sockaddr_llc *addr) |
861 |
+ { |
862 |
+ struct sock *sk = sock->sk; |
863 |
+ struct llc_sock *llc = llc_sk(sk); |
864 |
++ struct net_device *dev = NULL; |
865 |
+ struct llc_sap *sap; |
866 |
+ int rc = -EINVAL; |
867 |
+ |
868 |
+@@ -287,14 +288,14 @@ static int llc_ui_autobind(struct socket *sock, struct sockaddr_llc *addr) |
869 |
+ goto out; |
870 |
+ rc = -ENODEV; |
871 |
+ if (sk->sk_bound_dev_if) { |
872 |
+- llc->dev = dev_get_by_index(&init_net, sk->sk_bound_dev_if); |
873 |
+- if (llc->dev && addr->sllc_arphrd != llc->dev->type) { |
874 |
+- dev_put(llc->dev); |
875 |
+- llc->dev = NULL; |
876 |
++ dev = dev_get_by_index(&init_net, sk->sk_bound_dev_if); |
877 |
++ if (dev && addr->sllc_arphrd != dev->type) { |
878 |
++ dev_put(dev); |
879 |
++ dev = NULL; |
880 |
+ } |
881 |
+ } else |
882 |
+- llc->dev = dev_getfirstbyhwtype(&init_net, addr->sllc_arphrd); |
883 |
+- if (!llc->dev) |
884 |
++ dev = dev_getfirstbyhwtype(&init_net, addr->sllc_arphrd); |
885 |
++ if (!dev) |
886 |
+ goto out; |
887 |
+ rc = -EUSERS; |
888 |
+ llc->laddr.lsap = llc_ui_autoport(); |
889 |
+@@ -304,6 +305,11 @@ static int llc_ui_autobind(struct socket *sock, struct sockaddr_llc *addr) |
890 |
+ sap = llc_sap_open(llc->laddr.lsap, NULL); |
891 |
+ if (!sap) |
892 |
+ goto out; |
893 |
++ |
894 |
++ /* Note: We do not expect errors from this point. */ |
895 |
++ llc->dev = dev; |
896 |
++ dev = NULL; |
897 |
++ |
898 |
+ memcpy(llc->laddr.mac, llc->dev->dev_addr, IFHWADDRLEN); |
899 |
+ memcpy(&llc->addr, addr, sizeof(llc->addr)); |
900 |
+ /* assign new connection to its SAP */ |
901 |
+@@ -311,6 +317,7 @@ static int llc_ui_autobind(struct socket *sock, struct sockaddr_llc *addr) |
902 |
+ sock_reset_flag(sk, SOCK_ZAPPED); |
903 |
+ rc = 0; |
904 |
+ out: |
905 |
++ dev_put(dev); |
906 |
+ return rc; |
907 |
+ } |
908 |
+ |
909 |
+@@ -333,6 +340,7 @@ static int llc_ui_bind(struct socket *sock, struct sockaddr *uaddr, int addrlen) |
910 |
+ struct sockaddr_llc *addr = (struct sockaddr_llc *)uaddr; |
911 |
+ struct sock *sk = sock->sk; |
912 |
+ struct llc_sock *llc = llc_sk(sk); |
913 |
++ struct net_device *dev = NULL; |
914 |
+ struct llc_sap *sap; |
915 |
+ int rc = -EINVAL; |
916 |
+ |
917 |
+@@ -348,25 +356,26 @@ static int llc_ui_bind(struct socket *sock, struct sockaddr *uaddr, int addrlen) |
918 |
+ rc = -ENODEV; |
919 |
+ rcu_read_lock(); |
920 |
+ if (sk->sk_bound_dev_if) { |
921 |
+- llc->dev = dev_get_by_index_rcu(&init_net, sk->sk_bound_dev_if); |
922 |
+- if (llc->dev) { |
923 |
++ dev = dev_get_by_index_rcu(&init_net, sk->sk_bound_dev_if); |
924 |
++ if (dev) { |
925 |
+ if (is_zero_ether_addr(addr->sllc_mac)) |
926 |
+- memcpy(addr->sllc_mac, llc->dev->dev_addr, |
927 |
++ memcpy(addr->sllc_mac, dev->dev_addr, |
928 |
+ IFHWADDRLEN); |
929 |
+- if (addr->sllc_arphrd != llc->dev->type || |
930 |
++ if (addr->sllc_arphrd != dev->type || |
931 |
+ !ether_addr_equal(addr->sllc_mac, |
932 |
+- llc->dev->dev_addr)) { |
933 |
++ dev->dev_addr)) { |
934 |
+ rc = -EINVAL; |
935 |
+- llc->dev = NULL; |
936 |
++ dev = NULL; |
937 |
+ } |
938 |
+ } |
939 |
+- } else |
940 |
+- llc->dev = dev_getbyhwaddr_rcu(&init_net, addr->sllc_arphrd, |
941 |
++ } else { |
942 |
++ dev = dev_getbyhwaddr_rcu(&init_net, addr->sllc_arphrd, |
943 |
+ addr->sllc_mac); |
944 |
+- if (llc->dev) |
945 |
+- dev_hold(llc->dev); |
946 |
++ } |
947 |
++ if (dev) |
948 |
++ dev_hold(dev); |
949 |
+ rcu_read_unlock(); |
950 |
+- if (!llc->dev) |
951 |
++ if (!dev) |
952 |
+ goto out; |
953 |
+ if (!addr->sllc_sap) { |
954 |
+ rc = -EUSERS; |
955 |
+@@ -399,6 +408,11 @@ static int llc_ui_bind(struct socket *sock, struct sockaddr *uaddr, int addrlen) |
956 |
+ goto out_put; |
957 |
+ } |
958 |
+ } |
959 |
++ |
960 |
++ /* Note: We do not expect errors from this point. */ |
961 |
++ llc->dev = dev; |
962 |
++ dev = NULL; |
963 |
++ |
964 |
+ llc->laddr.lsap = addr->sllc_sap; |
965 |
+ memcpy(llc->laddr.mac, addr->sllc_mac, IFHWADDRLEN); |
966 |
+ memcpy(&llc->addr, addr, sizeof(llc->addr)); |
967 |
+@@ -409,6 +423,7 @@ static int llc_ui_bind(struct socket *sock, struct sockaddr *uaddr, int addrlen) |
968 |
+ out_put: |
969 |
+ llc_sap_put(sap); |
970 |
+ out: |
971 |
++ dev_put(dev); |
972 |
+ release_sock(sk); |
973 |
+ return rc; |
974 |
+ } |
975 |
+diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c |
976 |
+index d46ed4cbe7717..8010967a68741 100644 |
977 |
+--- a/net/mac80211/cfg.c |
978 |
++++ b/net/mac80211/cfg.c |
979 |
+@@ -2076,14 +2076,12 @@ static int copy_mesh_setup(struct ieee80211_if_mesh *ifmsh, |
980 |
+ const struct mesh_setup *setup) |
981 |
+ { |
982 |
+ u8 *new_ie; |
983 |
+- const u8 *old_ie; |
984 |
+ struct ieee80211_sub_if_data *sdata = container_of(ifmsh, |
985 |
+ struct ieee80211_sub_if_data, u.mesh); |
986 |
+ int i; |
987 |
+ |
988 |
+ /* allocate information elements */ |
989 |
+ new_ie = NULL; |
990 |
+- old_ie = ifmsh->ie; |
991 |
+ |
992 |
+ if (setup->ie_len) { |
993 |
+ new_ie = kmemdup(setup->ie, setup->ie_len, |
994 |
+@@ -2093,7 +2091,6 @@ static int copy_mesh_setup(struct ieee80211_if_mesh *ifmsh, |
995 |
+ } |
996 |
+ ifmsh->ie_len = setup->ie_len; |
997 |
+ ifmsh->ie = new_ie; |
998 |
+- kfree(old_ie); |
999 |
+ |
1000 |
+ /* now copy the rest of the setup parameters */ |
1001 |
+ ifmsh->mesh_id_len = setup->mesh_id_len; |
1002 |
+diff --git a/net/netfilter/nf_tables_core.c b/net/netfilter/nf_tables_core.c |
1003 |
+index dbc2e945c98eb..a61b5bf5aa0fb 100644 |
1004 |
+--- a/net/netfilter/nf_tables_core.c |
1005 |
++++ b/net/netfilter/nf_tables_core.c |
1006 |
+@@ -162,7 +162,7 @@ nft_do_chain(struct nft_pktinfo *pkt, void *priv) |
1007 |
+ struct nft_rule *const *rules; |
1008 |
+ const struct nft_rule *rule; |
1009 |
+ const struct nft_expr *expr, *last; |
1010 |
+- struct nft_regs regs; |
1011 |
++ struct nft_regs regs = {}; |
1012 |
+ unsigned int stackptr = 0; |
1013 |
+ struct nft_jumpstack jumpstack[NFT_JUMP_STACK_SIZE]; |
1014 |
+ bool genbit = READ_ONCE(net->nft.gencursor); |
1015 |
+diff --git a/sound/core/oss/pcm_oss.c b/sound/core/oss/pcm_oss.c |
1016 |
+index d79febeebf0c5..f88de74da1eb3 100644 |
1017 |
+--- a/sound/core/oss/pcm_oss.c |
1018 |
++++ b/sound/core/oss/pcm_oss.c |
1019 |
+@@ -774,6 +774,11 @@ static int snd_pcm_oss_period_size(struct snd_pcm_substream *substream, |
1020 |
+ |
1021 |
+ if (oss_period_size < 16) |
1022 |
+ return -EINVAL; |
1023 |
++ |
1024 |
++ /* don't allocate too large period; 1MB period must be enough */ |
1025 |
++ if (oss_period_size > 1024 * 1024) |
1026 |
++ return -ENOMEM; |
1027 |
++ |
1028 |
+ runtime->oss.period_bytes = oss_period_size; |
1029 |
+ runtime->oss.period_frames = 1; |
1030 |
+ runtime->oss.periods = oss_periods; |
1031 |
+@@ -1042,10 +1047,9 @@ static int snd_pcm_oss_change_params_locked(struct snd_pcm_substream *substream) |
1032 |
+ goto failure; |
1033 |
+ } |
1034 |
+ #endif |
1035 |
+- oss_period_size *= oss_frame_size; |
1036 |
+- |
1037 |
+- oss_buffer_size = oss_period_size * runtime->oss.periods; |
1038 |
+- if (oss_buffer_size < 0) { |
1039 |
++ oss_period_size = array_size(oss_period_size, oss_frame_size); |
1040 |
++ oss_buffer_size = array_size(oss_period_size, runtime->oss.periods); |
1041 |
++ if (oss_buffer_size <= 0) { |
1042 |
+ err = -EINVAL; |
1043 |
+ goto failure; |
1044 |
+ } |
1045 |
+diff --git a/sound/core/oss/pcm_plugin.c b/sound/core/oss/pcm_plugin.c |
1046 |
+index d5ca161d588c5..1e2d1b35c1946 100644 |
1047 |
+--- a/sound/core/oss/pcm_plugin.c |
1048 |
++++ b/sound/core/oss/pcm_plugin.c |
1049 |
+@@ -61,7 +61,10 @@ static int snd_pcm_plugin_alloc(struct snd_pcm_plugin *plugin, snd_pcm_uframes_t |
1050 |
+ } |
1051 |
+ if ((width = snd_pcm_format_physical_width(format->format)) < 0) |
1052 |
+ return width; |
1053 |
+- size = frames * format->channels * width; |
1054 |
++ size = array3_size(frames, format->channels, width); |
1055 |
++ /* check for too large period size once again */ |
1056 |
++ if (size > 1024 * 1024) |
1057 |
++ return -ENOMEM; |
1058 |
+ if (snd_BUG_ON(size % 8)) |
1059 |
+ return -ENXIO; |
1060 |
+ size /= 8; |
1061 |
+diff --git a/sound/core/pcm.c b/sound/core/pcm.c |
1062 |
+index a8ae5928decda..8e5c6b227e52d 100644 |
1063 |
+--- a/sound/core/pcm.c |
1064 |
++++ b/sound/core/pcm.c |
1065 |
+@@ -969,6 +969,7 @@ int snd_pcm_attach_substream(struct snd_pcm *pcm, int stream, |
1066 |
+ init_waitqueue_head(&runtime->tsleep); |
1067 |
+ |
1068 |
+ runtime->status->state = SNDRV_PCM_STATE_OPEN; |
1069 |
++ mutex_init(&runtime->buffer_mutex); |
1070 |
+ |
1071 |
+ substream->runtime = runtime; |
1072 |
+ substream->private_data = pcm->private_data; |
1073 |
+@@ -1002,6 +1003,7 @@ void snd_pcm_detach_substream(struct snd_pcm_substream *substream) |
1074 |
+ } else { |
1075 |
+ substream->runtime = NULL; |
1076 |
+ } |
1077 |
++ mutex_destroy(&runtime->buffer_mutex); |
1078 |
+ kfree(runtime); |
1079 |
+ put_pid(substream->pid); |
1080 |
+ substream->pid = NULL; |
1081 |
+diff --git a/sound/core/pcm_lib.c b/sound/core/pcm_lib.c |
1082 |
+index 5e04c4b9e0239..45afef73275f0 100644 |
1083 |
+--- a/sound/core/pcm_lib.c |
1084 |
++++ b/sound/core/pcm_lib.c |
1085 |
+@@ -1871,9 +1871,11 @@ static int wait_for_avail(struct snd_pcm_substream *substream, |
1086 |
+ if (avail >= runtime->twake) |
1087 |
+ break; |
1088 |
+ snd_pcm_stream_unlock_irq(substream); |
1089 |
++ mutex_unlock(&runtime->buffer_mutex); |
1090 |
+ |
1091 |
+ tout = schedule_timeout(wait_time); |
1092 |
+ |
1093 |
++ mutex_lock(&runtime->buffer_mutex); |
1094 |
+ snd_pcm_stream_lock_irq(substream); |
1095 |
+ set_current_state(TASK_INTERRUPTIBLE); |
1096 |
+ switch (runtime->status->state) { |
1097 |
+@@ -2167,6 +2169,7 @@ snd_pcm_sframes_t __snd_pcm_lib_xfer(struct snd_pcm_substream *substream, |
1098 |
+ |
1099 |
+ nonblock = !!(substream->f_flags & O_NONBLOCK); |
1100 |
+ |
1101 |
++ mutex_lock(&runtime->buffer_mutex); |
1102 |
+ snd_pcm_stream_lock_irq(substream); |
1103 |
+ err = pcm_accessible_state(runtime); |
1104 |
+ if (err < 0) |
1105 |
+@@ -2254,6 +2257,7 @@ snd_pcm_sframes_t __snd_pcm_lib_xfer(struct snd_pcm_substream *substream, |
1106 |
+ if (xfer > 0 && err >= 0) |
1107 |
+ snd_pcm_update_state(substream, runtime); |
1108 |
+ snd_pcm_stream_unlock_irq(substream); |
1109 |
++ mutex_unlock(&runtime->buffer_mutex); |
1110 |
+ return xfer > 0 ? (snd_pcm_sframes_t)xfer : err; |
1111 |
+ } |
1112 |
+ EXPORT_SYMBOL(__snd_pcm_lib_xfer); |
1113 |
+diff --git a/sound/core/pcm_memory.c b/sound/core/pcm_memory.c |
1114 |
+index 4f03ba8ed0ae5..a9a0d74f31656 100644 |
1115 |
+--- a/sound/core/pcm_memory.c |
1116 |
++++ b/sound/core/pcm_memory.c |
1117 |
+@@ -164,19 +164,20 @@ static void snd_pcm_lib_preallocate_proc_write(struct snd_info_entry *entry, |
1118 |
+ size_t size; |
1119 |
+ struct snd_dma_buffer new_dmab; |
1120 |
+ |
1121 |
++ mutex_lock(&substream->pcm->open_mutex); |
1122 |
+ if (substream->runtime) { |
1123 |
+ buffer->error = -EBUSY; |
1124 |
+- return; |
1125 |
++ goto unlock; |
1126 |
+ } |
1127 |
+ if (!snd_info_get_line(buffer, line, sizeof(line))) { |
1128 |
+ snd_info_get_str(str, line, sizeof(str)); |
1129 |
+ size = simple_strtoul(str, NULL, 10) * 1024; |
1130 |
+ if ((size != 0 && size < 8192) || size > substream->dma_max) { |
1131 |
+ buffer->error = -EINVAL; |
1132 |
+- return; |
1133 |
++ goto unlock; |
1134 |
+ } |
1135 |
+ if (substream->dma_buffer.bytes == size) |
1136 |
+- return; |
1137 |
++ goto unlock; |
1138 |
+ memset(&new_dmab, 0, sizeof(new_dmab)); |
1139 |
+ new_dmab.dev = substream->dma_buffer.dev; |
1140 |
+ if (size > 0) { |
1141 |
+@@ -185,7 +186,7 @@ static void snd_pcm_lib_preallocate_proc_write(struct snd_info_entry *entry, |
1142 |
+ substream->dma_buffer.dev.dev, |
1143 |
+ size, &new_dmab) < 0) { |
1144 |
+ buffer->error = -ENOMEM; |
1145 |
+- return; |
1146 |
++ goto unlock; |
1147 |
+ } |
1148 |
+ substream->buffer_bytes_max = size; |
1149 |
+ } else { |
1150 |
+@@ -197,6 +198,8 @@ static void snd_pcm_lib_preallocate_proc_write(struct snd_info_entry *entry, |
1151 |
+ } else { |
1152 |
+ buffer->error = -EINVAL; |
1153 |
+ } |
1154 |
++ unlock: |
1155 |
++ mutex_unlock(&substream->pcm->open_mutex); |
1156 |
+ } |
1157 |
+ |
1158 |
+ static inline void preallocate_info_init(struct snd_pcm_substream *substream) |
1159 |
+diff --git a/sound/core/pcm_native.c b/sound/core/pcm_native.c |
1160 |
+index c5ef5182fcf19..6579802c55116 100644 |
1161 |
+--- a/sound/core/pcm_native.c |
1162 |
++++ b/sound/core/pcm_native.c |
1163 |
+@@ -667,33 +667,40 @@ static int snd_pcm_hw_params_choose(struct snd_pcm_substream *pcm, |
1164 |
+ return 0; |
1165 |
+ } |
1166 |
+ |
1167 |
++#if IS_ENABLED(CONFIG_SND_PCM_OSS) |
1168 |
++#define is_oss_stream(substream) ((substream)->oss.oss) |
1169 |
++#else |
1170 |
++#define is_oss_stream(substream) false |
1171 |
++#endif |
1172 |
++ |
1173 |
+ static int snd_pcm_hw_params(struct snd_pcm_substream *substream, |
1174 |
+ struct snd_pcm_hw_params *params) |
1175 |
+ { |
1176 |
+ struct snd_pcm_runtime *runtime; |
1177 |
+- int err, usecs; |
1178 |
++ int err = 0, usecs; |
1179 |
+ unsigned int bits; |
1180 |
+ snd_pcm_uframes_t frames; |
1181 |
+ |
1182 |
+ if (PCM_RUNTIME_CHECK(substream)) |
1183 |
+ return -ENXIO; |
1184 |
+ runtime = substream->runtime; |
1185 |
++ mutex_lock(&runtime->buffer_mutex); |
1186 |
+ snd_pcm_stream_lock_irq(substream); |
1187 |
+ switch (runtime->status->state) { |
1188 |
+ case SNDRV_PCM_STATE_OPEN: |
1189 |
+ case SNDRV_PCM_STATE_SETUP: |
1190 |
+ case SNDRV_PCM_STATE_PREPARED: |
1191 |
++ if (!is_oss_stream(substream) && |
1192 |
++ atomic_read(&substream->mmap_count)) |
1193 |
++ err = -EBADFD; |
1194 |
+ break; |
1195 |
+ default: |
1196 |
+- snd_pcm_stream_unlock_irq(substream); |
1197 |
+- return -EBADFD; |
1198 |
++ err = -EBADFD; |
1199 |
++ break; |
1200 |
+ } |
1201 |
+ snd_pcm_stream_unlock_irq(substream); |
1202 |
+-#if IS_ENABLED(CONFIG_SND_PCM_OSS) |
1203 |
+- if (!substream->oss.oss) |
1204 |
+-#endif |
1205 |
+- if (atomic_read(&substream->mmap_count)) |
1206 |
+- return -EBADFD; |
1207 |
++ if (err) |
1208 |
++ goto unlock; |
1209 |
+ |
1210 |
+ snd_pcm_sync_stop(substream, true); |
1211 |
+ |
1212 |
+@@ -780,16 +787,21 @@ static int snd_pcm_hw_params(struct snd_pcm_substream *substream, |
1213 |
+ if ((usecs = period_to_usecs(runtime)) >= 0) |
1214 |
+ cpu_latency_qos_add_request(&substream->latency_pm_qos_req, |
1215 |
+ usecs); |
1216 |
+- return 0; |
1217 |
++ err = 0; |
1218 |
+ _error: |
1219 |
+- /* hardware might be unusable from this time, |
1220 |
+- so we force application to retry to set |
1221 |
+- the correct hardware parameter settings */ |
1222 |
+- snd_pcm_set_state(substream, SNDRV_PCM_STATE_OPEN); |
1223 |
+- if (substream->ops->hw_free != NULL) |
1224 |
+- substream->ops->hw_free(substream); |
1225 |
+- if (substream->managed_buffer_alloc) |
1226 |
+- snd_pcm_lib_free_pages(substream); |
1227 |
++ if (err) { |
1228 |
++ /* hardware might be unusable from this time, |
1229 |
++ * so we force application to retry to set |
1230 |
++ * the correct hardware parameter settings |
1231 |
++ */ |
1232 |
++ snd_pcm_set_state(substream, SNDRV_PCM_STATE_OPEN); |
1233 |
++ if (substream->ops->hw_free != NULL) |
1234 |
++ substream->ops->hw_free(substream); |
1235 |
++ if (substream->managed_buffer_alloc) |
1236 |
++ snd_pcm_lib_free_pages(substream); |
1237 |
++ } |
1238 |
++ unlock: |
1239 |
++ mutex_unlock(&runtime->buffer_mutex); |
1240 |
+ return err; |
1241 |
+ } |
1242 |
+ |
1243 |
+@@ -829,26 +841,31 @@ static int do_hw_free(struct snd_pcm_substream *substream) |
1244 |
+ static int snd_pcm_hw_free(struct snd_pcm_substream *substream) |
1245 |
+ { |
1246 |
+ struct snd_pcm_runtime *runtime; |
1247 |
+- int result; |
1248 |
++ int result = 0; |
1249 |
+ |
1250 |
+ if (PCM_RUNTIME_CHECK(substream)) |
1251 |
+ return -ENXIO; |
1252 |
+ runtime = substream->runtime; |
1253 |
++ mutex_lock(&runtime->buffer_mutex); |
1254 |
+ snd_pcm_stream_lock_irq(substream); |
1255 |
+ switch (runtime->status->state) { |
1256 |
+ case SNDRV_PCM_STATE_SETUP: |
1257 |
+ case SNDRV_PCM_STATE_PREPARED: |
1258 |
++ if (atomic_read(&substream->mmap_count)) |
1259 |
++ result = -EBADFD; |
1260 |
+ break; |
1261 |
+ default: |
1262 |
+- snd_pcm_stream_unlock_irq(substream); |
1263 |
+- return -EBADFD; |
1264 |
++ result = -EBADFD; |
1265 |
++ break; |
1266 |
+ } |
1267 |
+ snd_pcm_stream_unlock_irq(substream); |
1268 |
+- if (atomic_read(&substream->mmap_count)) |
1269 |
+- return -EBADFD; |
1270 |
++ if (result) |
1271 |
++ goto unlock; |
1272 |
+ result = do_hw_free(substream); |
1273 |
+ snd_pcm_set_state(substream, SNDRV_PCM_STATE_OPEN); |
1274 |
+ cpu_latency_qos_remove_request(&substream->latency_pm_qos_req); |
1275 |
++ unlock: |
1276 |
++ mutex_unlock(&runtime->buffer_mutex); |
1277 |
+ return result; |
1278 |
+ } |
1279 |
+ |
1280 |
+@@ -1154,15 +1171,17 @@ struct action_ops { |
1281 |
+ static int snd_pcm_action_group(const struct action_ops *ops, |
1282 |
+ struct snd_pcm_substream *substream, |
1283 |
+ snd_pcm_state_t state, |
1284 |
+- bool do_lock) |
1285 |
++ bool stream_lock) |
1286 |
+ { |
1287 |
+ struct snd_pcm_substream *s = NULL; |
1288 |
+ struct snd_pcm_substream *s1; |
1289 |
+ int res = 0, depth = 1; |
1290 |
+ |
1291 |
+ snd_pcm_group_for_each_entry(s, substream) { |
1292 |
+- if (do_lock && s != substream) { |
1293 |
+- if (s->pcm->nonatomic) |
1294 |
++ if (s != substream) { |
1295 |
++ if (!stream_lock) |
1296 |
++ mutex_lock_nested(&s->runtime->buffer_mutex, depth); |
1297 |
++ else if (s->pcm->nonatomic) |
1298 |
+ mutex_lock_nested(&s->self_group.mutex, depth); |
1299 |
+ else |
1300 |
+ spin_lock_nested(&s->self_group.lock, depth); |
1301 |
+@@ -1190,18 +1209,18 @@ static int snd_pcm_action_group(const struct action_ops *ops, |
1302 |
+ ops->post_action(s, state); |
1303 |
+ } |
1304 |
+ _unlock: |
1305 |
+- if (do_lock) { |
1306 |
+- /* unlock streams */ |
1307 |
+- snd_pcm_group_for_each_entry(s1, substream) { |
1308 |
+- if (s1 != substream) { |
1309 |
+- if (s1->pcm->nonatomic) |
1310 |
+- mutex_unlock(&s1->self_group.mutex); |
1311 |
+- else |
1312 |
+- spin_unlock(&s1->self_group.lock); |
1313 |
+- } |
1314 |
+- if (s1 == s) /* end */ |
1315 |
+- break; |
1316 |
++ /* unlock streams */ |
1317 |
++ snd_pcm_group_for_each_entry(s1, substream) { |
1318 |
++ if (s1 != substream) { |
1319 |
++ if (!stream_lock) |
1320 |
++ mutex_unlock(&s1->runtime->buffer_mutex); |
1321 |
++ else if (s1->pcm->nonatomic) |
1322 |
++ mutex_unlock(&s1->self_group.mutex); |
1323 |
++ else |
1324 |
++ spin_unlock(&s1->self_group.lock); |
1325 |
+ } |
1326 |
++ if (s1 == s) /* end */ |
1327 |
++ break; |
1328 |
+ } |
1329 |
+ return res; |
1330 |
+ } |
1331 |
+@@ -1331,10 +1350,12 @@ static int snd_pcm_action_nonatomic(const struct action_ops *ops, |
1332 |
+ |
1333 |
+ /* Guarantee the group members won't change during non-atomic action */ |
1334 |
+ down_read(&snd_pcm_link_rwsem); |
1335 |
++ mutex_lock(&substream->runtime->buffer_mutex); |
1336 |
+ if (snd_pcm_stream_linked(substream)) |
1337 |
+ res = snd_pcm_action_group(ops, substream, state, false); |
1338 |
+ else |
1339 |
+ res = snd_pcm_action_single(ops, substream, state); |
1340 |
++ mutex_unlock(&substream->runtime->buffer_mutex); |
1341 |
+ up_read(&snd_pcm_link_rwsem); |
1342 |
+ return res; |
1343 |
+ } |
1344 |
+@@ -1829,11 +1850,13 @@ static int snd_pcm_do_reset(struct snd_pcm_substream *substream, |
1345 |
+ int err = snd_pcm_ops_ioctl(substream, SNDRV_PCM_IOCTL1_RESET, NULL); |
1346 |
+ if (err < 0) |
1347 |
+ return err; |
1348 |
++ snd_pcm_stream_lock_irq(substream); |
1349 |
+ runtime->hw_ptr_base = 0; |
1350 |
+ runtime->hw_ptr_interrupt = runtime->status->hw_ptr - |
1351 |
+ runtime->status->hw_ptr % runtime->period_size; |
1352 |
+ runtime->silence_start = runtime->status->hw_ptr; |
1353 |
+ runtime->silence_filled = 0; |
1354 |
++ snd_pcm_stream_unlock_irq(substream); |
1355 |
+ return 0; |
1356 |
+ } |
1357 |
+ |
1358 |
+@@ -1841,10 +1864,12 @@ static void snd_pcm_post_reset(struct snd_pcm_substream *substream, |
1359 |
+ snd_pcm_state_t state) |
1360 |
+ { |
1361 |
+ struct snd_pcm_runtime *runtime = substream->runtime; |
1362 |
++ snd_pcm_stream_lock_irq(substream); |
1363 |
+ runtime->control->appl_ptr = runtime->status->hw_ptr; |
1364 |
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK && |
1365 |
+ runtime->silence_size > 0) |
1366 |
+ snd_pcm_playback_silence(substream, ULONG_MAX); |
1367 |
++ snd_pcm_stream_unlock_irq(substream); |
1368 |
+ } |
1369 |
+ |
1370 |
+ static const struct action_ops snd_pcm_action_reset = { |
1371 |
+diff --git a/sound/pci/ac97/ac97_codec.c b/sound/pci/ac97/ac97_codec.c |
1372 |
+index 012a7ee849e8a..963731cf0d8c8 100644 |
1373 |
+--- a/sound/pci/ac97/ac97_codec.c |
1374 |
++++ b/sound/pci/ac97/ac97_codec.c |
1375 |
+@@ -938,8 +938,8 @@ static int snd_ac97_ad18xx_pcm_get_volume(struct snd_kcontrol *kcontrol, struct |
1376 |
+ int codec = kcontrol->private_value & 3; |
1377 |
+ |
1378 |
+ mutex_lock(&ac97->page_mutex); |
1379 |
+- ucontrol->value.integer.value[0] = 31 - ((ac97->spec.ad18xx.pcmreg[codec] >> 0) & 31); |
1380 |
+- ucontrol->value.integer.value[1] = 31 - ((ac97->spec.ad18xx.pcmreg[codec] >> 8) & 31); |
1381 |
++ ucontrol->value.integer.value[0] = 31 - ((ac97->spec.ad18xx.pcmreg[codec] >> 8) & 31); |
1382 |
++ ucontrol->value.integer.value[1] = 31 - ((ac97->spec.ad18xx.pcmreg[codec] >> 0) & 31); |
1383 |
+ mutex_unlock(&ac97->page_mutex); |
1384 |
+ return 0; |
1385 |
+ } |
1386 |
+diff --git a/sound/pci/cmipci.c b/sound/pci/cmipci.c |
1387 |
+index 7363d61eaec23..120dd8b33ac81 100644 |
1388 |
+--- a/sound/pci/cmipci.c |
1389 |
++++ b/sound/pci/cmipci.c |
1390 |
+@@ -302,7 +302,6 @@ MODULE_PARM_DESC(joystick_port, "Joystick port address."); |
1391 |
+ #define CM_MICGAINZ 0x01 /* mic boost */ |
1392 |
+ #define CM_MICGAINZ_SHIFT 0 |
1393 |
+ |
1394 |
+-#define CM_REG_MIXER3 0x24 |
1395 |
+ #define CM_REG_AUX_VOL 0x26 |
1396 |
+ #define CM_VAUXL_MASK 0xf0 |
1397 |
+ #define CM_VAUXR_MASK 0x0f |
1398 |
+@@ -3291,7 +3290,7 @@ static void snd_cmipci_remove(struct pci_dev *pci) |
1399 |
+ */ |
1400 |
+ static const unsigned char saved_regs[] = { |
1401 |
+ CM_REG_FUNCTRL1, CM_REG_CHFORMAT, CM_REG_LEGACY_CTRL, CM_REG_MISC_CTRL, |
1402 |
+- CM_REG_MIXER0, CM_REG_MIXER1, CM_REG_MIXER2, CM_REG_MIXER3, CM_REG_PLL, |
1403 |
++ CM_REG_MIXER0, CM_REG_MIXER1, CM_REG_MIXER2, CM_REG_AUX_VOL, CM_REG_PLL, |
1404 |
+ CM_REG_CH0_FRAME1, CM_REG_CH0_FRAME2, |
1405 |
+ CM_REG_CH1_FRAME1, CM_REG_CH1_FRAME2, CM_REG_EXT_MISC, |
1406 |
+ CM_REG_INT_STATUS, CM_REG_INT_HLDCLR, CM_REG_FUNCTRL0, |
1407 |
+diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c |
1408 |
+index ed0cfcb05ef0d..3bd37c02ce0ed 100644 |
1409 |
+--- a/sound/pci/hda/patch_realtek.c |
1410 |
++++ b/sound/pci/hda/patch_realtek.c |
1411 |
+@@ -8801,6 +8801,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { |
1412 |
+ SND_PCI_QUIRK(0x1043, 0x1e51, "ASUS Zephyrus M15", ALC294_FIXUP_ASUS_GU502_PINS), |
1413 |
+ SND_PCI_QUIRK(0x1043, 0x1e8e, "ASUS Zephyrus G15", ALC289_FIXUP_ASUS_GA401), |
1414 |
+ SND_PCI_QUIRK(0x1043, 0x1f11, "ASUS Zephyrus G14", ALC289_FIXUP_ASUS_GA401), |
1415 |
++ SND_PCI_QUIRK(0x1043, 0x1d42, "ASUS Zephyrus G14 2022", ALC289_FIXUP_ASUS_GA401), |
1416 |
+ SND_PCI_QUIRK(0x1043, 0x16b2, "ASUS GU603", ALC289_FIXUP_ASUS_GA401), |
1417 |
+ SND_PCI_QUIRK(0x1043, 0x3030, "ASUS ZN270IE", ALC256_FIXUP_ASUS_AIO_GPIO2), |
1418 |
+ SND_PCI_QUIRK(0x1043, 0x831a, "ASUS P901", ALC269_FIXUP_STEREO_DMIC), |
1419 |
+@@ -8884,6 +8885,8 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { |
1420 |
+ SND_PCI_QUIRK(0x1558, 0x8561, "System76 Gazelle (gaze14)", ALC269_FIXUP_HEADSET_MIC), |
1421 |
+ SND_PCI_QUIRK(0x1558, 0x8562, "Clevo NH[5|7][0-9]RZ[Q]", ALC269_FIXUP_DMIC), |
1422 |
+ SND_PCI_QUIRK(0x1558, 0x8668, "Clevo NP50B[BE]", ALC293_FIXUP_SYSTEM76_MIC_NO_PRESENCE), |
1423 |
++ SND_PCI_QUIRK(0x1558, 0x866d, "Clevo NP5[05]PN[HJK]", ALC256_FIXUP_SYSTEM76_MIC_NO_PRESENCE), |
1424 |
++ SND_PCI_QUIRK(0x1558, 0x867d, "Clevo NP7[01]PN[HJK]", ALC256_FIXUP_SYSTEM76_MIC_NO_PRESENCE), |
1425 |
+ SND_PCI_QUIRK(0x1558, 0x8680, "Clevo NJ50LU", ALC293_FIXUP_SYSTEM76_MIC_NO_PRESENCE), |
1426 |
+ SND_PCI_QUIRK(0x1558, 0x8686, "Clevo NH50[CZ]U", ALC256_FIXUP_MIC_NO_PRESENCE_AND_RESUME), |
1427 |
+ SND_PCI_QUIRK(0x1558, 0x8a20, "Clevo NH55DCQ-Y", ALC293_FIXUP_SYSTEM76_MIC_NO_PRESENCE), |
1428 |
+@@ -10839,6 +10842,7 @@ static const struct snd_pci_quirk alc662_fixup_tbl[] = { |
1429 |
+ SND_PCI_QUIRK(0x1028, 0x069f, "Dell", ALC668_FIXUP_DELL_MIC_NO_PRESENCE), |
1430 |
+ SND_PCI_QUIRK(0x103c, 0x1632, "HP RP5800", ALC662_FIXUP_HP_RP5800), |
1431 |
+ SND_PCI_QUIRK(0x103c, 0x873e, "HP", ALC671_FIXUP_HP_HEADSET_MIC2), |
1432 |
++ SND_PCI_QUIRK(0x103c, 0x885f, "HP 288 Pro G8", ALC671_FIXUP_HP_HEADSET_MIC2), |
1433 |
+ SND_PCI_QUIRK(0x1043, 0x1080, "Asus UX501VW", ALC668_FIXUP_HEADSET_MODE), |
1434 |
+ SND_PCI_QUIRK(0x1043, 0x11cd, "Asus N550", ALC662_FIXUP_ASUS_Nx50), |
1435 |
+ SND_PCI_QUIRK(0x1043, 0x129d, "Asus N750", ALC662_FIXUP_ASUS_Nx50), |
1436 |
+diff --git a/sound/soc/sti/uniperif_player.c b/sound/soc/sti/uniperif_player.c |
1437 |
+index 2ed92c990b97c..dd9013c476649 100644 |
1438 |
+--- a/sound/soc/sti/uniperif_player.c |
1439 |
++++ b/sound/soc/sti/uniperif_player.c |
1440 |
+@@ -91,7 +91,7 @@ static irqreturn_t uni_player_irq_handler(int irq, void *dev_id) |
1441 |
+ SET_UNIPERIF_ITM_BCLR_FIFO_ERROR(player); |
1442 |
+ |
1443 |
+ /* Stop the player */ |
1444 |
+- snd_pcm_stop_xrun(player->substream); |
1445 |
++ snd_pcm_stop(player->substream, SNDRV_PCM_STATE_XRUN); |
1446 |
+ } |
1447 |
+ |
1448 |
+ ret = IRQ_HANDLED; |
1449 |
+@@ -105,7 +105,7 @@ static irqreturn_t uni_player_irq_handler(int irq, void *dev_id) |
1450 |
+ SET_UNIPERIF_ITM_BCLR_DMA_ERROR(player); |
1451 |
+ |
1452 |
+ /* Stop the player */ |
1453 |
+- snd_pcm_stop_xrun(player->substream); |
1454 |
++ snd_pcm_stop(player->substream, SNDRV_PCM_STATE_XRUN); |
1455 |
+ |
1456 |
+ ret = IRQ_HANDLED; |
1457 |
+ } |
1458 |
+@@ -138,7 +138,7 @@ static irqreturn_t uni_player_irq_handler(int irq, void *dev_id) |
1459 |
+ dev_err(player->dev, "Underflow recovery failed\n"); |
1460 |
+ |
1461 |
+ /* Stop the player */ |
1462 |
+- snd_pcm_stop_xrun(player->substream); |
1463 |
++ snd_pcm_stop(player->substream, SNDRV_PCM_STATE_XRUN); |
1464 |
+ |
1465 |
+ ret = IRQ_HANDLED; |
1466 |
+ } |
1467 |
+diff --git a/sound/soc/sti/uniperif_reader.c b/sound/soc/sti/uniperif_reader.c |
1468 |
+index 136059331211d..065c5f0d1f5f0 100644 |
1469 |
+--- a/sound/soc/sti/uniperif_reader.c |
1470 |
++++ b/sound/soc/sti/uniperif_reader.c |
1471 |
+@@ -65,7 +65,7 @@ static irqreturn_t uni_reader_irq_handler(int irq, void *dev_id) |
1472 |
+ if (unlikely(status & UNIPERIF_ITS_FIFO_ERROR_MASK(reader))) { |
1473 |
+ dev_err(reader->dev, "FIFO error detected\n"); |
1474 |
+ |
1475 |
+- snd_pcm_stop_xrun(reader->substream); |
1476 |
++ snd_pcm_stop(reader->substream, SNDRV_PCM_STATE_XRUN); |
1477 |
+ |
1478 |
+ ret = IRQ_HANDLED; |
1479 |
+ } |
1480 |
+diff --git a/sound/usb/mixer_maps.c b/sound/usb/mixer_maps.c |
1481 |
+index 8f6823df944ff..81ace832d7e42 100644 |
1482 |
+--- a/sound/usb/mixer_maps.c |
1483 |
++++ b/sound/usb/mixer_maps.c |
1484 |
+@@ -542,6 +542,16 @@ static const struct usbmix_ctl_map usbmix_ctl_maps[] = { |
1485 |
+ .id = USB_ID(0x25c4, 0x0003), |
1486 |
+ .map = scms_usb3318_map, |
1487 |
+ }, |
1488 |
++ { |
1489 |
++ /* Corsair Virtuoso SE Latest (wired mode) */ |
1490 |
++ .id = USB_ID(0x1b1c, 0x0a3f), |
1491 |
++ .map = corsair_virtuoso_map, |
1492 |
++ }, |
1493 |
++ { |
1494 |
++ /* Corsair Virtuoso SE Latest (wireless mode) */ |
1495 |
++ .id = USB_ID(0x1b1c, 0x0a40), |
1496 |
++ .map = corsair_virtuoso_map, |
1497 |
++ }, |
1498 |
+ { |
1499 |
+ .id = USB_ID(0x30be, 0x0101), /* Schiit Hel */ |
1500 |
+ .ignore_ctl_error = 1, |
1501 |
+diff --git a/sound/usb/mixer_quirks.c b/sound/usb/mixer_quirks.c |
1502 |
+index 86fdd669f3fd7..99f2203bf51f1 100644 |
1503 |
+--- a/sound/usb/mixer_quirks.c |
1504 |
++++ b/sound/usb/mixer_quirks.c |
1505 |
+@@ -3135,9 +3135,10 @@ void snd_usb_mixer_fu_apply_quirk(struct usb_mixer_interface *mixer, |
1506 |
+ if (unitid == 7 && cval->control == UAC_FU_VOLUME) |
1507 |
+ snd_dragonfly_quirk_db_scale(mixer, cval, kctl); |
1508 |
+ break; |
1509 |
+- /* lowest playback value is muted on C-Media devices */ |
1510 |
+- case USB_ID(0x0d8c, 0x000c): |
1511 |
+- case USB_ID(0x0d8c, 0x0014): |
1512 |
++ /* lowest playback value is muted on some devices */ |
1513 |
++ case USB_ID(0x0d8c, 0x000c): /* C-Media */ |
1514 |
++ case USB_ID(0x0d8c, 0x0014): /* C-Media */ |
1515 |
++ case USB_ID(0x19f7, 0x0003): /* RODE NT-USB */ |
1516 |
+ if (strstr(kctl->id.name, "Playback")) |
1517 |
+ cval->min_mute = 1; |
1518 |
+ break; |