linux/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0-only */
   2/*
   3 * Copyright (C) 2014 Traphandler
   4 * Copyright (C) 2014 Free Electrons
   5 * Copyright (C) 2014 Atmel
   6 *
   7 * Author: Jean-Jacques Hiblot <jjhiblot@traphandler.com>
   8 * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
   9 */
  10
  11#ifndef DRM_ATMEL_HLCDC_H
  12#define DRM_ATMEL_HLCDC_H
  13
  14#include <linux/clk.h>
  15#include <linux/dmapool.h>
  16#include <linux/irqdomain.h>
  17#include <linux/mfd/atmel-hlcdc.h>
  18#include <linux/pwm.h>
  19
  20#include <drm/drm_atomic.h>
  21#include <drm/drm_atomic_helper.h>
  22#include <drm/drm_crtc.h>
  23#include <drm/drm_probe_helper.h>
  24#include <drm/drm_fb_helper.h>
  25#include <drm/drm_fb_cma_helper.h>
  26#include <drm/drm_gem_cma_helper.h>
  27#include <drm/drm_gem_framebuffer_helper.h>
  28#include <drm/drm_panel.h>
  29#include <drm/drm_plane_helper.h>
  30#include <drm/drmP.h>
  31
  32#define ATMEL_HLCDC_LAYER_CHER                  0x0
  33#define ATMEL_HLCDC_LAYER_CHDR                  0x4
  34#define ATMEL_HLCDC_LAYER_CHSR                  0x8
  35#define ATMEL_HLCDC_LAYER_EN                    BIT(0)
  36#define ATMEL_HLCDC_LAYER_UPDATE                BIT(1)
  37#define ATMEL_HLCDC_LAYER_A2Q                   BIT(2)
  38#define ATMEL_HLCDC_LAYER_RST                   BIT(8)
  39
  40#define ATMEL_HLCDC_LAYER_IER                   0xc
  41#define ATMEL_HLCDC_LAYER_IDR                   0x10
  42#define ATMEL_HLCDC_LAYER_IMR                   0x14
  43#define ATMEL_HLCDC_LAYER_ISR                   0x18
  44#define ATMEL_HLCDC_LAYER_DFETCH                BIT(0)
  45#define ATMEL_HLCDC_LAYER_LFETCH                BIT(1)
  46#define ATMEL_HLCDC_LAYER_DMA_IRQ(p)            BIT(2 + (8 * (p)))
  47#define ATMEL_HLCDC_LAYER_DSCR_IRQ(p)           BIT(3 + (8 * (p)))
  48#define ATMEL_HLCDC_LAYER_ADD_IRQ(p)            BIT(4 + (8 * (p)))
  49#define ATMEL_HLCDC_LAYER_DONE_IRQ(p)           BIT(5 + (8 * (p)))
  50#define ATMEL_HLCDC_LAYER_OVR_IRQ(p)            BIT(6 + (8 * (p)))
  51
  52#define ATMEL_HLCDC_LAYER_PLANE_HEAD(p)         (((p) * 0x10) + 0x1c)
  53#define ATMEL_HLCDC_LAYER_PLANE_ADDR(p)         (((p) * 0x10) + 0x20)
  54#define ATMEL_HLCDC_LAYER_PLANE_CTRL(p)         (((p) * 0x10) + 0x24)
  55#define ATMEL_HLCDC_LAYER_PLANE_NEXT(p)         (((p) * 0x10) + 0x28)
  56
  57#define ATMEL_HLCDC_LAYER_DMA_CFG               0
  58#define ATMEL_HLCDC_LAYER_DMA_SIF               BIT(0)
  59#define ATMEL_HLCDC_LAYER_DMA_BLEN_MASK         GENMASK(5, 4)
  60#define ATMEL_HLCDC_LAYER_DMA_BLEN_SINGLE       (0 << 4)
  61#define ATMEL_HLCDC_LAYER_DMA_BLEN_INCR4        (1 << 4)
  62#define ATMEL_HLCDC_LAYER_DMA_BLEN_INCR8        (2 << 4)
  63#define ATMEL_HLCDC_LAYER_DMA_BLEN_INCR16       (3 << 4)
  64#define ATMEL_HLCDC_LAYER_DMA_DLBO              BIT(8)
  65#define ATMEL_HLCDC_LAYER_DMA_ROTDIS            BIT(12)
  66#define ATMEL_HLCDC_LAYER_DMA_LOCKDIS           BIT(13)
  67
  68#define ATMEL_HLCDC_LAYER_FORMAT_CFG            1
  69#define ATMEL_HLCDC_LAYER_RGB                   (0 << 0)
  70#define ATMEL_HLCDC_LAYER_CLUT                  (1 << 0)
  71#define ATMEL_HLCDC_LAYER_YUV                   (2 << 0)
  72#define ATMEL_HLCDC_RGB_MODE(m)                 \
  73        (ATMEL_HLCDC_LAYER_RGB | (((m) & 0xf) << 4))
  74#define ATMEL_HLCDC_CLUT_MODE(m)                \
  75        (ATMEL_HLCDC_LAYER_CLUT | (((m) & 0x3) << 8))
  76#define ATMEL_HLCDC_YUV_MODE(m)                 \
  77        (ATMEL_HLCDC_LAYER_YUV | (((m) & 0xf) << 12))
  78#define ATMEL_HLCDC_YUV422ROT                   BIT(16)
  79#define ATMEL_HLCDC_YUV422SWP                   BIT(17)
  80#define ATMEL_HLCDC_DSCALEOPT                   BIT(20)
  81
  82#define ATMEL_HLCDC_C1_MODE                     ATMEL_HLCDC_CLUT_MODE(0)
  83#define ATMEL_HLCDC_C2_MODE                     ATMEL_HLCDC_CLUT_MODE(1)
  84#define ATMEL_HLCDC_C4_MODE                     ATMEL_HLCDC_CLUT_MODE(2)
  85#define ATMEL_HLCDC_C8_MODE                     ATMEL_HLCDC_CLUT_MODE(3)
  86
  87#define ATMEL_HLCDC_XRGB4444_MODE               ATMEL_HLCDC_RGB_MODE(0)
  88#define ATMEL_HLCDC_ARGB4444_MODE               ATMEL_HLCDC_RGB_MODE(1)
  89#define ATMEL_HLCDC_RGBA4444_MODE               ATMEL_HLCDC_RGB_MODE(2)
  90#define ATMEL_HLCDC_RGB565_MODE                 ATMEL_HLCDC_RGB_MODE(3)
  91#define ATMEL_HLCDC_ARGB1555_MODE               ATMEL_HLCDC_RGB_MODE(4)
  92#define ATMEL_HLCDC_XRGB8888_MODE               ATMEL_HLCDC_RGB_MODE(9)
  93#define ATMEL_HLCDC_RGB888_MODE                 ATMEL_HLCDC_RGB_MODE(10)
  94#define ATMEL_HLCDC_ARGB8888_MODE               ATMEL_HLCDC_RGB_MODE(12)
  95#define ATMEL_HLCDC_RGBA8888_MODE               ATMEL_HLCDC_RGB_MODE(13)
  96
  97#define ATMEL_HLCDC_AYUV_MODE                   ATMEL_HLCDC_YUV_MODE(0)
  98#define ATMEL_HLCDC_YUYV_MODE                   ATMEL_HLCDC_YUV_MODE(1)
  99#define ATMEL_HLCDC_UYVY_MODE                   ATMEL_HLCDC_YUV_MODE(2)
 100#define ATMEL_HLCDC_YVYU_MODE                   ATMEL_HLCDC_YUV_MODE(3)
 101#define ATMEL_HLCDC_VYUY_MODE                   ATMEL_HLCDC_YUV_MODE(4)
 102#define ATMEL_HLCDC_NV61_MODE                   ATMEL_HLCDC_YUV_MODE(5)
 103#define ATMEL_HLCDC_YUV422_MODE                 ATMEL_HLCDC_YUV_MODE(6)
 104#define ATMEL_HLCDC_NV21_MODE                   ATMEL_HLCDC_YUV_MODE(7)
 105#define ATMEL_HLCDC_YUV420_MODE                 ATMEL_HLCDC_YUV_MODE(8)
 106
 107#define ATMEL_HLCDC_LAYER_POS(x, y)             ((x) | ((y) << 16))
 108#define ATMEL_HLCDC_LAYER_SIZE(w, h)            (((w) - 1) | (((h) - 1) << 16))
 109
 110#define ATMEL_HLCDC_LAYER_CRKEY                 BIT(0)
 111#define ATMEL_HLCDC_LAYER_INV                   BIT(1)
 112#define ATMEL_HLCDC_LAYER_ITER2BL               BIT(2)
 113#define ATMEL_HLCDC_LAYER_ITER                  BIT(3)
 114#define ATMEL_HLCDC_LAYER_REVALPHA              BIT(4)
 115#define ATMEL_HLCDC_LAYER_GAEN                  BIT(5)
 116#define ATMEL_HLCDC_LAYER_LAEN                  BIT(6)
 117#define ATMEL_HLCDC_LAYER_OVR                   BIT(7)
 118#define ATMEL_HLCDC_LAYER_DMA                   BIT(8)
 119#define ATMEL_HLCDC_LAYER_REP                   BIT(9)
 120#define ATMEL_HLCDC_LAYER_DSTKEY                BIT(10)
 121#define ATMEL_HLCDC_LAYER_DISCEN                BIT(11)
 122#define ATMEL_HLCDC_LAYER_GA_SHIFT              16
 123#define ATMEL_HLCDC_LAYER_GA_MASK               \
 124        GENMASK(23, ATMEL_HLCDC_LAYER_GA_SHIFT)
 125#define ATMEL_HLCDC_LAYER_GA(x)                 \
 126        ((x) << ATMEL_HLCDC_LAYER_GA_SHIFT)
 127
 128#define ATMEL_HLCDC_LAYER_DISC_POS(x, y)        ((x) | ((y) << 16))
 129#define ATMEL_HLCDC_LAYER_DISC_SIZE(w, h)       (((w) - 1) | (((h) - 1) << 16))
 130
 131#define ATMEL_HLCDC_LAYER_SCALER_FACTORS(x, y)  ((x) | ((y) << 16))
 132#define ATMEL_HLCDC_LAYER_SCALER_ENABLE         BIT(31)
 133
 134#define ATMEL_HLCDC_LAYER_MAX_PLANES            3
 135
 136#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_RESERVED   BIT(0)
 137#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED     BIT(1)
 138#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE       BIT(2)
 139#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_OVERRUN    BIT(3)
 140
 141#define ATMEL_HLCDC_CLUT_SIZE                   256
 142
 143#define ATMEL_HLCDC_MAX_LAYERS                  6
 144
 145/**
 146 * Atmel HLCDC Layer registers layout structure
 147 *
 148 * Each HLCDC layer has its own register organization and a given register
 149 * can be placed differently on 2 different layers depending on its
 150 * capabilities.
 151 * This structure stores common registers layout for a given layer and is
 152 * used by HLCDC layer code to choose the appropriate register to write to
 153 * or to read from.
 154 *
 155 * For all fields, a value of zero means "unsupported".
 156 *
 157 * See Atmel's datasheet for a detailled description of these registers.
 158 *
 159 * @xstride: xstride registers
 160 * @pstride: pstride registers
 161 * @pos: position register
 162 * @size: displayed size register
 163 * @memsize: memory size register
 164 * @default_color: default color register
 165 * @chroma_key: chroma key register
 166 * @chroma_key_mask: chroma key mask register
 167 * @general_config: general layer config register
 168 * @sacler_config: scaler factors register
 169 * @phicoeffs: X/Y PHI coefficient registers
 170 * @disc_pos: discard area position register
 171 * @disc_size: discard area size register
 172 * @csc: color space conversion register
 173 */
 174struct atmel_hlcdc_layer_cfg_layout {
 175        int xstride[ATMEL_HLCDC_LAYER_MAX_PLANES];
 176        int pstride[ATMEL_HLCDC_LAYER_MAX_PLANES];
 177        int pos;
 178        int size;
 179        int memsize;
 180        int default_color;
 181        int chroma_key;
 182        int chroma_key_mask;
 183        int general_config;
 184        int scaler_config;
 185        struct {
 186                int x;
 187                int y;
 188        } phicoeffs;
 189        int disc_pos;
 190        int disc_size;
 191        int csc;
 192};
 193
 194/**
 195 * Atmel HLCDC DMA descriptor structure
 196 *
 197 * This structure is used by the HLCDC DMA engine to schedule a DMA transfer.
 198 *
 199 * The structure fields must remain in this specific order, because they're
 200 * used by the HLCDC DMA engine, which expect them in this order.
 201 * HLCDC DMA descriptors must be aligned on 64 bits.
 202 *
 203 * @addr: buffer DMA address
 204 * @ctrl: DMA transfer options
 205 * @next: next DMA descriptor to fetch
 206 * @self: descriptor DMA address
 207 */
 208struct atmel_hlcdc_dma_channel_dscr {
 209        dma_addr_t addr;
 210        u32 ctrl;
 211        dma_addr_t next;
 212        dma_addr_t self;
 213} __aligned(sizeof(u64));
 214
 215/**
 216 * Atmel HLCDC layer types
 217 */
 218enum atmel_hlcdc_layer_type {
 219        ATMEL_HLCDC_NO_LAYER,
 220        ATMEL_HLCDC_BASE_LAYER,
 221        ATMEL_HLCDC_OVERLAY_LAYER,
 222        ATMEL_HLCDC_CURSOR_LAYER,
 223        ATMEL_HLCDC_PP_LAYER,
 224};
 225
 226/**
 227 * Atmel HLCDC Supported formats structure
 228 *
 229 * This structure list all the formats supported by a given layer.
 230 *
 231 * @nformats: number of supported formats
 232 * @formats: supported formats
 233 */
 234struct atmel_hlcdc_formats {
 235        int nformats;
 236        u32 *formats;
 237};
 238
 239/**
 240 * Atmel HLCDC Layer description structure
 241 *
 242 * This structure describes the capabilities provided by a given layer.
 243 *
 244 * @name: layer name
 245 * @type: layer type
 246 * @id: layer id
 247 * @regs_offset: offset of the layer registers from the HLCDC registers base
 248 * @cfgs_offset: CFGX registers offset from the layer registers base
 249 * @formats: supported formats
 250 * @layout: config registers layout
 251 * @max_width: maximum width supported by this layer (0 means unlimited)
 252 * @max_height: maximum height supported by this layer (0 means unlimited)
 253 */
 254struct atmel_hlcdc_layer_desc {
 255        const char *name;
 256        enum atmel_hlcdc_layer_type type;
 257        int id;
 258        int regs_offset;
 259        int cfgs_offset;
 260        int clut_offset;
 261        struct atmel_hlcdc_formats *formats;
 262        struct atmel_hlcdc_layer_cfg_layout layout;
 263        int max_width;
 264        int max_height;
 265};
 266
 267/**
 268 * Atmel HLCDC Layer.
 269 *
 270 * A layer can be a DRM plane of a post processing layer used to render
 271 * HLCDC composition into memory.
 272 *
 273 * @desc: layer description
 274 * @regmap: pointer to the HLCDC regmap
 275 */
 276struct atmel_hlcdc_layer {
 277        const struct atmel_hlcdc_layer_desc *desc;
 278        struct regmap *regmap;
 279};
 280
 281/**
 282 * Atmel HLCDC Plane.
 283 *
 284 * @base: base DRM plane structure
 285 * @layer: HLCDC layer structure
 286 * @properties: pointer to the property definitions structure
 287 */
 288struct atmel_hlcdc_plane {
 289        struct drm_plane base;
 290        struct atmel_hlcdc_layer layer;
 291};
 292
 293static inline struct atmel_hlcdc_plane *
 294drm_plane_to_atmel_hlcdc_plane(struct drm_plane *p)
 295{
 296        return container_of(p, struct atmel_hlcdc_plane, base);
 297}
 298
 299static inline struct atmel_hlcdc_plane *
 300atmel_hlcdc_layer_to_plane(struct atmel_hlcdc_layer *layer)
 301{
 302        return container_of(layer, struct atmel_hlcdc_plane, layer);
 303}
 304
 305/**
 306 * Atmel HLCDC Display Controller description structure.
 307 *
 308 * This structure describes the HLCDC IP capabilities and depends on the
 309 * HLCDC IP version (or Atmel SoC family).
 310 *
 311 * @min_width: minimum width supported by the Display Controller
 312 * @min_height: minimum height supported by the Display Controller
 313 * @max_width: maximum width supported by the Display Controller
 314 * @max_height: maximum height supported by the Display Controller
 315 * @max_spw: maximum vertical/horizontal pulse width
 316 * @max_vpw: maximum vertical back/front porch width
 317 * @max_hpw: maximum horizontal back/front porch width
 318 * @conflicting_output_formats: true if RGBXXX output formats conflict with
 319 *                              each other.
 320 * @fixed_clksrc: true if clock source is fixed
 321 * @layers: a layer description table describing available layers
 322 * @nlayers: layer description table size
 323 */
 324struct atmel_hlcdc_dc_desc {
 325        int min_width;
 326        int min_height;
 327        int max_width;
 328        int max_height;
 329        int max_spw;
 330        int max_vpw;
 331        int max_hpw;
 332        bool conflicting_output_formats;
 333        bool fixed_clksrc;
 334        const struct atmel_hlcdc_layer_desc *layers;
 335        int nlayers;
 336};
 337
 338/**
 339 * Atmel HLCDC Display Controller.
 340 *
 341 * @desc: HLCDC Display Controller description
 342 * @dscrpool: DMA coherent pool used to allocate DMA descriptors
 343 * @hlcdc: pointer to the atmel_hlcdc structure provided by the MFD device
 344 * @fbdev: framebuffer device attached to the Display Controller
 345 * @crtc: CRTC provided by the display controller
 346 * @planes: instantiated planes
 347 * @layers: active HLCDC layers
 348 * @wq: display controller workqueue
 349 * @suspend: used to store the HLCDC state when entering suspend
 350 * @commit: used for async commit handling
 351 */
 352struct atmel_hlcdc_dc {
 353        const struct atmel_hlcdc_dc_desc *desc;
 354        struct dma_pool *dscrpool;
 355        struct atmel_hlcdc *hlcdc;
 356        struct drm_crtc *crtc;
 357        struct atmel_hlcdc_layer *layers[ATMEL_HLCDC_MAX_LAYERS];
 358        struct workqueue_struct *wq;
 359        struct {
 360                u32 imr;
 361                struct drm_atomic_state *state;
 362        } suspend;
 363        struct {
 364                wait_queue_head_t wait;
 365                bool pending;
 366        } commit;
 367};
 368
 369extern struct atmel_hlcdc_formats atmel_hlcdc_plane_rgb_formats;
 370extern struct atmel_hlcdc_formats atmel_hlcdc_plane_rgb_and_yuv_formats;
 371
 372static inline void atmel_hlcdc_layer_write_reg(struct atmel_hlcdc_layer *layer,
 373                                               unsigned int reg, u32 val)
 374{
 375        regmap_write(layer->regmap, layer->desc->regs_offset + reg, val);
 376}
 377
 378static inline u32 atmel_hlcdc_layer_read_reg(struct atmel_hlcdc_layer *layer,
 379                                             unsigned int reg)
 380{
 381        u32 val;
 382
 383        regmap_read(layer->regmap, layer->desc->regs_offset + reg, &val);
 384
 385        return val;
 386}
 387
 388static inline void atmel_hlcdc_layer_write_cfg(struct atmel_hlcdc_layer *layer,
 389                                               unsigned int cfgid, u32 val)
 390{
 391        atmel_hlcdc_layer_write_reg(layer,
 392                                    layer->desc->cfgs_offset +
 393                                    (cfgid * sizeof(u32)), val);
 394}
 395
 396static inline u32 atmel_hlcdc_layer_read_cfg(struct atmel_hlcdc_layer *layer,
 397                                             unsigned int cfgid)
 398{
 399        return atmel_hlcdc_layer_read_reg(layer,
 400                                          layer->desc->cfgs_offset +
 401                                          (cfgid * sizeof(u32)));
 402}
 403
 404static inline void atmel_hlcdc_layer_write_clut(struct atmel_hlcdc_layer *layer,
 405                                                unsigned int c, u32 val)
 406{
 407        regmap_write(layer->regmap,
 408                     layer->desc->clut_offset + c * sizeof(u32),
 409                     val);
 410}
 411
 412static inline void atmel_hlcdc_layer_init(struct atmel_hlcdc_layer *layer,
 413                                const struct atmel_hlcdc_layer_desc *desc,
 414                                struct regmap *regmap)
 415{
 416        layer->desc = desc;
 417        layer->regmap = regmap;
 418}
 419
 420enum drm_mode_status
 421atmel_hlcdc_dc_mode_valid(struct atmel_hlcdc_dc *dc,
 422                          const struct drm_display_mode *mode);
 423
 424int atmel_hlcdc_create_planes(struct drm_device *dev);
 425void atmel_hlcdc_plane_irq(struct atmel_hlcdc_plane *plane);
 426
 427int atmel_hlcdc_plane_prepare_disc_area(struct drm_crtc_state *c_state);
 428int atmel_hlcdc_plane_prepare_ahb_routing(struct drm_crtc_state *c_state);
 429
 430void atmel_hlcdc_crtc_irq(struct drm_crtc *c);
 431
 432int atmel_hlcdc_crtc_create(struct drm_device *dev);
 433
 434int atmel_hlcdc_create_outputs(struct drm_device *dev);
 435int atmel_hlcdc_encoder_get_bus_fmt(struct drm_encoder *encoder);
 436
 437#endif /* DRM_ATMEL_HLCDC_H */
 438