drm/i915: Cleanup some of the CSB handling
[deliverable/linux.git] / drivers / gpu / drm / i915 / intel_lrc.c
index 88e12bdf79e23388a912fc53939658c9971a406f..7fb2035b71eb1b9c6b8736f47dd2a29c008dbae3 100644 (file)
 #define GEN8_CTX_L3LLC_COHERENT (1<<5)
 #define GEN8_CTX_PRIVILEGE (1<<8)
 
-#define ASSIGN_CTX_PDP(ppgtt, reg_state, n) { \
+#define ASSIGN_CTX_REG(reg_state, pos, reg, val) do { \
+       (reg_state)[(pos)+0] = i915_mmio_reg_offset(reg); \
+       (reg_state)[(pos)+1] = (val); \
+} while (0)
+
+#define ASSIGN_CTX_PDP(ppgtt, reg_state, n) do {               \
        const u64 _addr = i915_page_dir_dma_addr((ppgtt), (n)); \
        reg_state[CTX_PDP ## n ## _UDW+1] = upper_32_bits(_addr); \
        reg_state[CTX_PDP ## n ## _LDW+1] = lower_32_bits(_addr); \
-}
+} while (0)
 
-#define ASSIGN_CTX_PML4(ppgtt, reg_state) { \
+#define ASSIGN_CTX_PML4(ppgtt, reg_state) do { \
        reg_state[CTX_PDP0_UDW + 1] = upper_32_bits(px_dma(&ppgtt->pml4)); \
        reg_state[CTX_PDP0_LDW + 1] = lower_32_bits(px_dma(&ppgtt->pml4)); \
-}
+} while (0)
 
 enum {
        ADVANCED_CONTEXT = 0,
@@ -284,8 +289,8 @@ static bool disable_lite_restore_wa(struct intel_engine_cs *ring)
 {
        struct drm_device *dev = ring->dev;
 
-       return ((IS_SKYLAKE(dev) && INTEL_REVID(dev) <= SKL_REVID_B0) ||
-               (IS_BROXTON(dev) && INTEL_REVID(dev) == BXT_REVID_A0)) &&
+       return (IS_SKL_REVID(dev, 0, SKL_REVID_B0) ||
+               IS_BXT_REVID(dev, 0, BXT_REVID_A1)) &&
               (ring->id == VCS || ring->id == VCS2);
 }
 
@@ -367,7 +372,7 @@ static int execlists_update_context(struct drm_i915_gem_request *rq)
        WARN_ON(!i915_gem_obj_is_pinned(ctx_obj));
        WARN_ON(!i915_gem_obj_is_pinned(rb_obj));
 
-       page = i915_gem_object_get_page(ctx_obj, LRC_STATE_PN);
+       page = i915_gem_object_get_dirty_page(ctx_obj, LRC_STATE_PN);
        reg_state = kmap_atomic(page);
 
        reg_state[CTX_RING_TAIL+1] = rq->tail;
@@ -511,7 +516,7 @@ void intel_lrc_irq_handler(struct intel_engine_cs *ring)
        status_pointer = I915_READ(RING_CONTEXT_STATUS_PTR(ring));
 
        read_pointer = ring->next_context_status_buffer;
-       write_pointer = status_pointer & GEN8_CSB_PTR_MASK;
+       write_pointer = GEN8_CSB_WRITE_PTR(status_pointer);
        if (read_pointer > write_pointer)
                write_pointer += GEN8_CSB_ENTRIES;
 
@@ -533,8 +538,8 @@ void intel_lrc_irq_handler(struct intel_engine_cs *ring)
                                WARN(1, "Preemption without Lite Restore\n");
                }
 
-                if ((status & GEN8_CTX_STATUS_ACTIVE_IDLE) ||
-                    (status & GEN8_CTX_STATUS_ELEMENT_SWITCH)) {
+               if ((status & GEN8_CTX_STATUS_ACTIVE_IDLE) ||
+                   (status & GEN8_CTX_STATUS_ELEMENT_SWITCH)) {
                        if (execlists_check_remove_request(ring, status_id))
                                submit_contexts++;
                }
@@ -554,10 +559,11 @@ void intel_lrc_irq_handler(struct intel_engine_cs *ring)
        WARN(submit_contexts > 2, "More than two context complete events?\n");
        ring->next_context_status_buffer = write_pointer % GEN8_CSB_ENTRIES;
 
+       /* Update the read pointer to the old write pointer. Manual ringbuffer
+        * management ftw </sarcasm> */
        I915_WRITE(RING_CONTEXT_STATUS_PTR(ring),
-                  _MASKED_FIELD(GEN8_CSB_PTR_MASK << 8,
-                                ((u32)ring->next_context_status_buffer &
-                                 GEN8_CSB_PTR_MASK) << 8));
+                  _MASKED_FIELD(GEN8_CSB_READ_PTR_MASK,
+                                ring->next_context_status_buffer << 8));
 }
 
 static int execlists_context_queue(struct drm_i915_gem_request *request)
@@ -665,6 +671,19 @@ int intel_logical_ring_alloc_request_extras(struct drm_i915_gem_request *request
                        return ret;
        }
 
+       if (i915.enable_guc_submission) {
+               /*
+                * Check that the GuC has space for the request before
+                * going any further, as the i915_add_request() call
+                * later on mustn't fail ...
+                */
+               struct intel_guc *guc = &request->i915->guc;
+
+               ret = i915_guc_wq_check_space(guc->execbuf_client);
+               if (ret)
+                       return ret;
+       }
+
        return 0;
 }
 
@@ -921,7 +940,7 @@ int intel_execlists_submission(struct i915_execbuffer_params *params,
 
                intel_logical_ring_emit(ringbuf, MI_NOOP);
                intel_logical_ring_emit(ringbuf, MI_LOAD_REGISTER_IMM(1));
-               intel_logical_ring_emit(ringbuf, INSTPM);
+               intel_logical_ring_emit_reg(ringbuf, INSTPM);
                intel_logical_ring_emit(ringbuf, instp_mask << 16 | instp_mode);
                intel_logical_ring_advance(ringbuf);
 
@@ -1096,7 +1115,7 @@ static int intel_logical_ring_workarounds_emit(struct drm_i915_gem_request *req)
 
        intel_logical_ring_emit(ringbuf, MI_LOAD_REGISTER_IMM(w->count));
        for (i = 0; i < w->count; i++) {
-               intel_logical_ring_emit(ringbuf, w->reg[i].addr);
+               intel_logical_ring_emit_reg(ringbuf, w->reg[i].addr);
                intel_logical_ring_emit(ringbuf, w->reg[i].value);
        }
        intel_logical_ring_emit(ringbuf, MI_NOOP);
@@ -1120,6 +1139,8 @@ static int intel_logical_ring_workarounds_emit(struct drm_i915_gem_request *req)
                batch[__index] = (cmd);                                 \
        } while (0)
 
+#define wa_ctx_emit_reg(batch, index, reg) \
+       wa_ctx_emit((batch), (index), i915_mmio_reg_offset(reg))
 
 /*
  * In this WA we need to set GEN8_L3SQCREG4[21:21] and reset it after
@@ -1149,17 +1170,17 @@ static inline int gen8_emit_flush_coherentl3_wa(struct intel_engine_cs *ring,
         * this batch updates GEN8_L3SQCREG4 with default value we need to
         * set this bit here to retain the WA during flush.
         */
-       if (IS_SKYLAKE(ring->dev) && INTEL_REVID(ring->dev) <= SKL_REVID_E0)
+       if (IS_SKL_REVID(ring->dev, 0, SKL_REVID_E0))
                l3sqc4_flush |= GEN8_LQSC_RO_PERF_DIS;
 
        wa_ctx_emit(batch, index, (MI_STORE_REGISTER_MEM_GEN8 |
                                   MI_SRM_LRM_GLOBAL_GTT));
-       wa_ctx_emit(batch, index, GEN8_L3SQCREG4);
+       wa_ctx_emit_reg(batch, index, GEN8_L3SQCREG4);
        wa_ctx_emit(batch, index, ring->scratch.gtt_offset + 256);
        wa_ctx_emit(batch, index, 0);
 
        wa_ctx_emit(batch, index, MI_LOAD_REGISTER_IMM(1));
-       wa_ctx_emit(batch, index, GEN8_L3SQCREG4);
+       wa_ctx_emit_reg(batch, index, GEN8_L3SQCREG4);
        wa_ctx_emit(batch, index, l3sqc4_flush);
 
        wa_ctx_emit(batch, index, GFX_OP_PIPE_CONTROL(6));
@@ -1172,7 +1193,7 @@ static inline int gen8_emit_flush_coherentl3_wa(struct intel_engine_cs *ring,
 
        wa_ctx_emit(batch, index, (MI_LOAD_REGISTER_MEM_GEN8 |
                                   MI_SRM_LRM_GLOBAL_GTT));
-       wa_ctx_emit(batch, index, GEN8_L3SQCREG4);
+       wa_ctx_emit_reg(batch, index, GEN8_L3SQCREG4);
        wa_ctx_emit(batch, index, ring->scratch.gtt_offset + 256);
        wa_ctx_emit(batch, index, 0);
 
@@ -1314,8 +1335,8 @@ static int gen9_init_indirectctx_bb(struct intel_engine_cs *ring,
        uint32_t index = wa_ctx_start(wa_ctx, *offset, CACHELINE_DWORDS);
 
        /* WaDisableCtxRestoreArbitration:skl,bxt */
-       if ((IS_SKYLAKE(dev) && (INTEL_REVID(dev) <= SKL_REVID_D0)) ||
-           (IS_BROXTON(dev) && (INTEL_REVID(dev) == BXT_REVID_A0)))
+       if (IS_SKL_REVID(dev, 0, SKL_REVID_D0) ||
+           IS_BXT_REVID(dev, 0, BXT_REVID_A1))
                wa_ctx_emit(batch, index, MI_ARB_ON_OFF | MI_ARB_DISABLE);
 
        /* WaFlushCoherentL3CacheLinesAtContextSwitch:skl,bxt */
@@ -1340,18 +1361,18 @@ static int gen9_init_perctx_bb(struct intel_engine_cs *ring,
        uint32_t index = wa_ctx_start(wa_ctx, *offset, CACHELINE_DWORDS);
 
        /* WaSetDisablePixMaskCammingAndRhwoInCommonSliceChicken:skl,bxt */
-       if ((IS_SKYLAKE(dev) && (INTEL_REVID(dev) <= SKL_REVID_B0)) ||
-           (IS_BROXTON(dev) && (INTEL_REVID(dev) == BXT_REVID_A0))) {
+       if (IS_SKL_REVID(dev, 0, SKL_REVID_B0) ||
+           IS_BXT_REVID(dev, 0, BXT_REVID_A1)) {
                wa_ctx_emit(batch, index, MI_LOAD_REGISTER_IMM(1));
-               wa_ctx_emit(batch, index, GEN9_SLICE_COMMON_ECO_CHICKEN0);
+               wa_ctx_emit_reg(batch, index, GEN9_SLICE_COMMON_ECO_CHICKEN0);
                wa_ctx_emit(batch, index,
                            _MASKED_BIT_ENABLE(DISABLE_PIXEL_MASK_CAMMING));
                wa_ctx_emit(batch, index, MI_NOOP);
        }
 
        /* WaDisableCtxRestoreArbitration:skl,bxt */
-       if ((IS_SKYLAKE(dev) && (INTEL_REVID(dev) <= SKL_REVID_D0)) ||
-           (IS_BROXTON(dev) && (INTEL_REVID(dev) == BXT_REVID_A0)))
+       if (IS_SKL_REVID(dev, 0, SKL_REVID_D0) ||
+           IS_BXT_REVID(dev, 0, BXT_REVID_A1))
                wa_ctx_emit(batch, index, MI_ARB_ON_OFF | MI_ARB_ENABLE);
 
        wa_ctx_emit(batch, index, MI_BATCH_BUFFER_END);
@@ -1418,7 +1439,7 @@ static int intel_init_workaround_bb(struct intel_engine_cs *ring)
                return ret;
        }
 
-       page = i915_gem_object_get_page(wa_ctx->obj, 0);
+       page = i915_gem_object_get_dirty_page(wa_ctx->obj, 0);
        batch = kmap_atomic(page);
        offset = 0;
 
@@ -1472,12 +1493,6 @@ static int gen8_init_common_ring(struct intel_engine_cs *ring)
        I915_WRITE_IMR(ring, ~(ring->irq_enable_mask | ring->irq_keep_mask));
        I915_WRITE(RING_HWSTAM(ring->mmio_base), 0xffffffff);
 
-       if (ring->status_page.obj) {
-               I915_WRITE(RING_HWS_PGA(ring->mmio_base),
-                          (u32)ring->status_page.gfx_addr);
-               POSTING_READ(RING_HWS_PGA(ring->mmio_base));
-       }
-
        I915_WRITE(RING_MODE_GEN7(ring),
                   _MASKED_BIT_DISABLE(GFX_REPLAY_MODE) |
                   _MASKED_BIT_ENABLE(GFX_RUN_LIST_ENABLE));
@@ -1492,9 +1507,11 @@ static int gen8_init_common_ring(struct intel_engine_cs *ring)
         *      | Suspend-to-idle (freeze) | Suspend-to-RAM (mem) |
         * BDW  | CSB regs not reset       | CSB regs reset       |
         * CHT  | CSB regs not reset       | CSB regs not reset   |
+        * SKL  |         ?                |         ?            |
+        * BXT  |         ?                |         ?            |
         */
-       next_context_status_buffer_hw = (I915_READ(RING_CONTEXT_STATUS_PTR(ring))
-                                                  & GEN8_CSB_PTR_MASK);
+       next_context_status_buffer_hw =
+               GEN8_CSB_WRITE_PTR(I915_READ(RING_CONTEXT_STATUS_PTR(ring)));
 
        /*
         * When the CSB registers are reset (also after power-up / gpu reset),
@@ -1562,9 +1579,9 @@ static int intel_logical_ring_emit_pdps(struct drm_i915_gem_request *req)
        for (i = GEN8_LEGACY_PDPES - 1; i >= 0; i--) {
                const dma_addr_t pd_daddr = i915_page_dir_dma_addr(ppgtt, i);
 
-               intel_logical_ring_emit(ringbuf, GEN8_RING_PDP_UDW(ring, i));
+               intel_logical_ring_emit_reg(ringbuf, GEN8_RING_PDP_UDW(ring, i));
                intel_logical_ring_emit(ringbuf, upper_32_bits(pd_daddr));
-               intel_logical_ring_emit(ringbuf, GEN8_RING_PDP_LDW(ring, i));
+               intel_logical_ring_emit_reg(ringbuf, GEN8_RING_PDP_LDW(ring, i));
                intel_logical_ring_emit(ringbuf, lower_32_bits(pd_daddr));
        }
 
@@ -1697,7 +1714,7 @@ static int gen8_emit_flush_render(struct drm_i915_gem_request *request,
        struct intel_ringbuffer *ringbuf = request->ringbuf;
        struct intel_engine_cs *ring = ringbuf->ring;
        u32 scratch_addr = ring->scratch.gtt_offset + 2 * CACHELINE_BYTES;
-       bool vf_flush_wa;
+       bool vf_flush_wa = false;
        u32 flags = 0;
        int ret;
 
@@ -1718,14 +1735,14 @@ static int gen8_emit_flush_render(struct drm_i915_gem_request *request,
                flags |= PIPE_CONTROL_STATE_CACHE_INVALIDATE;
                flags |= PIPE_CONTROL_QW_WRITE;
                flags |= PIPE_CONTROL_GLOBAL_GTT_IVB;
-       }
 
-       /*
-        * On GEN9+ Before VF_CACHE_INVALIDATE we need to emit a NULL pipe
-        * control.
-        */
-       vf_flush_wa = INTEL_INFO(ring->dev)->gen >= 9 &&
-                     flags & PIPE_CONTROL_VF_CACHE_INVALIDATE;
+               /*
+                * On GEN9: before VF_CACHE_INVALIDATE we need to emit a NULL
+                * pipe control.
+                */
+               if (IS_GEN9(ring->dev))
+                       vf_flush_wa = true;
+       }
 
        ret = intel_logical_ring_begin(request, vf_flush_wa ? 12 : 6);
        if (ret)
@@ -1893,8 +1910,10 @@ void intel_logical_ring_cleanup(struct intel_engine_cs *ring)
 
        dev_priv = ring->dev->dev_private;
 
-       intel_logical_ring_stop(ring);
-       WARN_ON((I915_READ_MODE(ring) & MODE_IDLE) == 0);
+       if (ring->buffer) {
+               intel_logical_ring_stop(ring);
+               WARN_ON((I915_READ_MODE(ring) & MODE_IDLE) == 0);
+       }
 
        if (ring->cleanup)
                ring->cleanup(ring);
@@ -1908,6 +1927,7 @@ void intel_logical_ring_cleanup(struct intel_engine_cs *ring)
        }
 
        lrc_destroy_wa_ctx_obj(ring);
+       ring->dev = NULL;
 }
 
 static int logical_ring_init(struct drm_device *dev, struct intel_engine_cs *ring)
@@ -1923,17 +1943,18 @@ static int logical_ring_init(struct drm_device *dev, struct intel_engine_cs *rin
        i915_gem_batch_pool_init(dev, &ring->batch_pool);
        init_waitqueue_head(&ring->irq_queue);
 
+       INIT_LIST_HEAD(&ring->buffers);
        INIT_LIST_HEAD(&ring->execlist_queue);
        INIT_LIST_HEAD(&ring->execlist_retired_req_list);
        spin_lock_init(&ring->execlist_lock);
 
        ret = i915_cmd_parser_init_ring(ring);
        if (ret)
-               return ret;
+               goto error;
 
        ret = intel_lr_context_deferred_alloc(ring->default_context, ring);
        if (ret)
-               return ret;
+               goto error;
 
        /* As this is the default context, always pin it */
        ret = intel_lr_context_do_pin(
@@ -1944,9 +1965,13 @@ static int logical_ring_init(struct drm_device *dev, struct intel_engine_cs *rin
                DRM_ERROR(
                        "Failed to pin and map ringbuffer %s: %d\n",
                        ring->name, ret);
-               return ret;
+               goto error;
        }
 
+       return 0;
+
+error:
+       intel_logical_ring_cleanup(ring);
        return ret;
 }
 
@@ -1972,7 +1997,7 @@ static int logical_render_ring_init(struct drm_device *dev)
                ring->init_hw = gen8_init_render_ring;
        ring->init_context = gen8_init_rcs_context;
        ring->cleanup = intel_fini_pipe_control;
-       if (IS_BROXTON(dev) && INTEL_REVID(dev) < BXT_REVID_B0) {
+       if (IS_BXT_REVID(dev, 0, BXT_REVID_A1)) {
                ring->get_seqno = bxt_a_get_seqno;
                ring->set_seqno = bxt_a_set_seqno;
        } else {
@@ -2024,7 +2049,7 @@ static int logical_bsd_ring_init(struct drm_device *dev)
                GT_CONTEXT_SWITCH_INTERRUPT << GEN8_VCS1_IRQ_SHIFT;
 
        ring->init_hw = gen8_init_common_ring;
-       if (IS_BROXTON(dev) && INTEL_REVID(dev) < BXT_REVID_B0) {
+       if (IS_BXT_REVID(dev, 0, BXT_REVID_A1)) {
                ring->get_seqno = bxt_a_get_seqno;
                ring->set_seqno = bxt_a_set_seqno;
        } else {
@@ -2079,7 +2104,7 @@ static int logical_blt_ring_init(struct drm_device *dev)
                GT_CONTEXT_SWITCH_INTERRUPT << GEN8_BCS_IRQ_SHIFT;
 
        ring->init_hw = gen8_init_common_ring;
-       if (IS_BROXTON(dev) && INTEL_REVID(dev) < BXT_REVID_B0) {
+       if (IS_BXT_REVID(dev, 0, BXT_REVID_A1)) {
                ring->get_seqno = bxt_a_get_seqno;
                ring->set_seqno = bxt_a_set_seqno;
        } else {
@@ -2109,7 +2134,7 @@ static int logical_vebox_ring_init(struct drm_device *dev)
                GT_CONTEXT_SWITCH_INTERRUPT << GEN8_VECS_IRQ_SHIFT;
 
        ring->init_hw = gen8_init_common_ring;
-       if (IS_BROXTON(dev) && INTEL_REVID(dev) < BXT_REVID_B0) {
+       if (IS_BXT_REVID(dev, 0, BXT_REVID_A1)) {
                ring->get_seqno = bxt_a_get_seqno;
                ring->set_seqno = bxt_a_set_seqno;
        } else {
@@ -2255,7 +2280,7 @@ populate_lr_context(struct intel_context *ctx, struct drm_i915_gem_object *ctx_o
 
        /* The second page of the context object contains some fields which must
         * be set up prior to the first execution. */
-       page = i915_gem_object_get_page(ctx_obj, LRC_STATE_PN);
+       page = i915_gem_object_get_dirty_page(ctx_obj, LRC_STATE_PN);
        reg_state = kmap_atomic(page);
 
        /* A context is actually a big batch buffer with several MI_LOAD_REGISTER_IMM
@@ -2263,46 +2288,31 @@ populate_lr_context(struct intel_context *ctx, struct drm_i915_gem_object *ctx_o
         * only for the first context restore: on a subsequent save, the GPU will
         * recreate this batchbuffer with new values (including all the missing
         * MI_LOAD_REGISTER_IMM commands that we are not initializing here). */
-       if (ring->id == RCS)
-               reg_state[CTX_LRI_HEADER_0] = MI_LOAD_REGISTER_IMM(14);
-       else
-               reg_state[CTX_LRI_HEADER_0] = MI_LOAD_REGISTER_IMM(11);
-       reg_state[CTX_LRI_HEADER_0] |= MI_LRI_FORCE_POSTED;
-       reg_state[CTX_CONTEXT_CONTROL] = RING_CONTEXT_CONTROL(ring);
-       reg_state[CTX_CONTEXT_CONTROL+1] =
-               _MASKED_BIT_ENABLE(CTX_CTRL_INHIBIT_SYN_CTX_SWITCH |
-                                  CTX_CTRL_ENGINE_CTX_RESTORE_INHIBIT |
-                                  CTX_CTRL_RS_CTX_ENABLE);
-       reg_state[CTX_RING_HEAD] = RING_HEAD(ring->mmio_base);
-       reg_state[CTX_RING_HEAD+1] = 0;
-       reg_state[CTX_RING_TAIL] = RING_TAIL(ring->mmio_base);
-       reg_state[CTX_RING_TAIL+1] = 0;
-       reg_state[CTX_RING_BUFFER_START] = RING_START(ring->mmio_base);
+       reg_state[CTX_LRI_HEADER_0] =
+               MI_LOAD_REGISTER_IMM(ring->id == RCS ? 14 : 11) | MI_LRI_FORCE_POSTED;
+       ASSIGN_CTX_REG(reg_state, CTX_CONTEXT_CONTROL, RING_CONTEXT_CONTROL(ring),
+                      _MASKED_BIT_ENABLE(CTX_CTRL_INHIBIT_SYN_CTX_SWITCH |
+                                         CTX_CTRL_ENGINE_CTX_RESTORE_INHIBIT |
+                                         CTX_CTRL_RS_CTX_ENABLE));
+       ASSIGN_CTX_REG(reg_state, CTX_RING_HEAD, RING_HEAD(ring->mmio_base), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_RING_TAIL, RING_TAIL(ring->mmio_base), 0);
        /* Ring buffer start address is not known until the buffer is pinned.
         * It is written to the context image in execlists_update_context()
         */
-       reg_state[CTX_RING_BUFFER_CONTROL] = RING_CTL(ring->mmio_base);
-       reg_state[CTX_RING_BUFFER_CONTROL+1] =
-                       ((ringbuf->size - PAGE_SIZE) & RING_NR_PAGES) | RING_VALID;
-       reg_state[CTX_BB_HEAD_U] = ring->mmio_base + 0x168;
-       reg_state[CTX_BB_HEAD_U+1] = 0;
-       reg_state[CTX_BB_HEAD_L] = ring->mmio_base + 0x140;
-       reg_state[CTX_BB_HEAD_L+1] = 0;
-       reg_state[CTX_BB_STATE] = ring->mmio_base + 0x110;
-       reg_state[CTX_BB_STATE+1] = (1<<5);
-       reg_state[CTX_SECOND_BB_HEAD_U] = ring->mmio_base + 0x11c;
-       reg_state[CTX_SECOND_BB_HEAD_U+1] = 0;
-       reg_state[CTX_SECOND_BB_HEAD_L] = ring->mmio_base + 0x114;
-       reg_state[CTX_SECOND_BB_HEAD_L+1] = 0;
-       reg_state[CTX_SECOND_BB_STATE] = ring->mmio_base + 0x118;
-       reg_state[CTX_SECOND_BB_STATE+1] = 0;
+       ASSIGN_CTX_REG(reg_state, CTX_RING_BUFFER_START, RING_START(ring->mmio_base), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_RING_BUFFER_CONTROL, RING_CTL(ring->mmio_base),
+                      ((ringbuf->size - PAGE_SIZE) & RING_NR_PAGES) | RING_VALID);
+       ASSIGN_CTX_REG(reg_state, CTX_BB_HEAD_U, RING_BBADDR_UDW(ring->mmio_base), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_BB_HEAD_L, RING_BBADDR(ring->mmio_base), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_BB_STATE, RING_BBSTATE(ring->mmio_base),
+                      RING_BB_PPGTT);
+       ASSIGN_CTX_REG(reg_state, CTX_SECOND_BB_HEAD_U, RING_SBBADDR_UDW(ring->mmio_base), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_SECOND_BB_HEAD_L, RING_SBBADDR(ring->mmio_base), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_SECOND_BB_STATE, RING_SBBSTATE(ring->mmio_base), 0);
        if (ring->id == RCS) {
-               reg_state[CTX_BB_PER_CTX_PTR] = ring->mmio_base + 0x1c0;
-               reg_state[CTX_BB_PER_CTX_PTR+1] = 0;
-               reg_state[CTX_RCS_INDIRECT_CTX] = ring->mmio_base + 0x1c4;
-               reg_state[CTX_RCS_INDIRECT_CTX+1] = 0;
-               reg_state[CTX_RCS_INDIRECT_CTX_OFFSET] = ring->mmio_base + 0x1c8;
-               reg_state[CTX_RCS_INDIRECT_CTX_OFFSET+1] = 0;
+               ASSIGN_CTX_REG(reg_state, CTX_BB_PER_CTX_PTR, RING_BB_PER_CTX_PTR(ring->mmio_base), 0);
+               ASSIGN_CTX_REG(reg_state, CTX_RCS_INDIRECT_CTX, RING_INDIRECT_CTX(ring->mmio_base), 0);
+               ASSIGN_CTX_REG(reg_state, CTX_RCS_INDIRECT_CTX_OFFSET, RING_INDIRECT_CTX_OFFSET(ring->mmio_base), 0);
                if (ring->wa_ctx.obj) {
                        struct i915_ctx_workarounds *wa_ctx = &ring->wa_ctx;
                        uint32_t ggtt_offset = i915_gem_obj_ggtt_offset(wa_ctx->obj);
@@ -2319,18 +2329,17 @@ populate_lr_context(struct intel_context *ctx, struct drm_i915_gem_object *ctx_o
                                0x01;
                }
        }
-       reg_state[CTX_LRI_HEADER_1] = MI_LOAD_REGISTER_IMM(9);
-       reg_state[CTX_LRI_HEADER_1] |= MI_LRI_FORCE_POSTED;
-       reg_state[CTX_CTX_TIMESTAMP] = ring->mmio_base + 0x3a8;
-       reg_state[CTX_CTX_TIMESTAMP+1] = 0;
-       reg_state[CTX_PDP3_UDW] = GEN8_RING_PDP_UDW(ring, 3);
-       reg_state[CTX_PDP3_LDW] = GEN8_RING_PDP_LDW(ring, 3);
-       reg_state[CTX_PDP2_UDW] = GEN8_RING_PDP_UDW(ring, 2);
-       reg_state[CTX_PDP2_LDW] = GEN8_RING_PDP_LDW(ring, 2);
-       reg_state[CTX_PDP1_UDW] = GEN8_RING_PDP_UDW(ring, 1);
-       reg_state[CTX_PDP1_LDW] = GEN8_RING_PDP_LDW(ring, 1);
-       reg_state[CTX_PDP0_UDW] = GEN8_RING_PDP_UDW(ring, 0);
-       reg_state[CTX_PDP0_LDW] = GEN8_RING_PDP_LDW(ring, 0);
+       reg_state[CTX_LRI_HEADER_1] = MI_LOAD_REGISTER_IMM(9) | MI_LRI_FORCE_POSTED;
+       ASSIGN_CTX_REG(reg_state, CTX_CTX_TIMESTAMP, RING_CTX_TIMESTAMP(ring->mmio_base), 0);
+       /* PDP values well be assigned later if needed */
+       ASSIGN_CTX_REG(reg_state, CTX_PDP3_UDW, GEN8_RING_PDP_UDW(ring, 3), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP3_LDW, GEN8_RING_PDP_LDW(ring, 3), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP2_UDW, GEN8_RING_PDP_UDW(ring, 2), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP2_LDW, GEN8_RING_PDP_LDW(ring, 2), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP1_UDW, GEN8_RING_PDP_UDW(ring, 1), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP1_LDW, GEN8_RING_PDP_LDW(ring, 1), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP0_UDW, GEN8_RING_PDP_UDW(ring, 0), 0);
+       ASSIGN_CTX_REG(reg_state, CTX_PDP0_LDW, GEN8_RING_PDP_LDW(ring, 0), 0);
 
        if (USES_FULL_48BIT_PPGTT(ppgtt->base.dev)) {
                /* 64b PPGTT (48bit canonical)
@@ -2352,14 +2361,11 @@ populate_lr_context(struct intel_context *ctx, struct drm_i915_gem_object *ctx_o
 
        if (ring->id == RCS) {
                reg_state[CTX_LRI_HEADER_2] = MI_LOAD_REGISTER_IMM(1);
-               reg_state[CTX_R_PWR_CLK_STATE] = GEN8_R_PWR_CLK_STATE;
-               reg_state[CTX_R_PWR_CLK_STATE+1] = make_rpcs(dev);
+               ASSIGN_CTX_REG(reg_state, CTX_R_PWR_CLK_STATE, GEN8_R_PWR_CLK_STATE,
+                              make_rpcs(dev));
        }
 
        kunmap_atomic(reg_state);
-
-       ctx_obj->dirty = 1;
-       set_page_dirty(page);
        i915_gem_object_unpin_pages(ctx_obj);
 
        return 0;
@@ -2396,7 +2402,21 @@ void intel_lr_context_free(struct intel_context *ctx)
        }
 }
 
-static uint32_t get_lr_context_size(struct intel_engine_cs *ring)
+/**
+ * intel_lr_context_size() - return the size of the context for an engine
+ * @ring: which engine to find the context size for
+ *
+ * Each engine may require a different amount of space for a context image,
+ * so when allocating (or copying) an image, this function can be used to
+ * find the right size for the specific engine.
+ *
+ * Return: size (in bytes) of an engine-specific context image
+ *
+ * Note: this size includes the HWSP, which is part of the context image
+ * in LRC mode, but does not include the "shared data page" used with
+ * GuC submission. The caller should account for this if using the GuC.
+ */
+uint32_t intel_lr_context_size(struct intel_engine_cs *ring)
 {
        int ret = 0;
 
@@ -2464,7 +2484,7 @@ int intel_lr_context_deferred_alloc(struct intel_context *ctx,
        WARN_ON(ctx->legacy_hw_ctx.rcs_state != NULL);
        WARN_ON(ctx->engine[ring->id].state);
 
-       context_size = round_up(get_lr_context_size(ring), 4096);
+       context_size = round_up(intel_lr_context_size(ring), 4096);
 
        /* One extra page as the sharing data between driver and GuC */
        context_size += PAGE_SIZE * LRC_PPHWSP_PN;
@@ -2543,7 +2563,7 @@ void intel_lr_context_reset(struct drm_device *dev,
                        WARN(1, "Failed get_pages for context obj\n");
                        continue;
                }
-               page = i915_gem_object_get_page(ctx_obj, LRC_STATE_PN);
+               page = i915_gem_object_get_dirty_page(ctx_obj, LRC_STATE_PN);
                reg_state = kmap_atomic(page);
 
                reg_state[CTX_RING_HEAD+1] = 0;
This page took 0.033339 seconds and 5 git commands to generate.