From: Dave Gordon <david.s.gor...@intel.com>

The GuC firmware uses this for various purposes; it seems to be
required for preemption to work.

For: VIZ-2021
Signed-off-by: Dave Gordon <david.s.gor...@intel.com>
---
 drivers/gpu/drm/i915/i915_guc_reg.h        |  1 +
 drivers/gpu/drm/i915/i915_guc_submission.c | 57 ++++++++++++++++++++++-
 drivers/gpu/drm/i915/intel_guc.h           |  2 +
 drivers/gpu/drm/i915/intel_guc_fwif.h      | 73 +++++++++++++++++++++++++++++-
 drivers/gpu/drm/i915/intel_guc_loader.c    | 14 ++++--
 5 files changed, 141 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/i915/i915_guc_reg.h 
b/drivers/gpu/drm/i915/i915_guc_reg.h
index b51b828..10947de 100644
--- a/drivers/gpu/drm/i915/i915_guc_reg.h
+++ b/drivers/gpu/drm/i915/i915_guc_reg.h
@@ -40,6 +40,7 @@
 #define   GS_MIA_CORE_STATE              (1 << GS_MIA_SHIFT)
 
 #define SOFT_SCRATCH(n)                        (0xc180 + ((n) * 4))
+#define SOFT_SCRATCH_COUNT             16
 
 #define UOS_RSA_SCRATCH(i)             (0xc200 + (i) * 4)
 #define   UOS_RSA_SCRATCH_MAX_COUNT      64
diff --git a/drivers/gpu/drm/i915/i915_guc_submission.c 
b/drivers/gpu/drm/i915/i915_guc_submission.c
index d11bba9..035f126 100644
--- a/drivers/gpu/drm/i915/i915_guc_submission.c
+++ b/drivers/gpu/drm/i915/i915_guc_submission.c
@@ -611,9 +611,10 @@ static int guc_add_workqueue_item(struct i915_guc_client 
*gc,
        wqi->context_desc = (u32)intel_lr_context_descriptor(rq->ctx, rq->ring);
 
        /* The GuC firmware wants the tail index in QWords, not bytes */
+       WARN_ON(rq->ringbuf->tail & 7);
        tail = rq->ringbuf->tail >> 3;
        wqi->ring_tail = tail << WQ_RING_TAIL_SHIFT;
-       wqi->fence_id = 0; /*XXX: what fence to be here */
+       wqi->fence_id = rq->seqno; /*XXX: what fence to be here */
 
        kunmap_atomic(base);
 
@@ -926,6 +927,57 @@ static void guc_create_log(struct intel_guc *guc)
        guc->log_flags = (offset << GUC_LOG_BUF_ADDR_SHIFT) | flags;
 }
 
+static void guc_create_addon(struct intel_guc *guc)
+{
+       struct drm_i915_private *dev_priv = guc_to_i915(guc);
+       struct drm_i915_gem_object *obj;
+       struct guc_ads *ads;
+       struct intel_engine_cs *ring;
+       struct page *page;
+       u32 size, i;
+
+       /* The ads obj includes the struct itself, plus memory for GuC to use
+        * internally to save MMIO registers and states when reset or PM state
+        * change happens. */
+       size = PAGE_ALIGN(sizeof(struct guc_ads)) +
+               PAGE_ALIGN(sizeof(struct guc_mmio_reg_state)) +
+               GUC_MAX_S3_SAVE_SPACE_PAGES * PAGE_SIZE;
+
+       obj = guc->ads_obj;
+       if (!obj) {
+               obj = gem_allocate_guc_obj(dev_priv->dev, size);
+               if (!obj)
+                       return;
+
+               guc->ads_obj = obj;
+       }
+
+       page = i915_gem_object_get_page(obj, 0);
+       ads = kmap_atomic(page);
+       if (!ads) {
+               guc->ads_obj = NULL;
+               gem_release_guc_obj(obj);
+               return;
+       }
+
+       /* TODO: Fill up the register table here */
+       ads->mmio_reg_state_addr = i915_gem_obj_ggtt_offset(obj) +
+                       PAGE_ALIGN(sizeof(struct guc_ads));
+
+       ads->guc_state_saved_buffer = ads->mmio_reg_state_addr +
+                       PAGE_ALIGN(sizeof(struct guc_mmio_reg_state));
+
+       /* TODO: a Goldern Context is needed by GuC to initialize lrc context
+        * after reset. Here we use the render ring default context. */
+       ring = &dev_priv->ring[RCS];
+       ads->golden_context_lrca = ring->status_page.gfx_addr;
+
+       for_each_ring(ring, dev_priv, i)
+               ads->eng_state_size[i] = intel_lr_context_size(ring);
+
+       kunmap_atomic(ads);
+}
+
 /*
  * Set up the memory resources to be shared with the GuC.  At this point,
  * we require just one object that can be mapped through the GGTT.
@@ -953,6 +1005,7 @@ int i915_guc_submission_init(struct drm_device *dev)
        ida_init(&guc->ctx_ids);
 
        guc_create_log(guc);
+       guc_create_addon(guc);
 
        return 0;
 }
@@ -1000,6 +1053,8 @@ void i915_guc_submission_fini(struct drm_device *dev)
        struct drm_i915_private *dev_priv = dev->dev_private;
        struct intel_guc *guc = &dev_priv->guc;
 
+       gem_release_guc_obj(dev_priv->guc.ads_obj);
+       guc->ads_obj = NULL;
        gem_release_guc_obj(dev_priv->guc.log_obj);
        guc->log_obj = NULL;
 
diff --git a/drivers/gpu/drm/i915/intel_guc.h b/drivers/gpu/drm/i915/intel_guc.h
index 0793713..150d596 100644
--- a/drivers/gpu/drm/i915/intel_guc.h
+++ b/drivers/gpu/drm/i915/intel_guc.h
@@ -90,6 +90,8 @@ struct intel_guc {
        uint32_t log_flags;
        struct drm_i915_gem_object *log_obj;
 
+       struct drm_i915_gem_object *ads_obj;
+
        struct drm_i915_gem_object *ctx_pool_obj;
        struct ida ctx_ids;
 
diff --git a/drivers/gpu/drm/i915/intel_guc_fwif.h 
b/drivers/gpu/drm/i915/intel_guc_fwif.h
index 110496a..9f5be1d 100644
--- a/drivers/gpu/drm/i915/intel_guc_fwif.h
+++ b/drivers/gpu/drm/i915/intel_guc_fwif.h
@@ -81,11 +81,14 @@
 #define GUC_CTL_CTXINFO                        0
 #define   GUC_CTL_CTXNUM_IN16_SHIFT    0
 #define   GUC_CTL_BASE_ADDR_SHIFT      12
+
 #define GUC_CTL_ARAT_HIGH              1
 #define GUC_CTL_ARAT_LOW               2
+
 #define GUC_CTL_DEVICE_INFO            3
 #define   GUC_CTL_GTTYPE_SHIFT         0
 #define   GUC_CTL_COREFAMILY_SHIFT     7
+
 #define GUC_CTL_LOG_PARAMS             4
 #define   GUC_LOG_VALID                        (1 << 0)
 #define   GUC_LOG_NOTIFY_ON_HALF_FULL  (1 << 1)
@@ -97,9 +100,12 @@
 #define   GUC_LOG_ISR_PAGES            3
 #define   GUC_LOG_ISR_SHIFT            9
 #define   GUC_LOG_BUF_ADDR_SHIFT       12
+
 #define GUC_CTL_PAGE_FAULT_CONTROL     5
+
 #define GUC_CTL_WA                     6
 #define   GUC_CTL_WA_UK_BY_DRIVER      (1 << 3)
+
 #define GUC_CTL_FEATURE                        7
 #define   GUC_CTL_VCS2_ENABLED         (1 << 0)
 #define   GUC_CTL_KERNEL_SUBMISSIONS   (1 << 1)
@@ -109,6 +115,7 @@
 #define   GUC_CTL_PREEMPTION_LOG       (1 << 5)
 #define   GUC_CTL_ENABLE_SLPC          (1 << 7)
 #define   GUC_CTL_RESET_ON_PREMPT_FAILURE      (1 << 8)
+
 #define GUC_CTL_DEBUG                  8
 #define   GUC_LOG_VERBOSITY_SHIFT      0
 #define   GUC_LOG_VERBOSITY_LOW                (0 << GUC_LOG_VERBOSITY_SHIFT)
@@ -118,9 +125,19 @@
 /* Verbosity range-check limits, without the shift */
 #define          GUC_LOG_VERBOSITY_MIN         0
 #define          GUC_LOG_VERBOSITY_MAX         3
-#define GUC_CTL_RSRVD                  9
+#define          GUC_LOG_VERBOSITY_MASK        0x0000000f
+#define          GUC_LOG_DESTINATION_MASK      (3 << 4)
+#define   GUC_LOG_DISABLED             (1 << 6)
+#define   GUC_PROFILE_ENABLED          (1 << 7)
+#define   GUC_WQ_TRACK_ENABLED         (1 << 8)
+#define   GUC_ADS_ENABLED              (1 << 9)
+#define   GUC_DEBUG_RESERVED           (1 << 10)
+#define   GUC_ADS_ADDR_SHIFT           11
+#define   GUC_ADS_ADDR_MASK            0xfffff800
+
+#define GUC_CTL_RSRVD                  9       // GfxAddressKmSharedData?
 
-#define GUC_CTL_MAX_DWORDS             (GUC_CTL_RSRVD + 1)
+#define GUC_CTL_MAX_DWORDS             (SOFT_SCRATCH_COUNT - 2) /* [1..14] */
 
 /**
  * DOC: GuC Firmware Layout
@@ -304,16 +321,68 @@ struct guc_context_desc {
 #define GUC_POWER_D2           3
 #define GUC_POWER_D3           4
 
+/* GuC Additional Data Struct */
+
+#define GUC_REGSET_FLAGS_NONE          0x0
+#define GUC_REGSET_POWERCYCLE          0x1
+#define GUC_REGSET_MASKED              0x2
+#define GUC_REGSET_ENGINERESET         0x4
+#define GUC_REGSET_SAVE_DEFAULT_VALUE  0x8
+#define GUC_REGSET_SAVE_CURRENT_VALUE  0x10
+
+#define GUC_REGSET_MAX_REGISTERS_PER_SET       20
+
+#define KM_MMIO_WHITE_LIST_MAX_OFFSETS 12
+struct guc_mmio_white_list {
+       u32 mmio_start;
+       u32 offsets[KM_MMIO_WHITE_LIST_MAX_OFFSETS];
+       u32 count;
+} __packed;
+
+struct guc_mmio_reg {
+       u32 offset;
+       u32 value;
+       u32 Flags;
+} __packed;
+
+struct guc_mmio_regset {
+       struct guc_mmio_reg registers[GUC_REGSET_MAX_REGISTERS_PER_SET];
+       u32 values_valid;
+       u32 number_of_registers;
+} __packed;
+
+struct guc_mmio_reg_state {
+       struct guc_mmio_regset global_reg;
+       struct guc_mmio_regset node_reg[I915_NUM_RINGS];
+       /* MMIO registers that are set as non privileged */
+       struct guc_mmio_white_list mmio_white_list[I915_NUM_RINGS];
+} __packed;
+
+#define GUC_MAX_S3_SAVE_SPACE_PAGES    10
+
+/* Additional Data Struct */
+struct guc_ads {
+       u32 mmio_reg_state_addr;
+       u32 guc_state_saved_buffer;
+       u32 golden_context_lrca;
+       u32 scheduler_policies;
+       u32 reserved0[3];
+       u32 eng_state_size[I915_NUM_RINGS];
+       u32 reserved2[4];
+} __packed;
+
 /* This Action will be programmed in C180 - SOFT_SCRATCH_O_REG */
 enum host2guc_action {
        HOST2GUC_ACTION_DEFAULT = 0x0,
        HOST2GUC_ACTION_REQUEST_PREEMPTION = 0x2,
+       HOST2GUC_ACTION_REQUEST_ENGINE_RESET = 0x3,
        HOST2GUC_ACTION_SAMPLE_FORCEWAKE = 0x6,
        HOST2GUC_ACTION_ALLOCATE_DOORBELL = 0x10,
        HOST2GUC_ACTION_DEALLOCATE_DOORBELL = 0x20,
        HOST2GUC_ACTION_ENTER_S_STATE = 0x501,
        HOST2GUC_ACTION_EXIT_S_STATE = 0x502,
        HOST2GUC_ACTION_SLPC_REQUEST = 0x3003,
+       HOST2GUC_ACTION_AUTHENTICATE_HUC = 0x4000,
        HOST2GUC_ACTION_LIMIT
 };
 
diff --git a/drivers/gpu/drm/i915/intel_guc_loader.c 
b/drivers/gpu/drm/i915/intel_guc_loader.c
index 550921f..ce692cf 100644
--- a/drivers/gpu/drm/i915/intel_guc_loader.c
+++ b/drivers/gpu/drm/i915/intel_guc_loader.c
@@ -165,18 +165,26 @@ static void set_guc_init_params(struct drm_i915_private 
*dev_priv)
                        i915.guc_log_level << GUC_LOG_VERBOSITY_SHIFT;
        }
 
+       if (guc->ads_obj) {
+               u32 ads = (u32)i915_gem_obj_ggtt_offset(guc->ads_obj);
+               ads >>= PAGE_SHIFT;
+
+               params[GUC_CTL_DEBUG] |= ads << GUC_ADS_ADDR_SHIFT;
+               params[GUC_CTL_DEBUG] |= GUC_ADS_ENABLED;
+       }
+
        /* If GuC submission is enabled, set up additional parameters here */
        if (i915.enable_guc_submission) {
-               u32 pgs = i915_gem_obj_ggtt_offset(dev_priv->guc.ctx_pool_obj);
                u32 ctx_in_16 = GUC_MAX_GPU_CONTEXTS / 16;
-
+               u32 pgs = (u32)i915_gem_obj_ggtt_offset(guc->ctx_pool_obj);
                pgs >>= PAGE_SHIFT;
+
                params[GUC_CTL_CTXINFO] = (pgs << GUC_CTL_BASE_ADDR_SHIFT) |
                        (ctx_in_16 << GUC_CTL_CTXNUM_IN16_SHIFT);
 
                params[GUC_CTL_FEATURE] |= GUC_CTL_KERNEL_SUBMISSIONS;
 
-               /* Unmask this bit to enable the GuC's internal scheduler */
+               /* Clear this bit to enable the GuC's internal scheduler */
                params[GUC_CTL_FEATURE] &= ~GUC_CTL_DISABLE_SCHEDULER;
        }
 
-- 
1.9.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/intel-gfx

Reply via email to