bus/fsl-mc: Export a cleanup function for DPRC

Create and export a cleanup function for DPRC. The function
is used by the DPRC driver, but it will be used by the VFIO
driver as well.

Reviewed-by: Laurentiu Tudor <laurentiu.tudor@nxp.com>
Acked-by: Laurentiu Tudor <laurentiu.tudor@nxp.com>
Signed-off-by: Diana Craciun <diana.craciun@oss.nxp.com>
Link: https://lore.kernel.org/r/20200929085441.17448-9-diana.craciun@oss.nxp.com
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:
Diana Craciun 2020-09-29 11:54:36 +03:00 committed by Greg Kroah-Hartman
parent 5d781fabe6
commit 46f35b5fbb
2 changed files with 52 additions and 18 deletions

View File

@ -727,6 +727,55 @@ static void dprc_teardown_irq(struct fsl_mc_device *mc_dev)
fsl_mc_free_irqs(mc_dev);
}
/**
* dprc_cleanup - function that cleanups a DPRC
*
* @mc_dev: Pointer to fsl-mc device representing the DPRC
*
* It closes the DPRC device in the MC.
* It destroys the interrupt pool associated with this MC bus.
*/
int dprc_cleanup(struct fsl_mc_device *mc_dev)
{
int error;
struct fsl_mc_bus *mc_bus = to_fsl_mc_bus(mc_dev);
/* this function should be called only for DPRCs, it
* is an error to call it for regular objects
*/
if (!is_fsl_mc_bus_dprc(mc_dev))
return -EINVAL;
if (dev_get_msi_domain(&mc_dev->dev)) {
fsl_mc_cleanup_irq_pool(mc_bus);
dev_set_msi_domain(&mc_dev->dev, NULL);
}
fsl_mc_cleanup_all_resource_pools(mc_dev);
/* if this step fails we cannot go further with cleanup as there is no way of
* communicating with the firmware
*/
if (!mc_dev->mc_io) {
dev_err(&mc_dev->dev, "mc_io is NULL, tear down cannot be performed in firmware\n");
return -EINVAL;
}
error = dprc_close(mc_dev->mc_io, 0, mc_dev->mc_handle);
if (error < 0)
dev_err(&mc_dev->dev, "dprc_close() failed: %d\n", error);
if (!fsl_mc_is_root_dprc(&mc_dev->dev)) {
fsl_destroy_mc_io(mc_dev->mc_io);
mc_dev->mc_io = NULL;
}
return 0;
}
EXPORT_SYMBOL_GPL(dprc_cleanup);
/**
* dprc_remove - callback invoked when a DPRC is being unbound from this driver
*
@ -739,13 +788,10 @@ static void dprc_teardown_irq(struct fsl_mc_device *mc_dev)
*/
static int dprc_remove(struct fsl_mc_device *mc_dev)
{
int error;
struct fsl_mc_bus *mc_bus = to_fsl_mc_bus(mc_dev);
if (!is_fsl_mc_bus_dprc(mc_dev))
return -EINVAL;
if (!mc_dev->mc_io)
return -EINVAL;
if (!mc_bus->irq_resources)
return -EINVAL;
@ -755,21 +801,7 @@ static int dprc_remove(struct fsl_mc_device *mc_dev)
device_for_each_child(&mc_dev->dev, NULL, __fsl_mc_device_remove);
if (dev_get_msi_domain(&mc_dev->dev)) {
fsl_mc_cleanup_irq_pool(mc_bus);
dev_set_msi_domain(&mc_dev->dev, NULL);
}
fsl_mc_cleanup_all_resource_pools(mc_dev);
error = dprc_close(mc_dev->mc_io, 0, mc_dev->mc_handle);
if (error < 0)
dev_err(&mc_dev->dev, "dprc_close() failed: %d\n", error);
if (!fsl_mc_is_root_dprc(&mc_dev->dev)) {
fsl_destroy_mc_io(mc_dev->mc_io);
mc_dev->mc_io = NULL;
}
dprc_cleanup(mc_dev);
dev_info(&mc_dev->dev, "DPRC device unbound from driver");
return 0;

View File

@ -538,6 +538,8 @@ void dprc_remove_devices(struct fsl_mc_device *mc_bus_dev,
struct fsl_mc_obj_desc *obj_desc_array,
int num_child_objects_in_mc);
int dprc_cleanup(struct fsl_mc_device *mc_dev);
/*
* Data Path Buffer Pool (DPBP) API
* Contains initialization APIs and runtime control APIs for DPBP