drm/i915: Improve gen3/4 frame counter
Currently the logic to fix up the frame counter on gen3/4 assumes that start of vblank occurs at vblank_start*htotal pixels, when in fact it occurs htotal-hsync_start pixels earlier. Apply the appropriate adjustment to make the frame counter more accurate. Also fix the vblank start position for interlaced display modes. Reviewed-by: Imre Deak <imre.deak@intel.com> Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com> Reviewed-by: "Akash Goel <akash.goels@gmail.com>" Reviewed-by: "Sourab Gupta <sourabgupta@gmail.com>" Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
This commit is contained in:
parent
7e78f1cb38
commit
0b2a8e09f9
1 changed files with 16 additions and 5 deletions
|
@ -754,7 +754,7 @@ static u32 i915_get_vblank_counter(struct drm_device *dev, int pipe)
|
||||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||||
unsigned long high_frame;
|
unsigned long high_frame;
|
||||||
unsigned long low_frame;
|
unsigned long low_frame;
|
||||||
u32 high1, high2, low, pixel, vbl_start;
|
u32 high1, high2, low, pixel, vbl_start, hsync_start, htotal;
|
||||||
|
|
||||||
if (!i915_pipe_enabled(dev, pipe)) {
|
if (!i915_pipe_enabled(dev, pipe)) {
|
||||||
DRM_DEBUG_DRIVER("trying to get vblank count for disabled "
|
DRM_DEBUG_DRIVER("trying to get vblank count for disabled "
|
||||||
|
@ -768,17 +768,28 @@ static u32 i915_get_vblank_counter(struct drm_device *dev, int pipe)
|
||||||
const struct drm_display_mode *mode =
|
const struct drm_display_mode *mode =
|
||||||
&intel_crtc->config.adjusted_mode;
|
&intel_crtc->config.adjusted_mode;
|
||||||
|
|
||||||
vbl_start = mode->crtc_vblank_start * mode->crtc_htotal;
|
htotal = mode->crtc_htotal;
|
||||||
|
hsync_start = mode->crtc_hsync_start;
|
||||||
|
vbl_start = mode->crtc_vblank_start;
|
||||||
|
if (mode->flags & DRM_MODE_FLAG_INTERLACE)
|
||||||
|
vbl_start = DIV_ROUND_UP(vbl_start, 2);
|
||||||
} else {
|
} else {
|
||||||
enum transcoder cpu_transcoder = (enum transcoder) pipe;
|
enum transcoder cpu_transcoder = (enum transcoder) pipe;
|
||||||
u32 htotal;
|
|
||||||
|
|
||||||
htotal = ((I915_READ(HTOTAL(cpu_transcoder)) >> 16) & 0x1fff) + 1;
|
htotal = ((I915_READ(HTOTAL(cpu_transcoder)) >> 16) & 0x1fff) + 1;
|
||||||
|
hsync_start = (I915_READ(HSYNC(cpu_transcoder)) & 0x1fff) + 1;
|
||||||
vbl_start = (I915_READ(VBLANK(cpu_transcoder)) & 0x1fff) + 1;
|
vbl_start = (I915_READ(VBLANK(cpu_transcoder)) & 0x1fff) + 1;
|
||||||
|
if ((I915_READ(PIPECONF(cpu_transcoder)) &
|
||||||
vbl_start *= htotal;
|
PIPECONF_INTERLACE_MASK) != PIPECONF_PROGRESSIVE)
|
||||||
|
vbl_start = DIV_ROUND_UP(vbl_start, 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Convert to pixel count */
|
||||||
|
vbl_start *= htotal;
|
||||||
|
|
||||||
|
/* Start of vblank event occurs at start of hsync */
|
||||||
|
vbl_start -= htotal - hsync_start;
|
||||||
|
|
||||||
high_frame = PIPEFRAME(pipe);
|
high_frame = PIPEFRAME(pipe);
|
||||||
low_frame = PIPEFRAMEPIXEL(pipe);
|
low_frame = PIPEFRAMEPIXEL(pipe);
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue