Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

rapidio: rework device hierarchy and introduce mport class of devices

This patch removes an artificial RapidIO bus root device and establishes
actual device hierarchy by providing reference to real parent devices.
It also introduces device class for RapidIO controller devices (on-chip
or an eternal bridge, known as "mport").

Existing implementation was sufficient for SoC-based platforms that have
a single RapidIO controller. With introduction of devices using
multiple RapidIO controllers and PCIe-to-RapidIO bridges the old scheme
is very limiting or does not work at all. The implemented changes allow
to properly reference platform's local RapidIO mport devices and provide
device details needed for upper layers.

This change to RapidIO device hierarchy does not break any known
existing kernel or user space interfaces.

Signed-off-by: Alexandre Bounine <alexandre.bounine@idt.com>
Cc: Matt Porter <mporter@kernel.crashing.org>
Cc: Li Yang <leoli@freescale.com>
Cc: Kumar Gala <galak@kernel.crashing.org>
Cc: Andre van Herk <andre.van.herk@prodrive-technologies.com>
Cc: Stef van Os <stef.van.os@prodrive-technologies.com>
Cc: Jerry Jacobs <jerry.jacobs@prodrive-technologies.com>
Cc: Arno Tiemersma <arno.tiemersma@prodrive-technologies.com>
Cc: Rob Landley <rob@landley.net>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>

authored by

Alexandre Bounine and committed by
Linus Torvalds
2aaf308b 40f847ba

+133 -16
+58 -8
Documentation/rapidio/sysfs.txt
··· 2 2 3 3 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 4 4 5 - 1. Device Subdirectories 6 - ------------------------ 5 + 1. RapidIO Device Subdirectories 6 + -------------------------------- 7 7 8 8 For each RapidIO device, the RapidIO subsystem creates files in an individual 9 9 subdirectory with the following name, /sys/bus/rapidio/devices/<device_name>. ··· 25 25 NOTE: An enumerating or discovering endpoint does not create a sysfs entry for 26 26 itself, this is why an endpoint with destID=1 is not shown in the list. 27 27 28 - 2. Attributes Common for All Devices 29 - ------------------------------------ 28 + 2. Attributes Common for All RapidIO Devices 29 + -------------------------------------------- 30 30 31 31 Each device subdirectory contains the following informational read-only files: 32 32 ··· 52 52 and provides an access to the RapidIO device registers using standard file read 53 53 and write operations. 54 54 55 - 3. Endpoint Device Attributes 56 - ----------------------------- 55 + 3. RapidIO Endpoint Device Attributes 56 + ------------------------------------- 57 57 58 58 Currently Linux RapidIO subsystem does not create any endpoint specific sysfs 59 59 attributes. It is possible that RapidIO master port drivers and endpoint device 60 60 drivers will add their device-specific sysfs attributes but such attributes are 61 61 outside the scope of this document. 62 62 63 - 4. Switch Device Attributes 64 - --------------------------- 63 + 4. RapidIO Switch Device Attributes 64 + ----------------------------------- 65 65 66 66 RapidIO switches have additional attributes in sysfs. RapidIO subsystem supports 67 67 common and device-specific sysfs attributes for switches. Because switches are ··· 106 106 for that controller always will be 0. 107 107 To initiate RapidIO enumeration/discovery on all available mports 108 108 a user must write '-1' (or RIO_MPORT_ANY) into this attribute file. 109 + 110 + 111 + 6. RapidIO Bus Controllers/Ports 112 + -------------------------------- 113 + 114 + On-chip RapidIO controllers and PCIe-to-RapidIO bridges (referenced as 115 + "Master Port" or "mport") are presented in sysfs as the special class of 116 + devices: "rapidio_port". 117 + 118 + The /sys/class/rapidio_port subdirectory contains individual subdirectories 119 + named as "rapidioN" where N = mport ID registered with RapidIO subsystem. 120 + 121 + NOTE: An mport ID is not a RapidIO destination ID assigned to a given local 122 + mport device. 123 + 124 + Each mport device subdirectory in addition to standard entries contains the 125 + following device-specific attributes: 126 + 127 + port_destid - reports RapidIO destination ID assigned to the given RapidIO 128 + mport device. If value 0xFFFFFFFF is returned this means that 129 + no valid destination ID have been assigned to the mport (yet). 130 + Normally, before enumeration/discovery have been executed only 131 + fabric enumerating mports have a valid destination ID assigned 132 + to them using "hdid=..." rapidio module parameter. 133 + sys_size - reports RapidIO common transport system size: 134 + 0 = small (8-bit destination ID, max. 256 devices), 135 + 1 = large (16-bit destination ID, max. 65536 devices). 136 + 137 + After enumeration or discovery was performed for a given mport device, 138 + the corresponding subdirectory will also contain subdirectories for each 139 + child RapidIO device connected to the mport. Naming conventions for RapidIO 140 + devices are described in Section 1 above. 141 + 142 + The example below shows mport device subdirectory with several child RapidIO 143 + devices attached to it. 144 + 145 + [rio@rapidio ~]$ ls /sys/class/rapidio_port/rapidio0/ -l 146 + total 0 147 + drwxr-xr-x 3 root root 0 Feb 11 15:10 00:e:0001 148 + drwxr-xr-x 3 root root 0 Feb 11 15:10 00:e:0004 149 + drwxr-xr-x 3 root root 0 Feb 11 15:10 00:e:0007 150 + drwxr-xr-x 3 root root 0 Feb 11 15:10 00:s:0002 151 + drwxr-xr-x 3 root root 0 Feb 11 15:10 00:s:0003 152 + drwxr-xr-x 3 root root 0 Feb 11 15:10 00:s:0005 153 + lrwxrwxrwx 1 root root 0 Feb 11 15:11 device -> ../../../0000:01:00.0 154 + -r--r--r-- 1 root root 4096 Feb 11 15:11 port_destid 155 + drwxr-xr-x 2 root root 0 Feb 11 15:11 power 156 + lrwxrwxrwx 1 root root 0 Feb 11 15:04 subsystem -> ../../../../../../class/rapidio_port 157 + -r--r--r-- 1 root root 4096 Feb 11 15:11 sys_size 158 + -rw-r--r-- 1 root root 4096 Feb 11 15:04 uevent
+1
arch/powerpc/sysdev/fsl_rio.c
··· 531 531 sprintf(port->name, "RIO mport %d", i); 532 532 533 533 priv->dev = &dev->dev; 534 + port->dev.parent = &dev->dev; 534 535 port->ops = ops; 535 536 port->priv = priv; 536 537 port->phys_efptr = 0x100;
+1
drivers/net/rionet.c
··· 493 493 ndev->netdev_ops = &rionet_netdev_ops; 494 494 ndev->mtu = RIO_MAX_MSG_SIZE - 14; 495 495 ndev->features = NETIF_F_LLTX; 496 + SET_NETDEV_DEV(ndev, &mport->dev); 496 497 SET_ETHTOOL_OPS(ndev, &rionet_ethtool_ops); 497 498 498 499 spin_lock_init(&rnet->lock);
+1
drivers/rapidio/devices/tsi721.c
··· 2256 2256 mport->phy_type = RIO_PHY_SERIAL; 2257 2257 mport->priv = (void *)priv; 2258 2258 mport->phys_efptr = 0x100; 2259 + mport->dev.parent = &pdev->dev; 2259 2260 priv->mport = mport; 2260 2261 2261 2262 INIT_LIST_HEAD(&mport->dbells);
+15 -7
drivers/rapidio/rio-driver.c
··· 167 167 void rio_attach_device(struct rio_dev *rdev) 168 168 { 169 169 rdev->dev.bus = &rio_bus_type; 170 - rdev->dev.parent = &rio_bus; 171 170 } 172 171 EXPORT_SYMBOL_GPL(rio_attach_device); 173 172 ··· 215 216 return 0; 216 217 } 217 218 218 - struct device rio_bus = { 219 - .init_name = "rapidio", 219 + struct class rio_mport_class = { 220 + .name = "rapidio_port", 221 + .owner = THIS_MODULE, 222 + .dev_groups = rio_mport_groups, 220 223 }; 224 + EXPORT_SYMBOL_GPL(rio_mport_class); 221 225 222 226 struct bus_type rio_bus_type = { 223 227 .name = "rapidio", ··· 235 233 /** 236 234 * rio_bus_init - Register the RapidIO bus with the device model 237 235 * 238 - * Registers the RIO bus device and RIO bus type with the Linux 236 + * Registers the RIO mport device class and RIO bus type with the Linux 239 237 * device model. 240 238 */ 241 239 static int __init rio_bus_init(void) 242 240 { 243 - if (device_register(&rio_bus) < 0) 244 - printk("RIO: failed to register RIO bus device\n"); 245 - return bus_register(&rio_bus_type); 241 + int ret; 242 + 243 + ret = class_register(&rio_mport_class); 244 + if (!ret) { 245 + ret = bus_register(&rio_bus_type); 246 + if (ret) 247 + class_unregister(&rio_mport_class); 248 + } 249 + return ret; 246 250 } 247 251 248 252 postcore_initcall(rio_bus_init);
+1
drivers/rapidio/rio-scan.c
··· 461 461 rdev->comp_tag & RIO_CTAG_UDEVID); 462 462 } 463 463 464 + rdev->dev.parent = &port->dev; 464 465 rio_attach_device(rdev); 465 466 466 467 device_initialize(&rdev->dev);
+40
drivers/rapidio/rio-sysfs.c
··· 341 341 &rio_bus_group, 342 342 NULL, 343 343 }; 344 + 345 + static ssize_t 346 + port_destid_show(struct device *dev, struct device_attribute *attr, 347 + char *buf) 348 + { 349 + struct rio_mport *mport = to_rio_mport(dev); 350 + 351 + if (mport) 352 + return sprintf(buf, "0x%04x\n", mport->host_deviceid); 353 + else 354 + return -ENODEV; 355 + } 356 + static DEVICE_ATTR_RO(port_destid); 357 + 358 + static ssize_t sys_size_show(struct device *dev, struct device_attribute *attr, 359 + char *buf) 360 + { 361 + struct rio_mport *mport = to_rio_mport(dev); 362 + 363 + if (mport) 364 + return sprintf(buf, "%u\n", mport->sys_size); 365 + else 366 + return -ENODEV; 367 + } 368 + static DEVICE_ATTR_RO(sys_size); 369 + 370 + static struct attribute *rio_mport_attrs[] = { 371 + &dev_attr_port_destid.attr, 372 + &dev_attr_sys_size.attr, 373 + NULL, 374 + }; 375 + 376 + static const struct attribute_group rio_mport_group = { 377 + .attrs = rio_mport_attrs, 378 + }; 379 + 380 + const struct attribute_group *rio_mport_groups[] = { 381 + &rio_mport_group, 382 + NULL, 383 + };
+11
drivers/rapidio/rio.c
··· 1884 1884 int rio_register_mport(struct rio_mport *port) 1885 1885 { 1886 1886 struct rio_scan_node *scan = NULL; 1887 + int res = 0; 1887 1888 1888 1889 if (next_portid >= RIO_MAX_MPORTS) { 1889 1890 pr_err("RIO: reached specified max number of mports\n"); ··· 1894 1893 port->id = next_portid++; 1895 1894 port->host_deviceid = rio_get_hdid(port->id); 1896 1895 port->nscan = NULL; 1896 + 1897 + dev_set_name(&port->dev, "rapidio%d", port->id); 1898 + port->dev.class = &rio_mport_class; 1899 + 1900 + res = device_register(&port->dev); 1901 + if (res) 1902 + dev_err(&port->dev, "RIO: mport%d registration failed ERR=%d\n", 1903 + port->id, res); 1904 + else 1905 + dev_dbg(&port->dev, "RIO: mport%d registered\n", port->id); 1897 1906 1898 1907 mutex_lock(&rio_mport_list_lock); 1899 1908 list_add_tail(&port->node, &rio_mports);
+1
drivers/rapidio/rio.h
··· 50 50 /* Structures internal to the RIO core code */ 51 51 extern const struct attribute_group *rio_dev_groups[]; 52 52 extern const struct attribute_group *rio_bus_groups[]; 53 + extern const struct attribute_group *rio_mport_groups[]; 53 54 54 55 #define RIO_GET_DID(size, x) (size ? (x & 0xffff) : ((x & 0x00ff0000) >> 16)) 55 56 #define RIO_SET_DID(size, x) (size ? (x & 0xffff) : ((x & 0x000000ff) << 16))
+4 -1
include/linux/rio.h
··· 83 83 #define RIO_CTAG_UDEVID 0x0001ffff /* Unique device identifier */ 84 84 85 85 extern struct bus_type rio_bus_type; 86 - extern struct device rio_bus; 86 + extern struct class rio_mport_class; 87 87 88 88 struct rio_mport; 89 89 struct rio_dev; ··· 201 201 #define rio_dev_f(n) list_entry(n, struct rio_dev, net_list) 202 202 #define to_rio_dev(n) container_of(n, struct rio_dev, dev) 203 203 #define sw_to_rio_dev(n) container_of(n, struct rio_dev, rswitch[0]) 204 + #define to_rio_mport(n) container_of(n, struct rio_mport, dev) 204 205 205 206 /** 206 207 * struct rio_msg - RIO message event ··· 249 248 * @phy_type: RapidIO phy type 250 249 * @phys_efptr: RIO port extended features pointer 251 250 * @name: Port name string 251 + * @dev: device structure associated with an mport 252 252 * @priv: Master port private data 253 253 * @dma: DMA device associated with mport 254 254 * @nscan: RapidIO network enumeration/discovery operations ··· 274 272 enum rio_phy_type phy_type; /* RapidIO phy type */ 275 273 u32 phys_efptr; 276 274 unsigned char name[RIO_MAX_MPORT_NAME]; 275 + struct device dev; 277 276 void *priv; /* Master port private data */ 278 277 #ifdef CONFIG_RAPIDIO_DMA_ENGINE 279 278 struct dma_device dma;