summaryrefslogtreecommitdiff
path: root/drivers/media/cec/core
diff options
context:
space:
mode:
authorJani Nikula <jani.nikula@intel.com>2023-09-15 11:23:38 +0300
committerJani Nikula <jani.nikula@intel.com>2023-09-15 11:23:38 +0300
commita3f9e4bc1ec9d8f1e352eb7c1cbaea3168246be7 (patch)
tree5a2ad89248d8fe7a2da8904dd29042abb9f71739 /drivers/media/cec/core
parent3106c34df6ace8a123027b9afdc73bb05d530052 (diff)
parent0bb80ecc33a8fb5a682236443c1e740d5c917d1d (diff)
Merge drm/drm-next into drm-intel-next
Sync to v6.6-rc1. Signed-off-by: Jani Nikula <jani.nikula@intel.com>
Diffstat (limited to 'drivers/media/cec/core')
-rw-r--r--drivers/media/cec/core/cec-adap.c8
-rw-r--r--drivers/media/cec/core/cec-notifier.c1
-rw-r--r--drivers/media/cec/core/cec-pin-priv.h1
-rw-r--r--drivers/media/cec/core/cec-pin.c32
4 files changed, 28 insertions, 14 deletions
diff --git a/drivers/media/cec/core/cec-adap.c b/drivers/media/cec/core/cec-adap.c
index 1109af525c35..6bb49bb3f98c 100644
--- a/drivers/media/cec/core/cec-adap.c
+++ b/drivers/media/cec/core/cec-adap.c
@@ -385,8 +385,8 @@ static void cec_data_cancel(struct cec_data *data, u8 tx_status, u8 rx_status)
cec_queue_msg_monitor(adap, &data->msg, 1);
if (!data->blocking && data->msg.sequence)
- /* Allow drivers to process the message first */
- call_op(adap, received, &data->msg);
+ /* Allow drivers to react to a canceled transmit */
+ call_void_op(adap, adap_nb_transmit_canceled, &data->msg);
cec_data_completed(data);
}
@@ -1348,7 +1348,7 @@ static void cec_adap_unconfigure(struct cec_adapter *adap)
cec_flush(adap);
wake_up_interruptible(&adap->kthread_waitq);
cec_post_state_event(adap);
- call_void_op(adap, adap_configured, false);
+ call_void_op(adap, adap_unconfigured);
}
/*
@@ -1539,7 +1539,7 @@ configured:
adap->kthread_config = NULL;
complete(&adap->config_completion);
mutex_unlock(&adap->lock);
- call_void_op(adap, adap_configured, true);
+ call_void_op(adap, configured);
return 0;
unconfigure:
diff --git a/drivers/media/cec/core/cec-notifier.c b/drivers/media/cec/core/cec-notifier.c
index d600be0f7b67..1fed0b1c71e9 100644
--- a/drivers/media/cec/core/cec-notifier.c
+++ b/drivers/media/cec/core/cec-notifier.c
@@ -7,6 +7,7 @@
*/
#include <linux/export.h>
+#include <linux/platform_device.h>
#include <linux/string.h>
#include <linux/slab.h>
#include <linux/i2c.h>
diff --git a/drivers/media/cec/core/cec-pin-priv.h b/drivers/media/cec/core/cec-pin-priv.h
index 8eb5819e6ccb..156a9f81be94 100644
--- a/drivers/media/cec/core/cec-pin-priv.h
+++ b/drivers/media/cec/core/cec-pin-priv.h
@@ -183,6 +183,7 @@ struct cec_pin {
u16 la_mask;
bool monitor_all;
bool rx_eom;
+ bool enabled_irq;
bool enable_irq_failed;
enum cec_pin_state state;
struct cec_msg tx_msg;
diff --git a/drivers/media/cec/core/cec-pin.c b/drivers/media/cec/core/cec-pin.c
index 68353c5dc501..330d5d5d86ab 100644
--- a/drivers/media/cec/core/cec-pin.c
+++ b/drivers/media/cec/core/cec-pin.c
@@ -982,7 +982,7 @@ static enum hrtimer_restart cec_pin_timer(struct hrtimer *timer)
}
if (pin->state != CEC_ST_IDLE || pin->ops->enable_irq == NULL ||
pin->enable_irq_failed || adap->is_configuring ||
- adap->is_configured || adap->monitor_all_cnt)
+ adap->is_configured || adap->monitor_all_cnt || !adap->monitor_pin_cnt)
break;
/* Switch to interrupt mode */
atomic_set(&pin->work_irq_change, CEC_PIN_IRQ_ENABLE);
@@ -1033,8 +1033,9 @@ static int cec_pin_thread_func(void *_adap)
{
struct cec_adapter *adap = _adap;
struct cec_pin *pin = adap->pin;
- bool irq_enabled = false;
+ pin->enabled_irq = false;
+ pin->enable_irq_failed = false;
for (;;) {
wait_event_interruptible(pin->kthread_waitq,
kthread_should_stop() ||
@@ -1088,9 +1089,10 @@ static int cec_pin_thread_func(void *_adap)
switch (atomic_xchg(&pin->work_irq_change,
CEC_PIN_IRQ_UNCHANGED)) {
case CEC_PIN_IRQ_DISABLE:
- if (irq_enabled) {
- call_void_pin_op(pin, disable_irq);
- irq_enabled = false;
+ if (pin->enabled_irq) {
+ pin->ops->disable_irq(adap);
+ pin->enabled_irq = false;
+ pin->enable_irq_failed = false;
}
cec_pin_high(pin);
if (pin->state == CEC_ST_OFF)
@@ -1100,21 +1102,29 @@ static int cec_pin_thread_func(void *_adap)
HRTIMER_MODE_REL);
break;
case CEC_PIN_IRQ_ENABLE:
- if (irq_enabled)
+ if (pin->enabled_irq || !pin->ops->enable_irq ||
+ pin->adap->devnode.unregistered)
break;
- pin->enable_irq_failed = !call_pin_op(pin, enable_irq);
+ pin->enable_irq_failed = !pin->ops->enable_irq(adap);
if (pin->enable_irq_failed) {
cec_pin_to_idle(pin);
hrtimer_start(&pin->timer, ns_to_ktime(0),
HRTIMER_MODE_REL);
} else {
- irq_enabled = true;
+ pin->enabled_irq = true;
}
break;
default:
break;
}
}
+
+ if (pin->enabled_irq) {
+ pin->ops->disable_irq(pin->adap);
+ pin->enabled_irq = false;
+ pin->enable_irq_failed = false;
+ cec_pin_high(pin);
+ }
return 0;
}
@@ -1215,7 +1225,9 @@ static void cec_pin_adap_status(struct cec_adapter *adap,
seq_printf(file, "cec pin: %d\n", call_pin_op(pin, read));
seq_printf(file, "cec pin events dropped: %u\n",
pin->work_pin_events_dropped_cnt);
- seq_printf(file, "irq failed: %d\n", pin->enable_irq_failed);
+ if (pin->ops->enable_irq)
+ seq_printf(file, "irq %s\n", pin->enabled_irq ? "enabled" :
+ (pin->enable_irq_failed ? "failed" : "disabled"));
if (pin->timer_100us_overruns) {
seq_printf(file, "timer overruns > 100us: %u of %u\n",
pin->timer_100us_overruns, pin->timer_cnt);
@@ -1305,7 +1317,7 @@ void cec_pin_changed(struct cec_adapter *adap, bool value)
cec_pin_update(pin, value, false);
if (!value && (adap->is_configuring || adap->is_configured ||
- adap->monitor_all_cnt))
+ adap->monitor_all_cnt || !adap->monitor_pin_cnt))
atomic_set(&pin->work_irq_change, CEC_PIN_IRQ_DISABLE);
}
EXPORT_SYMBOL_GPL(cec_pin_changed);