1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * Copyright © 2006-2007 Intel Corporation 4 * 5 * Authors: 6 * Eric Anholt <eric@anholt.net> 7 */ 8 9#include <linux/delay.h> 10#include <linux/i2c.h> 11#include <linux/pm_runtime.h> 12 13#include <drm/drm_crtc.h> 14#include <drm/drm_fourcc.h> 15 16#include "framebuffer.h" 17#include "gma_display.h" 18#include "mdfld_dsi_output.h" 19#include "mdfld_output.h" 20#include "psb_intel_reg.h" 21 22/* Hardcoded currently */ 23static int ksel = KSEL_CRYSTAL_19; 24 25struct psb_intel_range_t { 26 int min, max; 27}; 28 29struct mrst_limit_t { 30 struct psb_intel_range_t dot, m, p1; 31}; 32 33struct mrst_clock_t { 34 /* derived values */ 35 int dot; 36 int m; 37 int p1; 38}; 39 40#define COUNT_MAX 0x10000000 41 42void mdfldWaitForPipeDisable(struct drm_device *dev, int pipe) 43{ 44 struct drm_psb_private *dev_priv = dev->dev_private; 45 const struct psb_offset *map = &dev_priv->regmap[pipe]; 46 int count, temp; 47 48 switch (pipe) { 49 case 0: 50 case 1: 51 case 2: 52 break; 53 default: 54 DRM_ERROR("Illegal Pipe Number.\n"); 55 return; 56 } 57 58 /* FIXME JLIU7_PO */ 59 gma_wait_for_vblank(dev); 60 return; 61 62 /* Wait for for the pipe disable to take effect. */ 63 for (count = 0; count < COUNT_MAX; count++) { 64 temp = REG_READ(map->conf); 65 if ((temp & PIPEACONF_PIPE_STATE) == 0) 66 break; 67 } 68} 69 70void mdfldWaitForPipeEnable(struct drm_device *dev, int pipe) 71{ 72 struct drm_psb_private *dev_priv = dev->dev_private; 73 const struct psb_offset *map = &dev_priv->regmap[pipe]; 74 int count, temp; 75 76 switch (pipe) { 77 case 0: 78 case 1: 79 case 2: 80 break; 81 default: 82 DRM_ERROR("Illegal Pipe Number.\n"); 83 return; 84 } 85 86 /* FIXME JLIU7_PO */ 87 gma_wait_for_vblank(dev); 88 return; 89 90 /* Wait for for the pipe enable to take effect. */ 91 for (count = 0; count < COUNT_MAX; count++) { 92 temp = REG_READ(map->conf); 93 if (temp & PIPEACONF_PIPE_STATE) 94 break; 95 } 96} 97 98/** 99 * Return the pipe currently connected to the panel fitter, 100 * or -1 if the panel fitter is not present or not in use 101 */ 102static int psb_intel_panel_fitter_pipe(struct drm_device *dev) 103{ 104 u32 pfit_control; 105 106 pfit_control = REG_READ(PFIT_CONTROL); 107 108 /* See if the panel fitter is in use */ 109 if ((pfit_control & PFIT_ENABLE) == 0) 110 return -1; 111 112 /* 965 can place panel fitter on either pipe */ 113 return (pfit_control >> 29) & 0x3; 114} 115 116static int check_fb(struct drm_framebuffer *fb) 117{ 118 if (!fb) 119 return 0; 120 121 switch (fb->format->cpp[0] * 8) { 122 case 8: 123 case 16: 124 case 24: 125 case 32: 126 return 0; 127 default: 128 DRM_ERROR("Unknown color depth\n"); 129 return -EINVAL; 130 } 131} 132 133static int mdfld__intel_pipe_set_base(struct drm_crtc *crtc, int x, int y, 134 struct drm_framebuffer *old_fb) 135{ 136 struct drm_device *dev = crtc->dev; 137 struct drm_psb_private *dev_priv = dev->dev_private; 138 struct drm_framebuffer *fb = crtc->primary->fb; 139 struct gma_crtc *gma_crtc = to_gma_crtc(crtc); 140 int pipe = gma_crtc->pipe; 141 const struct psb_offset *map = &dev_priv->regmap[pipe]; 142 unsigned long start, offset; 143 u32 dspcntr; 144 int ret; 145 146 dev_dbg(dev->dev, "pipe = 0x%x.\n", pipe); 147 148 /* no fb bound */ 149 if (!fb) { 150 dev_dbg(dev->dev, "No FB bound\n"); 151 return 0; 152 } 153 154 ret = check_fb(fb); 155 if (ret) 156 return ret; 157 158 if (pipe > 2) { 159 DRM_ERROR("Illegal Pipe Number.\n"); 160 return -EINVAL; 161 } 162 163 if (!gma_power_begin(dev, true)) 164 return 0; 165 166 start = to_gtt_range(fb->obj[0])->offset; 167 offset = y * fb->pitches[0] + x * fb->format->cpp[0]; 168 169 REG_WRITE(map->stride, fb->pitches[0]); 170 dspcntr = REG_READ(map->cntr); 171 dspcntr &= ~DISPPLANE_PIXFORMAT_MASK; 172 173 switch (fb->format->cpp[0] * 8) { 174 case 8: 175 dspcntr |= DISPPLANE_8BPP; 176 break; 177 case 16: 178 if (fb->format->depth == 15) 179 dspcntr |= DISPPLANE_15_16BPP; 180 else 181 dspcntr |= DISPPLANE_16BPP; 182 break; 183 case 24: 184 case 32: 185 dspcntr |= DISPPLANE_32BPP_NO_ALPHA; 186 break; 187 } 188 REG_WRITE(map->cntr, dspcntr); 189 190 dev_dbg(dev->dev, "Writing base %08lX %08lX %d %d\n", 191 start, offset, x, y); 192 REG_WRITE(map->linoff, offset); 193 REG_READ(map->linoff); 194 REG_WRITE(map->surf, start); 195 REG_READ(map->surf); 196 197 gma_power_end(dev); 198 199 return 0; 200} 201 202/* 203 * Disable the pipe, plane and pll. 204 * 205 */ 206void mdfld_disable_crtc(struct drm_device *dev, int pipe) 207{ 208 struct drm_psb_private *dev_priv = dev->dev_private; 209 const struct psb_offset *map = &dev_priv->regmap[pipe]; 210 u32 temp; 211 212 dev_dbg(dev->dev, "pipe = %d\n", pipe); 213 214 215 if (pipe != 1) 216 mdfld_dsi_gen_fifo_ready(dev, MIPI_GEN_FIFO_STAT_REG(pipe), 217 HS_CTRL_FIFO_EMPTY | HS_DATA_FIFO_EMPTY); 218 219 /* Disable display plane */ 220 temp = REG_READ(map->cntr); 221 if ((temp & DISPLAY_PLANE_ENABLE) != 0) { 222 REG_WRITE(map->cntr, 223 temp & ~DISPLAY_PLANE_ENABLE); 224 /* Flush the plane changes */ 225 REG_WRITE(map->base, REG_READ(map->base)); 226 REG_READ(map->base); 227 } 228 229 /* FIXME_JLIU7 MDFLD_PO revisit */ 230 231 /* Next, disable display pipes */ 232 temp = REG_READ(map->conf); 233 if ((temp & PIPEACONF_ENABLE) != 0) { 234 temp &= ~PIPEACONF_ENABLE; 235 temp |= PIPECONF_PLANE_OFF | PIPECONF_CURSOR_OFF; 236 REG_WRITE(map->conf, temp); 237 REG_READ(map->conf); 238 239 /* Wait for for the pipe disable to take effect. */ 240 mdfldWaitForPipeDisable(dev, pipe); 241 } 242 243 temp = REG_READ(map->dpll); 244 if (temp & DPLL_VCO_ENABLE) { 245 if ((pipe != 1 && 246 !((REG_READ(PIPEACONF) | REG_READ(PIPECCONF)) 247 & PIPEACONF_ENABLE)) || pipe == 1) { 248 temp &= ~(DPLL_VCO_ENABLE); 249 REG_WRITE(map->dpll, temp); 250 REG_READ(map->dpll); 251 /* Wait for the clocks to turn off. */ 252 /* FIXME_MDFLD PO may need more delay */ 253 udelay(500); 254 255 if (!(temp & MDFLD_PWR_GATE_EN)) { 256 /* gating power of DPLL */ 257 REG_WRITE(map->dpll, temp | MDFLD_PWR_GATE_EN); 258 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 259 udelay(5000); 260 } 261 } 262 } 263 264} 265 266/** 267 * Sets the power management mode of the pipe and plane. 268 * 269 * This code should probably grow support for turning the cursor off and back 270 * on appropriately at the same time as we're turning the pipe off/on. 271 */ 272static void mdfld_crtc_dpms(struct drm_crtc *crtc, int mode) 273{ 274 struct drm_device *dev = crtc->dev; 275 struct drm_psb_private *dev_priv = dev->dev_private; 276 struct gma_crtc *gma_crtc = to_gma_crtc(crtc); 277 int pipe = gma_crtc->pipe; 278 const struct psb_offset *map = &dev_priv->regmap[pipe]; 279 u32 pipeconf = dev_priv->pipeconf[pipe]; 280 u32 temp; 281 int timeout = 0; 282 283 dev_dbg(dev->dev, "mode = %d, pipe = %d\n", mode, pipe); 284 285 /* Note: Old code uses pipe a stat for pipe b but that appears 286 to be a bug */ 287 288 if (!gma_power_begin(dev, true)) 289 return; 290 291 /* XXX: When our outputs are all unaware of DPMS modes other than off 292 * and on, we should map those modes to DRM_MODE_DPMS_OFF in the CRTC. 293 */ 294 switch (mode) { 295 case DRM_MODE_DPMS_ON: 296 case DRM_MODE_DPMS_STANDBY: 297 case DRM_MODE_DPMS_SUSPEND: 298 /* Enable the DPLL */ 299 temp = REG_READ(map->dpll); 300 301 if ((temp & DPLL_VCO_ENABLE) == 0) { 302 /* When ungating power of DPLL, needs to wait 0.5us 303 before enable the VCO */ 304 if (temp & MDFLD_PWR_GATE_EN) { 305 temp &= ~MDFLD_PWR_GATE_EN; 306 REG_WRITE(map->dpll, temp); 307 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 308 udelay(500); 309 } 310 311 REG_WRITE(map->dpll, temp); 312 REG_READ(map->dpll); 313 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 314 udelay(500); 315 316 REG_WRITE(map->dpll, temp | DPLL_VCO_ENABLE); 317 REG_READ(map->dpll); 318 319 /** 320 * wait for DSI PLL to lock 321 * NOTE: only need to poll status of pipe 0 and pipe 1, 322 * since both MIPI pipes share the same PLL. 323 */ 324 while ((pipe != 2) && (timeout < 20000) && 325 !(REG_READ(map->conf) & PIPECONF_DSIPLL_LOCK)) { 326 udelay(150); 327 timeout++; 328 } 329 } 330 331 /* Enable the plane */ 332 temp = REG_READ(map->cntr); 333 if ((temp & DISPLAY_PLANE_ENABLE) == 0) { 334 REG_WRITE(map->cntr, 335 temp | DISPLAY_PLANE_ENABLE); 336 /* Flush the plane changes */ 337 REG_WRITE(map->base, REG_READ(map->base)); 338 } 339 340 /* Enable the pipe */ 341 temp = REG_READ(map->conf); 342 if ((temp & PIPEACONF_ENABLE) == 0) { 343 REG_WRITE(map->conf, pipeconf); 344 345 /* Wait for for the pipe enable to take effect. */ 346 mdfldWaitForPipeEnable(dev, pipe); 347 } 348 349 /*workaround for sighting 3741701 Random X blank display*/ 350 /*perform w/a in video mode only on pipe A or C*/ 351 if (pipe == 0 || pipe == 2) { 352 REG_WRITE(map->status, REG_READ(map->status)); 353 msleep(100); 354 if (PIPE_VBLANK_STATUS & REG_READ(map->status)) 355 dev_dbg(dev->dev, "OK"); 356 else { 357 dev_dbg(dev->dev, "STUCK!!!!"); 358 /*shutdown controller*/ 359 temp = REG_READ(map->cntr); 360 REG_WRITE(map->cntr, 361 temp & ~DISPLAY_PLANE_ENABLE); 362 REG_WRITE(map->base, REG_READ(map->base)); 363 /*mdfld_dsi_dpi_shut_down(dev, pipe);*/ 364 REG_WRITE(0xb048, 1); 365 msleep(100); 366 temp = REG_READ(map->conf); 367 temp &= ~PIPEACONF_ENABLE; 368 REG_WRITE(map->conf, temp); 369 msleep(100); /*wait for pipe disable*/ 370 REG_WRITE(MIPI_DEVICE_READY_REG(pipe), 0); 371 msleep(100); 372 REG_WRITE(0xb004, REG_READ(0xb004)); 373 /* try to bring the controller back up again*/ 374 REG_WRITE(MIPI_DEVICE_READY_REG(pipe), 1); 375 temp = REG_READ(map->cntr); 376 REG_WRITE(map->cntr, 377 temp | DISPLAY_PLANE_ENABLE); 378 REG_WRITE(map->base, REG_READ(map->base)); 379 /*mdfld_dsi_dpi_turn_on(dev, pipe);*/ 380 REG_WRITE(0xb048, 2); 381 msleep(100); 382 temp = REG_READ(map->conf); 383 temp |= PIPEACONF_ENABLE; 384 REG_WRITE(map->conf, temp); 385 } 386 } 387 388 gma_crtc_load_lut(crtc); 389 390 /* Give the overlay scaler a chance to enable 391 if it's on this pipe */ 392 /* psb_intel_crtc_dpms_video(crtc, true); TODO */ 393 394 break; 395 case DRM_MODE_DPMS_OFF: 396 /* Give the overlay scaler a chance to disable 397 * if it's on this pipe */ 398 /* psb_intel_crtc_dpms_video(crtc, FALSE); TODO */ 399 if (pipe != 1) 400 mdfld_dsi_gen_fifo_ready(dev, 401 MIPI_GEN_FIFO_STAT_REG(pipe), 402 HS_CTRL_FIFO_EMPTY | HS_DATA_FIFO_EMPTY); 403 404 /* Disable the VGA plane that we never use */ 405 REG_WRITE(VGACNTRL, VGA_DISP_DISABLE); 406 407 /* Disable display plane */ 408 temp = REG_READ(map->cntr); 409 if ((temp & DISPLAY_PLANE_ENABLE) != 0) { 410 REG_WRITE(map->cntr, 411 temp & ~DISPLAY_PLANE_ENABLE); 412 /* Flush the plane changes */ 413 REG_WRITE(map->base, REG_READ(map->base)); 414 REG_READ(map->base); 415 } 416 417 /* Next, disable display pipes */ 418 temp = REG_READ(map->conf); 419 if ((temp & PIPEACONF_ENABLE) != 0) { 420 temp &= ~PIPEACONF_ENABLE; 421 temp |= PIPECONF_PLANE_OFF | PIPECONF_CURSOR_OFF; 422 REG_WRITE(map->conf, temp); 423 REG_READ(map->conf); 424 425 /* Wait for for the pipe disable to take effect. */ 426 mdfldWaitForPipeDisable(dev, pipe); 427 } 428 429 temp = REG_READ(map->dpll); 430 if (temp & DPLL_VCO_ENABLE) { 431 if ((pipe != 1 && !((REG_READ(PIPEACONF) 432 | REG_READ(PIPECCONF)) & PIPEACONF_ENABLE)) 433 || pipe == 1) { 434 temp &= ~(DPLL_VCO_ENABLE); 435 REG_WRITE(map->dpll, temp); 436 REG_READ(map->dpll); 437 /* Wait for the clocks to turn off. */ 438 /* FIXME_MDFLD PO may need more delay */ 439 udelay(500); 440 } 441 } 442 break; 443 } 444 gma_power_end(dev); 445} 446 447 448#define MDFLD_LIMT_DPLL_19 0 449#define MDFLD_LIMT_DPLL_25 1 450#define MDFLD_LIMT_DPLL_83 2 451#define MDFLD_LIMT_DPLL_100 3 452#define MDFLD_LIMT_DSIPLL_19 4 453#define MDFLD_LIMT_DSIPLL_25 5 454#define MDFLD_LIMT_DSIPLL_83 6 455#define MDFLD_LIMT_DSIPLL_100 7 456 457#define MDFLD_DOT_MIN 19750 458#define MDFLD_DOT_MAX 120000 459#define MDFLD_DPLL_M_MIN_19 113 460#define MDFLD_DPLL_M_MAX_19 155 461#define MDFLD_DPLL_P1_MIN_19 2 462#define MDFLD_DPLL_P1_MAX_19 10 463#define MDFLD_DPLL_M_MIN_25 101 464#define MDFLD_DPLL_M_MAX_25 130 465#define MDFLD_DPLL_P1_MIN_25 2 466#define MDFLD_DPLL_P1_MAX_25 10 467#define MDFLD_DPLL_M_MIN_83 64 468#define MDFLD_DPLL_M_MAX_83 64 469#define MDFLD_DPLL_P1_MIN_83 2 470#define MDFLD_DPLL_P1_MAX_83 2 471#define MDFLD_DPLL_M_MIN_100 64 472#define MDFLD_DPLL_M_MAX_100 64 473#define MDFLD_DPLL_P1_MIN_100 2 474#define MDFLD_DPLL_P1_MAX_100 2 475#define MDFLD_DSIPLL_M_MIN_19 131 476#define MDFLD_DSIPLL_M_MAX_19 175 477#define MDFLD_DSIPLL_P1_MIN_19 3 478#define MDFLD_DSIPLL_P1_MAX_19 8 479#define MDFLD_DSIPLL_M_MIN_25 97 480#define MDFLD_DSIPLL_M_MAX_25 140 481#define MDFLD_DSIPLL_P1_MIN_25 3 482#define MDFLD_DSIPLL_P1_MAX_25 9 483#define MDFLD_DSIPLL_M_MIN_83 33 484#define MDFLD_DSIPLL_M_MAX_83 92 485#define MDFLD_DSIPLL_P1_MIN_83 2 486#define MDFLD_DSIPLL_P1_MAX_83 3 487#define MDFLD_DSIPLL_M_MIN_100 97 488#define MDFLD_DSIPLL_M_MAX_100 140 489#define MDFLD_DSIPLL_P1_MIN_100 3 490#define MDFLD_DSIPLL_P1_MAX_100 9 491 492static const struct mrst_limit_t mdfld_limits[] = { 493 { /* MDFLD_LIMT_DPLL_19 */ 494 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 495 .m = {.min = MDFLD_DPLL_M_MIN_19, .max = MDFLD_DPLL_M_MAX_19}, 496 .p1 = {.min = MDFLD_DPLL_P1_MIN_19, .max = MDFLD_DPLL_P1_MAX_19}, 497 }, 498 { /* MDFLD_LIMT_DPLL_25 */ 499 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 500 .m = {.min = MDFLD_DPLL_M_MIN_25, .max = MDFLD_DPLL_M_MAX_25}, 501 .p1 = {.min = MDFLD_DPLL_P1_MIN_25, .max = MDFLD_DPLL_P1_MAX_25}, 502 }, 503 { /* MDFLD_LIMT_DPLL_83 */ 504 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 505 .m = {.min = MDFLD_DPLL_M_MIN_83, .max = MDFLD_DPLL_M_MAX_83}, 506 .p1 = {.min = MDFLD_DPLL_P1_MIN_83, .max = MDFLD_DPLL_P1_MAX_83}, 507 }, 508 { /* MDFLD_LIMT_DPLL_100 */ 509 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 510 .m = {.min = MDFLD_DPLL_M_MIN_100, .max = MDFLD_DPLL_M_MAX_100}, 511 .p1 = {.min = MDFLD_DPLL_P1_MIN_100, .max = MDFLD_DPLL_P1_MAX_100}, 512 }, 513 { /* MDFLD_LIMT_DSIPLL_19 */ 514 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 515 .m = {.min = MDFLD_DSIPLL_M_MIN_19, .max = MDFLD_DSIPLL_M_MAX_19}, 516 .p1 = {.min = MDFLD_DSIPLL_P1_MIN_19, .max = MDFLD_DSIPLL_P1_MAX_19}, 517 }, 518 { /* MDFLD_LIMT_DSIPLL_25 */ 519 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 520 .m = {.min = MDFLD_DSIPLL_M_MIN_25, .max = MDFLD_DSIPLL_M_MAX_25}, 521 .p1 = {.min = MDFLD_DSIPLL_P1_MIN_25, .max = MDFLD_DSIPLL_P1_MAX_25}, 522 }, 523 { /* MDFLD_LIMT_DSIPLL_83 */ 524 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 525 .m = {.min = MDFLD_DSIPLL_M_MIN_83, .max = MDFLD_DSIPLL_M_MAX_83}, 526 .p1 = {.min = MDFLD_DSIPLL_P1_MIN_83, .max = MDFLD_DSIPLL_P1_MAX_83}, 527 }, 528 { /* MDFLD_LIMT_DSIPLL_100 */ 529 .dot = {.min = MDFLD_DOT_MIN, .max = MDFLD_DOT_MAX}, 530 .m = {.min = MDFLD_DSIPLL_M_MIN_100, .max = MDFLD_DSIPLL_M_MAX_100}, 531 .p1 = {.min = MDFLD_DSIPLL_P1_MIN_100, .max = MDFLD_DSIPLL_P1_MAX_100}, 532 }, 533}; 534 535#define MDFLD_M_MIN 21 536#define MDFLD_M_MAX 180 537static const u32 mdfld_m_converts[] = { 538/* M configuration table from 9-bit LFSR table */ 539 224, 368, 440, 220, 366, 439, 219, 365, 182, 347, /* 21 - 30 */ 540 173, 342, 171, 85, 298, 149, 74, 37, 18, 265, /* 31 - 40 */ 541 388, 194, 353, 432, 216, 108, 310, 155, 333, 166, /* 41 - 50 */ 542 83, 41, 276, 138, 325, 162, 337, 168, 340, 170, /* 51 - 60 */ 543 341, 426, 469, 234, 373, 442, 221, 110, 311, 411, /* 61 - 70 */ 544 461, 486, 243, 377, 188, 350, 175, 343, 427, 213, /* 71 - 80 */ 545 106, 53, 282, 397, 354, 227, 113, 56, 284, 142, /* 81 - 90 */ 546 71, 35, 273, 136, 324, 418, 465, 488, 500, 506, /* 91 - 100 */ 547 253, 126, 63, 287, 399, 455, 483, 241, 376, 444, /* 101 - 110 */ 548 478, 495, 503, 251, 381, 446, 479, 239, 375, 443, /* 111 - 120 */ 549 477, 238, 119, 315, 157, 78, 295, 147, 329, 420, /* 121 - 130 */ 550 210, 105, 308, 154, 77, 38, 275, 137, 68, 290, /* 131 - 140 */ 551 145, 328, 164, 82, 297, 404, 458, 485, 498, 249, /* 141 - 150 */ 552 380, 190, 351, 431, 471, 235, 117, 314, 413, 206, /* 151 - 160 */ 553 103, 51, 25, 12, 262, 387, 193, 96, 48, 280, /* 161 - 170 */ 554 396, 198, 99, 305, 152, 76, 294, 403, 457, 228, /* 171 - 180 */ 555}; 556 557static const struct mrst_limit_t *mdfld_limit(struct drm_crtc *crtc) 558{ 559 const struct mrst_limit_t *limit = NULL; 560 struct drm_device *dev = crtc->dev; 561 struct drm_psb_private *dev_priv = dev->dev_private; 562 563 if (gma_pipe_has_type(crtc, INTEL_OUTPUT_MIPI) 564 || gma_pipe_has_type(crtc, INTEL_OUTPUT_MIPI2)) { 565 if ((ksel == KSEL_CRYSTAL_19) || (ksel == KSEL_BYPASS_19)) 566 limit = &mdfld_limits[MDFLD_LIMT_DSIPLL_19]; 567 else if (ksel == KSEL_BYPASS_25) 568 limit = &mdfld_limits[MDFLD_LIMT_DSIPLL_25]; 569 else if ((ksel == KSEL_BYPASS_83_100) && 570 (dev_priv->core_freq == 166)) 571 limit = &mdfld_limits[MDFLD_LIMT_DSIPLL_83]; 572 else if ((ksel == KSEL_BYPASS_83_100) && 573 (dev_priv->core_freq == 100 || 574 dev_priv->core_freq == 200)) 575 limit = &mdfld_limits[MDFLD_LIMT_DSIPLL_100]; 576 } else if (gma_pipe_has_type(crtc, INTEL_OUTPUT_HDMI)) { 577 if ((ksel == KSEL_CRYSTAL_19) || (ksel == KSEL_BYPASS_19)) 578 limit = &mdfld_limits[MDFLD_LIMT_DPLL_19]; 579 else if (ksel == KSEL_BYPASS_25) 580 limit = &mdfld_limits[MDFLD_LIMT_DPLL_25]; 581 else if ((ksel == KSEL_BYPASS_83_100) && 582 (dev_priv->core_freq == 166)) 583 limit = &mdfld_limits[MDFLD_LIMT_DPLL_83]; 584 else if ((ksel == KSEL_BYPASS_83_100) && 585 (dev_priv->core_freq == 100 || 586 dev_priv->core_freq == 200)) 587 limit = &mdfld_limits[MDFLD_LIMT_DPLL_100]; 588 } else { 589 limit = NULL; 590 dev_dbg(dev->dev, "mdfld_limit Wrong display type.\n"); 591 } 592 593 return limit; 594} 595 596/** Derive the pixel clock for the given refclk and divisors for 8xx chips. */ 597static void mdfld_clock(int refclk, struct mrst_clock_t *clock) 598{ 599 clock->dot = (refclk * clock->m) / clock->p1; 600} 601 602/** 603 * Returns a set of divisors for the desired target clock with the given refclk, 604 * or FALSE. Divisor values are the actual divisors for 605 */ 606static bool 607mdfldFindBestPLL(struct drm_crtc *crtc, int target, int refclk, 608 struct mrst_clock_t *best_clock) 609{ 610 struct mrst_clock_t clock; 611 const struct mrst_limit_t *limit = mdfld_limit(crtc); 612 int err = target; 613 614 memset(best_clock, 0, sizeof(*best_clock)); 615 616 for (clock.m = limit->m.min; clock.m <= limit->m.max; clock.m++) { 617 for (clock.p1 = limit->p1.min; clock.p1 <= limit->p1.max; 618 clock.p1++) { 619 int this_err; 620 621 mdfld_clock(refclk, &clock); 622 623 this_err = abs(clock.dot - target); 624 if (this_err < err) { 625 *best_clock = clock; 626 err = this_err; 627 } 628 } 629 } 630 return err != target; 631} 632 633static int mdfld_crtc_mode_set(struct drm_crtc *crtc, 634 struct drm_display_mode *mode, 635 struct drm_display_mode *adjusted_mode, 636 int x, int y, 637 struct drm_framebuffer *old_fb) 638{ 639 struct drm_device *dev = crtc->dev; 640 struct gma_crtc *gma_crtc = to_gma_crtc(crtc); 641 struct drm_psb_private *dev_priv = dev->dev_private; 642 int pipe = gma_crtc->pipe; 643 const struct psb_offset *map = &dev_priv->regmap[pipe]; 644 int refclk = 0; 645 int clk_n = 0, clk_p2 = 0, clk_byte = 1, clk = 0, m_conv = 0, 646 clk_tmp = 0; 647 struct mrst_clock_t clock; 648 bool ok; 649 u32 dpll = 0, fp = 0; 650 bool is_mipi = false, is_mipi2 = false, is_hdmi = false; 651 struct drm_mode_config *mode_config = &dev->mode_config; 652 struct gma_encoder *gma_encoder = NULL; 653 uint64_t scalingType = DRM_MODE_SCALE_FULLSCREEN; 654 struct drm_encoder *encoder; 655 struct drm_connector *connector; 656 int timeout = 0; 657 int ret; 658 659 dev_dbg(dev->dev, "pipe = 0x%x\n", pipe); 660 661 ret = check_fb(crtc->primary->fb); 662 if (ret) 663 return ret; 664 665 dev_dbg(dev->dev, "adjusted_hdisplay = %d\n", 666 adjusted_mode->hdisplay); 667 dev_dbg(dev->dev, "adjusted_vdisplay = %d\n", 668 adjusted_mode->vdisplay); 669 dev_dbg(dev->dev, "adjusted_hsync_start = %d\n", 670 adjusted_mode->hsync_start); 671 dev_dbg(dev->dev, "adjusted_hsync_end = %d\n", 672 adjusted_mode->hsync_end); 673 dev_dbg(dev->dev, "adjusted_htotal = %d\n", 674 adjusted_mode->htotal); 675 dev_dbg(dev->dev, "adjusted_vsync_start = %d\n", 676 adjusted_mode->vsync_start); 677 dev_dbg(dev->dev, "adjusted_vsync_end = %d\n", 678 adjusted_mode->vsync_end); 679 dev_dbg(dev->dev, "adjusted_vtotal = %d\n", 680 adjusted_mode->vtotal); 681 dev_dbg(dev->dev, "adjusted_clock = %d\n", 682 adjusted_mode->clock); 683 dev_dbg(dev->dev, "hdisplay = %d\n", 684 mode->hdisplay); 685 dev_dbg(dev->dev, "vdisplay = %d\n", 686 mode->vdisplay); 687 688 if (!gma_power_begin(dev, true)) 689 return 0; 690 691 memcpy(&gma_crtc->saved_mode, mode, 692 sizeof(struct drm_display_mode)); 693 memcpy(&gma_crtc->saved_adjusted_mode, adjusted_mode, 694 sizeof(struct drm_display_mode)); 695 696 list_for_each_entry(connector, &mode_config->connector_list, head) { 697 encoder = connector->encoder; 698 if (!encoder) 699 continue; 700 701 if (encoder->crtc != crtc) 702 continue; 703 704 gma_encoder = gma_attached_encoder(connector); 705 706 switch (gma_encoder->type) { 707 case INTEL_OUTPUT_MIPI: 708 is_mipi = true; 709 break; 710 case INTEL_OUTPUT_MIPI2: 711 is_mipi2 = true; 712 break; 713 case INTEL_OUTPUT_HDMI: 714 is_hdmi = true; 715 break; 716 } 717 } 718 719 /* Disable the VGA plane that we never use */ 720 REG_WRITE(VGACNTRL, VGA_DISP_DISABLE); 721 722 /* Disable the panel fitter if it was on our pipe */ 723 if (psb_intel_panel_fitter_pipe(dev) == pipe) 724 REG_WRITE(PFIT_CONTROL, 0); 725 726 /* pipesrc and dspsize control the size that is scaled from, 727 * which should always be the user's requested size. 728 */ 729 if (pipe == 1) { 730 /* FIXME: To make HDMI display with 864x480 (TPO), 480x864 731 * (PYR) or 480x854 (TMD), set the sprite width/height and 732 * souce image size registers with the adjusted mode for 733 * pipe B. 734 */ 735 736 /* 737 * The defined sprite rectangle must always be completely 738 * contained within the displayable area of the screen image 739 * (frame buffer). 740 */ 741 REG_WRITE(map->size, ((min(mode->crtc_vdisplay, adjusted_mode->crtc_vdisplay) - 1) << 16) 742 | (min(mode->crtc_hdisplay, adjusted_mode->crtc_hdisplay) - 1)); 743 /* Set the CRTC with encoder mode. */ 744 REG_WRITE(map->src, ((mode->crtc_hdisplay - 1) << 16) 745 | (mode->crtc_vdisplay - 1)); 746 } else { 747 REG_WRITE(map->size, 748 ((mode->crtc_vdisplay - 1) << 16) | 749 (mode->crtc_hdisplay - 1)); 750 REG_WRITE(map->src, 751 ((mode->crtc_hdisplay - 1) << 16) | 752 (mode->crtc_vdisplay - 1)); 753 } 754 755 REG_WRITE(map->pos, 0); 756 757 if (gma_encoder) 758 drm_object_property_get_value(&connector->base, 759 dev->mode_config.scaling_mode_property, &scalingType); 760 761 if (scalingType == DRM_MODE_SCALE_NO_SCALE) { 762 /* Medfield doesn't have register support for centering so we 763 * need to mess with the h/vblank and h/vsync start and ends 764 * to get centering 765 */ 766 int offsetX = 0, offsetY = 0; 767 768 offsetX = (adjusted_mode->crtc_hdisplay - 769 mode->crtc_hdisplay) / 2; 770 offsetY = (adjusted_mode->crtc_vdisplay - 771 mode->crtc_vdisplay) / 2; 772 773 REG_WRITE(map->htotal, (mode->crtc_hdisplay - 1) | 774 ((adjusted_mode->crtc_htotal - 1) << 16)); 775 REG_WRITE(map->vtotal, (mode->crtc_vdisplay - 1) | 776 ((adjusted_mode->crtc_vtotal - 1) << 16)); 777 REG_WRITE(map->hblank, (adjusted_mode->crtc_hblank_start - 778 offsetX - 1) | 779 ((adjusted_mode->crtc_hblank_end - offsetX - 1) << 16)); 780 REG_WRITE(map->hsync, (adjusted_mode->crtc_hsync_start - 781 offsetX - 1) | 782 ((adjusted_mode->crtc_hsync_end - offsetX - 1) << 16)); 783 REG_WRITE(map->vblank, (adjusted_mode->crtc_vblank_start - 784 offsetY - 1) | 785 ((adjusted_mode->crtc_vblank_end - offsetY - 1) << 16)); 786 REG_WRITE(map->vsync, (adjusted_mode->crtc_vsync_start - 787 offsetY - 1) | 788 ((adjusted_mode->crtc_vsync_end - offsetY - 1) << 16)); 789 } else { 790 REG_WRITE(map->htotal, (adjusted_mode->crtc_hdisplay - 1) | 791 ((adjusted_mode->crtc_htotal - 1) << 16)); 792 REG_WRITE(map->vtotal, (adjusted_mode->crtc_vdisplay - 1) | 793 ((adjusted_mode->crtc_vtotal - 1) << 16)); 794 REG_WRITE(map->hblank, (adjusted_mode->crtc_hblank_start - 1) | 795 ((adjusted_mode->crtc_hblank_end - 1) << 16)); 796 REG_WRITE(map->hsync, (adjusted_mode->crtc_hsync_start - 1) | 797 ((adjusted_mode->crtc_hsync_end - 1) << 16)); 798 REG_WRITE(map->vblank, (adjusted_mode->crtc_vblank_start - 1) | 799 ((adjusted_mode->crtc_vblank_end - 1) << 16)); 800 REG_WRITE(map->vsync, (adjusted_mode->crtc_vsync_start - 1) | 801 ((adjusted_mode->crtc_vsync_end - 1) << 16)); 802 } 803 804 /* Flush the plane changes */ 805 { 806 const struct drm_crtc_helper_funcs *crtc_funcs = 807 crtc->helper_private; 808 crtc_funcs->mode_set_base(crtc, x, y, old_fb); 809 } 810 811 /* setup pipeconf */ 812 dev_priv->pipeconf[pipe] = PIPEACONF_ENABLE; /* FIXME_JLIU7 REG_READ(pipeconf_reg); */ 813 814 /* Set up the display plane register */ 815 dev_priv->dspcntr[pipe] = REG_READ(map->cntr); 816 dev_priv->dspcntr[pipe] |= pipe << DISPPLANE_SEL_PIPE_POS; 817 dev_priv->dspcntr[pipe] |= DISPLAY_PLANE_ENABLE; 818 819 if (is_mipi2) 820 goto mrst_crtc_mode_set_exit; 821 clk = adjusted_mode->clock; 822 823 if (is_hdmi) { 824 if ((ksel == KSEL_CRYSTAL_19) || (ksel == KSEL_BYPASS_19)) { 825 refclk = 19200; 826 827 if (is_mipi || is_mipi2) 828 clk_n = 1, clk_p2 = 8; 829 else if (is_hdmi) 830 clk_n = 1, clk_p2 = 10; 831 } else if (ksel == KSEL_BYPASS_25) { 832 refclk = 25000; 833 834 if (is_mipi || is_mipi2) 835 clk_n = 1, clk_p2 = 8; 836 else if (is_hdmi) 837 clk_n = 1, clk_p2 = 10; 838 } else if ((ksel == KSEL_BYPASS_83_100) && 839 dev_priv->core_freq == 166) { 840 refclk = 83000; 841 842 if (is_mipi || is_mipi2) 843 clk_n = 4, clk_p2 = 8; 844 else if (is_hdmi) 845 clk_n = 4, clk_p2 = 10; 846 } else if ((ksel == KSEL_BYPASS_83_100) && 847 (dev_priv->core_freq == 100 || 848 dev_priv->core_freq == 200)) { 849 refclk = 100000; 850 if (is_mipi || is_mipi2) 851 clk_n = 4, clk_p2 = 8; 852 else if (is_hdmi) 853 clk_n = 4, clk_p2 = 10; 854 } 855 856 if (is_mipi) 857 clk_byte = dev_priv->bpp / 8; 858 else if (is_mipi2) 859 clk_byte = dev_priv->bpp2 / 8; 860 861 clk_tmp = clk * clk_n * clk_p2 * clk_byte; 862 863 dev_dbg(dev->dev, "clk = %d, clk_n = %d, clk_p2 = %d.\n", 864 clk, clk_n, clk_p2); 865 dev_dbg(dev->dev, "adjusted_mode->clock = %d, clk_tmp = %d.\n", 866 adjusted_mode->clock, clk_tmp); 867 868 ok = mdfldFindBestPLL(crtc, clk_tmp, refclk, &clock); 869 870 if (!ok) { 871 DRM_ERROR 872 ("mdfldFindBestPLL fail in mdfld_crtc_mode_set.\n"); 873 } else { 874 m_conv = mdfld_m_converts[(clock.m - MDFLD_M_MIN)]; 875 876 dev_dbg(dev->dev, "dot clock = %d," 877 "m = %d, p1 = %d, m_conv = %d.\n", 878 clock.dot, clock.m, 879 clock.p1, m_conv); 880 } 881 882 dpll = REG_READ(map->dpll); 883 884 if (dpll & DPLL_VCO_ENABLE) { 885 dpll &= ~DPLL_VCO_ENABLE; 886 REG_WRITE(map->dpll, dpll); 887 REG_READ(map->dpll); 888 889 /* FIXME jliu7 check the DPLL lock bit PIPEACONF[29] */ 890 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 891 udelay(500); 892 893 /* reset M1, N1 & P1 */ 894 REG_WRITE(map->fp0, 0); 895 dpll &= ~MDFLD_P1_MASK; 896 REG_WRITE(map->dpll, dpll); 897 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 898 udelay(500); 899 } 900 901 /* When ungating power of DPLL, needs to wait 0.5us before 902 * enable the VCO */ 903 if (dpll & MDFLD_PWR_GATE_EN) { 904 dpll &= ~MDFLD_PWR_GATE_EN; 905 REG_WRITE(map->dpll, dpll); 906 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 907 udelay(500); 908 } 909 dpll = 0; 910 911 if (is_hdmi) 912 dpll |= MDFLD_VCO_SEL; 913 914 fp = (clk_n / 2) << 16; 915 fp |= m_conv; 916 917 /* compute bitmask from p1 value */ 918 dpll |= (1 << (clock.p1 - 2)) << 17; 919 920 } else { 921 dpll = 0x00800000; 922 fp = 0x000000c1; 923 } 924 925 REG_WRITE(map->fp0, fp); 926 REG_WRITE(map->dpll, dpll); 927 /* FIXME_MDFLD PO - change 500 to 1 after PO */ 928 udelay(500); 929 930 dpll |= DPLL_VCO_ENABLE; 931 REG_WRITE(map->dpll, dpll); 932 REG_READ(map->dpll); 933 934 /* wait for DSI PLL to lock */ 935 while (timeout < 20000 && 936 !(REG_READ(map->conf) & PIPECONF_DSIPLL_LOCK)) { 937 udelay(150); 938 timeout++; 939 } 940 941 if (is_mipi) 942 goto mrst_crtc_mode_set_exit; 943 944 dev_dbg(dev->dev, "is_mipi = 0x%x\n", is_mipi); 945 946 REG_WRITE(map->conf, dev_priv->pipeconf[pipe]); 947 REG_READ(map->conf); 948 949 /* Wait for for the pipe enable to take effect. */ 950 REG_WRITE(map->cntr, dev_priv->dspcntr[pipe]); 951 gma_wait_for_vblank(dev); 952 953mrst_crtc_mode_set_exit: 954 955 gma_power_end(dev); 956 957 return 0; 958} 959 960const struct drm_crtc_helper_funcs mdfld_helper_funcs = { 961 .dpms = mdfld_crtc_dpms, 962 .mode_set = mdfld_crtc_mode_set, 963 .mode_set_base = mdfld__intel_pipe_set_base, 964 .prepare = gma_crtc_prepare, 965 .commit = gma_crtc_commit, 966}; 967