direct-io.hg
changeset 14079:38fb6c392dec
Implement VBD and VIF handling on Solaris for libxenstat.
Also, fix up a confusion with ERR that was breaking xentop.
Signed-off-by: John Levon <john.levon@sun.com>
Also, fix up a confusion with ERR that was breaking xentop.
Signed-off-by: John Levon <john.levon@sun.com>
author | kfraser@localhost.localdomain |
---|---|
date | Fri Feb 23 10:47:55 2007 +0000 (2007-02-23) |
parents | d7fe2318fc5f |
children | cdc765772f69 |
files | tools/xenstat/libxenstat/Makefile tools/xenstat/libxenstat/src/xenstat.c tools/xenstat/libxenstat/src/xenstat.h tools/xenstat/libxenstat/src/xenstat_linux.c tools/xenstat/libxenstat/src/xenstat_priv.h tools/xenstat/libxenstat/src/xenstat_solaris.c tools/xenstat/xentop/xentop.c |
line diff
1.1 --- a/tools/xenstat/libxenstat/Makefile Fri Feb 23 10:43:00 2007 +0000 1.2 +++ b/tools/xenstat/libxenstat/Makefile Fri Feb 23 10:47:55 2007 +0000 1.3 @@ -14,7 +14,6 @@ 1.4 1.5 XEN_ROOT=../../.. 1.6 include $(XEN_ROOT)/tools/Rules.mk 1.7 -LINUX_ROOT := $(XEN_ROOT)/linux-2.6-xen-sparse 1.8 1.9 prefix=/usr 1.10 includedir=$(prefix)/include 1.11 @@ -29,26 +28,40 @@ MINOR=0 1.12 LIB=src/libxenstat.a 1.13 SHLIB=src/libxenstat.so.$(MAJOR).$(MINOR) 1.14 SHLIB_LINKS=src/libxenstat.so.$(MAJOR) src/libxenstat.so 1.15 -OBJECTS=src/xenstat.o 1.16 +OBJECTS-y=src/xenstat.o 1.17 +OBJECTS-$(CONFIG_Linux) += src/xenstat_linux.o 1.18 +OBJECTS-$(CONFIG_SunOS) += src/xenstat_solaris.o 1.19 SONAME_FLAGS=-Wl,$(SONAME_LDFLAG) -Wl,libxenstat.so.$(MAJOR) 1.20 1.21 WARN_FLAGS=-Wall -Werror 1.22 1.23 CFLAGS+=-Isrc -I$(XEN_LIBXC) -I$(XEN_XENSTORE) 1.24 LDFLAGS+=-Lsrc -L$(XEN_XENSTORE)/ -L$(XEN_LIBXC)/ 1.25 +LDLIBS-y = -lxenstore -lxenctrl 1.26 +LDLIBS-$(CONFIG_SunOS) += -lkstat 1.27 +ARLIBS-y = $(XEN_XENSTORE)/libxenstore.so $(XEN_LIBXC)/libxenctrl.so 1.28 +ARLIBS-x86_64 = /usr/lib/amd64/libkstat.so 1.29 +ARLIBS-x86_32 = /usr/lib/libkstat.so 1.30 +ARLIBS-$(CONFIG_SunOS) += $(ARLIBS-$(XEN_TARGET_ARCH)) 1.31 1.32 .PHONY: all 1.33 all: $(LIB) 1.34 1.35 -$(LIB): $(OBJECTS) 1.36 - $(AR) rc $@ $^ $(XEN_XENSTORE)/libxenstore.so $(XEN_LIBXC)/libxenctrl.so 1.37 +$(LIB): $(OBJECTS-y) 1.38 + $(AR) rc $@ $^ $(ARLIBS-y) 1.39 $(RANLIB) $@ 1.40 1.41 -$(SHLIB): $(OBJECTS) 1.42 - $(CC) $(CFLAGS) $(LDFLAGS) $(SONAME_FLAGS) $(SHLIB_CFLAGS) -o $@ $(OBJECTS) \ 1.43 - -lxenstore -lxenctrl 1.44 +$(SHLIB): $(OBJECTS-y) 1.45 + $(CC) $(CFLAGS) $(LDFLAGS) $(SONAME_FLAGS) $(SHLIB_CFLAGS) -o $@ \ 1.46 + $(OBJECTS-y) $(LDLIBS-y) 1.47 1.48 -src/xenstat.o: src/xenstat.c src/xenstat.h 1.49 +src/xenstat.o: src/xenstat.c src/xenstat.h src/xenstat_priv.h 1.50 + $(CC) $(CFLAGS) $(WARN_FLAGS) -c -o $@ $< 1.51 + 1.52 +src/xenstat_linux.o: src/xenstat_linux.c src/xenstat_priv.h 1.53 + $(CC) $(CFLAGS) $(WARN_FLAGS) -c -o $@ $< 1.54 + 1.55 +src/xenstat_solaris.o: src/xenstat_solaris.c src/xenstat_priv.h 1.56 $(CC) $(CFLAGS) $(WARN_FLAGS) -c -o $@ $< 1.57 1.58 src/libxenstat.so.$(MAJOR): $(LIB) 1.59 @@ -140,5 +153,5 @@ endif 1.60 1.61 .PHONY: clean 1.62 clean: 1.63 - rm -f $(LIB) $(SHLIB) $(SHLIB_LINKS) $(OBJECTS) \ 1.64 + rm -f $(LIB) $(SHLIB) $(SHLIB_LINKS) $(OBJECTS-y) \ 1.65 $(BINDINGS) $(BINDINGSRC)
2.1 --- a/tools/xenstat/libxenstat/src/xenstat.c Fri Feb 23 10:43:00 2007 +0000 2.2 +++ b/tools/xenstat/libxenstat/src/xenstat.c Fri Feb 23 10:47:55 2007 +0000 2.3 @@ -15,89 +15,17 @@ 2.4 * Lesser General Public License for more details. 2.5 */ 2.6 2.7 -#include <limits.h> 2.8 -#include <stdlib.h> 2.9 -#include <stdio.h> 2.10 -#include <string.h> 2.11 -#include <unistd.h> 2.12 -#include <fcntl.h> 2.13 -#include <dirent.h> 2.14 -#include <sys/types.h> 2.15 -#include <sys/stat.h> 2.16 -#include <xs.h> 2.17 -#include "xenstat.h" 2.18 - 2.19 -#include "xenctrl.h" 2.20 - 2.21 /* 2.22 - * Types 2.23 + * Copyright 2007 Sun Microsystems, Inc. All rights reserved. 2.24 + * Use is subject to license terms. 2.25 */ 2.26 -#define SHORT_ASC_LEN 5 /* length of 65535 */ 2.27 -#define VERSION_SIZE (2 * SHORT_ASC_LEN + 1 + sizeof(xen_extraversion_t) + 1) 2.28 - 2.29 -struct xenstat_handle { 2.30 - int xc_handle; 2.31 - struct xs_handle *xshandle; /* xenstore handle */ 2.32 - int page_size; 2.33 - FILE *procnetdev; 2.34 - DIR *sysfsvbd; 2.35 - char xen_version[VERSION_SIZE]; /* xen version running on this node */ 2.36 -}; 2.37 - 2.38 -struct xenstat_node { 2.39 - xenstat_handle *handle; 2.40 - unsigned int flags; 2.41 - unsigned long long cpu_hz; 2.42 - unsigned int num_cpus; 2.43 - unsigned long long tot_mem; 2.44 - unsigned long long free_mem; 2.45 - unsigned int num_domains; 2.46 - xenstat_domain *domains; /* Array of length num_domains */ 2.47 -}; 2.48 2.49 -struct xenstat_domain { 2.50 - unsigned int id; 2.51 - char *name; 2.52 - unsigned int state; 2.53 - unsigned long long cpu_ns; 2.54 - unsigned int num_vcpus; /* No. vcpus configured for domain */ 2.55 - xenstat_vcpu *vcpus; /* Array of length num_vcpus */ 2.56 - unsigned long long cur_mem; /* Current memory reservation */ 2.57 - unsigned long long max_mem; /* Total memory allowed */ 2.58 - unsigned int ssid; 2.59 - unsigned int num_networks; 2.60 - xenstat_network *networks; /* Array of length num_networks */ 2.61 - unsigned int num_vbds; 2.62 - xenstat_vbd *vbds; 2.63 -}; 2.64 - 2.65 -struct xenstat_vcpu { 2.66 - unsigned int online; 2.67 - unsigned long long ns; 2.68 -}; 2.69 +#include <stdlib.h> 2.70 +#include <string.h> 2.71 +#include <stdio.h> 2.72 +#include <unistd.h> 2.73 2.74 -struct xenstat_network { 2.75 - unsigned int id; 2.76 - /* Received */ 2.77 - unsigned long long rbytes; 2.78 - unsigned long long rpackets; 2.79 - unsigned long long rerrs; 2.80 - unsigned long long rdrop; 2.81 - /* Transmitted */ 2.82 - unsigned long long tbytes; 2.83 - unsigned long long tpackets; 2.84 - unsigned long long terrs; 2.85 - unsigned long long tdrop; 2.86 -}; 2.87 - 2.88 -struct xenstat_vbd { 2.89 - unsigned int dev; 2.90 - unsigned long long oo_reqs; 2.91 - unsigned long long rd_reqs; 2.92 - unsigned long long wr_reqs; 2.93 -}; 2.94 -#define SYSFS_VBD_PATH "/sys/devices/xen-backend/" 2.95 - 2.96 +#include "xenstat_priv.h" 2.97 2.98 /* 2.99 * Data-collection types 2.100 @@ -125,17 +53,13 @@ typedef struct xenstat_collector { 2.101 } xenstat_collector; 2.102 2.103 static int xenstat_collect_vcpus(xenstat_node * node); 2.104 -static int xenstat_collect_networks(xenstat_node * node); 2.105 static int xenstat_collect_xen_version(xenstat_node * node); 2.106 -static int xenstat_collect_vbds(xenstat_node * node); 2.107 static void xenstat_free_vcpus(xenstat_node * node); 2.108 static void xenstat_free_networks(xenstat_node * node); 2.109 static void xenstat_free_xen_version(xenstat_node * node); 2.110 static void xenstat_free_vbds(xenstat_node * node); 2.111 static void xenstat_uninit_vcpus(xenstat_handle * handle); 2.112 -static void xenstat_uninit_networks(xenstat_handle * handle); 2.113 static void xenstat_uninit_xen_version(xenstat_handle * handle); 2.114 -static void xenstat_uninit_vbds(xenstat_handle * handle); 2.115 static char *xenstat_get_domain_name(xenstat_handle * handle, unsigned int domain_id); 2.116 static void xenstat_prune_domain(xenstat_node *node, unsigned int entry); 2.117 2.118 @@ -202,6 +126,7 @@ void xenstat_uninit(xenstat_handle * han 2.119 collectors[i].uninit(handle); 2.120 xc_interface_close(handle->xc_handle); 2.121 xs_daemon_close(handle->xshandle); 2.122 + free(handle->priv); 2.123 free(handle); 2.124 } 2.125 } 2.126 @@ -586,97 +511,6 @@ unsigned long long xenstat_vcpu_ns(xenst 2.127 * Network functions 2.128 */ 2.129 2.130 -/* Expected format of /proc/net/dev */ 2.131 -static const char PROCNETDEV_HEADER[] = 2.132 - "Inter-| Receive |" 2.133 - " Transmit\n" 2.134 - " face |bytes packets errs drop fifo frame compressed multicast|" 2.135 - "bytes packets errs drop fifo colls carrier compressed\n"; 2.136 - 2.137 -/* Collect information about networks */ 2.138 -static int xenstat_collect_networks(xenstat_node * node) 2.139 -{ 2.140 - /* Open and validate /proc/net/dev if we haven't already */ 2.141 - if (node->handle->procnetdev == NULL) { 2.142 - char header[sizeof(PROCNETDEV_HEADER)]; 2.143 - node->handle->procnetdev = fopen("/proc/net/dev", "r"); 2.144 - if (node->handle->procnetdev == NULL) { 2.145 - perror("Error opening /proc/net/dev"); 2.146 - return 0; 2.147 - } 2.148 - 2.149 - /* Validate the format of /proc/net/dev */ 2.150 - if (fread(header, sizeof(PROCNETDEV_HEADER) - 1, 1, 2.151 - node->handle->procnetdev) != 1) { 2.152 - perror("Error reading /proc/net/dev header"); 2.153 - return 0; 2.154 - } 2.155 - header[sizeof(PROCNETDEV_HEADER) - 1] = '\0'; 2.156 - if (strcmp(header, PROCNETDEV_HEADER) != 0) { 2.157 - fprintf(stderr, 2.158 - "Unexpected /proc/net/dev format\n"); 2.159 - return 0; 2.160 - } 2.161 - } 2.162 - 2.163 - /* Fill in networks */ 2.164 - /* FIXME: optimize this */ 2.165 - fseek(node->handle->procnetdev, sizeof(PROCNETDEV_HEADER) - 1, 2.166 - SEEK_SET); 2.167 - while (1) { 2.168 - xenstat_domain *domain; 2.169 - xenstat_network net; 2.170 - unsigned int domid; 2.171 - int ret = fscanf(node->handle->procnetdev, 2.172 - "vif%u.%u:%llu%llu%llu%llu%*u%*u%*u%*u" 2.173 - "%llu%llu%llu%llu%*u%*u%*u%*u\n", 2.174 - &domid, &net.id, 2.175 - &net.tbytes, &net.tpackets, &net.terrs, 2.176 - &net.tdrop, 2.177 - &net.rbytes, &net.rpackets, &net.rerrs, 2.178 - &net.rdrop); 2.179 - if (ret == EOF) 2.180 - break; 2.181 - if (ret != 10) { 2.182 - unsigned int c; 2.183 - do { 2.184 - c = fgetc(node->handle->procnetdev); 2.185 - } while (c != '\n' && c != EOF); 2.186 - if (c == EOF) 2.187 - break; 2.188 - continue; 2.189 - } 2.190 - 2.191 - /* FIXME: this does a search for the domid */ 2.192 - domain = xenstat_node_domain(node, domid); 2.193 - if (domain == NULL) { 2.194 - fprintf(stderr, 2.195 - "Found interface vif%u.%u but domain %u" 2.196 - " does not exist.\n", domid, net.id, 2.197 - domid); 2.198 - continue; 2.199 - } 2.200 - if (domain->networks == NULL) { 2.201 - domain->num_networks = 1; 2.202 - domain->networks = malloc(sizeof(xenstat_network)); 2.203 - } else { 2.204 - struct xenstat_network *tmp; 2.205 - domain->num_networks++; 2.206 - tmp = realloc(domain->networks, 2.207 - domain->num_networks * 2.208 - sizeof(xenstat_network)); 2.209 - if (tmp == NULL) 2.210 - free(domain->networks); 2.211 - domain->networks = tmp; 2.212 - } 2.213 - if (domain->networks == NULL) 2.214 - return 0; 2.215 - domain->networks[domain->num_networks - 1] = net; 2.216 - } 2.217 - 2.218 - return 1; 2.219 -} 2.220 - 2.221 /* Free network information */ 2.222 static void xenstat_free_networks(xenstat_node * node) 2.223 { 2.224 @@ -685,13 +519,6 @@ static void xenstat_free_networks(xensta 2.225 free(node->domains[i].networks); 2.226 } 2.227 2.228 -/* Free network information in handle */ 2.229 -static void xenstat_uninit_networks(xenstat_handle * handle) 2.230 -{ 2.231 - if(handle->procnetdev) 2.232 - fclose(handle->procnetdev); 2.233 -} 2.234 - 2.235 /* Get the network ID */ 2.236 unsigned int xenstat_network_id(xenstat_network * network) 2.237 { 2.238 @@ -790,96 +617,6 @@ static void xenstat_uninit_xen_version(x 2.239 * VBD functions 2.240 */ 2.241 2.242 -static int read_attributes_vbd(const char *vbd_directory, const char *what, char *ret, int cap) 2.243 -{ 2.244 - static char file_name[80]; 2.245 - int fd, num_read; 2.246 - 2.247 - sprintf(file_name, "%s/%s/%s", SYSFS_VBD_PATH, vbd_directory, what); 2.248 - fd = open(file_name, O_RDONLY, 0); 2.249 - if (fd==-1) return -1; 2.250 - num_read = read(fd, ret, cap - 1); 2.251 - close(fd); 2.252 - if (num_read<=0) return -1; 2.253 - ret[num_read] = '\0'; 2.254 - return num_read; 2.255 -} 2.256 - 2.257 -/* Collect information about VBDs */ 2.258 -static int xenstat_collect_vbds(xenstat_node * node) 2.259 -{ 2.260 - struct dirent *dp; 2.261 - 2.262 - if (node->handle->sysfsvbd == NULL) { 2.263 - node->handle->sysfsvbd = opendir(SYSFS_VBD_PATH); 2.264 - if (node->handle->sysfsvbd == NULL) { 2.265 - perror("Error opening " SYSFS_VBD_PATH); 2.266 - return 0; 2.267 - } 2.268 - } 2.269 - 2.270 - rewinddir(node->handle->sysfsvbd); 2.271 - 2.272 - for(dp = readdir(node->handle->sysfsvbd); dp != NULL ; 2.273 - dp = readdir(node->handle->sysfsvbd)) { 2.274 - xenstat_domain *domain; 2.275 - xenstat_vbd vbd; 2.276 - unsigned int domid; 2.277 - int ret; 2.278 - char buf[256]; 2.279 - 2.280 - 2.281 - ret = sscanf(dp->d_name, "vbd-%u-%u", &domid, &vbd.dev); 2.282 - if (ret != 2) { 2.283 - continue; 2.284 - } 2.285 - printf("%s is VBD.\n",dp->d_name); 2.286 - 2.287 - domain = xenstat_node_domain(node, domid); 2.288 - if (domain == NULL) { 2.289 - fprintf(stderr, 2.290 - "Found interface vbd-%u-%u but domain %u" 2.291 - " does not exist.\n", 2.292 - domid, vbd.dev, domid); 2.293 - continue; 2.294 - } 2.295 - 2.296 - if((read_attributes_vbd(dp->d_name, "statistics/oo_req", buf, 256)<=0) 2.297 - || ((ret = sscanf(buf, "%llu", &vbd.oo_reqs)) != 1)) 2.298 - { 2.299 - continue; 2.300 - } 2.301 - 2.302 - if((read_attributes_vbd(dp->d_name, "statistics/rd_req", buf, 256)<=0) 2.303 - || ((ret = sscanf(buf, "%llu", &vbd.rd_reqs)) != 1)) 2.304 - { 2.305 - continue; 2.306 - } 2.307 - 2.308 - if((read_attributes_vbd(dp->d_name, "statistics/wr_req", buf, 256)<=0) 2.309 - || ((ret = sscanf(buf, "%llu", &vbd.wr_reqs)) != 1)) 2.310 - { 2.311 - continue; 2.312 - } 2.313 - 2.314 - 2.315 - if (domain->vbds == NULL) { 2.316 - domain->num_vbds = 1; 2.317 - domain->vbds = malloc(sizeof(xenstat_vbd)); 2.318 - } else { 2.319 - domain->num_vbds++; 2.320 - domain->vbds = realloc(domain->vbds, 2.321 - domain->num_vbds * 2.322 - sizeof(xenstat_vbd)); 2.323 - } 2.324 - if (domain->vbds == NULL) 2.325 - return 0; 2.326 - domain->vbds[domain->num_vbds - 1] = vbd; 2.327 - } 2.328 - 2.329 - return 1; 2.330 -} 2.331 - 2.332 /* Free VBD information */ 2.333 static void xenstat_free_vbds(xenstat_node * node) 2.334 { 2.335 @@ -888,13 +625,6 @@ static void xenstat_free_vbds(xenstat_no 2.336 free(node->domains[i].vbds); 2.337 } 2.338 2.339 -/* Free VBD information in handle */ 2.340 -static void xenstat_uninit_vbds(xenstat_handle * handle) 2.341 -{ 2.342 - if (handle->sysfsvbd) 2.343 - closedir(handle->sysfsvbd); 2.344 -} 2.345 - 2.346 /* Get the major number of VBD device */ 2.347 unsigned int xenstat_vbd_dev(xenstat_vbd * vbd) 2.348 { 2.349 @@ -948,4 +678,3 @@ static void xenstat_prune_domain(xenstat 2.350 strictly necessary but safer! */ 2.351 memset(&node->domains[node->num_domains], 0, sizeof(xenstat_domain)); 2.352 } 2.353 -
3.1 --- a/tools/xenstat/libxenstat/src/xenstat.h Fri Feb 23 10:43:00 2007 +0000 3.2 +++ b/tools/xenstat/libxenstat/src/xenstat.h Fri Feb 23 10:47:55 2007 +0000 3.3 @@ -17,6 +17,9 @@ 3.4 3.5 /* libxenstat API */ 3.6 3.7 +#ifndef XENSTAT_H 3.8 +#define XENSTAT_H 3.9 + 3.10 /* Opaque handles */ 3.11 typedef struct xenstat_handle xenstat_handle; 3.12 typedef struct xenstat_domain xenstat_domain; 3.13 @@ -176,3 +179,5 @@ unsigned int xenstat_vbd_dev(xenstat_vbd 3.14 unsigned long long xenstat_vbd_oo_reqs(xenstat_vbd * vbd); 3.15 unsigned long long xenstat_vbd_rd_reqs(xenstat_vbd * vbd); 3.16 unsigned long long xenstat_vbd_wr_reqs(xenstat_vbd * vbd); 3.17 + 3.18 +#endif /* XENSTAT_H */
4.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 4.2 +++ b/tools/xenstat/libxenstat/src/xenstat_linux.c Fri Feb 23 10:47:55 2007 +0000 4.3 @@ -0,0 +1,265 @@ 4.4 +/* libxenstat: statistics-collection library for Xen 4.5 + * Copyright (C) International Business Machines Corp., 2005 4.6 + * Authors: Josh Triplett <josht@us.ibm.com> 4.7 + * Judy Fischbach <jfisch@us.ibm.com> 4.8 + * David Hendricks <dhendrix@us.ibm.com> 4.9 + * 4.10 + * This library is free software; you can redistribute it and/or 4.11 + * modify it under the terms of the GNU Lesser General Public 4.12 + * License as published by the Free Software Foundation; either 4.13 + * version 2.1 of the License, or (at your option) any later version. 4.14 + * 4.15 + * This library is distributed in the hope that it will be useful, 4.16 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 4.17 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 4.18 + * Lesser General Public License for more details. 4.19 + */ 4.20 + 4.21 +/* 4.22 + * Copyright 2007 Sun Microsystems, Inc. All rights reserved. 4.23 + * Use is subject to license terms. 4.24 + */ 4.25 + 4.26 +#include <fcntl.h> 4.27 +#include <dirent.h> 4.28 +#include <sys/types.h> 4.29 +#include <sys/stat.h> 4.30 +#include <stdio.h> 4.31 +#include <stdlib.h> 4.32 +#include <string.h> 4.33 +#include <unistd.h> 4.34 + 4.35 +#include "xenstat_priv.h" 4.36 + 4.37 +#define SYSFS_VBD_PATH "/sys/devices/xen-backend/" 4.38 + 4.39 +struct priv_data { 4.40 + FILE *procnetdev; 4.41 + DIR *sysfsvbd; 4.42 +}; 4.43 + 4.44 +static struct priv_data * 4.45 +get_priv_data(xenstat_handle *handle) 4.46 +{ 4.47 + if (handle->priv != NULL) 4.48 + return handle->priv; 4.49 + 4.50 + handle->priv = malloc(sizeof(struct priv_data)); 4.51 + if (handle->priv == NULL) 4.52 + return (NULL); 4.53 + 4.54 + ((struct priv_data *)handle->priv)->procnetdev = NULL; 4.55 + ((struct priv_data *)handle->priv)->sysfsvbd = NULL; 4.56 + 4.57 + return handle->priv; 4.58 +} 4.59 + 4.60 +/* Expected format of /proc/net/dev */ 4.61 +static const char PROCNETDEV_HEADER[] = 4.62 + "Inter-| Receive |" 4.63 + " Transmit\n" 4.64 + " face |bytes packets errs drop fifo frame compressed multicast|" 4.65 + "bytes packets errs drop fifo colls carrier compressed\n"; 4.66 + 4.67 +/* Collect information about networks */ 4.68 +int xenstat_collect_networks(xenstat_node * node) 4.69 +{ 4.70 + struct priv_data *priv = get_priv_data(node->handle); 4.71 + 4.72 + if (priv == NULL) { 4.73 + perror("Allocation error"); 4.74 + return 0; 4.75 + } 4.76 + 4.77 + /* Open and validate /proc/net/dev if we haven't already */ 4.78 + if (priv->procnetdev == NULL) { 4.79 + char header[sizeof(PROCNETDEV_HEADER)]; 4.80 + priv->procnetdev = fopen("/proc/net/dev", "r"); 4.81 + if (priv->procnetdev == NULL) { 4.82 + perror("Error opening /proc/net/dev"); 4.83 + return 0; 4.84 + } 4.85 + 4.86 + /* Validate the format of /proc/net/dev */ 4.87 + if (fread(header, sizeof(PROCNETDEV_HEADER) - 1, 1, 4.88 + priv->procnetdev) != 1) { 4.89 + perror("Error reading /proc/net/dev header"); 4.90 + return 0; 4.91 + } 4.92 + header[sizeof(PROCNETDEV_HEADER) - 1] = '\0'; 4.93 + if (strcmp(header, PROCNETDEV_HEADER) != 0) { 4.94 + fprintf(stderr, 4.95 + "Unexpected /proc/net/dev format\n"); 4.96 + return 0; 4.97 + } 4.98 + } 4.99 + 4.100 + /* Fill in networks */ 4.101 + /* FIXME: optimize this */ 4.102 + fseek(priv->procnetdev, sizeof(PROCNETDEV_HEADER) - 1, 4.103 + SEEK_SET); 4.104 + while (1) { 4.105 + xenstat_domain *domain; 4.106 + xenstat_network net; 4.107 + unsigned int domid; 4.108 + int ret = fscanf(priv->procnetdev, 4.109 + "vif%u.%u:%llu%llu%llu%llu%*u%*u%*u%*u" 4.110 + "%llu%llu%llu%llu%*u%*u%*u%*u\n", 4.111 + &domid, &net.id, 4.112 + &net.tbytes, &net.tpackets, &net.terrs, 4.113 + &net.tdrop, 4.114 + &net.rbytes, &net.rpackets, &net.rerrs, 4.115 + &net.rdrop); 4.116 + if (ret == EOF) 4.117 + break; 4.118 + if (ret != 10) { 4.119 + unsigned int c; 4.120 + do { 4.121 + c = fgetc(priv->procnetdev); 4.122 + } while (c != '\n' && c != EOF); 4.123 + if (c == EOF) 4.124 + break; 4.125 + continue; 4.126 + } 4.127 + 4.128 + /* FIXME: this does a search for the domid */ 4.129 + domain = xenstat_node_domain(node, domid); 4.130 + if (domain == NULL) { 4.131 + fprintf(stderr, 4.132 + "Found interface vif%u.%u but domain %u" 4.133 + " does not exist.\n", domid, net.id, 4.134 + domid); 4.135 + continue; 4.136 + } 4.137 + if (domain->networks == NULL) { 4.138 + domain->num_networks = 1; 4.139 + domain->networks = malloc(sizeof(xenstat_network)); 4.140 + } else { 4.141 + struct xenstat_network *tmp; 4.142 + domain->num_networks++; 4.143 + tmp = realloc(domain->networks, 4.144 + domain->num_networks * 4.145 + sizeof(xenstat_network)); 4.146 + if (tmp == NULL) 4.147 + free(domain->networks); 4.148 + domain->networks = tmp; 4.149 + } 4.150 + if (domain->networks == NULL) 4.151 + return 0; 4.152 + domain->networks[domain->num_networks - 1] = net; 4.153 + } 4.154 + 4.155 + return 1; 4.156 +} 4.157 + 4.158 +/* Free network information in handle */ 4.159 +void xenstat_uninit_networks(xenstat_handle * handle) 4.160 +{ 4.161 + struct priv_data *priv = get_priv_data(handle); 4.162 + if (priv != NULL && priv->procnetdev != NULL) 4.163 + fclose(priv->procnetdev); 4.164 +} 4.165 + 4.166 +static int read_attributes_vbd(const char *vbd_directory, const char *what, char *ret, int cap) 4.167 +{ 4.168 + static char file_name[80]; 4.169 + int fd, num_read; 4.170 + 4.171 + sprintf(file_name, "%s/%s/%s", SYSFS_VBD_PATH, vbd_directory, what); 4.172 + fd = open(file_name, O_RDONLY, 0); 4.173 + if (fd==-1) return -1; 4.174 + num_read = read(fd, ret, cap - 1); 4.175 + close(fd); 4.176 + if (num_read<=0) return -1; 4.177 + ret[num_read] = '\0'; 4.178 + return num_read; 4.179 +} 4.180 + 4.181 +/* Collect information about VBDs */ 4.182 +int xenstat_collect_vbds(xenstat_node * node) 4.183 +{ 4.184 + struct dirent *dp; 4.185 + struct priv_data *priv = get_priv_data(node->handle); 4.186 + 4.187 + if (priv == NULL) { 4.188 + perror("Allocation error"); 4.189 + return 0; 4.190 + } 4.191 + 4.192 + if (priv->sysfsvbd == NULL) { 4.193 + priv->sysfsvbd = opendir(SYSFS_VBD_PATH); 4.194 + if (priv->sysfsvbd == NULL) { 4.195 + perror("Error opening " SYSFS_VBD_PATH); 4.196 + return 0; 4.197 + } 4.198 + } 4.199 + 4.200 + rewinddir(priv->sysfsvbd); 4.201 + 4.202 + for(dp = readdir(priv->sysfsvbd); dp != NULL ; 4.203 + dp = readdir(priv->sysfsvbd)) { 4.204 + xenstat_domain *domain; 4.205 + xenstat_vbd vbd; 4.206 + unsigned int domid; 4.207 + int ret; 4.208 + char buf[256]; 4.209 + 4.210 + 4.211 + ret = sscanf(dp->d_name, "vbd-%u-%u", &domid, &vbd.dev); 4.212 + if (ret != 2) { 4.213 + continue; 4.214 + } 4.215 + printf("%s is VBD.\n",dp->d_name); 4.216 + 4.217 + domain = xenstat_node_domain(node, domid); 4.218 + if (domain == NULL) { 4.219 + fprintf(stderr, 4.220 + "Found interface vbd-%u-%u but domain %u" 4.221 + " does not exist.\n", 4.222 + domid, vbd.dev, domid); 4.223 + continue; 4.224 + } 4.225 + 4.226 + if((read_attributes_vbd(dp->d_name, "statistics/oo_req", buf, 256)<=0) 4.227 + || ((ret = sscanf(buf, "%llu", &vbd.oo_reqs)) != 1)) 4.228 + { 4.229 + continue; 4.230 + } 4.231 + 4.232 + if((read_attributes_vbd(dp->d_name, "statistics/rd_req", buf, 256)<=0) 4.233 + || ((ret = sscanf(buf, "%llu", &vbd.rd_reqs)) != 1)) 4.234 + { 4.235 + continue; 4.236 + } 4.237 + 4.238 + if((read_attributes_vbd(dp->d_name, "statistics/wr_req", buf, 256)<=0) 4.239 + || ((ret = sscanf(buf, "%llu", &vbd.wr_reqs)) != 1)) 4.240 + { 4.241 + continue; 4.242 + } 4.243 + 4.244 + 4.245 + if (domain->vbds == NULL) { 4.246 + domain->num_vbds = 1; 4.247 + domain->vbds = malloc(sizeof(xenstat_vbd)); 4.248 + } else { 4.249 + domain->num_vbds++; 4.250 + domain->vbds = realloc(domain->vbds, 4.251 + domain->num_vbds * 4.252 + sizeof(xenstat_vbd)); 4.253 + } 4.254 + if (domain->vbds == NULL) 4.255 + return 0; 4.256 + domain->vbds[domain->num_vbds - 1] = vbd; 4.257 + } 4.258 + 4.259 + return 1; 4.260 +} 4.261 + 4.262 +/* Free VBD information in handle */ 4.263 +void xenstat_uninit_vbds(xenstat_handle * handle) 4.264 +{ 4.265 + struct priv_data *priv = get_priv_data(handle); 4.266 + if (priv != NULL && priv->sysfsvbd != NULL) 4.267 + closedir(priv->sysfsvbd); 4.268 +}
5.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 5.2 +++ b/tools/xenstat/libxenstat/src/xenstat_priv.h Fri Feb 23 10:47:55 2007 +0000 5.3 @@ -0,0 +1,101 @@ 5.4 +/* libxenstat: statistics-collection library for Xen 5.5 + * Copyright (C) International Business Machines Corp., 2005 5.6 + * Authors: Josh Triplett <josht@us.ibm.com> 5.7 + * Judy Fischbach <jfisch@us.ibm.com> 5.8 + * David Hendricks <dhendrix@us.ibm.com> 5.9 + * 5.10 + * This library is free software; you can redistribute it and/or 5.11 + * modify it under the terms of the GNU Lesser General Public 5.12 + * License as published by the Free Software Foundation; either 5.13 + * version 2.1 of the License, or (at your option) any later version. 5.14 + * 5.15 + * This library is distributed in the hope that it will be useful, 5.16 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 5.17 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 5.18 + * Lesser General Public License for more details. 5.19 + */ 5.20 + 5.21 +/* 5.22 + * Copyright 2007 Sun Microsystems, Inc. All rights reserved. 5.23 + * Use is subject to license terms. 5.24 + */ 5.25 + 5.26 +#ifndef XENSTAT_PRIV_H 5.27 +#define XENSTAT_PRIV_H 5.28 + 5.29 +#include <sys/types.h> 5.30 +#include <xs.h> 5.31 +#include "xenstat.h" 5.32 + 5.33 +#include "xenctrl.h" 5.34 + 5.35 +#define SHORT_ASC_LEN 5 /* length of 65535 */ 5.36 +#define VERSION_SIZE (2 * SHORT_ASC_LEN + 1 + sizeof(xen_extraversion_t) + 1) 5.37 + 5.38 +struct xenstat_handle { 5.39 + int xc_handle; 5.40 + struct xs_handle *xshandle; /* xenstore handle */ 5.41 + int page_size; 5.42 + void *priv; 5.43 + char xen_version[VERSION_SIZE]; /* xen version running on this node */ 5.44 +}; 5.45 + 5.46 +struct xenstat_node { 5.47 + xenstat_handle *handle; 5.48 + unsigned int flags; 5.49 + unsigned long long cpu_hz; 5.50 + unsigned int num_cpus; 5.51 + unsigned long long tot_mem; 5.52 + unsigned long long free_mem; 5.53 + unsigned int num_domains; 5.54 + xenstat_domain *domains; /* Array of length num_domains */ 5.55 +}; 5.56 + 5.57 +struct xenstat_domain { 5.58 + unsigned int id; 5.59 + char *name; 5.60 + unsigned int state; 5.61 + unsigned long long cpu_ns; 5.62 + unsigned int num_vcpus; /* No. vcpus configured for domain */ 5.63 + xenstat_vcpu *vcpus; /* Array of length num_vcpus */ 5.64 + unsigned long long cur_mem; /* Current memory reservation */ 5.65 + unsigned long long max_mem; /* Total memory allowed */ 5.66 + unsigned int ssid; 5.67 + unsigned int num_networks; 5.68 + xenstat_network *networks; /* Array of length num_networks */ 5.69 + unsigned int num_vbds; 5.70 + xenstat_vbd *vbds; 5.71 +}; 5.72 + 5.73 +struct xenstat_vcpu { 5.74 + unsigned int online; 5.75 + unsigned long long ns; 5.76 +}; 5.77 + 5.78 +struct xenstat_network { 5.79 + unsigned int id; 5.80 + /* Received */ 5.81 + unsigned long long rbytes; 5.82 + unsigned long long rpackets; 5.83 + unsigned long long rerrs; 5.84 + unsigned long long rdrop; 5.85 + /* Transmitted */ 5.86 + unsigned long long tbytes; 5.87 + unsigned long long tpackets; 5.88 + unsigned long long terrs; 5.89 + unsigned long long tdrop; 5.90 +}; 5.91 + 5.92 +struct xenstat_vbd { 5.93 + unsigned int dev; 5.94 + unsigned long long oo_reqs; 5.95 + unsigned long long rd_reqs; 5.96 + unsigned long long wr_reqs; 5.97 +}; 5.98 + 5.99 +extern int xenstat_collect_networks(xenstat_node * node); 5.100 +extern void xenstat_uninit_networks(xenstat_handle * handle); 5.101 +extern int xenstat_collect_vbds(xenstat_node * node); 5.102 +extern void xenstat_uninit_vbds(xenstat_handle * handle); 5.103 + 5.104 +#endif /* XENSTAT_PRIV_H */
6.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 6.2 +++ b/tools/xenstat/libxenstat/src/xenstat_solaris.c Fri Feb 23 10:47:55 2007 +0000 6.3 @@ -0,0 +1,431 @@ 6.4 +/* libxenstat: statistics-collection library for Xen 6.5 + * 6.6 + * This library is free software; you can redistribute it and/or 6.7 + * modify it under the terms of the GNU Lesser General Public 6.8 + * License as published by the Free Software Foundation; either 6.9 + * version 2.1 of the License, or (at your option) any later version. 6.10 + * 6.11 + * This library is distributed in the hope that it will be useful, 6.12 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 6.13 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 6.14 + * Lesser General Public License for more details. 6.15 + */ 6.16 + 6.17 +/* 6.18 + * Copyright 2007 Sun Microsystems, Inc. All rights reserved. 6.19 + * Use is subject to license terms. 6.20 + */ 6.21 + 6.22 +#include <strings.h> 6.23 +#include <string.h> 6.24 +#include <stdlib.h> 6.25 +#include <stdio.h> 6.26 +#include <ctype.h> 6.27 +#include <kstat.h> 6.28 + 6.29 +#include "xenstat_priv.h" 6.30 + 6.31 +#define DEVICE_NIC 1 6.32 +#define DEVICE_XDB 2 6.33 + 6.34 +typedef struct stdevice { 6.35 + int domid; 6.36 + int used; 6.37 + int type; 6.38 + char name[256]; 6.39 + int instance; 6.40 + uint64_t stats[2][8]; 6.41 + struct stdevice *next; 6.42 +} stdevice_t; 6.43 + 6.44 +typedef struct priv_data { 6.45 + kstat_ctl_t *kc; 6.46 + stdevice_t *devs; 6.47 +} priv_data_t; 6.48 + 6.49 +static priv_data_t *get_priv_data(xenstat_handle *handle) 6.50 +{ 6.51 + priv_data_t *priv = handle->priv; 6.52 + 6.53 + if (priv == NULL) { 6.54 + priv = malloc(sizeof (priv_data_t)); 6.55 + if (priv == NULL) 6.56 + return NULL; 6.57 + priv->devs = NULL; 6.58 + priv->kc = NULL; 6.59 + } 6.60 + 6.61 + if (priv->kc == NULL) { 6.62 + if ((priv->kc = kstat_open()) == NULL) { 6.63 + free(priv); 6.64 + return NULL; 6.65 + } 6.66 + } 6.67 + 6.68 + handle->priv = priv; 6.69 + return handle->priv; 6.70 +} 6.71 + 6.72 +static int kstat_get(kstat_t *ksp, const char *name, uint64_t *val) 6.73 +{ 6.74 + kstat_named_t *ksn = kstat_data_lookup(ksp, (char *)name); 6.75 + if (ksn == NULL) 6.76 + return 0; 6.77 + *val = ksn->value.ui64; 6.78 + return 1; 6.79 +} 6.80 + 6.81 +static void gc_devs(priv_data_t *priv, int type) 6.82 +{ 6.83 + stdevice_t *start = NULL; 6.84 + stdevice_t *dev; 6.85 + stdevice_t *tmp; 6.86 + 6.87 + for (dev = priv->devs; dev != NULL; dev = tmp) { 6.88 + tmp = dev->next; 6.89 + 6.90 + if (dev->used || dev->type != type) { 6.91 + dev->next = start; 6.92 + start = dev; 6.93 + } else { 6.94 + free(dev); 6.95 + } 6.96 + } 6.97 + 6.98 + priv->devs = start; 6.99 +} 6.100 + 6.101 +static void xenstat_uninit_devs(xenstat_handle *handle, int type) 6.102 +{ 6.103 + priv_data_t *priv = get_priv_data(handle); 6.104 + stdevice_t *dev; 6.105 + 6.106 + if (priv == NULL) 6.107 + return; 6.108 + 6.109 + for (dev = priv->devs; dev != NULL; dev = dev->next) 6.110 + dev->used = 0; 6.111 + 6.112 + gc_devs(priv, type); 6.113 + 6.114 + if (priv->kc != NULL) 6.115 + kstat_close(priv->kc); 6.116 + priv->kc = NULL; 6.117 +} 6.118 + 6.119 +static int parse_nic(const char *nic, char *module, int *instance) 6.120 +{ 6.121 + const char *c; 6.122 + 6.123 + for (c = &nic[strlen(nic) - 1]; c != nic && isdigit(*c); c--) 6.124 + ; 6.125 + 6.126 + if (c == nic) 6.127 + return 0; 6.128 + 6.129 + c++; 6.130 + 6.131 + if (sscanf(c, "%d", instance) != 1) 6.132 + return 0; 6.133 + 6.134 + strncpy(module, nic, c - nic); 6.135 + module[c - nic] = '\0'; 6.136 + return 1; 6.137 +} 6.138 + 6.139 +static int update_dev_stats(priv_data_t *priv, stdevice_t *dev) 6.140 +{ 6.141 + char mod[256]; 6.142 + const char *name; 6.143 + int inst; 6.144 + kstat_t *ksp; 6.145 + 6.146 + if (dev->type == DEVICE_NIC) { 6.147 + if (!parse_nic(dev->name, mod, &inst)) 6.148 + return 0; 6.149 + name = "mac"; 6.150 + } else { 6.151 + strcpy(mod, "xdb"); 6.152 + inst = dev->instance; 6.153 + name = "req_statistics"; 6.154 + } 6.155 + 6.156 + if (kstat_chain_update(priv->kc) == -1) 6.157 + return 0; 6.158 + 6.159 + ksp = kstat_lookup(priv->kc, mod, inst, (char *)name); 6.160 + if (ksp == NULL) 6.161 + return 0; 6.162 + if (kstat_read(priv->kc, ksp, NULL) == -1) 6.163 + return 0; 6.164 + 6.165 + dev->used = 1; 6.166 + 6.167 + bcopy(&(dev->stats[1][0]), &(dev->stats[0][0]), sizeof(dev->stats[0])); 6.168 + 6.169 + if (dev->type == DEVICE_NIC) { 6.170 + if (!kstat_get(ksp, "rbytes64", &dev->stats[1][0]) || 6.171 + !kstat_get(ksp, "ipackets64", &dev->stats[1][1]) || 6.172 + !kstat_get(ksp, "ierrors", &dev->stats[1][2]) || 6.173 + !kstat_get(ksp, "obytes64", &dev->stats[1][3]) || 6.174 + !kstat_get(ksp, "opackets64", &dev->stats[1][4]) || 6.175 + !kstat_get(ksp, "oerrors", &dev->stats[1][5])) 6.176 + return 0; 6.177 + 6.178 + dev->stats[1][6] = 0; 6.179 + dev->stats[1][7] = 0; 6.180 + } else { 6.181 + if (!kstat_get(ksp, "rd_reqs", &dev->stats[1][0]) || 6.182 + !kstat_get(ksp, "wr_reqs", &dev->stats[1][1]) || 6.183 + !kstat_get(ksp, "oo_reqs", &dev->stats[1][2])) 6.184 + return 0; 6.185 + } 6.186 + 6.187 + return 1; 6.188 +} 6.189 + 6.190 +static int init_dev(priv_data_t *priv, int type, const char *name, 6.191 + int instance, int domid) 6.192 +{ 6.193 + stdevice_t *dev; 6.194 + 6.195 + if (!(dev = malloc(sizeof(*dev)))) 6.196 + return 0; 6.197 + 6.198 + bzero(dev, sizeof(*dev)); 6.199 + dev->type = type; 6.200 + if (name != NULL) 6.201 + strcpy(dev->name, name); 6.202 + dev->instance = instance; 6.203 + dev->domid = domid; 6.204 + dev->next = priv->devs; 6.205 + priv->devs = dev; 6.206 + 6.207 + /* 6.208 + * Update twice to avoid delta-since-boot. 6.209 + */ 6.210 + if (!update_dev_stats(priv, dev)) 6.211 + return 0; 6.212 + return update_dev_stats(priv, dev); 6.213 +} 6.214 + 6.215 +static int update_nic(priv_data_t *priv, xenstat_domain *dom, 6.216 + xenstat_network *net, const char *name) 6.217 +{ 6.218 + stdevice_t *dev; 6.219 + 6.220 + for (dev = priv->devs; dev != NULL; dev = dev->next) { 6.221 + if (dev->type == DEVICE_NIC && dev->domid == dom->id && 6.222 + strcmp(name, dev->name) == 0) { 6.223 + if (!update_dev_stats(priv, dev)) 6.224 + return 0; 6.225 + net->rbytes = dev->stats[1][0] - dev->stats[0][0]; 6.226 + net->rpackets = dev->stats[1][1] - dev->stats[0][1]; 6.227 + net->rerrs = dev->stats[1][2] - dev->stats[0][2]; 6.228 + net->tbytes = dev->stats[1][3] - dev->stats[0][3]; 6.229 + net->tpackets = dev->stats[1][4] - dev->stats[0][4]; 6.230 + net->terrs = dev->stats[1][5] - dev->stats[0][5]; 6.231 + net->rdrop = dev->stats[1][6] - dev->stats[0][6]; 6.232 + net->tdrop = dev->stats[1][7] - dev->stats[0][7]; 6.233 + return 1; 6.234 + } 6.235 + } 6.236 + 6.237 + return init_dev(priv, DEVICE_NIC, name, 0, dom->id); 6.238 +} 6.239 + 6.240 +static int 6.241 +collect_dom_networks(xenstat_node *node, priv_data_t *priv, xenstat_domain *dom) 6.242 +{ 6.243 + char path[PATH_MAX]; 6.244 + char **vifs; 6.245 + int ret = 1; 6.246 + int nr; 6.247 + int i; 6.248 + 6.249 + snprintf(path, sizeof(path), "/local/domain/%d/device/vif", dom->id); 6.250 + 6.251 + dom->num_networks = 0; 6.252 + free(dom->networks); 6.253 + dom->networks = NULL; 6.254 + 6.255 + vifs = xs_directory(node->handle->xshandle, XBT_NULL, path, &nr); 6.256 + if (vifs == NULL) 6.257 + goto out; 6.258 + 6.259 + dom->num_networks = nr; 6.260 + dom->networks = calloc(nr, sizeof(xenstat_network)); 6.261 + 6.262 + for (i = 0; i < dom->num_networks; i++) { 6.263 + char *tmp; 6.264 + 6.265 + snprintf(path, sizeof(path), 6.266 + "/local/domain/%d/device/vif/%d/backend", dom->id, i); 6.267 + 6.268 + tmp = xs_read(node->handle->xshandle, XBT_NULL, path, NULL); 6.269 + 6.270 + if (tmp == NULL) 6.271 + goto out; 6.272 + 6.273 + snprintf(path, sizeof(path), "%s/nic", tmp); 6.274 + free(tmp); 6.275 + 6.276 + tmp = xs_read(node->handle->xshandle, XBT_NULL, path, NULL); 6.277 + 6.278 + if (tmp == NULL || tmp[0] == '\0') { 6.279 + free(tmp); 6.280 + goto out; 6.281 + } 6.282 + 6.283 + if (!(ret = update_nic(priv, dom, &dom->networks[i], tmp))) { 6.284 + free(tmp); 6.285 + goto out; 6.286 + } 6.287 + 6.288 + free(tmp); 6.289 + } 6.290 + 6.291 + ret = 1; 6.292 +out: 6.293 + free(vifs); 6.294 + return ret; 6.295 +} 6.296 + 6.297 +int xenstat_collect_networks(xenstat_node * node) 6.298 +{ 6.299 + int i; 6.300 + priv_data_t *priv = get_priv_data(node->handle); 6.301 + stdevice_t *dev; 6.302 + 6.303 + if (priv == NULL) 6.304 + return 0; 6.305 + 6.306 + for (dev = priv->devs; dev != NULL; dev = dev->next) 6.307 + dev->used = 0; 6.308 + 6.309 + for (i = 0; i < node->num_domains; i++) { 6.310 + if (node->domains[i].id == 0) 6.311 + continue; 6.312 + if (!collect_dom_networks(node, priv, &node->domains[i])) 6.313 + return 0; 6.314 + } 6.315 + 6.316 + gc_devs(priv, DEVICE_NIC); 6.317 + 6.318 + return 1; 6.319 +} 6.320 + 6.321 +void xenstat_uninit_networks(xenstat_handle *handle) 6.322 +{ 6.323 + xenstat_uninit_devs(handle, DEVICE_NIC); 6.324 +} 6.325 + 6.326 +static int update_xdb(priv_data_t *priv, xenstat_domain *dom, 6.327 + xenstat_vbd *vbd, int instance) 6.328 +{ 6.329 + stdevice_t *dev; 6.330 + 6.331 + for (dev = priv->devs; dev != NULL; dev = dev->next) { 6.332 + if (dev->type == DEVICE_XDB && dev->domid == dom->id && 6.333 + dev->instance == instance) { 6.334 + if (!update_dev_stats(priv, dev)) 6.335 + return 0; 6.336 + vbd->dev = dev->instance; 6.337 + vbd->rd_reqs = dev->stats[1][0] - dev->stats[0][0]; 6.338 + vbd->wr_reqs = dev->stats[1][1] - dev->stats[0][1]; 6.339 + vbd->oo_reqs = dev->stats[1][2] - dev->stats[0][2]; 6.340 + return 1; 6.341 + } 6.342 + } 6.343 + 6.344 + return init_dev(priv, DEVICE_XDB, NULL, instance, dom->id); 6.345 +} 6.346 + 6.347 +static int 6.348 +collect_dom_vbds(xenstat_node *node, priv_data_t *priv, xenstat_domain *dom) 6.349 +{ 6.350 + char path[PATH_MAX]; 6.351 + char **vbds; 6.352 + int ret = 1; 6.353 + int nr; 6.354 + int i; 6.355 + 6.356 + snprintf(path, sizeof(path), "/local/domain/%d/device/vbd", dom->id); 6.357 + 6.358 + dom->num_vbds = 0; 6.359 + free(dom->vbds); 6.360 + dom->vbds = NULL; 6.361 + 6.362 + vbds = xs_directory(node->handle->xshandle, XBT_NULL, path, &nr); 6.363 + if (vbds == NULL) 6.364 + goto out; 6.365 + 6.366 + dom->num_vbds = nr; 6.367 + dom->vbds = calloc(nr, sizeof(xenstat_vbd)); 6.368 + 6.369 + for (i = 0; i < dom->num_vbds; i++) { 6.370 + char *tmp; 6.371 + int inst; 6.372 + 6.373 + snprintf(path, sizeof(path), 6.374 + "/local/domain/%d/device/vbd/%s/backend", dom->id, vbds[i]); 6.375 + 6.376 + tmp = xs_read(node->handle->xshandle, XBT_NULL, path, NULL); 6.377 + 6.378 + if (tmp == NULL) 6.379 + goto out; 6.380 + 6.381 + snprintf(path, sizeof(path), "%s/instance", tmp); 6.382 + free(tmp); 6.383 + 6.384 + tmp = xs_read(node->handle->xshandle, XBT_NULL, path, NULL); 6.385 + 6.386 + /* 6.387 + * Fails when connection is not completed; mark it clearly with 6.388 + * a -1. 6.389 + */ 6.390 + if (tmp == NULL || sscanf(tmp, "%d", &inst) != 1) { 6.391 + dom->vbds[i].dev = -1; 6.392 + free(tmp); 6.393 + goto out; 6.394 + } 6.395 + 6.396 + free(tmp); 6.397 + 6.398 + if (!(ret = update_xdb(priv, dom, &dom->vbds[i], inst))) 6.399 + goto out; 6.400 + } 6.401 + 6.402 +out: 6.403 + free(vbds); 6.404 + return ret; 6.405 +} 6.406 + 6.407 +int xenstat_collect_vbds(xenstat_node * node) 6.408 +{ 6.409 + int i; 6.410 + priv_data_t *priv = get_priv_data(node->handle); 6.411 + stdevice_t *dev; 6.412 + 6.413 + if (priv == NULL) 6.414 + return 0; 6.415 + 6.416 + for (dev = priv->devs; dev != NULL; dev = dev->next) 6.417 + dev->used = 0; 6.418 + 6.419 + for (i = 0; i < node->num_domains; i++) { 6.420 + if (node->domains[i].id == 0) 6.421 + continue; 6.422 + if (!collect_dom_vbds(node, priv, &node->domains[i])) 6.423 + return 0; 6.424 + } 6.425 + 6.426 + gc_devs(priv, DEVICE_XDB); 6.427 + 6.428 + return 1; 6.429 +} 6.430 + 6.431 +void xenstat_uninit_vbds(xenstat_handle * handle) 6.432 +{ 6.433 + xenstat_uninit_devs(handle, DEVICE_XDB); 6.434 +}
7.1 --- a/tools/xenstat/xentop/xentop.c Fri Feb 23 10:43:00 2007 +0000 7.2 +++ b/tools/xenstat/xentop/xentop.c Fri Feb 23 10:47:55 2007 +0000 7.3 @@ -50,7 +50,11 @@ 7.4 #define KEY_ESCAPE '\x1B' 7.5 7.6 #ifdef HOST_SunOS 7.7 -/* Old curses library on Solaris takes non-const strings. */ 7.8 +/* Old curses library on Solaris takes non-const strings. Also, ERR interferes 7.9 + * with curse's definition. 7.10 + */ 7.11 +#undef ERR 7.12 +#define ERR (-1) 7.13 #define curses_str_t char * 7.14 #else 7.15 #define curses_str_t const char * 7.16 @@ -914,7 +918,7 @@ void do_vbd(xenstat_domain *domain) 7.17 for (i=0 ; i< num_vbds; i++) { 7.18 vbd = xenstat_domain_vbd(domain,i); 7.19 7.20 - print("VBD %4u [%2x:%2x] OO: %8llu RD: %8llu WR: %8llu\n", 7.21 + print("VBD %4d [%2x:%2x] OO: %8llu RD: %8llu WR: %8llu\n", 7.22 xenstat_vbd_dev(vbd), 7.23 MAJOR(xenstat_vbd_dev(vbd)), MINOR(xenstat_vbd_dev(vbd)), 7.24 xenstat_vbd_oo_reqs(vbd),