Subversion Repositories Kolibri OS

Rev

Rev 3746 | Rev 4560 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 3746 Rev 4104
Line 30... Line 30...
30
 * support.
30
 * support.
31
 */
31
 */
32
#include 
32
#include 
33
#include 
33
#include 
34
#include 
34
#include 
-
 
35
#include 
35
#include "intel_drv.h"
36
#include "intel_drv.h"
36
#include 
37
#include 
37
#include "i915_drv.h"
38
#include "i915_drv.h"
Line 38... Line 39...
38
 
39
 
39
static void
40
static void
-
 
41
vlv_update_plane(struct drm_plane *dplane, struct drm_crtc *crtc,
40
vlv_update_plane(struct drm_plane *dplane, struct drm_framebuffer *fb,
42
		 struct drm_framebuffer *fb,
41
		 struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
43
		 struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
42
		 unsigned int crtc_w, unsigned int crtc_h,
44
		 unsigned int crtc_w, unsigned int crtc_h,
43
		 uint32_t x, uint32_t y,
45
		 uint32_t x, uint32_t y,
44
		 uint32_t src_w, uint32_t src_h)
46
		 uint32_t src_w, uint32_t src_h)
Line 105... Line 107...
105
	if (obj->tiling_mode != I915_TILING_NONE)
107
	if (obj->tiling_mode != I915_TILING_NONE)
106
		sprctl |= SP_TILED;
108
		sprctl |= SP_TILED;
Line 107... Line 109...
107
 
109
 
Line -... Line 110...
-
 
110
	sprctl |= SP_ENABLE;
-
 
111
 
-
 
112
	intel_update_sprite_watermarks(dplane, crtc, src_w, pixel_size, true,
108
	sprctl |= SP_ENABLE;
113
				       src_w != crtc_w || src_h != crtc_h);
109
 
114
 
110
	/* Sizes are 0 based */
115
	/* Sizes are 0 based */
111
	src_w--;
116
	src_w--;
112
	src_h--;
117
	src_h--;
Line 113... Line -...
113
	crtc_w--;
-
 
114
	crtc_h--;
-
 
115
 
118
	crtc_w--;
116
	intel_update_sprite_watermarks(dev, pipe, crtc_w, pixel_size);
119
	crtc_h--;
Line 117... Line 120...
117
 
120
 
118
	I915_WRITE(SPSTRIDE(pipe, plane), fb->pitches[0]);
121
	I915_WRITE(SPSTRIDE(pipe, plane), fb->pitches[0]);
Line 130... Line 133...
130
	else
133
	else
131
		I915_WRITE(SPLINOFF(pipe, plane), linear_offset);
134
		I915_WRITE(SPLINOFF(pipe, plane), linear_offset);
Line 132... Line 135...
132
 
135
 
133
	I915_WRITE(SPSIZE(pipe, plane), (crtc_h << 16) | crtc_w);
136
	I915_WRITE(SPSIZE(pipe, plane), (crtc_h << 16) | crtc_w);
134
	I915_WRITE(SPCNTR(pipe, plane), sprctl);
137
	I915_WRITE(SPCNTR(pipe, plane), sprctl);
135
	I915_MODIFY_DISPBASE(SPSURF(pipe, plane), obj->gtt_offset +
138
	I915_MODIFY_DISPBASE(SPSURF(pipe, plane), i915_gem_obj_ggtt_offset(obj) +
136
			     sprsurf_offset);
139
			     sprsurf_offset);
137
	POSTING_READ(SPSURF(pipe, plane));
140
	POSTING_READ(SPSURF(pipe, plane));
Line 138... Line 141...
138
}
141
}
139
 
142
 
140
static void
143
static void
141
vlv_disable_plane(struct drm_plane *dplane)
144
vlv_disable_plane(struct drm_plane *dplane, struct drm_crtc *crtc)
142
{
145
{
143
	struct drm_device *dev = dplane->dev;
146
	struct drm_device *dev = dplane->dev;
144
	struct drm_i915_private *dev_priv = dev->dev_private;
147
	struct drm_i915_private *dev_priv = dev->dev_private;
Line 149... Line 152...
149
	I915_WRITE(SPCNTR(pipe, plane), I915_READ(SPCNTR(pipe, plane)) &
152
	I915_WRITE(SPCNTR(pipe, plane), I915_READ(SPCNTR(pipe, plane)) &
150
		   ~SP_ENABLE);
153
		   ~SP_ENABLE);
151
	/* Activate double buffered register update */
154
	/* Activate double buffered register update */
152
	I915_MODIFY_DISPBASE(SPSURF(pipe, plane), 0);
155
	I915_MODIFY_DISPBASE(SPSURF(pipe, plane), 0);
153
	POSTING_READ(SPSURF(pipe, plane));
156
	POSTING_READ(SPSURF(pipe, plane));
-
 
157
 
-
 
158
	intel_update_sprite_watermarks(dplane, crtc, 0, 0, false, false);
154
}
159
}
Line 155... Line 160...
155
 
160
 
156
static int
161
static int
157
vlv_update_colorkey(struct drm_plane *dplane,
162
vlv_update_colorkey(struct drm_plane *dplane,
Line 203... Line 208...
203
	else
208
	else
204
		key->flags = I915_SET_COLORKEY_NONE;
209
		key->flags = I915_SET_COLORKEY_NONE;
205
}
210
}
Line 206... Line 211...
206
 
211
 
207
static void
212
static void
-
 
213
ivb_update_plane(struct drm_plane *plane, struct drm_crtc *crtc,
208
ivb_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb,
214
		 struct drm_framebuffer *fb,
209
		 struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
215
		 struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
210
		 unsigned int crtc_w, unsigned int crtc_h,
216
		 unsigned int crtc_w, unsigned int crtc_h,
211
		 uint32_t x, uint32_t y,
217
		 uint32_t x, uint32_t y,
212
		 uint32_t src_w, uint32_t src_h)
218
		 uint32_t src_w, uint32_t src_h)
Line 252... Line 258...
252
	}
258
	}
Line 253... Line 259...
253
 
259
 
254
	if (obj->tiling_mode != I915_TILING_NONE)
260
	if (obj->tiling_mode != I915_TILING_NONE)
Line 255... Line 261...
255
		sprctl |= SPRITE_TILED;
261
		sprctl |= SPRITE_TILED;
-
 
262
 
-
 
263
	if (IS_HASWELL(dev))
256
 
264
		sprctl &= ~SPRITE_TRICKLE_FEED_DISABLE;
-
 
265
	else
257
	/* must disable */
266
	sprctl |= SPRITE_TRICKLE_FEED_DISABLE;
Line 258... Line 267...
258
	sprctl |= SPRITE_TRICKLE_FEED_DISABLE;
267
 
259
	sprctl |= SPRITE_ENABLE;
268
	sprctl |= SPRITE_ENABLE;
Line -... Line 269...
-
 
269
 
-
 
270
	if (IS_HASWELL(dev))
-
 
271
		sprctl |= SPRITE_PIPE_CSC_ENABLE;
260
 
272
 
261
	if (IS_HASWELL(dev))
273
	intel_update_sprite_watermarks(plane, crtc, src_w, pixel_size, true,
262
		sprctl |= SPRITE_PIPE_CSC_ENABLE;
274
				       src_w != crtc_w || src_h != crtc_h);
263
 
275
 
264
	/* Sizes are 0 based */
276
	/* Sizes are 0 based */
Line 265... Line -...
265
	src_w--;
-
 
266
	src_h--;
-
 
267
	crtc_w--;
277
	src_w--;
268
	crtc_h--;
278
	src_h--;
269
 
279
	crtc_w--;
270
	intel_update_sprite_watermarks(dev, pipe, crtc_w, pixel_size);
280
	crtc_h--;
271
 
281
 
Line 305... Line 315...
305
 
315
 
306
	I915_WRITE(SPRSIZE(pipe), (crtc_h << 16) | crtc_w);
316
	I915_WRITE(SPRSIZE(pipe), (crtc_h << 16) | crtc_w);
307
	if (intel_plane->can_scale)
317
	if (intel_plane->can_scale)
308
	I915_WRITE(SPRSCALE(pipe), sprscale);
318
	I915_WRITE(SPRSCALE(pipe), sprscale);
-
 
319
	I915_WRITE(SPRCTL(pipe), sprctl);
309
	I915_WRITE(SPRCTL(pipe), sprctl);
320
	I915_MODIFY_DISPBASE(SPRSURF(pipe),
310
	I915_MODIFY_DISPBASE(SPRSURF(pipe), obj->gtt_offset + sprsurf_offset);
321
			     i915_gem_obj_ggtt_offset(obj) + sprsurf_offset);
Line 311... Line 322...
311
	POSTING_READ(SPRSURF(pipe));
322
	POSTING_READ(SPRSURF(pipe));
312
 
323
 
313
	/* potentially re-enable LP watermarks */
324
	/* potentially re-enable LP watermarks */
314
	if (scaling_was_enabled && !dev_priv->sprite_scaling_enabled)
325
	if (scaling_was_enabled && !dev_priv->sprite_scaling_enabled)
Line 315... Line 326...
315
		intel_update_watermarks(dev);
326
		intel_update_watermarks(dev);
316
}
327
}
317
 
328
 
318
static void
329
static void
319
ivb_disable_plane(struct drm_plane *plane)
330
ivb_disable_plane(struct drm_plane *plane, struct drm_crtc *crtc)
320
{
331
{
321
	struct drm_device *dev = plane->dev;
332
	struct drm_device *dev = plane->dev;
Line 332... Line 343...
332
	I915_MODIFY_DISPBASE(SPRSURF(pipe), 0);
343
	I915_MODIFY_DISPBASE(SPRSURF(pipe), 0);
333
	POSTING_READ(SPRSURF(pipe));
344
	POSTING_READ(SPRSURF(pipe));
Line 334... Line 345...
334
 
345
 
Line -... Line 346...
-
 
346
	dev_priv->sprite_scaling_enabled &= ~(1 << pipe);
-
 
347
 
335
	dev_priv->sprite_scaling_enabled &= ~(1 << pipe);
348
	intel_update_sprite_watermarks(plane, crtc, 0, 0, false, false);
336
 
349
 
337
	/* potentially re-enable LP watermarks */
350
	/* potentially re-enable LP watermarks */
338
	if (scaling_was_enabled && !dev_priv->sprite_scaling_enabled)
351
	if (scaling_was_enabled && !dev_priv->sprite_scaling_enabled)
Line 392... Line 405...
392
	else
405
	else
393
		key->flags = I915_SET_COLORKEY_NONE;
406
		key->flags = I915_SET_COLORKEY_NONE;
394
}
407
}
Line 395... Line 408...
395
 
408
 
396
static void
409
static void
-
 
410
ilk_update_plane(struct drm_plane *plane, struct drm_crtc *crtc,
397
ilk_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb,
411
		 struct drm_framebuffer *fb,
398
		 struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
412
		 struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
399
		 unsigned int crtc_w, unsigned int crtc_h,
413
		 unsigned int crtc_w, unsigned int crtc_h,
400
		 uint32_t x, uint32_t y,
414
		 uint32_t x, uint32_t y,
401
		 uint32_t src_w, uint32_t src_h)
415
		 uint32_t src_w, uint32_t src_h)
Line 444... Line 458...
444
 
458
 
445
	if (IS_GEN6(dev))
459
	if (IS_GEN6(dev))
446
		dvscntr |= DVS_TRICKLE_FEED_DISABLE; /* must disable */
460
		dvscntr |= DVS_TRICKLE_FEED_DISABLE; /* must disable */
Line -... Line 461...
-
 
461
	dvscntr |= DVS_ENABLE;
-
 
462
 
-
 
463
	intel_update_sprite_watermarks(plane, crtc, src_w, pixel_size, true,
447
	dvscntr |= DVS_ENABLE;
464
				       src_w != crtc_w || src_h != crtc_h);
448
 
465
 
449
	/* Sizes are 0 based */
466
	/* Sizes are 0 based */
450
	src_w--;
467
	src_w--;
451
	src_h--;
468
	src_h--;
Line 452... Line -...
452
	crtc_w--;
-
 
453
	crtc_h--;
-
 
454
 
469
	crtc_w--;
455
	intel_update_sprite_watermarks(dev, pipe, crtc_w, pixel_size);
470
	crtc_h--;
456
 
471
 
Line 457... Line 472...
457
	dvsscale = 0;
472
	dvsscale = 0;
Line 473... Line 488...
473
		I915_WRITE(DVSLINOFF(pipe), linear_offset);
488
		I915_WRITE(DVSLINOFF(pipe), linear_offset);
Line 474... Line 489...
474
 
489
 
475
	I915_WRITE(DVSSIZE(pipe), (crtc_h << 16) | crtc_w);
490
	I915_WRITE(DVSSIZE(pipe), (crtc_h << 16) | crtc_w);
476
	I915_WRITE(DVSSCALE(pipe), dvsscale);
491
	I915_WRITE(DVSSCALE(pipe), dvsscale);
-
 
492
	I915_WRITE(DVSCNTR(pipe), dvscntr);
477
	I915_WRITE(DVSCNTR(pipe), dvscntr);
493
	I915_MODIFY_DISPBASE(DVSSURF(pipe),
478
	I915_MODIFY_DISPBASE(DVSSURF(pipe), obj->gtt_offset + dvssurf_offset);
494
			     i915_gem_obj_ggtt_offset(obj) + dvssurf_offset);
479
	POSTING_READ(DVSSURF(pipe));
495
	POSTING_READ(DVSSURF(pipe));
Line 480... Line 496...
480
}
496
}
481
 
497
 
482
static void
498
static void
483
ilk_disable_plane(struct drm_plane *plane)
499
ilk_disable_plane(struct drm_plane *plane, struct drm_crtc *crtc)
484
{
500
{
485
	struct drm_device *dev = plane->dev;
501
	struct drm_device *dev = plane->dev;
486
	struct drm_i915_private *dev_priv = dev->dev_private;
502
	struct drm_i915_private *dev_priv = dev->dev_private;
Line 491... Line 507...
491
	/* Disable the scaler */
507
	/* Disable the scaler */
492
	I915_WRITE(DVSSCALE(pipe), 0);
508
	I915_WRITE(DVSSCALE(pipe), 0);
493
	/* Flush double buffered register updates */
509
	/* Flush double buffered register updates */
494
	I915_MODIFY_DISPBASE(DVSSURF(pipe), 0);
510
	I915_MODIFY_DISPBASE(DVSSURF(pipe), 0);
495
	POSTING_READ(DVSSURF(pipe));
511
	POSTING_READ(DVSSURF(pipe));
-
 
512
 
-
 
513
	intel_update_sprite_watermarks(plane, crtc, 0, 0, false, false);
496
}
514
}
Line 497... Line 515...
497
 
515
 
498
static void
516
static void
499
intel_enable_primary(struct drm_crtc *crtc)
517
intel_enable_primary(struct drm_crtc *crtc)
Line 581... Line 599...
581
		key->flags = I915_SET_COLORKEY_SOURCE;
599
		key->flags = I915_SET_COLORKEY_SOURCE;
582
	else
600
	else
583
		key->flags = I915_SET_COLORKEY_NONE;
601
		key->flags = I915_SET_COLORKEY_NONE;
584
}
602
}
Line -... Line 603...
-
 
603
 
-
 
604
static bool
-
 
605
format_is_yuv(uint32_t format)
-
 
606
{
-
 
607
	switch (format) {
-
 
608
	case DRM_FORMAT_YUYV:
-
 
609
	case DRM_FORMAT_UYVY:
-
 
610
	case DRM_FORMAT_VYUY:
-
 
611
	case DRM_FORMAT_YVYU:
-
 
612
		return true;
-
 
613
	default:
-
 
614
		return false;
-
 
615
	}
-
 
616
}
585
 
617
 
586
static int
618
static int
587
intel_update_plane(struct drm_plane *plane, struct drm_crtc *crtc,
619
intel_update_plane(struct drm_plane *plane, struct drm_crtc *crtc,
588
		   struct drm_framebuffer *fb, int crtc_x, int crtc_y,
620
		   struct drm_framebuffer *fb, int crtc_x, int crtc_y,
589
		   unsigned int crtc_w, unsigned int crtc_h,
621
		   unsigned int crtc_w, unsigned int crtc_h,
Line 598... Line 630...
598
	struct drm_i915_gem_object *obj, *old_obj;
630
	struct drm_i915_gem_object *obj, *old_obj;
599
	int pipe = intel_plane->pipe;
631
	int pipe = intel_plane->pipe;
600
	enum transcoder cpu_transcoder = intel_pipe_to_cpu_transcoder(dev_priv,
632
	enum transcoder cpu_transcoder = intel_pipe_to_cpu_transcoder(dev_priv,
601
								      pipe);
633
								      pipe);
602
	int ret = 0;
634
	int ret = 0;
603
	int x = src_x >> 16, y = src_y >> 16;
-
 
604
	int primary_w = crtc->mode.hdisplay, primary_h = crtc->mode.vdisplay;
-
 
605
	bool disable_primary = false;
635
	bool disable_primary = false;
-
 
636
	bool visible;
-
 
637
	int hscale, vscale;
-
 
638
	int max_scale, min_scale;
-
 
639
	int pixel_size = drm_format_plane_cpp(fb->pixel_format, 0);
-
 
640
	struct drm_rect src = {
-
 
641
		/* sample coordinates in 16.16 fixed point */
-
 
642
		.x1 = src_x,
-
 
643
		.x2 = src_x + src_w,
-
 
644
		.y1 = src_y,
-
 
645
		.y2 = src_y + src_h,
-
 
646
	};
-
 
647
	struct drm_rect dst = {
-
 
648
		/* integer pixels */
-
 
649
		.x1 = crtc_x,
-
 
650
		.x2 = crtc_x + crtc_w,
-
 
651
		.y1 = crtc_y,
-
 
652
		.y2 = crtc_y + crtc_h,
-
 
653
	};
-
 
654
	const struct drm_rect clip = {
-
 
655
		.x2 = crtc->mode.hdisplay,
-
 
656
		.y2 = crtc->mode.vdisplay,
-
 
657
	};
Line 606... Line 658...
606
 
658
 
607
	intel_fb = to_intel_framebuffer(fb);
659
	intel_fb = to_intel_framebuffer(fb);
Line 608... Line 660...
608
	obj = intel_fb->obj;
660
	obj = intel_fb->obj;
Line 616... Line 668...
616
	intel_plane->src_x = src_x;
668
	intel_plane->src_x = src_x;
617
	intel_plane->src_y = src_y;
669
	intel_plane->src_y = src_y;
618
	intel_plane->src_w = src_w;
670
	intel_plane->src_w = src_w;
619
	intel_plane->src_h = src_h;
671
	intel_plane->src_h = src_h;
Line 620... Line -...
620
 
-
 
621
	src_w = src_w >> 16;
-
 
622
	src_h = src_h >> 16;
-
 
623
 
672
 
624
	/* Pipe must be running... */
673
	/* Pipe must be running... */
-
 
674
	if (!(I915_READ(PIPECONF(cpu_transcoder)) & PIPECONF_ENABLE)) {
625
	if (!(I915_READ(PIPECONF(cpu_transcoder)) & PIPECONF_ENABLE))
675
		DRM_DEBUG_KMS("Pipe disabled\n");
-
 
676
		return -EINVAL;
Line -... Line 677...
-
 
677
	}
626
		return -EINVAL;
678
 
-
 
679
	/* Don't modify another pipe's plane */
627
 
680
	if (intel_plane->pipe != intel_crtc->pipe) {
-
 
681
		DRM_DEBUG_KMS("Wrong plane <-> crtc mapping\n");
Line 628... Line 682...
628
	if (crtc_x >= primary_w || crtc_y >= primary_h)
682
		return -EINVAL;
629
		return -EINVAL;
683
	}
-
 
684
 
630
 
685
	/* FIXME check all gen limits */
-
 
686
	if (fb->width < 3 || fb->height < 3 || fb->pitches[0] > 16384) {
Line 631... Line 687...
631
	/* Don't modify another pipe's plane */
687
		DRM_DEBUG_KMS("Unsuitable framebuffer for plane\n");
632
	if (intel_plane->pipe != intel_crtc->pipe)
688
		return -EINVAL;
633
		return -EINVAL;
689
	}
634
 
690
 
635
	/* Sprite planes can be linear or x-tiled surfaces */
691
	/* Sprite planes can be linear or x-tiled surfaces */
636
	switch (obj->tiling_mode) {
692
	switch (obj->tiling_mode) {
-
 
693
		case I915_TILING_NONE:
637
		case I915_TILING_NONE:
694
		case I915_TILING_X:
638
		case I915_TILING_X:
695
			break;
Line 639... Line 696...
639
			break;
696
		default:
640
		default:
697
			DRM_DEBUG_KMS("Unsupported tiling mode\n");
641
			return -EINVAL;
698
			return -EINVAL;
642
	}
699
	}
643
 
700
 
644
	/*
701
	/*
-
 
702
	 * FIXME the following code does a bunch of fuzzy adjustments to the
-
 
703
	 * coordinates and sizes. We probably need some way to decide whether
-
 
704
	 * more strict checking should be done instead.
-
 
705
	 */
-
 
706
	max_scale = intel_plane->max_downscale << 16;
-
 
707
	min_scale = intel_plane->can_scale ? 1 : (1 << 16);
-
 
708
 
-
 
709
	hscale = drm_rect_calc_hscale_relaxed(&src, &dst, min_scale, max_scale);
-
 
710
	BUG_ON(hscale < 0);
-
 
711
 
645
	 * Clamp the width & height into the visible area.  Note we don't
712
	vscale = drm_rect_calc_vscale_relaxed(&src, &dst, min_scale, max_scale);
646
	 * try to scale the source if part of the visible region is offscreen.
713
	BUG_ON(vscale < 0);
-
 
714
 
-
 
715
	visible = drm_rect_clip_scaled(&src, &dst, &clip, hscale, vscale);
-
 
716
 
-
 
717
	crtc_x = dst.x1;
-
 
718
	crtc_y = dst.y1;
-
 
719
	crtc_w = drm_rect_width(&dst);
-
 
720
	crtc_h = drm_rect_height(&dst);
-
 
721
 
-
 
722
	if (visible) {
-
 
723
		/* check again in case clipping clamped the results */
-
 
724
		hscale = drm_rect_calc_hscale(&src, &dst, min_scale, max_scale);
-
 
725
		if (hscale < 0) {
647
	 * The caller must handle that by adjusting source offset and size.
726
			DRM_DEBUG_KMS("Horizontal scaling factor out of limits\n");
648
	 */
-
 
649
	if ((crtc_x < 0) && ((crtc_x + crtc_w) > 0)) {
-
 
650
		crtc_w += crtc_x;
-
 
651
		crtc_x = 0;
-
 
Line 652... Line 727...
652
	}
727
			drm_rect_debug_print(&src, true);
653
	if ((crtc_x + crtc_w) <= 0) /* Nothing to display */
728
			drm_rect_debug_print(&dst, false);
-
 
729
 
-
 
730
			return hscale;
-
 
731
	}
-
 
732
 
654
		goto out;
733
		vscale = drm_rect_calc_vscale(&src, &dst, min_scale, max_scale);
655
	if ((crtc_x + crtc_w) > primary_w)
734
		if (vscale < 0) {
656
		crtc_w = primary_w - crtc_x;
-
 
657
 
-
 
658
	if ((crtc_y < 0) && ((crtc_y + crtc_h) > 0)) {
-
 
659
		crtc_h += crtc_y;
-
 
Line -... Line 735...
-
 
735
			DRM_DEBUG_KMS("Vertical scaling factor out of limits\n");
-
 
736
			drm_rect_debug_print(&src, true);
-
 
737
			drm_rect_debug_print(&dst, false);
-
 
738
 
-
 
739
			return vscale;
660
		crtc_y = 0;
740
	}
-
 
741
 
661
	}
742
		/* Make the source viewport size an exact multiple of the scaling factors. */
-
 
743
		drm_rect_adjust_size(&src,
-
 
744
				     drm_rect_width(&dst) * hscale - drm_rect_width(&src),
Line 662... Line 745...
662
	if ((crtc_y + crtc_h) <= 0) /* Nothing to display */
745
				     drm_rect_height(&dst) * vscale - drm_rect_height(&src));
-
 
746
 
-
 
747
		/* sanity check to make sure the src viewport wasn't enlarged */
663
		goto out;
748
		WARN_ON(src.x1 < (int) src_x ||
-
 
749
			src.y1 < (int) src_y ||
664
	if (crtc_y + crtc_h > primary_h)
750
			src.x2 > (int) (src_x + src_w) ||
-
 
751
			src.y2 > (int) (src_y + src_h));
665
		crtc_h = primary_h - crtc_y;
752
 
-
 
753
	/*
-
 
754
		 * Hardware doesn't handle subpixel coordinates.
-
 
755
		 * Adjust to (macro)pixel boundary, but be careful not to
-
 
756
		 * increase the source viewport size, because that could
-
 
757
		 * push the downscaling factor out of bounds.
666
 
758
	 */
Line 667... Line 759...
667
	if (!crtc_w || !crtc_h) /* Again, nothing to display */
759
		src_x = src.x1 >> 16;
668
		goto out;
760
		src_w = drm_rect_width(&src) >> 16;
669
 
761
		src_y = src.y1 >> 16;
670
	/*
762
		src_h = drm_rect_height(&src) >> 16;
-
 
763
 
-
 
764
		if (format_is_yuv(fb->pixel_format)) {
-
 
765
			src_x &= ~1;
-
 
766
			src_w &= ~1;
-
 
767
 
-
 
768
	/*
-
 
769
			 * Must keep src and dst the
-
 
770
			 * same if we can't scale.
-
 
771
	 */
671
	 * We may not have a scaler, eg. HSW does not have it any more
772
			if (!intel_plane->can_scale)
-
 
773
				crtc_w &= ~1;
-
 
774
 
-
 
775
			if (crtc_w == 0)
-
 
776
				visible = false;
-
 
777
		}
-
 
778
	}
-
 
779
 
-
 
780
	/* Check size restrictions when scaling */
-
 
781
	if (visible && (src_w != crtc_w || src_h != crtc_h)) {
-
 
782
		unsigned int width_bytes;
-
 
783
 
-
 
784
		WARN_ON(!intel_plane->can_scale);
-
 
785
 
-
 
786
		/* FIXME interlacing min height is 6 */
-
 
787
 
-
 
788
		if (crtc_w < 3 || crtc_h < 3)
-
 
789
			visible = false;
672
	 */
790
 
-
 
791
		if (src_w < 3 || src_h < 3)
-
 
792
			visible = false;
-
 
793
 
-
 
794
		width_bytes = ((src_x * pixel_size) & 63) + src_w * pixel_size;
-
 
795
 
-
 
796
		if (src_w > 2048 || src_h > 2048 ||
-
 
797
		    width_bytes > 4096 || fb->pitches[0] > 4096) {
Line 673... Line 798...
673
	if (!intel_plane->can_scale && (crtc_w != src_w || crtc_h != src_h))
798
			DRM_DEBUG_KMS("Source dimensions exceed hardware limits\n");
674
		return -EINVAL;
799
		return -EINVAL;
675
 
800
		}
676
	/*
801
	}
677
	 * We can take a larger source and scale it down, but
-
 
678
	 * only so much...  16x is the max on SNB.
802
 
679
	 */
803
	dst.x1 = crtc_x;
Line 680... Line 804...
680
	if (((src_w * src_h) / (crtc_w * crtc_h)) > intel_plane->max_downscale)
804
	dst.x2 = crtc_x + crtc_w;
Line 681... Line 805...
681
		return -EINVAL;
805
	dst.y1 = crtc_y;
682
 
806
	dst.y2 = crtc_y + crtc_h;
Line 706... Line 830...
706
	 * covering it fully.
830
	 * covering it fully.
707
	 */
831
	 */
708
	if (!disable_primary)
832
	if (!disable_primary)
709
		intel_enable_primary(crtc);
833
		intel_enable_primary(crtc);
Line -... Line 834...
-
 
834
 
710
 
835
	if (visible)
-
 
836
		intel_plane->update_plane(plane, crtc, fb, obj,
711
	intel_plane->update_plane(plane, fb, obj, crtc_x, crtc_y,
837
					  crtc_x, crtc_y, crtc_w, crtc_h,
-
 
838
					  src_x, src_y, src_w, src_h);
-
 
839
	else
Line 712... Line 840...
712
				  crtc_w, crtc_h, x, y, src_w, src_h);
840
		intel_plane->disable_plane(plane, crtc);
713
 
841
 
Line 714... Line 842...
714
	if (disable_primary)
842
	if (disable_primary)
Line 730... Line 858...
730
		intel_unpin_fb_obj(old_obj);
858
		intel_unpin_fb_obj(old_obj);
731
	}
859
	}
Line 732... Line 860...
732
 
860
 
733
out_unlock:
861
out_unlock:
734
	mutex_unlock(&dev->struct_mutex);
-
 
735
out:
862
	mutex_unlock(&dev->struct_mutex);
736
	return ret;
863
	return ret;
Line 737... Line 864...
737
}
864
}
738
 
865
 
739
static int
866
static int
740
intel_disable_plane(struct drm_plane *plane)
867
intel_disable_plane(struct drm_plane *plane)
741
{
868
{
742
	struct drm_device *dev = plane->dev;
869
	struct drm_device *dev = plane->dev;
Line 743... Line 870...
743
	struct intel_plane *intel_plane = to_intel_plane(plane);
870
	struct intel_plane *intel_plane = to_intel_plane(plane);
-
 
871
	int ret = 0;
-
 
872
 
-
 
873
	if (!plane->fb)
-
 
874
		return 0;
-
 
875
 
744
	int ret = 0;
876
	if (WARN_ON(!plane->crtc))
745
 
877
		return -EINVAL;
Line 746... Line 878...
746
	if (plane->crtc)
878
 
747
		intel_enable_primary(plane->crtc);
879
		intel_enable_primary(plane->crtc);
Line 748... Line 880...
748
	intel_plane->disable_plane(plane);
880
	intel_plane->disable_plane(plane, plane->crtc);
Line 843... Line 975...
843
			   intel_plane->crtc_w, intel_plane->crtc_h,
975
			   intel_plane->crtc_w, intel_plane->crtc_h,
844
			   intel_plane->src_x, intel_plane->src_y,
976
			   intel_plane->src_x, intel_plane->src_y,
845
			   intel_plane->src_w, intel_plane->src_h);
977
			   intel_plane->src_w, intel_plane->src_h);
846
}
978
}
Line -... Line 979...
-
 
979
 
-
 
980
void intel_plane_disable(struct drm_plane *plane)
-
 
981
{
-
 
982
	if (!plane->crtc || !plane->fb)
-
 
983
		return;
-
 
984
 
-
 
985
	intel_disable_plane(plane);
-
 
986
}
847
 
987
 
848
static const struct drm_plane_funcs intel_plane_funcs = {
988
static const struct drm_plane_funcs intel_plane_funcs = {
849
	.update_plane = intel_update_plane,
989
	.update_plane = intel_update_plane,
850
	.disable_plane = intel_disable_plane,
990
	.disable_plane = intel_disable_plane,
851
	.destroy = intel_destroy_plane,
991
	.destroy = intel_destroy_plane,
Line 916... Line 1056...
916
			num_plane_formats = ARRAY_SIZE(ilk_plane_formats);
1056
			num_plane_formats = ARRAY_SIZE(ilk_plane_formats);
917
		}
1057
		}
918
		break;
1058
		break;
Line 919... Line 1059...
919
 
1059
 
920
	case 7:
1060
	case 7:
921
		if (IS_HASWELL(dev) || IS_VALLEYVIEW(dev))
-
 
922
			intel_plane->can_scale = false;
-
 
923
		else
1061
		if (IS_IVYBRIDGE(dev)) {
-
 
1062
			intel_plane->can_scale = true;
-
 
1063
			intel_plane->max_downscale = 2;
-
 
1064
		} else {
-
 
1065
			intel_plane->can_scale = false;
-
 
1066
			intel_plane->max_downscale = 1;
Line 924... Line 1067...
924
			intel_plane->can_scale = true;
1067
		}
925
 
-
 
926
		if (IS_VALLEYVIEW(dev)) {
1068
 
927
			intel_plane->max_downscale = 1;
1069
		if (IS_VALLEYVIEW(dev)) {
928
			intel_plane->update_plane = vlv_update_plane;
1070
			intel_plane->update_plane = vlv_update_plane;
929
			intel_plane->disable_plane = vlv_disable_plane;
1071
			intel_plane->disable_plane = vlv_disable_plane;
Line 930... Line 1072...
930
			intel_plane->update_colorkey = vlv_update_colorkey;
1072
			intel_plane->update_colorkey = vlv_update_colorkey;
931
			intel_plane->get_colorkey = vlv_get_colorkey;
1073
			intel_plane->get_colorkey = vlv_get_colorkey;
932
 
1074
 
933
			plane_formats = vlv_plane_formats;
-
 
934
			num_plane_formats = ARRAY_SIZE(vlv_plane_formats);
1075
			plane_formats = vlv_plane_formats;
935
		} else {
1076
			num_plane_formats = ARRAY_SIZE(vlv_plane_formats);
936
		intel_plane->max_downscale = 2;
1077
		} else {
937
		intel_plane->update_plane = ivb_update_plane;
1078
		intel_plane->update_plane = ivb_update_plane;