1 |
commit: 399535a40d9c13d6954ea337eab72175869f49e0 |
2 |
Author: Mike Pagano <mpagano <AT> gentoo <DOT> org> |
3 |
AuthorDate: Sat Jan 29 17:43:13 2022 +0000 |
4 |
Commit: Mike Pagano <mpagano <AT> gentoo <DOT> org> |
5 |
CommitDate: Sat Jan 29 17:43:13 2022 +0000 |
6 |
URL: https://gitweb.gentoo.org/proj/linux-patches.git/commit/?id=399535a4 |
7 |
|
8 |
Linux patch 5.10.95 |
9 |
|
10 |
Signed-off-by: Mike Pagano <mpagano <AT> gentoo.org> |
11 |
|
12 |
0000_README | 4 + |
13 |
1094_linux-5.10.95.patch | 823 +++++++++++++++++++++++++++++++++++++++++++++++ |
14 |
2 files changed, 827 insertions(+) |
15 |
|
16 |
diff --git a/0000_README b/0000_README |
17 |
index 8c30f470..5f3cbb9a 100644 |
18 |
--- a/0000_README |
19 |
+++ b/0000_README |
20 |
@@ -419,6 +419,10 @@ Patch: 1093_linux-5.10.94.patch |
21 |
From: http://www.kernel.org |
22 |
Desc: Linux 5.10.94 |
23 |
|
24 |
+Patch: 1094_linux-5.10.95.patch |
25 |
+From: http://www.kernel.org |
26 |
+Desc: Linux 5.10.95 |
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/1094_linux-5.10.95.patch b/1094_linux-5.10.95.patch |
33 |
new file mode 100644 |
34 |
index 00000000..a12f7b89 |
35 |
--- /dev/null |
36 |
+++ b/1094_linux-5.10.95.patch |
37 |
@@ -0,0 +1,823 @@ |
38 |
+diff --git a/Makefile b/Makefile |
39 |
+index 1071ec486aa5b..fa98893aae615 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 = 94 |
47 |
++SUBLEVEL = 95 |
48 |
+ EXTRAVERSION = |
49 |
+ NAME = Dare mighty things |
50 |
+ |
51 |
+diff --git a/arch/x86/kvm/mmu/tdp_mmu.c b/arch/x86/kvm/mmu/tdp_mmu.c |
52 |
+index f2ddf663e72e9..7e08efb068393 100644 |
53 |
+--- a/arch/x86/kvm/mmu/tdp_mmu.c |
54 |
++++ b/arch/x86/kvm/mmu/tdp_mmu.c |
55 |
+@@ -1130,12 +1130,12 @@ static bool write_protect_gfn(struct kvm *kvm, struct kvm_mmu_page *root, |
56 |
+ bool spte_set = false; |
57 |
+ |
58 |
+ tdp_root_for_each_leaf_pte(iter, root, gfn, gfn + 1) { |
59 |
+- if (!is_writable_pte(iter.old_spte)) |
60 |
+- break; |
61 |
+- |
62 |
+ new_spte = iter.old_spte & |
63 |
+ ~(PT_WRITABLE_MASK | SPTE_MMU_WRITEABLE); |
64 |
+ |
65 |
++ if (new_spte == iter.old_spte) |
66 |
++ break; |
67 |
++ |
68 |
+ tdp_mmu_set_spte(kvm, &iter, new_spte); |
69 |
+ spte_set = true; |
70 |
+ } |
71 |
+diff --git a/drivers/gpu/drm/i915/gem/i915_gem_object_types.h b/drivers/gpu/drm/i915/gem/i915_gem_object_types.h |
72 |
+index d6711caa7f399..dbc88fc7136bf 100644 |
73 |
+--- a/drivers/gpu/drm/i915/gem/i915_gem_object_types.h |
74 |
++++ b/drivers/gpu/drm/i915/gem/i915_gem_object_types.h |
75 |
+@@ -159,6 +159,7 @@ struct drm_i915_gem_object { |
76 |
+ #define I915_BO_ALLOC_VOLATILE BIT(1) |
77 |
+ #define I915_BO_ALLOC_FLAGS (I915_BO_ALLOC_CONTIGUOUS | I915_BO_ALLOC_VOLATILE) |
78 |
+ #define I915_BO_READONLY BIT(2) |
79 |
++#define I915_BO_WAS_BOUND_BIT 3 |
80 |
+ |
81 |
+ /* |
82 |
+ * Is the object to be mapped as read-only to the GPU |
83 |
+diff --git a/drivers/gpu/drm/i915/gem/i915_gem_pages.c b/drivers/gpu/drm/i915/gem/i915_gem_pages.c |
84 |
+index f60ca6dc911f2..27d24cb38c0d2 100644 |
85 |
+--- a/drivers/gpu/drm/i915/gem/i915_gem_pages.c |
86 |
++++ b/drivers/gpu/drm/i915/gem/i915_gem_pages.c |
87 |
+@@ -10,6 +10,8 @@ |
88 |
+ #include "i915_gem_lmem.h" |
89 |
+ #include "i915_gem_mman.h" |
90 |
+ |
91 |
++#include "gt/intel_gt.h" |
92 |
++ |
93 |
+ void __i915_gem_object_set_pages(struct drm_i915_gem_object *obj, |
94 |
+ struct sg_table *pages, |
95 |
+ unsigned int sg_page_sizes) |
96 |
+@@ -186,6 +188,14 @@ __i915_gem_object_unset_pages(struct drm_i915_gem_object *obj) |
97 |
+ __i915_gem_object_reset_page_iter(obj); |
98 |
+ obj->mm.page_sizes.phys = obj->mm.page_sizes.sg = 0; |
99 |
+ |
100 |
++ if (test_and_clear_bit(I915_BO_WAS_BOUND_BIT, &obj->flags)) { |
101 |
++ struct drm_i915_private *i915 = to_i915(obj->base.dev); |
102 |
++ intel_wakeref_t wakeref; |
103 |
++ |
104 |
++ with_intel_runtime_pm_if_active(&i915->runtime_pm, wakeref) |
105 |
++ intel_gt_invalidate_tlbs(&i915->gt); |
106 |
++ } |
107 |
++ |
108 |
+ return pages; |
109 |
+ } |
110 |
+ |
111 |
+diff --git a/drivers/gpu/drm/i915/gt/intel_gt.c b/drivers/gpu/drm/i915/gt/intel_gt.c |
112 |
+index 39b428c5049c0..6615eb5147e23 100644 |
113 |
+--- a/drivers/gpu/drm/i915/gt/intel_gt.c |
114 |
++++ b/drivers/gpu/drm/i915/gt/intel_gt.c |
115 |
+@@ -26,6 +26,8 @@ void intel_gt_init_early(struct intel_gt *gt, struct drm_i915_private *i915) |
116 |
+ |
117 |
+ spin_lock_init(>->irq_lock); |
118 |
+ |
119 |
++ mutex_init(>->tlb_invalidate_lock); |
120 |
++ |
121 |
+ INIT_LIST_HEAD(>->closed_vma); |
122 |
+ spin_lock_init(>->closed_lock); |
123 |
+ |
124 |
+@@ -661,3 +663,103 @@ void intel_gt_info_print(const struct intel_gt_info *info, |
125 |
+ |
126 |
+ intel_sseu_dump(&info->sseu, p); |
127 |
+ } |
128 |
++ |
129 |
++struct reg_and_bit { |
130 |
++ i915_reg_t reg; |
131 |
++ u32 bit; |
132 |
++}; |
133 |
++ |
134 |
++static struct reg_and_bit |
135 |
++get_reg_and_bit(const struct intel_engine_cs *engine, const bool gen8, |
136 |
++ const i915_reg_t *regs, const unsigned int num) |
137 |
++{ |
138 |
++ const unsigned int class = engine->class; |
139 |
++ struct reg_and_bit rb = { }; |
140 |
++ |
141 |
++ if (drm_WARN_ON_ONCE(&engine->i915->drm, |
142 |
++ class >= num || !regs[class].reg)) |
143 |
++ return rb; |
144 |
++ |
145 |
++ rb.reg = regs[class]; |
146 |
++ if (gen8 && class == VIDEO_DECODE_CLASS) |
147 |
++ rb.reg.reg += 4 * engine->instance; /* GEN8_M2TCR */ |
148 |
++ else |
149 |
++ rb.bit = engine->instance; |
150 |
++ |
151 |
++ rb.bit = BIT(rb.bit); |
152 |
++ |
153 |
++ return rb; |
154 |
++} |
155 |
++ |
156 |
++void intel_gt_invalidate_tlbs(struct intel_gt *gt) |
157 |
++{ |
158 |
++ static const i915_reg_t gen8_regs[] = { |
159 |
++ [RENDER_CLASS] = GEN8_RTCR, |
160 |
++ [VIDEO_DECODE_CLASS] = GEN8_M1TCR, /* , GEN8_M2TCR */ |
161 |
++ [VIDEO_ENHANCEMENT_CLASS] = GEN8_VTCR, |
162 |
++ [COPY_ENGINE_CLASS] = GEN8_BTCR, |
163 |
++ }; |
164 |
++ static const i915_reg_t gen12_regs[] = { |
165 |
++ [RENDER_CLASS] = GEN12_GFX_TLB_INV_CR, |
166 |
++ [VIDEO_DECODE_CLASS] = GEN12_VD_TLB_INV_CR, |
167 |
++ [VIDEO_ENHANCEMENT_CLASS] = GEN12_VE_TLB_INV_CR, |
168 |
++ [COPY_ENGINE_CLASS] = GEN12_BLT_TLB_INV_CR, |
169 |
++ }; |
170 |
++ struct drm_i915_private *i915 = gt->i915; |
171 |
++ struct intel_uncore *uncore = gt->uncore; |
172 |
++ struct intel_engine_cs *engine; |
173 |
++ enum intel_engine_id id; |
174 |
++ const i915_reg_t *regs; |
175 |
++ unsigned int num = 0; |
176 |
++ |
177 |
++ if (I915_SELFTEST_ONLY(gt->awake == -ENODEV)) |
178 |
++ return; |
179 |
++ |
180 |
++ if (INTEL_GEN(i915) == 12) { |
181 |
++ regs = gen12_regs; |
182 |
++ num = ARRAY_SIZE(gen12_regs); |
183 |
++ } else if (INTEL_GEN(i915) >= 8 && INTEL_GEN(i915) <= 11) { |
184 |
++ regs = gen8_regs; |
185 |
++ num = ARRAY_SIZE(gen8_regs); |
186 |
++ } else if (INTEL_GEN(i915) < 8) { |
187 |
++ return; |
188 |
++ } |
189 |
++ |
190 |
++ if (drm_WARN_ONCE(&i915->drm, !num, |
191 |
++ "Platform does not implement TLB invalidation!")) |
192 |
++ return; |
193 |
++ |
194 |
++ GEM_TRACE("\n"); |
195 |
++ |
196 |
++ assert_rpm_wakelock_held(&i915->runtime_pm); |
197 |
++ |
198 |
++ mutex_lock(>->tlb_invalidate_lock); |
199 |
++ intel_uncore_forcewake_get(uncore, FORCEWAKE_ALL); |
200 |
++ |
201 |
++ for_each_engine(engine, gt, id) { |
202 |
++ /* |
203 |
++ * HW architecture suggest typical invalidation time at 40us, |
204 |
++ * with pessimistic cases up to 100us and a recommendation to |
205 |
++ * cap at 1ms. We go a bit higher just in case. |
206 |
++ */ |
207 |
++ const unsigned int timeout_us = 100; |
208 |
++ const unsigned int timeout_ms = 4; |
209 |
++ struct reg_and_bit rb; |
210 |
++ |
211 |
++ rb = get_reg_and_bit(engine, regs == gen8_regs, regs, num); |
212 |
++ if (!i915_mmio_reg_offset(rb.reg)) |
213 |
++ continue; |
214 |
++ |
215 |
++ intel_uncore_write_fw(uncore, rb.reg, rb.bit); |
216 |
++ if (__intel_wait_for_register_fw(uncore, |
217 |
++ rb.reg, rb.bit, 0, |
218 |
++ timeout_us, timeout_ms, |
219 |
++ NULL)) |
220 |
++ drm_err_ratelimited(>->i915->drm, |
221 |
++ "%s TLB invalidation did not complete in %ums!\n", |
222 |
++ engine->name, timeout_ms); |
223 |
++ } |
224 |
++ |
225 |
++ intel_uncore_forcewake_put_delayed(uncore, FORCEWAKE_ALL); |
226 |
++ mutex_unlock(>->tlb_invalidate_lock); |
227 |
++} |
228 |
+diff --git a/drivers/gpu/drm/i915/gt/intel_gt.h b/drivers/gpu/drm/i915/gt/intel_gt.h |
229 |
+index 9157c7411f603..d9a1168172ae3 100644 |
230 |
+--- a/drivers/gpu/drm/i915/gt/intel_gt.h |
231 |
++++ b/drivers/gpu/drm/i915/gt/intel_gt.h |
232 |
+@@ -77,4 +77,6 @@ static inline bool intel_gt_is_wedged(const struct intel_gt *gt) |
233 |
+ void intel_gt_info_print(const struct intel_gt_info *info, |
234 |
+ struct drm_printer *p); |
235 |
+ |
236 |
++void intel_gt_invalidate_tlbs(struct intel_gt *gt); |
237 |
++ |
238 |
+ #endif /* __INTEL_GT_H__ */ |
239 |
+diff --git a/drivers/gpu/drm/i915/gt/intel_gt_types.h b/drivers/gpu/drm/i915/gt/intel_gt_types.h |
240 |
+index 6d39a4a11bf39..78c061614d8bb 100644 |
241 |
+--- a/drivers/gpu/drm/i915/gt/intel_gt_types.h |
242 |
++++ b/drivers/gpu/drm/i915/gt/intel_gt_types.h |
243 |
+@@ -36,6 +36,8 @@ struct intel_gt { |
244 |
+ |
245 |
+ struct intel_uc uc; |
246 |
+ |
247 |
++ struct mutex tlb_invalidate_lock; |
248 |
++ |
249 |
+ struct intel_gt_timelines { |
250 |
+ spinlock_t lock; /* protects active_list */ |
251 |
+ struct list_head active_list; |
252 |
+diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h |
253 |
+index ce8c91c5fdd3b..12488996a7f4f 100644 |
254 |
+--- a/drivers/gpu/drm/i915/i915_reg.h |
255 |
++++ b/drivers/gpu/drm/i915/i915_reg.h |
256 |
+@@ -2639,6 +2639,12 @@ static inline bool i915_mmio_reg_valid(i915_reg_t reg) |
257 |
+ #define GAMT_CHKN_DISABLE_DYNAMIC_CREDIT_SHARING (1 << 28) |
258 |
+ #define GAMT_CHKN_DISABLE_I2M_CYCLE_ON_WR_PORT (1 << 24) |
259 |
+ |
260 |
++#define GEN8_RTCR _MMIO(0x4260) |
261 |
++#define GEN8_M1TCR _MMIO(0x4264) |
262 |
++#define GEN8_M2TCR _MMIO(0x4268) |
263 |
++#define GEN8_BTCR _MMIO(0x426c) |
264 |
++#define GEN8_VTCR _MMIO(0x4270) |
265 |
++ |
266 |
+ #if 0 |
267 |
+ #define PRB0_TAIL _MMIO(0x2030) |
268 |
+ #define PRB0_HEAD _MMIO(0x2034) |
269 |
+@@ -2728,6 +2734,11 @@ static inline bool i915_mmio_reg_valid(i915_reg_t reg) |
270 |
+ #define FAULT_VA_HIGH_BITS (0xf << 0) |
271 |
+ #define FAULT_GTT_SEL (1 << 4) |
272 |
+ |
273 |
++#define GEN12_GFX_TLB_INV_CR _MMIO(0xced8) |
274 |
++#define GEN12_VD_TLB_INV_CR _MMIO(0xcedc) |
275 |
++#define GEN12_VE_TLB_INV_CR _MMIO(0xcee0) |
276 |
++#define GEN12_BLT_TLB_INV_CR _MMIO(0xcee4) |
277 |
++ |
278 |
+ #define GEN12_AUX_ERR_DBG _MMIO(0x43f4) |
279 |
+ |
280 |
+ #define FPGA_DBG _MMIO(0x42300) |
281 |
+diff --git a/drivers/gpu/drm/i915/i915_vma.c b/drivers/gpu/drm/i915/i915_vma.c |
282 |
+index caa9b041616b0..50a86fd89d005 100644 |
283 |
+--- a/drivers/gpu/drm/i915/i915_vma.c |
284 |
++++ b/drivers/gpu/drm/i915/i915_vma.c |
285 |
+@@ -439,6 +439,9 @@ int i915_vma_bind(struct i915_vma *vma, |
286 |
+ vma->ops->bind_vma(vma->vm, NULL, vma, cache_level, bind_flags); |
287 |
+ } |
288 |
+ |
289 |
++ if (vma->obj) |
290 |
++ set_bit(I915_BO_WAS_BOUND_BIT, &vma->obj->flags); |
291 |
++ |
292 |
+ atomic_or(bind_flags, &vma->flags); |
293 |
+ return 0; |
294 |
+ } |
295 |
+diff --git a/drivers/gpu/drm/i915/intel_uncore.c b/drivers/gpu/drm/i915/intel_uncore.c |
296 |
+index 97ded2a59cf4c..01849840ac560 100644 |
297 |
+--- a/drivers/gpu/drm/i915/intel_uncore.c |
298 |
++++ b/drivers/gpu/drm/i915/intel_uncore.c |
299 |
+@@ -694,7 +694,8 @@ void intel_uncore_forcewake_get__locked(struct intel_uncore *uncore, |
300 |
+ } |
301 |
+ |
302 |
+ static void __intel_uncore_forcewake_put(struct intel_uncore *uncore, |
303 |
+- enum forcewake_domains fw_domains) |
304 |
++ enum forcewake_domains fw_domains, |
305 |
++ bool delayed) |
306 |
+ { |
307 |
+ struct intel_uncore_forcewake_domain *domain; |
308 |
+ unsigned int tmp; |
309 |
+@@ -709,7 +710,11 @@ static void __intel_uncore_forcewake_put(struct intel_uncore *uncore, |
310 |
+ continue; |
311 |
+ } |
312 |
+ |
313 |
+- uncore->funcs.force_wake_put(uncore, domain->mask); |
314 |
++ if (delayed && |
315 |
++ !(domain->uncore->fw_domains_timer & domain->mask)) |
316 |
++ fw_domain_arm_timer(domain); |
317 |
++ else |
318 |
++ uncore->funcs.force_wake_put(uncore, domain->mask); |
319 |
+ } |
320 |
+ } |
321 |
+ |
322 |
+@@ -730,7 +735,20 @@ void intel_uncore_forcewake_put(struct intel_uncore *uncore, |
323 |
+ return; |
324 |
+ |
325 |
+ spin_lock_irqsave(&uncore->lock, irqflags); |
326 |
+- __intel_uncore_forcewake_put(uncore, fw_domains); |
327 |
++ __intel_uncore_forcewake_put(uncore, fw_domains, false); |
328 |
++ spin_unlock_irqrestore(&uncore->lock, irqflags); |
329 |
++} |
330 |
++ |
331 |
++void intel_uncore_forcewake_put_delayed(struct intel_uncore *uncore, |
332 |
++ enum forcewake_domains fw_domains) |
333 |
++{ |
334 |
++ unsigned long irqflags; |
335 |
++ |
336 |
++ if (!uncore->funcs.force_wake_put) |
337 |
++ return; |
338 |
++ |
339 |
++ spin_lock_irqsave(&uncore->lock, irqflags); |
340 |
++ __intel_uncore_forcewake_put(uncore, fw_domains, true); |
341 |
+ spin_unlock_irqrestore(&uncore->lock, irqflags); |
342 |
+ } |
343 |
+ |
344 |
+@@ -772,7 +790,7 @@ void intel_uncore_forcewake_put__locked(struct intel_uncore *uncore, |
345 |
+ if (!uncore->funcs.force_wake_put) |
346 |
+ return; |
347 |
+ |
348 |
+- __intel_uncore_forcewake_put(uncore, fw_domains); |
349 |
++ __intel_uncore_forcewake_put(uncore, fw_domains, false); |
350 |
+ } |
351 |
+ |
352 |
+ void assert_forcewakes_inactive(struct intel_uncore *uncore) |
353 |
+diff --git a/drivers/gpu/drm/i915/intel_uncore.h b/drivers/gpu/drm/i915/intel_uncore.h |
354 |
+index c4b22d9d0b451..034f04e0de8b7 100644 |
355 |
+--- a/drivers/gpu/drm/i915/intel_uncore.h |
356 |
++++ b/drivers/gpu/drm/i915/intel_uncore.h |
357 |
+@@ -211,6 +211,8 @@ void intel_uncore_forcewake_get(struct intel_uncore *uncore, |
358 |
+ enum forcewake_domains domains); |
359 |
+ void intel_uncore_forcewake_put(struct intel_uncore *uncore, |
360 |
+ enum forcewake_domains domains); |
361 |
++void intel_uncore_forcewake_put_delayed(struct intel_uncore *uncore, |
362 |
++ enum forcewake_domains domains); |
363 |
+ void intel_uncore_forcewake_flush(struct intel_uncore *uncore, |
364 |
+ enum forcewake_domains fw_domains); |
365 |
+ |
366 |
+diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h |
367 |
+index 1523b51a7284c..ad208a5f4ebe5 100644 |
368 |
+--- a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h |
369 |
++++ b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h |
370 |
+@@ -1088,15 +1088,14 @@ extern int vmw_execbuf_fence_commands(struct drm_file *file_priv, |
371 |
+ struct vmw_private *dev_priv, |
372 |
+ struct vmw_fence_obj **p_fence, |
373 |
+ uint32_t *p_handle); |
374 |
+-extern void vmw_execbuf_copy_fence_user(struct vmw_private *dev_priv, |
375 |
++extern int vmw_execbuf_copy_fence_user(struct vmw_private *dev_priv, |
376 |
+ struct vmw_fpriv *vmw_fp, |
377 |
+ int ret, |
378 |
+ struct drm_vmw_fence_rep __user |
379 |
+ *user_fence_rep, |
380 |
+ struct vmw_fence_obj *fence, |
381 |
+ uint32_t fence_handle, |
382 |
+- int32_t out_fence_fd, |
383 |
+- struct sync_file *sync_file); |
384 |
++ int32_t out_fence_fd); |
385 |
+ bool vmw_cmd_describe(const void *buf, u32 *size, char const **cmd); |
386 |
+ |
387 |
+ /** |
388 |
+diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c |
389 |
+index 83e1b54eb8647..739cbc77d8867 100644 |
390 |
+--- a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c |
391 |
++++ b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c |
392 |
+@@ -3816,17 +3816,17 @@ int vmw_execbuf_fence_commands(struct drm_file *file_priv, |
393 |
+ * Also if copying fails, user-space will be unable to signal the fence object |
394 |
+ * so we wait for it immediately, and then unreference the user-space reference. |
395 |
+ */ |
396 |
+-void |
397 |
++int |
398 |
+ vmw_execbuf_copy_fence_user(struct vmw_private *dev_priv, |
399 |
+ struct vmw_fpriv *vmw_fp, int ret, |
400 |
+ struct drm_vmw_fence_rep __user *user_fence_rep, |
401 |
+ struct vmw_fence_obj *fence, uint32_t fence_handle, |
402 |
+- int32_t out_fence_fd, struct sync_file *sync_file) |
403 |
++ int32_t out_fence_fd) |
404 |
+ { |
405 |
+ struct drm_vmw_fence_rep fence_rep; |
406 |
+ |
407 |
+ if (user_fence_rep == NULL) |
408 |
+- return; |
409 |
++ return 0; |
410 |
+ |
411 |
+ memset(&fence_rep, 0, sizeof(fence_rep)); |
412 |
+ |
413 |
+@@ -3854,20 +3854,14 @@ vmw_execbuf_copy_fence_user(struct vmw_private *dev_priv, |
414 |
+ * handle. |
415 |
+ */ |
416 |
+ if (unlikely(ret != 0) && (fence_rep.error == 0)) { |
417 |
+- if (sync_file) |
418 |
+- fput(sync_file->file); |
419 |
+- |
420 |
+- if (fence_rep.fd != -1) { |
421 |
+- put_unused_fd(fence_rep.fd); |
422 |
+- fence_rep.fd = -1; |
423 |
+- } |
424 |
+- |
425 |
+ ttm_ref_object_base_unref(vmw_fp->tfile, fence_handle, |
426 |
+ TTM_REF_USAGE); |
427 |
+ VMW_DEBUG_USER("Fence copy error. Syncing.\n"); |
428 |
+ (void) vmw_fence_obj_wait(fence, false, false, |
429 |
+ VMW_FENCE_WAIT_TIMEOUT); |
430 |
+ } |
431 |
++ |
432 |
++ return ret ? -EFAULT : 0; |
433 |
+ } |
434 |
+ |
435 |
+ /** |
436 |
+@@ -4209,16 +4203,23 @@ int vmw_execbuf_process(struct drm_file *file_priv, |
437 |
+ |
438 |
+ (void) vmw_fence_obj_wait(fence, false, false, |
439 |
+ VMW_FENCE_WAIT_TIMEOUT); |
440 |
++ } |
441 |
++ } |
442 |
++ |
443 |
++ ret = vmw_execbuf_copy_fence_user(dev_priv, vmw_fpriv(file_priv), ret, |
444 |
++ user_fence_rep, fence, handle, out_fence_fd); |
445 |
++ |
446 |
++ if (sync_file) { |
447 |
++ if (ret) { |
448 |
++ /* usercopy of fence failed, put the file object */ |
449 |
++ fput(sync_file->file); |
450 |
++ put_unused_fd(out_fence_fd); |
451 |
+ } else { |
452 |
+ /* Link the fence with the FD created earlier */ |
453 |
+ fd_install(out_fence_fd, sync_file->file); |
454 |
+ } |
455 |
+ } |
456 |
+ |
457 |
+- vmw_execbuf_copy_fence_user(dev_priv, vmw_fpriv(file_priv), ret, |
458 |
+- user_fence_rep, fence, handle, out_fence_fd, |
459 |
+- sync_file); |
460 |
+- |
461 |
+ /* Don't unreference when handing fence out */ |
462 |
+ if (unlikely(out_fence != NULL)) { |
463 |
+ *out_fence = fence; |
464 |
+@@ -4236,7 +4237,7 @@ int vmw_execbuf_process(struct drm_file *file_priv, |
465 |
+ */ |
466 |
+ vmw_validation_unref_lists(&val_ctx); |
467 |
+ |
468 |
+- return 0; |
469 |
++ return ret; |
470 |
+ |
471 |
+ out_unlock_binding: |
472 |
+ mutex_unlock(&dev_priv->binding_mutex); |
473 |
+diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_fence.c b/drivers/gpu/drm/vmwgfx/vmwgfx_fence.c |
474 |
+index 0f8d293971576..8bc41ec97d71a 100644 |
475 |
+--- a/drivers/gpu/drm/vmwgfx/vmwgfx_fence.c |
476 |
++++ b/drivers/gpu/drm/vmwgfx/vmwgfx_fence.c |
477 |
+@@ -1171,7 +1171,7 @@ int vmw_fence_event_ioctl(struct drm_device *dev, void *data, |
478 |
+ } |
479 |
+ |
480 |
+ vmw_execbuf_copy_fence_user(dev_priv, vmw_fp, 0, user_fence_rep, fence, |
481 |
+- handle, -1, NULL); |
482 |
++ handle, -1); |
483 |
+ vmw_fence_obj_unreference(&fence); |
484 |
+ return 0; |
485 |
+ out_no_create: |
486 |
+diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c b/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c |
487 |
+index 312ed0881a99b..e58112997c881 100644 |
488 |
+--- a/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c |
489 |
++++ b/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c |
490 |
+@@ -2479,7 +2479,7 @@ void vmw_kms_helper_validation_finish(struct vmw_private *dev_priv, |
491 |
+ if (file_priv) |
492 |
+ vmw_execbuf_copy_fence_user(dev_priv, vmw_fpriv(file_priv), |
493 |
+ ret, user_fence_rep, fence, |
494 |
+- handle, -1, NULL); |
495 |
++ handle, -1); |
496 |
+ if (out_fence) |
497 |
+ *out_fence = fence; |
498 |
+ else |
499 |
+diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h |
500 |
+index d04994840b87d..bb3ba614fb174 100644 |
501 |
+--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h |
502 |
++++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h |
503 |
+@@ -1850,6 +1850,14 @@ struct bnx2x { |
504 |
+ |
505 |
+ /* Vxlan/Geneve related information */ |
506 |
+ u16 udp_tunnel_ports[BNX2X_UDP_PORT_MAX]; |
507 |
++ |
508 |
++#define FW_CAP_INVALIDATE_VF_FP_HSI BIT(0) |
509 |
++ u32 fw_cap; |
510 |
++ |
511 |
++ u32 fw_major; |
512 |
++ u32 fw_minor; |
513 |
++ u32 fw_rev; |
514 |
++ u32 fw_eng; |
515 |
+ }; |
516 |
+ |
517 |
+ /* Tx queues may be less or equal to Rx queues */ |
518 |
+@@ -2526,5 +2534,6 @@ void bnx2x_register_phc(struct bnx2x *bp); |
519 |
+ * Meant for implicit re-load flows. |
520 |
+ */ |
521 |
+ int bnx2x_vlan_reconfigure_vid(struct bnx2x *bp); |
522 |
+- |
523 |
++int bnx2x_init_firmware(struct bnx2x *bp); |
524 |
++void bnx2x_release_firmware(struct bnx2x *bp); |
525 |
+ #endif /* bnx2x.h */ |
526 |
+diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c |
527 |
+index b5d954cb409ae..41ebbb2c7d3ac 100644 |
528 |
+--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c |
529 |
++++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c |
530 |
+@@ -2364,10 +2364,8 @@ int bnx2x_compare_fw_ver(struct bnx2x *bp, u32 load_code, bool print_err) |
531 |
+ if (load_code != FW_MSG_CODE_DRV_LOAD_COMMON_CHIP && |
532 |
+ load_code != FW_MSG_CODE_DRV_LOAD_COMMON) { |
533 |
+ /* build my FW version dword */ |
534 |
+- u32 my_fw = (BCM_5710_FW_MAJOR_VERSION) + |
535 |
+- (BCM_5710_FW_MINOR_VERSION << 8) + |
536 |
+- (BCM_5710_FW_REVISION_VERSION << 16) + |
537 |
+- (BCM_5710_FW_ENGINEERING_VERSION << 24); |
538 |
++ u32 my_fw = (bp->fw_major) + (bp->fw_minor << 8) + |
539 |
++ (bp->fw_rev << 16) + (bp->fw_eng << 24); |
540 |
+ |
541 |
+ /* read loaded FW from chip */ |
542 |
+ u32 loaded_fw = REG_RD(bp, XSEM_REG_PRAM); |
543 |
+diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_fw_defs.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_fw_defs.h |
544 |
+index 3f8435208bf49..a84d015da5dfa 100644 |
545 |
+--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_fw_defs.h |
546 |
++++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_fw_defs.h |
547 |
+@@ -241,6 +241,8 @@ |
548 |
+ IRO[221].m2)) |
549 |
+ #define XSTORM_VF_TO_PF_OFFSET(funcId) \ |
550 |
+ (IRO[48].base + ((funcId) * IRO[48].m1)) |
551 |
++#define XSTORM_ETH_FUNCTION_INFO_FP_HSI_VALID_E2_OFFSET(fid) \ |
552 |
++ (IRO[386].base + ((fid) * IRO[386].m1)) |
553 |
+ #define COMMON_ASM_INVALID_ASSERT_OPCODE 0x0 |
554 |
+ |
555 |
+ /* eth hsi version */ |
556 |
+diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_hsi.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_hsi.h |
557 |
+index 622fadc50316e..611efee758340 100644 |
558 |
+--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_hsi.h |
559 |
++++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_hsi.h |
560 |
+@@ -3024,7 +3024,8 @@ struct afex_stats { |
561 |
+ |
562 |
+ #define BCM_5710_FW_MAJOR_VERSION 7 |
563 |
+ #define BCM_5710_FW_MINOR_VERSION 13 |
564 |
+-#define BCM_5710_FW_REVISION_VERSION 15 |
565 |
++#define BCM_5710_FW_REVISION_VERSION 21 |
566 |
++#define BCM_5710_FW_REVISION_VERSION_V15 15 |
567 |
+ #define BCM_5710_FW_ENGINEERING_VERSION 0 |
568 |
+ #define BCM_5710_FW_COMPILE_FLAGS 1 |
569 |
+ |
570 |
+diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c |
571 |
+index 28069b2908625..9a86367a26369 100644 |
572 |
+--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c |
573 |
++++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c |
574 |
+@@ -74,9 +74,19 @@ |
575 |
+ __stringify(BCM_5710_FW_MINOR_VERSION) "." \ |
576 |
+ __stringify(BCM_5710_FW_REVISION_VERSION) "." \ |
577 |
+ __stringify(BCM_5710_FW_ENGINEERING_VERSION) |
578 |
++ |
579 |
++#define FW_FILE_VERSION_V15 \ |
580 |
++ __stringify(BCM_5710_FW_MAJOR_VERSION) "." \ |
581 |
++ __stringify(BCM_5710_FW_MINOR_VERSION) "." \ |
582 |
++ __stringify(BCM_5710_FW_REVISION_VERSION_V15) "." \ |
583 |
++ __stringify(BCM_5710_FW_ENGINEERING_VERSION) |
584 |
++ |
585 |
+ #define FW_FILE_NAME_E1 "bnx2x/bnx2x-e1-" FW_FILE_VERSION ".fw" |
586 |
+ #define FW_FILE_NAME_E1H "bnx2x/bnx2x-e1h-" FW_FILE_VERSION ".fw" |
587 |
+ #define FW_FILE_NAME_E2 "bnx2x/bnx2x-e2-" FW_FILE_VERSION ".fw" |
588 |
++#define FW_FILE_NAME_E1_V15 "bnx2x/bnx2x-e1-" FW_FILE_VERSION_V15 ".fw" |
589 |
++#define FW_FILE_NAME_E1H_V15 "bnx2x/bnx2x-e1h-" FW_FILE_VERSION_V15 ".fw" |
590 |
++#define FW_FILE_NAME_E2_V15 "bnx2x/bnx2x-e2-" FW_FILE_VERSION_V15 ".fw" |
591 |
+ |
592 |
+ /* Time in jiffies before concluding the transmitter is hung */ |
593 |
+ #define TX_TIMEOUT (5*HZ) |
594 |
+@@ -747,9 +757,7 @@ static int bnx2x_mc_assert(struct bnx2x *bp) |
595 |
+ CHIP_IS_E1(bp) ? "everest1" : |
596 |
+ CHIP_IS_E1H(bp) ? "everest1h" : |
597 |
+ CHIP_IS_E2(bp) ? "everest2" : "everest3", |
598 |
+- BCM_5710_FW_MAJOR_VERSION, |
599 |
+- BCM_5710_FW_MINOR_VERSION, |
600 |
+- BCM_5710_FW_REVISION_VERSION); |
601 |
++ bp->fw_major, bp->fw_minor, bp->fw_rev); |
602 |
+ |
603 |
+ return rc; |
604 |
+ } |
605 |
+@@ -12355,6 +12363,15 @@ static int bnx2x_init_bp(struct bnx2x *bp) |
606 |
+ |
607 |
+ bnx2x_read_fwinfo(bp); |
608 |
+ |
609 |
++ if (IS_PF(bp)) { |
610 |
++ rc = bnx2x_init_firmware(bp); |
611 |
++ |
612 |
++ if (rc) { |
613 |
++ bnx2x_free_mem_bp(bp); |
614 |
++ return rc; |
615 |
++ } |
616 |
++ } |
617 |
++ |
618 |
+ func = BP_FUNC(bp); |
619 |
+ |
620 |
+ /* need to reset chip if undi was active */ |
621 |
+@@ -12367,6 +12384,7 @@ static int bnx2x_init_bp(struct bnx2x *bp) |
622 |
+ |
623 |
+ rc = bnx2x_prev_unload(bp); |
624 |
+ if (rc) { |
625 |
++ bnx2x_release_firmware(bp); |
626 |
+ bnx2x_free_mem_bp(bp); |
627 |
+ return rc; |
628 |
+ } |
629 |
+@@ -13366,16 +13384,11 @@ static int bnx2x_check_firmware(struct bnx2x *bp) |
630 |
+ /* Check FW version */ |
631 |
+ offset = be32_to_cpu(fw_hdr->fw_version.offset); |
632 |
+ fw_ver = firmware->data + offset; |
633 |
+- if ((fw_ver[0] != BCM_5710_FW_MAJOR_VERSION) || |
634 |
+- (fw_ver[1] != BCM_5710_FW_MINOR_VERSION) || |
635 |
+- (fw_ver[2] != BCM_5710_FW_REVISION_VERSION) || |
636 |
+- (fw_ver[3] != BCM_5710_FW_ENGINEERING_VERSION)) { |
637 |
++ if (fw_ver[0] != bp->fw_major || fw_ver[1] != bp->fw_minor || |
638 |
++ fw_ver[2] != bp->fw_rev || fw_ver[3] != bp->fw_eng) { |
639 |
+ BNX2X_ERR("Bad FW version:%d.%d.%d.%d. Should be %d.%d.%d.%d\n", |
640 |
+- fw_ver[0], fw_ver[1], fw_ver[2], fw_ver[3], |
641 |
+- BCM_5710_FW_MAJOR_VERSION, |
642 |
+- BCM_5710_FW_MINOR_VERSION, |
643 |
+- BCM_5710_FW_REVISION_VERSION, |
644 |
+- BCM_5710_FW_ENGINEERING_VERSION); |
645 |
++ fw_ver[0], fw_ver[1], fw_ver[2], fw_ver[3], |
646 |
++ bp->fw_major, bp->fw_minor, bp->fw_rev, bp->fw_eng); |
647 |
+ return -EINVAL; |
648 |
+ } |
649 |
+ |
650 |
+@@ -13453,34 +13466,51 @@ do { \ |
651 |
+ (u8 *)bp->arr, len); \ |
652 |
+ } while (0) |
653 |
+ |
654 |
+-static int bnx2x_init_firmware(struct bnx2x *bp) |
655 |
++int bnx2x_init_firmware(struct bnx2x *bp) |
656 |
+ { |
657 |
+- const char *fw_file_name; |
658 |
++ const char *fw_file_name, *fw_file_name_v15; |
659 |
+ struct bnx2x_fw_file_hdr *fw_hdr; |
660 |
+ int rc; |
661 |
+ |
662 |
+ if (bp->firmware) |
663 |
+ return 0; |
664 |
+ |
665 |
+- if (CHIP_IS_E1(bp)) |
666 |
++ if (CHIP_IS_E1(bp)) { |
667 |
+ fw_file_name = FW_FILE_NAME_E1; |
668 |
+- else if (CHIP_IS_E1H(bp)) |
669 |
++ fw_file_name_v15 = FW_FILE_NAME_E1_V15; |
670 |
++ } else if (CHIP_IS_E1H(bp)) { |
671 |
+ fw_file_name = FW_FILE_NAME_E1H; |
672 |
+- else if (!CHIP_IS_E1x(bp)) |
673 |
++ fw_file_name_v15 = FW_FILE_NAME_E1H_V15; |
674 |
++ } else if (!CHIP_IS_E1x(bp)) { |
675 |
+ fw_file_name = FW_FILE_NAME_E2; |
676 |
+- else { |
677 |
++ fw_file_name_v15 = FW_FILE_NAME_E2_V15; |
678 |
++ } else { |
679 |
+ BNX2X_ERR("Unsupported chip revision\n"); |
680 |
+ return -EINVAL; |
681 |
+ } |
682 |
++ |
683 |
+ BNX2X_DEV_INFO("Loading %s\n", fw_file_name); |
684 |
+ |
685 |
+ rc = request_firmware(&bp->firmware, fw_file_name, &bp->pdev->dev); |
686 |
+ if (rc) { |
687 |
+- BNX2X_ERR("Can't load firmware file %s\n", |
688 |
+- fw_file_name); |
689 |
+- goto request_firmware_exit; |
690 |
++ BNX2X_DEV_INFO("Trying to load older fw %s\n", fw_file_name_v15); |
691 |
++ |
692 |
++ /* try to load prev version */ |
693 |
++ rc = request_firmware(&bp->firmware, fw_file_name_v15, &bp->pdev->dev); |
694 |
++ |
695 |
++ if (rc) |
696 |
++ goto request_firmware_exit; |
697 |
++ |
698 |
++ bp->fw_rev = BCM_5710_FW_REVISION_VERSION_V15; |
699 |
++ } else { |
700 |
++ bp->fw_cap |= FW_CAP_INVALIDATE_VF_FP_HSI; |
701 |
++ bp->fw_rev = BCM_5710_FW_REVISION_VERSION; |
702 |
+ } |
703 |
+ |
704 |
++ bp->fw_major = BCM_5710_FW_MAJOR_VERSION; |
705 |
++ bp->fw_minor = BCM_5710_FW_MINOR_VERSION; |
706 |
++ bp->fw_eng = BCM_5710_FW_ENGINEERING_VERSION; |
707 |
++ |
708 |
+ rc = bnx2x_check_firmware(bp); |
709 |
+ if (rc) { |
710 |
+ BNX2X_ERR("Corrupt firmware file %s\n", fw_file_name); |
711 |
+@@ -13536,7 +13566,7 @@ request_firmware_exit: |
712 |
+ return rc; |
713 |
+ } |
714 |
+ |
715 |
+-static void bnx2x_release_firmware(struct bnx2x *bp) |
716 |
++void bnx2x_release_firmware(struct bnx2x *bp) |
717 |
+ { |
718 |
+ kfree(bp->init_ops_offsets); |
719 |
+ kfree(bp->init_ops); |
720 |
+@@ -14053,6 +14083,7 @@ static int bnx2x_init_one(struct pci_dev *pdev, |
721 |
+ return 0; |
722 |
+ |
723 |
+ init_one_freemem: |
724 |
++ bnx2x_release_firmware(bp); |
725 |
+ bnx2x_free_mem_bp(bp); |
726 |
+ |
727 |
+ init_one_exit: |
728 |
+diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c |
729 |
+index 03eb0179ec008..08437eaacbb96 100644 |
730 |
+--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c |
731 |
++++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c |
732 |
+@@ -758,9 +758,18 @@ static void bnx2x_vf_igu_reset(struct bnx2x *bp, struct bnx2x_virtf *vf) |
733 |
+ |
734 |
+ void bnx2x_vf_enable_access(struct bnx2x *bp, u8 abs_vfid) |
735 |
+ { |
736 |
++ u16 abs_fid; |
737 |
++ |
738 |
++ abs_fid = FW_VF_HANDLE(abs_vfid); |
739 |
++ |
740 |
+ /* set the VF-PF association in the FW */ |
741 |
+- storm_memset_vf_to_pf(bp, FW_VF_HANDLE(abs_vfid), BP_FUNC(bp)); |
742 |
+- storm_memset_func_en(bp, FW_VF_HANDLE(abs_vfid), 1); |
743 |
++ storm_memset_vf_to_pf(bp, abs_fid, BP_FUNC(bp)); |
744 |
++ storm_memset_func_en(bp, abs_fid, 1); |
745 |
++ |
746 |
++ /* Invalidate fp_hsi version for vfs */ |
747 |
++ if (bp->fw_cap & FW_CAP_INVALIDATE_VF_FP_HSI) |
748 |
++ REG_WR8(bp, BAR_XSTRORM_INTMEM + |
749 |
++ XSTORM_ETH_FUNCTION_INFO_FP_HSI_VALID_E2_OFFSET(abs_fid), 0); |
750 |
+ |
751 |
+ /* clear vf errors*/ |
752 |
+ bnx2x_vf_semi_clear_err(bp, abs_vfid); |
753 |
+diff --git a/fs/select.c b/fs/select.c |
754 |
+index 945896d0ac9e7..5edffee1162c2 100644 |
755 |
+--- a/fs/select.c |
756 |
++++ b/fs/select.c |
757 |
+@@ -458,9 +458,11 @@ get_max: |
758 |
+ return max; |
759 |
+ } |
760 |
+ |
761 |
+-#define POLLIN_SET (EPOLLRDNORM | EPOLLRDBAND | EPOLLIN | EPOLLHUP | EPOLLERR) |
762 |
+-#define POLLOUT_SET (EPOLLWRBAND | EPOLLWRNORM | EPOLLOUT | EPOLLERR) |
763 |
+-#define POLLEX_SET (EPOLLPRI) |
764 |
++#define POLLIN_SET (EPOLLRDNORM | EPOLLRDBAND | EPOLLIN | EPOLLHUP | EPOLLERR |\ |
765 |
++ EPOLLNVAL) |
766 |
++#define POLLOUT_SET (EPOLLWRBAND | EPOLLWRNORM | EPOLLOUT | EPOLLERR |\ |
767 |
++ EPOLLNVAL) |
768 |
++#define POLLEX_SET (EPOLLPRI | EPOLLNVAL) |
769 |
+ |
770 |
+ static inline void wait_key_set(poll_table *wait, unsigned long in, |
771 |
+ unsigned long out, unsigned long bit, |
772 |
+@@ -527,6 +529,7 @@ static int do_select(int n, fd_set_bits *fds, struct timespec64 *end_time) |
773 |
+ break; |
774 |
+ if (!(bit & all_bits)) |
775 |
+ continue; |
776 |
++ mask = EPOLLNVAL; |
777 |
+ f = fdget(i); |
778 |
+ if (f.file) { |
779 |
+ wait_key_set(wait, in, out, bit, |
780 |
+@@ -534,34 +537,34 @@ static int do_select(int n, fd_set_bits *fds, struct timespec64 *end_time) |
781 |
+ mask = vfs_poll(f.file, wait); |
782 |
+ |
783 |
+ fdput(f); |
784 |
+- if ((mask & POLLIN_SET) && (in & bit)) { |
785 |
+- res_in |= bit; |
786 |
+- retval++; |
787 |
+- wait->_qproc = NULL; |
788 |
+- } |
789 |
+- if ((mask & POLLOUT_SET) && (out & bit)) { |
790 |
+- res_out |= bit; |
791 |
+- retval++; |
792 |
+- wait->_qproc = NULL; |
793 |
+- } |
794 |
+- if ((mask & POLLEX_SET) && (ex & bit)) { |
795 |
+- res_ex |= bit; |
796 |
+- retval++; |
797 |
+- wait->_qproc = NULL; |
798 |
+- } |
799 |
+- /* got something, stop busy polling */ |
800 |
+- if (retval) { |
801 |
+- can_busy_loop = false; |
802 |
+- busy_flag = 0; |
803 |
+- |
804 |
+- /* |
805 |
+- * only remember a returned |
806 |
+- * POLL_BUSY_LOOP if we asked for it |
807 |
+- */ |
808 |
+- } else if (busy_flag & mask) |
809 |
+- can_busy_loop = true; |
810 |
+- |
811 |
+ } |
812 |
++ if ((mask & POLLIN_SET) && (in & bit)) { |
813 |
++ res_in |= bit; |
814 |
++ retval++; |
815 |
++ wait->_qproc = NULL; |
816 |
++ } |
817 |
++ if ((mask & POLLOUT_SET) && (out & bit)) { |
818 |
++ res_out |= bit; |
819 |
++ retval++; |
820 |
++ wait->_qproc = NULL; |
821 |
++ } |
822 |
++ if ((mask & POLLEX_SET) && (ex & bit)) { |
823 |
++ res_ex |= bit; |
824 |
++ retval++; |
825 |
++ wait->_qproc = NULL; |
826 |
++ } |
827 |
++ /* got something, stop busy polling */ |
828 |
++ if (retval) { |
829 |
++ can_busy_loop = false; |
830 |
++ busy_flag = 0; |
831 |
++ |
832 |
++ /* |
833 |
++ * only remember a returned |
834 |
++ * POLL_BUSY_LOOP if we asked for it |
835 |
++ */ |
836 |
++ } else if (busy_flag & mask) |
837 |
++ can_busy_loop = true; |
838 |
++ |
839 |
+ } |
840 |
+ if (res_in) |
841 |
+ *rinp = res_in; |
842 |
+diff --git a/kernel/rcu/tree.c b/kernel/rcu/tree.c |
843 |
+index b74e7ace4376b..844c35803739e 100644 |
844 |
+--- a/kernel/rcu/tree.c |
845 |
++++ b/kernel/rcu/tree.c |
846 |
+@@ -1581,10 +1581,11 @@ static void __maybe_unused rcu_advance_cbs_nowake(struct rcu_node *rnp, |
847 |
+ struct rcu_data *rdp) |
848 |
+ { |
849 |
+ rcu_lockdep_assert_cblist_protected(rdp); |
850 |
+- if (!rcu_seq_state(rcu_seq_current(&rnp->gp_seq)) || |
851 |
+- !raw_spin_trylock_rcu_node(rnp)) |
852 |
++ if (!rcu_seq_state(rcu_seq_current(&rnp->gp_seq)) || !raw_spin_trylock_rcu_node(rnp)) |
853 |
+ return; |
854 |
+- WARN_ON_ONCE(rcu_advance_cbs(rnp, rdp)); |
855 |
++ // The grace period cannot end while we hold the rcu_node lock. |
856 |
++ if (rcu_seq_state(rcu_seq_current(&rnp->gp_seq))) |
857 |
++ WARN_ON_ONCE(rcu_advance_cbs(rnp, rdp)); |
858 |
+ raw_spin_unlock_rcu_node(rnp); |
859 |
+ } |
860 |
+ |