linux/drivers/gpu/drm/pl111/pl111_display.c
<<
>>
Prefs
   1/*
   2 * (C) COPYRIGHT 2012-2013 ARM Limited. All rights reserved.
   3 *
   4 * Parts of this file were based on sources as follows:
   5 *
   6 * Copyright (c) 2006-2008 Intel Corporation
   7 * Copyright (c) 2007 Dave Airlie <airlied@linux.ie>
   8 * Copyright (C) 2011 Texas Instruments
   9 *
  10 * This program is free software and is provided to you under the terms of the
  11 * GNU General Public License version 2 as published by the Free Software
  12 * Foundation, and any use by you of this program is subject to the terms of
  13 * such GNU licence.
  14 *
  15 */
  16
  17#include <linux/amba/clcd-regs.h>
  18#include <linux/clk.h>
  19#include <linux/version.h>
  20#include <linux/dma-buf.h>
  21#include <linux/of_graph.h>
  22
  23#include <drm/drmP.h>
  24#include <drm/drm_gem_cma_helper.h>
  25#include <drm/drm_gem_framebuffer_helper.h>
  26#include <drm/drm_fb_cma_helper.h>
  27
  28#include "pl111_drm.h"
  29
  30irqreturn_t pl111_irq(int irq, void *data)
  31{
  32        struct pl111_drm_dev_private *priv = data;
  33        u32 irq_stat;
  34        irqreturn_t status = IRQ_NONE;
  35
  36        irq_stat = readl(priv->regs + CLCD_PL111_MIS);
  37
  38        if (!irq_stat)
  39                return IRQ_NONE;
  40
  41        if (irq_stat & CLCD_IRQ_NEXTBASE_UPDATE) {
  42                drm_crtc_handle_vblank(&priv->pipe.crtc);
  43
  44                status = IRQ_HANDLED;
  45        }
  46
  47        /* Clear the interrupt once done */
  48        writel(irq_stat, priv->regs + CLCD_PL111_ICR);
  49
  50        return status;
  51}
  52
  53static enum drm_mode_status
  54pl111_mode_valid(struct drm_crtc *crtc,
  55                 const struct drm_display_mode *mode)
  56{
  57        struct drm_device *drm = crtc->dev;
  58        struct pl111_drm_dev_private *priv = drm->dev_private;
  59        u32 cpp = priv->variant->fb_bpp / 8;
  60        u64 bw;
  61
  62        /*
  63         * We use the pixelclock to also account for interlaced modes, the
  64         * resulting bandwidth is in bytes per second.
  65         */
  66        bw = mode->clock * 1000; /* In Hz */
  67        bw = bw * mode->hdisplay * mode->vdisplay * cpp;
  68        bw = div_u64(bw, mode->htotal * mode->vtotal);
  69
  70        /*
  71         * If no bandwidth constraints, anything goes, else
  72         * check if we are too fast.
  73         */
  74        if (priv->memory_bw && (bw > priv->memory_bw)) {
  75                DRM_DEBUG_KMS("%d x %d @ %d Hz, %d cpp, bw %llu too fast\n",
  76                              mode->hdisplay, mode->vdisplay,
  77                              mode->clock * 1000, cpp, bw);
  78
  79                return MODE_BAD;
  80        }
  81        DRM_DEBUG_KMS("%d x %d @ %d Hz, %d cpp, bw %llu bytes/s OK\n",
  82                      mode->hdisplay, mode->vdisplay,
  83                      mode->clock * 1000, cpp, bw);
  84
  85        return MODE_OK;
  86}
  87
  88static int pl111_display_check(struct drm_simple_display_pipe *pipe,
  89                               struct drm_plane_state *pstate,
  90                               struct drm_crtc_state *cstate)
  91{
  92        const struct drm_display_mode *mode = &cstate->mode;
  93        struct drm_framebuffer *old_fb = pipe->plane.state->fb;
  94        struct drm_framebuffer *fb = pstate->fb;
  95
  96        if (mode->hdisplay % 16)
  97                return -EINVAL;
  98
  99        if (fb) {
 100                u32 offset = drm_fb_cma_get_gem_addr(fb, pstate, 0);
 101
 102                /* FB base address must be dword aligned. */
 103                if (offset & 3)
 104                        return -EINVAL;
 105
 106                /* There's no pitch register -- the mode's hdisplay
 107                 * controls it.
 108                 */
 109                if (fb->pitches[0] != mode->hdisplay * fb->format->cpp[0])
 110                        return -EINVAL;
 111
 112                /* We can't change the FB format in a flicker-free
 113                 * manner (and only update it during CRTC enable).
 114                 */
 115                if (old_fb && old_fb->format != fb->format)
 116                        cstate->mode_changed = true;
 117        }
 118
 119        return 0;
 120}
 121
 122static void pl111_display_enable(struct drm_simple_display_pipe *pipe,
 123                                 struct drm_crtc_state *cstate,
 124                                 struct drm_plane_state *plane_state)
 125{
 126        struct drm_crtc *crtc = &pipe->crtc;
 127        struct drm_plane *plane = &pipe->plane;
 128        struct drm_device *drm = crtc->dev;
 129        struct pl111_drm_dev_private *priv = drm->dev_private;
 130        const struct drm_display_mode *mode = &cstate->mode;
 131        struct drm_framebuffer *fb = plane->state->fb;
 132        struct drm_connector *connector = priv->connector;
 133        struct drm_bridge *bridge = priv->bridge;
 134        u32 cntl;
 135        u32 ppl, hsw, hfp, hbp;
 136        u32 lpp, vsw, vfp, vbp;
 137        u32 cpl, tim2;
 138        int ret;
 139
 140        ret = clk_set_rate(priv->clk, mode->clock * 1000);
 141        if (ret) {
 142                dev_err(drm->dev,
 143                        "Failed to set pixel clock rate to %d: %d\n",
 144                        mode->clock * 1000, ret);
 145        }
 146
 147        clk_prepare_enable(priv->clk);
 148
 149        ppl = (mode->hdisplay / 16) - 1;
 150        hsw = mode->hsync_end - mode->hsync_start - 1;
 151        hfp = mode->hsync_start - mode->hdisplay - 1;
 152        hbp = mode->htotal - mode->hsync_end - 1;
 153
 154        lpp = mode->vdisplay - 1;
 155        vsw = mode->vsync_end - mode->vsync_start - 1;
 156        vfp = mode->vsync_start - mode->vdisplay;
 157        vbp = mode->vtotal - mode->vsync_end;
 158
 159        cpl = mode->hdisplay - 1;
 160
 161        writel((ppl << 2) |
 162               (hsw << 8) |
 163               (hfp << 16) |
 164               (hbp << 24),
 165               priv->regs + CLCD_TIM0);
 166        writel(lpp |
 167               (vsw << 10) |
 168               (vfp << 16) |
 169               (vbp << 24),
 170               priv->regs + CLCD_TIM1);
 171
 172        spin_lock(&priv->tim2_lock);
 173
 174        tim2 = readl(priv->regs + CLCD_TIM2);
 175        tim2 &= (TIM2_BCD | TIM2_PCD_LO_MASK | TIM2_PCD_HI_MASK);
 176
 177        if (priv->variant->broken_clockdivider)
 178                tim2 |= TIM2_BCD;
 179
 180        if (mode->flags & DRM_MODE_FLAG_NHSYNC)
 181                tim2 |= TIM2_IHS;
 182
 183        if (mode->flags & DRM_MODE_FLAG_NVSYNC)
 184                tim2 |= TIM2_IVS;
 185
 186        if (connector) {
 187                if (connector->display_info.bus_flags & DRM_BUS_FLAG_DE_LOW)
 188                        tim2 |= TIM2_IOE;
 189
 190                if (connector->display_info.bus_flags &
 191                    DRM_BUS_FLAG_PIXDATA_NEGEDGE)
 192                        tim2 |= TIM2_IPC;
 193        }
 194
 195        if (bridge) {
 196                const struct drm_bridge_timings *btimings = bridge->timings;
 197
 198                /*
 199                 * Here is when things get really fun. Sometimes the bridge
 200                 * timings are such that the signal out from PL11x is not
 201                 * stable before the receiving bridge (such as a dumb VGA DAC
 202                 * or similar) samples it. If that happens, we compensate by
 203                 * the only method we have: output the data on the opposite
 204                 * edge of the clock so it is for sure stable when it gets
 205                 * sampled.
 206                 *
 207                 * The PL111 manual does not contain proper timining diagrams
 208                 * or data for these details, but we know from experiments
 209                 * that the setup time is more than 3000 picoseconds (3 ns).
 210                 * If we have a bridge that requires the signal to be stable
 211                 * earlier than 3000 ps before the clock pulse, we have to
 212                 * output the data on the opposite edge to avoid flicker.
 213                 */
 214                if (btimings && btimings->setup_time_ps >= 3000)
 215                        tim2 ^= TIM2_IPC;
 216        }
 217
 218        tim2 |= cpl << 16;
 219        writel(tim2, priv->regs + CLCD_TIM2);
 220        spin_unlock(&priv->tim2_lock);
 221
 222        writel(0, priv->regs + CLCD_TIM3);
 223
 224        /* Hard-code TFT panel */
 225        cntl = CNTL_LCDEN | CNTL_LCDTFT | CNTL_LCDVCOMP(1);
 226
 227        /* Note that the the hardware's format reader takes 'r' from
 228         * the low bit, while DRM formats list channels from high bit
 229         * to low bit as you read left to right.
 230         */
 231        switch (fb->format->format) {
 232        case DRM_FORMAT_ABGR8888:
 233        case DRM_FORMAT_XBGR8888:
 234                cntl |= CNTL_LCDBPP24;
 235                break;
 236        case DRM_FORMAT_ARGB8888:
 237        case DRM_FORMAT_XRGB8888:
 238                cntl |= CNTL_LCDBPP24 | CNTL_BGR;
 239                break;
 240        case DRM_FORMAT_BGR565:
 241                if (priv->variant->is_pl110)
 242                        cntl |= CNTL_LCDBPP16;
 243                else
 244                        cntl |= CNTL_LCDBPP16_565;
 245                break;
 246        case DRM_FORMAT_RGB565:
 247                if (priv->variant->is_pl110)
 248                        cntl |= CNTL_LCDBPP16;
 249                else
 250                        cntl |= CNTL_LCDBPP16_565;
 251                cntl |= CNTL_BGR;
 252                break;
 253        case DRM_FORMAT_ABGR1555:
 254        case DRM_FORMAT_XBGR1555:
 255                cntl |= CNTL_LCDBPP16;
 256                break;
 257        case DRM_FORMAT_ARGB1555:
 258        case DRM_FORMAT_XRGB1555:
 259                cntl |= CNTL_LCDBPP16 | CNTL_BGR;
 260                break;
 261        case DRM_FORMAT_ABGR4444:
 262        case DRM_FORMAT_XBGR4444:
 263                cntl |= CNTL_LCDBPP16_444;
 264                break;
 265        case DRM_FORMAT_ARGB4444:
 266        case DRM_FORMAT_XRGB4444:
 267                cntl |= CNTL_LCDBPP16_444 | CNTL_BGR;
 268                break;
 269        default:
 270                WARN_ONCE(true, "Unknown FB format 0x%08x\n",
 271                          fb->format->format);
 272                break;
 273        }
 274
 275        /* The PL110 in Integrator/Versatile does the BGR routing externally */
 276        if (priv->variant->external_bgr)
 277                cntl &= ~CNTL_BGR;
 278
 279        /* Power sequence: first enable and chill */
 280        writel(cntl, priv->regs + priv->ctrl);
 281
 282        /*
 283         * We expect this delay to stabilize the contrast
 284         * voltage Vee as stipulated by the manual
 285         */
 286        msleep(20);
 287
 288        if (priv->variant_display_enable)
 289                priv->variant_display_enable(drm, fb->format->format);
 290
 291        /* Power Up */
 292        cntl |= CNTL_LCDPWR;
 293        writel(cntl, priv->regs + priv->ctrl);
 294
 295        if (!priv->variant->broken_vblank)
 296                drm_crtc_vblank_on(crtc);
 297}
 298
 299void pl111_display_disable(struct drm_simple_display_pipe *pipe)
 300{
 301        struct drm_crtc *crtc = &pipe->crtc;
 302        struct drm_device *drm = crtc->dev;
 303        struct pl111_drm_dev_private *priv = drm->dev_private;
 304        u32 cntl;
 305
 306        if (!priv->variant->broken_vblank)
 307                drm_crtc_vblank_off(crtc);
 308
 309        /* Power Down */
 310        cntl = readl(priv->regs + priv->ctrl);
 311        if (cntl & CNTL_LCDPWR) {
 312                cntl &= ~CNTL_LCDPWR;
 313                writel(cntl, priv->regs + priv->ctrl);
 314        }
 315
 316        /*
 317         * We expect this delay to stabilize the contrast voltage Vee as
 318         * stipulated by the manual
 319         */
 320        msleep(20);
 321
 322        if (priv->variant_display_disable)
 323                priv->variant_display_disable(drm);
 324
 325        /* Disable */
 326        writel(0, priv->regs + priv->ctrl);
 327
 328        clk_disable_unprepare(priv->clk);
 329}
 330
 331static void pl111_display_update(struct drm_simple_display_pipe *pipe,
 332                                 struct drm_plane_state *old_pstate)
 333{
 334        struct drm_crtc *crtc = &pipe->crtc;
 335        struct drm_device *drm = crtc->dev;
 336        struct pl111_drm_dev_private *priv = drm->dev_private;
 337        struct drm_pending_vblank_event *event = crtc->state->event;
 338        struct drm_plane *plane = &pipe->plane;
 339        struct drm_plane_state *pstate = plane->state;
 340        struct drm_framebuffer *fb = pstate->fb;
 341
 342        if (fb) {
 343                u32 addr = drm_fb_cma_get_gem_addr(fb, pstate, 0);
 344
 345                writel(addr, priv->regs + CLCD_UBAS);
 346        }
 347
 348        if (event) {
 349                crtc->state->event = NULL;
 350
 351                spin_lock_irq(&crtc->dev->event_lock);
 352                if (crtc->state->active && drm_crtc_vblank_get(crtc) == 0)
 353                        drm_crtc_arm_vblank_event(crtc, event);
 354                else
 355                        drm_crtc_send_vblank_event(crtc, event);
 356                spin_unlock_irq(&crtc->dev->event_lock);
 357        }
 358}
 359
 360static int pl111_display_enable_vblank(struct drm_simple_display_pipe *pipe)
 361{
 362        struct drm_crtc *crtc = &pipe->crtc;
 363        struct drm_device *drm = crtc->dev;
 364        struct pl111_drm_dev_private *priv = drm->dev_private;
 365
 366        writel(CLCD_IRQ_NEXTBASE_UPDATE, priv->regs + priv->ienb);
 367
 368        return 0;
 369}
 370
 371static void pl111_display_disable_vblank(struct drm_simple_display_pipe *pipe)
 372{
 373        struct drm_crtc *crtc = &pipe->crtc;
 374        struct drm_device *drm = crtc->dev;
 375        struct pl111_drm_dev_private *priv = drm->dev_private;
 376
 377        writel(0, priv->regs + priv->ienb);
 378}
 379
 380static struct drm_simple_display_pipe_funcs pl111_display_funcs = {
 381        .mode_valid = pl111_mode_valid,
 382        .check = pl111_display_check,
 383        .enable = pl111_display_enable,
 384        .disable = pl111_display_disable,
 385        .update = pl111_display_update,
 386        .prepare_fb = drm_gem_fb_simple_display_pipe_prepare_fb,
 387};
 388
 389static int pl111_clk_div_choose_div(struct clk_hw *hw, unsigned long rate,
 390                                    unsigned long *prate, bool set_parent)
 391{
 392        int best_div = 1, div;
 393        struct clk_hw *parent = clk_hw_get_parent(hw);
 394        unsigned long best_prate = 0;
 395        unsigned long best_diff = ~0ul;
 396        int max_div = (1 << (TIM2_PCD_LO_BITS + TIM2_PCD_HI_BITS)) - 1;
 397
 398        for (div = 1; div < max_div; div++) {
 399                unsigned long this_prate, div_rate, diff;
 400
 401                if (set_parent)
 402                        this_prate = clk_hw_round_rate(parent, rate * div);
 403                else
 404                        this_prate = *prate;
 405                div_rate = DIV_ROUND_UP_ULL(this_prate, div);
 406                diff = abs(rate - div_rate);
 407
 408                if (diff < best_diff) {
 409                        best_div = div;
 410                        best_diff = diff;
 411                        best_prate = this_prate;
 412                }
 413        }
 414
 415        *prate = best_prate;
 416        return best_div;
 417}
 418
 419static long pl111_clk_div_round_rate(struct clk_hw *hw, unsigned long rate,
 420                                     unsigned long *prate)
 421{
 422        int div = pl111_clk_div_choose_div(hw, rate, prate, true);
 423
 424        return DIV_ROUND_UP_ULL(*prate, div);
 425}
 426
 427static unsigned long pl111_clk_div_recalc_rate(struct clk_hw *hw,
 428                                               unsigned long prate)
 429{
 430        struct pl111_drm_dev_private *priv =
 431                container_of(hw, struct pl111_drm_dev_private, clk_div);
 432        u32 tim2 = readl(priv->regs + CLCD_TIM2);
 433        int div;
 434
 435        if (tim2 & TIM2_BCD)
 436                return prate;
 437
 438        div = tim2 & TIM2_PCD_LO_MASK;
 439        div |= (tim2 & TIM2_PCD_HI_MASK) >>
 440                (TIM2_PCD_HI_SHIFT - TIM2_PCD_LO_BITS);
 441        div += 2;
 442
 443        return DIV_ROUND_UP_ULL(prate, div);
 444}
 445
 446static int pl111_clk_div_set_rate(struct clk_hw *hw, unsigned long rate,
 447                                  unsigned long prate)
 448{
 449        struct pl111_drm_dev_private *priv =
 450                container_of(hw, struct pl111_drm_dev_private, clk_div);
 451        int div = pl111_clk_div_choose_div(hw, rate, &prate, false);
 452        u32 tim2;
 453
 454        spin_lock(&priv->tim2_lock);
 455        tim2 = readl(priv->regs + CLCD_TIM2);
 456        tim2 &= ~(TIM2_BCD | TIM2_PCD_LO_MASK | TIM2_PCD_HI_MASK);
 457
 458        if (div == 1) {
 459                tim2 |= TIM2_BCD;
 460        } else {
 461                div -= 2;
 462                tim2 |= div & TIM2_PCD_LO_MASK;
 463                tim2 |= (div >> TIM2_PCD_LO_BITS) << TIM2_PCD_HI_SHIFT;
 464        }
 465
 466        writel(tim2, priv->regs + CLCD_TIM2);
 467        spin_unlock(&priv->tim2_lock);
 468
 469        return 0;
 470}
 471
 472static const struct clk_ops pl111_clk_div_ops = {
 473        .recalc_rate = pl111_clk_div_recalc_rate,
 474        .round_rate = pl111_clk_div_round_rate,
 475        .set_rate = pl111_clk_div_set_rate,
 476};
 477
 478static int
 479pl111_init_clock_divider(struct drm_device *drm)
 480{
 481        struct pl111_drm_dev_private *priv = drm->dev_private;
 482        struct clk *parent = devm_clk_get(drm->dev, "clcdclk");
 483        struct clk_hw *div = &priv->clk_div;
 484        const char *parent_name;
 485        struct clk_init_data init = {
 486                .name = "pl111_div",
 487                .ops = &pl111_clk_div_ops,
 488                .parent_names = &parent_name,
 489                .num_parents = 1,
 490                .flags = CLK_SET_RATE_PARENT,
 491        };
 492        int ret;
 493
 494        if (IS_ERR(parent)) {
 495                dev_err(drm->dev, "CLCD: unable to get clcdclk.\n");
 496                return PTR_ERR(parent);
 497        }
 498        /* If the clock divider is broken, use the parent directly */
 499        if (priv->variant->broken_clockdivider) {
 500                priv->clk = parent;
 501                return 0;
 502        }
 503        parent_name = __clk_get_name(parent);
 504
 505        spin_lock_init(&priv->tim2_lock);
 506        div->init = &init;
 507
 508        ret = devm_clk_hw_register(drm->dev, div);
 509
 510        priv->clk = div->clk;
 511        return ret;
 512}
 513
 514int pl111_display_init(struct drm_device *drm)
 515{
 516        struct pl111_drm_dev_private *priv = drm->dev_private;
 517        struct device *dev = drm->dev;
 518        struct device_node *endpoint;
 519        u32 tft_r0b0g0[3];
 520        int ret;
 521
 522        endpoint = of_graph_get_next_endpoint(dev->of_node, NULL);
 523        if (!endpoint)
 524                return -ENODEV;
 525
 526        if (of_property_read_u32_array(endpoint,
 527                                       "arm,pl11x,tft-r0g0b0-pads",
 528                                       tft_r0b0g0,
 529                                       ARRAY_SIZE(tft_r0b0g0)) != 0) {
 530                dev_err(dev, "arm,pl11x,tft-r0g0b0-pads should be 3 ints\n");
 531                of_node_put(endpoint);
 532                return -ENOENT;
 533        }
 534        of_node_put(endpoint);
 535
 536        ret = pl111_init_clock_divider(drm);
 537        if (ret)
 538                return ret;
 539
 540        if (!priv->variant->broken_vblank) {
 541                pl111_display_funcs.enable_vblank = pl111_display_enable_vblank;
 542                pl111_display_funcs.disable_vblank = pl111_display_disable_vblank;
 543        }
 544
 545        ret = drm_simple_display_pipe_init(drm, &priv->pipe,
 546                                           &pl111_display_funcs,
 547                                           priv->variant->formats,
 548                                           priv->variant->nformats,
 549                                           NULL,
 550                                           priv->connector);
 551        if (ret)
 552                return ret;
 553
 554        return 0;
 555}
 556