fpga: bridge: change api, don't use drvdata
Change fpga_bridge_register to not set drvdata. This is to support the case where a PCIe device can have more than one bridge. Add API functions to create/free the fpga bridge struct. Change fpga_bridge_register/unregister to take FPGA bridge struct as the only parameter. struct fpga_bridge *fpga_bridge_create(struct device *dev, const char *name, const struct fpga_bridge_ops *br_ops, void *priv); void fpga_bridge_free(struct fpga_bridge *br); int fpga_bridge_register(struct fpga_bridge *br); void fpga_bridge_unregister(struct fpga_bridge *br); Update the drivers that call fpga_bridge_register with the new API. Signed-off-by: Alan Tull <atull@kernel.org> Reported-by: Jiuyue Ma <majiuyue@huawei.com> Signed-off-by: Moritz Fischer <mdf@kernel.org> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:

committed by
Greg Kroah-Hartman

parent
7085e2a94f
commit
371cd1b1fd
@@ -328,28 +328,29 @@ static struct attribute *fpga_bridge_attrs[] = {
|
||||
ATTRIBUTE_GROUPS(fpga_bridge);
|
||||
|
||||
/**
|
||||
* fpga_bridge_register - register a fpga bridge driver
|
||||
* fpga_bridge_create - create and initialize a struct fpga_bridge
|
||||
* @dev: FPGA bridge device from pdev
|
||||
* @name: FPGA bridge name
|
||||
* @br_ops: pointer to structure of fpga bridge ops
|
||||
* @priv: FPGA bridge private data
|
||||
*
|
||||
* Return: 0 for success, error code otherwise.
|
||||
* Return: struct fpga_bridge or NULL
|
||||
*/
|
||||
int fpga_bridge_register(struct device *dev, const char *name,
|
||||
const struct fpga_bridge_ops *br_ops, void *priv)
|
||||
struct fpga_bridge *fpga_bridge_create(struct device *dev, const char *name,
|
||||
const struct fpga_bridge_ops *br_ops,
|
||||
void *priv)
|
||||
{
|
||||
struct fpga_bridge *bridge;
|
||||
int id, ret = 0;
|
||||
|
||||
if (!name || !strlen(name)) {
|
||||
dev_err(dev, "Attempt to register with no name!\n");
|
||||
return -EINVAL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bridge = kzalloc(sizeof(*bridge), GFP_KERNEL);
|
||||
if (!bridge)
|
||||
return -ENOMEM;
|
||||
return NULL;
|
||||
|
||||
id = ida_simple_get(&fpga_bridge_ida, 0, 0, GFP_KERNEL);
|
||||
if (id < 0) {
|
||||
@@ -370,40 +371,62 @@ int fpga_bridge_register(struct device *dev, const char *name,
|
||||
bridge->dev.parent = dev;
|
||||
bridge->dev.of_node = dev->of_node;
|
||||
bridge->dev.id = id;
|
||||
dev_set_drvdata(dev, bridge);
|
||||
|
||||
ret = dev_set_name(&bridge->dev, "br%d", id);
|
||||
if (ret)
|
||||
goto error_device;
|
||||
|
||||
ret = device_add(&bridge->dev);
|
||||
if (ret)
|
||||
goto error_device;
|
||||
|
||||
of_platform_populate(dev->of_node, NULL, NULL, dev);
|
||||
|
||||
dev_info(bridge->dev.parent, "fpga bridge [%s] registered\n",
|
||||
bridge->name);
|
||||
|
||||
return 0;
|
||||
return bridge;
|
||||
|
||||
error_device:
|
||||
ida_simple_remove(&fpga_bridge_ida, id);
|
||||
error_kfree:
|
||||
kfree(bridge);
|
||||
|
||||
return ret;
|
||||
return NULL;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(fpga_bridge_create);
|
||||
|
||||
/**
|
||||
* fpga_bridge_free - free a fpga bridge and its id
|
||||
* @bridge: FPGA bridge struct created by fpga_bridge_create
|
||||
*/
|
||||
void fpga_bridge_free(struct fpga_bridge *bridge)
|
||||
{
|
||||
ida_simple_remove(&fpga_bridge_ida, bridge->dev.id);
|
||||
kfree(bridge);
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(fpga_bridge_free);
|
||||
|
||||
/**
|
||||
* fpga_bridge_register - register a fpga bridge
|
||||
* @bridge: FPGA bridge struct created by fpga_bridge_create
|
||||
*
|
||||
* Return: 0 for success, error code otherwise.
|
||||
*/
|
||||
int fpga_bridge_register(struct fpga_bridge *bridge)
|
||||
{
|
||||
struct device *dev = &bridge->dev;
|
||||
int ret;
|
||||
|
||||
ret = device_add(dev);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
of_platform_populate(dev->of_node, NULL, NULL, dev);
|
||||
|
||||
dev_info(dev->parent, "fpga bridge [%s] registered\n", bridge->name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(fpga_bridge_register);
|
||||
|
||||
/**
|
||||
* fpga_bridge_unregister - unregister a fpga bridge driver
|
||||
* @dev: FPGA bridge device from pdev
|
||||
* @bridge: FPGA bridge struct created by fpga_bridge_create
|
||||
*/
|
||||
void fpga_bridge_unregister(struct device *dev)
|
||||
void fpga_bridge_unregister(struct fpga_bridge *bridge)
|
||||
{
|
||||
struct fpga_bridge *bridge = dev_get_drvdata(dev);
|
||||
|
||||
/*
|
||||
* If the low level driver provides a method for putting bridge into
|
||||
* a desired state upon unregister, do it.
|
||||
@@ -419,8 +442,7 @@ static void fpga_bridge_dev_release(struct device *dev)
|
||||
{
|
||||
struct fpga_bridge *bridge = to_fpga_bridge(dev);
|
||||
|
||||
ida_simple_remove(&fpga_bridge_ida, bridge->dev.id);
|
||||
kfree(bridge);
|
||||
fpga_bridge_free(bridge);
|
||||
}
|
||||
|
||||
static int __init fpga_bridge_dev_init(void)
|
||||
|
Reference in New Issue
Block a user