status_t
socket_get_next_stat(uint32* _cookie, int family, struct net_stat* stat)
{
	MutexLocker locker(sSocketLock);

	net_socket_private* socket = NULL;
	SocketList::Iterator iterator = sSocketList.GetIterator();
	uint32 cookie = *_cookie;
	uint32 count = 0;

	while (true) {
		socket = iterator.Next();
		if (socket == NULL)
			return B_ENTRY_NOT_FOUND;

		// TODO: also traverse the pending connections
		if (count == cookie)
			break;

		if (family == -1 || family == socket->family)
			count++;
	}

	*_cookie = count + 1;

	stat->family = socket->family;
	stat->type = socket->type;
	stat->protocol = socket->protocol;
	stat->owner = socket->owner;
	stat->state[0] = '\0';
	memcpy(&stat->address, &socket->address, sizeof(struct sockaddr_storage));
	memcpy(&stat->peer, &socket->peer, sizeof(struct sockaddr_storage));
	stat->receive_queue_size = 0;
	stat->send_queue_size = 0;

	// fill in protocol specific data (if supported by the protocol)
	size_t length = sizeof(net_stat);
	socket->first_info->control(socket->first_protocol, socket->protocol,
		NET_STAT_SOCKET, stat, &length);

	return B_OK;
}
static int
dump_sockets(int argc, char** argv)
{
	kprintf("address        kind  owner protocol   module_info parent\n");

	SocketList::Iterator iterator = sSocketList.GetIterator();
	while (net_socket_private* socket = iterator.Next()) {
		print_socket_line(socket, "");

		SocketList::Iterator childIterator
			= socket->pending_children.GetIterator();
		while (net_socket_private* child = childIterator.Next()) {
			print_socket_line(child, " ");
		}

		childIterator = socket->connected_children.GetIterator();
		while (net_socket_private* child = childIterator.Next()) {
			print_socket_line(child, " ");
		}
	}

	return 0;
}