From: Niu Bing <bing....@intel.com>

GVT-g supports an indirect display mode by mapping guest display framebuffer
into host graphics memory space as a GEM object, so that host windows system
/ GL can easily manipulate it like a common GEM object.

For example, use an EGL extension to wrap a guest framebuffer GEM object into
an EGL image, or just use i915 MMAP_GTT ioctl to map it into host aperture,
so that userspace application can easily use them.

To create this special GEM object, GVT-g has to know the surface format of
guest framebuffer, like RGB/NV12, stride, tiling format. vGPU framebuffer
format decoder will extract these information from guest virtual plane
registers and expose them to GVT GEM object logics.

Signed-off-by: Bing Niu <bing....@intel.com>
---
 drivers/gpu/drm/i915/gvt/Makefile     |   3 +-
 drivers/gpu/drm/i915/gvt/fb_decoder.c | 295 ++++++++++++++++++++++++-
 drivers/gpu/drm/i915/gvt/gvt.h        |   1 +
 drivers/gpu/drm/i915/gvt/reg.h        | 404 ++++++++++++++++++++++++++++++++++
 4 files changed, 700 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/i915/gvt/Makefile 
b/drivers/gpu/drm/i915/gvt/Makefile
index 8f59bbc..b0a3a1a 100644
--- a/drivers/gpu/drm/i915/gvt/Makefile
+++ b/drivers/gpu/drm/i915/gvt/Makefile
@@ -1,5 +1,6 @@
 GVT_SOURCE := gvt.o params.o aperture_gm.o mmio.o handlers.o instance.o \
-               trace_points.o interrupt.o gtt.o cfg_space.o opregion.o 
utility.o fb_decoder.o
+               trace_points.o interrupt.o gtt.o cfg_space.o opregion.o 
utility.o \
+               fb_decoder.o
 
 ccflags-y                      += -I$(src) -I$(src)/.. -Wall -Werror 
-Wno-unused-function
 i915_gvt-y                     := $(GVT_SOURCE)
diff --git a/drivers/gpu/drm/i915/gvt/fb_decoder.c 
b/drivers/gpu/drm/i915/gvt/fb_decoder.c
index a219819..dfb8cb3 100644
--- a/drivers/gpu/drm/i915/gvt/fb_decoder.c
+++ b/drivers/gpu/drm/i915/gvt/fb_decoder.c
@@ -23,12 +23,303 @@
 
 #include "gvt.h"
 
-int gvt_decode_fb_format(struct pgt_device *pdev, int vmid, struct 
gvt_fb_format *fb)
+#define FORMAT_NUM     16
+struct pixel_format {
+       int     drm_format;     /* Pixel format in DRM definition */
+       int     bpp;            /* Bits per pixel, 0 indicates invalid */
+       char    *desc;          /* The description */
+};
+
+/* non-supported format has bpp default to 0 */
+static struct pixel_format primary_pixel_formats[FORMAT_NUM] = {
+       [0b0010]  = {DRM_FORMAT_C8, 8, "8-bit Indexed"},
+       [0b0101]  = {DRM_FORMAT_RGB565, 16, "16-bit BGRX (5:6:5 MSB-R:G:B)"},
+       [0b0110]  = {DRM_FORMAT_XRGB8888, 32, "32-bit BGRX (8:8:8:8 
MSB-X:R:G:B)"},
+       [0b1000]  = {DRM_FORMAT_XBGR2101010, 32, "32-bit RGBX (2:10:10:10 
MSB-X:B:G:R)"},
+       [0b1010] = {DRM_FORMAT_XRGB2101010, 32, "32-bit BGRX (2:10:10:10 
MSB-X:R:G:B)"},
+       [0b1110] = {DRM_FORMAT_XBGR8888, 32, "32-bit RGBX (8:8:8:8 
MSB-X:B:G:R)"},
+};
+
+/* non-supported format has bpp default to 0 */
+static struct pixel_format skl_pixel_formats[FORMAT_NUM] = {
+       [0b1100]  = {DRM_FORMAT_C8, 8, "8-bit Indexed"},
+       [0b1110]  = {DRM_FORMAT_RGB565, 16, "16-bit BGRX (5:6:5 MSB-R:G:B)"},
+       [0b0100]  = {DRM_FORMAT_XRGB8888, 32, "32-bit BGRX (8:8:8:8 
MSB-X:R:G:B)"},
+       [0b1010]  = {DRM_FORMAT_XRGB2101010, 32, "32-bit BGRX (2:10:10:10 
MSB-X:R:G:B)"},
+};
+
+static ATOMIC_NOTIFIER_HEAD(gvt_fb_notifier_list);
+
+int gvt_decode_primary_plane_format(struct vgt_device *vgt,
+       int pipe, struct gvt_primary_plane_format *plane)
 {
+       u32     val, fmt;
+       struct drm_device *dev = vgt->pdev->dev_priv->dev;
+
+       val = __vreg(vgt, GVT_DSPCNTR(pipe));
+       plane->enabled = !!(val & DISPLAY_PLANE_ENABLE);
+       if (!plane->enabled)
+               return 0;
+
+       if (IS_SKYLAKE(dev)) {
+               plane->tiled = !!(val & PLANE_CTL_TILED_MASK);
+               fmt = (val & PLANE_CTL_FORMAT_MASK) >> 24;
+       } else {
+               plane->tiled = !!(val & DISPPLANE_TILED);
+               fmt = (val & DISPPLANE_PIXFORMAT_MASK) >> _PRI_PLANE_FMT_SHIFT;
+       }
+
+       if ((IS_SKYLAKE(dev) && !skl_pixel_formats[fmt].bpp)
+                       || (!IS_SKYLAKE(dev) && 
!primary_pixel_formats[fmt].bpp)) {
+               gvt_err("Non-supported pixel format (0x%x)\n", fmt);
+               return -EINVAL;
+       }
+
+       plane->hw_format = fmt;
+       plane->bpp = primary_pixel_formats[fmt].bpp;
+       plane->drm_format = primary_pixel_formats[fmt].drm_format;
+
+       plane->base = __vreg(vgt, GVT_DSPSURF(pipe)) & GTT_PAGE_MASK;
+       plane->stride = __vreg(vgt, GVT_DSPSTRIDE(pipe)) &
+               _PRI_PLANE_STRIDE_MASK;
+       plane->width = (__vreg(vgt, GVT_PIPESRC(pipe)) & _PIPE_H_SRCSZ_MASK) >>
+               _PIPE_H_SRCSZ_SHIFT;
+       plane->width += 1;
+       plane->height = (__vreg(vgt, GVT_PIPESRC(pipe)) &
+                       _PIPE_V_SRCSZ_MASK) >> _PIPE_V_SRCSZ_SHIFT;
+       plane->height += 1;     /* raw height is one minus the real value */
+
+       val = __vreg(vgt, GVT_DSPTILEOFF(pipe));
+       plane->x_offset = (val & _PRI_PLANE_X_OFF_MASK) >>
+               _PRI_PLANE_X_OFF_SHIFT;
+       plane->y_offset = (val & _PRI_PLANE_Y_OFF_MASK) >>
+               _PRI_PLANE_Y_OFF_SHIFT;
+
        return 0;
 }
 
-int gvt_fb_notifier_call_chain(unsigned long val, void *data)
+#define CURSOR_MODE_NUM        (1 << 6)
+struct cursor_mode_format {
+       int     drm_format;     /* Pixel format in DRM definition */
+       u8      bpp;            /* Bits per pixel; 0 indicates invalid */
+       u32     width;          /* In pixel */
+       u32     height;         /* In lines */
+       char    *desc;          /* The description */
+};
+
+/* non-supported format has bpp default to 0 */
+static struct cursor_mode_format cursor_pixel_formats[CURSOR_MODE_NUM] = {
+       [0b100010]  = {DRM_FORMAT_ARGB8888, 32, 128, 128,"128x128 32bpp ARGB"},
+       [0b100011]  = {DRM_FORMAT_ARGB8888, 32, 256, 256, "256x256 32bpp ARGB"},
+       [0b100111]  = {DRM_FORMAT_ARGB8888, 32, 64, 64, "64x64 32bpp ARGB"},
+       [0b000111]  = {DRM_FORMAT_ARGB8888, 32, 64, 64, "64x64 32bpp 
ARGB"},//actually inverted... figure this out later
+};
+
+int gvt_decode_cursor_plane_format(struct vgt_device *vgt,
+       int pipe, struct gvt_cursor_plane_format *plane)
 {
+       u32 val, mode;
+       u32 alpha_plane, alpha_force;
+
+       val = __vreg(vgt, GVT_CURCNTR(pipe));
+       mode = val & _CURSOR_MODE;
+       plane->enabled = (mode != _CURSOR_MODE_DISABLE);
+       if (!plane->enabled)
+               return 0;
+
+       if (!cursor_pixel_formats[mode].bpp) {
+               gvt_err("Non-supported cursor mode (0x%x)\n", mode);
+               return -EINVAL;
+       }
+       plane->mode = mode;
+       plane->bpp = cursor_pixel_formats[mode].bpp;
+       plane->drm_format = cursor_pixel_formats[mode].drm_format;
+       plane->width = cursor_pixel_formats[mode].width;
+       plane->height = cursor_pixel_formats[mode].height;
+
+       alpha_plane = (val & _CURSOR_ALPHA_PLANE_MASK) >>
+                               _CURSOR_ALPHA_PLANE_SHIFT;
+       alpha_force = (val & _CURSOR_ALPHA_FORCE_MASK) >>
+                               _CURSOR_ALPHA_FORCE_SHIFT;
+       if (alpha_plane || alpha_force)
+               gvt_warn("alpha_plane=0x%x, alpha_force=0x%x\n",
+                       alpha_plane, alpha_force);
+
+       plane->base = __vreg(vgt, GVT_CURBASE(pipe)) & GTT_PAGE_MASK;
+
+       val = __vreg(vgt, GVT_CURPOS(pipe));
+       plane->x_pos = (val & _CURSOR_POS_X_MASK) >> _CURSOR_POS_X_SHIFT;
+       plane->x_sign = (val & _CURSOR_SIGN_X_MASK) >> _CURSOR_SIGN_X_SHIFT;
+       plane->y_pos = (val & _CURSOR_POS_Y_MASK) >> _CURSOR_POS_Y_SHIFT;
+       plane->y_sign = (val & _CURSOR_SIGN_Y_MASK) >> _CURSOR_SIGN_Y_SHIFT;
+       plane->x_hot = __vreg(vgt, _vgtif_reg(xhot));
+       plane->y_hot = __vreg(vgt, _vgtif_reg(xhot));
+
+       return 0;
+}
+
+#define FORMAT_NUM_SRRITE      (1 << 3)
+
+static struct pixel_format sprite_pixel_formats[FORMAT_NUM_SRRITE] = {
+       [0b000]  = {DRM_FORMAT_YUV422, 16, "YUV 16-bit 4:2:2 packed"},
+       [0b001]  = {DRM_FORMAT_XRGB2101010, 32, "RGB 32-bit 2:10:10:10"},
+       [0b010]  = {DRM_FORMAT_XRGB8888, 32, "RGB 32-bit 8:8:8:8"},
+       [0b100] = {DRM_FORMAT_AYUV, 32, "YUV 32-bit 4:4:4 packed (8:8:8:8 
MSB-X:Y:U:V)"},
+};
+
+int gvt_decode_sprite_plane_format(struct vgt_device *vgt,
+       int pipe, struct gvt_sprite_plane_format *plane)
+{
+       u32 val, fmt;
+       u32 width;
+       u32 color_order, yuv_order;
+       int drm_format;
+
+       val = __vreg(vgt, GVT_SPRCTL(pipe));
+       plane->enabled = !!(val & SPRITE_ENABLE);
+       if (!plane->enabled)
+               return 0;
+
+       plane->tiled = !!(val & SPRITE_TILED);
+       color_order = !!(val & SPRITE_RGB_ORDER_RGBX);
+       yuv_order = (val & SPRITE_YUV_BYTE_ORDER_MASK) >>
+                               _SPRITE_YUV_ORDER_SHIFT;
+
+       fmt = (val & SPRITE_PIXFORMAT_MASK) >> _SPRITE_FMT_SHIFT;
+       if (!sprite_pixel_formats[fmt].bpp) {
+               gvt_err("Non-supported pixel format (0x%x)\n", fmt);
+               return -EINVAL;
+       }
+       plane->hw_format = fmt;
+       plane->bpp = sprite_pixel_formats[fmt].bpp;
+       drm_format = sprite_pixel_formats[fmt].drm_format;
+
+       /* Order of RGB values in an RGBxxx buffer may be ordered RGB or
+        * BGR depending on the state of the color_order field
+        */
+       if (!color_order) {
+               if (drm_format == DRM_FORMAT_XRGB2101010)
+                       drm_format = DRM_FORMAT_XBGR2101010;
+               else if (drm_format == DRM_FORMAT_XRGB8888)
+                       drm_format = DRM_FORMAT_XBGR8888;
+       }
+
+       if (drm_format == DRM_FORMAT_YUV422) {
+               switch (yuv_order){
+               case    0:
+                       drm_format = DRM_FORMAT_YUYV;
+                       break;
+               case    1:
+                       drm_format = DRM_FORMAT_UYVY;
+                       break;
+               case    2:
+                       drm_format = DRM_FORMAT_YVYU;
+                       break;
+               case    3:
+                       drm_format = DRM_FORMAT_VYUY;
+                       break;
+               default:
+                       /* yuv_order has only 2 bits */
+                       BUG();
+                       break;
+               }
+       }
+
+       plane->drm_format = drm_format;
+
+       plane->base = __vreg(vgt, GVT_SPRSURF(pipe)) & GTT_PAGE_MASK;
+       plane->width = __vreg(vgt, GVT_SPRSTRIDE(pipe)) &
+                               _SPRITE_STRIDE_MASK;
+       plane->width /= plane->bpp / 8; /* raw width in bytes */
+
+       val = __vreg(vgt, GVT_SPRSIZE(pipe));
+       plane->height = (val & _SPRITE_SIZE_HEIGHT_MASK) >>
+               _SPRITE_SIZE_HEIGHT_SHIFT;
+       width = (val & _SPRITE_SIZE_WIDTH_MASK) >> _SPRITE_SIZE_WIDTH_SHIFT;
+       plane->height += 1;     /* raw height is one minus the real value */
+       width += 1;             /* raw width is one minus the real value */
+       if (plane->width != width)
+               gvt_warn("sprite_plane: plane->width=%d, width=%d\n",
+                       plane->width, width);
+
+       val = __vreg(vgt, GVT_SPRPOS(pipe));
+       plane->x_pos = (val & _SPRITE_POS_X_MASK) >> _SPRITE_POS_X_SHIFT;
+       plane->y_pos = (val & _SPRITE_POS_Y_MASK) >> _SPRITE_POS_Y_SHIFT;
+
+       val = __vreg(vgt, GVT_SPROFFSET(pipe));
+       plane->x_offset = (val & _SPRITE_OFFSET_START_X_MASK) >>
+                          _SPRITE_OFFSET_START_X_SHIFT;
+       plane->y_offset = (val & _SPRITE_OFFSET_START_Y_MASK) >>
+                          _SPRITE_OFFSET_START_Y_SHIFT;
        return 0;
 }
+
+/*
+ * Decode framebuffer information from raw vMMIO
+ *
+ * INPUT:
+ *   [domid] - specify the VM
+ * OUTPUT:
+ *   [format] - contain the decoded format info
+ *
+ * NOTE: The caller is expected to poll this interface, and reconstruct
+ * previous reference to the new format information
+ */
+
+int gvt_decode_fb_format(struct pgt_device *pdev, int vmid, struct 
gvt_fb_format *fb)
+{
+       int i;
+       struct vgt_device *vgt = NULL;
+       int ret = 0;
+
+       if (!fb)
+               return -EINVAL;
+
+       /* TODO: use fine-grained refcnt later */
+       mutex_lock(&pdev->lock);
+
+       for_each_online_instance(pdev, vgt, i)
+               if (vgt->vm_id == vmid)
+                       break;
+
+       if (!vgt) {
+               gvt_err("Invalid domain ID (%d)\n", vmid);
+               mutex_unlock(&pdev->lock);
+               return -ENODEV;
+       }
+
+       for (i = 0; i < I915_MAX_PIPES; i++) {
+               struct gvt_pipe_format *pipe = &fb->pipes[i];
+               u32 ddi_func_ctl = __vreg(vgt, _GVT_TRANS_DDI_FUNC_CTL(i));
+
+               if (!(ddi_func_ctl & TRANS_DDI_FUNC_ENABLE)) {
+                       pipe->ddi_port = DDI_PORT_NONE;
+               } else {
+                       u32 port = (ddi_func_ctl & TRANS_DDI_PORT_MASK) >>
+                                               TRANS_DDI_PORT_SHIFT;
+                       if (port <= DDI_PORT_E)
+                               pipe->ddi_port = port;
+                       else
+                               pipe->ddi_port = DDI_PORT_NONE;
+               }
+
+               ret |= gvt_decode_primary_plane_format(vgt, i, &pipe->primary);
+               ret |= gvt_decode_sprite_plane_format(vgt, i, &pipe->sprite);
+               ret |= gvt_decode_cursor_plane_format(vgt, i, &pipe->cursor);
+
+               if (ret) {
+                       gvt_err("Decode format error for pipe(%d)\n", i);
+                       ret = -EINVAL;
+                       break;
+               }
+       }
+
+       mutex_unlock(&pdev->lock);
+
+       return ret;
+}
+
+int gvt_fb_notifier_call_chain(unsigned long val, void *data)
+{
+       return atomic_notifier_call_chain(&gvt_fb_notifier_list, val, data);
+}
diff --git a/drivers/gpu/drm/i915/gvt/gvt.h b/drivers/gpu/drm/i915/gvt/gvt.h
index cf88bd6..456b332 100644
--- a/drivers/gpu/drm/i915/gvt/gvt.h
+++ b/drivers/gpu/drm/i915/gvt/gvt.h
@@ -38,6 +38,7 @@
 #include "gtt.h"
 #include "cfg_space.h"
 #include "opregion.h"
+#include "fb_decoder.h"
 
 #define GVT_MAX_VGPU 8
 
diff --git a/drivers/gpu/drm/i915/gvt/reg.h b/drivers/gpu/drm/i915/gvt/reg.h
index 3fb4495..c66a2dc 100644
--- a/drivers/gpu/drm/i915/gvt/reg.h
+++ b/drivers/gpu/drm/i915/gvt/reg.h
@@ -68,6 +68,407 @@
 #define    _REGBIT_BDW_GMCH_GMS_SHIFT   8
 #define    _REGBIT_BDW_GMCH_GMS_MASK    0xff
 
+#define        _PRI_PLANE_FMT_SHIFT    26
+#define        _PRI_PLANE_TILE_SHIFT   10
+
+#define        _PRI_PLANE_STRIDE_SHIFT 6
+#define        _PRI_PLANE_STRIDE_MASK  (0x3ff << _PRI_PLANE_STRIDE_SHIFT)
+
+#define        _PRI_PLANE_X_OFF_SHIFT  0
+#define        _PRI_PLANE_X_OFF_MASK   (0x1fff << _PRI_PLANE_X_OFF_SHIFT)
+#define        _PRI_PLANE_Y_OFF_SHIFT  16
+#define        _PRI_PLANE_Y_OFF_MASK   (0xfff << _PRI_PLANE_Y_OFF_SHIFT)
+
+#define     _PIPE_V_SRCSZ_SHIFT        0
+#define     _PIPE_V_SRCSZ_MASK (0xfff << _PIPE_V_SRCSZ_SHIFT)
+#define     _PIPE_H_SRCSZ_SHIFT        16
+#define     _PIPE_H_SRCSZ_MASK (0x1fff << _PIPE_H_SRCSZ_SHIFT)
+
+#define _CURSOR_MODE   0x3f
+#define _CURSOR_MODE_DISABLE   0x00
+#define _CURSOR_ALPHA_FORCE_SHIFT      8
+#define _CURSOR_ALPHA_FORCE_MASK       (0x3 << _CURSOR_ALPHA_FORCE_SHIFT)
+#define _CURSOR_ALPHA_PLANE_SHIFT      10
+#define _CURSOR_ALPHA_PLANE_MASK       (0x3 << _CURSOR_ALPHA_PLANE_SHIFT)
+#define _CURSOR_POS_X_SHIFT    0
+#define _CURSOR_POS_X_MASK     (0x1fff << _CURSOR_POS_X_SHIFT)
+#define _CURSOR_SIGN_X_SHIFT   15
+#define _CURSOR_SIGN_X_MASK    (1 << _CURSOR_SIGN_X_SHIFT)
+#define _CURSOR_POS_Y_SHIFT            16
+#define _CURSOR_POS_Y_MASK     (0xfff << _CURSOR_POS_Y_SHIFT)
+#define _CURSOR_SIGN_Y_SHIFT   31
+#define _CURSOR_SIGN_Y_MASK    (1 << _CURSOR_SIGN_Y_SHIFT)
+
+#define GVT_CURCNTR(pipe)      _PIPE(pipe, _CURACNTR, _CURBCNTR_IVB)
+#define GVT_CURBASE(pipe)      _PIPE(pipe, _CURABASE, _CURBBASE_IVB)
+#define GVT_CURPOS(pipe)       _PIPE(pipe, _CURAPOS, _CURBPOS_IVB)
+
+#define        _SPRITE_FMT_SHIFT       25
+#define        _SPRITE_COLOR_ORDER_SHIFT       20
+#define        _SPRITE_YUV_ORDER_SHIFT 16
+
+#define        _SPRITE_STRIDE_SHIFT    6
+#define        _SPRITE_STRIDE_MASK     (0x1ff << _SPRITE_STRIDE_SHIFT)
+
+#define        _SPRITE_POS_X_SHIFT     0
+#define        _SPRITE_POS_Y_SHIFT     16
+#define        _SPRITE_POS_X_MASK      (0x1fff << _SPRITE_POS_X_SHIFT)
+#define        _SPRITE_POS_Y_MASK      (0xfff << _SPRITE_POS_Y_SHIFT)
+
+#define        _SPRITE_SIZE_WIDTH_SHIFT        0
+#define        _SPRITE_SIZE_HEIGHT_SHIFT       16
+#define        _SPRITE_SIZE_WIDTH_MASK (0x1fff << _SPRITE_SIZE_WIDTH_SHIFT)
+#define        _SPRITE_SIZE_HEIGHT_MASK        (0xfff << 
_SPRITE_SIZE_HEIGHT_SHIFT)
+
+#define        _SPRITE_OFFSET_START_X_SHIFT    0
+#define        _SPRITE_OFFSET_START_Y_SHIFT    16
+#define        _SPRITE_OFFSET_START_X_MASK     (0x1fff << 
_SPRITE_OFFSET_START_X_SHIFT)
+#define        _SPRITE_OFFSET_START_Y_MASK     (0xfff << 
_SPRITE_OFFSET_START_Y_SHIFT)
+
+#define GVT_SPRCTL(pipe)       _PIPE(pipe, _SPRA_CTL, _PLANE_CTL_2_B)
+#define GVT_SPRSTRIDE(pipe)    _PIPE(pipe, _SPRA_STRIDE, _PLANE_STRIDE_2_B)
+#define GVT_SPRPOS(pipe)       _PIPE(pipe, _PLANE_POS_2_A, _PLANE_POS_2_B)
+#define GVT_SPRSIZE(pipe)      _PIPE(pipe, _PLANE_SIZE_2_A, _PLANE_SIZE_2_B)
+#define GVT_SPROFFSET(pipe)    _PIPE(pipe, _PLANE_OFFSET_2_A, 
_PLANE_OFFSET_2_B)
+
+#define GVT_DSPCNTR(pipe) _PIPE(pipe, _DSPACNTR, 0x71180)
+#define GVT_DSPCNTRPIPE(dspcntr) _GVT_GET_PIPE(dspcntr, _DSPACNTR, 0x71180)
+
+#define GVT_DSPLINOFF(pipe) _PIPE(pipe, _DSPAADDR, 0x71184)
+#define GVT_DSPSTRIDE(pipe) _PIPE(pipe, _DSPASTRIDE, 0x71188)
+#define GVT_DSPTILEOFF(pipe) _PIPE(pipe, _DSPATILEOFF, 0x711A4)
+
+#define GVT_DSPSURF(pipe) _PIPE(pipe, _DSPASURF, 0x7119C)
+#define GVT_DSPSURFPIPE(dspsurf) _GVT_GET_PIPE(dspsurf, _DSPASURF, 0x7119C)
+
+#define GVT_DSPSURFLIVE(pipe) _PIPE(pipe, _DSPASURFLIVE, 0x711AC)
+#define GVT_DSPSURFLIVEPIPE(dspsurf) _GVT_GET_PIPE(dspsurf, _DSPASURFLIVE, 
0x711AC)
+
+#define GVT_DSPPOS(pipe) _PIPE(pipe, _DSPAPOS, 0x7118C)
+#define GVT_DSPSIZE(pipe) _PIPE(pipe, _DSPASIZE, 0x71190)
+
+#define GVT_CURSURF(pipe) _PIPE(pipe, _CURABASE, _CURBBASE_IVB)
+#define GVT_CURCNTR(pipe) _PIPE(pipe, _CURACNTR, _CURBCNTR_IVB)
+#define GVT_CURPOS(pipe)       _PIPE(pipe, _CURAPOS, _CURBPOS_IVB)
+#define GVT_CURSURFLIVE(pipe) _PIPE(pipe, 0x700AC, 0x710AC)
+
+#define GVT_CURSURFPIPE(cursurf) _GVT_GET_PIPE(cursurf, _CURABASE, 
_CURBBASE_IVB)
+#define GVT_CURCNTRPIPE(curcntr) _GVT_GET_PIPE(curcntr, 
_CURACNTR,_CURBCNTR_IVB)
+
+#define GVT_SPRSURF(pipe) _PIPE(pipe, _SPRA_SURF, _SPRB_SURF)
+#define GVT_SPRSURFLIVE(pipe) _PIPE(pipe, _SPRA_SURFLIVE, _SPRB_SURFLIVE)
+#define GVT_SPRSURFPIPE(sprsurf) _GVT_GET_PIPE(sprsurf, _SPRA_SURF, _SPRB_SURF)
+
+#define GVT_SPRCNTR(pipe) _PIPE(pipe, _SPRA_CTL, _SPRB_CTL)
+#define GVT_SPRCNTRPIPE(sprcntr) _GVT_GET_PIPE(sprcntr, _SPRA_CTL, _SPRB_CTL)
+
+/*
+ * We use _IMM instead of _INDEX, to avoid switching hardware
+ * status page
+ */
+#define MI_STORE_DATA_IMM              ((0x20<<23) | 2)
+#define MI_STORE_DATA_IMM_QWORD                ((0x20<<23) | 3)
+#define   MI_SDI_USE_GTT               (1<<22)
+#define MI_LRI_CMD                     (0x22<<23 | 1)
+#define   MI_LRI_BYTE0_DISABLE         (1<<8)
+#define   MI_LRI_BYTE1_DISABLE         (1<<9)
+#define   MI_LRI_BYTE2_DISABLE         (1<<10)
+#define   MI_LRI_BYTE3_DISABLE         (1<<11)
+
+#define   MI_WAIT_FOR_PLANE_C_FLIP_PENDING      (1<<15)
+#define   MI_WAIT_FOR_PLANE_B_FLIP_PENDING      (1<<9)
+#define   MI_WAIT_FOR_PLANE_A_FLIP_PENDING      (1<<1)
+
+#define   MI_WAIT_FOR_SPRITE_C_FLIP_PENDING      (1<<20)
+#define   MI_WAIT_FOR_SPRITE_B_FLIP_PENDING      (1<<10)
+#define   MI_WAIT_FOR_SPRITE_A_FLIP_PENDING      (1<<2)
+
+#define        PIPE_CONTROL_DC_FLUSH_ENABLE                    (1<<5)
+#define DUMMY_3D               (0x6d800005)
+#define PRIM_TRILIST           (0x4)
+
+/*
+ * Display engine regs
+ */
+
+#define _REG_SWF               0x4f000
+#define _REG_PIPE_MISC_C       0x72030
+
+/* CPU panel fitter */
+#define _REG_PF_CTL_2                  0x69080
+#define _REG_PF_WIN_SZ_2               0x69074
+#define _REG_PF_WIN_POS_2              0x69070
+
+#define GVT_HTOTAL(pipe)       _PIPE(pipe, _HTOTAL_A, _HTOTAL_B)
+#define GVT_HBLANK(pipe)       _PIPE(pipe, _HBLANK_A, _HBLANK_B)
+#define GVT_HSYNC(pipe)                _PIPE(pipe, _HSYNC_A, _HSYNC_B)
+#define GVT_VTOTAL(pipe)       _PIPE(pipe, _VTOTAL_A, _VTOTAL_B)
+#define GVT_VBLANK(pipe)       _PIPE(pipe, _VBLANK_A, _VBLANK_B)
+#define GVT_VSYNC(pipe)                _PIPE(pipe, _VSYNC_A, _VSYNC_B)
+#define GVT_BCLRPAT(pipe)      _PIPE(pipe, _BCLRPAT_A, _BCLRPAT_B)
+#define GVT_VSYNCSHIFT(pipe)   _PIPE(pipe, _VSYNCSHIFT_A, _VSYNCSHIFT_B)
+#define GVT_PIPESRC(pipe)      _PIPE(pipe, _PIPEASRC, _PIPEBSRC)
+
+#define GVT_PCH_DPLL(pipe)     _PIPE(pipe, _REG_PCH_DPLL_A, _REG_PCH_DPLL_B)
+
+#define GVT_PCH_FP0(pipe)      _PIPE(pipe, _REG_PCH_FPA0, _REG_PCH_FPB0)
+#define GVT_PCH_FP1(pipe)      _PIPE(pipe, _REG_PCH_FPA1, _REG_PCH_FPB1)
+
+/* PIPE C timing regs are same start from 0x61000 */
+#define _REG_PIPEC_DATA_M1             0x62030
+#define _REG_PIPEC_DATA_N1             0x62034
+#define _REG_PIPEC_LINK_M1             0x62040
+#define _REG_PIPEC_LINK_N1             0x62044
+
+#define _REG_PIPEC_DATA_M2             0x62038
+#define _REG_PIPEC_DATA_N2             0x6203c
+#define _REG_PIPEC_LINK_M2             0x62048
+#define _REG_PIPEC_LINK_N2             0x6204c
+
+#define GVT_PIPE_DATA_M1(pipe) _PIPE(pipe, _REG_PIPEA_DATA_M1, 
_REG_PIPEB_DATA_M1)
+#define GVT_PIPE_DATA_N1(pipe) _PIPE(pipe, _REG_PIPEA_DATA_N1, 
_REG_PIPEB_DATA_N1)
+#define GVT_PIPE_DATA_M2(pipe) _PIPE(pipe, _REG_PIPEA_DATA_M2, 
_REG_PIPEB_DATA_M2)
+#define GVT_PIPE_DATA_N2(pipe) _PIPE(pipe, _REG_PIPEA_DATA_N2, 
_REG_PIPEB_DATA_N2)
+#define GVT_PIPE_LINK_M1(pipe) _PIPE(pipe, _REG_PIPEA_LINK_M1, 
_REG_PIPEB_LINK_M1)
+#define GVT_PIPE_LINK_N1(pipe) _PIPE(pipe, _REG_PIPEA_LINK_N1, 
_REG_PIPEB_LINK_N1)
+#define GVT_PIPE_LINK_M2(pipe) _PIPE(pipe, _REG_PIPEA_LINK_M2, 
_REG_PIPEB_LINK_M2)
+#define GVT_PIPE_LINK_N2(pipe) _PIPE(pipe, _REG_PIPEA_LINK_N2, 
_REG_PIPEB_LINK_N2)
+
+/* FDI_RX, FDI_X is hard-wired to Transcoder_X */
+
+#define _REG_FDI_RXC_CTL                       0xf200c
+#define _REGBIT_FDI_RX_PORT_WIDTH_MASK         (0x7 << 19)
+#define _REGBIT_FDI_RX_FDI_AUTO_TRAIN_ENABLE   (0x1 << 10)
+
+#define _REG_FDI_RXC_IIR                       0xf2014
+#define _REG_FDI_RXC_IMR                       0xf2018
+
+#define GVT_FDI_RX_IIR(pipe) _PIPE(pipe, _FDI_RXA_IIR, _FDI_RXB_IIR)
+#define GVT_FDI_RX_IMR(pipe) _PIPE(pipe, _FDI_RXA_IMR, _FDI_RXB_IMR)
+
+#define _REGBIT_FDI_RX_INTER_LANE_ALIGN                (1<<10)
+#define _REGBIT_FDI_RX_SYMBOL_LOCK             (1 << 9) /* train 2*/
+#define _REGBIT_FDI_RX_BIT_LOCK                        (1 << 8) /* train 1*/
+#define _REGBIT_FDI_RX_TRAIN_PATTERN_2_FAIL    (1<<7)
+#define _REGBIT_FDI_RX_FS_CODE_ERR             (1<<6)
+#define _REGBIT_FDI_RX_FE_CODE_ERR             (1<<5)
+#define _REGBIT_FDI_RX_SYMBOL_ERR_RATE_ABOVE   (1<<4)
+#define _REGBIT_FDI_RX_HDCP_LINK_FAIL          (1<<3)
+#define _REGBIT_FDI_RX_PIXEL_FIFO_OVERFLOW     (1<<2)
+#define _REGBIT_FDI_RX_CROSS_CLOCK_OVERFLOW    (1<<1)
+#define _REGBIT_FDI_RX_SYMBOL_QUEUE_OVERFLOW   (1<<0)
+
+
+#define GVT_FDI_RX_CTL_BPC_MASK                (0x7 << 16)
+#define GVT_FDI_RX_CTL(pipe) _PIPE(pipe, _FDI_RXA_CTL, _FDI_RXB_CTL)
+
+#define GVT_FDI_RX_TUSIZE1(pipe) _PIPE(pipe, 
_REG_FDI_RXA_TUSIZE1,_REG_FDI_RXB_TUSIZE1)
+
+/* CPU: FDI_TX */
+#define _REG_FDI_TXC_CTL               0x62100
+
+#define _REGBIT_FDI_TX_ENABLE                          (1 << 31)
+#define _REGBIT_FDI_TX_PLL_ENABLE                      (1 << 14)
+#define _REGBIT_FDI_TX_ENHANCE_FRAME_ENABLE            (1<<18)
+
+#define GVT_FDI_TX_CTL(pipe) _PIPE(pipe, _FDI_TXA_CTL, _FDI_TXB_CTL)
+
+/* CRT */
+#define _REGBIT_ADPA_DAC_ENABLE                        (1 << 31)
+#define PORT_TRANS_SEL_SHIFT                   29
+#define GVT_PORT_TRANS_SEL_CPT(pipe)           ((pipe) << PORT_TRANS_SEL_SHIFT)
+#define _REGBIT_ADPA_VSYNC_ACTIVE_HIGH         (1 << 4)
+#define _REGBIT_ADPA_HSYNC_ACTIVE_HIGH         (1 << 3)
+
+/*Intermediate Pixel Storage*/
+union _PCH_PP_CTL
+{
+       uint32_t data;
+       struct
+       {
+               uint32_t power_state_target     : 1; // bit 0
+               uint32_t power_down_on_reset    : 1; // bit 1
+               uint32_t backlight_enable       : 1; // bit 2
+               uint32_t edp_vdd_override_for_aux : 1; // bit 3
+               uint32_t reserve : 12;                  // bits 15:4
+               uint32_t write_protect_key :16; // bits 31:16 0xABCD to disable 
protected)
+       };
+};
+
+union _PCH_PP_STAUTS
+{
+       uint32_t data;
+       struct
+       {
+               uint32_t reserv1        : 4;    // bit 3:0
+               uint32_t reserv2        : 23;   // bit 26:4
+               uint32_t power_cycle_delay_active       :1;     // bit 27
+               uint32_t power_sequence_progress        :2;     // bits 29:28
+               uint32_t require_asset_status           :1;     // bit 30
+               uint32_t panel_powere_on_statue         :1;     // bit 31 (0 - 
Disable, 1 - Enable)
+       };
+};
+
+/* Per-transcoder DIP controls */
+
+#define GVT_TRANSCONF(plane)   _PIPE(plane, _PCH_TRANSACONF, _PCH_TRANSBCONF)
+
+union _TRANS_CONFIG
+{
+       uint32_t data;
+       struct
+       {
+               uint32_t reserve1 : 10;                 // bit 9:0
+               uint32_t xvycc_color_range_limit : 1;   // bit 10
+               uint32_t reserve2 : 10;                 // bit 20:11
+               uint32_t interlaced_mode: 3;            // bit 23:21
+               uint32_t reserve3 : 6;                  // bit 29:24
+               uint32_t transcoder_state : 1;          // bit 30
+               uint32_t transcoder_enable : 1;         // bit 31
+       };
+};
+
+#define _REG_TRANSC_VIDEO_DIP_CTL      0xE2200
+#define _REG_TRANSC_VIDEO_DIP_DATA     0xE2208
+#define _REG_TRANSC_VIDEO_DIP_GCP      0xE2210
+
+/* eDP */
+#define _REG_PIPE_EDP_CONF     0x7f008
+
+/* bit fields of pipestat */
+#define GVT_PIPEDSL(pipe)      _PIPE(pipe, _PIPEADSL, 0x71000)
+#define GVT_PIPECONF(pipe)     _PIPE(pipe, _PIPEACONF, 0x71008)
+#define GVT_PIPESTAT(pipe)     _PIPE(pipe, _PIPEASTAT, 0x71024)
+#define GVT_PIPE_FRMCOUNT(pipe)        _PIPE(pipe, _PIPEA_FRMCOUNT_G4X, 
0x71040)
+#define GVT_PIPE_FLIPCOUNT(pipe) _PIPE(pipe, _PIPEA_FLIPCOUNT_G4X, 0x71044)
+
+#define GVT_PIPECONFPIPE(pipeconf) _GVT_GET_PIPE(pipeconf, _PIPEACONF, 0x71008)
+#define GVT_FRMCOUNTPIPE(frmcount) _GVT_GET_PIPE(frmcount, 
_PIPEA_FRMCOUNT_G4X, 0x71040)
+
+#define GVT_PALETTE(pipe) _PIPE(pipe, _PALETTE_A_OFFSET, _PALETTE_B_OFFSET)
+
+/* legacy palette */
+#define _REG_LGC_PALETTE_C             0x4b000
+
+/* Display Port */
+#define _REG_DP_TP_CTL_C               0x64240
+#define _REG_DP_TP_CTL_D               0x64340
+#define _REG_DP_TP_CTL_E               0x64440
+#define  _REGBIT_DP_TP_FDI_AUTO_TRAIN_ENABLE   (1 << 15)
+#define  _DDI_BUFCTL_DETECT_MASK       0x1
+#define  _REGBIT_DDI_BUF_ENABLE                (1 << 31)
+#define  _REGBIT_DDI_BUF_IS_IDLE       (1<<7)
+#define _REG_DDI_BUF_CTL_C             0x64200
+#define _REG_DDI_BUF_CTL_D             0x64300
+#define _REG_DDI_BUF_CTL_E             0x64400
+#define _REG_DP_TP_STATUS_C                    0x64244
+#define _REG_DP_TP_STATUS_D                    0x64344
+#define _REG_DP_TP_STATUS_E                    0x64444
+#define GVT_DP_TP_CTL(port)            _PORT(port, _DP_TP_CTL_A, \
+               _DP_TP_CTL_B)
+
+#define DP_TP_PORT(reg)                _GVT_GET_PORT(reg, _DP_TP_CTL_A, \
+               _DP_TP_CTL_B)
+
+#define DRM_MODE_DPMS_ON               0
+
+#define _PCH_DPA_AUX_CH_CTL    0x64010
+#define _PCH_DPB_AUX_CH_CTL    0xe4110
+#define _PCH_DPC_AUX_CH_CTL    0xe4210
+#define _PCH_DPD_AUX_CH_CTL    0xe4310
+
+/* DPCD */
+#define DP_SET_POWER           0x600
+#define DP_SET_POWER_D0                0x1
+#define AUX_NATIVE_WRITE       0x8
+#define AUX_NATIVE_READ                0x9
+
+#define AUX_NATIVE_REPLY_MASK  (0x3 << 4)
+#define AUX_NATIVE_REPLY_ACK   (0x0 << 4)
+#define AUX_NATIVE_REPLY_NAK   (0x1 << 4)
+#define AUX_NATIVE_REPLY_DEFER (0x2 << 4)
+
+#define AUX_BURST_SIZE         16
+
+/* DPCD 0x106 */
+
+#define DP_TRAINING_PATTERN_SET                        0x102
+#define DP_TRAINING_PATTERN_DISABLE            0
+#define DP_TRAINING_PATTERN_1                  1
+#define DP_TRAINING_PATTERN_2                  2
+#define DP_LINK_SCRAMBLING_DISABLE             (1 << 5)
+
+#define DP_LINK_CONFIGURATION_SIZE             9
+#define    DP_LINK_BW_SET                      0x100
+# define DP_SET_ANSI_8B10B                     (1 << 0)
+
+#define DP_LINK_STATUS_SIZE                    6
+#define DP_TRAIN_MAX_SWING_REACHED             (1 << 2)
+
+#define DP_TRAINING_LANE0_SET                  0x103
+
+#define DP_TRAIN_VOLTAGE_SWING_MASK            0x3
+#define DP_TRAIN_VOLTAGE_SWING_SHIFT           0
+#define DP_TRAIN_VOLTAGE_SWING_400             (0 << 0)
+#define DP_TRAIN_VOLTAGE_SWING_600             (1 << 0)
+#define DP_TRAIN_VOLTAGE_SWING_800             (2 << 0)
+#define DP_TRAIN_VOLTAGE_SWING_1200            (3 << 0)
+
+#define DP_TRAIN_PRE_EMPHASIS_MASK             (3 << 3)
+#define DP_TRAIN_PRE_EMPHASIS_0                        (0 << 3)
+#define DP_TRAIN_PRE_EMPHASIS_3_5              (1 << 3)
+#define DP_TRAIN_PRE_EMPHASIS_6                        (2 << 3)
+#define DP_TRAIN_PRE_EMPHASIS_9_5              (3 << 3)
+
+#define DP_TRAIN_PRE_EMPHASIS_SHIFT            3
+#define DP_TRAIN_MAX_PRE_EMPHASIS_REACHED      (1 << 5)
+
+#define DP_LANE0_1_STATUS                      0x202
+#define DP_LANE_CR_DONE                                (1 << 0)
+
+#define DP_LANE_ALIGN_STATUS_UPDATED           0x204
+#define DP_INTERLANE_ALIGN_DONE                        (1 << 0)
+#define DP_LANE_CHANNEL_EQ_DONE                        (1 << 1)
+#define DP_LANE_SYMBOL_LOCKED                  (1 << 2)
+
+#define DP_ADJUST_REQUEST_LANE0_1              0x206
+
+#define DP_ADJUST_VOLTAGE_SWING_LANE0_SHIFT 0
+#define DP_ADJUST_VOLTAGE_SWING_LANE1_SHIFT 4
+#define DP_ADJUST_PRE_EMPHASIS_LANE0_SHIFT  2
+#define DP_ADJUST_PRE_EMPHASIS_LANE1_SHIFT  6
+/* Ironlake */
+#define        _REG_CPU_VGACNTRL       CPU_VGACNTRL
+#define _REGBIT_VGA_DISPLAY_DISABLE    (1UL << 31)
+#define _REG_DPFC_CB_BASE              0x43200
+#define _REG_DPFC_CONTROL              0x43208
+#define _REG_DPFC_RECOMP_CTL           0x4320c
+#define _REG_DPFC_CPU_FENCE_OFFSET     0x43218
+#define _REG_DPFC_CONTROL_SA           0x100100
+#define _REG_DPFC_CPU_FENCE_OFFSET_SA  0x100104
+
+#define _REG_CSC_A_COEFFICIENTS                0x49010
+#define _REG_CSC_A_MODE                        0x49028
+#define _REG_PRECSC_A_HIGH_COLOR_CHANNEL_OFFSET                0x49030
+#define _REG_PRECSC_A_MEDIUM_COLOR_CHANNEL_OFFSET      0x49034
+#define _REG_PRECSC_A_LOW_COLOR_CHANNEL_OFFSET         0x49038
+
+#define _REG_CSC_B_COEFFICIENTS                0x49110
+#define _REG_CSC_B_MODE                        0x49128
+#define _REG_PRECSC_B_HIGH_COLOR_CHANNEL_OFFSET                0x49130
+#define _REG_PRECSC_B_MEDIUM_COLOR_CHANNEL_OFFSET      0x49134
+#define _REG_PRECSC_B_LOW_COLOR_CHANNEL_OFFSET         0x49138
+
+#define _REG_CSC_C_COEFFICIENTS                0x49210
+#define _REG_CSC_C_MODE                        0x49228
+#define _REG_PRECSC_C_HIGH_COLOR_CHANNEL_OFFSET                0x49230
+#define _REG_PRECSC_C_MEDIUM_COLOR_CHANNEL_OFFSET      0x49234
+#define _REG_PRECSC_C_LOW_COLOR_CHANNEL_OFFSET         0x49238
+
+#define _REG_DP_BUFTRANS               0xe4f00
+
+#define _PCH_GMBUS0                    0xc5100
+#define _PCH_GMBUS1                    0xc5104
 #define _PCH_GMBUS2                    0xc5108
 
 #define _GEN6_GDRST                    0x941c
@@ -105,4 +506,7 @@
 #define _GEN8_DE_PIPE_IIR(pipe) (0x44408 + (0x10 * (pipe)))
 #define _GEN8_DE_PIPE_IER(pipe) (0x4440c + (0x10 * (pipe)))
 
+#define _GVT_TRANS_DDI_FUNC_CTL(tran)   _TRANS(tran, _TRANS_DDI_FUNC_CTL_A, \
+               _TRANS_DDI_FUNC_CTL_B)
+
 #endif
-- 
1.9.1

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

Reply via email to