mei: bus: use zero vtag for bus clients.

The zero vtag is required for the read flow to work also for
devices on the mei client bus.

Signed-off-by: Alexander Usyskin <alexander.usyskin@intel.com>
Signed-off-by: Tomas Winkler <tomas.winkler@intel.com>
Link: https://lore.kernel.org/r/20200818115147.2567012-10-tomas.winkler@intel.com
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:
Alexander Usyskin 2020-08-18 14:51:43 +03:00 committed by Greg Kroah-Hartman
parent 15ffa991d9
commit e5617d2bf5

View File

@ -495,6 +495,68 @@ static void mei_cl_bus_module_put(struct mei_cl_device *cldev)
module_put(cldev->bus->dev->driver->owner);
}
/**
* mei_cl_bus_vtag - get bus vtag entry wrapper
* The tag for bus client is always first.
*
* @cl: host client
*
* Return: bus vtag or NULL
*/
static inline struct mei_cl_vtag *mei_cl_bus_vtag(struct mei_cl *cl)
{
return list_first_entry_or_null(&cl->vtag_map,
struct mei_cl_vtag, list);
}
/**
* mei_cl_bus_vtag_alloc - add bus client entry to vtag map
*
* @cldev: me client device
*
* Return:
* * 0 on success
* * -ENOMEM if memory allocation failed
*/
static int mei_cl_bus_vtag_alloc(struct mei_cl_device *cldev)
{
struct mei_cl *cl = cldev->cl;
struct mei_cl_vtag *cl_vtag;
/*
* Bail out if the client does not supports vtags
* or has already allocated one
*/
if (mei_cl_vt_support_check(cl) || mei_cl_bus_vtag(cl))
return 0;
cl_vtag = mei_cl_vtag_alloc(NULL, 0);
if (IS_ERR(cl_vtag))
return -ENOMEM;
list_add_tail(&cl_vtag->list, &cl->vtag_map);
return 0;
}
/**
* mei_cl_bus_vtag_free - remove the bus entry from vtag map
*
* @cldev: me client device
*/
static void mei_cl_bus_vtag_free(struct mei_cl_device *cldev)
{
struct mei_cl *cl = cldev->cl;
struct mei_cl_vtag *cl_vtag;
cl_vtag = mei_cl_bus_vtag(cl);
if (!cl_vtag)
return;
list_del(&cl_vtag->list);
kfree(cl_vtag);
}
/**
* mei_cldev_enable - enable me client device
* create connection with me client
@ -531,9 +593,15 @@ int mei_cldev_enable(struct mei_cl_device *cldev)
goto out;
}
ret = mei_cl_bus_vtag_alloc(cldev);
if (ret)
goto out;
ret = mei_cl_connect(cl, cldev->me_cl, NULL);
if (ret < 0)
if (ret < 0) {
dev_err(&cldev->dev, "cannot connect\n");
mei_cl_bus_vtag_free(cldev);
}
out:
mutex_unlock(&bus->device_lock);
@ -586,6 +654,8 @@ int mei_cldev_disable(struct mei_cl_device *cldev)
mutex_lock(&bus->device_lock);
mei_cl_bus_vtag_free(cldev);
if (!mei_cl_is_connected(cl)) {
dev_dbg(bus->dev, "Already disconnected\n");
err = 0;