Skip to content

Commit ea83a54

Browse files
Mr-MoratkylieeXD
authored andcommitted
kernel: Optimize performance latency paths for app launch and wake-up
Improve overall responsiveness by reducing delays during cold app start and screen wake-up. System components now react faster to load changes, ensuring smoother and more responsive user interactions Signed-off-by: Mr-Morat <mtarom124@gmail.com>
1 parent 9e528f5 commit ea83a54

File tree

3 files changed

+110
-17
lines changed

3 files changed

+110
-17
lines changed

drivers/video/fbdev/msm/mdss_dsi.c

Lines changed: 85 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1916,6 +1916,68 @@ static irqreturn_t test_hw_vsync_handler(int irq, void *data)
19161916
return IRQ_HANDLED;
19171917
}
19181918

1919+
static int mdss_dsi_disp_wake_thread(void *data)
1920+
{
1921+
static const struct sched_param max_rt_param = {
1922+
.sched_priority = MAX_RT_PRIO - 1
1923+
};
1924+
struct mdss_dsi_ctrl_pdata *ctrl_pdata = data;
1925+
struct mdss_panel_data *pdata = &ctrl_pdata->panel_data;
1926+
1927+
sched_setscheduler_nocheck(current, SCHED_FIFO, &max_rt_param);
1928+
1929+
while (1) {
1930+
bool should_stop;
1931+
1932+
wait_event(ctrl_pdata->wake_waitq,
1933+
(should_stop = kthread_should_stop()) ||
1934+
atomic_cmpxchg(&ctrl_pdata->disp_en,
1935+
MDSS_DISPLAY_WAKING,
1936+
MDSS_DISPLAY_ON) == MDSS_DISPLAY_WAKING);
1937+
1938+
if (should_stop)
1939+
break;
1940+
1941+
/* MDSS_EVENT_LINK_READY */
1942+
if (ctrl_pdata->refresh_clk_rate)
1943+
mdss_dsi_clk_refresh(pdata,
1944+
ctrl_pdata->update_phy_timing);
1945+
mdss_dsi_on(pdata);
1946+
1947+
/* MDSS_EVENT_UNBLANK */
1948+
mdss_dsi_unblank(pdata);
1949+
1950+
/* MDSS_EVENT_PANEL_ON */
1951+
ctrl_pdata->ctrl_state |= CTRL_STATE_MDP_ACTIVE;
1952+
pdata->panel_info.esd_rdy = true;
1953+
1954+
complete_all(&ctrl_pdata->wake_comp);
1955+
}
1956+
1957+
return 0;
1958+
}
1959+
1960+
static void mdss_dsi_display_wake(struct mdss_dsi_ctrl_pdata *ctrl_pdata)
1961+
{
1962+
if (atomic_cmpxchg(&ctrl_pdata->disp_en, MDSS_DISPLAY_OFF,
1963+
MDSS_DISPLAY_WAKING) == MDSS_DISPLAY_OFF)
1964+
wake_up(&ctrl_pdata->wake_waitq);
1965+
}
1966+
1967+
static int mdss_dsi_fb_unblank_cb(struct notifier_block *nb,
1968+
unsigned long action, void *data)
1969+
{
1970+
struct mdss_dsi_ctrl_pdata *ctrl_pdata =
1971+
container_of(nb, typeof(*ctrl_pdata), wake_notif);
1972+
int *blank = ((struct fb_event *)data)->data;
1973+
1974+
/* Parse unblank events as soon as they occur */
1975+
if (action == FB_EARLY_EVENT_BLANK && *blank == FB_BLANK_UNBLANK)
1976+
mdss_dsi_display_wake(ctrl_pdata);
1977+
1978+
return NOTIFY_OK;
1979+
}
1980+
19191981
int mdss_dsi_cont_splash_on(struct mdss_panel_data *pdata)
19201982
{
19211983
int ret = 0;
@@ -3029,25 +3091,12 @@ static int mdss_dsi_event_handler(struct mdss_panel_data *pdata,
30293091
ctrl_pdata->refresh_clk_rate = true;
30303092
break;
30313093
case MDSS_EVENT_LINK_READY:
3032-
if (ctrl_pdata->refresh_clk_rate)
3033-
rc = mdss_dsi_clk_refresh(pdata,
3034-
ctrl_pdata->update_phy_timing);
3035-
3036-
rc = mdss_dsi_on(pdata);
3037-
break;
3038-
case MDSS_EVENT_UNBLANK:
3039-
if (ctrl_pdata->on_cmds.link_state == DSI_LP_MODE)
3040-
rc = mdss_dsi_unblank(pdata);
3094+
/* The unblank notifier handles waking for unblank events */
3095+
mdss_dsi_display_wake(ctrl_pdata);
30413096
break;
30423097
case MDSS_EVENT_POST_PANEL_ON:
30433098
rc = mdss_dsi_post_panel_on(pdata);
30443099
break;
3045-
case MDSS_EVENT_PANEL_ON:
3046-
ctrl_pdata->ctrl_state |= CTRL_STATE_MDP_ACTIVE;
3047-
if (ctrl_pdata->on_cmds.link_state == DSI_HS_MODE)
3048-
rc = mdss_dsi_unblank(pdata);
3049-
pdata->panel_info.esd_rdy = true;
3050-
break;
30513100
case MDSS_EVENT_BLANK:
30523101
power_state = (int) (unsigned long) arg;
30533102
if (ctrl_pdata->off_cmds.link_state == DSI_HS_MODE)
@@ -3059,6 +3108,8 @@ static int mdss_dsi_event_handler(struct mdss_panel_data *pdata,
30593108
if (ctrl_pdata->off_cmds.link_state == DSI_LP_MODE)
30603109
rc = mdss_dsi_blank(pdata, power_state);
30613110
rc = mdss_dsi_off(pdata, power_state);
3111+
reinit_completion(&ctrl_pdata->wake_comp);
3112+
atomic_set(&ctrl_pdata->disp_en, MDSS_DISPLAY_OFF);
30623113
break;
30633114
case MDSS_EVENT_DISABLE_PANEL:
30643115
/* disable esd thread */
@@ -3807,6 +3858,23 @@ static int mdss_dsi_ctrl_probe(struct platform_device *pdev)
38073858
#ifdef CONFIG_DEBUG_FS
38083859
mdss_dsi_debug_bus_init(mdss_dsi_res);
38093860
#endif
3861+
3862+
init_completion(&ctrl_pdata->wake_comp);
3863+
init_waitqueue_head(&ctrl_pdata->wake_waitq);
3864+
ctrl_pdata->wake_thread = kthread_run(mdss_dsi_disp_wake_thread,
3865+
ctrl_pdata, "mdss_display_wake");
3866+
if (IS_ERR(ctrl_pdata->wake_thread)) {
3867+
rc = PTR_ERR(ctrl_pdata->wake_thread);
3868+
pr_err("%s: Failed to start display wake thread, rc=%d\n",
3869+
__func__, rc);
3870+
goto error_shadow_clk_deinit;
3871+
}
3872+
3873+
/* It's sad but not fatal for the fb client register to fail */
3874+
ctrl_pdata->wake_notif.notifier_call = mdss_dsi_fb_unblank_cb;
3875+
ctrl_pdata->wake_notif.priority = INT_MAX;
3876+
fb_register_client(&ctrl_pdata->wake_notif);
3877+
38103878
return 0;
38113879

38123880
error_shadow_clk_deinit:
@@ -4276,7 +4344,8 @@ static int mdss_dsi_ctrl_remove(struct platform_device *pdev)
42764344
}
42774345

42784346
mdss_dsi_pm_qos_remove_request(ctrl_pdata->shared_data);
4279-
4347+
fb_unregister_client(&ctrl_pdata->wake_notif);
4348+
kthread_stop(ctrl_pdata->wake_thread);
42804349
if (msm_dss_config_vreg(&pdev->dev,
42814350
ctrl_pdata->panel_power_data.vreg_config,
42824351
ctrl_pdata->panel_power_data.num_vreg, 1) < 0)

drivers/video/fbdev/msm/mdss_dsi.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -601,6 +601,18 @@ struct mdss_dsi_ctrl_pdata {
601601
bool update_phy_timing; /* flag to recalculate PHY timings */
602602

603603
bool phy_power_off;
604+
605+
struct notifier_block wake_notif;
606+
struct task_struct *wake_thread;
607+
struct completion wake_comp;
608+
wait_queue_head_t wake_waitq;
609+
atomic_t disp_en;
610+
};
611+
612+
enum {
613+
MDSS_DISPLAY_OFF,
614+
MDSS_DISPLAY_WAKING,
615+
MDSS_DISPLAY_ON
604616
};
605617

606618
struct dsi_status_data {

drivers/video/fbdev/msm/mdss_mdp_ctl.c

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
#include "mdss_mdp.h"
2828
#include "mdss_mdp_trace.h"
2929
#include "mdss_debug.h"
30+
#include "mdss_dsi.h"
3031

3132
#define MDSS_MDP_QSEED3_VER_DOWNSCALE_LIM 2
3233
#define NUM_MIXERCFG_REGS 3
@@ -4269,6 +4270,14 @@ int mdss_mdp_ctl_destroy(struct mdss_mdp_ctl *ctl)
42694270
return 0;
42704271
}
42714272

4273+
static void mdss_mdp_wait_for_panel_on(struct mdss_panel_data *pdata)
4274+
{
4275+
struct mdss_dsi_ctrl_pdata *ctrl_pdata =
4276+
container_of(pdata, typeof(*ctrl_pdata), panel_data);
4277+
4278+
wait_for_completion(&ctrl_pdata->wake_comp);
4279+
}
4280+
42724281
int mdss_mdp_ctl_intf_event(struct mdss_mdp_ctl *ctl, int event, void *arg,
42734282
u32 flags)
42744283
{
@@ -4292,8 +4301,11 @@ int mdss_mdp_ctl_intf_event(struct mdss_mdp_ctl *ctl, int event, void *arg,
42924301
pr_debug("sending ctl=%d event=%d flag=0x%x\n", ctl->num, event, flags);
42934302

42944303
do {
4295-
if (pdata->event_handler)
4304+
if (pdata->event_handler) {
42964305
rc = pdata->event_handler(pdata, event, arg);
4306+
if (event == MDSS_EVENT_LINK_READY)
4307+
mdss_mdp_wait_for_panel_on(pdata);
4308+
}
42974309
pdata = pdata->next;
42984310
} while (rc == 0 && pdata && pdata->active &&
42994311
!(flags & CTL_INTF_EVENT_FLAG_SKIP_BROADCAST));

0 commit comments

Comments
 (0)