1 /* 2 * Copyright © 2006-2010 Intel Corporation 3 * Copyright (c) 2006 Dave Airlie <airlied@linux.ie> 4 * 5 * Permission is hereby granted, free of charge, to any person obtaining a 6 * copy of this software and associated documentation files (the "Software"), 7 * to deal in the Software without restriction, including without limitation 8 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 9 * and/or sell copies of the Software, and to permit persons to whom the 10 * Software is furnished to do so, subject to the following conditions: 11 * 12 * The above copyright notice and this permission notice (including the next 13 * paragraph) shall be included in all copies or substantial portions of the 14 * Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 22 * DEALINGS IN THE SOFTWARE. 23 * 24 * Authors: 25 * Eric Anholt <eric@anholt.net> 26 * Dave Airlie <airlied@linux.ie> 27 * Jesse Barnes <jesse.barnes@intel.com> 28 * Chris Wilson <chris@chris-wilson.co.uk> 29 */ 30 31 #define KBUILD_MODNAME "i915" 32 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 33 34 #include <linux/kernel.h> 35 #include <linux/moduleparam.h> 36 #include <linux/pwm.h> 37 #include "intel_drv.h" 38 39 #define CRC_PMIC_PWM_PERIOD_NS 21333 40 41 void 42 intel_fixed_panel_mode(const struct drm_display_mode *fixed_mode, 43 struct drm_display_mode *adjusted_mode) 44 { 45 drm_mode_copy(adjusted_mode, fixed_mode); 46 47 drm_mode_set_crtcinfo(adjusted_mode, 0); 48 } 49 50 /** 51 * intel_find_panel_downclock - find the reduced downclock for LVDS in EDID 52 * @dev: drm device 53 * @fixed_mode : panel native mode 54 * @connector: LVDS/eDP connector 55 * 56 * Return downclock_avail 57 * Find the reduced downclock for LVDS/eDP in EDID. 58 */ 59 struct drm_display_mode * 60 intel_find_panel_downclock(struct drm_device *dev, 61 struct drm_display_mode *fixed_mode, 62 struct drm_connector *connector) 63 { 64 struct drm_display_mode *scan, *tmp_mode; 65 int temp_downclock; 66 67 temp_downclock = fixed_mode->clock; 68 tmp_mode = NULL; 69 70 list_for_each_entry(scan, &connector->probed_modes, head) { 71 /* 72 * If one mode has the same resolution with the fixed_panel 73 * mode while they have the different refresh rate, it means 74 * that the reduced downclock is found. In such 75 * case we can set the different FPx0/1 to dynamically select 76 * between low and high frequency. 77 */ 78 if (scan->hdisplay == fixed_mode->hdisplay && 79 scan->hsync_start == fixed_mode->hsync_start && 80 scan->hsync_end == fixed_mode->hsync_end && 81 scan->htotal == fixed_mode->htotal && 82 scan->vdisplay == fixed_mode->vdisplay && 83 scan->vsync_start == fixed_mode->vsync_start && 84 scan->vsync_end == fixed_mode->vsync_end && 85 scan->vtotal == fixed_mode->vtotal) { 86 if (scan->clock < temp_downclock) { 87 /* 88 * The downclock is already found. But we 89 * expect to find the lower downclock. 90 */ 91 temp_downclock = scan->clock; 92 tmp_mode = scan; 93 } 94 } 95 } 96 97 if (temp_downclock < fixed_mode->clock) 98 return drm_mode_duplicate(dev, tmp_mode); 99 else 100 return NULL; 101 } 102 103 /* adjusted_mode has been preset to be the panel's fixed mode */ 104 void 105 intel_pch_panel_fitting(struct intel_crtc *intel_crtc, 106 struct intel_crtc_state *pipe_config, 107 int fitting_mode) 108 { 109 const struct drm_display_mode *adjusted_mode = &pipe_config->base.adjusted_mode; 110 int x = 0, y = 0, width = 0, height = 0; 111 112 /* Native modes don't need fitting */ 113 if (adjusted_mode->crtc_hdisplay == pipe_config->pipe_src_w && 114 adjusted_mode->crtc_vdisplay == pipe_config->pipe_src_h) 115 goto done; 116 117 switch (fitting_mode) { 118 case DRM_MODE_SCALE_CENTER: 119 width = pipe_config->pipe_src_w; 120 height = pipe_config->pipe_src_h; 121 x = (adjusted_mode->crtc_hdisplay - width + 1)/2; 122 y = (adjusted_mode->crtc_vdisplay - height + 1)/2; 123 break; 124 125 case DRM_MODE_SCALE_ASPECT: 126 /* Scale but preserve the aspect ratio */ 127 { 128 u32 scaled_width = adjusted_mode->crtc_hdisplay 129 * pipe_config->pipe_src_h; 130 u32 scaled_height = pipe_config->pipe_src_w 131 * adjusted_mode->crtc_vdisplay; 132 if (scaled_width > scaled_height) { /* pillar */ 133 width = scaled_height / pipe_config->pipe_src_h; 134 if (width & 1) 135 width++; 136 x = (adjusted_mode->crtc_hdisplay - width + 1) / 2; 137 y = 0; 138 height = adjusted_mode->crtc_vdisplay; 139 } else if (scaled_width < scaled_height) { /* letter */ 140 height = scaled_width / pipe_config->pipe_src_w; 141 if (height & 1) 142 height++; 143 y = (adjusted_mode->crtc_vdisplay - height + 1) / 2; 144 x = 0; 145 width = adjusted_mode->crtc_hdisplay; 146 } else { 147 x = y = 0; 148 width = adjusted_mode->crtc_hdisplay; 149 height = adjusted_mode->crtc_vdisplay; 150 } 151 } 152 break; 153 154 case DRM_MODE_SCALE_FULLSCREEN: 155 x = y = 0; 156 width = adjusted_mode->crtc_hdisplay; 157 height = adjusted_mode->crtc_vdisplay; 158 break; 159 160 default: 161 WARN(1, "bad panel fit mode: %d\n", fitting_mode); 162 return; 163 } 164 165 done: 166 pipe_config->pch_pfit.pos = (x << 16) | y; 167 pipe_config->pch_pfit.size = (width << 16) | height; 168 pipe_config->pch_pfit.enabled = pipe_config->pch_pfit.size != 0; 169 } 170 171 static void 172 centre_horizontally(struct drm_display_mode *adjusted_mode, 173 int width) 174 { 175 u32 border, sync_pos, blank_width, sync_width; 176 177 /* keep the hsync and hblank widths constant */ 178 sync_width = adjusted_mode->crtc_hsync_end - adjusted_mode->crtc_hsync_start; 179 blank_width = adjusted_mode->crtc_hblank_end - adjusted_mode->crtc_hblank_start; 180 sync_pos = (blank_width - sync_width + 1) / 2; 181 182 border = (adjusted_mode->crtc_hdisplay - width + 1) / 2; 183 border += border & 1; /* make the border even */ 184 185 adjusted_mode->crtc_hdisplay = width; 186 adjusted_mode->crtc_hblank_start = width + border; 187 adjusted_mode->crtc_hblank_end = adjusted_mode->crtc_hblank_start + blank_width; 188 189 adjusted_mode->crtc_hsync_start = adjusted_mode->crtc_hblank_start + sync_pos; 190 adjusted_mode->crtc_hsync_end = adjusted_mode->crtc_hsync_start + sync_width; 191 } 192 193 static void 194 centre_vertically(struct drm_display_mode *adjusted_mode, 195 int height) 196 { 197 u32 border, sync_pos, blank_width, sync_width; 198 199 /* keep the vsync and vblank widths constant */ 200 sync_width = adjusted_mode->crtc_vsync_end - adjusted_mode->crtc_vsync_start; 201 blank_width = adjusted_mode->crtc_vblank_end - adjusted_mode->crtc_vblank_start; 202 sync_pos = (blank_width - sync_width + 1) / 2; 203 204 border = (adjusted_mode->crtc_vdisplay - height + 1) / 2; 205 206 adjusted_mode->crtc_vdisplay = height; 207 adjusted_mode->crtc_vblank_start = height + border; 208 adjusted_mode->crtc_vblank_end = adjusted_mode->crtc_vblank_start + blank_width; 209 210 adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vblank_start + sync_pos; 211 adjusted_mode->crtc_vsync_end = adjusted_mode->crtc_vsync_start + sync_width; 212 } 213 214 static inline u32 panel_fitter_scaling(u32 source, u32 target) 215 { 216 /* 217 * Floating point operation is not supported. So the FACTOR 218 * is defined, which can avoid the floating point computation 219 * when calculating the panel ratio. 220 */ 221 #define ACCURACY 12 222 #define FACTOR (1 << ACCURACY) 223 u32 ratio = source * FACTOR / target; 224 return (FACTOR * ratio + FACTOR/2) / FACTOR; 225 } 226 227 static void i965_scale_aspect(struct intel_crtc_state *pipe_config, 228 u32 *pfit_control) 229 { 230 const struct drm_display_mode *adjusted_mode = &pipe_config->base.adjusted_mode; 231 u32 scaled_width = adjusted_mode->crtc_hdisplay * 232 pipe_config->pipe_src_h; 233 u32 scaled_height = pipe_config->pipe_src_w * 234 adjusted_mode->crtc_vdisplay; 235 236 /* 965+ is easy, it does everything in hw */ 237 if (scaled_width > scaled_height) 238 *pfit_control |= PFIT_ENABLE | 239 PFIT_SCALING_PILLAR; 240 else if (scaled_width < scaled_height) 241 *pfit_control |= PFIT_ENABLE | 242 PFIT_SCALING_LETTER; 243 else if (adjusted_mode->crtc_hdisplay != pipe_config->pipe_src_w) 244 *pfit_control |= PFIT_ENABLE | PFIT_SCALING_AUTO; 245 } 246 247 static void i9xx_scale_aspect(struct intel_crtc_state *pipe_config, 248 u32 *pfit_control, u32 *pfit_pgm_ratios, 249 u32 *border) 250 { 251 struct drm_display_mode *adjusted_mode = &pipe_config->base.adjusted_mode; 252 u32 scaled_width = adjusted_mode->crtc_hdisplay * 253 pipe_config->pipe_src_h; 254 u32 scaled_height = pipe_config->pipe_src_w * 255 adjusted_mode->crtc_vdisplay; 256 u32 bits; 257 258 /* 259 * For earlier chips we have to calculate the scaling 260 * ratio by hand and program it into the 261 * PFIT_PGM_RATIO register 262 */ 263 if (scaled_width > scaled_height) { /* pillar */ 264 centre_horizontally(adjusted_mode, 265 scaled_height / 266 pipe_config->pipe_src_h); 267 268 *border = LVDS_BORDER_ENABLE; 269 if (pipe_config->pipe_src_h != adjusted_mode->crtc_vdisplay) { 270 bits = panel_fitter_scaling(pipe_config->pipe_src_h, 271 adjusted_mode->crtc_vdisplay); 272 273 *pfit_pgm_ratios |= (bits << PFIT_HORIZ_SCALE_SHIFT | 274 bits << PFIT_VERT_SCALE_SHIFT); 275 *pfit_control |= (PFIT_ENABLE | 276 VERT_INTERP_BILINEAR | 277 HORIZ_INTERP_BILINEAR); 278 } 279 } else if (scaled_width < scaled_height) { /* letter */ 280 centre_vertically(adjusted_mode, 281 scaled_width / 282 pipe_config->pipe_src_w); 283 284 *border = LVDS_BORDER_ENABLE; 285 if (pipe_config->pipe_src_w != adjusted_mode->crtc_hdisplay) { 286 bits = panel_fitter_scaling(pipe_config->pipe_src_w, 287 adjusted_mode->crtc_hdisplay); 288 289 *pfit_pgm_ratios |= (bits << PFIT_HORIZ_SCALE_SHIFT | 290 bits << PFIT_VERT_SCALE_SHIFT); 291 *pfit_control |= (PFIT_ENABLE | 292 VERT_INTERP_BILINEAR | 293 HORIZ_INTERP_BILINEAR); 294 } 295 } else { 296 /* Aspects match, Let hw scale both directions */ 297 *pfit_control |= (PFIT_ENABLE | 298 VERT_AUTO_SCALE | HORIZ_AUTO_SCALE | 299 VERT_INTERP_BILINEAR | 300 HORIZ_INTERP_BILINEAR); 301 } 302 } 303 304 void intel_gmch_panel_fitting(struct intel_crtc *intel_crtc, 305 struct intel_crtc_state *pipe_config, 306 int fitting_mode) 307 { 308 struct drm_device *dev = intel_crtc->base.dev; 309 u32 pfit_control = 0, pfit_pgm_ratios = 0, border = 0; 310 struct drm_display_mode *adjusted_mode = &pipe_config->base.adjusted_mode; 311 312 /* Native modes don't need fitting */ 313 if (adjusted_mode->crtc_hdisplay == pipe_config->pipe_src_w && 314 adjusted_mode->crtc_vdisplay == pipe_config->pipe_src_h) 315 goto out; 316 317 switch (fitting_mode) { 318 case DRM_MODE_SCALE_CENTER: 319 /* 320 * For centered modes, we have to calculate border widths & 321 * heights and modify the values programmed into the CRTC. 322 */ 323 centre_horizontally(adjusted_mode, pipe_config->pipe_src_w); 324 centre_vertically(adjusted_mode, pipe_config->pipe_src_h); 325 border = LVDS_BORDER_ENABLE; 326 break; 327 case DRM_MODE_SCALE_ASPECT: 328 /* Scale but preserve the aspect ratio */ 329 if (INTEL_INFO(dev)->gen >= 4) 330 i965_scale_aspect(pipe_config, &pfit_control); 331 else 332 i9xx_scale_aspect(pipe_config, &pfit_control, 333 &pfit_pgm_ratios, &border); 334 break; 335 case DRM_MODE_SCALE_FULLSCREEN: 336 /* 337 * Full scaling, even if it changes the aspect ratio. 338 * Fortunately this is all done for us in hw. 339 */ 340 if (pipe_config->pipe_src_h != adjusted_mode->crtc_vdisplay || 341 pipe_config->pipe_src_w != adjusted_mode->crtc_hdisplay) { 342 pfit_control |= PFIT_ENABLE; 343 if (INTEL_INFO(dev)->gen >= 4) 344 pfit_control |= PFIT_SCALING_AUTO; 345 else 346 pfit_control |= (VERT_AUTO_SCALE | 347 VERT_INTERP_BILINEAR | 348 HORIZ_AUTO_SCALE | 349 HORIZ_INTERP_BILINEAR); 350 } 351 break; 352 default: 353 WARN(1, "bad panel fit mode: %d\n", fitting_mode); 354 return; 355 } 356 357 /* 965+ wants fuzzy fitting */ 358 /* FIXME: handle multiple panels by failing gracefully */ 359 if (INTEL_INFO(dev)->gen >= 4) 360 pfit_control |= ((intel_crtc->pipe << PFIT_PIPE_SHIFT) | 361 PFIT_FILTER_FUZZY); 362 363 out: 364 if ((pfit_control & PFIT_ENABLE) == 0) { 365 pfit_control = 0; 366 pfit_pgm_ratios = 0; 367 } 368 369 /* Make sure pre-965 set dither correctly for 18bpp panels. */ 370 if (INTEL_INFO(dev)->gen < 4 && pipe_config->pipe_bpp == 18) 371 pfit_control |= PANEL_8TO6_DITHER_ENABLE; 372 373 pipe_config->gmch_pfit.control = pfit_control; 374 pipe_config->gmch_pfit.pgm_ratios = pfit_pgm_ratios; 375 pipe_config->gmch_pfit.lvds_border_bits = border; 376 } 377 378 enum drm_connector_status 379 intel_panel_detect(struct drm_device *dev) 380 { 381 struct drm_i915_private *dev_priv = to_i915(dev); 382 383 /* Assume that the BIOS does not lie through the OpRegion... */ 384 if (!i915.panel_ignore_lid && dev_priv->opregion.lid_state) { 385 return *dev_priv->opregion.lid_state & 0x1 ? 386 connector_status_connected : 387 connector_status_disconnected; 388 } 389 390 switch (i915.panel_ignore_lid) { 391 case -2: 392 return connector_status_connected; 393 case -1: 394 return connector_status_disconnected; 395 default: 396 return connector_status_unknown; 397 } 398 } 399 400 /** 401 * scale - scale values from one range to another 402 * 403 * @source_val: value in range [@source_min..@source_max] 404 * 405 * Return @source_val in range [@source_min..@source_max] scaled to range 406 * [@target_min..@target_max]. 407 */ 408 static uint32_t scale(uint32_t source_val, 409 uint32_t source_min, uint32_t source_max, 410 uint32_t target_min, uint32_t target_max) 411 { 412 uint64_t target_val; 413 414 WARN_ON(source_min > source_max); 415 WARN_ON(target_min > target_max); 416 417 /* defensive */ 418 source_val = clamp(source_val, source_min, source_max); 419 420 /* avoid overflows */ 421 target_val = DIV_ROUND_CLOSEST_ULL((uint64_t)(source_val - source_min) * 422 (target_max - target_min), source_max - source_min); 423 target_val += target_min; 424 425 return target_val; 426 } 427 428 /* Scale user_level in range [0..user_max] to [hw_min..hw_max]. */ 429 static inline u32 scale_user_to_hw(struct intel_connector *connector, 430 u32 user_level, u32 user_max) 431 { 432 struct intel_panel *panel = &connector->panel; 433 434 return scale(user_level, 0, user_max, 435 panel->backlight.min, panel->backlight.max); 436 } 437 438 /* Scale user_level in range [0..user_max] to [0..hw_max], clamping the result 439 * to [hw_min..hw_max]. */ 440 static inline u32 clamp_user_to_hw(struct intel_connector *connector, 441 u32 user_level, u32 user_max) 442 { 443 struct intel_panel *panel = &connector->panel; 444 u32 hw_level; 445 446 hw_level = scale(user_level, 0, user_max, 0, panel->backlight.max); 447 hw_level = clamp(hw_level, panel->backlight.min, panel->backlight.max); 448 449 return hw_level; 450 } 451 452 /* Scale hw_level in range [hw_min..hw_max] to [0..user_max]. */ 453 static inline u32 scale_hw_to_user(struct intel_connector *connector, 454 u32 hw_level, u32 user_max) 455 { 456 struct intel_panel *panel = &connector->panel; 457 458 return scale(hw_level, panel->backlight.min, panel->backlight.max, 459 0, user_max); 460 } 461 462 static u32 intel_panel_compute_brightness(struct intel_connector *connector, 463 u32 val) 464 { 465 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 466 struct intel_panel *panel = &connector->panel; 467 468 WARN_ON(panel->backlight.max == 0); 469 470 if (i915.invert_brightness < 0) 471 return val; 472 473 if (i915.invert_brightness > 0 || 474 dev_priv->quirks & QUIRK_INVERT_BRIGHTNESS) { 475 return panel->backlight.max - val; 476 } 477 478 return val; 479 } 480 481 static u32 lpt_get_backlight(struct intel_connector *connector) 482 { 483 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 484 485 return I915_READ(BLC_PWM_PCH_CTL2) & BACKLIGHT_DUTY_CYCLE_MASK; 486 } 487 488 static u32 pch_get_backlight(struct intel_connector *connector) 489 { 490 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 491 492 return I915_READ(BLC_PWM_CPU_CTL) & BACKLIGHT_DUTY_CYCLE_MASK; 493 } 494 495 static u32 i9xx_get_backlight(struct intel_connector *connector) 496 { 497 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 498 struct intel_panel *panel = &connector->panel; 499 u32 val; 500 501 val = I915_READ(BLC_PWM_CTL) & BACKLIGHT_DUTY_CYCLE_MASK; 502 if (INTEL_INFO(dev_priv)->gen < 4) 503 val >>= 1; 504 505 if (panel->backlight.combination_mode) { 506 u8 lbpc; 507 508 pci_read_config_byte(dev_priv->drm.pdev, LBPC, &lbpc); 509 val *= lbpc; 510 } 511 512 return val; 513 } 514 515 static u32 _vlv_get_backlight(struct drm_i915_private *dev_priv, enum i915_pipe pipe) 516 { 517 if (WARN_ON(pipe != PIPE_A && pipe != PIPE_B)) 518 return 0; 519 520 return I915_READ(VLV_BLC_PWM_CTL(pipe)) & BACKLIGHT_DUTY_CYCLE_MASK; 521 } 522 523 static u32 vlv_get_backlight(struct intel_connector *connector) 524 { 525 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 526 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 527 528 return _vlv_get_backlight(dev_priv, pipe); 529 } 530 531 static u32 bxt_get_backlight(struct intel_connector *connector) 532 { 533 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 534 struct intel_panel *panel = &connector->panel; 535 536 return I915_READ(BXT_BLC_PWM_DUTY(panel->backlight.controller)); 537 } 538 539 static u32 pwm_get_backlight(struct intel_connector *connector) 540 { 541 struct intel_panel *panel = &connector->panel; 542 int duty_ns; 543 544 duty_ns = pwm_get_duty_cycle(panel->backlight.pwm); 545 return DIV_ROUND_UP(duty_ns * 100, CRC_PMIC_PWM_PERIOD_NS); 546 } 547 548 #if 0 549 static u32 intel_panel_get_backlight(struct intel_connector *connector) 550 { 551 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 552 struct intel_panel *panel = &connector->panel; 553 u32 val = 0; 554 555 mutex_lock(&dev_priv->backlight_lock); 556 557 if (panel->backlight.enabled) { 558 val = panel->backlight.get(connector); 559 val = intel_panel_compute_brightness(connector, val); 560 } 561 562 mutex_unlock(&dev_priv->backlight_lock); 563 564 DRM_DEBUG_DRIVER("get backlight PWM = %d\n", val); 565 return val; 566 } 567 #endif 568 569 static void lpt_set_backlight(struct intel_connector *connector, u32 level) 570 { 571 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 572 u32 val = I915_READ(BLC_PWM_PCH_CTL2) & ~BACKLIGHT_DUTY_CYCLE_MASK; 573 I915_WRITE(BLC_PWM_PCH_CTL2, val | level); 574 } 575 576 static void pch_set_backlight(struct intel_connector *connector, u32 level) 577 { 578 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 579 u32 tmp; 580 581 tmp = I915_READ(BLC_PWM_CPU_CTL) & ~BACKLIGHT_DUTY_CYCLE_MASK; 582 I915_WRITE(BLC_PWM_CPU_CTL, tmp | level); 583 } 584 585 static void i9xx_set_backlight(struct intel_connector *connector, u32 level) 586 { 587 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 588 struct intel_panel *panel = &connector->panel; 589 u32 tmp, mask; 590 591 WARN_ON(panel->backlight.max == 0); 592 593 if (panel->backlight.combination_mode) { 594 u8 lbpc; 595 596 lbpc = level * 0xfe / panel->backlight.max + 1; 597 level /= lbpc; 598 pci_write_config_byte(dev_priv->drm.pdev, LBPC, lbpc); 599 } 600 601 if (IS_GEN4(dev_priv)) { 602 mask = BACKLIGHT_DUTY_CYCLE_MASK; 603 } else { 604 level <<= 1; 605 mask = BACKLIGHT_DUTY_CYCLE_MASK_PNV; 606 } 607 608 tmp = I915_READ(BLC_PWM_CTL) & ~mask; 609 I915_WRITE(BLC_PWM_CTL, tmp | level); 610 } 611 612 static void vlv_set_backlight(struct intel_connector *connector, u32 level) 613 { 614 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 615 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 616 u32 tmp; 617 618 if (WARN_ON(pipe != PIPE_A && pipe != PIPE_B)) 619 return; 620 621 tmp = I915_READ(VLV_BLC_PWM_CTL(pipe)) & ~BACKLIGHT_DUTY_CYCLE_MASK; 622 I915_WRITE(VLV_BLC_PWM_CTL(pipe), tmp | level); 623 } 624 625 static void bxt_set_backlight(struct intel_connector *connector, u32 level) 626 { 627 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 628 struct intel_panel *panel = &connector->panel; 629 630 I915_WRITE(BXT_BLC_PWM_DUTY(panel->backlight.controller), level); 631 } 632 633 static void pwm_set_backlight(struct intel_connector *connector, u32 level) 634 { 635 struct intel_panel *panel = &connector->panel; 636 int duty_ns = DIV_ROUND_UP(level * CRC_PMIC_PWM_PERIOD_NS, 100); 637 638 pwm_config(panel->backlight.pwm, duty_ns, CRC_PMIC_PWM_PERIOD_NS); 639 } 640 641 static void 642 intel_panel_actually_set_backlight(struct intel_connector *connector, u32 level) 643 { 644 struct intel_panel *panel = &connector->panel; 645 646 DRM_DEBUG_DRIVER("set backlight PWM = %d\n", level); 647 648 level = intel_panel_compute_brightness(connector, level); 649 panel->backlight.set(connector, level); 650 } 651 652 /* set backlight brightness to level in range [0..max], scaling wrt hw min */ 653 static void intel_panel_set_backlight(struct intel_connector *connector, 654 u32 user_level, u32 user_max) 655 { 656 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 657 struct intel_panel *panel = &connector->panel; 658 u32 hw_level; 659 660 if (!panel->backlight.present) 661 return; 662 663 mutex_lock(&dev_priv->backlight_lock); 664 665 WARN_ON(panel->backlight.max == 0); 666 667 hw_level = scale_user_to_hw(connector, user_level, user_max); 668 panel->backlight.level = hw_level; 669 670 if (panel->backlight.enabled) 671 intel_panel_actually_set_backlight(connector, hw_level); 672 673 mutex_unlock(&dev_priv->backlight_lock); 674 } 675 676 /* set backlight brightness to level in range [0..max], assuming hw min is 677 * respected. 678 */ 679 void intel_panel_set_backlight_acpi(struct intel_connector *connector, 680 u32 user_level, u32 user_max) 681 { 682 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 683 struct intel_panel *panel = &connector->panel; 684 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 685 u32 hw_level; 686 687 /* 688 * INVALID_PIPE may occur during driver init because 689 * connection_mutex isn't held across the entire backlight 690 * setup + modeset readout, and the BIOS can issue the 691 * requests at any time. 692 */ 693 if (!panel->backlight.present || pipe == INVALID_PIPE) 694 return; 695 696 mutex_lock(&dev_priv->backlight_lock); 697 698 WARN_ON(panel->backlight.max == 0); 699 700 hw_level = clamp_user_to_hw(connector, user_level, user_max); 701 panel->backlight.level = hw_level; 702 703 if (panel->backlight.device) 704 panel->backlight.device->props.brightness = 705 scale_hw_to_user(connector, 706 panel->backlight.level, 707 panel->backlight.device->props.max_brightness); 708 709 if (panel->backlight.enabled) 710 intel_panel_actually_set_backlight(connector, hw_level); 711 712 mutex_unlock(&dev_priv->backlight_lock); 713 } 714 715 static void lpt_disable_backlight(struct intel_connector *connector) 716 { 717 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 718 u32 tmp; 719 720 intel_panel_actually_set_backlight(connector, 0); 721 722 /* 723 * Although we don't support or enable CPU PWM with LPT/SPT based 724 * systems, it may have been enabled prior to loading the 725 * driver. Disable to avoid warnings on LCPLL disable. 726 * 727 * This needs rework if we need to add support for CPU PWM on PCH split 728 * platforms. 729 */ 730 tmp = I915_READ(BLC_PWM_CPU_CTL2); 731 if (tmp & BLM_PWM_ENABLE) { 732 DRM_DEBUG_KMS("cpu backlight was enabled, disabling\n"); 733 I915_WRITE(BLC_PWM_CPU_CTL2, tmp & ~BLM_PWM_ENABLE); 734 } 735 736 tmp = I915_READ(BLC_PWM_PCH_CTL1); 737 I915_WRITE(BLC_PWM_PCH_CTL1, tmp & ~BLM_PCH_PWM_ENABLE); 738 } 739 740 static void pch_disable_backlight(struct intel_connector *connector) 741 { 742 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 743 u32 tmp; 744 745 intel_panel_actually_set_backlight(connector, 0); 746 747 tmp = I915_READ(BLC_PWM_CPU_CTL2); 748 I915_WRITE(BLC_PWM_CPU_CTL2, tmp & ~BLM_PWM_ENABLE); 749 750 tmp = I915_READ(BLC_PWM_PCH_CTL1); 751 I915_WRITE(BLC_PWM_PCH_CTL1, tmp & ~BLM_PCH_PWM_ENABLE); 752 } 753 754 static void i9xx_disable_backlight(struct intel_connector *connector) 755 { 756 intel_panel_actually_set_backlight(connector, 0); 757 } 758 759 static void i965_disable_backlight(struct intel_connector *connector) 760 { 761 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 762 u32 tmp; 763 764 intel_panel_actually_set_backlight(connector, 0); 765 766 tmp = I915_READ(BLC_PWM_CTL2); 767 I915_WRITE(BLC_PWM_CTL2, tmp & ~BLM_PWM_ENABLE); 768 } 769 770 static void vlv_disable_backlight(struct intel_connector *connector) 771 { 772 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 773 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 774 u32 tmp; 775 776 if (WARN_ON(pipe != PIPE_A && pipe != PIPE_B)) 777 return; 778 779 intel_panel_actually_set_backlight(connector, 0); 780 781 tmp = I915_READ(VLV_BLC_PWM_CTL2(pipe)); 782 I915_WRITE(VLV_BLC_PWM_CTL2(pipe), tmp & ~BLM_PWM_ENABLE); 783 } 784 785 static void bxt_disable_backlight(struct intel_connector *connector) 786 { 787 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 788 struct intel_panel *panel = &connector->panel; 789 u32 tmp, val; 790 791 intel_panel_actually_set_backlight(connector, 0); 792 793 tmp = I915_READ(BXT_BLC_PWM_CTL(panel->backlight.controller)); 794 I915_WRITE(BXT_BLC_PWM_CTL(panel->backlight.controller), 795 tmp & ~BXT_BLC_PWM_ENABLE); 796 797 if (panel->backlight.controller == 1) { 798 val = I915_READ(UTIL_PIN_CTL); 799 val &= ~UTIL_PIN_ENABLE; 800 I915_WRITE(UTIL_PIN_CTL, val); 801 } 802 } 803 804 static void pwm_disable_backlight(struct intel_connector *connector) 805 { 806 struct intel_panel *panel = &connector->panel; 807 808 /* Disable the backlight */ 809 pwm_config(panel->backlight.pwm, 0, CRC_PMIC_PWM_PERIOD_NS); 810 usleep_range(2000, 3000); 811 pwm_disable(panel->backlight.pwm); 812 } 813 814 void intel_panel_disable_backlight(struct intel_connector *connector) 815 { 816 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 817 struct intel_panel *panel = &connector->panel; 818 819 if (!panel->backlight.present) 820 return; 821 822 /* 823 * Do not disable backlight on the vga_switcheroo path. When switching 824 * away from i915, the other client may depend on i915 to handle the 825 * backlight. This will leave the backlight on unnecessarily when 826 * another client is not activated. 827 */ 828 if (dev_priv->drm.switch_power_state == DRM_SWITCH_POWER_CHANGING) { 829 DRM_DEBUG_DRIVER("Skipping backlight disable on vga switch\n"); 830 return; 831 } 832 833 mutex_lock(&dev_priv->backlight_lock); 834 835 if (panel->backlight.device) 836 panel->backlight.device->props.power = FB_BLANK_POWERDOWN; 837 panel->backlight.enabled = false; 838 panel->backlight.disable(connector); 839 840 mutex_unlock(&dev_priv->backlight_lock); 841 } 842 843 static void lpt_enable_backlight(struct intel_connector *connector) 844 { 845 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 846 struct intel_panel *panel = &connector->panel; 847 u32 pch_ctl1, pch_ctl2, schicken; 848 849 pch_ctl1 = I915_READ(BLC_PWM_PCH_CTL1); 850 if (pch_ctl1 & BLM_PCH_PWM_ENABLE) { 851 DRM_DEBUG_KMS("pch backlight already enabled\n"); 852 pch_ctl1 &= ~BLM_PCH_PWM_ENABLE; 853 I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1); 854 } 855 856 if (HAS_PCH_LPT(dev_priv)) { 857 schicken = I915_READ(SOUTH_CHICKEN2); 858 if (panel->backlight.alternate_pwm_increment) 859 schicken |= LPT_PWM_GRANULARITY; 860 else 861 schicken &= ~LPT_PWM_GRANULARITY; 862 I915_WRITE(SOUTH_CHICKEN2, schicken); 863 } else { 864 schicken = I915_READ(SOUTH_CHICKEN1); 865 if (panel->backlight.alternate_pwm_increment) 866 schicken |= SPT_PWM_GRANULARITY; 867 else 868 schicken &= ~SPT_PWM_GRANULARITY; 869 I915_WRITE(SOUTH_CHICKEN1, schicken); 870 } 871 872 pch_ctl2 = panel->backlight.max << 16; 873 I915_WRITE(BLC_PWM_PCH_CTL2, pch_ctl2); 874 875 pch_ctl1 = 0; 876 if (panel->backlight.active_low_pwm) 877 pch_ctl1 |= BLM_PCH_POLARITY; 878 879 /* After LPT, override is the default. */ 880 if (HAS_PCH_LPT(dev_priv)) 881 pch_ctl1 |= BLM_PCH_OVERRIDE_ENABLE; 882 883 I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1); 884 POSTING_READ(BLC_PWM_PCH_CTL1); 885 I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1 | BLM_PCH_PWM_ENABLE); 886 887 /* This won't stick until the above enable. */ 888 intel_panel_actually_set_backlight(connector, panel->backlight.level); 889 } 890 891 static void pch_enable_backlight(struct intel_connector *connector) 892 { 893 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 894 struct intel_panel *panel = &connector->panel; 895 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 896 enum transcoder cpu_transcoder = 897 intel_pipe_to_cpu_transcoder(dev_priv, pipe); 898 u32 cpu_ctl2, pch_ctl1, pch_ctl2; 899 900 cpu_ctl2 = I915_READ(BLC_PWM_CPU_CTL2); 901 if (cpu_ctl2 & BLM_PWM_ENABLE) { 902 DRM_DEBUG_KMS("cpu backlight already enabled\n"); 903 cpu_ctl2 &= ~BLM_PWM_ENABLE; 904 I915_WRITE(BLC_PWM_CPU_CTL2, cpu_ctl2); 905 } 906 907 pch_ctl1 = I915_READ(BLC_PWM_PCH_CTL1); 908 if (pch_ctl1 & BLM_PCH_PWM_ENABLE) { 909 DRM_DEBUG_KMS("pch backlight already enabled\n"); 910 pch_ctl1 &= ~BLM_PCH_PWM_ENABLE; 911 I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1); 912 } 913 914 if (cpu_transcoder == TRANSCODER_EDP) 915 cpu_ctl2 = BLM_TRANSCODER_EDP; 916 else 917 cpu_ctl2 = BLM_PIPE(cpu_transcoder); 918 I915_WRITE(BLC_PWM_CPU_CTL2, cpu_ctl2); 919 POSTING_READ(BLC_PWM_CPU_CTL2); 920 I915_WRITE(BLC_PWM_CPU_CTL2, cpu_ctl2 | BLM_PWM_ENABLE); 921 922 /* This won't stick until the above enable. */ 923 intel_panel_actually_set_backlight(connector, panel->backlight.level); 924 925 pch_ctl2 = panel->backlight.max << 16; 926 I915_WRITE(BLC_PWM_PCH_CTL2, pch_ctl2); 927 928 pch_ctl1 = 0; 929 if (panel->backlight.active_low_pwm) 930 pch_ctl1 |= BLM_PCH_POLARITY; 931 932 I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1); 933 POSTING_READ(BLC_PWM_PCH_CTL1); 934 I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1 | BLM_PCH_PWM_ENABLE); 935 } 936 937 static void i9xx_enable_backlight(struct intel_connector *connector) 938 { 939 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 940 struct intel_panel *panel = &connector->panel; 941 u32 ctl, freq; 942 943 ctl = I915_READ(BLC_PWM_CTL); 944 if (ctl & BACKLIGHT_DUTY_CYCLE_MASK_PNV) { 945 DRM_DEBUG_KMS("backlight already enabled\n"); 946 I915_WRITE(BLC_PWM_CTL, 0); 947 } 948 949 freq = panel->backlight.max; 950 if (panel->backlight.combination_mode) 951 freq /= 0xff; 952 953 ctl = freq << 17; 954 if (panel->backlight.combination_mode) 955 ctl |= BLM_LEGACY_MODE; 956 if (IS_PINEVIEW(dev_priv) && panel->backlight.active_low_pwm) 957 ctl |= BLM_POLARITY_PNV; 958 959 I915_WRITE(BLC_PWM_CTL, ctl); 960 POSTING_READ(BLC_PWM_CTL); 961 962 /* XXX: combine this into above write? */ 963 intel_panel_actually_set_backlight(connector, panel->backlight.level); 964 965 /* 966 * Needed to enable backlight on some 855gm models. BLC_HIST_CTL is 967 * 855gm only, but checking for gen2 is safe, as 855gm is the only gen2 968 * that has backlight. 969 */ 970 if (IS_GEN2(dev_priv)) 971 I915_WRITE(BLC_HIST_CTL, BLM_HISTOGRAM_ENABLE); 972 } 973 974 static void i965_enable_backlight(struct intel_connector *connector) 975 { 976 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 977 struct intel_panel *panel = &connector->panel; 978 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 979 u32 ctl, ctl2, freq; 980 981 ctl2 = I915_READ(BLC_PWM_CTL2); 982 if (ctl2 & BLM_PWM_ENABLE) { 983 DRM_DEBUG_KMS("backlight already enabled\n"); 984 ctl2 &= ~BLM_PWM_ENABLE; 985 I915_WRITE(BLC_PWM_CTL2, ctl2); 986 } 987 988 freq = panel->backlight.max; 989 if (panel->backlight.combination_mode) 990 freq /= 0xff; 991 992 ctl = freq << 16; 993 I915_WRITE(BLC_PWM_CTL, ctl); 994 995 ctl2 = BLM_PIPE(pipe); 996 if (panel->backlight.combination_mode) 997 ctl2 |= BLM_COMBINATION_MODE; 998 if (panel->backlight.active_low_pwm) 999 ctl2 |= BLM_POLARITY_I965; 1000 I915_WRITE(BLC_PWM_CTL2, ctl2); 1001 POSTING_READ(BLC_PWM_CTL2); 1002 I915_WRITE(BLC_PWM_CTL2, ctl2 | BLM_PWM_ENABLE); 1003 1004 intel_panel_actually_set_backlight(connector, panel->backlight.level); 1005 } 1006 1007 static void vlv_enable_backlight(struct intel_connector *connector) 1008 { 1009 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1010 struct intel_panel *panel = &connector->panel; 1011 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 1012 u32 ctl, ctl2; 1013 1014 if (WARN_ON(pipe != PIPE_A && pipe != PIPE_B)) 1015 return; 1016 1017 ctl2 = I915_READ(VLV_BLC_PWM_CTL2(pipe)); 1018 if (ctl2 & BLM_PWM_ENABLE) { 1019 DRM_DEBUG_KMS("backlight already enabled\n"); 1020 ctl2 &= ~BLM_PWM_ENABLE; 1021 I915_WRITE(VLV_BLC_PWM_CTL2(pipe), ctl2); 1022 } 1023 1024 ctl = panel->backlight.max << 16; 1025 I915_WRITE(VLV_BLC_PWM_CTL(pipe), ctl); 1026 1027 /* XXX: combine this into above write? */ 1028 intel_panel_actually_set_backlight(connector, panel->backlight.level); 1029 1030 ctl2 = 0; 1031 if (panel->backlight.active_low_pwm) 1032 ctl2 |= BLM_POLARITY_I965; 1033 I915_WRITE(VLV_BLC_PWM_CTL2(pipe), ctl2); 1034 POSTING_READ(VLV_BLC_PWM_CTL2(pipe)); 1035 I915_WRITE(VLV_BLC_PWM_CTL2(pipe), ctl2 | BLM_PWM_ENABLE); 1036 } 1037 1038 static void bxt_enable_backlight(struct intel_connector *connector) 1039 { 1040 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1041 struct intel_panel *panel = &connector->panel; 1042 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 1043 u32 pwm_ctl, val; 1044 1045 /* To use 2nd set of backlight registers, utility pin has to be 1046 * enabled with PWM mode. 1047 * The field should only be changed when the utility pin is disabled 1048 */ 1049 if (panel->backlight.controller == 1) { 1050 val = I915_READ(UTIL_PIN_CTL); 1051 if (val & UTIL_PIN_ENABLE) { 1052 DRM_DEBUG_KMS("util pin already enabled\n"); 1053 val &= ~UTIL_PIN_ENABLE; 1054 I915_WRITE(UTIL_PIN_CTL, val); 1055 } 1056 1057 val = 0; 1058 if (panel->backlight.util_pin_active_low) 1059 val |= UTIL_PIN_POLARITY; 1060 I915_WRITE(UTIL_PIN_CTL, val | UTIL_PIN_PIPE(pipe) | 1061 UTIL_PIN_MODE_PWM | UTIL_PIN_ENABLE); 1062 } 1063 1064 pwm_ctl = I915_READ(BXT_BLC_PWM_CTL(panel->backlight.controller)); 1065 if (pwm_ctl & BXT_BLC_PWM_ENABLE) { 1066 DRM_DEBUG_KMS("backlight already enabled\n"); 1067 pwm_ctl &= ~BXT_BLC_PWM_ENABLE; 1068 I915_WRITE(BXT_BLC_PWM_CTL(panel->backlight.controller), 1069 pwm_ctl); 1070 } 1071 1072 I915_WRITE(BXT_BLC_PWM_FREQ(panel->backlight.controller), 1073 panel->backlight.max); 1074 1075 intel_panel_actually_set_backlight(connector, panel->backlight.level); 1076 1077 pwm_ctl = 0; 1078 if (panel->backlight.active_low_pwm) 1079 pwm_ctl |= BXT_BLC_PWM_POLARITY; 1080 1081 I915_WRITE(BXT_BLC_PWM_CTL(panel->backlight.controller), pwm_ctl); 1082 POSTING_READ(BXT_BLC_PWM_CTL(panel->backlight.controller)); 1083 I915_WRITE(BXT_BLC_PWM_CTL(panel->backlight.controller), 1084 pwm_ctl | BXT_BLC_PWM_ENABLE); 1085 } 1086 1087 static void pwm_enable_backlight(struct intel_connector *connector) 1088 { 1089 struct intel_panel *panel = &connector->panel; 1090 1091 pwm_enable(panel->backlight.pwm); 1092 intel_panel_actually_set_backlight(connector, panel->backlight.level); 1093 } 1094 1095 void intel_panel_enable_backlight(struct intel_connector *connector) 1096 { 1097 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1098 struct intel_panel *panel = &connector->panel; 1099 enum i915_pipe pipe = intel_get_pipe_from_connector(connector); 1100 1101 if (!panel->backlight.present) 1102 return; 1103 1104 DRM_DEBUG_KMS("pipe %c\n", pipe_name(pipe)); 1105 1106 mutex_lock(&dev_priv->backlight_lock); 1107 1108 WARN_ON(panel->backlight.max == 0); 1109 1110 if (panel->backlight.level <= panel->backlight.min) { 1111 panel->backlight.level = panel->backlight.max; 1112 if (panel->backlight.device) 1113 panel->backlight.device->props.brightness = 1114 scale_hw_to_user(connector, 1115 panel->backlight.level, 1116 panel->backlight.device->props.max_brightness); 1117 } 1118 1119 panel->backlight.enable(connector); 1120 panel->backlight.enabled = true; 1121 if (panel->backlight.device) 1122 panel->backlight.device->props.power = FB_BLANK_UNBLANK; 1123 1124 mutex_unlock(&dev_priv->backlight_lock); 1125 } 1126 1127 #if IS_ENABLED(CONFIG_BACKLIGHT_CLASS_DEVICE) 1128 #if 0 /* unused */ 1129 static int intel_backlight_device_update_status(struct backlight_device *bd) 1130 { 1131 struct intel_connector *connector = bl_get_data(bd); 1132 struct intel_panel *panel = &connector->panel; 1133 struct drm_device *dev = connector->base.dev; 1134 1135 drm_modeset_lock(&dev->mode_config.connection_mutex, NULL); 1136 DRM_DEBUG_KMS("updating intel_backlight, brightness=%d/%d\n", 1137 bd->props.brightness, bd->props.max_brightness); 1138 intel_panel_set_backlight(connector, bd->props.brightness, 1139 bd->props.max_brightness); 1140 1141 /* 1142 * Allow flipping bl_power as a sub-state of enabled. Sadly the 1143 * backlight class device does not make it easy to to differentiate 1144 * between callbacks for brightness and bl_power, so our backlight_power 1145 * callback needs to take this into account. 1146 */ 1147 if (panel->backlight.enabled) { 1148 if (panel->backlight.power) { 1149 bool enable = bd->props.power == FB_BLANK_UNBLANK && 1150 bd->props.brightness != 0; 1151 panel->backlight.power(connector, enable); 1152 } 1153 } else { 1154 bd->props.power = FB_BLANK_POWERDOWN; 1155 } 1156 1157 drm_modeset_unlock(&dev->mode_config.connection_mutex); 1158 return 0; 1159 } 1160 1161 static int intel_backlight_device_get_brightness(struct backlight_device *bd) 1162 { 1163 struct intel_connector *connector = bl_get_data(bd); 1164 struct drm_device *dev = connector->base.dev; 1165 struct drm_i915_private *dev_priv = to_i915(dev); 1166 u32 hw_level; 1167 int ret; 1168 1169 intel_runtime_pm_get(dev_priv); 1170 drm_modeset_lock(&dev->mode_config.connection_mutex, NULL); 1171 1172 hw_level = intel_panel_get_backlight(connector); 1173 ret = scale_hw_to_user(connector, hw_level, bd->props.max_brightness); 1174 1175 drm_modeset_unlock(&dev->mode_config.connection_mutex); 1176 intel_runtime_pm_put(dev_priv); 1177 1178 return ret; 1179 } 1180 1181 static const struct backlight_ops intel_backlight_device_ops = { 1182 .update_status = intel_backlight_device_update_status, 1183 .get_brightness = intel_backlight_device_get_brightness, 1184 }; 1185 #endif 1186 1187 int intel_backlight_device_register(struct intel_connector *connector) 1188 { 1189 struct intel_panel *panel = &connector->panel; 1190 struct backlight_properties props; 1191 1192 if (WARN_ON(panel->backlight.device)) 1193 return -ENODEV; 1194 1195 if (!panel->backlight.present) 1196 return 0; 1197 1198 WARN_ON(panel->backlight.max == 0); 1199 1200 memset(&props, 0, sizeof(props)); 1201 props.type = BACKLIGHT_RAW; 1202 1203 /* 1204 * Note: Everything should work even if the backlight device max 1205 * presented to the userspace is arbitrarily chosen. 1206 */ 1207 props.max_brightness = panel->backlight.max; 1208 props.brightness = scale_hw_to_user(connector, 1209 panel->backlight.level, 1210 props.max_brightness); 1211 1212 if (panel->backlight.enabled) 1213 props.power = FB_BLANK_UNBLANK; 1214 else 1215 props.power = FB_BLANK_POWERDOWN; 1216 1217 /* 1218 * Note: using the same name independent of the connector prevents 1219 * registration of multiple backlight devices in the driver. 1220 */ 1221 #if 0 1222 panel->backlight.device = 1223 backlight_device_register("intel_backlight", 1224 connector->base.kdev, 1225 connector, 1226 &intel_backlight_device_ops, &props); 1227 1228 if (IS_ERR(panel->backlight.device)) { 1229 DRM_ERROR("Failed to register backlight: %ld\n", 1230 PTR_ERR(panel->backlight.device)); 1231 panel->backlight.device = NULL; 1232 return -ENODEV; 1233 } 1234 1235 DRM_DEBUG_KMS("Connector %s backlight sysfs interface registered\n", 1236 connector->base.name); 1237 #endif 1238 1239 return 0; 1240 } 1241 1242 void intel_backlight_device_unregister(struct intel_connector *connector) 1243 { 1244 #if 0 1245 struct intel_panel *panel = &connector->panel; 1246 1247 if (panel->backlight.device) { 1248 backlight_device_unregister(panel->backlight.device); 1249 panel->backlight.device = NULL; 1250 } 1251 #endif 1252 } 1253 #endif /* CONFIG_BACKLIGHT_CLASS_DEVICE */ 1254 1255 /* 1256 * BXT: PWM clock frequency = 19.2 MHz. 1257 */ 1258 static u32 bxt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1259 { 1260 return DIV_ROUND_CLOSEST(KHz(19200), pwm_freq_hz); 1261 } 1262 1263 /* 1264 * SPT: This value represents the period of the PWM stream in clock periods 1265 * multiplied by 16 (default increment) or 128 (alternate increment selected in 1266 * SCHICKEN_1 bit 0). PWM clock is 24 MHz. 1267 */ 1268 static u32 spt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1269 { 1270 struct intel_panel *panel = &connector->panel; 1271 u32 mul; 1272 1273 if (panel->backlight.alternate_pwm_increment) 1274 mul = 128; 1275 else 1276 mul = 16; 1277 1278 return DIV_ROUND_CLOSEST(MHz(24), pwm_freq_hz * mul); 1279 } 1280 1281 /* 1282 * LPT: This value represents the period of the PWM stream in clock periods 1283 * multiplied by 128 (default increment) or 16 (alternate increment, selected in 1284 * LPT SOUTH_CHICKEN2 register bit 5). 1285 */ 1286 static u32 lpt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1287 { 1288 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1289 struct intel_panel *panel = &connector->panel; 1290 u32 mul, clock; 1291 1292 if (panel->backlight.alternate_pwm_increment) 1293 mul = 16; 1294 else 1295 mul = 128; 1296 1297 if (HAS_PCH_LPT_H(dev_priv)) 1298 clock = MHz(135); /* LPT:H */ 1299 else 1300 clock = MHz(24); /* LPT:LP */ 1301 1302 return DIV_ROUND_CLOSEST(clock, pwm_freq_hz * mul); 1303 } 1304 1305 /* 1306 * ILK/SNB/IVB: This value represents the period of the PWM stream in PCH 1307 * display raw clocks multiplied by 128. 1308 */ 1309 static u32 pch_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1310 { 1311 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1312 1313 return DIV_ROUND_CLOSEST(KHz(dev_priv->rawclk_freq), pwm_freq_hz * 128); 1314 } 1315 1316 /* 1317 * Gen2: This field determines the number of time base events (display core 1318 * clock frequency/32) in total for a complete cycle of modulated backlight 1319 * control. 1320 * 1321 * Gen3: A time base event equals the display core clock ([DevPNV] HRAW clock) 1322 * divided by 32. 1323 */ 1324 static u32 i9xx_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1325 { 1326 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1327 int clock; 1328 1329 if (IS_PINEVIEW(dev_priv)) 1330 clock = KHz(dev_priv->rawclk_freq); 1331 else 1332 clock = KHz(dev_priv->cdclk_freq); 1333 1334 return DIV_ROUND_CLOSEST(clock, pwm_freq_hz * 32); 1335 } 1336 1337 /* 1338 * Gen4: This value represents the period of the PWM stream in display core 1339 * clocks ([DevCTG] HRAW clocks) multiplied by 128. 1340 * 1341 */ 1342 static u32 i965_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1343 { 1344 struct drm_device *dev = connector->base.dev; 1345 struct drm_i915_private *dev_priv = to_i915(dev); 1346 int clock; 1347 1348 if (IS_G4X(dev_priv)) 1349 clock = KHz(dev_priv->rawclk_freq); 1350 else 1351 clock = KHz(dev_priv->cdclk_freq); 1352 1353 return DIV_ROUND_CLOSEST(clock, pwm_freq_hz * 128); 1354 } 1355 1356 /* 1357 * VLV: This value represents the period of the PWM stream in display core 1358 * clocks ([DevCTG] 200MHz HRAW clocks) multiplied by 128 or 25MHz S0IX clocks 1359 * multiplied by 16. CHV uses a 19.2MHz S0IX clock. 1360 */ 1361 static u32 vlv_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz) 1362 { 1363 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1364 int mul, clock; 1365 1366 if ((I915_READ(CBR1_VLV) & CBR_PWM_CLOCK_MUX_SELECT) == 0) { 1367 if (IS_CHERRYVIEW(dev_priv)) 1368 clock = KHz(19200); 1369 else 1370 clock = MHz(25); 1371 mul = 16; 1372 } else { 1373 clock = KHz(dev_priv->rawclk_freq); 1374 mul = 128; 1375 } 1376 1377 return DIV_ROUND_CLOSEST(clock, pwm_freq_hz * mul); 1378 } 1379 1380 static u32 get_backlight_max_vbt(struct intel_connector *connector) 1381 { 1382 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1383 struct intel_panel *panel = &connector->panel; 1384 u16 pwm_freq_hz = dev_priv->vbt.backlight.pwm_freq_hz; 1385 u32 pwm; 1386 1387 if (!panel->backlight.hz_to_pwm) { 1388 DRM_DEBUG_KMS("backlight frequency conversion not supported\n"); 1389 return 0; 1390 } 1391 1392 if (pwm_freq_hz) { 1393 DRM_DEBUG_KMS("VBT defined backlight frequency %u Hz\n", 1394 pwm_freq_hz); 1395 } else { 1396 pwm_freq_hz = 200; 1397 DRM_DEBUG_KMS("default backlight frequency %u Hz\n", 1398 pwm_freq_hz); 1399 } 1400 1401 pwm = panel->backlight.hz_to_pwm(connector, pwm_freq_hz); 1402 if (!pwm) { 1403 DRM_DEBUG_KMS("backlight frequency conversion failed\n"); 1404 return 0; 1405 } 1406 1407 return pwm; 1408 } 1409 1410 /* 1411 * Note: The setup hooks can't assume pipe is set! 1412 */ 1413 static u32 get_backlight_min_vbt(struct intel_connector *connector) 1414 { 1415 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1416 struct intel_panel *panel = &connector->panel; 1417 int min; 1418 1419 WARN_ON(panel->backlight.max == 0); 1420 1421 /* 1422 * XXX: If the vbt value is 255, it makes min equal to max, which leads 1423 * to problems. There are such machines out there. Either our 1424 * interpretation is wrong or the vbt has bogus data. Or both. Safeguard 1425 * against this by letting the minimum be at most (arbitrarily chosen) 1426 * 25% of the max. 1427 */ 1428 min = clamp_t(int, dev_priv->vbt.backlight.min_brightness, 0, 64); 1429 if (min != dev_priv->vbt.backlight.min_brightness) { 1430 DRM_DEBUG_KMS("clamping VBT min backlight %d/255 to %d/255\n", 1431 dev_priv->vbt.backlight.min_brightness, min); 1432 } 1433 1434 /* vbt value is a coefficient in range [0..255] */ 1435 return scale(min, 0, 255, 0, panel->backlight.max); 1436 } 1437 1438 static int lpt_setup_backlight(struct intel_connector *connector, enum i915_pipe unused) 1439 { 1440 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1441 struct intel_panel *panel = &connector->panel; 1442 u32 pch_ctl1, pch_ctl2, val; 1443 bool alt; 1444 1445 if (HAS_PCH_LPT(dev_priv)) 1446 alt = I915_READ(SOUTH_CHICKEN2) & LPT_PWM_GRANULARITY; 1447 else 1448 alt = I915_READ(SOUTH_CHICKEN1) & SPT_PWM_GRANULARITY; 1449 panel->backlight.alternate_pwm_increment = alt; 1450 1451 pch_ctl1 = I915_READ(BLC_PWM_PCH_CTL1); 1452 panel->backlight.active_low_pwm = pch_ctl1 & BLM_PCH_POLARITY; 1453 1454 pch_ctl2 = I915_READ(BLC_PWM_PCH_CTL2); 1455 panel->backlight.max = pch_ctl2 >> 16; 1456 1457 if (!panel->backlight.max) 1458 panel->backlight.max = get_backlight_max_vbt(connector); 1459 1460 if (!panel->backlight.max) 1461 return -ENODEV; 1462 1463 panel->backlight.min = get_backlight_min_vbt(connector); 1464 1465 val = lpt_get_backlight(connector); 1466 val = intel_panel_compute_brightness(connector, val); 1467 panel->backlight.level = clamp(val, panel->backlight.min, 1468 panel->backlight.max); 1469 1470 panel->backlight.enabled = pch_ctl1 & BLM_PCH_PWM_ENABLE; 1471 1472 return 0; 1473 } 1474 1475 static int pch_setup_backlight(struct intel_connector *connector, enum i915_pipe unused) 1476 { 1477 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1478 struct intel_panel *panel = &connector->panel; 1479 u32 cpu_ctl2, pch_ctl1, pch_ctl2, val; 1480 1481 pch_ctl1 = I915_READ(BLC_PWM_PCH_CTL1); 1482 panel->backlight.active_low_pwm = pch_ctl1 & BLM_PCH_POLARITY; 1483 1484 pch_ctl2 = I915_READ(BLC_PWM_PCH_CTL2); 1485 panel->backlight.max = pch_ctl2 >> 16; 1486 1487 if (!panel->backlight.max) 1488 panel->backlight.max = get_backlight_max_vbt(connector); 1489 1490 if (!panel->backlight.max) 1491 return -ENODEV; 1492 1493 panel->backlight.min = get_backlight_min_vbt(connector); 1494 1495 val = pch_get_backlight(connector); 1496 val = intel_panel_compute_brightness(connector, val); 1497 panel->backlight.level = clamp(val, panel->backlight.min, 1498 panel->backlight.max); 1499 1500 cpu_ctl2 = I915_READ(BLC_PWM_CPU_CTL2); 1501 panel->backlight.enabled = (cpu_ctl2 & BLM_PWM_ENABLE) && 1502 (pch_ctl1 & BLM_PCH_PWM_ENABLE); 1503 1504 return 0; 1505 } 1506 1507 static int i9xx_setup_backlight(struct intel_connector *connector, enum i915_pipe unused) 1508 { 1509 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1510 struct intel_panel *panel = &connector->panel; 1511 u32 ctl, val; 1512 1513 ctl = I915_READ(BLC_PWM_CTL); 1514 1515 if (IS_GEN2(dev_priv) || IS_I915GM(dev_priv) || IS_I945GM(dev_priv)) 1516 panel->backlight.combination_mode = ctl & BLM_LEGACY_MODE; 1517 1518 if (IS_PINEVIEW(dev_priv)) 1519 panel->backlight.active_low_pwm = ctl & BLM_POLARITY_PNV; 1520 1521 panel->backlight.max = ctl >> 17; 1522 1523 if (!panel->backlight.max) { 1524 panel->backlight.max = get_backlight_max_vbt(connector); 1525 panel->backlight.max >>= 1; 1526 } 1527 1528 if (!panel->backlight.max) 1529 return -ENODEV; 1530 1531 if (panel->backlight.combination_mode) 1532 panel->backlight.max *= 0xff; 1533 1534 panel->backlight.min = get_backlight_min_vbt(connector); 1535 1536 val = i9xx_get_backlight(connector); 1537 val = intel_panel_compute_brightness(connector, val); 1538 panel->backlight.level = clamp(val, panel->backlight.min, 1539 panel->backlight.max); 1540 1541 panel->backlight.enabled = val != 0; 1542 1543 return 0; 1544 } 1545 1546 static int i965_setup_backlight(struct intel_connector *connector, enum i915_pipe unused) 1547 { 1548 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1549 struct intel_panel *panel = &connector->panel; 1550 u32 ctl, ctl2, val; 1551 1552 ctl2 = I915_READ(BLC_PWM_CTL2); 1553 panel->backlight.combination_mode = ctl2 & BLM_COMBINATION_MODE; 1554 panel->backlight.active_low_pwm = ctl2 & BLM_POLARITY_I965; 1555 1556 ctl = I915_READ(BLC_PWM_CTL); 1557 panel->backlight.max = ctl >> 16; 1558 1559 if (!panel->backlight.max) 1560 panel->backlight.max = get_backlight_max_vbt(connector); 1561 1562 if (!panel->backlight.max) 1563 return -ENODEV; 1564 1565 if (panel->backlight.combination_mode) 1566 panel->backlight.max *= 0xff; 1567 1568 panel->backlight.min = get_backlight_min_vbt(connector); 1569 1570 val = i9xx_get_backlight(connector); 1571 val = intel_panel_compute_brightness(connector, val); 1572 panel->backlight.level = clamp(val, panel->backlight.min, 1573 panel->backlight.max); 1574 1575 panel->backlight.enabled = ctl2 & BLM_PWM_ENABLE; 1576 1577 return 0; 1578 } 1579 1580 static int vlv_setup_backlight(struct intel_connector *connector, enum i915_pipe pipe) 1581 { 1582 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1583 struct intel_panel *panel = &connector->panel; 1584 u32 ctl, ctl2, val; 1585 1586 if (WARN_ON(pipe != PIPE_A && pipe != PIPE_B)) 1587 return -ENODEV; 1588 1589 ctl2 = I915_READ(VLV_BLC_PWM_CTL2(pipe)); 1590 panel->backlight.active_low_pwm = ctl2 & BLM_POLARITY_I965; 1591 1592 ctl = I915_READ(VLV_BLC_PWM_CTL(pipe)); 1593 panel->backlight.max = ctl >> 16; 1594 1595 if (!panel->backlight.max) 1596 panel->backlight.max = get_backlight_max_vbt(connector); 1597 1598 if (!panel->backlight.max) 1599 return -ENODEV; 1600 1601 panel->backlight.min = get_backlight_min_vbt(connector); 1602 1603 val = _vlv_get_backlight(dev_priv, pipe); 1604 val = intel_panel_compute_brightness(connector, val); 1605 panel->backlight.level = clamp(val, panel->backlight.min, 1606 panel->backlight.max); 1607 1608 panel->backlight.enabled = ctl2 & BLM_PWM_ENABLE; 1609 1610 return 0; 1611 } 1612 1613 static int 1614 bxt_setup_backlight(struct intel_connector *connector, enum i915_pipe unused) 1615 { 1616 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1617 struct intel_panel *panel = &connector->panel; 1618 u32 pwm_ctl, val; 1619 1620 /* 1621 * For BXT hard coding the Backlight controller to 0. 1622 * TODO : Read the controller value from VBT and generalize 1623 */ 1624 panel->backlight.controller = 0; 1625 1626 pwm_ctl = I915_READ(BXT_BLC_PWM_CTL(panel->backlight.controller)); 1627 1628 /* Keeping the check if controller 1 is to be programmed. 1629 * This will come into affect once the VBT parsing 1630 * is fixed for controller selection, and controller 1 is used 1631 * for a prticular display configuration. 1632 */ 1633 if (panel->backlight.controller == 1) { 1634 val = I915_READ(UTIL_PIN_CTL); 1635 panel->backlight.util_pin_active_low = 1636 val & UTIL_PIN_POLARITY; 1637 } 1638 1639 panel->backlight.active_low_pwm = pwm_ctl & BXT_BLC_PWM_POLARITY; 1640 panel->backlight.max = 1641 I915_READ(BXT_BLC_PWM_FREQ(panel->backlight.controller)); 1642 1643 if (!panel->backlight.max) 1644 panel->backlight.max = get_backlight_max_vbt(connector); 1645 1646 if (!panel->backlight.max) 1647 return -ENODEV; 1648 1649 val = bxt_get_backlight(connector); 1650 val = intel_panel_compute_brightness(connector, val); 1651 panel->backlight.level = clamp(val, panel->backlight.min, 1652 panel->backlight.max); 1653 1654 panel->backlight.enabled = pwm_ctl & BXT_BLC_PWM_ENABLE; 1655 1656 return 0; 1657 } 1658 1659 static int pwm_setup_backlight(struct intel_connector *connector, 1660 enum i915_pipe pipe) 1661 { 1662 struct drm_device *dev = connector->base.dev; 1663 struct intel_panel *panel = &connector->panel; 1664 int retval; 1665 1666 /* Get the PWM chip for backlight control */ 1667 panel->backlight.pwm = pwm_get(dev->dev, "pwm_backlight"); 1668 if (IS_ERR(panel->backlight.pwm)) { 1669 DRM_ERROR("Failed to own the pwm chip\n"); 1670 panel->backlight.pwm = NULL; 1671 return -ENODEV; 1672 } 1673 1674 /* 1675 * FIXME: pwm_apply_args() should be removed when switching to 1676 * the atomic PWM API. 1677 */ 1678 #if 0 1679 pwm_apply_args(panel->backlight.pwm); 1680 #endif 1681 1682 retval = pwm_config(panel->backlight.pwm, CRC_PMIC_PWM_PERIOD_NS, 1683 CRC_PMIC_PWM_PERIOD_NS); 1684 if (retval < 0) { 1685 DRM_ERROR("Failed to configure the pwm chip\n"); 1686 pwm_put(panel->backlight.pwm); 1687 panel->backlight.pwm = NULL; 1688 return retval; 1689 } 1690 1691 panel->backlight.min = 0; /* 0% */ 1692 panel->backlight.max = 100; /* 100% */ 1693 panel->backlight.level = DIV_ROUND_UP( 1694 pwm_get_duty_cycle(panel->backlight.pwm) * 100, 1695 CRC_PMIC_PWM_PERIOD_NS); 1696 panel->backlight.enabled = panel->backlight.level != 0; 1697 1698 return 0; 1699 } 1700 1701 #ifdef __DragonFly__ 1702 /* 1703 * Read max backlight level 1704 */ 1705 static int 1706 sysctl_backlight_max(SYSCTL_HANDLER_ARGS) 1707 { 1708 int err, val; 1709 struct intel_connector *connector = arg1; 1710 struct drm_device *dev = connector->base.dev; 1711 struct drm_i915_private *dev_priv = dev->dev_private; 1712 struct intel_panel *panel = &connector->panel; 1713 1714 mutex_lock(&dev_priv->backlight_lock); 1715 val = panel->backlight.max; 1716 mutex_unlock(&dev_priv->backlight_lock); 1717 1718 err = sysctl_handle_int(oidp, &val, 0, req); 1719 return(err); 1720 } 1721 1722 /* 1723 * Read/write backlight level 1724 */ 1725 static int 1726 sysctl_backlight_handler(SYSCTL_HANDLER_ARGS) 1727 { 1728 struct intel_connector *connector = arg1; 1729 struct drm_device *dev = connector->base.dev; 1730 struct drm_i915_private *dev_priv = dev->dev_private; 1731 struct intel_panel *panel = &connector->panel; 1732 int err, val; 1733 u32 user_level, max_brightness; 1734 1735 mutex_lock(&dev_priv->backlight_lock); 1736 max_brightness = panel->backlight.max; 1737 user_level = scale_hw_to_user(connector, panel->backlight.level, 1738 max_brightness); 1739 mutex_unlock(&dev_priv->backlight_lock); 1740 1741 val = user_level; 1742 err = sysctl_handle_int(oidp, &val, 0, req); 1743 if (err != 0 || req->newptr == NULL) { 1744 return(err); 1745 } 1746 1747 if (val != user_level && val >= 0 && val <= max_brightness) { 1748 drm_modeset_lock(&dev->mode_config.connection_mutex, NULL); 1749 intel_panel_set_backlight(arg1, val, max_brightness); 1750 drm_modeset_unlock(&dev->mode_config.connection_mutex); 1751 } 1752 1753 return(err); 1754 } 1755 #endif /* __DragonFly__ */ 1756 1757 int intel_panel_setup_backlight(struct drm_connector *connector, enum i915_pipe pipe) 1758 { 1759 struct drm_i915_private *dev_priv = to_i915(connector->dev); 1760 struct intel_connector *intel_connector = to_intel_connector(connector); 1761 struct intel_panel *panel = &intel_connector->panel; 1762 int ret; 1763 1764 if (!dev_priv->vbt.backlight.present) { 1765 if (dev_priv->quirks & QUIRK_BACKLIGHT_PRESENT) { 1766 DRM_DEBUG_KMS("no backlight present per VBT, but present per quirk\n"); 1767 } else { 1768 DRM_DEBUG_KMS("no backlight present per VBT\n"); 1769 return 0; 1770 } 1771 } 1772 1773 /* ensure intel_panel has been initialized first */ 1774 if (WARN_ON(!panel->backlight.setup)) 1775 return -ENODEV; 1776 1777 /* set level and max in panel struct */ 1778 mutex_lock(&dev_priv->backlight_lock); 1779 ret = panel->backlight.setup(intel_connector, pipe); 1780 mutex_unlock(&dev_priv->backlight_lock); 1781 1782 if (ret) { 1783 DRM_DEBUG_KMS("failed to setup backlight for connector %s\n", 1784 connector->name); 1785 return ret; 1786 } 1787 1788 panel->backlight.present = true; 1789 1790 #ifdef __DragonFly__ 1791 SYSCTL_ADD_PROC(&connector->dev->sysctl->ctx, &sysctl__hw_children, 1792 OID_AUTO, "backlight_max", 1793 CTLTYPE_INT | CTLFLAG_RD | CTLFLAG_ANYBODY, 1794 connector, sizeof(int), 1795 sysctl_backlight_max, 1796 "I", "Max backlight level"); 1797 SYSCTL_ADD_PROC(&connector->dev->sysctl->ctx, &sysctl__hw_children, 1798 OID_AUTO, "backlight_level", 1799 CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_ANYBODY, 1800 connector, sizeof(int), 1801 sysctl_backlight_handler, 1802 "I", "Backlight level"); 1803 #endif 1804 1805 DRM_DEBUG_KMS("Connector %s backlight initialized, %s, brightness %u/%u\n", 1806 connector->name, 1807 panel->backlight.enabled ? "enabled" : "disabled", 1808 panel->backlight.level, panel->backlight.max); 1809 1810 return 0; 1811 } 1812 1813 void intel_panel_destroy_backlight(struct drm_connector *connector) 1814 { 1815 struct intel_connector *intel_connector = to_intel_connector(connector); 1816 struct intel_panel *panel = &intel_connector->panel; 1817 1818 /* dispose of the pwm */ 1819 if (panel->backlight.pwm) 1820 pwm_put(panel->backlight.pwm); 1821 1822 panel->backlight.present = false; 1823 } 1824 1825 /* Set up chip specific backlight functions */ 1826 static void 1827 intel_panel_init_backlight_funcs(struct intel_panel *panel) 1828 { 1829 struct intel_connector *connector = 1830 container_of(panel, struct intel_connector, panel); 1831 struct drm_i915_private *dev_priv = to_i915(connector->base.dev); 1832 1833 if (connector->base.connector_type == DRM_MODE_CONNECTOR_eDP && 1834 intel_dp_aux_init_backlight_funcs(connector) == 0) 1835 return; 1836 1837 if (connector->base.connector_type == DRM_MODE_CONNECTOR_DSI && 1838 intel_dsi_dcs_init_backlight_funcs(connector) == 0) 1839 return; 1840 1841 if (IS_BROXTON(dev_priv)) { 1842 panel->backlight.setup = bxt_setup_backlight; 1843 panel->backlight.enable = bxt_enable_backlight; 1844 panel->backlight.disable = bxt_disable_backlight; 1845 panel->backlight.set = bxt_set_backlight; 1846 panel->backlight.get = bxt_get_backlight; 1847 panel->backlight.hz_to_pwm = bxt_hz_to_pwm; 1848 } else if (HAS_PCH_LPT(dev_priv) || HAS_PCH_SPT(dev_priv) || 1849 HAS_PCH_KBP(dev_priv)) { 1850 panel->backlight.setup = lpt_setup_backlight; 1851 panel->backlight.enable = lpt_enable_backlight; 1852 panel->backlight.disable = lpt_disable_backlight; 1853 panel->backlight.set = lpt_set_backlight; 1854 panel->backlight.get = lpt_get_backlight; 1855 if (HAS_PCH_LPT(dev_priv)) 1856 panel->backlight.hz_to_pwm = lpt_hz_to_pwm; 1857 else 1858 panel->backlight.hz_to_pwm = spt_hz_to_pwm; 1859 } else if (HAS_PCH_SPLIT(dev_priv)) { 1860 panel->backlight.setup = pch_setup_backlight; 1861 panel->backlight.enable = pch_enable_backlight; 1862 panel->backlight.disable = pch_disable_backlight; 1863 panel->backlight.set = pch_set_backlight; 1864 panel->backlight.get = pch_get_backlight; 1865 panel->backlight.hz_to_pwm = pch_hz_to_pwm; 1866 } else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) { 1867 if (connector->base.connector_type == DRM_MODE_CONNECTOR_DSI) { 1868 panel->backlight.setup = pwm_setup_backlight; 1869 panel->backlight.enable = pwm_enable_backlight; 1870 panel->backlight.disable = pwm_disable_backlight; 1871 panel->backlight.set = pwm_set_backlight; 1872 panel->backlight.get = pwm_get_backlight; 1873 } else { 1874 panel->backlight.setup = vlv_setup_backlight; 1875 panel->backlight.enable = vlv_enable_backlight; 1876 panel->backlight.disable = vlv_disable_backlight; 1877 panel->backlight.set = vlv_set_backlight; 1878 panel->backlight.get = vlv_get_backlight; 1879 panel->backlight.hz_to_pwm = vlv_hz_to_pwm; 1880 } 1881 } else if (IS_GEN4(dev_priv)) { 1882 panel->backlight.setup = i965_setup_backlight; 1883 panel->backlight.enable = i965_enable_backlight; 1884 panel->backlight.disable = i965_disable_backlight; 1885 panel->backlight.set = i9xx_set_backlight; 1886 panel->backlight.get = i9xx_get_backlight; 1887 panel->backlight.hz_to_pwm = i965_hz_to_pwm; 1888 } else { 1889 panel->backlight.setup = i9xx_setup_backlight; 1890 panel->backlight.enable = i9xx_enable_backlight; 1891 panel->backlight.disable = i9xx_disable_backlight; 1892 panel->backlight.set = i9xx_set_backlight; 1893 panel->backlight.get = i9xx_get_backlight; 1894 panel->backlight.hz_to_pwm = i9xx_hz_to_pwm; 1895 } 1896 } 1897 1898 int intel_panel_init(struct intel_panel *panel, 1899 struct drm_display_mode *fixed_mode, 1900 struct drm_display_mode *downclock_mode) 1901 { 1902 intel_panel_init_backlight_funcs(panel); 1903 1904 panel->fixed_mode = fixed_mode; 1905 panel->downclock_mode = downclock_mode; 1906 1907 return 0; 1908 } 1909 1910 void intel_panel_fini(struct intel_panel *panel) 1911 { 1912 struct intel_connector *intel_connector = 1913 container_of(panel, struct intel_connector, panel); 1914 1915 if (panel->fixed_mode) 1916 drm_mode_destroy(intel_connector->base.dev, panel->fixed_mode); 1917 1918 if (panel->downclock_mode) 1919 drm_mode_destroy(intel_connector->base.dev, 1920 panel->downclock_mode); 1921 } 1922