1 /* 2 * Copyright (C) 2012 Avionic Design GmbH 3 * Copyright (C) 2012-2013, NVIDIA Corporation 4 * 5 * This program is free software; you can redistribute it and/or modify it 6 * under the terms and conditions of the GNU General Public License, 7 * version 2, as published by the Free Software Foundation. 8 * 9 * This program is distributed in the hope it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 12 * more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program. If not, see <http://www.gnu.org/licenses/>. 16 */ 17 18 #include <linux/host1x.h> 19 #include <linux/of.h> 20 #include <linux/slab.h> 21 22 #include "dev.h" 23 24 static DEFINE_MUTEX(clients_lock); 25 static LIST_HEAD(clients); 26 27 static DEFINE_MUTEX(drivers_lock); 28 static LIST_HEAD(drivers); 29 30 static DEFINE_MUTEX(devices_lock); 31 static LIST_HEAD(devices); 32 33 struct host1x_subdev { 34 struct host1x_client *client; 35 struct device_node *np; 36 struct list_head list; 37 }; 38 39 /** 40 * host1x_subdev_add() - add a new subdevice with an associated device node 41 */ 42 static int host1x_subdev_add(struct host1x_device *device, 43 struct device_node *np) 44 { 45 struct host1x_subdev *subdev; 46 47 subdev = kzalloc(sizeof(*subdev), GFP_KERNEL); 48 if (!subdev) 49 return -ENOMEM; 50 51 INIT_LIST_HEAD(&subdev->list); 52 subdev->np = of_node_get(np); 53 54 mutex_lock(&device->subdevs_lock); 55 list_add_tail(&subdev->list, &device->subdevs); 56 mutex_unlock(&device->subdevs_lock); 57 58 return 0; 59 } 60 61 /** 62 * host1x_subdev_del() - remove subdevice 63 */ 64 static void host1x_subdev_del(struct host1x_subdev *subdev) 65 { 66 list_del(&subdev->list); 67 of_node_put(subdev->np); 68 kfree(subdev); 69 } 70 71 /** 72 * host1x_device_parse_dt() - scan device tree and add matching subdevices 73 */ 74 static int host1x_device_parse_dt(struct host1x_device *device) 75 { 76 struct device_node *np; 77 int err; 78 79 for_each_child_of_node(device->dev.parent->of_node, np) { 80 if (of_match_node(device->driver->subdevs, np) && 81 of_device_is_available(np)) { 82 err = host1x_subdev_add(device, np); 83 if (err < 0) 84 return err; 85 } 86 } 87 88 return 0; 89 } 90 91 static void host1x_subdev_register(struct host1x_device *device, 92 struct host1x_subdev *subdev, 93 struct host1x_client *client) 94 { 95 int err; 96 97 /* 98 * Move the subdevice to the list of active (registered) subdevices 99 * and associate it with a client. At the same time, associate the 100 * client with its parent device. 101 */ 102 mutex_lock(&device->subdevs_lock); 103 mutex_lock(&device->clients_lock); 104 list_move_tail(&client->list, &device->clients); 105 list_move_tail(&subdev->list, &device->active); 106 client->parent = &device->dev; 107 subdev->client = client; 108 mutex_unlock(&device->clients_lock); 109 mutex_unlock(&device->subdevs_lock); 110 111 /* 112 * When all subdevices have been registered, the composite device is 113 * ready to be probed. 114 */ 115 if (list_empty(&device->subdevs)) { 116 err = device->driver->probe(device); 117 if (err < 0) 118 dev_err(&device->dev, "probe failed: %d\n", err); 119 } 120 } 121 122 static void __host1x_subdev_unregister(struct host1x_device *device, 123 struct host1x_subdev *subdev) 124 { 125 struct host1x_client *client = subdev->client; 126 int err; 127 128 /* 129 * If all subdevices have been activated, we're about to remove the 130 * first active subdevice, so unload the driver first. 131 */ 132 if (list_empty(&device->subdevs)) { 133 err = device->driver->remove(device); 134 if (err < 0) 135 dev_err(&device->dev, "remove failed: %d\n", err); 136 } 137 138 /* 139 * Move the subdevice back to the list of idle subdevices and remove 140 * it from list of clients. 141 */ 142 mutex_lock(&device->clients_lock); 143 subdev->client = NULL; 144 client->parent = NULL; 145 list_move_tail(&subdev->list, &device->subdevs); 146 /* 147 * XXX: Perhaps don't do this here, but rather explicitly remove it 148 * when the device is about to be deleted. 149 * 150 * This is somewhat complicated by the fact that this function is 151 * used to remove the subdevice when a client is unregistered but 152 * also when the composite device is about to be removed. 153 */ 154 list_del_init(&client->list); 155 mutex_unlock(&device->clients_lock); 156 } 157 158 static void host1x_subdev_unregister(struct host1x_device *device, 159 struct host1x_subdev *subdev) 160 { 161 mutex_lock(&device->subdevs_lock); 162 __host1x_subdev_unregister(device, subdev); 163 mutex_unlock(&device->subdevs_lock); 164 } 165 166 int host1x_device_init(struct host1x_device *device) 167 { 168 struct host1x_client *client; 169 int err; 170 171 mutex_lock(&device->clients_lock); 172 173 list_for_each_entry(client, &device->clients, list) { 174 if (client->ops && client->ops->init) { 175 err = client->ops->init(client); 176 if (err < 0) { 177 dev_err(&device->dev, 178 "failed to initialize %s: %d\n", 179 dev_name(client->dev), err); 180 mutex_unlock(&device->clients_lock); 181 return err; 182 } 183 } 184 } 185 186 mutex_unlock(&device->clients_lock); 187 188 return 0; 189 } 190 191 int host1x_device_exit(struct host1x_device *device) 192 { 193 struct host1x_client *client; 194 int err; 195 196 mutex_lock(&device->clients_lock); 197 198 list_for_each_entry_reverse(client, &device->clients, list) { 199 if (client->ops && client->ops->exit) { 200 err = client->ops->exit(client); 201 if (err < 0) { 202 dev_err(&device->dev, 203 "failed to cleanup %s: %d\n", 204 dev_name(client->dev), err); 205 mutex_unlock(&device->clients_lock); 206 return err; 207 } 208 } 209 } 210 211 mutex_unlock(&device->clients_lock); 212 213 return 0; 214 } 215 216 static int host1x_register_client(struct host1x *host1x, 217 struct host1x_client *client) 218 { 219 struct host1x_device *device; 220 struct host1x_subdev *subdev; 221 222 mutex_lock(&host1x->devices_lock); 223 224 list_for_each_entry(device, &host1x->devices, list) { 225 list_for_each_entry(subdev, &device->subdevs, list) { 226 if (subdev->np == client->dev->of_node) { 227 host1x_subdev_register(device, subdev, client); 228 mutex_unlock(&host1x->devices_lock); 229 return 0; 230 } 231 } 232 } 233 234 mutex_unlock(&host1x->devices_lock); 235 return -ENODEV; 236 } 237 238 static int host1x_unregister_client(struct host1x *host1x, 239 struct host1x_client *client) 240 { 241 struct host1x_device *device, *dt; 242 struct host1x_subdev *subdev; 243 244 mutex_lock(&host1x->devices_lock); 245 246 list_for_each_entry_safe(device, dt, &host1x->devices, list) { 247 list_for_each_entry(subdev, &device->active, list) { 248 if (subdev->client == client) { 249 host1x_subdev_unregister(device, subdev); 250 mutex_unlock(&host1x->devices_lock); 251 return 0; 252 } 253 } 254 } 255 256 mutex_unlock(&host1x->devices_lock); 257 return -ENODEV; 258 } 259 260 struct bus_type host1x_bus_type = { 261 .name = "host1x", 262 }; 263 264 int host1x_bus_init(void) 265 { 266 return bus_register(&host1x_bus_type); 267 } 268 269 void host1x_bus_exit(void) 270 { 271 bus_unregister(&host1x_bus_type); 272 } 273 274 static void host1x_device_release(struct device *dev) 275 { 276 struct host1x_device *device = to_host1x_device(dev); 277 278 kfree(device); 279 } 280 281 static int host1x_device_add(struct host1x *host1x, 282 struct host1x_driver *driver) 283 { 284 struct host1x_client *client, *tmp; 285 struct host1x_subdev *subdev; 286 struct host1x_device *device; 287 int err; 288 289 device = kzalloc(sizeof(*device), GFP_KERNEL); 290 if (!device) 291 return -ENOMEM; 292 293 mutex_init(&device->subdevs_lock); 294 INIT_LIST_HEAD(&device->subdevs); 295 INIT_LIST_HEAD(&device->active); 296 mutex_init(&device->clients_lock); 297 INIT_LIST_HEAD(&device->clients); 298 INIT_LIST_HEAD(&device->list); 299 device->driver = driver; 300 301 device->dev.coherent_dma_mask = host1x->dev->coherent_dma_mask; 302 device->dev.dma_mask = &device->dev.coherent_dma_mask; 303 device->dev.release = host1x_device_release; 304 dev_set_name(&device->dev, driver->name); 305 device->dev.bus = &host1x_bus_type; 306 device->dev.parent = host1x->dev; 307 308 err = device_register(&device->dev); 309 if (err < 0) 310 return err; 311 312 err = host1x_device_parse_dt(device); 313 if (err < 0) { 314 device_unregister(&device->dev); 315 return err; 316 } 317 318 mutex_lock(&host1x->devices_lock); 319 list_add_tail(&device->list, &host1x->devices); 320 mutex_unlock(&host1x->devices_lock); 321 322 mutex_lock(&clients_lock); 323 324 list_for_each_entry_safe(client, tmp, &clients, list) { 325 list_for_each_entry(subdev, &device->subdevs, list) { 326 if (subdev->np == client->dev->of_node) { 327 host1x_subdev_register(device, subdev, client); 328 break; 329 } 330 } 331 } 332 333 mutex_unlock(&clients_lock); 334 335 return 0; 336 } 337 338 /* 339 * Removes a device by first unregistering any subdevices and then removing 340 * itself from the list of devices. 341 * 342 * This function must be called with the host1x->devices_lock held. 343 */ 344 static void host1x_device_del(struct host1x *host1x, 345 struct host1x_device *device) 346 { 347 struct host1x_subdev *subdev, *sd; 348 struct host1x_client *client, *cl; 349 350 mutex_lock(&device->subdevs_lock); 351 352 /* unregister subdevices */ 353 list_for_each_entry_safe(subdev, sd, &device->active, list) { 354 /* 355 * host1x_subdev_unregister() will remove the client from 356 * any lists, so we'll need to manually add it back to the 357 * list of idle clients. 358 * 359 * XXX: Alternatively, perhaps don't remove the client from 360 * any lists in host1x_subdev_unregister() and instead do 361 * that explicitly from host1x_unregister_client()? 362 */ 363 client = subdev->client; 364 365 __host1x_subdev_unregister(device, subdev); 366 367 /* add the client to the list of idle clients */ 368 mutex_lock(&clients_lock); 369 list_add_tail(&client->list, &clients); 370 mutex_unlock(&clients_lock); 371 } 372 373 /* remove subdevices */ 374 list_for_each_entry_safe(subdev, sd, &device->subdevs, list) 375 host1x_subdev_del(subdev); 376 377 mutex_unlock(&device->subdevs_lock); 378 379 /* move clients to idle list */ 380 mutex_lock(&clients_lock); 381 mutex_lock(&device->clients_lock); 382 383 list_for_each_entry_safe(client, cl, &device->clients, list) 384 list_move_tail(&client->list, &clients); 385 386 mutex_unlock(&device->clients_lock); 387 mutex_unlock(&clients_lock); 388 389 /* finally remove the device */ 390 list_del_init(&device->list); 391 device_unregister(&device->dev); 392 } 393 394 static void host1x_attach_driver(struct host1x *host1x, 395 struct host1x_driver *driver) 396 { 397 struct host1x_device *device; 398 int err; 399 400 mutex_lock(&host1x->devices_lock); 401 402 list_for_each_entry(device, &host1x->devices, list) { 403 if (device->driver == driver) { 404 mutex_unlock(&host1x->devices_lock); 405 return; 406 } 407 } 408 409 mutex_unlock(&host1x->devices_lock); 410 411 err = host1x_device_add(host1x, driver); 412 if (err < 0) 413 dev_err(host1x->dev, "failed to allocate device: %d\n", err); 414 } 415 416 static void host1x_detach_driver(struct host1x *host1x, 417 struct host1x_driver *driver) 418 { 419 struct host1x_device *device, *tmp; 420 421 mutex_lock(&host1x->devices_lock); 422 423 list_for_each_entry_safe(device, tmp, &host1x->devices, list) 424 if (device->driver == driver) 425 host1x_device_del(host1x, device); 426 427 mutex_unlock(&host1x->devices_lock); 428 } 429 430 int host1x_register(struct host1x *host1x) 431 { 432 struct host1x_driver *driver; 433 434 mutex_lock(&devices_lock); 435 list_add_tail(&host1x->list, &devices); 436 mutex_unlock(&devices_lock); 437 438 mutex_lock(&drivers_lock); 439 440 list_for_each_entry(driver, &drivers, list) 441 host1x_attach_driver(host1x, driver); 442 443 mutex_unlock(&drivers_lock); 444 445 return 0; 446 } 447 448 int host1x_unregister(struct host1x *host1x) 449 { 450 struct host1x_driver *driver; 451 452 mutex_lock(&drivers_lock); 453 454 list_for_each_entry(driver, &drivers, list) 455 host1x_detach_driver(host1x, driver); 456 457 mutex_unlock(&drivers_lock); 458 459 mutex_lock(&devices_lock); 460 list_del_init(&host1x->list); 461 mutex_unlock(&devices_lock); 462 463 return 0; 464 } 465 466 int host1x_driver_register(struct host1x_driver *driver) 467 { 468 struct host1x *host1x; 469 470 INIT_LIST_HEAD(&driver->list); 471 472 mutex_lock(&drivers_lock); 473 list_add_tail(&driver->list, &drivers); 474 mutex_unlock(&drivers_lock); 475 476 mutex_lock(&devices_lock); 477 478 list_for_each_entry(host1x, &devices, list) 479 host1x_attach_driver(host1x, driver); 480 481 mutex_unlock(&devices_lock); 482 483 return 0; 484 } 485 EXPORT_SYMBOL(host1x_driver_register); 486 487 void host1x_driver_unregister(struct host1x_driver *driver) 488 { 489 mutex_lock(&drivers_lock); 490 list_del_init(&driver->list); 491 mutex_unlock(&drivers_lock); 492 } 493 EXPORT_SYMBOL(host1x_driver_unregister); 494 495 int host1x_client_register(struct host1x_client *client) 496 { 497 struct host1x *host1x; 498 int err; 499 500 mutex_lock(&devices_lock); 501 502 list_for_each_entry(host1x, &devices, list) { 503 err = host1x_register_client(host1x, client); 504 if (!err) { 505 mutex_unlock(&devices_lock); 506 return 0; 507 } 508 } 509 510 mutex_unlock(&devices_lock); 511 512 mutex_lock(&clients_lock); 513 list_add_tail(&client->list, &clients); 514 mutex_unlock(&clients_lock); 515 516 return 0; 517 } 518 EXPORT_SYMBOL(host1x_client_register); 519 520 int host1x_client_unregister(struct host1x_client *client) 521 { 522 struct host1x_client *c; 523 struct host1x *host1x; 524 int err; 525 526 mutex_lock(&devices_lock); 527 528 list_for_each_entry(host1x, &devices, list) { 529 err = host1x_unregister_client(host1x, client); 530 if (!err) { 531 mutex_unlock(&devices_lock); 532 return 0; 533 } 534 } 535 536 mutex_unlock(&devices_lock); 537 mutex_lock(&clients_lock); 538 539 list_for_each_entry(c, &clients, list) { 540 if (c == client) { 541 list_del_init(&c->list); 542 break; 543 } 544 } 545 546 mutex_unlock(&clients_lock); 547 548 return 0; 549 } 550 EXPORT_SYMBOL(host1x_client_unregister); 551