From a3ec278addf578e09deac1159bba3f1a8a72b336 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Axel=20D=C3=B6rfler?= Date: Mon, 15 Feb 2010 13:28:33 +0000 Subject: [PATCH] * Made some internal lists use DoublyLinkedLists instead of struct list. * Added a few KDL commands to improve your debugging experience. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@35469 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- src/add-ons/kernel/network/stack/domains.cpp | 112 ++++++++++++------ src/add-ons/kernel/network/stack/domains.h | 12 +- .../kernel/network/stack/interfaces.cpp | 104 ++++++++++++++++ src/add-ons/kernel/network/stack/interfaces.h | 2 +- .../kernel/network/stack/net_buffer.cpp | 2 +- 5 files changed, 191 insertions(+), 41 deletions(-) diff --git a/src/add-ons/kernel/network/stack/domains.cpp b/src/add-ons/kernel/network/stack/domains.cpp index 10bcbc90cc..9af66f0a85 100644 --- a/src/add-ons/kernel/network/stack/domains.cpp +++ b/src/add-ons/kernel/network/stack/domains.cpp @@ -1,5 +1,5 @@ /* - * Copyright 2006-2009, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2010, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -32,8 +32,13 @@ # define TRACE(x) ; #endif +#define ENABLE_DEBUGGER_COMMANDS 1 + + +typedef DoublyLinkedList DomainList; + static mutex sDomainLock; -static list sDomains; +static DomainList sDomains; /*! Scans the domain list for the specified family. @@ -42,12 +47,8 @@ static list sDomains; static net_domain_private* lookup_domain(int family) { - net_domain_private* domain = NULL; - while (true) { - domain = (net_domain_private*)list_get_next_item(&sDomains, domain); - if (domain == NULL) - break; - + DomainList::Iterator iterator = sDomains.GetIterator(); + while (net_domain_private* domain = iterator.Next()) { if (domain->family == family) return domain; } @@ -56,6 +57,55 @@ lookup_domain(int family) } +#if ENABLE_DEBUGGER_COMMANDS + + +static int +dump_domains(int argc, char** argv) +{ + DomainList::Iterator iterator = sDomains.GetIterator(); + while (net_domain_private* domain = iterator.Next()) { + kprintf("domain: %p, %s, %d\n", domain, domain->name, domain->family); + kprintf(" module: %p\n", domain->module); + kprintf(" address_module: %p\n", domain->address_module); + + if (!list_is_empty(&domain->interfaces)) + kprintf(" interfaces:\n"); + + net_interface* interface = NULL; + while (true) { + interface = (net_interface*)list_get_next_item(&domain->interfaces, + interface); + if (interface == NULL) + break; + + kprintf(" %p\n", interface); + } + + if (!domain->routes.IsEmpty()) + kprintf(" routes:\n"); + + RouteList::Iterator routeIterator = domain->routes.GetIterator(); + while (net_route* route = routeIterator.Next()) { + kprintf(" %p\n", route); + } + + if (!domain->route_infos.IsEmpty()) + kprintf(" route infos:\n"); + + RouteInfoList::Iterator infoIterator = domain->route_infos.GetIterator(); + while (net_route_info* info = infoIterator.Next()) { + kprintf(" %p\n", info); + } + } + + return 0; +} + + +#endif // ENABLE_DEBUGGER_COMMANDS + + // #pragma mark - @@ -74,14 +124,10 @@ count_domain_interfaces() { MutexLocker locker(sDomainLock); - net_domain_private* domain = NULL; uint32 count = 0; - while (true) { - domain = (net_domain_private*)list_get_next_item(&sDomains, domain); - if (domain == NULL) - break; - + DomainList::Iterator iterator = sDomains.GetIterator(); + while (net_domain_private* domain = iterator.Next()) { net_interface* interface = NULL; while (true) { interface = (net_interface*)list_get_next_item(&domain->interfaces, @@ -97,8 +143,7 @@ count_domain_interfaces() } -/*! - Dumps a list of all interfaces into the supplied userland buffer. +/*! Dumps a list of all interfaces into the supplied userland buffer. If the interfaces don't fit into the buffer, an error (\c ENOBUFS) is returned. */ @@ -108,13 +153,9 @@ list_domain_interfaces(void* _buffer, size_t* bufferSize) MutexLocker locker(sDomainLock); UserBuffer buffer(_buffer, *bufferSize); - net_domain_private* domain = NULL; - - while (true) { - domain = (net_domain_private*)list_get_next_item(&sDomains, domain); - if (domain == NULL) - break; + DomainList::Iterator iterator = sDomains.GetIterator(); + while (net_domain_private* domain = iterator.Next()) { RecursiveLocker locker(domain->lock); net_interface* interface = NULL; @@ -193,8 +234,7 @@ add_interface_to_domain(net_domain* _domain, } -/*! - Removes the interface from its domain, and deletes it. +/*! Removes the interface from its domain, and deletes it. You need to hold the domain's lock when calling this function. */ status_t @@ -281,12 +321,8 @@ domain_removed_device_interface(net_device_interface* deviceInterface) { MutexLocker locker(sDomainLock); - net_domain_private* domain = NULL; - while (true) { - domain = (net_domain_private*)list_get_next_item(&sDomains, domain); - if (domain == NULL) - break; - + DomainList::Iterator iterator = sDomains.GetIterator(); + while (net_domain_private* domain = iterator.Next()) { RecursiveLocker locker(domain->lock); net_interface_private* interface = find_interface(domain, @@ -325,7 +361,7 @@ register_domain(int family, const char* name, list_init(&domain->interfaces); - list_add_item(&sDomains, domain); + sDomains.Add(domain); *_domain = domain; return B_OK; @@ -341,7 +377,7 @@ unregister_domain(net_domain* _domain) net_domain_private* domain = (net_domain_private*)_domain; MutexLocker locker(sDomainLock); - list_remove_item(&sDomains, domain); + sDomains.Remove(domain); net_interface_private* interface = NULL; while (true) { @@ -364,7 +400,13 @@ init_domains() { mutex_init(&sDomainLock, "net domains"); - list_init_etc(&sDomains, offsetof(struct net_domain_private, link)); + new (&sDomains) DomainList; + // static C++ objects are not initialized in the module startup + +#if ENABLE_DEBUGGER_COMMANDS + add_debugger_command("net_domains", &dump_domains, + "Dump network domains"); +#endif return B_OK; } @@ -372,6 +414,10 @@ init_domains() status_t uninit_domains() { +#if ENABLE_DEBUGGER_COMMANDS + remove_debugger_command("net_domains", &dump_domains); +#endif + mutex_destroy(&sDomainLock); return B_OK; } diff --git a/src/add-ons/kernel/network/stack/domains.h b/src/add-ons/kernel/network/stack/domains.h index 84778ec04a..6da5ca147d 100644 --- a/src/add-ons/kernel/network/stack/domains.h +++ b/src/add-ons/kernel/network/stack/domains.h @@ -1,5 +1,5 @@ /* - * Copyright 2006-2009, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2010, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -9,19 +9,18 @@ #define DOMAINS_H -#include "routes.h" - #include #include #include +#include "routes.h" + struct net_device_interface; -struct net_domain_private : net_domain { - struct list_link link; - +struct net_domain_private : net_domain, + DoublyLinkedListLinkImpl { recursive_lock lock; RouteList routes; @@ -47,4 +46,5 @@ status_t register_domain(int family, const char* name, struct net_address_module_info* addressModule, net_domain* *_domain); status_t unregister_domain(net_domain* domain); + #endif // DOMAINS_H diff --git a/src/add-ons/kernel/network/stack/interfaces.cpp b/src/add-ons/kernel/network/stack/interfaces.cpp index 1523e47476..da217c44ae 100644 --- a/src/add-ons/kernel/network/stack/interfaces.cpp +++ b/src/add-ons/kernel/network/stack/interfaces.cpp @@ -33,6 +33,8 @@ # define TRACE(x) ; #endif +#define ENABLE_DEBUGGER_COMMANDS 1 + static mutex sInterfaceLock; static DeviceInterfaceList sInterfaces; @@ -180,6 +182,93 @@ notify_device_monitors(net_device_interface* interface, int32 event) } +#if ENABLE_DEBUGGER_COMMANDS + + +static int +dump_interface(int argc, char** argv) +{ + if (argc != 2) { + kprintf("usage: %s [address]\n", argv[0]); + return 0; + } + + net_interface_private* interface + = (net_interface_private*)parse_expression(argv[1]); + + kprintf("name: %s\n", interface->name); + kprintf("base_name: %s\n", interface->name); + kprintf("domain: %p\n", interface->domain); + kprintf("device: %p\n", interface->device); + kprintf("device_interface: %p\n", interface->device_interface); + kprintf("direct_route: %p\n", &interface->direct_route); + kprintf("first_protocol: %p\n", interface->first_protocol); + kprintf("first_info: %p\n", interface->first_info); + kprintf("address: %p\n", interface->address); + kprintf("destination: %p\n", interface->destination); + kprintf("mask: %p\n", interface->mask); + kprintf("index: %" B_PRIu32 "\n", interface->index); + kprintf("flags: %#" B_PRIx32 "\n", interface->flags); + kprintf("type: %u\n", interface->type); + kprintf("mtu: %" B_PRIu32 "\n", interface->mtu); + kprintf("metric: %" B_PRIu32 "\n", interface->metric); + + return 0; +} + + +static int +dump_device_interface(int argc, char** argv) +{ + if (argc != 2) { + kprintf("usage: %s [address]\n", argv[0]); + return 0; + } + + net_device_interface* interface + = (net_device_interface*)parse_expression(argv[1]); + + kprintf("device: %p\n", interface->device); + kprintf("reader_thread: %ld\n", interface->reader_thread); + kprintf("up_count: %" B_PRIu32 "\n", interface->up_count); + kprintf("ref_count: %" B_PRId32 "\n", interface->ref_count); + kprintf("deframe_func: %p\n", interface->deframe_func); + kprintf("deframe_ref_count: %" B_PRId32 "\n", interface->ref_count); + kprintf("monitor_funcs:\n"); + kprintf("receive_funcs:\n"); + kprintf("consumer_thread: %ld\n", interface->consumer_thread); + kprintf("receive_lock: %p\n", &interface->receive_lock); + kprintf("receive_queue: %p\n", &interface->receive_queue); + + DeviceMonitorList::Iterator monitorIterator + = interface->monitor_funcs.GetIterator(); + while (monitorIterator.HasNext()) + kprintf(" %p\n", monitorIterator.Next()); + + DeviceHandlerList::Iterator handlerIterator + = interface->receive_funcs.GetIterator(); + while (handlerIterator.HasNext()) + kprintf(" %p\n", handlerIterator.Next()); + + return 0; +} + + +static int +dump_device_interfaces(int argc, char** argv) +{ + DeviceInterfaceList::Iterator iterator = sInterfaces.GetIterator(); + while (net_device_interface* interface = iterator.Next()) { + kprintf(" %p\n", interface); + } + + return 0; +} + + +#endif // ENABLE_DEBUGGER_COMMANDS + + // #pragma mark - interfaces @@ -806,6 +895,15 @@ init_interfaces() new (&sInterfaces) DeviceInterfaceList; // static C++ objects are not initialized in the module startup + +#if ENABLE_DEBUGGER_COMMANDS + add_debugger_command("net_interface", &dump_interface, + "Dump the given network interface"); + add_debugger_command("net_device_interface", &dump_device_interface, + "Dump the given network device interface"); + add_debugger_command("net_device_interfaces", &dump_device_interfaces, + "Dump network device interfaces"); +#endif return B_OK; } @@ -813,6 +911,12 @@ init_interfaces() status_t uninit_interfaces() { +#if ENABLE_DEBUGGER_COMMANDS + remove_debugger_command("net_interface", &dump_interface); + remove_debugger_command("net_device_interface", &dump_device_interface); + remove_debugger_command("net_device_interfaces", &dump_device_interfaces); +#endif + mutex_destroy(&sInterfaceLock); return B_OK; } diff --git a/src/add-ons/kernel/network/stack/interfaces.h b/src/add-ons/kernel/network/stack/interfaces.h index 262d6f5ac2..024931f00e 100644 --- a/src/add-ons/kernel/network/stack/interfaces.h +++ b/src/add-ons/kernel/network/stack/interfaces.h @@ -15,7 +15,7 @@ #include -struct net_device_handler : public DoublyLinkedListLinkImpl { +struct net_device_handler : DoublyLinkedListLinkImpl { net_receive_func func; int32 type; void* cookie; diff --git a/src/add-ons/kernel/network/stack/net_buffer.cpp b/src/add-ons/kernel/network/stack/net_buffer.cpp index 702eb02751..cd65180114 100644 --- a/src/add-ons/kernel/network/stack/net_buffer.cpp +++ b/src/add-ons/kernel/network/stack/net_buffer.cpp @@ -43,7 +43,7 @@ // maximum implementation derived buffer size is 65536 #define ENABLE_DEBUGGER_COMMANDS 1 -//#define ENABLE_STATS 1 +#define ENABLE_STATS 1 #define PARANOID_BUFFER_CHECK NET_BUFFER_PARANOIA #define COMPONENT_PARANOIA_LEVEL NET_BUFFER_PARANOIA