diff options
author | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2018-03-20 06:27:18 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2018-03-20 06:27:18 -0400 |
commit | 4958134df54c2c84e9c22ea042761d439164d26e (patch) | |
tree | 503177afab11f7d25b12a84ce25b481d305c51ba /drivers/gpu/drm/i915 | |
parent | c4f528795d1add8b63652673f7262729f679c6c1 (diff) | |
parent | c698ca5278934c0ae32297a8725ced2e27585d7f (diff) |
Merge 4.16-rc6 into tty-next
We want the serial/tty fixes in here as well.
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/gpu/drm/i915')
-rw-r--r-- | drivers/gpu/drm/i915/gvt/cmd_parser.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/gvt/mmio_context.c | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/gvt/scheduler.c | 71 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/gvt/scheduler.h | 5 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_gem.c | 22 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_gem_execbuffer.c | 4 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_gem_request.c | 4 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_perf.c | 40 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_reg.h | 4 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_sysfs.c | 10 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/intel_audio.c | 6 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/intel_dp.c | 10 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/intel_lrc.c | 5 |
13 files changed, 138 insertions, 53 deletions
diff --git a/drivers/gpu/drm/i915/gvt/cmd_parser.c b/drivers/gpu/drm/i915/gvt/cmd_parser.c index c8454ac43fae..db6b94dda5df 100644 --- a/drivers/gpu/drm/i915/gvt/cmd_parser.c +++ b/drivers/gpu/drm/i915/gvt/cmd_parser.c | |||
@@ -471,6 +471,7 @@ struct parser_exec_state { | |||
471 | * used when ret from 2nd level batch buffer | 471 | * used when ret from 2nd level batch buffer |
472 | */ | 472 | */ |
473 | int saved_buf_addr_type; | 473 | int saved_buf_addr_type; |
474 | bool is_ctx_wa; | ||
474 | 475 | ||
475 | struct cmd_info *info; | 476 | struct cmd_info *info; |
476 | 477 | ||
@@ -1715,6 +1716,11 @@ static int perform_bb_shadow(struct parser_exec_state *s) | |||
1715 | bb->accessing = true; | 1716 | bb->accessing = true; |
1716 | bb->bb_start_cmd_va = s->ip_va; | 1717 | bb->bb_start_cmd_va = s->ip_va; |
1717 | 1718 | ||
1719 | if ((s->buf_type == BATCH_BUFFER_INSTRUCTION) && (!s->is_ctx_wa)) | ||
1720 | bb->bb_offset = s->ip_va - s->rb_va; | ||
1721 | else | ||
1722 | bb->bb_offset = 0; | ||
1723 | |||
1718 | /* | 1724 | /* |
1719 | * ip_va saves the virtual address of the shadow batch buffer, while | 1725 | * ip_va saves the virtual address of the shadow batch buffer, while |
1720 | * ip_gma saves the graphics address of the original batch buffer. | 1726 | * ip_gma saves the graphics address of the original batch buffer. |
@@ -2571,6 +2577,7 @@ static int scan_workload(struct intel_vgpu_workload *workload) | |||
2571 | s.ring_tail = gma_tail; | 2577 | s.ring_tail = gma_tail; |
2572 | s.rb_va = workload->shadow_ring_buffer_va; | 2578 | s.rb_va = workload->shadow_ring_buffer_va; |
2573 | s.workload = workload; | 2579 | s.workload = workload; |
2580 | s.is_ctx_wa = false; | ||
2574 | 2581 | ||
2575 | if ((bypass_scan_mask & (1 << workload->ring_id)) || | 2582 | if ((bypass_scan_mask & (1 << workload->ring_id)) || |
2576 | gma_head == gma_tail) | 2583 | gma_head == gma_tail) |
@@ -2624,6 +2631,7 @@ static int scan_wa_ctx(struct intel_shadow_wa_ctx *wa_ctx) | |||
2624 | s.ring_tail = gma_tail; | 2631 | s.ring_tail = gma_tail; |
2625 | s.rb_va = wa_ctx->indirect_ctx.shadow_va; | 2632 | s.rb_va = wa_ctx->indirect_ctx.shadow_va; |
2626 | s.workload = workload; | 2633 | s.workload = workload; |
2634 | s.is_ctx_wa = true; | ||
2627 | 2635 | ||
2628 | if (!intel_gvt_ggtt_validate_range(s.vgpu, s.ring_start, s.ring_size)) { | 2636 | if (!intel_gvt_ggtt_validate_range(s.vgpu, s.ring_start, s.ring_size)) { |
2629 | ret = -EINVAL; | 2637 | ret = -EINVAL; |
diff --git a/drivers/gpu/drm/i915/gvt/mmio_context.c b/drivers/gpu/drm/i915/gvt/mmio_context.c index 256f1bb522b7..152df3d0291e 100644 --- a/drivers/gpu/drm/i915/gvt/mmio_context.c +++ b/drivers/gpu/drm/i915/gvt/mmio_context.c | |||
@@ -394,9 +394,11 @@ void intel_gvt_switch_mmio(struct intel_vgpu *pre, | |||
394 | * performace for batch mmio read/write, so we need | 394 | * performace for batch mmio read/write, so we need |
395 | * handle forcewake mannually. | 395 | * handle forcewake mannually. |
396 | */ | 396 | */ |
397 | intel_runtime_pm_get(dev_priv); | ||
397 | intel_uncore_forcewake_get(dev_priv, FORCEWAKE_ALL); | 398 | intel_uncore_forcewake_get(dev_priv, FORCEWAKE_ALL); |
398 | switch_mmio(pre, next, ring_id); | 399 | switch_mmio(pre, next, ring_id); |
399 | intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); | 400 | intel_uncore_forcewake_put(dev_priv, FORCEWAKE_ALL); |
401 | intel_runtime_pm_put(dev_priv); | ||
400 | } | 402 | } |
401 | 403 | ||
402 | /** | 404 | /** |
diff --git a/drivers/gpu/drm/i915/gvt/scheduler.c b/drivers/gpu/drm/i915/gvt/scheduler.c index b55b3580ca1d..d74d6f05c62c 100644 --- a/drivers/gpu/drm/i915/gvt/scheduler.c +++ b/drivers/gpu/drm/i915/gvt/scheduler.c | |||
@@ -52,6 +52,54 @@ static void set_context_pdp_root_pointer( | |||
52 | pdp_pair[i].val = pdp[7 - i]; | 52 | pdp_pair[i].val = pdp[7 - i]; |
53 | } | 53 | } |
54 | 54 | ||
55 | /* | ||
56 | * when populating shadow ctx from guest, we should not overrride oa related | ||
57 | * registers, so that they will not be overlapped by guest oa configs. Thus | ||
58 | * made it possible to capture oa data from host for both host and guests. | ||
59 | */ | ||
60 | static void sr_oa_regs(struct intel_vgpu_workload *workload, | ||
61 | u32 *reg_state, bool save) | ||
62 | { | ||
63 | struct drm_i915_private *dev_priv = workload->vgpu->gvt->dev_priv; | ||
64 | u32 ctx_oactxctrl = dev_priv->perf.oa.ctx_oactxctrl_offset; | ||
65 | u32 ctx_flexeu0 = dev_priv->perf.oa.ctx_flexeu0_offset; | ||
66 | int i = 0; | ||
67 | u32 flex_mmio[] = { | ||
68 | i915_mmio_reg_offset(EU_PERF_CNTL0), | ||
69 | i915_mmio_reg_offset(EU_PERF_CNTL1), | ||
70 | i915_mmio_reg_offset(EU_PERF_CNTL2), | ||
71 | i915_mmio_reg_offset(EU_PERF_CNTL3), | ||
72 | i915_mmio_reg_offset(EU_PERF_CNTL4), | ||
73 | i915_mmio_reg_offset(EU_PERF_CNTL5), | ||
74 | i915_mmio_reg_offset(EU_PERF_CNTL6), | ||
75 | }; | ||
76 | |||
77 | if (!workload || !reg_state || workload->ring_id != RCS) | ||
78 | return; | ||
79 | |||
80 | if (save) { | ||
81 | workload->oactxctrl = reg_state[ctx_oactxctrl + 1]; | ||
82 | |||
83 | for (i = 0; i < ARRAY_SIZE(workload->flex_mmio); i++) { | ||
84 | u32 state_offset = ctx_flexeu0 + i * 2; | ||
85 | |||
86 | workload->flex_mmio[i] = reg_state[state_offset + 1]; | ||
87 | } | ||
88 | } else { | ||
89 | reg_state[ctx_oactxctrl] = | ||
90 | i915_mmio_reg_offset(GEN8_OACTXCONTROL); | ||
91 | reg_state[ctx_oactxctrl + 1] = workload->oactxctrl; | ||
92 | |||
93 | for (i = 0; i < ARRAY_SIZE(workload->flex_mmio); i++) { | ||
94 | u32 state_offset = ctx_flexeu0 + i * 2; | ||
95 | u32 mmio = flex_mmio[i]; | ||
96 | |||
97 | reg_state[state_offset] = mmio; | ||
98 | reg_state[state_offset + 1] = workload->flex_mmio[i]; | ||
99 | } | ||
100 | } | ||
101 | } | ||
102 | |||
55 | static int populate_shadow_context(struct intel_vgpu_workload *workload) | 103 | static int populate_shadow_context(struct intel_vgpu_workload *workload) |
56 | { | 104 | { |
57 | struct intel_vgpu *vgpu = workload->vgpu; | 105 | struct intel_vgpu *vgpu = workload->vgpu; |
@@ -98,6 +146,7 @@ static int populate_shadow_context(struct intel_vgpu_workload *workload) | |||
98 | page = i915_gem_object_get_page(ctx_obj, LRC_STATE_PN); | 146 | page = i915_gem_object_get_page(ctx_obj, LRC_STATE_PN); |
99 | shadow_ring_context = kmap(page); | 147 | shadow_ring_context = kmap(page); |
100 | 148 | ||
149 | sr_oa_regs(workload, (u32 *)shadow_ring_context, true); | ||
101 | #define COPY_REG(name) \ | 150 | #define COPY_REG(name) \ |
102 | intel_gvt_hypervisor_read_gpa(vgpu, workload->ring_context_gpa \ | 151 | intel_gvt_hypervisor_read_gpa(vgpu, workload->ring_context_gpa \ |
103 | + RING_CTX_OFF(name.val), &shadow_ring_context->name.val, 4) | 152 | + RING_CTX_OFF(name.val), &shadow_ring_context->name.val, 4) |
@@ -122,6 +171,7 @@ static int populate_shadow_context(struct intel_vgpu_workload *workload) | |||
122 | sizeof(*shadow_ring_context), | 171 | sizeof(*shadow_ring_context), |
123 | I915_GTT_PAGE_SIZE - sizeof(*shadow_ring_context)); | 172 | I915_GTT_PAGE_SIZE - sizeof(*shadow_ring_context)); |
124 | 173 | ||
174 | sr_oa_regs(workload, (u32 *)shadow_ring_context, false); | ||
125 | kunmap(page); | 175 | kunmap(page); |
126 | return 0; | 176 | return 0; |
127 | } | 177 | } |
@@ -376,6 +426,17 @@ static int prepare_shadow_batch_buffer(struct intel_vgpu_workload *workload) | |||
376 | goto err; | 426 | goto err; |
377 | } | 427 | } |
378 | 428 | ||
429 | /* For privilge batch buffer and not wa_ctx, the bb_start_cmd_va | ||
430 | * is only updated into ring_scan_buffer, not real ring address | ||
431 | * allocated in later copy_workload_to_ring_buffer. pls be noted | ||
432 | * shadow_ring_buffer_va is now pointed to real ring buffer va | ||
433 | * in copy_workload_to_ring_buffer. | ||
434 | */ | ||
435 | |||
436 | if (bb->bb_offset) | ||
437 | bb->bb_start_cmd_va = workload->shadow_ring_buffer_va | ||
438 | + bb->bb_offset; | ||
439 | |||
379 | /* relocate shadow batch buffer */ | 440 | /* relocate shadow batch buffer */ |
380 | bb->bb_start_cmd_va[1] = i915_ggtt_offset(bb->vma); | 441 | bb->bb_start_cmd_va[1] = i915_ggtt_offset(bb->vma); |
381 | if (gmadr_bytes == 8) | 442 | if (gmadr_bytes == 8) |
@@ -1044,10 +1105,12 @@ int intel_vgpu_setup_submission(struct intel_vgpu *vgpu) | |||
1044 | 1105 | ||
1045 | bitmap_zero(s->shadow_ctx_desc_updated, I915_NUM_ENGINES); | 1106 | bitmap_zero(s->shadow_ctx_desc_updated, I915_NUM_ENGINES); |
1046 | 1107 | ||
1047 | s->workloads = kmem_cache_create("gvt-g_vgpu_workload", | 1108 | s->workloads = kmem_cache_create_usercopy("gvt-g_vgpu_workload", |
1048 | sizeof(struct intel_vgpu_workload), 0, | 1109 | sizeof(struct intel_vgpu_workload), 0, |
1049 | SLAB_HWCACHE_ALIGN, | 1110 | SLAB_HWCACHE_ALIGN, |
1050 | NULL); | 1111 | offsetof(struct intel_vgpu_workload, rb_tail), |
1112 | sizeof_field(struct intel_vgpu_workload, rb_tail), | ||
1113 | NULL); | ||
1051 | 1114 | ||
1052 | if (!s->workloads) { | 1115 | if (!s->workloads) { |
1053 | ret = -ENOMEM; | 1116 | ret = -ENOMEM; |
diff --git a/drivers/gpu/drm/i915/gvt/scheduler.h b/drivers/gpu/drm/i915/gvt/scheduler.h index ff175a98b19e..a79a4f60637e 100644 --- a/drivers/gpu/drm/i915/gvt/scheduler.h +++ b/drivers/gpu/drm/i915/gvt/scheduler.h | |||
@@ -110,6 +110,10 @@ struct intel_vgpu_workload { | |||
110 | /* shadow batch buffer */ | 110 | /* shadow batch buffer */ |
111 | struct list_head shadow_bb; | 111 | struct list_head shadow_bb; |
112 | struct intel_shadow_wa_ctx wa_ctx; | 112 | struct intel_shadow_wa_ctx wa_ctx; |
113 | |||
114 | /* oa registers */ | ||
115 | u32 oactxctrl; | ||
116 | u32 flex_mmio[7]; | ||
113 | }; | 117 | }; |
114 | 118 | ||
115 | struct intel_vgpu_shadow_bb { | 119 | struct intel_vgpu_shadow_bb { |
@@ -120,6 +124,7 @@ struct intel_vgpu_shadow_bb { | |||
120 | u32 *bb_start_cmd_va; | 124 | u32 *bb_start_cmd_va; |
121 | unsigned int clflush; | 125 | unsigned int clflush; |
122 | bool accessing; | 126 | bool accessing; |
127 | unsigned long bb_offset; | ||
123 | }; | 128 | }; |
124 | 129 | ||
125 | #define workload_q_head(vgpu, ring_id) \ | 130 | #define workload_q_head(vgpu, ring_id) \ |
diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index dd89abd2263d..6ff5d655c202 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c | |||
@@ -434,20 +434,28 @@ i915_gem_object_wait_reservation(struct reservation_object *resv, | |||
434 | dma_fence_put(shared[i]); | 434 | dma_fence_put(shared[i]); |
435 | kfree(shared); | 435 | kfree(shared); |
436 | 436 | ||
437 | /* | ||
438 | * If both shared fences and an exclusive fence exist, | ||
439 | * then by construction the shared fences must be later | ||
440 | * than the exclusive fence. If we successfully wait for | ||
441 | * all the shared fences, we know that the exclusive fence | ||
442 | * must all be signaled. If all the shared fences are | ||
443 | * signaled, we can prune the array and recover the | ||
444 | * floating references on the fences/requests. | ||
445 | */ | ||
437 | prune_fences = count && timeout >= 0; | 446 | prune_fences = count && timeout >= 0; |
438 | } else { | 447 | } else { |
439 | excl = reservation_object_get_excl_rcu(resv); | 448 | excl = reservation_object_get_excl_rcu(resv); |
440 | } | 449 | } |
441 | 450 | ||
442 | if (excl && timeout >= 0) { | 451 | if (excl && timeout >= 0) |
443 | timeout = i915_gem_object_wait_fence(excl, flags, timeout, | 452 | timeout = i915_gem_object_wait_fence(excl, flags, timeout, |
444 | rps_client); | 453 | rps_client); |
445 | prune_fences = timeout >= 0; | ||
446 | } | ||
447 | 454 | ||
448 | dma_fence_put(excl); | 455 | dma_fence_put(excl); |
449 | 456 | ||
450 | /* Oportunistically prune the fences iff we know they have *all* been | 457 | /* |
458 | * Opportunistically prune the fences iff we know they have *all* been | ||
451 | * signaled and that the reservation object has not been changed (i.e. | 459 | * signaled and that the reservation object has not been changed (i.e. |
452 | * no new fences have been added). | 460 | * no new fences have been added). |
453 | */ | 461 | */ |
@@ -3205,8 +3213,10 @@ void i915_gem_set_wedged(struct drm_i915_private *i915) | |||
3205 | * rolling the global seqno forward (since this would complete requests | 3213 | * rolling the global seqno forward (since this would complete requests |
3206 | * for which we haven't set the fence error to EIO yet). | 3214 | * for which we haven't set the fence error to EIO yet). |
3207 | */ | 3215 | */ |
3208 | for_each_engine(engine, i915, id) | 3216 | for_each_engine(engine, i915, id) { |
3217 | i915_gem_reset_prepare_engine(engine); | ||
3209 | engine->submit_request = nop_submit_request; | 3218 | engine->submit_request = nop_submit_request; |
3219 | } | ||
3210 | 3220 | ||
3211 | /* | 3221 | /* |
3212 | * Make sure no one is running the old callback before we proceed with | 3222 | * Make sure no one is running the old callback before we proceed with |
@@ -3244,6 +3254,8 @@ void i915_gem_set_wedged(struct drm_i915_private *i915) | |||
3244 | intel_engine_init_global_seqno(engine, | 3254 | intel_engine_init_global_seqno(engine, |
3245 | intel_engine_last_submit(engine)); | 3255 | intel_engine_last_submit(engine)); |
3246 | spin_unlock_irqrestore(&engine->timeline->lock, flags); | 3256 | spin_unlock_irqrestore(&engine->timeline->lock, flags); |
3257 | |||
3258 | i915_gem_reset_finish_engine(engine); | ||
3247 | } | 3259 | } |
3248 | 3260 | ||
3249 | set_bit(I915_WEDGED, &i915->gpu_error.flags); | 3261 | set_bit(I915_WEDGED, &i915->gpu_error.flags); |
diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index 4401068ff468..3ab1ace2a6bd 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c | |||
@@ -505,6 +505,8 @@ eb_add_vma(struct i915_execbuffer *eb, unsigned int i, struct i915_vma *vma) | |||
505 | list_add_tail(&vma->exec_link, &eb->unbound); | 505 | list_add_tail(&vma->exec_link, &eb->unbound); |
506 | if (drm_mm_node_allocated(&vma->node)) | 506 | if (drm_mm_node_allocated(&vma->node)) |
507 | err = i915_vma_unbind(vma); | 507 | err = i915_vma_unbind(vma); |
508 | if (unlikely(err)) | ||
509 | vma->exec_flags = NULL; | ||
508 | } | 510 | } |
509 | return err; | 511 | return err; |
510 | } | 512 | } |
@@ -2410,7 +2412,7 @@ err_request: | |||
2410 | if (out_fence) { | 2412 | if (out_fence) { |
2411 | if (err == 0) { | 2413 | if (err == 0) { |
2412 | fd_install(out_fence_fd, out_fence->file); | 2414 | fd_install(out_fence_fd, out_fence->file); |
2413 | args->rsvd2 &= GENMASK_ULL(0, 31); /* keep in-fence */ | 2415 | args->rsvd2 &= GENMASK_ULL(31, 0); /* keep in-fence */ |
2414 | args->rsvd2 |= (u64)out_fence_fd << 32; | 2416 | args->rsvd2 |= (u64)out_fence_fd << 32; |
2415 | out_fence_fd = -1; | 2417 | out_fence_fd = -1; |
2416 | } else { | 2418 | } else { |
diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c index e09d18df8b7f..a3e93d46316a 100644 --- a/drivers/gpu/drm/i915/i915_gem_request.c +++ b/drivers/gpu/drm/i915/i915_gem_request.c | |||
@@ -476,8 +476,6 @@ void __i915_gem_request_submit(struct drm_i915_gem_request *request) | |||
476 | GEM_BUG_ON(!irqs_disabled()); | 476 | GEM_BUG_ON(!irqs_disabled()); |
477 | lockdep_assert_held(&engine->timeline->lock); | 477 | lockdep_assert_held(&engine->timeline->lock); |
478 | 478 | ||
479 | trace_i915_gem_request_execute(request); | ||
480 | |||
481 | /* Transfer from per-context onto the global per-engine timeline */ | 479 | /* Transfer from per-context onto the global per-engine timeline */ |
482 | timeline = engine->timeline; | 480 | timeline = engine->timeline; |
483 | GEM_BUG_ON(timeline == request->timeline); | 481 | GEM_BUG_ON(timeline == request->timeline); |
@@ -501,6 +499,8 @@ void __i915_gem_request_submit(struct drm_i915_gem_request *request) | |||
501 | list_move_tail(&request->link, &timeline->requests); | 499 | list_move_tail(&request->link, &timeline->requests); |
502 | spin_unlock(&request->timeline->lock); | 500 | spin_unlock(&request->timeline->lock); |
503 | 501 | ||
502 | trace_i915_gem_request_execute(request); | ||
503 | |||
504 | wake_up_all(&request->execute); | 504 | wake_up_all(&request->execute); |
505 | } | 505 | } |
506 | 506 | ||
diff --git a/drivers/gpu/drm/i915/i915_perf.c b/drivers/gpu/drm/i915/i915_perf.c index 0be50e43507d..f8fe5ffcdcff 100644 --- a/drivers/gpu/drm/i915/i915_perf.c +++ b/drivers/gpu/drm/i915/i915_perf.c | |||
@@ -1303,9 +1303,8 @@ static void i915_oa_stream_destroy(struct i915_perf_stream *stream) | |||
1303 | */ | 1303 | */ |
1304 | mutex_lock(&dev_priv->drm.struct_mutex); | 1304 | mutex_lock(&dev_priv->drm.struct_mutex); |
1305 | dev_priv->perf.oa.exclusive_stream = NULL; | 1305 | dev_priv->perf.oa.exclusive_stream = NULL; |
1306 | mutex_unlock(&dev_priv->drm.struct_mutex); | ||
1307 | |||
1308 | dev_priv->perf.oa.ops.disable_metric_set(dev_priv); | 1306 | dev_priv->perf.oa.ops.disable_metric_set(dev_priv); |
1307 | mutex_unlock(&dev_priv->drm.struct_mutex); | ||
1309 | 1308 | ||
1310 | free_oa_buffer(dev_priv); | 1309 | free_oa_buffer(dev_priv); |
1311 | 1310 | ||
@@ -1756,22 +1755,13 @@ static int gen8_switch_to_updated_kernel_context(struct drm_i915_private *dev_pr | |||
1756 | * Note: it's only the RCS/Render context that has any OA state. | 1755 | * Note: it's only the RCS/Render context that has any OA state. |
1757 | */ | 1756 | */ |
1758 | static int gen8_configure_all_contexts(struct drm_i915_private *dev_priv, | 1757 | static int gen8_configure_all_contexts(struct drm_i915_private *dev_priv, |
1759 | const struct i915_oa_config *oa_config, | 1758 | const struct i915_oa_config *oa_config) |
1760 | bool interruptible) | ||
1761 | { | 1759 | { |
1762 | struct i915_gem_context *ctx; | 1760 | struct i915_gem_context *ctx; |
1763 | int ret; | 1761 | int ret; |
1764 | unsigned int wait_flags = I915_WAIT_LOCKED; | 1762 | unsigned int wait_flags = I915_WAIT_LOCKED; |
1765 | 1763 | ||
1766 | if (interruptible) { | 1764 | lockdep_assert_held(&dev_priv->drm.struct_mutex); |
1767 | ret = i915_mutex_lock_interruptible(&dev_priv->drm); | ||
1768 | if (ret) | ||
1769 | return ret; | ||
1770 | |||
1771 | wait_flags |= I915_WAIT_INTERRUPTIBLE; | ||
1772 | } else { | ||
1773 | mutex_lock(&dev_priv->drm.struct_mutex); | ||
1774 | } | ||
1775 | 1765 | ||
1776 | /* Switch away from any user context. */ | 1766 | /* Switch away from any user context. */ |
1777 | ret = gen8_switch_to_updated_kernel_context(dev_priv, oa_config); | 1767 | ret = gen8_switch_to_updated_kernel_context(dev_priv, oa_config); |
@@ -1819,8 +1809,6 @@ static int gen8_configure_all_contexts(struct drm_i915_private *dev_priv, | |||
1819 | } | 1809 | } |
1820 | 1810 | ||
1821 | out: | 1811 | out: |
1822 | mutex_unlock(&dev_priv->drm.struct_mutex); | ||
1823 | |||
1824 | return ret; | 1812 | return ret; |
1825 | } | 1813 | } |
1826 | 1814 | ||
@@ -1863,7 +1851,7 @@ static int gen8_enable_metric_set(struct drm_i915_private *dev_priv, | |||
1863 | * to make sure all slices/subslices are ON before writing to NOA | 1851 | * to make sure all slices/subslices are ON before writing to NOA |
1864 | * registers. | 1852 | * registers. |
1865 | */ | 1853 | */ |
1866 | ret = gen8_configure_all_contexts(dev_priv, oa_config, true); | 1854 | ret = gen8_configure_all_contexts(dev_priv, oa_config); |
1867 | if (ret) | 1855 | if (ret) |
1868 | return ret; | 1856 | return ret; |
1869 | 1857 | ||
@@ -1878,7 +1866,7 @@ static int gen8_enable_metric_set(struct drm_i915_private *dev_priv, | |||
1878 | static void gen8_disable_metric_set(struct drm_i915_private *dev_priv) | 1866 | static void gen8_disable_metric_set(struct drm_i915_private *dev_priv) |
1879 | { | 1867 | { |
1880 | /* Reset all contexts' slices/subslices configurations. */ | 1868 | /* Reset all contexts' slices/subslices configurations. */ |
1881 | gen8_configure_all_contexts(dev_priv, NULL, false); | 1869 | gen8_configure_all_contexts(dev_priv, NULL); |
1882 | 1870 | ||
1883 | I915_WRITE(GDT_CHICKEN_BITS, (I915_READ(GDT_CHICKEN_BITS) & | 1871 | I915_WRITE(GDT_CHICKEN_BITS, (I915_READ(GDT_CHICKEN_BITS) & |
1884 | ~GT_NOA_ENABLE)); | 1872 | ~GT_NOA_ENABLE)); |
@@ -1888,7 +1876,7 @@ static void gen8_disable_metric_set(struct drm_i915_private *dev_priv) | |||
1888 | static void gen10_disable_metric_set(struct drm_i915_private *dev_priv) | 1876 | static void gen10_disable_metric_set(struct drm_i915_private *dev_priv) |
1889 | { | 1877 | { |
1890 | /* Reset all contexts' slices/subslices configurations. */ | 1878 | /* Reset all contexts' slices/subslices configurations. */ |
1891 | gen8_configure_all_contexts(dev_priv, NULL, false); | 1879 | gen8_configure_all_contexts(dev_priv, NULL); |
1892 | 1880 | ||
1893 | /* Make sure we disable noa to save power. */ | 1881 | /* Make sure we disable noa to save power. */ |
1894 | I915_WRITE(RPM_CONFIG1, | 1882 | I915_WRITE(RPM_CONFIG1, |
@@ -2138,6 +2126,10 @@ static int i915_oa_stream_init(struct i915_perf_stream *stream, | |||
2138 | if (ret) | 2126 | if (ret) |
2139 | goto err_oa_buf_alloc; | 2127 | goto err_oa_buf_alloc; |
2140 | 2128 | ||
2129 | ret = i915_mutex_lock_interruptible(&dev_priv->drm); | ||
2130 | if (ret) | ||
2131 | goto err_lock; | ||
2132 | |||
2141 | ret = dev_priv->perf.oa.ops.enable_metric_set(dev_priv, | 2133 | ret = dev_priv->perf.oa.ops.enable_metric_set(dev_priv, |
2142 | stream->oa_config); | 2134 | stream->oa_config); |
2143 | if (ret) | 2135 | if (ret) |
@@ -2145,23 +2137,17 @@ static int i915_oa_stream_init(struct i915_perf_stream *stream, | |||
2145 | 2137 | ||
2146 | stream->ops = &i915_oa_stream_ops; | 2138 | stream->ops = &i915_oa_stream_ops; |
2147 | 2139 | ||
2148 | /* Lock device for exclusive_stream access late because | ||
2149 | * enable_metric_set() might lock as well on gen8+. | ||
2150 | */ | ||
2151 | ret = i915_mutex_lock_interruptible(&dev_priv->drm); | ||
2152 | if (ret) | ||
2153 | goto err_lock; | ||
2154 | |||
2155 | dev_priv->perf.oa.exclusive_stream = stream; | 2140 | dev_priv->perf.oa.exclusive_stream = stream; |
2156 | 2141 | ||
2157 | mutex_unlock(&dev_priv->drm.struct_mutex); | 2142 | mutex_unlock(&dev_priv->drm.struct_mutex); |
2158 | 2143 | ||
2159 | return 0; | 2144 | return 0; |
2160 | 2145 | ||
2161 | err_lock: | 2146 | err_enable: |
2162 | dev_priv->perf.oa.ops.disable_metric_set(dev_priv); | 2147 | dev_priv->perf.oa.ops.disable_metric_set(dev_priv); |
2148 | mutex_unlock(&dev_priv->drm.struct_mutex); | ||
2163 | 2149 | ||
2164 | err_enable: | 2150 | err_lock: |
2165 | free_oa_buffer(dev_priv); | 2151 | free_oa_buffer(dev_priv); |
2166 | 2152 | ||
2167 | err_oa_buf_alloc: | 2153 | err_oa_buf_alloc: |
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index a2108e35c599..33eb0c5b1d32 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h | |||
@@ -2027,7 +2027,7 @@ enum i915_power_well_id { | |||
2027 | #define _CNL_PORT_TX_DW5_LN0_AE 0x162454 | 2027 | #define _CNL_PORT_TX_DW5_LN0_AE 0x162454 |
2028 | #define _CNL_PORT_TX_DW5_LN0_B 0x162654 | 2028 | #define _CNL_PORT_TX_DW5_LN0_B 0x162654 |
2029 | #define _CNL_PORT_TX_DW5_LN0_C 0x162C54 | 2029 | #define _CNL_PORT_TX_DW5_LN0_C 0x162C54 |
2030 | #define _CNL_PORT_TX_DW5_LN0_D 0x162ED4 | 2030 | #define _CNL_PORT_TX_DW5_LN0_D 0x162E54 |
2031 | #define _CNL_PORT_TX_DW5_LN0_F 0x162854 | 2031 | #define _CNL_PORT_TX_DW5_LN0_F 0x162854 |
2032 | #define CNL_PORT_TX_DW5_GRP(port) _MMIO_PORT6(port, \ | 2032 | #define CNL_PORT_TX_DW5_GRP(port) _MMIO_PORT6(port, \ |
2033 | _CNL_PORT_TX_DW5_GRP_AE, \ | 2033 | _CNL_PORT_TX_DW5_GRP_AE, \ |
@@ -2058,7 +2058,7 @@ enum i915_power_well_id { | |||
2058 | #define _CNL_PORT_TX_DW7_LN0_AE 0x16245C | 2058 | #define _CNL_PORT_TX_DW7_LN0_AE 0x16245C |
2059 | #define _CNL_PORT_TX_DW7_LN0_B 0x16265C | 2059 | #define _CNL_PORT_TX_DW7_LN0_B 0x16265C |
2060 | #define _CNL_PORT_TX_DW7_LN0_C 0x162C5C | 2060 | #define _CNL_PORT_TX_DW7_LN0_C 0x162C5C |
2061 | #define _CNL_PORT_TX_DW7_LN0_D 0x162EDC | 2061 | #define _CNL_PORT_TX_DW7_LN0_D 0x162E5C |
2062 | #define _CNL_PORT_TX_DW7_LN0_F 0x16285C | 2062 | #define _CNL_PORT_TX_DW7_LN0_F 0x16285C |
2063 | #define CNL_PORT_TX_DW7_GRP(port) _MMIO_PORT6(port, \ | 2063 | #define CNL_PORT_TX_DW7_GRP(port) _MMIO_PORT6(port, \ |
2064 | _CNL_PORT_TX_DW7_GRP_AE, \ | 2064 | _CNL_PORT_TX_DW7_GRP_AE, \ |
diff --git a/drivers/gpu/drm/i915/i915_sysfs.c b/drivers/gpu/drm/i915/i915_sysfs.c index b33d2158c234..e5e6f6bb2b05 100644 --- a/drivers/gpu/drm/i915/i915_sysfs.c +++ b/drivers/gpu/drm/i915/i915_sysfs.c | |||
@@ -304,8 +304,9 @@ static ssize_t gt_boost_freq_mhz_store(struct device *kdev, | |||
304 | { | 304 | { |
305 | struct drm_i915_private *dev_priv = kdev_minor_to_i915(kdev); | 305 | struct drm_i915_private *dev_priv = kdev_minor_to_i915(kdev); |
306 | struct intel_rps *rps = &dev_priv->gt_pm.rps; | 306 | struct intel_rps *rps = &dev_priv->gt_pm.rps; |
307 | u32 val; | 307 | bool boost = false; |
308 | ssize_t ret; | 308 | ssize_t ret; |
309 | u32 val; | ||
309 | 310 | ||
310 | ret = kstrtou32(buf, 0, &val); | 311 | ret = kstrtou32(buf, 0, &val); |
311 | if (ret) | 312 | if (ret) |
@@ -317,8 +318,13 @@ static ssize_t gt_boost_freq_mhz_store(struct device *kdev, | |||
317 | return -EINVAL; | 318 | return -EINVAL; |
318 | 319 | ||
319 | mutex_lock(&dev_priv->pcu_lock); | 320 | mutex_lock(&dev_priv->pcu_lock); |
320 | rps->boost_freq = val; | 321 | if (val != rps->boost_freq) { |
322 | rps->boost_freq = val; | ||
323 | boost = atomic_read(&rps->num_waiters); | ||
324 | } | ||
321 | mutex_unlock(&dev_priv->pcu_lock); | 325 | mutex_unlock(&dev_priv->pcu_lock); |
326 | if (boost) | ||
327 | schedule_work(&rps->work); | ||
322 | 328 | ||
323 | return count; | 329 | return count; |
324 | } | 330 | } |
diff --git a/drivers/gpu/drm/i915/intel_audio.c b/drivers/gpu/drm/i915/intel_audio.c index 522d54fecb53..4a01f62a392d 100644 --- a/drivers/gpu/drm/i915/intel_audio.c +++ b/drivers/gpu/drm/i915/intel_audio.c | |||
@@ -779,11 +779,11 @@ static struct intel_encoder *get_saved_enc(struct drm_i915_private *dev_priv, | |||
779 | { | 779 | { |
780 | struct intel_encoder *encoder; | 780 | struct intel_encoder *encoder; |
781 | 781 | ||
782 | if (WARN_ON(pipe >= ARRAY_SIZE(dev_priv->av_enc_map))) | ||
783 | return NULL; | ||
784 | |||
785 | /* MST */ | 782 | /* MST */ |
786 | if (pipe >= 0) { | 783 | if (pipe >= 0) { |
784 | if (WARN_ON(pipe >= ARRAY_SIZE(dev_priv->av_enc_map))) | ||
785 | return NULL; | ||
786 | |||
787 | encoder = dev_priv->av_enc_map[pipe]; | 787 | encoder = dev_priv->av_enc_map[pipe]; |
788 | /* | 788 | /* |
789 | * when bootup, audio driver may not know it is | 789 | * when bootup, audio driver may not know it is |
diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 35c5299feab6..a29868cd30c7 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c | |||
@@ -620,19 +620,15 @@ static int | |||
620 | bxt_power_sequencer_idx(struct intel_dp *intel_dp) | 620 | bxt_power_sequencer_idx(struct intel_dp *intel_dp) |
621 | { | 621 | { |
622 | struct drm_i915_private *dev_priv = to_i915(intel_dp_to_dev(intel_dp)); | 622 | struct drm_i915_private *dev_priv = to_i915(intel_dp_to_dev(intel_dp)); |
623 | int backlight_controller = dev_priv->vbt.backlight.controller; | ||
623 | 624 | ||
624 | lockdep_assert_held(&dev_priv->pps_mutex); | 625 | lockdep_assert_held(&dev_priv->pps_mutex); |
625 | 626 | ||
626 | /* We should never land here with regular DP ports */ | 627 | /* We should never land here with regular DP ports */ |
627 | WARN_ON(!intel_dp_is_edp(intel_dp)); | 628 | WARN_ON(!intel_dp_is_edp(intel_dp)); |
628 | 629 | ||
629 | /* | ||
630 | * TODO: BXT has 2 PPS instances. The correct port->PPS instance | ||
631 | * mapping needs to be retrieved from VBT, for now just hard-code to | ||
632 | * use instance #0 always. | ||
633 | */ | ||
634 | if (!intel_dp->pps_reset) | 630 | if (!intel_dp->pps_reset) |
635 | return 0; | 631 | return backlight_controller; |
636 | 632 | ||
637 | intel_dp->pps_reset = false; | 633 | intel_dp->pps_reset = false; |
638 | 634 | ||
@@ -642,7 +638,7 @@ bxt_power_sequencer_idx(struct intel_dp *intel_dp) | |||
642 | */ | 638 | */ |
643 | intel_dp_init_panel_power_sequencer_registers(intel_dp, false); | 639 | intel_dp_init_panel_power_sequencer_registers(intel_dp, false); |
644 | 640 | ||
645 | return 0; | 641 | return backlight_controller; |
646 | } | 642 | } |
647 | 643 | ||
648 | typedef bool (*vlv_pipe_check)(struct drm_i915_private *dev_priv, | 644 | typedef bool (*vlv_pipe_check)(struct drm_i915_private *dev_priv, |
diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index 7ece2f061b9e..e0fca035ff78 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c | |||
@@ -719,6 +719,8 @@ static void execlists_cancel_requests(struct intel_engine_cs *engine) | |||
719 | struct rb_node *rb; | 719 | struct rb_node *rb; |
720 | unsigned long flags; | 720 | unsigned long flags; |
721 | 721 | ||
722 | GEM_TRACE("%s\n", engine->name); | ||
723 | |||
722 | spin_lock_irqsave(&engine->timeline->lock, flags); | 724 | spin_lock_irqsave(&engine->timeline->lock, flags); |
723 | 725 | ||
724 | /* Cancel the requests on the HW and clear the ELSP tracker. */ | 726 | /* Cancel the requests on the HW and clear the ELSP tracker. */ |
@@ -765,6 +767,9 @@ static void execlists_cancel_requests(struct intel_engine_cs *engine) | |||
765 | */ | 767 | */ |
766 | clear_bit(ENGINE_IRQ_EXECLIST, &engine->irq_posted); | 768 | clear_bit(ENGINE_IRQ_EXECLIST, &engine->irq_posted); |
767 | 769 | ||
770 | /* Mark all CS interrupts as complete */ | ||
771 | execlists->active = 0; | ||
772 | |||
768 | spin_unlock_irqrestore(&engine->timeline->lock, flags); | 773 | spin_unlock_irqrestore(&engine->timeline->lock, flags); |
769 | } | 774 | } |
770 | 775 | ||