summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--drivers/char/diag/diag_dci.c4
-rw-r--r--drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c8
-rw-r--r--drivers/media/platform/msm/vidc/hfi_response_handler.c30
-rw-r--r--drivers/media/platform/msm/vidc/vidc_hfi.h4
-rw-r--r--drivers/media/platform/msm/vidc/vidc_hfi_helper.h1
-rw-r--r--drivers/soc/qcom/icnss.c109
-rw-r--r--drivers/video/fbdev/msm/mdss_hdmi_tx.c5
-rw-r--r--drivers/video/fbdev/msm/mdss_hdmi_util.c6
-rw-r--r--include/soc/qcom/icnss.h4
-rw-r--r--sound/soc/msm/qdsp6v2/q6afe.c2
10 files changed, 154 insertions, 19 deletions
diff --git a/drivers/char/diag/diag_dci.c b/drivers/char/diag/diag_dci.c
index 19fbd702c0e6..ad00b91ae173 100644
--- a/drivers/char/diag/diag_dci.c
+++ b/drivers/char/diag/diag_dci.c
@@ -1813,9 +1813,9 @@ static int diag_dci_process_apps_pkt(struct diag_pkt_header_t *pkt_header,
unsigned char *req_buf, int req_len,
int tag, int pkt_header_len)
{
- uint8_t cmd_code, subsys_id, i, goto_download = 0;
+ uint8_t cmd_code = 0, subsys_id = 0, i, goto_download = 0;
uint8_t header_len = sizeof(struct diag_dci_pkt_header_t);
- uint16_t ss_cmd_code;
+ uint16_t ss_cmd_code = 0;
uint32_t write_len = 0;
unsigned char *dest_buf = driver->apps_dci_buf;
unsigned char *payload_ptr = driver->apps_dci_buf + header_len;
diff --git a/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c b/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c
index 252a6289881f..75543c768d45 100644
--- a/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c
+++ b/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016-2018, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2019, The Linux Foundation. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -123,6 +123,9 @@ static ssize_t debugfs_state_info_read(struct file *file,
dsi_ctrl->clk_info.link_clks.pixel_clk_rate,
dsi_ctrl->clk_info.link_clks.esc_clk_rate);
+ if (len > count)
+ len = count;
+
/* TODO: make sure that this does not exceed 4K */
if (copy_to_user(buff, buf, len)) {
kfree(buf);
@@ -162,6 +165,9 @@ static ssize_t debugfs_reg_dump_read(struct file *file,
"Core clocks are not turned on, cannot read\n");
}
+ if (len > count)
+ len = count;
+
/* TODO: make sure that this does not exceed 4K */
if (copy_to_user(buff, buf, len)) {
kfree(buf);
diff --git a/drivers/media/platform/msm/vidc/hfi_response_handler.c b/drivers/media/platform/msm/vidc/hfi_response_handler.c
index e3e4c97a5220..ec55bc7b0d89 100644
--- a/drivers/media/platform/msm/vidc/hfi_response_handler.c
+++ b/drivers/media/platform/msm/vidc/hfi_response_handler.c
@@ -284,6 +284,12 @@ static int hfi_process_evt_release_buffer_ref(u32 device_id,
"hal_process_session_init_done: bad_pkt_size\n");
return -E2BIG;
}
+ if (pkt->size < sizeof(struct hfi_msg_event_notify_packet) - sizeof(u32)
+ + sizeof(struct hfi_msg_release_buffer_ref_event_packet)) {
+ dprintk(VIDC_ERR, "%s: bad_pkt_size: %d\n",
+ __func__, pkt->size);
+ return -E2BIG;
+ }
data = (struct hfi_msg_release_buffer_ref_event_packet *)
pkt->rg_ext_event_data;
@@ -1546,15 +1552,13 @@ static int hfi_process_session_etb_done(u32 device_id,
struct hfi_msg_session_empty_buffer_done_packet *pkt = _pkt;
struct msm_vidc_cb_data_done data_done = {0};
struct hfi_picture_type *hfi_picture_type = NULL;
+ u32 is_sync_frame;
dprintk(VIDC_DBG, "RECEIVED: SESSION_ETB_DONE[%#x]\n", pkt->session_id);
if (!pkt || pkt->size <
- sizeof(struct hfi_msg_session_empty_buffer_done_packet)) {
- dprintk(VIDC_ERR,
- "hal_process_session_etb_done: bad_pkt_size\n");
- return -E2BIG;
- }
+ sizeof(struct hfi_msg_session_empty_buffer_done_packet))
+ goto bad_packet_size;
data_done.device_id = device_id;
data_done.session_id = (void *)(uintptr_t)pkt->session_id;
@@ -1569,8 +1573,13 @@ static int hfi_process_session_etb_done(u32 device_id,
(ion_phys_addr_t)pkt->extra_data_buffer;
data_done.input_done.status =
hfi_map_err_status(pkt->error_type);
- hfi_picture_type = (struct hfi_picture_type *)&pkt->rgData[0];
- if (hfi_picture_type->is_sync_frame) {
+ is_sync_frame = pkt->rgData[0];
+ if (is_sync_frame == 1) {
+ if (pkt->size <
+ sizeof(struct hfi_msg_session_empty_buffer_done_packet)
+ + sizeof(struct hfi_picture_type))
+ goto bad_packet_size;
+ hfi_picture_type = (struct hfi_picture_type *)&pkt->rgData[1];
if (hfi_picture_type->picture_type)
data_done.input_done.flags =
hfi_picture_type->picture_type;
@@ -1589,6 +1598,10 @@ static int hfi_process_session_etb_done(u32 device_id,
};
return 0;
+bad_packet_size:
+ dprintk(VIDC_ERR, "%s: bad_pkt_size: %d\n",
+ __func__, pkt ? pkt->size : 0);
+ return -E2BIG;
}
static int hfi_process_session_ftb_done(
@@ -1829,8 +1842,7 @@ static int hfi_process_session_rel_buf_done(u32 device_id,
cmd_done.session_id = (void *)(uintptr_t)pkt->session_id;
cmd_done.status = hfi_map_err_status(pkt->error_type);
if (pkt->rg_buffer_info) {
- cmd_done.data.buffer_info =
- *(struct hal_buffer_info *)pkt->rg_buffer_info;
+ cmd_done.data.buffer_info.buffer_addr = *pkt->rg_buffer_info;
cmd_done.size = sizeof(struct hal_buffer_info);
} else {
dprintk(VIDC_ERR, "invalid payload in rel_buff_done\n");
diff --git a/drivers/media/platform/msm/vidc/vidc_hfi.h b/drivers/media/platform/msm/vidc/vidc_hfi.h
index 4cbb59d12f92..978fdc6bbb6d 100644
--- a/drivers/media/platform/msm/vidc/vidc_hfi.h
+++ b/drivers/media/platform/msm/vidc/vidc_hfi.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012-2016, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2012-2016,2019 The Linux Foundation. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -662,7 +662,7 @@ struct hfi_msg_session_empty_buffer_done_packet {
u32 input_tag;
u32 packet_buffer;
u32 extra_data_buffer;
- u32 rgData[0];
+ u32 rgData[1];
};
struct hfi_msg_session_fill_buffer_done_compressed_packet {
diff --git a/drivers/media/platform/msm/vidc/vidc_hfi_helper.h b/drivers/media/platform/msm/vidc/vidc_hfi_helper.h
index 3709ad9fc658..27acb5fd9ca4 100644
--- a/drivers/media/platform/msm/vidc/vidc_hfi_helper.h
+++ b/drivers/media/platform/msm/vidc/vidc_hfi_helper.h
@@ -703,7 +703,6 @@ struct hfi_bit_depth {
};
struct hfi_picture_type {
- u32 is_sync_frame;
u32 picture_type;
};
diff --git a/drivers/soc/qcom/icnss.c b/drivers/soc/qcom/icnss.c
index 17bfb06a5651..714a4f16cd01 100644
--- a/drivers/soc/qcom/icnss.c
+++ b/drivers/soc/qcom/icnss.c
@@ -196,6 +196,8 @@ enum icnss_driver_event_type {
ICNSS_DRIVER_EVENT_REGISTER_DRIVER,
ICNSS_DRIVER_EVENT_UNREGISTER_DRIVER,
ICNSS_DRIVER_EVENT_PD_SERVICE_DOWN,
+ ICNSS_DRIVER_EVENT_IDLE_SHUTDOWN,
+ ICNSS_DRIVER_EVENT_IDLE_RESTART,
ICNSS_DRIVER_EVENT_MAX,
};
@@ -303,6 +305,7 @@ enum icnss_driver_state {
ICNSS_REJUVENATE,
ICNSS_BLOCK_SHUTDOWN,
ICNSS_PDR,
+ ICNSS_MODEM_CRASHED,
};
struct ce_irq_list {
@@ -636,6 +639,10 @@ static char *icnss_driver_event_to_str(enum icnss_driver_event_type type)
return "UNREGISTER_DRIVER";
case ICNSS_DRIVER_EVENT_PD_SERVICE_DOWN:
return "PD_SERVICE_DOWN";
+ case ICNSS_DRIVER_EVENT_IDLE_SHUTDOWN:
+ return "IDLE_SHUTDOWN";
+ case ICNSS_DRIVER_EVENT_IDLE_RESTART:
+ return "IDLE_RESTART";
case ICNSS_DRIVER_EVENT_MAX:
return "EVENT_MAX";
}
@@ -2303,6 +2310,7 @@ static int icnss_pd_restart_complete(struct icnss_priv *priv)
icnss_call_driver_shutdown(priv);
clear_bit(ICNSS_PDR, &priv->state);
+ clear_bit(ICNSS_MODEM_CRASHED, &priv->state);
clear_bit(ICNSS_REJUVENATE, &priv->state);
clear_bit(ICNSS_PD_RESTART, &priv->state);
priv->is_ssr = false;
@@ -2494,6 +2502,52 @@ out:
return ret;
}
+static int icnss_driver_event_idle_shutdown(void *data)
+{
+ int ret = 0;
+
+ if (!penv->ops || !penv->ops->idle_shutdown)
+ return 0;
+
+ if (test_bit(ICNSS_MODEM_CRASHED, &penv->state) ||
+ test_bit(ICNSS_PDR, &penv->state) ||
+ test_bit(ICNSS_REJUVENATE, &penv->state)) {
+ icnss_pr_err("SSR/PDR is already in-progress during idle shutdown callback\n");
+ ret = -EBUSY;
+ } else {
+ icnss_pr_dbg("Calling driver idle shutdown, state: 0x%lx\n",
+ penv->state);
+ icnss_block_shutdown(true);
+ ret = penv->ops->idle_shutdown(&penv->pdev->dev);
+ icnss_block_shutdown(false);
+ }
+
+ return ret;
+}
+
+static int icnss_driver_event_idle_restart(void *data)
+{
+ int ret = 0;
+
+ if (!penv->ops || !penv->ops->idle_restart)
+ return 0;
+
+ if (test_bit(ICNSS_MODEM_CRASHED, &penv->state) ||
+ test_bit(ICNSS_PDR, &penv->state) ||
+ test_bit(ICNSS_REJUVENATE, &penv->state)) {
+ icnss_pr_err("SSR/PDR is already in-progress during idle restart callback\n");
+ ret = -EBUSY;
+ } else {
+ icnss_pr_dbg("Calling driver idle restart, state: 0x%lx\n",
+ penv->state);
+ icnss_block_shutdown(true);
+ ret = penv->ops->idle_restart(&penv->pdev->dev);
+ icnss_block_shutdown(false);
+ }
+
+ return ret;
+}
+
static void icnss_driver_event_work(struct work_struct *work)
{
struct icnss_driver_event *event;
@@ -2535,6 +2589,12 @@ static void icnss_driver_event_work(struct work_struct *work)
ret = icnss_driver_event_pd_service_down(penv,
event->data);
break;
+ case ICNSS_DRIVER_EVENT_IDLE_SHUTDOWN:
+ ret = icnss_driver_event_idle_shutdown(event->data);
+ break;
+ case ICNSS_DRIVER_EVENT_IDLE_RESTART:
+ ret = icnss_driver_event_idle_restart(event->data);
+ break;
default:
icnss_pr_err("Invalid Event type: %d", event->type);
kfree(event);
@@ -2641,6 +2701,9 @@ static int icnss_modem_notifier_nb(struct notifier_block *nb,
priv->is_ssr = true;
+ if (notif->crashed)
+ set_bit(ICNSS_MODEM_CRASHED, &priv->state);
+
if (code == SUBSYS_BEFORE_SHUTDOWN && !notif->crashed &&
test_bit(ICNSS_BLOCK_SHUTDOWN, &priv->state)) {
if (!wait_for_completion_timeout(&priv->unblock_shutdown,
@@ -3597,6 +3660,48 @@ out:
}
EXPORT_SYMBOL(icnss_trigger_recovery);
+int icnss_idle_shutdown(struct device *dev)
+{
+ struct icnss_priv *priv = dev_get_drvdata(dev);
+
+ if (!priv) {
+ icnss_pr_err("Invalid drvdata: dev %pK", dev);
+ return -EINVAL;
+ }
+
+ if (test_bit(ICNSS_MODEM_CRASHED, &priv->state) ||
+ test_bit(ICNSS_PDR, &priv->state) ||
+ test_bit(ICNSS_REJUVENATE, &penv->state)) {
+ icnss_pr_err("SSR/PDR is already in-progress during idle shutdown\n");
+ return -EBUSY;
+ }
+
+ return icnss_driver_event_post(ICNSS_DRIVER_EVENT_IDLE_SHUTDOWN,
+ ICNSS_EVENT_SYNC_UNINTERRUPTIBLE, NULL);
+}
+EXPORT_SYMBOL(icnss_idle_shutdown);
+
+int icnss_idle_restart(struct device *dev)
+{
+ struct icnss_priv *priv = dev_get_drvdata(dev);
+
+ if (!priv) {
+ icnss_pr_err("Invalid drvdata: dev %pK", dev);
+ return -EINVAL;
+ }
+
+ if (test_bit(ICNSS_MODEM_CRASHED, &priv->state) ||
+ test_bit(ICNSS_PDR, &priv->state) ||
+ test_bit(ICNSS_REJUVENATE, &penv->state)) {
+ icnss_pr_err("SSR/PDR is already in-progress during idle restart\n");
+ return -EBUSY;
+ }
+
+ return icnss_driver_event_post(ICNSS_DRIVER_EVENT_IDLE_RESTART,
+ ICNSS_EVENT_SYNC_UNINTERRUPTIBLE, NULL);
+}
+EXPORT_SYMBOL(icnss_idle_restart);
+
static int icnss_smmu_init(struct icnss_priv *priv)
{
@@ -4053,6 +4158,10 @@ static int icnss_stats_show_state(struct seq_file *s, struct icnss_priv *priv)
continue;
case ICNSS_PDR:
seq_puts(s, "PDR TRIGGERED");
+ continue;
+ case ICNSS_MODEM_CRASHED:
+ seq_puts(s, "MODEM CRASHED");
+ continue;
}
seq_printf(s, "UNKNOWN-%d", i);
diff --git a/drivers/video/fbdev/msm/mdss_hdmi_tx.c b/drivers/video/fbdev/msm/mdss_hdmi_tx.c
index 4f30f7864bb0..0778e43fe0ff 100644
--- a/drivers/video/fbdev/msm/mdss_hdmi_tx.c
+++ b/drivers/video/fbdev/msm/mdss_hdmi_tx.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2010-2017, 2019, The Linux Foundation. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -3742,7 +3742,8 @@ static int hdmi_tx_hdcp_off(struct hdmi_tx_ctrl *hdmi_ctrl)
DEV_DBG("%s: Turning off HDCP\n", __func__);
hdmi_ctrl->hdcp_ops->off(hdmi_ctrl->hdcp_data);
- flush_delayed_work(&hdmi_ctrl->hdcp_cb_work);
+ hdmi_ctrl->hdcp_status = HDCP_STATE_INACTIVE;
+ cancel_delayed_work(&hdmi_ctrl->hdcp_cb_work);
hdmi_ctrl->hdcp_ops = NULL;
diff --git a/drivers/video/fbdev/msm/mdss_hdmi_util.c b/drivers/video/fbdev/msm/mdss_hdmi_util.c
index 8b8b4120d3fb..8e854c54bae8 100644
--- a/drivers/video/fbdev/msm/mdss_hdmi_util.c
+++ b/drivers/video/fbdev/msm/mdss_hdmi_util.c
@@ -959,13 +959,17 @@ error:
void hdmi_ddc_config(struct hdmi_tx_ddc_ctrl *ddc_ctrl)
{
+ u32 ddc_speed;
+
if (!ddc_ctrl || !ddc_ctrl->io) {
pr_err("invalid input\n");
return;
}
/* Configure Pre-Scale multiplier & Threshold */
- DSS_REG_W_ND(ddc_ctrl->io, HDMI_DDC_SPEED, (10 << 16) | (2 << 0));
+ ddc_speed = DSS_REG_R_ND(ddc_ctrl->io, HDMI_DDC_SPEED);
+ ddc_speed |= (12 << 16) | (2 << 0);
+ DSS_REG_W_ND(ddc_ctrl->io, HDMI_DDC_SPEED, ddc_speed);
/*
* Setting 31:24 bits : Time units to wait before timeout
diff --git a/include/soc/qcom/icnss.h b/include/soc/qcom/icnss.h
index 4de4cd5e89dc..716e28054e60 100644
--- a/include/soc/qcom/icnss.h
+++ b/include/soc/qcom/icnss.h
@@ -56,6 +56,8 @@ struct icnss_driver_ops {
int (*suspend_noirq)(struct device *dev);
int (*resume_noirq)(struct device *dev);
int (*uevent)(struct device *dev, struct icnss_uevent_data *uevent);
+ int (*idle_shutdown)(struct device *dev);
+ int (*idle_restart)(struct device *dev);
};
@@ -159,4 +161,6 @@ extern u8 *icnss_get_wlan_mac_address(struct device *dev, uint32_t *num);
extern int icnss_trigger_recovery(struct device *dev);
extern void icnss_block_shutdown(bool status);
extern bool icnss_is_pdr(void);
+extern int icnss_idle_restart(struct device *dev);
+extern int icnss_idle_shutdown(struct device *dev);
#endif /* _ICNSS_WLAN_H_ */
diff --git a/sound/soc/msm/qdsp6v2/q6afe.c b/sound/soc/msm/qdsp6v2/q6afe.c
index c8a2cc37363c..7ee774ddccf7 100644
--- a/sound/soc/msm/qdsp6v2/q6afe.c
+++ b/sound/soc/msm/qdsp6v2/q6afe.c
@@ -1241,7 +1241,7 @@ static int q6afe_get_params_v2(u16 port_id, int index,
afe_get_param.apr_hdr.hdr_field =
APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD, APR_HDR_LEN(APR_HDR_SIZE),
APR_PKT_VER);
- afe_get_param.apr_hdr.pkt_size = sizeof(afe_get_param) + param_size;
+ afe_get_param.apr_hdr.pkt_size = sizeof(afe_get_param);
afe_get_param.apr_hdr.src_port = 0;
afe_get_param.apr_hdr.dest_port = 0;
afe_get_param.apr_hdr.token = index;