]> asedeno.scripts.mit.edu Git - linux.git/commitdiff
Merge airlied/drm-next into drm-misc-next
authorSean Paul <seanpaul@chromium.org>
Wed, 21 Mar 2018 13:40:55 +0000 (09:40 -0400)
committerSean Paul <seanpaul@chromium.org>
Wed, 21 Mar 2018 13:40:55 +0000 (09:40 -0400)
Refresh -misc-next

Signed-off-by: Sean Paul <seanpaul@chromium.org>
1  2 
drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
drivers/gpu/drm/drm_plane.c
drivers/gpu/drm/i915/intel_color.c
drivers/gpu/drm/i915/intel_display.c
drivers/gpu/drm/qxl/qxl_object.c

index ba4335fd4f65d3b18e4f6107935e84f3f6bf1db9,e6709362994a3e331c45c9622e6f94e3dffd6de7..2337d4bfd85c7f34ff6432bcb1eaf518edf5789a
   * - 3.21.0 - Add DRM_AMDGPU_FENCE_TO_HANDLE ioctl
   * - 3.22.0 - Add DRM_AMDGPU_SCHED ioctl
   * - 3.23.0 - Add query for VRAM lost counter
+  * - 3.24.0 - Add high priority compute support for gfx9
+  * - 3.25.0 - Add support for sensor query info (stable pstate sclk/mclk).
   */
  #define KMS_DRIVER_MAJOR      3
- #define KMS_DRIVER_MINOR      23
+ #define KMS_DRIVER_MINOR      25
  #define KMS_DRIVER_PATCHLEVEL 0
  
  int amdgpu_vram_limit = 0;
@@@ -119,7 -121,7 +121,7 @@@ uint amdgpu_pg_mask = 0xffffffff
  uint amdgpu_sdma_phase_quantum = 32;
  char *amdgpu_disable_cu = NULL;
  char *amdgpu_virtual_display = NULL;
- uint amdgpu_pp_feature_mask = 0xffffffff;
+ uint amdgpu_pp_feature_mask = 0xffffbfff;
  int amdgpu_ngg = 0;
  int amdgpu_prim_buf_per_se = 0;
  int amdgpu_pos_buf_per_se = 0;
@@@ -129,6 -131,7 +131,7 @@@ int amdgpu_job_hang_limit = 0
  int amdgpu_lbpw = -1;
  int amdgpu_compute_multipipe = -1;
  int amdgpu_gpu_recovery = -1; /* auto */
+ int amdgpu_emu_mode = 0;
  
  MODULE_PARM_DESC(vramlimit, "Restrict VRAM for testing, in megabytes");
  module_param_named(vramlimit, amdgpu_vram_limit, int, 0600);
@@@ -281,9 -284,12 +284,12 @@@ module_param_named(lbpw, amdgpu_lbpw, i
  MODULE_PARM_DESC(compute_multipipe, "Force compute queues to be spread across pipes (1 = enable, 0 = disable, -1 = auto)");
  module_param_named(compute_multipipe, amdgpu_compute_multipipe, int, 0444);
  
- MODULE_PARM_DESC(gpu_recovery, "Enable GPU recovery mechanism, (1 = enable, 0 = disable, -1 = auto");
+ MODULE_PARM_DESC(gpu_recovery, "Enable GPU recovery mechanism, (1 = enable, 0 = disable, -1 = auto)");
  module_param_named(gpu_recovery, amdgpu_gpu_recovery, int, 0444);
  
+ MODULE_PARM_DESC(emu_mode, "Emulation mode, (1 = enable, 0 = disable)");
+ module_param_named(emu_mode, amdgpu_emu_mode, int, 0444);
  #ifdef CONFIG_DRM_AMDGPU_SI
  
  #if defined(CONFIG_DRM_RADEON) || defined(CONFIG_DRM_RADEON_MODULE)
@@@ -576,6 -582,11 +582,11 @@@ static int amdgpu_pci_probe(struct pci_
        struct drm_device *dev;
        unsigned long flags = ent->driver_data;
        int ret, retry = 0;
+       bool supports_atomic = false;
+       if (!amdgpu_virtual_display &&
+           amdgpu_device_asic_has_dc_support(flags & AMD_ASIC_MASK))
+               supports_atomic = true;
  
        if ((flags & AMD_EXP_HW_SUPPORT) && !amdgpu_exp_hw_support) {
                DRM_INFO("This hardware requires experimental hardware support.\n"
        if (ret)
                return ret;
  
+       /* warn the user if they mix atomic and non-atomic capable GPUs */
+       if ((kms_driver.driver_features & DRIVER_ATOMIC) && !supports_atomic)
+               DRM_ERROR("Mixing atomic and non-atomic capable GPUs!\n");
+       /* support atomic early so the atomic debugfs stuff gets created */
+       if (supports_atomic)
+               kms_driver.driver_features |= DRIVER_ATOMIC;
        dev = drm_dev_alloc(&kms_driver, &pdev->dev);
        if (IS_ERR(dev))
                return PTR_ERR(dev);
@@@ -720,6 -738,7 +738,6 @@@ static int amdgpu_pmops_runtime_suspend
  
        drm_dev->switch_power_state = DRM_SWITCH_POWER_CHANGING;
        drm_kms_helper_poll_disable(drm_dev);
 -      vga_switcheroo_set_dynamic_switch(pdev, VGA_SWITCHEROO_OFF);
  
        ret = amdgpu_device_suspend(drm_dev, false, false);
        pci_save_state(pdev);
@@@ -756,6 -775,7 +774,6 @@@ static int amdgpu_pmops_runtime_resume(
  
        ret = amdgpu_device_resume(drm_dev, false, false);
        drm_kms_helper_poll_enable(drm_dev);
 -      vga_switcheroo_set_dynamic_switch(pdev, VGA_SWITCHEROO_ON);
        drm_dev->switch_power_state = DRM_SWITCH_POWER_ON;
        return 0;
  }
@@@ -833,8 -853,8 +851,8 @@@ amdgpu_get_crtc_scanout_position(struc
                                 ktime_t *stime, ktime_t *etime,
                                 const struct drm_display_mode *mode)
  {
-       return amdgpu_get_crtc_scanoutpos(dev, pipe, 0, vpos, hpos,
-                                         stime, etime, mode);
+       return amdgpu_display_get_crtc_scanoutpos(dev, pipe, 0, vpos, hpos,
+                                                 stime, etime, mode);
  }
  
  static struct drm_driver kms_driver = {
        .disable_vblank = amdgpu_disable_vblank_kms,
        .get_vblank_timestamp = drm_calc_vbltimestamp_from_scanoutpos,
        .get_scanout_position = amdgpu_get_crtc_scanout_position,
-       .irq_preinstall = amdgpu_irq_preinstall,
-       .irq_postinstall = amdgpu_irq_postinstall,
-       .irq_uninstall = amdgpu_irq_uninstall,
        .irq_handler = amdgpu_irq_handler,
        .ioctls = amdgpu_ioctls_kms,
        .gem_free_object_unlocked = amdgpu_gem_object_free,
        .prime_handle_to_fd = drm_gem_prime_handle_to_fd,
        .prime_fd_to_handle = drm_gem_prime_fd_to_handle,
        .gem_prime_export = amdgpu_gem_prime_export,
-       .gem_prime_import = drm_gem_prime_import,
-       .gem_prime_pin = amdgpu_gem_prime_pin,
-       .gem_prime_unpin = amdgpu_gem_prime_unpin,
+       .gem_prime_import = amdgpu_gem_prime_import,
        .gem_prime_res_obj = amdgpu_gem_prime_res_obj,
        .gem_prime_get_sg_table = amdgpu_gem_prime_get_sg_table,
        .gem_prime_import_sg_table = amdgpu_gem_prime_import_sg_table,
index 977a66dfc5f1c1ac8940c5563e18baf82e0a1506,a5d1fc7e8a37bece80bd8682c19b9b4e3eb4461d..6d2a6e428a3eac751877507f258d932e3112f5a8
@@@ -104,7 -104,7 +104,7 @@@ static int create_in_format_blob(struc
        if (IS_ERR(blob))
                return -1;
  
 -      blob_data = (struct drm_format_modifier_blob *)blob->data;
 +      blob_data = blob->data;
        blob_data->version = FORMAT_BLOB_CURRENT;
        blob_data->count_formats = plane->format_count;
        blob_data->formats_offset = sizeof(struct drm_format_modifier_blob);
@@@ -967,7 -967,7 +967,7 @@@ int drm_mode_page_flip_ioctl(struct drm
                if (r)
                        return r;
  
-               current_vblank = drm_crtc_vblank_count(crtc);
+               current_vblank = (u32)drm_crtc_vblank_count(crtc);
  
                switch (page_flip->flags & DRM_MODE_PAGE_FLIP_TARGET) {
                case DRM_MODE_PAGE_FLIP_TARGET_ABSOLUTE:
index 768f1c26080e91f3388434597e189e5f0fcbfd4d,89ab0f70aa2203827933313c0c16d1a828e7b79a..c6a7beabd58d1f636af7f3fb53a16214b4a7e6a1
@@@ -39,7 -39,7 +39,7 @@@
  #define CTM_COEFF_NEGATIVE(coeff)     (((coeff) & CTM_COEFF_SIGN) != 0)
  #define CTM_COEFF_ABS(coeff)          ((coeff) & (CTM_COEFF_SIGN - 1))
  
 -#define LEGACY_LUT_LENGTH             (sizeof(struct drm_color_lut) * 256)
 +#define LEGACY_LUT_LENGTH             256
  
  /* Post offset values for RGB->YCBCR conversion */
  #define POSTOFF_RGB_TO_YUV_HI 0x800
   * of the CTM coefficient and we write the value from bit 3. We also round the
   * value.
   */
- #define I9XX_CSC_COEFF_FP(coeff, fbits)       \
+ #define ILK_CSC_COEFF_FP(coeff, fbits)        \
        (clamp_val(((coeff) >> (32 - (fbits) - 3)) + 4, 0, 0xfff) & 0xff8)
  
- #define I9XX_CSC_COEFF_LIMITED_RANGE  \
-       I9XX_CSC_COEFF_FP(CTM_COEFF_LIMITED_RANGE, 9)
- #define I9XX_CSC_COEFF_1_0            \
-       ((7 << 12) | I9XX_CSC_COEFF_FP(CTM_COEFF_1_0, 8))
+ #define ILK_CSC_COEFF_LIMITED_RANGE   \
+       ILK_CSC_COEFF_FP(CTM_COEFF_LIMITED_RANGE, 9)
+ #define ILK_CSC_COEFF_1_0             \
+       ((7 << 12) | ILK_CSC_COEFF_FP(CTM_COEFF_1_0, 8))
  
  static bool crtc_state_is_legacy_gamma(struct drm_crtc_state *state)
  {
        return !state->degamma_lut &&
                !state->ctm &&
                state->gamma_lut &&
 -              state->gamma_lut->length == LEGACY_LUT_LENGTH;
 +              drm_color_lut_size(state->gamma_lut) == LEGACY_LUT_LENGTH;
  }
  
  /*
   * When using limited range, multiply the matrix given by userspace by
-  * the matrix that we would use for the limited range. We do the
-  * multiplication in U2.30 format.
+  * the matrix that we would use for the limited range.
   */
- static void ctm_mult_by_limited(uint64_t *result, int64_t *input)
+ static u64 *ctm_mult_by_limited(u64 *result, const u64 *input)
  {
        int i;
  
-       for (i = 0; i < 9; i++)
-               result[i] = 0;
+       for (i = 0; i < 9; i++) {
+               u64 user_coeff = input[i];
+               u32 limited_coeff = CTM_COEFF_LIMITED_RANGE;
+               u32 abs_coeff = clamp_val(CTM_COEFF_ABS(user_coeff), 0,
+                                         CTM_COEFF_4_0 - 1) >> 2;
  
-       for (i = 0; i < 3; i++) {
-               int64_t user_coeff = input[i * 3 + i];
-               uint64_t limited_coeff = CTM_COEFF_LIMITED_RANGE >> 2;
-               uint64_t abs_coeff = clamp_val(CTM_COEFF_ABS(user_coeff),
-                                              0,
-                                              CTM_COEFF_4_0 - 1) >> 2;
-               result[i * 3 + i] = (limited_coeff * abs_coeff) >> 27;
-               if (CTM_COEFF_NEGATIVE(user_coeff))
-                       result[i * 3 + i] |= CTM_COEFF_SIGN;
+               /*
+                * By scaling every co-efficient with limited range (16-235)
+                * vs full range (0-255) the final o/p will be scaled down to
+                * fit in the limited range supported by the panel.
+                */
+               result[i] = mul_u32_u32(limited_coeff, abs_coeff) >> 30;
+               result[i] |= user_coeff & CTM_COEFF_SIGN;
        }
+       return result;
  }
  
- static void i9xx_load_ycbcr_conversion_matrix(struct intel_crtc *intel_crtc)
+ static void ilk_load_ycbcr_conversion_matrix(struct intel_crtc *intel_crtc)
  {
        int pipe = intel_crtc->pipe;
        struct drm_i915_private *dev_priv = to_i915(intel_crtc->base.dev);
        I915_WRITE(PIPE_CSC_MODE(pipe), 0);
  }
  
- /* Set up the pipe CSC unit. */
- static void i9xx_load_csc_matrix(struct drm_crtc_state *crtc_state)
+ static void ilk_load_csc_matrix(struct drm_crtc_state *crtc_state)
  {
        struct drm_crtc *crtc = crtc_state->crtc;
        struct drm_i915_private *dev_priv = to_i915(crtc->dev);
        int i, pipe = intel_crtc->pipe;
        uint16_t coeffs[9] = { 0, };
        struct intel_crtc_state *intel_crtc_state = to_intel_crtc_state(crtc_state);
+       bool limited_color_range = false;
+       /*
+        * FIXME if there's a gamma LUT after the CSC, we should
+        * do the range compression using the gamma LUT instead.
+        */
+       if (INTEL_GEN(dev_priv) >= 8 || IS_HASWELL(dev_priv))
+               limited_color_range = intel_crtc_state->limited_color_range;
  
        if (intel_crtc_state->ycbcr420) {
-               i9xx_load_ycbcr_conversion_matrix(intel_crtc);
+               ilk_load_ycbcr_conversion_matrix(intel_crtc);
                return;
        } else if (crtc_state->ctm) {
 -              struct drm_color_ctm *ctm =
 -                      (struct drm_color_ctm *)crtc_state->ctm->data;
 +              struct drm_color_ctm *ctm = crtc_state->ctm->data;
-               uint64_t input[9] = { 0, };
+               const u64 *input;
+               u64 temp[9];
  
-               if (intel_crtc_state->limited_color_range) {
-                       ctm_mult_by_limited(input, ctm->matrix);
-               } else {
-                       for (i = 0; i < ARRAY_SIZE(input); i++)
-                               input[i] = ctm->matrix[i];
-               }
+               if (limited_color_range)
+                       input = ctm_mult_by_limited(temp, ctm->matrix);
+               else
+                       input = ctm->matrix;
  
                /*
                 * Convert fixed point S31.32 input to format supported by the
  
                        if (abs_coeff < CTM_COEFF_0_125)
                                coeffs[i] |= (3 << 12) |
-                                       I9XX_CSC_COEFF_FP(abs_coeff, 12);
+                                       ILK_CSC_COEFF_FP(abs_coeff, 12);
                        else if (abs_coeff < CTM_COEFF_0_25)
                                coeffs[i] |= (2 << 12) |
-                                       I9XX_CSC_COEFF_FP(abs_coeff, 11);
+                                       ILK_CSC_COEFF_FP(abs_coeff, 11);
                        else if (abs_coeff < CTM_COEFF_0_5)
                                coeffs[i] |= (1 << 12) |
-                                       I9XX_CSC_COEFF_FP(abs_coeff, 10);
+                                       ILK_CSC_COEFF_FP(abs_coeff, 10);
                        else if (abs_coeff < CTM_COEFF_1_0)
-                               coeffs[i] |= I9XX_CSC_COEFF_FP(abs_coeff, 9);
+                               coeffs[i] |= ILK_CSC_COEFF_FP(abs_coeff, 9);
                        else if (abs_coeff < CTM_COEFF_2_0)
                                coeffs[i] |= (7 << 12) |
-                                       I9XX_CSC_COEFF_FP(abs_coeff, 8);
+                                       ILK_CSC_COEFF_FP(abs_coeff, 8);
                        else
                                coeffs[i] |= (6 << 12) |
-                                       I9XX_CSC_COEFF_FP(abs_coeff, 7);
+                                       ILK_CSC_COEFF_FP(abs_coeff, 7);
                }
        } else {
                /*
                 * into consideration.
                 */
                for (i = 0; i < 3; i++) {
-                       if (intel_crtc_state->limited_color_range)
+                       if (limited_color_range)
                                coeffs[i * 3 + i] =
-                                       I9XX_CSC_COEFF_LIMITED_RANGE;
+                                       ILK_CSC_COEFF_LIMITED_RANGE;
                        else
-                               coeffs[i * 3 + i] = I9XX_CSC_COEFF_1_0;
+                               coeffs[i * 3 + i] = ILK_CSC_COEFF_1_0;
                }
        }
  
        if (INTEL_GEN(dev_priv) > 6) {
                uint16_t postoff = 0;
  
-               if (intel_crtc_state->limited_color_range)
+               if (limited_color_range)
                        postoff = (16 * (1 << 12) / 255) & 0x1fff;
  
                I915_WRITE(PIPE_CSC_POSTOFF_HI(pipe), postoff);
        } else {
                uint32_t mode = CSC_MODE_YUV_TO_RGB;
  
-               if (intel_crtc_state->limited_color_range)
+               if (limited_color_range)
                        mode |= CSC_BLACK_SCREEN_OFFSET;
  
                I915_WRITE(PIPE_CSC_MODE(pipe), mode);
@@@ -254,7 -262,8 +261,7 @@@ static void cherryview_load_csc_matrix(
        uint32_t mode;
  
        if (state->ctm) {
 -              struct drm_color_ctm *ctm =
 -                      (struct drm_color_ctm *) state->ctm->data;
 +              struct drm_color_ctm *ctm = state->ctm->data;
                uint16_t coeffs[9] = { 0, };
                int i;
  
@@@ -321,7 -330,7 +328,7 @@@ static void i9xx_load_luts_internal(str
        }
  
        if (blob) {
 -              struct drm_color_lut *lut = (struct drm_color_lut *) blob->data;
 +              struct drm_color_lut *lut = blob->data;
                for (i = 0; i < 256; i++) {
                        uint32_t word =
                                (drm_color_lut_extract(lut[i].red, 8) << 16) |
@@@ -391,7 -400,8 +398,7 @@@ static void bdw_load_degamma_lut(struc
                   PAL_PREC_SPLIT_MODE | PAL_PREC_AUTO_INCREMENT);
  
        if (state->degamma_lut) {
 -              struct drm_color_lut *lut =
 -                      (struct drm_color_lut *) state->degamma_lut->data;
 +              struct drm_color_lut *lut = state->degamma_lut->data;
  
                for (i = 0; i < lut_size; i++) {
                        uint32_t word =
@@@ -425,7 -435,8 +432,7 @@@ static void bdw_load_gamma_lut(struct d
                   offset);
  
        if (state->gamma_lut) {
 -              struct drm_color_lut *lut =
 -                      (struct drm_color_lut *) state->gamma_lut->data;
 +              struct drm_color_lut *lut = state->gamma_lut->data;
  
                for (i = 0; i < lut_size; i++) {
                        uint32_t word =
@@@ -557,7 -568,7 +564,7 @@@ static void cherryview_load_luts(struc
        }
  
        if (state->degamma_lut) {
 -              lut = (struct drm_color_lut *) state->degamma_lut->data;
 +              lut = state->degamma_lut->data;
                lut_size = INTEL_INFO(dev_priv)->color.degamma_lut_size;
                for (i = 0; i < lut_size; i++) {
                        /* Write LUT in U0.14 format. */
        }
  
        if (state->gamma_lut) {
 -              lut = (struct drm_color_lut *) state->gamma_lut->data;
 +              lut = state->gamma_lut->data;
                lut_size = INTEL_INFO(dev_priv)->color.gamma_lut_size;
                for (i = 0; i < lut_size; i++) {
                        /* Write LUT in U0.10 format. */
@@@ -612,17 -623,19 +619,17 @@@ int intel_color_check(struct drm_crtc *
        struct drm_i915_private *dev_priv = to_i915(crtc->dev);
        size_t gamma_length, degamma_length;
  
 -      degamma_length = INTEL_INFO(dev_priv)->color.degamma_lut_size *
 -              sizeof(struct drm_color_lut);
 -      gamma_length = INTEL_INFO(dev_priv)->color.gamma_lut_size *
 -              sizeof(struct drm_color_lut);
 +      degamma_length = INTEL_INFO(dev_priv)->color.degamma_lut_size;
 +      gamma_length = INTEL_INFO(dev_priv)->color.gamma_lut_size;
  
        /*
         * We allow both degamma & gamma luts at the right size or
         * NULL.
         */
        if ((!crtc_state->degamma_lut ||
 -           crtc_state->degamma_lut->length == degamma_length) &&
 +           drm_color_lut_size(crtc_state->degamma_lut) == degamma_length) &&
            (!crtc_state->gamma_lut ||
 -           crtc_state->gamma_lut->length == gamma_length))
 +           drm_color_lut_size(crtc_state->gamma_lut) == gamma_length))
                return 0;
  
        /*
@@@ -645,14 -658,14 +652,14 @@@ void intel_color_init(struct drm_crtc *
                dev_priv->display.load_csc_matrix = cherryview_load_csc_matrix;
                dev_priv->display.load_luts = cherryview_load_luts;
        } else if (IS_HASWELL(dev_priv)) {
-               dev_priv->display.load_csc_matrix = i9xx_load_csc_matrix;
+               dev_priv->display.load_csc_matrix = ilk_load_csc_matrix;
                dev_priv->display.load_luts = haswell_load_luts;
        } else if (IS_BROADWELL(dev_priv) || IS_GEN9_BC(dev_priv) ||
                   IS_BROXTON(dev_priv)) {
-               dev_priv->display.load_csc_matrix = i9xx_load_csc_matrix;
+               dev_priv->display.load_csc_matrix = ilk_load_csc_matrix;
                dev_priv->display.load_luts = broadwell_load_luts;
        } else if (IS_GEMINILAKE(dev_priv) || IS_CANNONLAKE(dev_priv)) {
-               dev_priv->display.load_csc_matrix = i9xx_load_csc_matrix;
+               dev_priv->display.load_csc_matrix = ilk_load_csc_matrix;
                dev_priv->display.load_luts = glk_load_luts;
        } else {
                dev_priv->display.load_luts = i9xx_load_luts;
index da8e2d4d84b5446146fecee4aa9d43769937fdcc,331084082545cfb5fbc4351067148f490a66b512..3b48fd2561feccc48b5e0c549ee68e5d25214555
@@@ -558,11 -558,11 +558,11 @@@ int chv_calc_dpll_params(int refclk, st
  }
  
  #define INTELPllInvalid(s)   do { /* DRM_DEBUG(s); */ return false; } while (0)
- /**
+ /*
   * Returns whether the given set of divisors are valid for a given refclk with
   * the given connectors.
   */
  static bool intel_PLL_is_valid(struct drm_i915_private *dev_priv,
                               const struct intel_limit *limit,
                               const struct dpll *clock)
@@@ -2029,12 -2029,12 +2029,12 @@@ static unsigned int intel_cursor_alignm
  
  static unsigned int intel_linear_alignment(const struct drm_i915_private *dev_priv)
  {
-       if (INTEL_INFO(dev_priv)->gen >= 9)
+       if (INTEL_GEN(dev_priv) >= 9)
                return 256 * 1024;
        else if (IS_I965G(dev_priv) || IS_I965GM(dev_priv) ||
                 IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv))
                return 128 * 1024;
-       else if (INTEL_INFO(dev_priv)->gen >= 4)
+       else if (INTEL_GEN(dev_priv) >= 4)
                return 4 * 1024;
        else
                return 0;
@@@ -2067,14 -2067,26 +2067,26 @@@ static unsigned int intel_surf_alignmen
        }
  }
  
+ static bool intel_plane_uses_fence(const struct intel_plane_state *plane_state)
+ {
+       struct intel_plane *plane = to_intel_plane(plane_state->base.plane);
+       struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
+       return INTEL_GEN(dev_priv) < 4 || plane->has_fbc;
+ }
  struct i915_vma *
- intel_pin_and_fence_fb_obj(struct drm_framebuffer *fb, unsigned int rotation)
+ intel_pin_and_fence_fb_obj(struct drm_framebuffer *fb,
+                          unsigned int rotation,
+                          bool uses_fence,
+                          unsigned long *out_flags)
  {
        struct drm_device *dev = fb->dev;
        struct drm_i915_private *dev_priv = to_i915(dev);
        struct drm_i915_gem_object *obj = intel_fb_obj(fb);
        struct i915_ggtt_view view;
        struct i915_vma *vma;
+       unsigned int pinctl;
        u32 alignment;
  
        WARN_ON(!mutex_is_locked(&dev->struct_mutex));
  
        atomic_inc(&dev_priv->gpu_error.pending_fb_pin);
  
-       vma = i915_gem_object_pin_to_display_plane(obj, alignment, &view);
+       pinctl = 0;
+       /* Valleyview is definitely limited to scanning out the first
+        * 512MiB. Lets presume this behaviour was inherited from the
+        * g4x display engine and that all earlier gen are similarly
+        * limited. Testing suggests that it is a little more
+        * complicated than this. For example, Cherryview appears quite
+        * happy to scanout from anywhere within its global aperture.
+        */
+       if (HAS_GMCH_DISPLAY(dev_priv))
+               pinctl |= PIN_MAPPABLE;
+       vma = i915_gem_object_pin_to_display_plane(obj,
+                                                  alignment, &view, pinctl);
        if (IS_ERR(vma))
                goto err;
  
-       if (i915_vma_is_map_and_fenceable(vma)) {
+       if (uses_fence && i915_vma_is_map_and_fenceable(vma)) {
+               int ret;
                /* Install a fence for tiled scan-out. Pre-i965 always needs a
                 * fence, whereas 965+ only requires a fence if using
                 * framebuffer compression.  For simplicity, we always, when
                 * something and try to run the system in a "less than optimal"
                 * mode that matches the user configuration.
                 */
-               i915_vma_pin_fence(vma);
+               ret = i915_vma_pin_fence(vma);
+               if (ret != 0 && INTEL_GEN(dev_priv) < 4) {
+                       i915_gem_object_unpin_from_display_plane(vma);
+                       vma = ERR_PTR(ret);
+                       goto err;
+               }
+               if (ret == 0 && vma->fence)
+                       *out_flags |= PLANE_HAS_FENCE;
        }
  
        i915_vma_get(vma);
        return vma;
  }
  
- void intel_unpin_fb_vma(struct i915_vma *vma)
+ void intel_unpin_fb_vma(struct i915_vma *vma, unsigned long flags)
  {
        lockdep_assert_held(&vma->vm->i915->drm.struct_mutex);
  
-       i915_vma_unpin_fence(vma);
+       if (flags & PLANE_HAS_FENCE)
+               i915_vma_unpin_fence(vma);
        i915_gem_object_unpin_from_display_plane(vma);
        i915_vma_put(vma);
  }
@@@ -2808,7 -2844,10 +2844,10 @@@ intel_find_initial_plane_obj(struct int
  valid_fb:
        mutex_lock(&dev->struct_mutex);
        intel_state->vma =
-               intel_pin_and_fence_fb_obj(fb, primary->state->rotation);
+               intel_pin_and_fence_fb_obj(fb,
+                                          primary->state->rotation,
+                                          intel_plane_uses_fence(intel_state),
+                                          &intel_state->flags);
        mutex_unlock(&dev->struct_mutex);
        if (IS_ERR(intel_state->vma)) {
                DRM_ERROR("failed to pin boot fb on pipe %d: %li\n",
@@@ -3155,7 -3194,7 +3194,7 @@@ static u32 i9xx_plane_ctl(const struct 
        if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv))
                dspcntr |= DISPPLANE_PIPE_CSC_ENABLE;
  
-       if (INTEL_GEN(dev_priv) < 4)
+       if (INTEL_GEN(dev_priv) < 5)
                dspcntr |= DISPPLANE_SEL_PIPE(crtc->pipe);
  
        switch (fb->format->format) {
@@@ -4764,8 -4803,7 +4803,7 @@@ int skl_update_scaler_crtc(struct intel
  
  /**
   * skl_update_scaler_plane - Stages update to scaler state for a given plane.
-  *
-  * @state: crtc's scaler state
+  * @crtc_state: crtc's scaler state
   * @plane_state: atomic plane state to update
   *
   * Return
@@@ -4962,6 -5000,7 +5000,7 @@@ static void intel_crtc_dpms_overlay_dis
  /**
   * intel_post_enable_primary - Perform operations after enabling primary plane
   * @crtc: the CRTC whose primary plane was just enabled
+  * @new_crtc_state: the enabling state
   *
   * Performs potentially sleeping operations that must be done after the primary
   * plane is enabled, such as updating FBC and IPS.  Note that this may be
@@@ -5426,6 -5465,20 +5465,20 @@@ static void glk_pipe_scaler_clock_gatin
        I915_WRITE(CLKGATE_DIS_PSL(pipe), val);
  }
  
+ static void icl_pipe_mbus_enable(struct intel_crtc *crtc)
+ {
+       struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
+       enum pipe pipe = crtc->pipe;
+       uint32_t val;
+       val = MBUS_DBOX_BW_CREDIT(1) | MBUS_DBOX_A_CREDIT(2);
+       /* Program B credit equally to all pipes */
+       val |= MBUS_DBOX_B_CREDIT(24 / INTEL_INFO(dev_priv)->num_pipes);
+       I915_WRITE(PIPE_MBUS_DBOX_CTL(pipe), val);
+ }
  static void haswell_crtc_enable(struct intel_crtc_state *pipe_config,
                                struct drm_atomic_state *old_state)
  {
        if (dev_priv->display.initial_watermarks != NULL)
                dev_priv->display.initial_watermarks(old_intel_state, pipe_config);
  
+       if (INTEL_GEN(dev_priv) >= 11)
+               icl_pipe_mbus_enable(intel_crtc);
        /* XXX: Do the pipe assertions at the right place for BXT DSI. */
        if (!transcoder_is_dsi(cpu_transcoder))
                intel_enable_pipe(pipe_config);
@@@ -6315,7 -6371,7 +6371,7 @@@ static bool intel_crtc_supports_double_
        const struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
  
        /* GDG double wide on either pipe, otherwise pipe A only */
-       return INTEL_INFO(dev_priv)->gen < 4 &&
+       return INTEL_GEN(dev_priv) < 4 &&
                (crtc->pipe == PIPE_A || IS_I915G(dev_priv));
  }
  
@@@ -8202,7 -8258,7 +8258,7 @@@ static void haswell_set_pipemisc(struc
        struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
        struct intel_crtc_state *config = intel_crtc->config;
  
-       if (IS_BROADWELL(dev_priv) || INTEL_INFO(dev_priv)->gen >= 9) {
+       if (IS_BROADWELL(dev_priv) || INTEL_GEN(dev_priv) >= 9) {
                u32 val = 0;
  
                switch (intel_crtc->config->pipe_bpp) {
@@@ -9539,7 -9595,8 +9595,8 @@@ static u32 i9xx_cursor_ctl(const struc
        if (HAS_DDI(dev_priv))
                cntl |= CURSOR_PIPE_CSC_ENABLE;
  
-       cntl |= MCURSOR_PIPE_SELECT(crtc->pipe);
+       if (INTEL_GEN(dev_priv) < 5 && !IS_G4X(dev_priv))
+               cntl |= MCURSOR_PIPE_SELECT(crtc->pipe);
  
        switch (plane_state->base.crtc_w) {
        case 64:
@@@ -10704,6 -10761,7 +10761,7 @@@ static bool check_digital_port_conflict
        struct drm_connector_list_iter conn_iter;
        unsigned int used_ports = 0;
        unsigned int used_mst_ports = 0;
+       bool ret = true;
  
        /*
         * Walk the connector list instead of the encoder
  
                        /* the same port mustn't appear more than once */
                        if (used_ports & port_mask)
-                               return false;
+                               ret = false;
  
                        used_ports |= port_mask;
                        break;
        if (used_ports & used_mst_ports)
                return false;
  
-       return true;
+       return ret;
  }
  
  static void
@@@ -11001,17 -11059,24 +11059,17 @@@ intel_compare_link_m_n(const struct int
  static void __printf(3, 4)
  pipe_config_err(bool adjust, const char *name, const char *format, ...)
  {
 -      char *level;
 -      unsigned int category;
        struct va_format vaf;
        va_list args;
  
 -      if (adjust) {
 -              level = KERN_DEBUG;
 -              category = DRM_UT_KMS;
 -      } else {
 -              level = KERN_ERR;
 -              category = DRM_UT_NONE;
 -      }
 -
        va_start(args, format);
        vaf.fmt = format;
        vaf.va = &args;
  
 -      drm_printk(level, category, "mismatch in %s %pV", name, &vaf);
 +      if (adjust)
 +              drm_dbg(DRM_UT_KMS, "mismatch in %s %pV", name, &vaf);
 +      else
 +              drm_err("mismatch in %s %pV", name, &vaf);
  
        va_end(args);
  }
@@@ -11988,6 -12053,14 +12046,14 @@@ static int intel_atomic_check(struct dr
        int ret, i;
        bool any_ms = false;
  
+       /* Catch I915_MODE_FLAG_INHERITED */
+       for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state,
+                                     crtc_state, i) {
+               if (crtc_state->mode.private_flags !=
+                   old_crtc_state->mode.private_flags)
+                       crtc_state->mode_changed = true;
+       }
        ret = drm_atomic_helper_check_modeset(dev, state);
        if (ret)
                return ret;
                struct intel_crtc_state *pipe_config =
                        to_intel_crtc_state(crtc_state);
  
-               /* Catch I915_MODE_FLAG_INHERITED */
-               if (crtc_state->mode.private_flags != old_crtc_state->mode.private_flags)
-                       crtc_state->mode_changed = true;
                if (!needs_modeset(crtc_state))
                        continue;
  
                        continue;
                }
  
-               /* FIXME: For only active_changed we shouldn't need to do any
-                * state recomputation at all. */
-               ret = drm_atomic_add_affected_connectors(state, crtc);
-               if (ret)
-                       return ret;
                ret = intel_modeset_pipe_config(crtc, pipe_config);
                if (ret) {
                        intel_dump_pipe_config(to_intel_crtc(crtc),
                if (needs_modeset(crtc_state))
                        any_ms = true;
  
-               ret = drm_atomic_add_affected_planes(state, crtc);
-               if (ret)
-                       return ret;
                intel_dump_pipe_config(to_intel_crtc(crtc), pipe_config,
                                       needs_modeset(crtc_state) ?
                                       "[modeset]" : "[fastset]");
@@@ -12070,7 -12128,7 +12121,7 @@@ u32 intel_crtc_get_vblank_counter(struc
        struct drm_device *dev = crtc->base.dev;
  
        if (!dev->max_vblank_count)
-               return drm_crtc_accurate_vblank_count(&crtc->base);
+               return (u32)drm_crtc_accurate_vblank_count(&crtc->base);
  
        return dev->driver->get_vblank_counter(dev, crtc->pipe);
  }
@@@ -12554,23 -12612,23 +12605,23 @@@ struct wait_rps_boost 
        struct wait_queue_entry wait;
  
        struct drm_crtc *crtc;
-       struct drm_i915_gem_request *request;
+       struct i915_request *request;
  };
  
  static int do_rps_boost(struct wait_queue_entry *_wait,
                        unsigned mode, int sync, void *key)
  {
        struct wait_rps_boost *wait = container_of(_wait, typeof(*wait), wait);
-       struct drm_i915_gem_request *rq = wait->request;
+       struct i915_request *rq = wait->request;
  
        /*
         * If we missed the vblank, but the request is already running it
         * is reasonable to assume that it will complete before the next
         * vblank without our intervention, so leave RPS alone.
         */
-       if (!i915_gem_request_started(rq))
+       if (!i915_request_started(rq))
                gen6_rps_boost(rq, NULL);
-       i915_gem_request_put(rq);
+       i915_request_put(rq);
  
        drm_crtc_vblank_put(wait->crtc);
  
@@@ -12608,10 -12666,46 +12659,46 @@@ static void add_rps_boost_after_vblank(
        add_wait_queue(drm_crtc_vblank_waitqueue(crtc), &wait->wait);
  }
  
+ static int intel_plane_pin_fb(struct intel_plane_state *plane_state)
+ {
+       struct intel_plane *plane = to_intel_plane(plane_state->base.plane);
+       struct drm_i915_private *dev_priv = to_i915(plane->base.dev);
+       struct drm_framebuffer *fb = plane_state->base.fb;
+       struct i915_vma *vma;
+       if (plane->id == PLANE_CURSOR &&
+           INTEL_INFO(dev_priv)->cursor_needs_physical) {
+               struct drm_i915_gem_object *obj = intel_fb_obj(fb);
+               const int align = intel_cursor_alignment(dev_priv);
+               return i915_gem_object_attach_phys(obj, align);
+       }
+       vma = intel_pin_and_fence_fb_obj(fb,
+                                        plane_state->base.rotation,
+                                        intel_plane_uses_fence(plane_state),
+                                        &plane_state->flags);
+       if (IS_ERR(vma))
+               return PTR_ERR(vma);
+       plane_state->vma = vma;
+       return 0;
+ }
+ static void intel_plane_unpin_fb(struct intel_plane_state *old_plane_state)
+ {
+       struct i915_vma *vma;
+       vma = fetch_and_zero(&old_plane_state->vma);
+       if (vma)
+               intel_unpin_fb_vma(vma, old_plane_state->flags);
+ }
  /**
   * intel_prepare_plane_fb - Prepare fb for usage on plane
   * @plane: drm plane to prepare for
-  * @fb: framebuffer to prepare for presentation
+  * @new_state: the plane state being prepared
   *
   * Prepares a framebuffer for usage on a display plane.  Generally this
   * involves pinning the underlying object and updating the frontbuffer tracking
@@@ -12682,20 -12776,7 +12769,7 @@@ intel_prepare_plane_fb(struct drm_plan
                return ret;
        }
  
-       if (plane->type == DRM_PLANE_TYPE_CURSOR &&
-           INTEL_INFO(dev_priv)->cursor_needs_physical) {
-               const int align = intel_cursor_alignment(dev_priv);
-               ret = i915_gem_object_attach_phys(obj, align);
-       } else {
-               struct i915_vma *vma;
-               vma = intel_pin_and_fence_fb_obj(fb, new_state->rotation);
-               if (!IS_ERR(vma))
-                       to_intel_plane_state(new_state)->vma = vma;
-               else
-                       ret =  PTR_ERR(vma);
-       }
+       ret = intel_plane_pin_fb(to_intel_plane_state(new_state));
  
        i915_gem_object_wait_priority(obj, 0, I915_PRIORITY_DISPLAY);
  
  /**
   * intel_cleanup_plane_fb - Cleans up an fb after plane use
   * @plane: drm plane to clean up for
-  * @fb: old framebuffer that was on plane
+  * @old_state: the state from the previous modeset
   *
   * Cleans up a framebuffer that has just been removed from a plane.
   *
  intel_cleanup_plane_fb(struct drm_plane *plane,
                       struct drm_plane_state *old_state)
  {
-       struct i915_vma *vma;
+       struct drm_i915_private *dev_priv = to_i915(plane->dev);
  
        /* Should only be called after a successful intel_prepare_plane_fb()! */
-       vma = fetch_and_zero(&to_intel_plane_state(old_state)->vma);
-       if (vma) {
-               mutex_lock(&plane->dev->struct_mutex);
-               intel_unpin_fb_vma(vma);
-               mutex_unlock(&plane->dev->struct_mutex);
-       }
+       mutex_lock(&dev_priv->drm.struct_mutex);
+       intel_plane_unpin_fb(to_intel_plane_state(old_state));
+       mutex_unlock(&dev_priv->drm.struct_mutex);
  }
  
  int
@@@ -13032,7 -13110,6 +13103,6 @@@ intel_legacy_cursor_update(struct drm_p
        struct intel_plane *intel_plane = to_intel_plane(plane);
        struct drm_framebuffer *old_fb;
        struct drm_crtc_state *crtc_state = crtc->state;
-       struct i915_vma *old_vma, *vma;
  
        /*
         * When crtc is inactive or there is a modeset pending,
        if (ret)
                goto out_free;
  
-       if (INTEL_INFO(dev_priv)->cursor_needs_physical) {
-               int align = intel_cursor_alignment(dev_priv);
-               ret = i915_gem_object_attach_phys(intel_fb_obj(fb), align);
-               if (ret) {
-                       DRM_DEBUG_KMS("failed to attach phys object\n");
-                       goto out_unlock;
-               }
-       } else {
-               vma = intel_pin_and_fence_fb_obj(fb, new_plane_state->rotation);
-               if (IS_ERR(vma)) {
-                       DRM_DEBUG_KMS("failed to pin object\n");
-                       ret = PTR_ERR(vma);
-                       goto out_unlock;
-               }
-               to_intel_plane_state(new_plane_state)->vma = vma;
-       }
+       ret = intel_plane_pin_fb(to_intel_plane_state(new_plane_state));
+       if (ret)
+               goto out_unlock;
  
        old_fb = old_plane_state->fb;
  
                intel_plane->disable_plane(intel_plane, to_intel_crtc(crtc));
        }
  
-       old_vma = fetch_and_zero(&to_intel_plane_state(old_plane_state)->vma);
-       if (old_vma)
-               intel_unpin_fb_vma(old_vma);
+       intel_plane_unpin_fb(to_intel_plane_state(old_plane_state));
  
  out_unlock:
        mutex_unlock(&dev_priv->drm.struct_mutex);
@@@ -13159,6 -13218,32 +13211,32 @@@ static const struct drm_plane_funcs int
        .format_mod_supported = intel_cursor_plane_format_mod_supported,
  };
  
+ static bool i9xx_plane_has_fbc(struct drm_i915_private *dev_priv,
+                              enum i9xx_plane_id i9xx_plane)
+ {
+       if (!HAS_FBC(dev_priv))
+               return false;
+       if (IS_BROADWELL(dev_priv) || IS_HASWELL(dev_priv))
+               return i9xx_plane == PLANE_A; /* tied to pipe A */
+       else if (IS_IVYBRIDGE(dev_priv))
+               return i9xx_plane == PLANE_A || i9xx_plane == PLANE_B ||
+                       i9xx_plane == PLANE_C;
+       else if (INTEL_GEN(dev_priv) >= 4)
+               return i9xx_plane == PLANE_A || i9xx_plane == PLANE_B;
+       else
+               return i9xx_plane == PLANE_A;
+ }
+ static bool skl_plane_has_fbc(struct drm_i915_private *dev_priv,
+                             enum pipe pipe, enum plane_id plane_id)
+ {
+       if (!HAS_FBC(dev_priv))
+               return false;
+       return pipe == PIPE_A && plane_id == PLANE_PRIMARY;
+ }
  static struct intel_plane *
  intel_primary_plane_create(struct drm_i915_private *dev_priv, enum pipe pipe)
  {
                primary->i9xx_plane = (enum i9xx_plane_id) pipe;
        primary->id = PLANE_PRIMARY;
        primary->frontbuffer_bit = INTEL_FRONTBUFFER(pipe, primary->id);
+       if (INTEL_GEN(dev_priv) >= 9)
+               primary->has_fbc = skl_plane_has_fbc(dev_priv,
+                                                    primary->pipe,
+                                                    primary->id);
+       else
+               primary->has_fbc = i9xx_plane_has_fbc(dev_priv,
+                                                     primary->i9xx_plane);
+       if (primary->has_fbc) {
+               struct intel_fbc *fbc = &dev_priv->fbc;
+               fbc->possible_framebuffer_bits |= primary->frontbuffer_bit;
+       }
        primary->check_plane = intel_check_primary_plane;
  
        if (INTEL_GEN(dev_priv) >= 9) {
@@@ -13496,8 -13596,8 +13589,8 @@@ enum pipe intel_get_pipe_from_connector
        return to_intel_crtc(connector->base.state->crtc)->pipe;
  }
  
- int intel_get_pipe_from_crtc_id(struct drm_device *dev, void *data,
-                               struct drm_file *file)
+ int intel_get_pipe_from_crtc_id_ioctl(struct drm_device *dev, void *data,
+                                     struct drm_file *file)
  {
        struct drm_i915_get_pipe_from_crtc_id *pipe_from_crtc_id = data;
        struct drm_crtc *drmmode_crtc;
@@@ -13945,7 -14045,7 +14038,7 @@@ static int intel_framebuffer_init(struc
         * gen2/3 display engine uses the fence if present,
         * so the tiling mode must match the fb modifier exactly.
         */
-       if (INTEL_INFO(dev_priv)->gen < 4 &&
+       if (INTEL_GEN(dev_priv) < 4 &&
            tiling != intel_fb_modifier_to_tiling(mode_cmd->modifier[0])) {
                DRM_DEBUG_KMS("tiling_mode must match fb modifier exactly on gen2/3\n");
                goto err;
@@@ -14160,7 -14260,7 +14253,7 @@@ void intel_init_display_hooks(struct dr
  {
        intel_init_cdclk_hooks(dev_priv);
  
-       if (INTEL_INFO(dev_priv)->gen >= 9) {
+       if (INTEL_GEN(dev_priv) >= 9) {
                dev_priv->display.get_pipe_config = haswell_get_pipe_config;
                dev_priv->display.get_initial_plane_config =
                        skylake_get_initial_plane_config;
index e9fb0ab6ceeab660d52bf7a630869ac4b91b34d1,af62824ed4ccb5bee68cc4cd28f8dc139b979097..6a30196e9d6c1a371c0b74071b4369b5c237cc4f
@@@ -109,7 -109,7 +109,7 @@@ int qxl_bo_create(struct qxl_device *qd
        qxl_ttm_placement_from_domain(bo, domain, pinned);
  
        r = ttm_bo_init(&qdev->mman.bdev, &bo->tbo, size, type,
-                       &bo->placement, 0, !kernel, NULL, size,
+                       &bo->placement, 0, !kernel, size,
                        NULL, NULL, &qxl_ttm_bo_destroy);
        if (unlikely(r != 0)) {
                if (r != -ERESTARTSYS)
@@@ -211,13 -211,13 +211,13 @@@ void qxl_bo_unref(struct qxl_bo **bo
        if ((*bo) == NULL)
                return;
  
 -      drm_gem_object_unreference_unlocked(&(*bo)->gem_base);
 +      drm_gem_object_put_unlocked(&(*bo)->gem_base);
        *bo = NULL;
  }
  
  struct qxl_bo *qxl_bo_ref(struct qxl_bo *bo)
  {
 -      drm_gem_object_reference(&bo->gem_base);
 +      drm_gem_object_get(&bo->gem_base);
        return bo;
  }
  
@@@ -318,7 -318,7 +318,7 @@@ void qxl_bo_force_delete(struct qxl_dev
                list_del_init(&bo->list);
                mutex_unlock(&qdev->gem.mutex);
                /* this should unref the ttm bo */
 -              drm_gem_object_unreference_unlocked(&bo->gem_base);
 +              drm_gem_object_put_unlocked(&bo->gem_base);
        }
  }