From: Takashi Iwai <tiwai@suse.de>
Subject: media: dvb_frontend: kABI workaround
Patch-mainline: Never, kABI workaround
References: CVE-2022-45885 bsc#1205758
For keeping the kABI workaround, the newly introduced remove_mutex
of dvb_frontend to be a global one. It's not urgent for performance,
so we can live with that.
Signed-off-by: Takashi Iwai <tiwai@suse.de>
---
drivers/media/dvb-core/dvb_frontend.c | 23 ++++++++++++-----------
drivers/media/dvb-core/dvb_frontend.h | 4 ----
2 files changed, 12 insertions(+), 15 deletions(-)
--- a/drivers/media/dvb-core/dvb_frontend.c
+++ b/drivers/media/dvb-core/dvb_frontend.c
@@ -100,6 +100,8 @@ MODULE_PARM_DESC(dvb_mfe_wait_time, "Wai
static DEFINE_MUTEX(frontend_mutex);
+static DEFINE_MUTEX(remove_mutex);
+
struct dvb_frontend_private {
/* thread/frontend values */
struct dvb_device *dvbdev;
@@ -816,20 +818,20 @@ static void dvb_frontend_stop(struct dvb
dev_dbg(fe->dvb->device, "%s:\n", __func__);
- mutex_lock(&fe->remove_mutex);
+ mutex_lock(&remove_mutex);
if (fe->exit != DVB_FE_DEVICE_REMOVED)
fe->exit = DVB_FE_NORMAL_EXIT;
mb();
if (!fepriv->thread) {
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
return;
}
kthread_stop(fepriv->thread);
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
if (fepriv->dvbdev->users < -1) {
wait_event(fepriv->dvbdev->wait_queue,
@@ -2507,7 +2509,7 @@ static int dvb_frontend_open(struct inod
struct dvb_adapter *adapter = fe->dvb;
int ret;
- mutex_lock(&fe->remove_mutex);
+ mutex_lock(&remove_mutex);
dev_dbg(fe->dvb->device, "%s:\n", __func__);
if (fe->exit == DVB_FE_DEVICE_REMOVED) {
@@ -2607,7 +2609,7 @@ static int dvb_frontend_open(struct inod
if (adapter->mfe_shared)
mutex_unlock (&adapter->mfe_lock);
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
return ret;
err3:
@@ -2629,7 +2631,7 @@ err0:
mutex_unlock (&adapter->mfe_lock);
err_remove_mutex:
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
return ret;
}
@@ -2640,7 +2642,7 @@ static int dvb_frontend_release(struct i
struct dvb_frontend_private *fepriv = fe->frontend_priv;
int ret;
- mutex_lock(&fe->remove_mutex);
+ mutex_lock(&remove_mutex);
dev_dbg(fe->dvb->device, "%s:\n", __func__);
@@ -2665,14 +2667,14 @@ static int dvb_frontend_release(struct i
fe->ops.ts_bus_ctrl(fe, 0);
if (fe->exit != DVB_FE_NO_EXIT) {
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
wake_up(&dvbdev->wait_queue);
} else {
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
}
} else {
- mutex_unlock(&fe->remove_mutex);
+ mutex_unlock(&remove_mutex);
}
dvb_frontend_put(fe);
@@ -2766,7 +2768,6 @@ int dvb_register_frontend(struct dvb_ada
fepriv = fe->frontend_priv;
kref_init(&fe->refcount);
- mutex_init(&fe->remove_mutex);
/*
* After initialization, there need to be two references: one
--- a/drivers/media/dvb-core/dvb_frontend.h
+++ b/drivers/media/dvb-core/dvb_frontend.h
@@ -659,9 +659,6 @@ struct dtv_frontend_properties {
* @exit: Used to inform the DVB core that the frontend
* thread should exit (usually, means that the hardware
* got disconnected).
- * @remove_mutex: mutex that avoids a race condition between a callback
- * called when the hardware is disconnected and the
- * file_operations of dvb_frontend.
*/
struct dvb_frontend {
@@ -679,7 +676,6 @@ struct dvb_frontend {
int (*callback)(void *adapter_priv, int component, int cmd, int arg);
int id;
unsigned int exit;
- struct mutex remove_mutex;
};
/**