disp: msm: sde: add new support for digital dimming
Add new properties to support dynamically turning on and off digital dimming and setting new minimum backlight. Change-Id: I3b94190877d556768ba2c92ec59432dec44de0de Signed-off-by: Ping Li <pingli@codeaurora.org>
This commit is contained in:
@@ -719,6 +719,8 @@ struct drm_msm_fp16_csc {
|
||||
__u32 cfg_param_1[FP16_CSC_CFG1_PARAM_LEN];
|
||||
};
|
||||
|
||||
#define DIMMING_ENABLE (1 << 0)
|
||||
#define DIMMING_MIN_BL_VALID (1 << 1)
|
||||
struct drm_msm_backlight_info {
|
||||
__u32 brightness_max;
|
||||
__u32 brightness;
|
||||
@@ -726,6 +728,8 @@ struct drm_msm_backlight_info {
|
||||
__u32 bl_level;
|
||||
__u32 bl_scale;
|
||||
__u32 bl_scale_sv;
|
||||
__u32 status;
|
||||
__u32 min_bl;
|
||||
};
|
||||
|
||||
#define DIMMING_BL_LUT_LEN 8192
|
||||
|
@@ -249,7 +249,7 @@ int dsi_display_set_backlight(struct drm_connector *connector,
|
||||
/* use bl_temp as index of dimming bl lut to find the dimming panel backlight */
|
||||
if (bl_temp != 0 && panel->bl_config.dimming_bl_lut &&
|
||||
bl_temp < panel->bl_config.dimming_bl_lut->length) {
|
||||
pr_debug("before dimming bl_temp = %u, after dimming bl_temp = %lu\n",
|
||||
DSI_DEBUG("before dimming bl_temp = %u, after dimming bl_temp = %lu\n",
|
||||
bl_temp, panel->bl_config.dimming_bl_lut->mapped_bl[bl_temp]);
|
||||
bl_temp = panel->bl_config.dimming_bl_lut->mapped_bl[bl_temp];
|
||||
}
|
||||
@@ -257,10 +257,10 @@ int dsi_display_set_backlight(struct drm_connector *connector,
|
||||
if (bl_temp > panel->bl_config.bl_max_level)
|
||||
bl_temp = panel->bl_config.bl_max_level;
|
||||
|
||||
if (bl_temp && (bl_temp < panel->bl_config.bl_min_level))
|
||||
bl_temp = panel->bl_config.bl_min_level;
|
||||
if (bl_temp && (bl_temp < panel->bl_config.bl_min_level))
|
||||
bl_temp = panel->bl_config.bl_min_level;
|
||||
|
||||
pr_debug("bl_scale = %u, bl_scale_sv = %u, bl_lvl = %u\n",
|
||||
DSI_DEBUG("bl_scale = %u, bl_scale_sv = %u, bl_lvl = %u\n",
|
||||
bl_scale, bl_scale_sv, (u32)bl_temp);
|
||||
|
||||
rc = dsi_panel_set_backlight(panel, (u32)bl_temp);
|
||||
|
@@ -2445,6 +2445,9 @@ static int dsi_panel_parse_bl_config(struct dsi_panel *panel)
|
||||
|
||||
panel->bl_config.bl_scale = MAX_BL_SCALE_LEVEL;
|
||||
panel->bl_config.bl_scale_sv = MAX_SV_BL_SCALE_LEVEL;
|
||||
panel->bl_config.dimming_min_bl = 0;
|
||||
panel->bl_config.dimming_status = DIMMING_ENABLE;
|
||||
panel->bl_config.user_disable_notification = false;
|
||||
|
||||
rc = utils->read_u32(utils->data, "qcom,mdss-dsi-bl-min-level", &val);
|
||||
if (rc) {
|
||||
|
@@ -13,6 +13,7 @@
|
||||
#include <linux/backlight.h>
|
||||
#include <drm/drm_panel.h>
|
||||
#include <drm/msm_drm.h>
|
||||
#include <drm/msm_drm_pp.h>
|
||||
|
||||
#include "dsi_defs.h"
|
||||
#include "dsi_ctrl_hw.h"
|
||||
@@ -134,6 +135,9 @@ struct dsi_backlight_config {
|
||||
bool bl_inverted_dbv;
|
||||
/* digital dimming backlight LUT */
|
||||
struct drm_msm_dimming_bl_lut *dimming_bl_lut;
|
||||
u32 dimming_min_bl;
|
||||
u32 dimming_status;
|
||||
bool user_disable_notification;
|
||||
|
||||
int en_gpio;
|
||||
/* PWM params */
|
||||
|
@@ -216,6 +216,8 @@ enum msm_mdp_conn_property {
|
||||
CONNECTOR_PROP_SV_BL_SCALE,
|
||||
CONNECTOR_PROP_SUPPORTED_COLORSPACES,
|
||||
CONNECTOR_PROP_DYN_BIT_CLK,
|
||||
CONNECTOR_PROP_DIMMING_CTRL,
|
||||
CONNECTOR_PROP_DIMMING_MIN_BL,
|
||||
|
||||
/* enum/bitmask properties */
|
||||
CONNECTOR_PROP_TOPOLOGY_NAME,
|
||||
|
@@ -106,7 +106,10 @@ static void sde_dimming_bl_notify(struct sde_connector *conn, struct dsi_backlig
|
||||
|
||||
if (!conn || !config)
|
||||
return;
|
||||
if (!conn->dimming_bl_notify_enabled)
|
||||
|
||||
SDE_DEBUG("bl_config.dimming_status 0x%x user_disable_notify %d\n",
|
||||
config->dimming_status, config->user_disable_notification);
|
||||
if (!conn->dimming_bl_notify_enabled || config->user_disable_notification)
|
||||
return;
|
||||
|
||||
bl_info.brightness_max = config->brightness_max_level;
|
||||
@@ -115,10 +118,13 @@ static void sde_dimming_bl_notify(struct sde_connector *conn, struct dsi_backlig
|
||||
bl_info.bl_level = config->bl_level;
|
||||
bl_info.bl_scale = config->bl_scale;
|
||||
bl_info.bl_scale_sv = config->bl_scale_sv;
|
||||
bl_info.status = config->dimming_status;
|
||||
bl_info.min_bl = config->dimming_min_bl;
|
||||
event.type = DRM_EVENT_DIMMING_BL;
|
||||
event.length = sizeof(bl_info);
|
||||
SDE_DEBUG("dimming BL event bl_level %d bl_scale %d, bl_scale_sv = %d\n",
|
||||
bl_info.bl_level, bl_info.bl_scale, bl_info.bl_scale_sv);
|
||||
SDE_DEBUG("dimming BL event bl_level %d bl_scale %d, bl_scale_sv = %d "
|
||||
"min_bl %d status 0x%x\n", bl_info.bl_level, bl_info.bl_scale,
|
||||
bl_info.bl_scale_sv, bl_info.min_bl, bl_info.status);
|
||||
msm_mode_object_event_notify(&conn->base.base, conn->base.dev, &event, (u8 *)&bl_info);
|
||||
}
|
||||
|
||||
@@ -181,7 +187,8 @@ static int sde_backlight_device_update_status(struct backlight_device *bd)
|
||||
}
|
||||
rc = c_conn->ops.set_backlight(&c_conn->base,
|
||||
c_conn->display, bl_lvl);
|
||||
sde_dimming_bl_notify(c_conn, &display->panel->bl_config);
|
||||
if (!rc)
|
||||
sde_dimming_bl_notify(c_conn, &display->panel->bl_config);
|
||||
c_conn->unset_bl_level = 0;
|
||||
}
|
||||
|
||||
@@ -693,6 +700,7 @@ static int _sde_connector_update_dimming_bl_lut(struct sde_connector *c_conn,
|
||||
size_t sz = 0;
|
||||
struct dsi_display *dsi_display;
|
||||
struct dsi_backlight_config *bl_config;
|
||||
int rc = 0;
|
||||
|
||||
if (!c_conn || !c_state) {
|
||||
SDE_ERROR("invalid arguments\n");
|
||||
@@ -716,6 +724,81 @@ static int _sde_connector_update_dimming_bl_lut(struct sde_connector *c_conn,
|
||||
bl_config = &dsi_display->panel->bl_config;
|
||||
bl_config->dimming_bl_lut = msm_property_get_blob(&c_conn->property_info,
|
||||
&c_state->property_state, &sz, CONNECTOR_PROP_DIMMING_BL_LUT);
|
||||
rc = c_conn->ops.set_backlight(&c_conn->base,
|
||||
dsi_display, bl_config->bl_level);
|
||||
if (!rc)
|
||||
c_conn->unset_bl_level = 0;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _sde_connector_update_dimming_ctrl(struct sde_connector *c_conn,
|
||||
struct sde_connector_state *c_state, uint64_t val)
|
||||
{
|
||||
struct dsi_display *dsi_display;
|
||||
struct dsi_backlight_config *bl_config;
|
||||
bool prev, curr = (bool)val;
|
||||
|
||||
if (!c_conn || !c_state) {
|
||||
SDE_ERROR("invalid arguments\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
dsi_display = c_conn->display;
|
||||
if (!dsi_display || !dsi_display->panel) {
|
||||
SDE_ERROR("Invalid params(s) dsi_display %pK, panel %pK\n",
|
||||
dsi_display,
|
||||
((dsi_display) ? dsi_display->panel : NULL));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
bl_config = &dsi_display->panel->bl_config;
|
||||
prev = (bool)(bl_config->dimming_status & DIMMING_ENABLE);
|
||||
if (curr == prev)
|
||||
return 0;
|
||||
|
||||
if(val) {
|
||||
bl_config->dimming_status |= DIMMING_ENABLE;
|
||||
} else {
|
||||
bl_config->dimming_status &= ~DIMMING_ENABLE;
|
||||
}
|
||||
bl_config->user_disable_notification = false;
|
||||
sde_dimming_bl_notify(c_conn, bl_config);
|
||||
if (!val)
|
||||
bl_config->user_disable_notification = true;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _sde_connector_update_dimming_min_bl(struct sde_connector *c_conn,
|
||||
struct sde_connector_state *c_state, uint64_t val)
|
||||
{
|
||||
struct dsi_display *dsi_display;
|
||||
struct dsi_backlight_config *bl_config;
|
||||
uint32_t tmp = 0;
|
||||
|
||||
if (!c_conn || !c_state) {
|
||||
SDE_ERROR("invalid arguments\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
dsi_display = c_conn->display;
|
||||
if (!dsi_display || !dsi_display->panel) {
|
||||
SDE_ERROR("Invalid params(s) dsi_display %pK, panel %pK\n",
|
||||
dsi_display,
|
||||
((dsi_display) ? dsi_display->panel : NULL));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
bl_config = &dsi_display->panel->bl_config;
|
||||
tmp = (uint32_t)val;
|
||||
if (tmp == bl_config->dimming_min_bl)
|
||||
return 0;
|
||||
bl_config->dimming_min_bl = tmp;
|
||||
bl_config->dimming_status |= DIMMING_MIN_BL_VALID;
|
||||
sde_dimming_bl_notify(c_conn, bl_config);
|
||||
bl_config->dimming_status &= ~DIMMING_MIN_BL_VALID;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1673,6 +1756,12 @@ static int sde_connector_atomic_set_property(struct drm_connector *connector,
|
||||
case CONNECTOR_PROP_DIMMING_BL_LUT:
|
||||
rc = _sde_connector_update_dimming_bl_lut(c_conn, c_state);
|
||||
break;
|
||||
case CONNECTOR_PROP_DIMMING_CTRL:
|
||||
rc = _sde_connector_update_dimming_ctrl(c_conn, c_state, val);
|
||||
break;
|
||||
case CONNECTOR_PROP_DIMMING_MIN_BL:
|
||||
rc = _sde_connector_update_dimming_min_bl(c_conn, c_state, val);
|
||||
break;
|
||||
case CONNECTOR_PROP_HDR_METADATA:
|
||||
rc = _sde_connector_set_ext_hdr_info(c_conn,
|
||||
c_state, (void *)(uintptr_t)val);
|
||||
@@ -2911,10 +3000,16 @@ static int _sde_connector_install_properties(struct drm_device *dev,
|
||||
|
||||
if (connector_type == DRM_MODE_CONNECTOR_DSI) {
|
||||
dsi_display = (struct dsi_display *)(display);
|
||||
if (dsi_display && dsi_display->panel)
|
||||
if (dsi_display && dsi_display->panel) {
|
||||
msm_property_install_blob(&c_conn->property_info,
|
||||
"dimming_bl_lut", DRM_MODE_PROP_BLOB,
|
||||
CONNECTOR_PROP_DIMMING_BL_LUT);
|
||||
msm_property_install_range(&c_conn->property_info, "dimming_dyn_ctrl",
|
||||
0x0, 0, ~0, 0, CONNECTOR_PROP_DIMMING_CTRL);
|
||||
msm_property_install_range(&c_conn->property_info, "dimming_min_bl",
|
||||
0x0, 0, dsi_display->panel->bl_config.brightness_max_level, 0,
|
||||
CONNECTOR_PROP_DIMMING_MIN_BL);
|
||||
}
|
||||
|
||||
if (dsi_display && dsi_display->panel &&
|
||||
dsi_display->panel->hdr_props.hdr_enabled == true) {
|
||||
|
Reference in New Issue
Block a user