[Intel-gfx] [PATCH 07/12] drm/i915/bdw: Support 64 bit PPGTT in lrc mode
akash goel
akash.goels at gmail.com
Tue Mar 3 05:08:34 PST 2015
On Fri, Feb 20, 2015 at 11:16 PM, Michel Thierry
<michel.thierry at intel.com> wrote:
> In 64b (48bit canonical) PPGTT addressing, the PDP0 register contains
> the base address to PML4, while the other PDP registers are ignored.
>
> Also, the addressing mode must be specified in every context descriptor.
>
> Signed-off-by: Michel Thierry <michel.thierry at intel.com>
> ---
> drivers/gpu/drm/i915/intel_lrc.c | 167 ++++++++++++++++++++++++++-------------
> 1 file changed, 114 insertions(+), 53 deletions(-)
>
> diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c
> index f461631..2b6d262 100644
> --- a/drivers/gpu/drm/i915/intel_lrc.c
> +++ b/drivers/gpu/drm/i915/intel_lrc.c
> @@ -255,7 +255,8 @@ u32 intel_execlists_ctx_id(struct drm_i915_gem_object *ctx_obj)
> }
>
> static uint64_t execlists_ctx_descriptor(struct intel_engine_cs *ring,
> - struct drm_i915_gem_object *ctx_obj)
> + struct drm_i915_gem_object *ctx_obj,
> + bool legacy_64bit_ctx)
The 'legacy_64bit_ctx' flag can be derived within the
execlists_ctx_descriptor function also,
through USES_FULL_48BIT_PPGTT macro, as 'dev' pointer is already available.
Doing so, will avoid the modification of function’s prototype and
modification to ‘execlists_elsp_write’.
> {
> struct drm_device *dev = ring->dev;
> uint64_t desc;
> @@ -264,7 +265,10 @@ static uint64_t execlists_ctx_descriptor(struct intel_engine_cs *ring,
> WARN_ON(lrca & 0xFFFFFFFF00000FFFULL);
>
> desc = GEN8_CTX_VALID;
> - desc |= LEGACY_CONTEXT << GEN8_CTX_MODE_SHIFT;
> + if (legacy_64bit_ctx)
> + desc |= LEGACY_64B_CONTEXT << GEN8_CTX_MODE_SHIFT;
> + else
> + desc |= LEGACY_CONTEXT << GEN8_CTX_MODE_SHIFT;
> desc |= GEN8_CTX_L3LLC_COHERENT;
> desc |= GEN8_CTX_PRIVILEGE;
> desc |= lrca;
> @@ -292,16 +296,17 @@ static void execlists_elsp_write(struct intel_engine_cs *ring,
> struct drm_i915_private *dev_priv = dev->dev_private;
> uint64_t temp = 0;
> uint32_t desc[4];
> + bool legacy_64bit_ctx = USES_FULL_48BIT_PPGTT(dev);
>
> /* XXX: You must always write both descriptors in the order below. */
> if (ctx_obj1)
> - temp = execlists_ctx_descriptor(ring, ctx_obj1);
> + temp = execlists_ctx_descriptor(ring, ctx_obj1, legacy_64bit_ctx);
> else
> temp = 0;
> desc[1] = (u32)(temp >> 32);
> desc[0] = (u32)temp;
>
> - temp = execlists_ctx_descriptor(ring, ctx_obj0);
> + temp = execlists_ctx_descriptor(ring, ctx_obj0, legacy_64bit_ctx);
> desc[3] = (u32)(temp >> 32);
> desc[2] = (u32)temp;
>
> @@ -332,37 +337,60 @@ static int execlists_update_context(struct drm_i915_gem_object *ctx_obj,
> reg_state[CTX_RING_TAIL+1] = tail;
> reg_state[CTX_RING_BUFFER_START+1] = i915_gem_obj_ggtt_offset(ring_obj);
>
> - /* True PPGTT with dynamic page allocation: update PDP registers and
> - * point the unallocated PDPs to the scratch page
> - */
> - if (ppgtt) {
> + if (ppgtt && USES_FULL_48BIT_PPGTT(ppgtt->base.dev)) {
> + /* True 64b PPGTT (48bit canonical)
> + * PDP0_DESCRIPTOR contains the base address to PML4 and
> + * other PDP Descriptors are ignored
> + */
> + reg_state[CTX_PDP0_UDW+1] = upper_32_bits(ppgtt->pml4.daddr);
> + reg_state[CTX_PDP0_LDW+1] = lower_32_bits(ppgtt->pml4.daddr);
> + } else if (ppgtt) {
> + /* True 32b PPGTT with dynamic page allocation: update PDP
> + * registers and point the unallocated PDPs to the scratch page
> + */
> if (test_bit(3, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP3_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> - reg_state[CTX_PDP3_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> + reg_state[CTX_PDP3_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> + reg_state[CTX_PDP3_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> } else {
> - reg_state[CTX_PDP3_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP3_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP3_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP3_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> }
> if (test_bit(2, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP2_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> - reg_state[CTX_PDP2_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> + reg_state[CTX_PDP2_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> + reg_state[CTX_PDP2_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> } else {
> - reg_state[CTX_PDP2_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP2_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP2_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP2_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> }
> if (test_bit(1, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP1_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> - reg_state[CTX_PDP1_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> + reg_state[CTX_PDP1_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> + reg_state[CTX_PDP1_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> } else {
> - reg_state[CTX_PDP1_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP1_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP1_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP1_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> }
> if (test_bit(0, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP0_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> - reg_state[CTX_PDP0_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> + reg_state[CTX_PDP0_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> + reg_state[CTX_PDP0_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> } else {
> - reg_state[CTX_PDP0_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP0_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP0_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP0_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> }
> }
>
> @@ -1771,36 +1799,69 @@ populate_lr_context(struct intel_context *ctx, struct drm_i915_gem_object *ctx_o
> reg_state[CTX_PDP0_UDW] = GEN8_RING_PDP_UDW(ring, 0);
> reg_state[CTX_PDP0_LDW] = GEN8_RING_PDP_LDW(ring, 0);
>
> - /* With dynamic page allocation, PDPs may not be allocated at this point,
> - * Point the unallocated PDPs to the scratch page
> - */
> - if (test_bit(3, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP3_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> - reg_state[CTX_PDP3_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> - } else {
> - reg_state[CTX_PDP3_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP3_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> - }
> - if (test_bit(2, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP2_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> - reg_state[CTX_PDP2_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> - } else {
> - reg_state[CTX_PDP2_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP2_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> - }
> - if (test_bit(1, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP1_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> - reg_state[CTX_PDP1_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> - } else {
> - reg_state[CTX_PDP1_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP1_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> - }
> - if (test_bit(0, ppgtt->pdp.used_pdpes)) {
> - reg_state[CTX_PDP0_UDW+1] = upper_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> - reg_state[CTX_PDP0_LDW+1] = lower_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> + if (USES_FULL_48BIT_PPGTT(ppgtt->base.dev)) {
> + /* 64b PPGTT (48bit canonical)
> + * PDP0_DESCRIPTOR contains the base address to PML4 and
> + * other PDP Descriptors are ignored
> + */
> + reg_state[CTX_PDP3_UDW+1] = 0;
> + reg_state[CTX_PDP3_LDW+1] = 0;
> + reg_state[CTX_PDP2_UDW+1] = 0;
> + reg_state[CTX_PDP2_LDW+1] = 0;
> + reg_state[CTX_PDP1_UDW+1] = 0;
> + reg_state[CTX_PDP1_LDW+1] = 0;
> + reg_state[CTX_PDP0_UDW+1] = upper_32_bits(ppgtt->pml4.daddr);
> + reg_state[CTX_PDP0_LDW+1] = lower_32_bits(ppgtt->pml4.daddr);
> } else {
> - reg_state[CTX_PDP0_UDW+1] = upper_32_bits(ppgtt->scratch_pd->daddr);
> - reg_state[CTX_PDP0_LDW+1] = lower_32_bits(ppgtt->scratch_pd->daddr);
> + /* 32b PPGTT
> + * PDP*_DESCRIPTOR contains the base address of space supported.
> + * With dynamic page allocation, PDPs may not be allocated at
> + * this point. Point the unallocated PDPs to the scratch page
> + */
> + if (test_bit(3, ppgtt->pdp.used_pdpes)) {
> + reg_state[CTX_PDP3_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> + reg_state[CTX_PDP3_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[3]->daddr);
> + } else {
> + reg_state[CTX_PDP3_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP3_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> + }
> + if (test_bit(2, ppgtt->pdp.used_pdpes)) {
> + reg_state[CTX_PDP2_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> + reg_state[CTX_PDP2_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[2]->daddr);
> + } else {
> + reg_state[CTX_PDP2_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP2_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> + }
> + if (test_bit(1, ppgtt->pdp.used_pdpes)) {
> + reg_state[CTX_PDP1_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> + reg_state[CTX_PDP1_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[1]->daddr);
> + } else {
> + reg_state[CTX_PDP1_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP1_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> + }
> + if (test_bit(0, ppgtt->pdp.used_pdpes)) {
> + reg_state[CTX_PDP0_UDW+1] =
> + upper_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> + reg_state[CTX_PDP0_LDW+1] =
> + lower_32_bits(ppgtt->pdp.page_directory[0]->daddr);
> + } else {
> + reg_state[CTX_PDP0_UDW+1] =
> + upper_32_bits(ppgtt->scratch_pd->daddr);
> + reg_state[CTX_PDP0_LDW+1] =
> + lower_32_bits(ppgtt->scratch_pd->daddr);
> + }
> }
>
> if (ring->id == RCS) {
> --
> 2.1.1
>
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/intel-gfx
More information about the Intel-gfx
mailing list