1 // SPDX-License-Identifier: GPL-2.0
3 * Greybus Bridged-Phy Bus driver
5 * Copyright 2014 Google Inc.
6 * Copyright 2014 Linaro Ltd.
9 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
11 #include <linux/types.h>
12 #include <linux/module.h>
13 #include <linux/kernel.h>
14 #include <linux/slab.h>
15 #include <linux/device.h>
16 #include <linux/greybus.h>
20 #define GB_GBPHY_AUTOSUSPEND_MS 3000
23 struct gb_bundle
*bundle
;
24 struct list_head devices
;
27 static DEFINE_IDA(gbphy_id
);
29 static ssize_t
protocol_id_show(struct device
*dev
,
30 struct device_attribute
*attr
, char *buf
)
32 struct gbphy_device
*gbphy_dev
= to_gbphy_dev(dev
);
34 return sprintf(buf
, "0x%02x\n", gbphy_dev
->cport_desc
->protocol_id
);
36 static DEVICE_ATTR_RO(protocol_id
);
38 static struct attribute
*gbphy_dev_attrs
[] = {
39 &dev_attr_protocol_id
.attr
,
43 ATTRIBUTE_GROUPS(gbphy_dev
);
45 static void gbphy_dev_release(struct device
*dev
)
47 struct gbphy_device
*gbphy_dev
= to_gbphy_dev(dev
);
49 ida_simple_remove(&gbphy_id
, gbphy_dev
->id
);
54 static int gb_gbphy_idle(struct device
*dev
)
56 pm_runtime_mark_last_busy(dev
);
57 pm_request_autosuspend(dev
);
62 static const struct dev_pm_ops gb_gbphy_pm_ops
= {
63 SET_RUNTIME_PM_OPS(pm_generic_runtime_suspend
,
64 pm_generic_runtime_resume
,
68 static const struct device_type greybus_gbphy_dev_type
= {
69 .name
= "gbphy_device",
70 .release
= gbphy_dev_release
,
71 .pm
= &gb_gbphy_pm_ops
,
74 static int gbphy_dev_uevent(struct device
*dev
, struct kobj_uevent_env
*env
)
76 struct gbphy_device
*gbphy_dev
= to_gbphy_dev(dev
);
77 struct greybus_descriptor_cport
*cport_desc
= gbphy_dev
->cport_desc
;
78 struct gb_bundle
*bundle
= gbphy_dev
->bundle
;
79 struct gb_interface
*intf
= bundle
->intf
;
80 struct gb_module
*module
= intf
->module
;
81 struct gb_host_device
*hd
= intf
->hd
;
83 if (add_uevent_var(env
, "BUS=%u", hd
->bus_id
))
85 if (add_uevent_var(env
, "MODULE=%u", module
->module_id
))
87 if (add_uevent_var(env
, "INTERFACE=%u", intf
->interface_id
))
89 if (add_uevent_var(env
, "GREYBUS_ID=%08x/%08x",
90 intf
->vendor_id
, intf
->product_id
))
92 if (add_uevent_var(env
, "BUNDLE=%u", gbphy_dev
->bundle
->id
))
94 if (add_uevent_var(env
, "BUNDLE_CLASS=%02x", bundle
->class))
96 if (add_uevent_var(env
, "GBPHY=%u", gbphy_dev
->id
))
98 if (add_uevent_var(env
, "PROTOCOL_ID=%02x", cport_desc
->protocol_id
))
104 static const struct gbphy_device_id
*
105 gbphy_dev_match_id(struct gbphy_device
*gbphy_dev
,
106 struct gbphy_driver
*gbphy_drv
)
108 const struct gbphy_device_id
*id
= gbphy_drv
->id_table
;
113 for (; id
->protocol_id
; id
++)
114 if (id
->protocol_id
== gbphy_dev
->cport_desc
->protocol_id
)
120 static int gbphy_dev_match(struct device
*dev
, struct device_driver
*drv
)
122 struct gbphy_driver
*gbphy_drv
= to_gbphy_driver(drv
);
123 struct gbphy_device
*gbphy_dev
= to_gbphy_dev(dev
);
124 const struct gbphy_device_id
*id
;
126 id
= gbphy_dev_match_id(gbphy_dev
, gbphy_drv
);
133 static int gbphy_dev_probe(struct device
*dev
)
135 struct gbphy_driver
*gbphy_drv
= to_gbphy_driver(dev
->driver
);
136 struct gbphy_device
*gbphy_dev
= to_gbphy_dev(dev
);
137 const struct gbphy_device_id
*id
;
140 id
= gbphy_dev_match_id(gbphy_dev
, gbphy_drv
);
144 /* for old kernels we need get_sync to resume parent devices */
145 ret
= gb_pm_runtime_get_sync(gbphy_dev
->bundle
);
149 pm_runtime_set_autosuspend_delay(dev
, GB_GBPHY_AUTOSUSPEND_MS
);
150 pm_runtime_use_autosuspend(dev
);
151 pm_runtime_get_noresume(dev
);
152 pm_runtime_set_active(dev
);
153 pm_runtime_enable(dev
);
156 * Drivers should call put on the gbphy dev before returning
157 * from probe if they support runtime pm.
159 ret
= gbphy_drv
->probe(gbphy_dev
, id
);
161 pm_runtime_disable(dev
);
162 pm_runtime_set_suspended(dev
);
163 pm_runtime_put_noidle(dev
);
164 pm_runtime_dont_use_autosuspend(dev
);
167 gb_pm_runtime_put_autosuspend(gbphy_dev
->bundle
);
172 static int gbphy_dev_remove(struct device
*dev
)
174 struct gbphy_driver
*gbphy_drv
= to_gbphy_driver(dev
->driver
);
175 struct gbphy_device
*gbphy_dev
= to_gbphy_dev(dev
);
177 gbphy_drv
->remove(gbphy_dev
);
179 pm_runtime_disable(dev
);
180 pm_runtime_set_suspended(dev
);
181 pm_runtime_put_noidle(dev
);
182 pm_runtime_dont_use_autosuspend(dev
);
187 static struct bus_type gbphy_bus_type
= {
189 .match
= gbphy_dev_match
,
190 .probe
= gbphy_dev_probe
,
191 .remove
= gbphy_dev_remove
,
192 .uevent
= gbphy_dev_uevent
,
195 int gb_gbphy_register_driver(struct gbphy_driver
*driver
,
196 struct module
*owner
, const char *mod_name
)
200 if (greybus_disabled())
203 driver
->driver
.bus
= &gbphy_bus_type
;
204 driver
->driver
.name
= driver
->name
;
205 driver
->driver
.owner
= owner
;
206 driver
->driver
.mod_name
= mod_name
;
208 retval
= driver_register(&driver
->driver
);
212 pr_info("registered new driver %s\n", driver
->name
);
215 EXPORT_SYMBOL_GPL(gb_gbphy_register_driver
);
217 void gb_gbphy_deregister_driver(struct gbphy_driver
*driver
)
219 driver_unregister(&driver
->driver
);
221 EXPORT_SYMBOL_GPL(gb_gbphy_deregister_driver
);
223 static struct gbphy_device
*gb_gbphy_create_dev(struct gb_bundle
*bundle
,
224 struct greybus_descriptor_cport
*cport_desc
)
226 struct gbphy_device
*gbphy_dev
;
230 id
= ida_simple_get(&gbphy_id
, 1, 0, GFP_KERNEL
);
234 gbphy_dev
= kzalloc(sizeof(*gbphy_dev
), GFP_KERNEL
);
236 ida_simple_remove(&gbphy_id
, id
);
237 return ERR_PTR(-ENOMEM
);
241 gbphy_dev
->bundle
= bundle
;
242 gbphy_dev
->cport_desc
= cport_desc
;
243 gbphy_dev
->dev
.parent
= &bundle
->dev
;
244 gbphy_dev
->dev
.bus
= &gbphy_bus_type
;
245 gbphy_dev
->dev
.type
= &greybus_gbphy_dev_type
;
246 gbphy_dev
->dev
.groups
= gbphy_dev_groups
;
247 gbphy_dev
->dev
.dma_mask
= bundle
->dev
.dma_mask
;
248 dev_set_name(&gbphy_dev
->dev
, "gbphy%d", id
);
250 retval
= device_register(&gbphy_dev
->dev
);
252 put_device(&gbphy_dev
->dev
);
253 return ERR_PTR(retval
);
259 static void gb_gbphy_disconnect(struct gb_bundle
*bundle
)
261 struct gbphy_host
*gbphy_host
= greybus_get_drvdata(bundle
);
262 struct gbphy_device
*gbphy_dev
, *temp
;
265 ret
= gb_pm_runtime_get_sync(bundle
);
267 gb_pm_runtime_get_noresume(bundle
);
269 list_for_each_entry_safe(gbphy_dev
, temp
, &gbphy_host
->devices
, list
) {
270 list_del(&gbphy_dev
->list
);
271 device_unregister(&gbphy_dev
->dev
);
277 static int gb_gbphy_probe(struct gb_bundle
*bundle
,
278 const struct greybus_bundle_id
*id
)
280 struct gbphy_host
*gbphy_host
;
281 struct gbphy_device
*gbphy_dev
;
284 if (bundle
->num_cports
== 0)
287 gbphy_host
= kzalloc(sizeof(*gbphy_host
), GFP_KERNEL
);
291 gbphy_host
->bundle
= bundle
;
292 INIT_LIST_HEAD(&gbphy_host
->devices
);
293 greybus_set_drvdata(bundle
, gbphy_host
);
296 * Create a bunch of children devices, one per cport, and bind the
297 * bridged phy drivers to them.
299 for (i
= 0; i
< bundle
->num_cports
; ++i
) {
300 gbphy_dev
= gb_gbphy_create_dev(bundle
, &bundle
->cport_desc
[i
]);
301 if (IS_ERR(gbphy_dev
)) {
302 gb_gbphy_disconnect(bundle
);
303 return PTR_ERR(gbphy_dev
);
305 list_add(&gbphy_dev
->list
, &gbphy_host
->devices
);
308 gb_pm_runtime_put_autosuspend(bundle
);
313 static const struct greybus_bundle_id gb_gbphy_id_table
[] = {
314 { GREYBUS_DEVICE_CLASS(GREYBUS_CLASS_BRIDGED_PHY
) },
317 MODULE_DEVICE_TABLE(greybus
, gb_gbphy_id_table
);
319 static struct greybus_driver gb_gbphy_driver
= {
321 .probe
= gb_gbphy_probe
,
322 .disconnect
= gb_gbphy_disconnect
,
323 .id_table
= gb_gbphy_id_table
,
326 static int __init
gbphy_init(void)
330 retval
= bus_register(&gbphy_bus_type
);
332 pr_err("gbphy bus register failed (%d)\n", retval
);
336 retval
= greybus_register(&gb_gbphy_driver
);
338 pr_err("error registering greybus driver\n");
345 bus_unregister(&gbphy_bus_type
);
346 ida_destroy(&gbphy_id
);
349 module_init(gbphy_init
);
351 static void __exit
gbphy_exit(void)
353 greybus_deregister(&gb_gbphy_driver
);
354 bus_unregister(&gbphy_bus_type
);
355 ida_destroy(&gbphy_id
);
357 module_exit(gbphy_exit
);
359 MODULE_LICENSE("GPL v2");