1 /* 2 * Copyright 2003-2005, Axel Dörfler, axeld@pinc-software.de. All rights reserved. 3 * Distributed under the terms of the MIT License. 4 */ 5 6 #include <platform/openfirmware/devices.h> 7 #include <platform/openfirmware/openfirmware.h> 8 #include <util/kernel_cpp.h> 9 10 #include <string.h> 11 12 13 /** Gets all device types of the specified type by doing a 14 * depth-first search of the OpenFirmware device tree. 15 * If a root != 0 is given, the function only traverses the subtree spanned 16 * by the root (inclusively). Otherwise the whole device tree is searched. 17 * 18 * The cookie has to be initialized to zero. 19 */ 20 status_t 21 of_get_next_device(int *_cookie, int root, const char *type, char *path, 22 size_t pathSize) 23 { 24 int node = *_cookie; 25 26 while (true) { 27 int next; 28 29 if (node == 0) { 30 // node is NULL, meaning that this is the initial function call. 31 // If a root was supplied, we take that, otherwise the device tree 32 // root. 33 if (root != 0) 34 node = root; 35 else 36 node = of_peer(0); 37 38 if (node == OF_FAILED) 39 return B_ERROR; 40 if (node == 0) 41 return B_ENTRY_NOT_FOUND; 42 43 // We want to visit the root first. 44 next = node; 45 } else 46 next = of_child(node); 47 48 if (next == OF_FAILED) 49 return B_ERROR; 50 51 if (next == 0) { 52 // no child node found 53 next = of_peer(node); 54 if (next == OF_FAILED) 55 return B_ERROR; 56 57 while (next == 0) { 58 // no peer node found, we are using the device 59 // tree itself as our search stack 60 61 next = of_parent(node); 62 if (next == OF_FAILED) 63 return B_ERROR; 64 65 if (next == root || next == 0) { 66 // We have searched the whole device tree 67 return B_ENTRY_NOT_FOUND; 68 } 69 70 // look into the next tree 71 node = next; 72 next = of_peer(node); 73 } 74 } 75 76 *_cookie = node = next; 77 78 char nodeType[16]; 79 int length; 80 if (of_getprop(node, "device_type", nodeType, sizeof(nodeType)) 81 == OF_FAILED 82 || strcmp(nodeType, type) 83 || (length = of_package_to_path(node, path, pathSize - 1)) 84 == OF_FAILED) { 85 continue; 86 } 87 88 path[length] = '\0'; 89 return B_OK; 90 } 91 } 92 93