]> git.proxmox.com Git - mirror_ubuntu-artful-kernel.git/blobdiff - drivers/gpu/drm/i915/i915_drv.h
drm/i915: Cache last obj->pages location for i915_gem_object_get_page()
[mirror_ubuntu-artful-kernel.git] / drivers / gpu / drm / i915 / i915_drv.h
index e5516a3bb5cb0405a974a7dd1388347ac39e47d1..924676fdb26f1eb3ee8beb32f785a9c2e8d4cfd9 100644 (file)
@@ -56,7 +56,7 @@
 
 #define DRIVER_NAME            "i915"
 #define DRIVER_DESC            "Intel Graphics"
-#define DRIVER_DATE            "20150227"
+#define DRIVER_DATE            "20150327"
 
 #undef WARN_ON
 /* Many gcc seem to no see through this and fall over :( */
@@ -70,6 +70,9 @@
 #define WARN_ON(x) WARN((x), "WARN_ON(" #x ")")
 #endif
 
+#undef WARN_ON_ONCE
+#define WARN_ON_ONCE(x) WARN_ONCE((x), "WARN_ON_ONCE(" #x ")")
+
 #define MISSING_CASE(x) WARN(1, "Missing switch case (%lu) in %s\n", \
                             (long) (x), __func__);
 
@@ -424,6 +427,8 @@ struct drm_i915_error_state {
        u32 forcewake;
        u32 error; /* gen6+ */
        u32 err_int; /* gen7 */
+       u32 fault_data0; /* gen8, gen9 */
+       u32 fault_data1; /* gen8, gen9 */
        u32 done_reg;
        u32 gac_eco;
        u32 gam_ecochk;
@@ -541,7 +546,7 @@ struct drm_i915_display_funcs {
         * Returns true on success, false on failure.
         */
        bool (*find_dpll)(const struct intel_limit *limit,
-                         struct intel_crtc *crtc,
+                         struct intel_crtc_state *crtc_state,
                          int target, int refclk,
                          struct dpll *match_clock,
                          struct dpll *best_clock);
@@ -550,7 +555,7 @@ struct drm_i915_display_funcs {
                                 struct drm_crtc *crtc,
                                 uint32_t sprite_width, uint32_t sprite_height,
                                 int pixel_size, bool enable, bool scaled);
-       void (*modeset_global_resources)(struct drm_device *dev);
+       void (*modeset_global_resources)(struct drm_atomic_state *state);
        /* Returns the active state of the crtc, and if the crtc is active,
         * fills out the pipe-config with the hw state. */
        bool (*get_pipe_config)(struct intel_crtc *,
@@ -876,6 +881,8 @@ struct i915_psr {
        struct delayed_work work;
        unsigned busy_frontbuffer_bits;
        bool link_standby;
+       bool psr2_support;
+       bool aux_frame_sync;
 };
 
 enum intel_pch {
@@ -1022,13 +1029,12 @@ struct intel_gen6_power_mgmt {
        u8 max_freq_softlimit;  /* Max frequency permitted by the driver */
        u8 max_freq;            /* Maximum frequency, RP0 if not overclocking */
        u8 min_freq;            /* AKA RPn. Minimum frequency */
+       u8 idle_freq;           /* Frequency to request when we are idle */
        u8 efficient_freq;      /* AKA RPe. Pre-determined balanced frequency */
        u8 rp1_freq;            /* "less than" RP0 power/freqency */
        u8 rp0_freq;            /* Non-overclocked max frequency. */
        u32 cz_freq;
 
-       u32 ei_interrupt_count;
-
        int last_adj;
        enum { LOW_POWER, BETWEEN, HIGH_POWER } power;
 
@@ -1407,6 +1413,25 @@ struct ilk_wm_values {
        enum intel_ddb_partitioning partitioning;
 };
 
+struct vlv_wm_values {
+       struct {
+               uint16_t primary;
+               uint16_t sprite[2];
+               uint8_t cursor;
+       } pipe[3];
+
+       struct {
+               uint16_t plane;
+               uint8_t cursor;
+       } sr;
+
+       struct {
+               uint8_t cursor;
+               uint8_t sprite[2];
+               uint8_t primary;
+       } ddl[3];
+};
+
 struct skl_ddb_entry {
        uint16_t start, end;    /* in number of blocks, 'end' is exclusive */
 };
@@ -1551,8 +1576,7 @@ struct drm_i915_private {
 
        struct i915_virtual_gpu vgpu;
 
-       struct intel_gmbus gmbus[GMBUS_NUM_PORTS];
-
+       struct intel_gmbus gmbus[GMBUS_NUM_PINS];
 
        /** gmbus_mutex protects against concurrent usage of the single hw gmbus
         * controller on different i2c buses. */
@@ -1769,6 +1793,7 @@ struct drm_i915_private {
                union {
                        struct ilk_wm_values hw;
                        struct skl_wm_values skl_hw;
+                       struct vlv_wm_values vlv;
                };
        } wm;
 
@@ -1790,13 +1815,13 @@ struct drm_i915_private {
 
        /* Abstract the submission mechanism (legacy ringbuffer or execlists) away */
        struct {
-               int (*do_execbuf)(struct drm_device *dev, struct drm_file *file,
-                                 struct intel_engine_cs *ring,
-                                 struct intel_context *ctx,
-                                 struct drm_i915_gem_execbuffer2 *args,
-                                 struct list_head *vmas,
-                                 struct drm_i915_gem_object *batch_obj,
-                                 u64 exec_start, u32 flags);
+               int (*execbuf_submit)(struct drm_device *dev, struct drm_file *file,
+                                     struct intel_engine_cs *ring,
+                                     struct intel_context *ctx,
+                                     struct drm_i915_gem_execbuffer2 *args,
+                                     struct list_head *vmas,
+                                     struct drm_i915_gem_object *batch_obj,
+                                     u64 exec_start, u32 flags);
                int (*init_rings)(struct drm_device *dev);
                void (*cleanup_ring)(struct intel_engine_cs *ring);
                void (*stop_ring)(struct intel_engine_cs *ring);
@@ -1961,6 +1986,10 @@ struct drm_i915_gem_object {
 
        struct sg_table *pages;
        int pages_pin_count;
+       struct get_page {
+               struct scatterlist *sg;
+               int last;
+       } get_page;
 
        /* prime dma-buf support */
        void *dma_buf_vmapping;
@@ -2091,6 +2120,8 @@ struct drm_i915_gem_request {
 
 };
 
+int i915_gem_request_alloc(struct intel_engine_cs *ring,
+                          struct intel_context *ctx);
 void i915_gem_request_free(struct kref *req_ref);
 
 static inline uint32_t
@@ -2118,6 +2149,19 @@ i915_gem_request_unreference(struct drm_i915_gem_request *req)
        kref_put(&req->ref, i915_gem_request_free);
 }
 
+static inline void
+i915_gem_request_unreference__unlocked(struct drm_i915_gem_request *req)
+{
+       struct drm_device *dev;
+
+       if (!req)
+               return;
+
+       dev = req->ring->dev;
+       if (kref_put_mutex(&req->ref, i915_gem_request_free, &dev->struct_mutex))
+               mutex_unlock(&dev->struct_mutex);
+}
+
 static inline void i915_gem_request_assign(struct drm_i915_gem_request **pdst,
                                           struct drm_i915_gem_request *src)
 {
@@ -2405,6 +2449,7 @@ struct drm_i915_cmd_table {
 #define NUM_L3_SLICES(dev) (IS_HSW_GT3(dev) ? 2 : HAS_L3_DPF(dev))
 
 #define GT_FREQUENCY_MULTIPLIER 50
+#define GEN9_FREQ_SCALER 3
 
 #include "i915_trace.h"
 
@@ -2418,7 +2463,6 @@ extern int i915_resume_legacy(struct drm_device *dev);
 struct i915_params {
        int modeset;
        int panel_ignore_lid;
-       unsigned int powersave;
        int semaphores;
        unsigned int lvds_downclock;
        int lvds_channel_mode;
@@ -2438,11 +2482,12 @@ struct i915_params {
        bool enable_hangcheck;
        bool fastboot;
        bool prefault_disable;
+       bool load_detect_test;
        bool reset;
        bool disable_display;
        bool disable_vtd_wa;
        int use_mmio_flip;
-       bool mmio_debug;
+       int mmio_debug;
        bool verbose_state_checks;
        bool nuclear_pageflip;
 };
@@ -2577,12 +2622,6 @@ int i915_gem_get_aperture_ioctl(struct drm_device *dev, void *data,
 int i915_gem_wait_ioctl(struct drm_device *dev, void *data,
                        struct drm_file *file_priv);
 void i915_gem_load(struct drm_device *dev);
-unsigned long i915_gem_shrink(struct drm_i915_private *dev_priv,
-                             long target,
-                             unsigned flags);
-#define I915_SHRINK_PURGEABLE 0x1
-#define I915_SHRINK_UNBOUND 0x2
-#define I915_SHRINK_BOUND 0x4
 void *i915_gem_object_alloc(struct drm_device *dev);
 void i915_gem_object_free(struct drm_i915_gem_object *obj);
 void i915_gem_object_init(struct drm_i915_gem_object *obj,
@@ -2599,20 +2638,16 @@ void i915_gem_vma_destroy(struct i915_vma *vma);
 #define PIN_GLOBAL 0x4
 #define PIN_OFFSET_BIAS 0x8
 #define PIN_OFFSET_MASK (~4095)
-int __must_check i915_gem_object_pin_view(struct drm_i915_gem_object *obj,
-                                         struct i915_address_space *vm,
-                                         uint32_t alignment,
-                                         uint64_t flags,
-                                         const struct i915_ggtt_view *view);
-static inline
-int __must_check i915_gem_object_pin(struct drm_i915_gem_object *obj,
-                                    struct i915_address_space *vm,
-                                    uint32_t alignment,
-                                    uint64_t flags)
-{
-       return i915_gem_object_pin_view(obj, vm, alignment, flags,
-                                               &i915_ggtt_view_normal);
-}
+int __must_check
+i915_gem_object_pin(struct drm_i915_gem_object *obj,
+                   struct i915_address_space *vm,
+                   uint32_t alignment,
+                   uint64_t flags);
+int __must_check
+i915_gem_object_ggtt_pin(struct drm_i915_gem_object *obj,
+                        const struct i915_ggtt_view *view,
+                        uint32_t alignment,
+                        uint64_t flags);
 
 int i915_vma_bind(struct i915_vma *vma, enum i915_cache_level cache_level,
                  u32 flags);
@@ -2625,15 +2660,32 @@ int i915_gem_obj_prepare_shmem_read(struct drm_i915_gem_object *obj,
                                    int *needs_clflush);
 
 int __must_check i915_gem_object_get_pages(struct drm_i915_gem_object *obj);
-static inline struct page *i915_gem_object_get_page(struct drm_i915_gem_object *obj, int n)
+
+static inline int __sg_page_count(struct scatterlist *sg)
+{
+       return sg->length >> PAGE_SHIFT;
+}
+
+static inline struct page *
+i915_gem_object_get_page(struct drm_i915_gem_object *obj, int n)
 {
-       struct sg_page_iter sg_iter;
+       if (WARN_ON(n >= obj->base.size >> PAGE_SHIFT))
+               return NULL;
+
+       if (n < obj->get_page.last) {
+               obj->get_page.sg = obj->pages->sgl;
+               obj->get_page.last = 0;
+       }
 
-       for_each_sg_page(obj->pages->sgl, &sg_iter, obj->pages->nents, n)
-               return sg_page_iter_page(&sg_iter);
+       while (obj->get_page.last + __sg_page_count(obj->get_page.sg) <= n) {
+               obj->get_page.last += __sg_page_count(obj->get_page.sg++);
+               if (unlikely(sg_is_chain(obj->get_page.sg)))
+                       obj->get_page.sg = sg_chain_ptr(obj->get_page.sg);
+       }
 
-       return NULL;
+       return nth_page(sg_page(obj->get_page.sg), n - obj->get_page.last);
 }
+
 static inline void i915_gem_object_pin_pages(struct drm_i915_gem_object *obj)
 {
        BUG_ON(obj->pages == NULL);
@@ -2752,8 +2804,10 @@ i915_gem_object_set_to_cpu_domain(struct drm_i915_gem_object *obj, bool write);
 int __must_check
 i915_gem_object_pin_to_display_plane(struct drm_i915_gem_object *obj,
                                     u32 alignment,
-                                    struct intel_engine_cs *pipelined);
-void i915_gem_object_unpin_from_display_plane(struct drm_i915_gem_object *obj);
+                                    struct intel_engine_cs *pipelined,
+                                    const struct i915_ggtt_view *view);
+void i915_gem_object_unpin_from_display_plane(struct drm_i915_gem_object *obj,
+                                             const struct i915_ggtt_view *view);
 int i915_gem_object_attach_phys(struct drm_i915_gem_object *obj,
                                int align);
 int i915_gem_open(struct drm_device *dev, struct drm_file *file);
@@ -2776,60 +2830,46 @@ struct dma_buf *i915_gem_prime_export(struct drm_device *dev,
 
 void i915_gem_restore_fences(struct drm_device *dev);
 
-unsigned long i915_gem_obj_offset_view(struct drm_i915_gem_object *o,
-                                      struct i915_address_space *vm,
-                                      enum i915_ggtt_view_type view);
-static inline
-unsigned long i915_gem_obj_offset(struct drm_i915_gem_object *o,
-                                 struct i915_address_space *vm)
+unsigned long
+i915_gem_obj_ggtt_offset_view(struct drm_i915_gem_object *o,
+                             const struct i915_ggtt_view *view);
+unsigned long
+i915_gem_obj_offset(struct drm_i915_gem_object *o,
+                   struct i915_address_space *vm);
+static inline unsigned long
+i915_gem_obj_ggtt_offset(struct drm_i915_gem_object *o)
 {
-       return i915_gem_obj_offset_view(o, vm, I915_GGTT_VIEW_NORMAL);
+       return i915_gem_obj_ggtt_offset_view(o, &i915_ggtt_view_normal);
 }
+
 bool i915_gem_obj_bound_any(struct drm_i915_gem_object *o);
-bool i915_gem_obj_bound_view(struct drm_i915_gem_object *o,
-                            struct i915_address_space *vm,
-                            enum i915_ggtt_view_type view);
-static inline
+bool i915_gem_obj_ggtt_bound_view(struct drm_i915_gem_object *o,
+                                 const struct i915_ggtt_view *view);
 bool i915_gem_obj_bound(struct drm_i915_gem_object *o,
-                       struct i915_address_space *vm)
-{
-       return i915_gem_obj_bound_view(o, vm, I915_GGTT_VIEW_NORMAL);
-}
+                       struct i915_address_space *vm);
 
 unsigned long i915_gem_obj_size(struct drm_i915_gem_object *o,
                                struct i915_address_space *vm);
-struct i915_vma *i915_gem_obj_to_vma_view(struct drm_i915_gem_object *obj,
-                                         struct i915_address_space *vm,
-                                         const struct i915_ggtt_view *view);
-static inline
-struct i915_vma *i915_gem_obj_to_vma(struct drm_i915_gem_object *obj,
-                                    struct i915_address_space *vm)
-{
-       return i915_gem_obj_to_vma_view(obj, vm, &i915_ggtt_view_normal);
-}
-
 struct i915_vma *
-i915_gem_obj_lookup_or_create_vma_view(struct drm_i915_gem_object *obj,
-                                      struct i915_address_space *vm,
-                                      const struct i915_ggtt_view *view);
+i915_gem_obj_to_vma(struct drm_i915_gem_object *obj,
+                   struct i915_address_space *vm);
+struct i915_vma *
+i915_gem_obj_to_ggtt_view(struct drm_i915_gem_object *obj,
+                         const struct i915_ggtt_view *view);
 
-static inline
 struct i915_vma *
 i915_gem_obj_lookup_or_create_vma(struct drm_i915_gem_object *obj,
-                                 struct i915_address_space *vm)
-{
-       return i915_gem_obj_lookup_or_create_vma_view(obj, vm,
-                                               &i915_ggtt_view_normal);
-}
+                                 struct i915_address_space *vm);
+struct i915_vma *
+i915_gem_obj_lookup_or_create_ggtt_vma(struct drm_i915_gem_object *obj,
+                                      const struct i915_ggtt_view *view);
 
-struct i915_vma *i915_gem_obj_to_ggtt(struct drm_i915_gem_object *obj);
-static inline bool i915_gem_obj_is_pinned(struct drm_i915_gem_object *obj) {
-       struct i915_vma *vma;
-       list_for_each_entry(vma, &obj->vma_list, vma_link)
-               if (vma->pin_count > 0)
-                       return true;
-       return false;
+static inline struct i915_vma *
+i915_gem_obj_to_ggtt(struct drm_i915_gem_object *obj)
+{
+       return i915_gem_obj_to_ggtt_view(obj, &i915_ggtt_view_normal);
 }
+bool i915_gem_obj_is_pinned(struct drm_i915_gem_object *obj);
 
 /* Some GGTT VM helpers */
 #define i915_obj_to_ggtt(obj) \
@@ -2852,13 +2892,7 @@ i915_vm_to_ppgtt(struct i915_address_space *vm)
 
 static inline bool i915_gem_obj_ggtt_bound(struct drm_i915_gem_object *obj)
 {
-       return i915_gem_obj_bound(obj, i915_obj_to_ggtt(obj));
-}
-
-static inline unsigned long
-i915_gem_obj_ggtt_offset(struct drm_i915_gem_object *obj)
-{
-       return i915_gem_obj_offset(obj, i915_obj_to_ggtt(obj));
+       return i915_gem_obj_ggtt_bound_view(obj, &i915_ggtt_view_normal);
 }
 
 static inline unsigned long
@@ -2882,7 +2916,13 @@ i915_gem_object_ggtt_unbind(struct drm_i915_gem_object *obj)
        return i915_vma_unbind(i915_gem_obj_to_ggtt(obj));
 }
 
-void i915_gem_object_ggtt_unpin(struct drm_i915_gem_object *obj);
+void i915_gem_object_ggtt_unpin_view(struct drm_i915_gem_object *obj,
+                                    const struct i915_ggtt_view *view);
+static inline void
+i915_gem_object_ggtt_unpin(struct drm_i915_gem_object *obj)
+{
+       i915_gem_object_ggtt_unpin_view(obj, &i915_ggtt_view_normal);
+}
 
 /* i915_gem_context.c */
 int __must_check i915_gem_context_init(struct drm_device *dev);
@@ -2954,6 +2994,17 @@ i915_gem_object_create_stolen_for_preallocated(struct drm_device *dev,
                                               u32 gtt_offset,
                                               u32 size);
 
+/* i915_gem_shrinker.c */
+unsigned long i915_gem_shrink(struct drm_i915_private *dev_priv,
+                             long target,
+                             unsigned flags);
+#define I915_SHRINK_PURGEABLE 0x1
+#define I915_SHRINK_UNBOUND 0x2
+#define I915_SHRINK_BOUND 0x4
+unsigned long i915_gem_shrink_all(struct drm_i915_private *dev_priv);
+void i915_gem_shrinker_init(struct drm_i915_private *dev_priv);
+
+
 /* i915_gem_tiling.c */
 static inline bool i915_gem_object_needs_bit17_swizzle(struct drm_i915_gem_object *obj)
 {
@@ -2977,6 +3028,7 @@ int i915_verify_lists(struct drm_device *dev);
 /* i915_debugfs.c */
 int i915_debugfs_init(struct drm_minor *minor);
 void i915_debugfs_cleanup(struct drm_minor *minor);
+int i915_debugfs_connector_add(struct drm_connector *connector);
 #ifdef CONFIG_DEBUG_FS
 void intel_display_crc_init(struct drm_device *dev);
 #else
@@ -3036,13 +3088,11 @@ void i915_teardown_sysfs(struct drm_device *dev_priv);
 /* intel_i2c.c */
 extern int intel_setup_gmbus(struct drm_device *dev);
 extern void intel_teardown_gmbus(struct drm_device *dev);
-static inline bool intel_gmbus_is_port_valid(unsigned port)
-{
-       return (port >= GMBUS_PORT_SSC && port <= GMBUS_PORT_DPD);
-}
+extern bool intel_gmbus_is_valid_pin(struct drm_i915_private *dev_priv,
+                                    unsigned int pin);
 
-extern struct i2c_adapter *intel_gmbus_get_adapter(
-               struct drm_i915_private *dev_priv, unsigned port);
+extern struct i2c_adapter *
+intel_gmbus_get_adapter(struct drm_i915_private *dev_priv, unsigned int pin);
 extern void intel_gmbus_set_speed(struct i2c_adapter *adapter, int speed);
 extern void intel_gmbus_force_bit(struct i2c_adapter *adapter, bool force_bit);
 static inline bool intel_gmbus_is_forced_bit(struct i2c_adapter *adapter)