Changeset 59dc181 in mainline
- Timestamp:
- 2013-09-10T19:10:09Z (11 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- a60e90b
- Parents:
- 38e52c92
- Location:
- uspace/srv/devman
- Files:
-
- 2 added
- 7 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/srv/devman/Makefile
r38e52c92 r59dc181 34 34 SOURCES = \ 35 35 dev.c \ 36 devtree.c \ 36 37 devman.c \ 37 38 driver.c \ -
uspace/srv/devman/dev.c
r38e52c92 r59dc181 32 32 33 33 #include <errno.h> 34 #include <fcntl.h>35 #include <sys/stat.h>36 #include <io/log.h>37 #include <ipc/driver.h>38 #include <ipc/devman.h>39 #include <loc.h>40 #include <str_error.h>41 #include <stdio.h>42 34 43 35 #include "dev.h" -
uspace/srv/devman/devman.c
r38e52c92 r59dc181 65 65 #include "fun.h" 66 66 67 /* hash table operations */68 69 static inline size_t handle_key_hash(void *key)70 {71 devman_handle_t handle = *(devman_handle_t*)key;72 return handle;73 }74 75 static size_t devman_devices_hash(const ht_link_t *item)76 {77 dev_node_t *dev = hash_table_get_inst(item, dev_node_t, devman_dev);78 return handle_key_hash(&dev->handle);79 }80 81 static size_t devman_functions_hash(const ht_link_t *item)82 {83 fun_node_t *fun = hash_table_get_inst(item, fun_node_t, devman_fun);84 return handle_key_hash(&fun->handle);85 }86 87 static bool devman_devices_key_equal(void *key, const ht_link_t *item)88 {89 devman_handle_t handle = *(devman_handle_t*)key;90 dev_node_t *dev = hash_table_get_inst(item, dev_node_t, devman_dev);91 return dev->handle == handle;92 }93 94 static bool devman_functions_key_equal(void *key, const ht_link_t *item)95 {96 devman_handle_t handle = *(devman_handle_t*)key;97 fun_node_t *fun = hash_table_get_inst(item, fun_node_t, devman_fun);98 return fun->handle == handle;99 }100 101 static inline size_t service_id_key_hash(void *key)102 {103 service_id_t service_id = *(service_id_t*)key;104 return service_id;105 }106 107 static size_t loc_functions_hash(const ht_link_t *item)108 {109 fun_node_t *fun = hash_table_get_inst(item, fun_node_t, loc_fun);110 return service_id_key_hash(&fun->service_id);111 }112 113 static bool loc_functions_key_equal(void *key, const ht_link_t *item)114 {115 service_id_t service_id = *(service_id_t*)key;116 fun_node_t *fun = hash_table_get_inst(item, fun_node_t, loc_fun);117 return fun->service_id == service_id;118 }119 120 121 static hash_table_ops_t devman_devices_ops = {122 .hash = devman_devices_hash,123 .key_hash = handle_key_hash,124 .key_equal = devman_devices_key_equal,125 .equal = NULL,126 .remove_callback = NULL127 };128 129 static hash_table_ops_t devman_functions_ops = {130 .hash = devman_functions_hash,131 .key_hash = handle_key_hash,132 .key_equal = devman_functions_key_equal,133 .equal = NULL,134 .remove_callback = NULL135 };136 137 static hash_table_ops_t loc_devices_ops = {138 .hash = loc_functions_hash,139 .key_hash = service_id_key_hash,140 .key_equal = loc_functions_key_equal,141 .equal = NULL,142 .remove_callback = NULL143 };144 145 67 /** Read match id at the specified position of a string and set the position in 146 68 * the string to the first character following the id. … … 278 200 279 201 return suc; 280 }281 282 /** Create root device and function node in the device tree.283 *284 * @param tree The device tree.285 * @return True on success, false otherwise.286 */287 bool create_root_nodes(dev_tree_t *tree)288 {289 fun_node_t *fun;290 dev_node_t *dev;291 292 log_msg(LOG_DEFAULT, LVL_DEBUG, "create_root_nodes()");293 294 fibril_rwlock_write_lock(&tree->rwlock);295 296 /*297 * Create root function. This is a pseudo function to which298 * the root device node is attached. It allows us to match299 * the root device driver in a standard manner, i.e. against300 * the parent function.301 */302 303 fun = create_fun_node();304 if (fun == NULL) {305 fibril_rwlock_write_unlock(&tree->rwlock);306 return false;307 }308 309 fun_add_ref(fun);310 insert_fun_node(tree, fun, str_dup(""), NULL);311 312 match_id_t *id = create_match_id();313 id->id = str_dup("root");314 id->score = 100;315 add_match_id(&fun->match_ids, id);316 tree->root_node = fun;317 318 /*319 * Create root device node.320 */321 dev = create_dev_node();322 if (dev == NULL) {323 fibril_rwlock_write_unlock(&tree->rwlock);324 return false;325 }326 327 dev_add_ref(dev);328 insert_dev_node(tree, dev, fun);329 330 fibril_rwlock_write_unlock(&tree->rwlock);331 332 return dev != NULL;333 202 } 334 203 … … 421 290 } 422 291 423 /** Initialize the device tree.424 *425 * Create root device node of the tree and assign driver to it.426 *427 * @param tree The device tree.428 * @param drivers_list the list of available drivers.429 * @return True on success, false otherwise.430 */431 bool init_device_tree(dev_tree_t *tree, driver_list_t *drivers_list)432 {433 log_msg(LOG_DEFAULT, LVL_DEBUG, "init_device_tree()");434 435 tree->current_handle = 0;436 437 hash_table_create(&tree->devman_devices, 0, 0, &devman_devices_ops);438 hash_table_create(&tree->devman_functions, 0, 0, &devman_functions_ops);439 hash_table_create(&tree->loc_functions, 0, 0, &loc_devices_ops);440 441 fibril_rwlock_initialize(&tree->rwlock);442 443 /* Create root function and root device and add them to the device tree. */444 if (!create_root_nodes(tree))445 return false;446 447 /* Find suitable driver and start it. */448 dev_node_t *rdev = tree->root_node->child;449 dev_add_ref(rdev);450 int rc = assign_driver(rdev, drivers_list, tree);451 dev_del_ref(rdev);452 453 return rc;454 }455 456 /** Insert new device into device tree.457 *458 * @param tree The device tree.459 * @param dev The newly added device node.460 * @param pfun The parent function node.461 *462 * @return True on success, false otherwise (insufficient resources463 * etc.).464 */465 bool insert_dev_node(dev_tree_t *tree, dev_node_t *dev, fun_node_t *pfun)466 {467 assert(fibril_rwlock_is_write_locked(&tree->rwlock));468 469 log_msg(LOG_DEFAULT, LVL_DEBUG, "insert_dev_node(dev=%p, pfun=%p [\"%s\"])",470 dev, pfun, pfun->pathname);471 472 /* Add the node to the handle-to-node map. */473 dev->handle = ++tree->current_handle;474 hash_table_insert(&tree->devman_devices, &dev->devman_dev);475 476 /* Add the node to the list of its parent's children. */477 dev->pfun = pfun;478 pfun->child = dev;479 480 return true;481 }482 483 /** Remove device from device tree.484 *485 * @param tree Device tree486 * @param dev Device node487 */488 void remove_dev_node(dev_tree_t *tree, dev_node_t *dev)489 {490 assert(fibril_rwlock_is_write_locked(&tree->rwlock));491 492 log_msg(LOG_DEFAULT, LVL_DEBUG, "remove_dev_node(dev=%p)", dev);493 494 /* Remove node from the handle-to-node map. */495 hash_table_remove(&tree->devman_devices, &dev->handle);496 497 /* Unlink from parent function. */498 dev->pfun->child = NULL;499 dev->pfun = NULL;500 501 dev->state = DEVICE_REMOVED;502 }503 504 505 /** Insert new function into device tree.506 *507 * @param tree The device tree.508 * @param fun The newly added function node.509 * @param fun_name The name of the newly added function.510 * @param dev Owning device node.511 *512 * @return True on success, false otherwise (insufficient resources513 * etc.).514 */515 bool insert_fun_node(dev_tree_t *tree, fun_node_t *fun, char *fun_name,516 dev_node_t *dev)517 {518 fun_node_t *pfun;519 520 assert(fun_name != NULL);521 assert(fibril_rwlock_is_write_locked(&tree->rwlock));522 523 /*524 * The root function is a special case, it does not belong to any525 * device so for the root function dev == NULL.526 */527 pfun = (dev != NULL) ? dev->pfun : NULL;528 529 fun->name = fun_name;530 if (!set_fun_path(tree, fun, pfun)) {531 return false;532 }533 534 /* Add the node to the handle-to-node map. */535 fun->handle = ++tree->current_handle;536 hash_table_insert(&tree->devman_functions, &fun->devman_fun);537 538 /* Add the node to the list of its parent's children. */539 fun->dev = dev;540 if (dev != NULL)541 list_append(&fun->dev_functions, &dev->functions);542 543 return true;544 }545 546 /** Remove function from device tree.547 *548 * @param tree Device tree549 * @param node Function node to remove550 */551 void remove_fun_node(dev_tree_t *tree, fun_node_t *fun)552 {553 assert(fibril_rwlock_is_write_locked(&tree->rwlock));554 555 /* Remove the node from the handle-to-node map. */556 hash_table_remove(&tree->devman_functions, &fun->handle);557 558 /* Remove the node from the list of its parent's children. */559 if (fun->dev != NULL)560 list_remove(&fun->dev_functions);561 562 fun->dev = NULL;563 fun->state = FUN_REMOVED;564 }565 566 292 /* loc devices */ 567 293 -
uspace/srv/devman/devman.h
r38e52c92 r59dc181 244 244 extern char *read_id(const char **); 245 245 246 /* Device tree */247 248 extern bool init_device_tree(dev_tree_t *, driver_list_t *);249 extern bool create_root_nodes(dev_tree_t *);250 extern bool insert_dev_node(dev_tree_t *, dev_node_t *, fun_node_t *);251 extern void remove_dev_node(dev_tree_t *, dev_node_t *);252 extern bool insert_fun_node(dev_tree_t *, fun_node_t *, char *, dev_node_t *);253 extern void remove_fun_node(dev_tree_t *, fun_node_t *);254 255 246 /* Loc services */ 256 247 -
uspace/srv/devman/driver.c
r38e52c92 r59dc181 37 37 #include <io/log.h> 38 38 #include <ipc/driver.h> 39 #include <ipc/devman.h>40 39 #include <loc.h> 41 40 #include <str_error.h> -
uspace/srv/devman/fun.c
r38e52c92 r59dc181 32 32 33 33 #include <errno.h> 34 #include <fcntl.h>35 #include <sys/stat.h>36 34 #include <io/log.h> 37 #include <ipc/driver.h>38 #include <ipc/devman.h>39 #include <loc.h>40 #include <str_error.h>41 #include <stdio.h>42 35 43 36 #include "devman.h" -
uspace/srv/devman/main.c
r38e52c92 r59dc181 60 60 #include "dev.h" 61 61 #include "devman.h" 62 #include "devtree.h" 62 63 #include "driver.h" 63 64 #include "fun.h"
Note:
See TracChangeset
for help on using the changeset viewer.