Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/sparc-2.6
[pandora-kernel.git] / drivers / gpu / drm / i915 / intel_overlay.c
1 /*
2  * Copyright © 2009
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a
5  * copy of this software and associated documentation files (the "Software"),
6  * to deal in the Software without restriction, including without limitation
7  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8  * and/or sell copies of the Software, and to permit persons to whom the
9  * Software is furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice (including the next
12  * paragraph) shall be included in all copies or substantial portions of the
13  * Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21  * SOFTWARE.
22  *
23  * Authors:
24  *    Daniel Vetter <daniel@ffwll.ch>
25  *
26  * Derived from Xorg ddx, xf86-video-intel, src/i830_video.c
27  */
28
29 #include <linux/seq_file.h>
30 #include "drmP.h"
31 #include "drm.h"
32 #include "i915_drm.h"
33 #include "i915_drv.h"
34 #include "i915_reg.h"
35 #include "intel_drv.h"
36
37 /* Limits for overlay size. According to intel doc, the real limits are:
38  * Y width: 4095, UV width (planar): 2047, Y height: 2047,
39  * UV width (planar): * 1023. But the xorg thinks 2048 for height and width. Use
40  * the mininum of both.  */
41 #define IMAGE_MAX_WIDTH         2048
42 #define IMAGE_MAX_HEIGHT        2046 /* 2 * 1023 */
43 /* on 830 and 845 these large limits result in the card hanging */
44 #define IMAGE_MAX_WIDTH_LEGACY  1024
45 #define IMAGE_MAX_HEIGHT_LEGACY 1088
46
47 /* overlay register definitions */
48 /* OCMD register */
49 #define OCMD_TILED_SURFACE      (0x1<<19)
50 #define OCMD_MIRROR_MASK        (0x3<<17)
51 #define OCMD_MIRROR_MODE        (0x3<<17)
52 #define OCMD_MIRROR_HORIZONTAL  (0x1<<17)
53 #define OCMD_MIRROR_VERTICAL    (0x2<<17)
54 #define OCMD_MIRROR_BOTH        (0x3<<17)
55 #define OCMD_BYTEORDER_MASK     (0x3<<14) /* zero for YUYV or FOURCC YUY2 */
56 #define OCMD_UV_SWAP            (0x1<<14) /* YVYU */
57 #define OCMD_Y_SWAP             (0x2<<14) /* UYVY or FOURCC UYVY */
58 #define OCMD_Y_AND_UV_SWAP      (0x3<<14) /* VYUY */
59 #define OCMD_SOURCE_FORMAT_MASK (0xf<<10)
60 #define OCMD_RGB_888            (0x1<<10) /* not in i965 Intel docs */
61 #define OCMD_RGB_555            (0x2<<10) /* not in i965 Intel docs */
62 #define OCMD_RGB_565            (0x3<<10) /* not in i965 Intel docs */
63 #define OCMD_YUV_422_PACKED     (0x8<<10)
64 #define OCMD_YUV_411_PACKED     (0x9<<10) /* not in i965 Intel docs */
65 #define OCMD_YUV_420_PLANAR     (0xc<<10)
66 #define OCMD_YUV_422_PLANAR     (0xd<<10)
67 #define OCMD_YUV_410_PLANAR     (0xe<<10) /* also 411 */
68 #define OCMD_TVSYNCFLIP_PARITY  (0x1<<9)
69 #define OCMD_TVSYNCFLIP_ENABLE  (0x1<<7)
70 #define OCMD_BUF_TYPE_MASK      (0x1<<5)
71 #define OCMD_BUF_TYPE_FRAME     (0x0<<5)
72 #define OCMD_BUF_TYPE_FIELD     (0x1<<5)
73 #define OCMD_TEST_MODE          (0x1<<4)
74 #define OCMD_BUFFER_SELECT      (0x3<<2)
75 #define OCMD_BUFFER0            (0x0<<2)
76 #define OCMD_BUFFER1            (0x1<<2)
77 #define OCMD_FIELD_SELECT       (0x1<<2)
78 #define OCMD_FIELD0             (0x0<<1)
79 #define OCMD_FIELD1             (0x1<<1)
80 #define OCMD_ENABLE             (0x1<<0)
81
82 /* OCONFIG register */
83 #define OCONF_PIPE_MASK         (0x1<<18)
84 #define OCONF_PIPE_A            (0x0<<18)
85 #define OCONF_PIPE_B            (0x1<<18)
86 #define OCONF_GAMMA2_ENABLE     (0x1<<16)
87 #define OCONF_CSC_MODE_BT601    (0x0<<5)
88 #define OCONF_CSC_MODE_BT709    (0x1<<5)
89 #define OCONF_CSC_BYPASS        (0x1<<4)
90 #define OCONF_CC_OUT_8BIT       (0x1<<3)
91 #define OCONF_TEST_MODE         (0x1<<2)
92 #define OCONF_THREE_LINE_BUFFER (0x1<<0)
93 #define OCONF_TWO_LINE_BUFFER   (0x0<<0)
94
95 /* DCLRKM (dst-key) register */
96 #define DST_KEY_ENABLE          (0x1<<31)
97 #define CLK_RGB24_MASK          0x0
98 #define CLK_RGB16_MASK          0x070307
99 #define CLK_RGB15_MASK          0x070707
100 #define CLK_RGB8I_MASK          0xffffff
101
102 #define RGB16_TO_COLORKEY(c) \
103         (((c & 0xF800) << 8) | ((c & 0x07E0) << 5) | ((c & 0x001F) << 3))
104 #define RGB15_TO_COLORKEY(c) \
105         (((c & 0x7c00) << 9) | ((c & 0x03E0) << 6) | ((c & 0x001F) << 3))
106
107 /* overlay flip addr flag */
108 #define OFC_UPDATE              0x1
109
110 /* polyphase filter coefficients */
111 #define N_HORIZ_Y_TAPS          5
112 #define N_VERT_Y_TAPS           3
113 #define N_HORIZ_UV_TAPS         3
114 #define N_VERT_UV_TAPS          3
115 #define N_PHASES                17
116 #define MAX_TAPS                5
117
118 /* memory bufferd overlay registers */
119 struct overlay_registers {
120     u32 OBUF_0Y;
121     u32 OBUF_1Y;
122     u32 OBUF_0U;
123     u32 OBUF_0V;
124     u32 OBUF_1U;
125     u32 OBUF_1V;
126     u32 OSTRIDE;
127     u32 YRGB_VPH;
128     u32 UV_VPH;
129     u32 HORZ_PH;
130     u32 INIT_PHS;
131     u32 DWINPOS;
132     u32 DWINSZ;
133     u32 SWIDTH;
134     u32 SWIDTHSW;
135     u32 SHEIGHT;
136     u32 YRGBSCALE;
137     u32 UVSCALE;
138     u32 OCLRC0;
139     u32 OCLRC1;
140     u32 DCLRKV;
141     u32 DCLRKM;
142     u32 SCLRKVH;
143     u32 SCLRKVL;
144     u32 SCLRKEN;
145     u32 OCONFIG;
146     u32 OCMD;
147     u32 RESERVED1; /* 0x6C */
148     u32 OSTART_0Y;
149     u32 OSTART_1Y;
150     u32 OSTART_0U;
151     u32 OSTART_0V;
152     u32 OSTART_1U;
153     u32 OSTART_1V;
154     u32 OTILEOFF_0Y;
155     u32 OTILEOFF_1Y;
156     u32 OTILEOFF_0U;
157     u32 OTILEOFF_0V;
158     u32 OTILEOFF_1U;
159     u32 OTILEOFF_1V;
160     u32 FASTHSCALE; /* 0xA0 */
161     u32 UVSCALEV; /* 0xA4 */
162     u32 RESERVEDC[(0x200 - 0xA8) / 4]; /* 0xA8 - 0x1FC */
163     u16 Y_VCOEFS[N_VERT_Y_TAPS * N_PHASES]; /* 0x200 */
164     u16 RESERVEDD[0x100 / 2 - N_VERT_Y_TAPS * N_PHASES];
165     u16 Y_HCOEFS[N_HORIZ_Y_TAPS * N_PHASES]; /* 0x300 */
166     u16 RESERVEDE[0x200 / 2 - N_HORIZ_Y_TAPS * N_PHASES];
167     u16 UV_VCOEFS[N_VERT_UV_TAPS * N_PHASES]; /* 0x500 */
168     u16 RESERVEDF[0x100 / 2 - N_VERT_UV_TAPS * N_PHASES];
169     u16 UV_HCOEFS[N_HORIZ_UV_TAPS * N_PHASES]; /* 0x600 */
170     u16 RESERVEDG[0x100 / 2 - N_HORIZ_UV_TAPS * N_PHASES];
171 };
172
173 struct intel_overlay {
174         struct drm_device *dev;
175         struct intel_crtc *crtc;
176         struct drm_i915_gem_object *vid_bo;
177         struct drm_i915_gem_object *old_vid_bo;
178         int active;
179         int pfit_active;
180         u32 pfit_vscale_ratio; /* shifted-point number, (1<<12) == 1.0 */
181         u32 color_key;
182         u32 brightness, contrast, saturation;
183         u32 old_xscale, old_yscale;
184         /* register access */
185         u32 flip_addr;
186         struct drm_i915_gem_object *reg_bo;
187         /* flip handling */
188         uint32_t last_flip_req;
189         void (*flip_tail)(struct intel_overlay *);
190 };
191
192 static struct overlay_registers *
193 intel_overlay_map_regs(struct intel_overlay *overlay)
194 {
195         drm_i915_private_t *dev_priv = overlay->dev->dev_private;
196         struct overlay_registers *regs;
197
198         if (OVERLAY_NEEDS_PHYSICAL(overlay->dev))
199                 regs = overlay->reg_bo->phys_obj->handle->vaddr;
200         else
201                 regs = io_mapping_map_wc(dev_priv->mm.gtt_mapping,
202                                          overlay->reg_bo->gtt_offset);
203
204         return regs;
205 }
206
207 static void intel_overlay_unmap_regs(struct intel_overlay *overlay,
208                                      struct overlay_registers *regs)
209 {
210         if (!OVERLAY_NEEDS_PHYSICAL(overlay->dev))
211                 io_mapping_unmap(regs);
212 }
213
214 static int intel_overlay_do_wait_request(struct intel_overlay *overlay,
215                                          struct drm_i915_gem_request *request,
216                                          bool interruptible,
217                                          void (*tail)(struct intel_overlay *))
218 {
219         struct drm_device *dev = overlay->dev;
220         drm_i915_private_t *dev_priv = dev->dev_private;
221         int ret;
222
223         BUG_ON(overlay->last_flip_req);
224         overlay->last_flip_req =
225                 i915_add_request(dev, NULL, request, &dev_priv->render_ring);
226         if (overlay->last_flip_req == 0)
227                 return -ENOMEM;
228
229         overlay->flip_tail = tail;
230         ret = i915_do_wait_request(dev,
231                                    overlay->last_flip_req, true,
232                                    &dev_priv->render_ring);
233         if (ret)
234                 return ret;
235
236         overlay->last_flip_req = 0;
237         return 0;
238 }
239
240 /* Workaround for i830 bug where pipe a must be enable to change control regs */
241 static int
242 i830_activate_pipe_a(struct drm_device *dev)
243 {
244         drm_i915_private_t *dev_priv = dev->dev_private;
245         struct intel_crtc *crtc;
246         struct drm_crtc_helper_funcs *crtc_funcs;
247         struct drm_display_mode vesa_640x480 = {
248                 DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656,
249                          752, 800, 0, 480, 489, 492, 525, 0,
250                          DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC)
251         }, *mode;
252
253         crtc = to_intel_crtc(dev_priv->pipe_to_crtc_mapping[0]);
254         if (crtc->dpms_mode == DRM_MODE_DPMS_ON)
255                 return 0;
256
257         /* most i8xx have pipe a forced on, so don't trust dpms mode */
258         if (I915_READ(PIPEACONF) & PIPECONF_ENABLE)
259                 return 0;
260
261         crtc_funcs = crtc->base.helper_private;
262         if (crtc_funcs->dpms == NULL)
263                 return 0;
264
265         DRM_DEBUG_DRIVER("Enabling pipe A in order to enable overlay\n");
266
267         mode = drm_mode_duplicate(dev, &vesa_640x480);
268         drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
269         if(!drm_crtc_helper_set_mode(&crtc->base, mode,
270                                        crtc->base.x, crtc->base.y,
271                                        crtc->base.fb))
272                 return 0;
273
274         crtc_funcs->dpms(&crtc->base, DRM_MODE_DPMS_ON);
275         return 1;
276 }
277
278 static void
279 i830_deactivate_pipe_a(struct drm_device *dev)
280 {
281         drm_i915_private_t *dev_priv = dev->dev_private;
282         struct drm_crtc *crtc = dev_priv->pipe_to_crtc_mapping[0];
283         struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
284
285         crtc_funcs->dpms(crtc, DRM_MODE_DPMS_OFF);
286 }
287
288 /* overlay needs to be disable in OCMD reg */
289 static int intel_overlay_on(struct intel_overlay *overlay)
290 {
291         struct drm_device *dev = overlay->dev;
292         struct drm_i915_gem_request *request;
293         int pipe_a_quirk = 0;
294         int ret;
295
296         BUG_ON(overlay->active);
297         overlay->active = 1;
298
299         if (IS_I830(dev)) {
300                 pipe_a_quirk = i830_activate_pipe_a(dev);
301                 if (pipe_a_quirk < 0)
302                         return pipe_a_quirk;
303         }
304
305         request = kzalloc(sizeof(*request), GFP_KERNEL);
306         if (request == NULL) {
307                 ret = -ENOMEM;
308                 goto out;
309         }
310
311         BEGIN_LP_RING(4);
312         OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_ON);
313         OUT_RING(overlay->flip_addr | OFC_UPDATE);
314         OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP);
315         OUT_RING(MI_NOOP);
316         ADVANCE_LP_RING();
317
318         ret = intel_overlay_do_wait_request(overlay, request, true, NULL);
319 out:
320         if (pipe_a_quirk)
321                 i830_deactivate_pipe_a(dev);
322
323         return ret;
324 }
325
326 /* overlay needs to be enabled in OCMD reg */
327 static int intel_overlay_continue(struct intel_overlay *overlay,
328                                   bool load_polyphase_filter)
329 {
330         struct drm_device *dev = overlay->dev;
331         drm_i915_private_t *dev_priv = dev->dev_private;
332         struct drm_i915_gem_request *request;
333         u32 flip_addr = overlay->flip_addr;
334         u32 tmp;
335
336         BUG_ON(!overlay->active);
337
338         request = kzalloc(sizeof(*request), GFP_KERNEL);
339         if (request == NULL)
340                 return -ENOMEM;
341
342         if (load_polyphase_filter)
343                 flip_addr |= OFC_UPDATE;
344
345         /* check for underruns */
346         tmp = I915_READ(DOVSTA);
347         if (tmp & (1 << 17))
348                 DRM_DEBUG("overlay underrun, DOVSTA: %x\n", tmp);
349
350         BEGIN_LP_RING(2);
351         OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_CONTINUE);
352         OUT_RING(flip_addr);
353         ADVANCE_LP_RING();
354
355         overlay->last_flip_req =
356                 i915_add_request(dev, NULL, request, &dev_priv->render_ring);
357         return 0;
358 }
359
360 static void intel_overlay_release_old_vid_tail(struct intel_overlay *overlay)
361 {
362         struct drm_gem_object *obj = &overlay->old_vid_bo->base;
363
364         i915_gem_object_unpin(obj);
365         drm_gem_object_unreference(obj);
366
367         overlay->old_vid_bo = NULL;
368 }
369
370 static void intel_overlay_off_tail(struct intel_overlay *overlay)
371 {
372         struct drm_gem_object *obj;
373
374         /* never have the overlay hw on without showing a frame */
375         BUG_ON(!overlay->vid_bo);
376         obj = &overlay->vid_bo->base;
377
378         i915_gem_object_unpin(obj);
379         drm_gem_object_unreference(obj);
380         overlay->vid_bo = NULL;
381
382         overlay->crtc->overlay = NULL;
383         overlay->crtc = NULL;
384         overlay->active = 0;
385 }
386
387 /* overlay needs to be disabled in OCMD reg */
388 static int intel_overlay_off(struct intel_overlay *overlay,
389                              bool interruptible)
390 {
391         struct drm_device *dev = overlay->dev;
392         u32 flip_addr = overlay->flip_addr;
393         struct drm_i915_gem_request *request;
394
395         BUG_ON(!overlay->active);
396
397         request = kzalloc(sizeof(*request), GFP_KERNEL);
398         if (request == NULL)
399                 return -ENOMEM;
400
401         /* According to intel docs the overlay hw may hang (when switching
402          * off) without loading the filter coeffs. It is however unclear whether
403          * this applies to the disabling of the overlay or to the switching off
404          * of the hw. Do it in both cases */
405         flip_addr |= OFC_UPDATE;
406
407         BEGIN_LP_RING(6);
408         /* wait for overlay to go idle */
409         OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_CONTINUE);
410         OUT_RING(flip_addr);
411         OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP);
412         /* turn overlay off */
413         OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_OFF);
414         OUT_RING(flip_addr);
415         OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP);
416         ADVANCE_LP_RING();
417
418         return intel_overlay_do_wait_request(overlay, request, interruptible,
419                                              intel_overlay_off_tail);
420 }
421
422 /* recover from an interruption due to a signal
423  * We have to be careful not to repeat work forever an make forward progess. */
424 static int intel_overlay_recover_from_interrupt(struct intel_overlay *overlay,
425                                                 bool interruptible)
426 {
427         struct drm_device *dev = overlay->dev;
428         drm_i915_private_t *dev_priv = dev->dev_private;
429         int ret;
430
431         if (overlay->last_flip_req == 0)
432                 return 0;
433
434         ret = i915_do_wait_request(dev, overlay->last_flip_req,
435                                    interruptible, &dev_priv->render_ring);
436         if (ret)
437                 return ret;
438
439         if (overlay->flip_tail)
440                 overlay->flip_tail(overlay);
441
442         overlay->last_flip_req = 0;
443         return 0;
444 }
445
446 /* Wait for pending overlay flip and release old frame.
447  * Needs to be called before the overlay register are changed
448  * via intel_overlay_(un)map_regs
449  */
450 static int intel_overlay_release_old_vid(struct intel_overlay *overlay)
451 {
452         struct drm_device *dev = overlay->dev;
453         drm_i915_private_t *dev_priv = dev->dev_private;
454         int ret;
455
456         /* Only wait if there is actually an old frame to release to
457          * guarantee forward progress.
458          */
459         if (!overlay->old_vid_bo)
460                 return 0;
461
462         if (I915_READ(ISR) & I915_OVERLAY_PLANE_FLIP_PENDING_INTERRUPT) {
463                 struct drm_i915_gem_request *request;
464
465                 /* synchronous slowpath */
466                 request = kzalloc(sizeof(*request), GFP_KERNEL);
467                 if (request == NULL)
468                         return -ENOMEM;
469
470                 BEGIN_LP_RING(2);
471                 OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP);
472                 OUT_RING(MI_NOOP);
473                 ADVANCE_LP_RING();
474
475                 ret = intel_overlay_do_wait_request(overlay, request, true,
476                                                     intel_overlay_release_old_vid_tail);
477                 if (ret)
478                         return ret;
479         }
480
481         intel_overlay_release_old_vid_tail(overlay);
482         return 0;
483 }
484
485 struct put_image_params {
486         int format;
487         short dst_x;
488         short dst_y;
489         short dst_w;
490         short dst_h;
491         short src_w;
492         short src_scan_h;
493         short src_scan_w;
494         short src_h;
495         short stride_Y;
496         short stride_UV;
497         int offset_Y;
498         int offset_U;
499         int offset_V;
500 };
501
502 static int packed_depth_bytes(u32 format)
503 {
504         switch (format & I915_OVERLAY_DEPTH_MASK) {
505         case I915_OVERLAY_YUV422:
506                 return 4;
507         case I915_OVERLAY_YUV411:
508                 /* return 6; not implemented */
509         default:
510                 return -EINVAL;
511         }
512 }
513
514 static int packed_width_bytes(u32 format, short width)
515 {
516         switch (format & I915_OVERLAY_DEPTH_MASK) {
517         case I915_OVERLAY_YUV422:
518                 return width << 1;
519         default:
520                 return -EINVAL;
521         }
522 }
523
524 static int uv_hsubsampling(u32 format)
525 {
526         switch (format & I915_OVERLAY_DEPTH_MASK) {
527         case I915_OVERLAY_YUV422:
528         case I915_OVERLAY_YUV420:
529                 return 2;
530         case I915_OVERLAY_YUV411:
531         case I915_OVERLAY_YUV410:
532                 return 4;
533         default:
534                 return -EINVAL;
535         }
536 }
537
538 static int uv_vsubsampling(u32 format)
539 {
540         switch (format & I915_OVERLAY_DEPTH_MASK) {
541         case I915_OVERLAY_YUV420:
542         case I915_OVERLAY_YUV410:
543                 return 2;
544         case I915_OVERLAY_YUV422:
545         case I915_OVERLAY_YUV411:
546                 return 1;
547         default:
548                 return -EINVAL;
549         }
550 }
551
552 static u32 calc_swidthsw(struct drm_device *dev, u32 offset, u32 width)
553 {
554         u32 mask, shift, ret;
555         if (IS_GEN2(dev)) {
556                 mask = 0x1f;
557                 shift = 5;
558         } else {
559                 mask = 0x3f;
560                 shift = 6;
561         }
562         ret = ((offset + width + mask) >> shift) - (offset >> shift);
563         if (!IS_GEN2(dev))
564                 ret <<= 1;
565         ret -=1;
566         return ret << 2;
567 }
568
569 static const u16 y_static_hcoeffs[N_HORIZ_Y_TAPS * N_PHASES] = {
570         0x3000, 0xb4a0, 0x1930, 0x1920, 0xb4a0,
571         0x3000, 0xb500, 0x19d0, 0x1880, 0xb440,
572         0x3000, 0xb540, 0x1a88, 0x2f80, 0xb3e0,
573         0x3000, 0xb580, 0x1b30, 0x2e20, 0xb380,
574         0x3000, 0xb5c0, 0x1bd8, 0x2cc0, 0xb320,
575         0x3020, 0xb5e0, 0x1c60, 0x2b80, 0xb2c0,
576         0x3020, 0xb5e0, 0x1cf8, 0x2a20, 0xb260,
577         0x3020, 0xb5e0, 0x1d80, 0x28e0, 0xb200,
578         0x3020, 0xb5c0, 0x1e08, 0x3f40, 0xb1c0,
579         0x3020, 0xb580, 0x1e78, 0x3ce0, 0xb160,
580         0x3040, 0xb520, 0x1ed8, 0x3aa0, 0xb120,
581         0x3040, 0xb4a0, 0x1f30, 0x3880, 0xb0e0,
582         0x3040, 0xb400, 0x1f78, 0x3680, 0xb0a0,
583         0x3020, 0xb340, 0x1fb8, 0x34a0, 0xb060,
584         0x3020, 0xb240, 0x1fe0, 0x32e0, 0xb040,
585         0x3020, 0xb140, 0x1ff8, 0x3160, 0xb020,
586         0xb000, 0x3000, 0x0800, 0x3000, 0xb000
587 };
588
589 static const u16 uv_static_hcoeffs[N_HORIZ_UV_TAPS * N_PHASES] = {
590         0x3000, 0x1800, 0x1800, 0xb000, 0x18d0, 0x2e60,
591         0xb000, 0x1990, 0x2ce0, 0xb020, 0x1a68, 0x2b40,
592         0xb040, 0x1b20, 0x29e0, 0xb060, 0x1bd8, 0x2880,
593         0xb080, 0x1c88, 0x3e60, 0xb0a0, 0x1d28, 0x3c00,
594         0xb0c0, 0x1db8, 0x39e0, 0xb0e0, 0x1e40, 0x37e0,
595         0xb100, 0x1eb8, 0x3620, 0xb100, 0x1f18, 0x34a0,
596         0xb100, 0x1f68, 0x3360, 0xb0e0, 0x1fa8, 0x3240,
597         0xb0c0, 0x1fe0, 0x3140, 0xb060, 0x1ff0, 0x30a0,
598         0x3000, 0x0800, 0x3000
599 };
600
601 static void update_polyphase_filter(struct overlay_registers *regs)
602 {
603         memcpy(regs->Y_HCOEFS, y_static_hcoeffs, sizeof(y_static_hcoeffs));
604         memcpy(regs->UV_HCOEFS, uv_static_hcoeffs, sizeof(uv_static_hcoeffs));
605 }
606
607 static bool update_scaling_factors(struct intel_overlay *overlay,
608                                    struct overlay_registers *regs,
609                                    struct put_image_params *params)
610 {
611         /* fixed point with a 12 bit shift */
612         u32 xscale, yscale, xscale_UV, yscale_UV;
613 #define FP_SHIFT 12
614 #define FRACT_MASK 0xfff
615         bool scale_changed = false;
616         int uv_hscale = uv_hsubsampling(params->format);
617         int uv_vscale = uv_vsubsampling(params->format);
618
619         if (params->dst_w > 1)
620                 xscale = ((params->src_scan_w - 1) << FP_SHIFT)
621                         /(params->dst_w);
622         else
623                 xscale = 1 << FP_SHIFT;
624
625         if (params->dst_h > 1)
626                 yscale = ((params->src_scan_h - 1) << FP_SHIFT)
627                         /(params->dst_h);
628         else
629                 yscale = 1 << FP_SHIFT;
630
631         /*if (params->format & I915_OVERLAY_YUV_PLANAR) {*/
632         xscale_UV = xscale/uv_hscale;
633         yscale_UV = yscale/uv_vscale;
634         /* make the Y scale to UV scale ratio an exact multiply */
635         xscale = xscale_UV * uv_hscale;
636         yscale = yscale_UV * uv_vscale;
637         /*} else {
638           xscale_UV = 0;
639           yscale_UV = 0;
640           }*/
641
642         if (xscale != overlay->old_xscale || yscale != overlay->old_yscale)
643                 scale_changed = true;
644         overlay->old_xscale = xscale;
645         overlay->old_yscale = yscale;
646
647         regs->YRGBSCALE = (((yscale & FRACT_MASK) << 20) |
648                            ((xscale >> FP_SHIFT)  << 16) |
649                            ((xscale & FRACT_MASK) << 3));
650
651         regs->UVSCALE = (((yscale_UV & FRACT_MASK) << 20) |
652                          ((xscale_UV >> FP_SHIFT)  << 16) |
653                          ((xscale_UV & FRACT_MASK) << 3));
654
655         regs->UVSCALEV = ((((yscale    >> FP_SHIFT) << 16) |
656                            ((yscale_UV >> FP_SHIFT) << 0)));
657
658         if (scale_changed)
659                 update_polyphase_filter(regs);
660
661         return scale_changed;
662 }
663
664 static void update_colorkey(struct intel_overlay *overlay,
665                             struct overlay_registers *regs)
666 {
667         u32 key = overlay->color_key;
668
669         switch (overlay->crtc->base.fb->bits_per_pixel) {
670         case 8:
671                 regs->DCLRKV = 0;
672                 regs->DCLRKM = CLK_RGB8I_MASK | DST_KEY_ENABLE;
673                 break;
674
675         case 16:
676                 if (overlay->crtc->base.fb->depth == 15) {
677                         regs->DCLRKV = RGB15_TO_COLORKEY(key);
678                         regs->DCLRKM = CLK_RGB15_MASK | DST_KEY_ENABLE;
679                 } else {
680                         regs->DCLRKV = RGB16_TO_COLORKEY(key);
681                         regs->DCLRKM = CLK_RGB16_MASK | DST_KEY_ENABLE;
682                 }
683                 break;
684
685         case 24:
686         case 32:
687                 regs->DCLRKV = key;
688                 regs->DCLRKM = CLK_RGB24_MASK | DST_KEY_ENABLE;
689                 break;
690         }
691 }
692
693 static u32 overlay_cmd_reg(struct put_image_params *params)
694 {
695         u32 cmd = OCMD_ENABLE | OCMD_BUF_TYPE_FRAME | OCMD_BUFFER0;
696
697         if (params->format & I915_OVERLAY_YUV_PLANAR) {
698                 switch (params->format & I915_OVERLAY_DEPTH_MASK) {
699                 case I915_OVERLAY_YUV422:
700                         cmd |= OCMD_YUV_422_PLANAR;
701                         break;
702                 case I915_OVERLAY_YUV420:
703                         cmd |= OCMD_YUV_420_PLANAR;
704                         break;
705                 case I915_OVERLAY_YUV411:
706                 case I915_OVERLAY_YUV410:
707                         cmd |= OCMD_YUV_410_PLANAR;
708                         break;
709                 }
710         } else { /* YUV packed */
711                 switch (params->format & I915_OVERLAY_DEPTH_MASK) {
712                 case I915_OVERLAY_YUV422:
713                         cmd |= OCMD_YUV_422_PACKED;
714                         break;
715                 case I915_OVERLAY_YUV411:
716                         cmd |= OCMD_YUV_411_PACKED;
717                         break;
718                 }
719
720                 switch (params->format & I915_OVERLAY_SWAP_MASK) {
721                 case I915_OVERLAY_NO_SWAP:
722                         break;
723                 case I915_OVERLAY_UV_SWAP:
724                         cmd |= OCMD_UV_SWAP;
725                         break;
726                 case I915_OVERLAY_Y_SWAP:
727                         cmd |= OCMD_Y_SWAP;
728                         break;
729                 case I915_OVERLAY_Y_AND_UV_SWAP:
730                         cmd |= OCMD_Y_AND_UV_SWAP;
731                         break;
732                 }
733         }
734
735         return cmd;
736 }
737
738 static int intel_overlay_do_put_image(struct intel_overlay *overlay,
739                                       struct drm_gem_object *new_bo,
740                                       struct put_image_params *params)
741 {
742         int ret, tmp_width;
743         struct overlay_registers *regs;
744         bool scale_changed = false;
745         struct drm_i915_gem_object *bo_priv = to_intel_bo(new_bo);
746         struct drm_device *dev = overlay->dev;
747
748         BUG_ON(!mutex_is_locked(&dev->struct_mutex));
749         BUG_ON(!mutex_is_locked(&dev->mode_config.mutex));
750         BUG_ON(!overlay);
751
752         ret = intel_overlay_release_old_vid(overlay);
753         if (ret != 0)
754                 return ret;
755
756         ret = i915_gem_object_pin(new_bo, PAGE_SIZE);
757         if (ret != 0)
758                 return ret;
759
760         ret = i915_gem_object_set_to_gtt_domain(new_bo, 0);
761         if (ret != 0)
762                 goto out_unpin;
763
764         if (!overlay->active) {
765                 regs = intel_overlay_map_regs(overlay);
766                 if (!regs) {
767                         ret = -ENOMEM;
768                         goto out_unpin;
769                 }
770                 regs->OCONFIG = OCONF_CC_OUT_8BIT;
771                 if (IS_GEN4(overlay->dev))
772                         regs->OCONFIG |= OCONF_CSC_MODE_BT709;
773                 regs->OCONFIG |= overlay->crtc->pipe == 0 ?
774                         OCONF_PIPE_A : OCONF_PIPE_B;
775                 intel_overlay_unmap_regs(overlay, regs);
776
777                 ret = intel_overlay_on(overlay);
778                 if (ret != 0)
779                         goto out_unpin;
780         }
781
782         regs = intel_overlay_map_regs(overlay);
783         if (!regs) {
784                 ret = -ENOMEM;
785                 goto out_unpin;
786         }
787
788         regs->DWINPOS = (params->dst_y << 16) | params->dst_x;
789         regs->DWINSZ = (params->dst_h << 16) | params->dst_w;
790
791         if (params->format & I915_OVERLAY_YUV_PACKED)
792                 tmp_width = packed_width_bytes(params->format, params->src_w);
793         else
794                 tmp_width = params->src_w;
795
796         regs->SWIDTH = params->src_w;
797         regs->SWIDTHSW = calc_swidthsw(overlay->dev,
798                                        params->offset_Y, tmp_width);
799         regs->SHEIGHT = params->src_h;
800         regs->OBUF_0Y = bo_priv->gtt_offset + params-> offset_Y;
801         regs->OSTRIDE = params->stride_Y;
802
803         if (params->format & I915_OVERLAY_YUV_PLANAR) {
804                 int uv_hscale = uv_hsubsampling(params->format);
805                 int uv_vscale = uv_vsubsampling(params->format);
806                 u32 tmp_U, tmp_V;
807                 regs->SWIDTH |= (params->src_w/uv_hscale) << 16;
808                 tmp_U = calc_swidthsw(overlay->dev, params->offset_U,
809                                       params->src_w/uv_hscale);
810                 tmp_V = calc_swidthsw(overlay->dev, params->offset_V,
811                                       params->src_w/uv_hscale);
812                 regs->SWIDTHSW |= max_t(u32, tmp_U, tmp_V) << 16;
813                 regs->SHEIGHT |= (params->src_h/uv_vscale) << 16;
814                 regs->OBUF_0U = bo_priv->gtt_offset + params->offset_U;
815                 regs->OBUF_0V = bo_priv->gtt_offset + params->offset_V;
816                 regs->OSTRIDE |= params->stride_UV << 16;
817         }
818
819         scale_changed = update_scaling_factors(overlay, regs, params);
820
821         update_colorkey(overlay, regs);
822
823         regs->OCMD = overlay_cmd_reg(params);
824
825         intel_overlay_unmap_regs(overlay, regs);
826
827         ret = intel_overlay_continue(overlay, scale_changed);
828         if (ret)
829                 goto out_unpin;
830
831         overlay->old_vid_bo = overlay->vid_bo;
832         overlay->vid_bo = to_intel_bo(new_bo);
833
834         return 0;
835
836 out_unpin:
837         i915_gem_object_unpin(new_bo);
838         return ret;
839 }
840
841 int intel_overlay_switch_off(struct intel_overlay *overlay,
842                              bool interruptible)
843 {
844         struct overlay_registers *regs;
845         struct drm_device *dev = overlay->dev;
846         int ret;
847
848         BUG_ON(!mutex_is_locked(&dev->struct_mutex));
849         BUG_ON(!mutex_is_locked(&dev->mode_config.mutex));
850
851         ret = intel_overlay_recover_from_interrupt(overlay, interruptible);
852         if (ret != 0)
853                 return ret;
854
855         if (!overlay->active)
856                 return 0;
857
858         ret = intel_overlay_release_old_vid(overlay);
859         if (ret != 0)
860                 return ret;
861
862         regs = intel_overlay_map_regs(overlay);
863         regs->OCMD = 0;
864         intel_overlay_unmap_regs(overlay, regs);
865
866         ret = intel_overlay_off(overlay, interruptible);
867         if (ret != 0)
868                 return ret;
869
870         intel_overlay_off_tail(overlay);
871         return 0;
872 }
873
874 static int check_overlay_possible_on_crtc(struct intel_overlay *overlay,
875                                           struct intel_crtc *crtc)
876 {
877         drm_i915_private_t *dev_priv = overlay->dev->dev_private;
878
879         if (!crtc->active)
880                 return -EINVAL;
881
882         /* can't use the overlay with double wide pipe */
883         if (INTEL_INFO(overlay->dev)->gen < 4 &&
884             (I915_READ(PIPECONF(crtc->pipe)) & (PIPECONF_DOUBLE_WIDE | PIPECONF_ENABLE)) != PIPECONF_ENABLE)
885                 return -EINVAL;
886
887         return 0;
888 }
889
890 static void update_pfit_vscale_ratio(struct intel_overlay *overlay)
891 {
892         struct drm_device *dev = overlay->dev;
893         drm_i915_private_t *dev_priv = dev->dev_private;
894         u32 pfit_control = I915_READ(PFIT_CONTROL);
895         u32 ratio;
896
897         /* XXX: This is not the same logic as in the xorg driver, but more in
898          * line with the intel documentation for the i965
899          */
900         if (INTEL_INFO(dev)->gen >= 4) {
901                 /* on i965 use the PGM reg to read out the autoscaler values */
902                 ratio = I915_READ(PFIT_PGM_RATIOS) >> PFIT_VERT_SCALE_SHIFT_965;
903         } else {
904                 if (pfit_control & VERT_AUTO_SCALE)
905                         ratio = I915_READ(PFIT_AUTO_RATIOS);
906                 else
907                         ratio = I915_READ(PFIT_PGM_RATIOS);
908                 ratio >>= PFIT_VERT_SCALE_SHIFT;
909         }
910
911         overlay->pfit_vscale_ratio = ratio;
912 }
913
914 static int check_overlay_dst(struct intel_overlay *overlay,
915                              struct drm_intel_overlay_put_image *rec)
916 {
917         struct drm_display_mode *mode = &overlay->crtc->base.mode;
918
919         if (rec->dst_x < mode->crtc_hdisplay &&
920             rec->dst_x + rec->dst_width <= mode->crtc_hdisplay &&
921             rec->dst_y < mode->crtc_vdisplay &&
922             rec->dst_y + rec->dst_height <= mode->crtc_vdisplay)
923                 return 0;
924         else
925                 return -EINVAL;
926 }
927
928 static int check_overlay_scaling(struct put_image_params *rec)
929 {
930         u32 tmp;
931
932         /* downscaling limit is 8.0 */
933         tmp = ((rec->src_scan_h << 16) / rec->dst_h) >> 16;
934         if (tmp > 7)
935                 return -EINVAL;
936         tmp = ((rec->src_scan_w << 16) / rec->dst_w) >> 16;
937         if (tmp > 7)
938                 return -EINVAL;
939
940         return 0;
941 }
942
943 static int check_overlay_src(struct drm_device *dev,
944                              struct drm_intel_overlay_put_image *rec,
945                              struct drm_gem_object *new_bo)
946 {
947         int uv_hscale = uv_hsubsampling(rec->flags);
948         int uv_vscale = uv_vsubsampling(rec->flags);
949         u32 stride_mask, depth, tmp;
950
951         /* check src dimensions */
952         if (IS_845G(dev) || IS_I830(dev)) {
953                 if (rec->src_height > IMAGE_MAX_HEIGHT_LEGACY ||
954                     rec->src_width  > IMAGE_MAX_WIDTH_LEGACY)
955                         return -EINVAL;
956         } else {
957                 if (rec->src_height > IMAGE_MAX_HEIGHT ||
958                     rec->src_width  > IMAGE_MAX_WIDTH)
959                         return -EINVAL;
960         }
961
962         /* better safe than sorry, use 4 as the maximal subsampling ratio */
963         if (rec->src_height < N_VERT_Y_TAPS*4 ||
964             rec->src_width  < N_HORIZ_Y_TAPS*4)
965                 return -EINVAL;
966
967         /* check alignment constraints */
968         switch (rec->flags & I915_OVERLAY_TYPE_MASK) {
969         case I915_OVERLAY_RGB:
970                 /* not implemented */
971                 return -EINVAL;
972
973         case I915_OVERLAY_YUV_PACKED:
974                 if (uv_vscale != 1)
975                         return -EINVAL;
976
977                 depth = packed_depth_bytes(rec->flags);
978                 if (depth < 0)
979                         return depth;
980
981                 /* ignore UV planes */
982                 rec->stride_UV = 0;
983                 rec->offset_U = 0;
984                 rec->offset_V = 0;
985                 /* check pixel alignment */
986                 if (rec->offset_Y % depth)
987                         return -EINVAL;
988                 break;
989
990         case I915_OVERLAY_YUV_PLANAR:
991                 if (uv_vscale < 0 || uv_hscale < 0)
992                         return -EINVAL;
993                 /* no offset restrictions for planar formats */
994                 break;
995
996         default:
997                 return -EINVAL;
998         }
999
1000         if (rec->src_width % uv_hscale)
1001                 return -EINVAL;
1002
1003         /* stride checking */
1004         if (IS_I830(dev) || IS_845G(dev))
1005                 stride_mask = 255;
1006         else
1007                 stride_mask = 63;
1008
1009         if (rec->stride_Y & stride_mask || rec->stride_UV & stride_mask)
1010                 return -EINVAL;
1011         if (IS_GEN4(dev) && rec->stride_Y < 512)
1012                 return -EINVAL;
1013
1014         tmp = (rec->flags & I915_OVERLAY_TYPE_MASK) == I915_OVERLAY_YUV_PLANAR ?
1015                 4096 : 8192;
1016         if (rec->stride_Y > tmp || rec->stride_UV > 2*1024)
1017                 return -EINVAL;
1018
1019         /* check buffer dimensions */
1020         switch (rec->flags & I915_OVERLAY_TYPE_MASK) {
1021         case I915_OVERLAY_RGB:
1022         case I915_OVERLAY_YUV_PACKED:
1023                 /* always 4 Y values per depth pixels */
1024                 if (packed_width_bytes(rec->flags, rec->src_width) > rec->stride_Y)
1025                         return -EINVAL;
1026
1027                 tmp = rec->stride_Y*rec->src_height;
1028                 if (rec->offset_Y + tmp > new_bo->size)
1029                         return -EINVAL;
1030                 break;
1031
1032         case I915_OVERLAY_YUV_PLANAR:
1033                 if (rec->src_width > rec->stride_Y)
1034                         return -EINVAL;
1035                 if (rec->src_width/uv_hscale > rec->stride_UV)
1036                         return -EINVAL;
1037
1038                 tmp = rec->stride_Y * rec->src_height;
1039                 if (rec->offset_Y + tmp > new_bo->size)
1040                         return -EINVAL;
1041
1042                 tmp = rec->stride_UV * (rec->src_height / uv_vscale);
1043                 if (rec->offset_U + tmp > new_bo->size ||
1044                     rec->offset_V + tmp > new_bo->size)
1045                         return -EINVAL;
1046                 break;
1047         }
1048
1049         return 0;
1050 }
1051
1052 /**
1053  * Return the pipe currently connected to the panel fitter,
1054  * or -1 if the panel fitter is not present or not in use
1055  */
1056 static int intel_panel_fitter_pipe(struct drm_device *dev)
1057 {
1058         struct drm_i915_private *dev_priv = dev->dev_private;
1059         u32  pfit_control;
1060
1061         /* i830 doesn't have a panel fitter */
1062         if (IS_I830(dev))
1063                 return -1;
1064
1065         pfit_control = I915_READ(PFIT_CONTROL);
1066
1067         /* See if the panel fitter is in use */
1068         if ((pfit_control & PFIT_ENABLE) == 0)
1069                 return -1;
1070
1071         /* 965 can place panel fitter on either pipe */
1072         if (IS_GEN4(dev))
1073                 return (pfit_control >> 29) & 0x3;
1074
1075         /* older chips can only use pipe 1 */
1076         return 1;
1077 }
1078
1079 int intel_overlay_put_image(struct drm_device *dev, void *data,
1080                             struct drm_file *file_priv)
1081 {
1082         struct drm_intel_overlay_put_image *put_image_rec = data;
1083         drm_i915_private_t *dev_priv = dev->dev_private;
1084         struct intel_overlay *overlay;
1085         struct drm_mode_object *drmmode_obj;
1086         struct intel_crtc *crtc;
1087         struct drm_gem_object *new_bo;
1088         struct put_image_params *params;
1089         int ret;
1090
1091         if (!dev_priv) {
1092                 DRM_ERROR("called with no initialization\n");
1093                 return -EINVAL;
1094         }
1095
1096         overlay = dev_priv->overlay;
1097         if (!overlay) {
1098                 DRM_DEBUG("userspace bug: no overlay\n");
1099                 return -ENODEV;
1100         }
1101
1102         if (!(put_image_rec->flags & I915_OVERLAY_ENABLE)) {
1103                 mutex_lock(&dev->mode_config.mutex);
1104                 mutex_lock(&dev->struct_mutex);
1105
1106                 ret = intel_overlay_switch_off(overlay, true);
1107
1108                 mutex_unlock(&dev->struct_mutex);
1109                 mutex_unlock(&dev->mode_config.mutex);
1110
1111                 return ret;
1112         }
1113
1114         params = kmalloc(sizeof(struct put_image_params), GFP_KERNEL);
1115         if (!params)
1116                 return -ENOMEM;
1117
1118         drmmode_obj = drm_mode_object_find(dev, put_image_rec->crtc_id,
1119                                            DRM_MODE_OBJECT_CRTC);
1120         if (!drmmode_obj) {
1121                 ret = -ENOENT;
1122                 goto out_free;
1123         }
1124         crtc = to_intel_crtc(obj_to_crtc(drmmode_obj));
1125
1126         new_bo = drm_gem_object_lookup(dev, file_priv,
1127                                        put_image_rec->bo_handle);
1128         if (!new_bo) {
1129                 ret = -ENOENT;
1130                 goto out_free;
1131         }
1132
1133         mutex_lock(&dev->mode_config.mutex);
1134         mutex_lock(&dev->struct_mutex);
1135
1136         ret = intel_overlay_recover_from_interrupt(overlay, true);
1137         if (ret != 0)
1138                 goto out_unlock;
1139
1140         if (overlay->crtc != crtc) {
1141                 struct drm_display_mode *mode = &crtc->base.mode;
1142                 ret = intel_overlay_switch_off(overlay, true);
1143                 if (ret != 0)
1144                         goto out_unlock;
1145
1146                 ret = check_overlay_possible_on_crtc(overlay, crtc);
1147                 if (ret != 0)
1148                         goto out_unlock;
1149
1150                 overlay->crtc = crtc;
1151                 crtc->overlay = overlay;
1152
1153                 /* line too wide, i.e. one-line-mode */
1154                 if (mode->hdisplay > 1024 &&
1155                     intel_panel_fitter_pipe(dev) == crtc->pipe) {
1156                         overlay->pfit_active = 1;
1157                         update_pfit_vscale_ratio(overlay);
1158                 } else
1159                         overlay->pfit_active = 0;
1160         }
1161
1162         ret = check_overlay_dst(overlay, put_image_rec);
1163         if (ret != 0)
1164                 goto out_unlock;
1165
1166         if (overlay->pfit_active) {
1167                 params->dst_y = ((((u32)put_image_rec->dst_y) << 12) /
1168                                  overlay->pfit_vscale_ratio);
1169                 /* shifting right rounds downwards, so add 1 */
1170                 params->dst_h = ((((u32)put_image_rec->dst_height) << 12) /
1171                                  overlay->pfit_vscale_ratio) + 1;
1172         } else {
1173                 params->dst_y = put_image_rec->dst_y;
1174                 params->dst_h = put_image_rec->dst_height;
1175         }
1176         params->dst_x = put_image_rec->dst_x;
1177         params->dst_w = put_image_rec->dst_width;
1178
1179         params->src_w = put_image_rec->src_width;
1180         params->src_h = put_image_rec->src_height;
1181         params->src_scan_w = put_image_rec->src_scan_width;
1182         params->src_scan_h = put_image_rec->src_scan_height;
1183         if (params->src_scan_h > params->src_h ||
1184             params->src_scan_w > params->src_w) {
1185                 ret = -EINVAL;
1186                 goto out_unlock;
1187         }
1188
1189         ret = check_overlay_src(dev, put_image_rec, new_bo);
1190         if (ret != 0)
1191                 goto out_unlock;
1192         params->format = put_image_rec->flags & ~I915_OVERLAY_FLAGS_MASK;
1193         params->stride_Y = put_image_rec->stride_Y;
1194         params->stride_UV = put_image_rec->stride_UV;
1195         params->offset_Y = put_image_rec->offset_Y;
1196         params->offset_U = put_image_rec->offset_U;
1197         params->offset_V = put_image_rec->offset_V;
1198
1199         /* Check scaling after src size to prevent a divide-by-zero. */
1200         ret = check_overlay_scaling(params);
1201         if (ret != 0)
1202                 goto out_unlock;
1203
1204         ret = intel_overlay_do_put_image(overlay, new_bo, params);
1205         if (ret != 0)
1206                 goto out_unlock;
1207
1208         mutex_unlock(&dev->struct_mutex);
1209         mutex_unlock(&dev->mode_config.mutex);
1210
1211         kfree(params);
1212
1213         return 0;
1214
1215 out_unlock:
1216         mutex_unlock(&dev->struct_mutex);
1217         mutex_unlock(&dev->mode_config.mutex);
1218         drm_gem_object_unreference_unlocked(new_bo);
1219 out_free:
1220         kfree(params);
1221
1222         return ret;
1223 }
1224
1225 static void update_reg_attrs(struct intel_overlay *overlay,
1226                              struct overlay_registers *regs)
1227 {
1228         regs->OCLRC0 = (overlay->contrast << 18) | (overlay->brightness & 0xff);
1229         regs->OCLRC1 = overlay->saturation;
1230 }
1231
1232 static bool check_gamma_bounds(u32 gamma1, u32 gamma2)
1233 {
1234         int i;
1235
1236         if (gamma1 & 0xff000000 || gamma2 & 0xff000000)
1237                 return false;
1238
1239         for (i = 0; i < 3; i++) {
1240                 if (((gamma1 >> i*8) & 0xff) >= ((gamma2 >> i*8) & 0xff))
1241                         return false;
1242         }
1243
1244         return true;
1245 }
1246
1247 static bool check_gamma5_errata(u32 gamma5)
1248 {
1249         int i;
1250
1251         for (i = 0; i < 3; i++) {
1252                 if (((gamma5 >> i*8) & 0xff) == 0x80)
1253                         return false;
1254         }
1255
1256         return true;
1257 }
1258
1259 static int check_gamma(struct drm_intel_overlay_attrs *attrs)
1260 {
1261         if (!check_gamma_bounds(0, attrs->gamma0) ||
1262             !check_gamma_bounds(attrs->gamma0, attrs->gamma1) ||
1263             !check_gamma_bounds(attrs->gamma1, attrs->gamma2) ||
1264             !check_gamma_bounds(attrs->gamma2, attrs->gamma3) ||
1265             !check_gamma_bounds(attrs->gamma3, attrs->gamma4) ||
1266             !check_gamma_bounds(attrs->gamma4, attrs->gamma5) ||
1267             !check_gamma_bounds(attrs->gamma5, 0x00ffffff))
1268                 return -EINVAL;
1269
1270         if (!check_gamma5_errata(attrs->gamma5))
1271                 return -EINVAL;
1272
1273         return 0;
1274 }
1275
1276 int intel_overlay_attrs(struct drm_device *dev, void *data,
1277                         struct drm_file *file_priv)
1278 {
1279         struct drm_intel_overlay_attrs *attrs = data;
1280         drm_i915_private_t *dev_priv = dev->dev_private;
1281         struct intel_overlay *overlay;
1282         struct overlay_registers *regs;
1283         int ret;
1284
1285         if (!dev_priv) {
1286                 DRM_ERROR("called with no initialization\n");
1287                 return -EINVAL;
1288         }
1289
1290         overlay = dev_priv->overlay;
1291         if (!overlay) {
1292                 DRM_DEBUG("userspace bug: no overlay\n");
1293                 return -ENODEV;
1294         }
1295
1296         mutex_lock(&dev->mode_config.mutex);
1297         mutex_lock(&dev->struct_mutex);
1298
1299         ret = -EINVAL;
1300         if (!(attrs->flags & I915_OVERLAY_UPDATE_ATTRS)) {
1301                 attrs->color_key  = overlay->color_key;
1302                 attrs->brightness = overlay->brightness;
1303                 attrs->contrast   = overlay->contrast;
1304                 attrs->saturation = overlay->saturation;
1305
1306                 if (!IS_GEN2(dev)) {
1307                         attrs->gamma0 = I915_READ(OGAMC0);
1308                         attrs->gamma1 = I915_READ(OGAMC1);
1309                         attrs->gamma2 = I915_READ(OGAMC2);
1310                         attrs->gamma3 = I915_READ(OGAMC3);
1311                         attrs->gamma4 = I915_READ(OGAMC4);
1312                         attrs->gamma5 = I915_READ(OGAMC5);
1313                 }
1314         } else {
1315                 if (attrs->brightness < -128 || attrs->brightness > 127)
1316                         goto out_unlock;
1317                 if (attrs->contrast > 255)
1318                         goto out_unlock;
1319                 if (attrs->saturation > 1023)
1320                         goto out_unlock;
1321
1322                 overlay->color_key  = attrs->color_key;
1323                 overlay->brightness = attrs->brightness;
1324                 overlay->contrast   = attrs->contrast;
1325                 overlay->saturation = attrs->saturation;
1326
1327                 regs = intel_overlay_map_regs(overlay);
1328                 if (!regs) {
1329                         ret = -ENOMEM;
1330                         goto out_unlock;
1331                 }
1332
1333                 update_reg_attrs(overlay, regs);
1334
1335                 intel_overlay_unmap_regs(overlay, regs);
1336
1337                 if (attrs->flags & I915_OVERLAY_UPDATE_GAMMA) {
1338                         if (IS_GEN2(dev))
1339                                 goto out_unlock;
1340
1341                         if (overlay->active) {
1342                                 ret = -EBUSY;
1343                                 goto out_unlock;
1344                         }
1345
1346                         ret = check_gamma(attrs);
1347                         if (ret)
1348                                 goto out_unlock;
1349
1350                         I915_WRITE(OGAMC0, attrs->gamma0);
1351                         I915_WRITE(OGAMC1, attrs->gamma1);
1352                         I915_WRITE(OGAMC2, attrs->gamma2);
1353                         I915_WRITE(OGAMC3, attrs->gamma3);
1354                         I915_WRITE(OGAMC4, attrs->gamma4);
1355                         I915_WRITE(OGAMC5, attrs->gamma5);
1356                 }
1357         }
1358
1359         ret = 0;
1360 out_unlock:
1361         mutex_unlock(&dev->struct_mutex);
1362         mutex_unlock(&dev->mode_config.mutex);
1363
1364         return ret;
1365 }
1366
1367 void intel_setup_overlay(struct drm_device *dev)
1368 {
1369         drm_i915_private_t *dev_priv = dev->dev_private;
1370         struct intel_overlay *overlay;
1371         struct drm_gem_object *reg_bo;
1372         struct overlay_registers *regs;
1373         int ret;
1374
1375         if (!HAS_OVERLAY(dev))
1376                 return;
1377
1378         overlay = kzalloc(sizeof(struct intel_overlay), GFP_KERNEL);
1379         if (!overlay)
1380                 return;
1381         overlay->dev = dev;
1382
1383         reg_bo = i915_gem_alloc_object(dev, PAGE_SIZE);
1384         if (!reg_bo)
1385                 goto out_free;
1386         overlay->reg_bo = to_intel_bo(reg_bo);
1387
1388         if (OVERLAY_NEEDS_PHYSICAL(dev)) {
1389                 ret = i915_gem_attach_phys_object(dev, reg_bo,
1390                                                   I915_GEM_PHYS_OVERLAY_REGS,
1391                                                   PAGE_SIZE);
1392                 if (ret) {
1393                         DRM_ERROR("failed to attach phys overlay regs\n");
1394                         goto out_free_bo;
1395                 }
1396                 overlay->flip_addr = overlay->reg_bo->phys_obj->handle->busaddr;
1397         } else {
1398                 ret = i915_gem_object_pin(reg_bo, PAGE_SIZE);
1399                 if (ret) {
1400                         DRM_ERROR("failed to pin overlay register bo\n");
1401                         goto out_free_bo;
1402                 }
1403                 overlay->flip_addr = overlay->reg_bo->gtt_offset;
1404
1405                 ret = i915_gem_object_set_to_gtt_domain(reg_bo, true);
1406                 if (ret) {
1407                         DRM_ERROR("failed to move overlay register bo into the GTT\n");
1408                         goto out_unpin_bo;
1409                 }
1410         }
1411
1412         /* init all values */
1413         overlay->color_key = 0x0101fe;
1414         overlay->brightness = -19;
1415         overlay->contrast = 75;
1416         overlay->saturation = 146;
1417
1418         regs = intel_overlay_map_regs(overlay);
1419         if (!regs)
1420                 goto out_free_bo;
1421
1422         memset(regs, 0, sizeof(struct overlay_registers));
1423         update_polyphase_filter(regs);
1424         update_reg_attrs(overlay, regs);
1425
1426         intel_overlay_unmap_regs(overlay, regs);
1427
1428         dev_priv->overlay = overlay;
1429         DRM_INFO("initialized overlay support\n");
1430         return;
1431
1432 out_unpin_bo:
1433         i915_gem_object_unpin(reg_bo);
1434 out_free_bo:
1435         drm_gem_object_unreference(reg_bo);
1436 out_free:
1437         kfree(overlay);
1438         return;
1439 }
1440
1441 void intel_cleanup_overlay(struct drm_device *dev)
1442 {
1443         drm_i915_private_t *dev_priv = dev->dev_private;
1444
1445         if (!dev_priv->overlay)
1446                 return;
1447
1448         /* The bo's should be free'd by the generic code already.
1449          * Furthermore modesetting teardown happens beforehand so the
1450          * hardware should be off already */
1451         BUG_ON(dev_priv->overlay->active);
1452
1453         drm_gem_object_unreference_unlocked(&dev_priv->overlay->reg_bo->base);
1454         kfree(dev_priv->overlay);
1455 }
1456
1457 #ifdef CONFIG_DEBUG_FS
1458 #include <linux/seq_file.h>
1459
1460 struct intel_overlay_error_state {
1461         struct overlay_registers regs;
1462         unsigned long base;
1463         u32 dovsta;
1464         u32 isr;
1465 };
1466
1467 static struct overlay_registers *
1468 intel_overlay_map_regs_atomic(struct intel_overlay *overlay)
1469 {
1470         drm_i915_private_t *dev_priv = overlay->dev->dev_private;
1471         struct overlay_registers *regs;
1472
1473         if (OVERLAY_NEEDS_PHYSICAL(overlay->dev))
1474                 regs = overlay->reg_bo->phys_obj->handle->vaddr;
1475         else
1476                 regs = io_mapping_map_atomic_wc(dev_priv->mm.gtt_mapping,
1477                                                 overlay->reg_bo->gtt_offset);
1478
1479         return regs;
1480 }
1481
1482 static void intel_overlay_unmap_regs_atomic(struct intel_overlay *overlay,
1483                                             struct overlay_registers *regs)
1484 {
1485         if (!OVERLAY_NEEDS_PHYSICAL(overlay->dev))
1486                 io_mapping_unmap_atomic(regs);
1487 }
1488
1489
1490 struct intel_overlay_error_state *
1491 intel_overlay_capture_error_state(struct drm_device *dev)
1492 {
1493         drm_i915_private_t *dev_priv = dev->dev_private;
1494         struct intel_overlay *overlay = dev_priv->overlay;
1495         struct intel_overlay_error_state *error;
1496         struct overlay_registers __iomem *regs;
1497
1498         if (!overlay || !overlay->active)
1499                 return NULL;
1500
1501         error = kmalloc(sizeof(*error), GFP_ATOMIC);
1502         if (error == NULL)
1503                 return NULL;
1504
1505         error->dovsta = I915_READ(DOVSTA);
1506         error->isr = I915_READ(ISR);
1507         if (OVERLAY_NEEDS_PHYSICAL(overlay->dev))
1508                 error->base = (long) overlay->reg_bo->phys_obj->handle->vaddr;
1509         else
1510                 error->base = (long) overlay->reg_bo->gtt_offset;
1511
1512         regs = intel_overlay_map_regs_atomic(overlay);
1513         if (!regs)
1514                 goto err;
1515
1516         memcpy_fromio(&error->regs, regs, sizeof(struct overlay_registers));
1517         intel_overlay_unmap_regs_atomic(overlay, regs);
1518
1519         return error;
1520
1521 err:
1522         kfree(error);
1523         return NULL;
1524 }
1525
1526 void
1527 intel_overlay_print_error_state(struct seq_file *m, struct intel_overlay_error_state *error)
1528 {
1529         seq_printf(m, "Overlay, status: 0x%08x, interrupt: 0x%08x\n",
1530                    error->dovsta, error->isr);
1531         seq_printf(m, "  Register file at 0x%08lx:\n",
1532                    error->base);
1533
1534 #define P(x) seq_printf(m, "    " #x ": 0x%08x\n", error->regs.x)
1535         P(OBUF_0Y);
1536         P(OBUF_1Y);
1537         P(OBUF_0U);
1538         P(OBUF_0V);
1539         P(OBUF_1U);
1540         P(OBUF_1V);
1541         P(OSTRIDE);
1542         P(YRGB_VPH);
1543         P(UV_VPH);
1544         P(HORZ_PH);
1545         P(INIT_PHS);
1546         P(DWINPOS);
1547         P(DWINSZ);
1548         P(SWIDTH);
1549         P(SWIDTHSW);
1550         P(SHEIGHT);
1551         P(YRGBSCALE);
1552         P(UVSCALE);
1553         P(OCLRC0);
1554         P(OCLRC1);
1555         P(DCLRKV);
1556         P(DCLRKM);
1557         P(SCLRKVH);
1558         P(SCLRKVL);
1559         P(SCLRKEN);
1560         P(OCONFIG);
1561         P(OCMD);
1562         P(OSTART_0Y);
1563         P(OSTART_1Y);
1564         P(OSTART_0U);
1565         P(OSTART_0V);
1566         P(OSTART_1U);
1567         P(OSTART_1V);
1568         P(OTILEOFF_0Y);
1569         P(OTILEOFF_1Y);
1570         P(OTILEOFF_0U);
1571         P(OTILEOFF_0V);
1572         P(OTILEOFF_1U);
1573         P(OTILEOFF_1V);
1574         P(FASTHSCALE);
1575         P(UVSCALEV);
1576 #undef P
1577 }
1578 #endif