diff mbox series

[RFC,v1,5/6] tools: xentop: show time spent in IRQ and HYP states.

Message ID 20200612002205.174295-6-volodymyr_babchuk@epam.com (mailing list archive)
State New, archived
Headers show
Series Fair scheduling | expand

Commit Message

Volodymyr Babchuk June 12, 2020, 12:22 a.m. UTC
xentop show the values in the header like this:

IRQ Time 0.2s    0.0% HYP Time 1.3s    0.1%

The first value is the total time spent in corresponding mode, the
second value is the instant load percentage, similar to vCPU load
value.

"IRQ" corresponds to time spent in IRQ handler.
"HYP" is the time used by hypervisor for own tasks.

Signed-off-by: Volodymyr Babchuk <volodymyr_babchuk@epam.com>
---
 tools/xenstat/libxenstat/src/xenstat.c      | 12 +++++
 tools/xenstat/libxenstat/src/xenstat.h      |  6 +++
 tools/xenstat/libxenstat/src/xenstat_priv.h |  2 +
 tools/xenstat/xentop/xentop.c               | 54 ++++++++++++++++-----
 4 files changed, 63 insertions(+), 11 deletions(-)
diff mbox series

Patch

diff --git a/tools/xenstat/libxenstat/src/xenstat.c b/tools/xenstat/libxenstat/src/xenstat.c
index 6f93d4e982..30c9d3d2cc 100644
--- a/tools/xenstat/libxenstat/src/xenstat.c
+++ b/tools/xenstat/libxenstat/src/xenstat.c
@@ -162,6 +162,8 @@  xenstat_node *xenstat_get_node(xenstat_handle * handle, unsigned int flags)
 	node->free_mem = ((unsigned long long)physinfo.free_pages)
 	    * handle->page_size;
 
+	node->irq_time = physinfo.irq_time;
+	node->hyp_time = physinfo.hyp_time;
 	node->freeable_mb = 0;
 	/* malloc(0) is not portable, so allocate a single domain.  This will
 	 * be resized below. */
@@ -332,6 +334,16 @@  unsigned long long xenstat_node_cpu_hz(xenstat_node * node)
 	return node->cpu_hz;
 }
 
+unsigned long long xenstat_node_irq_time(xenstat_node * node)
+{
+	return node->irq_time;
+}
+
+unsigned long long xenstat_node_hyp_time(xenstat_node * node)
+{
+	return node->hyp_time;
+}
+
 /* Get the domain ID for this domain */
 unsigned xenstat_domain_id(xenstat_domain * domain)
 {
diff --git a/tools/xenstat/libxenstat/src/xenstat.h b/tools/xenstat/libxenstat/src/xenstat.h
index 76a660f321..8d2e561008 100644
--- a/tools/xenstat/libxenstat/src/xenstat.h
+++ b/tools/xenstat/libxenstat/src/xenstat.h
@@ -80,6 +80,12 @@  unsigned int xenstat_node_num_cpus(xenstat_node * node);
 /* Get information about the CPU speed */
 unsigned long long xenstat_node_cpu_hz(xenstat_node * node);
 
+/* Get information about time spent in IRQ handlers */
+unsigned long long xenstat_node_irq_time(xenstat_node * node);
+
+/* Get information about time spent doing hypervisor work */
+unsigned long long xenstat_node_hyp_time(xenstat_node * node);
+
 /*
  * Domain functions - extract information from a xenstat_domain
  */
diff --git a/tools/xenstat/libxenstat/src/xenstat_priv.h b/tools/xenstat/libxenstat/src/xenstat_priv.h
index 4eb44a8ebb..d259765593 100644
--- a/tools/xenstat/libxenstat/src/xenstat_priv.h
+++ b/tools/xenstat/libxenstat/src/xenstat_priv.h
@@ -48,6 +48,8 @@  struct xenstat_node {
 	unsigned long long tot_mem;
 	unsigned long long free_mem;
 	unsigned int num_domains;
+	unsigned long long irq_time;
+	unsigned long long hyp_time;
 	xenstat_domain *domains;	/* Array of length num_domains */
 	long freeable_mb;
 };
diff --git a/tools/xenstat/xentop/xentop.c b/tools/xenstat/xentop/xentop.c
index ebed070c0f..aaeba81cd9 100644
--- a/tools/xenstat/xentop/xentop.c
+++ b/tools/xenstat/xentop/xentop.c
@@ -496,11 +496,25 @@  static void print_cpu(xenstat_domain *domain)
 	print("%10llu", xenstat_domain_cpu_ns(domain)/1000000000);
 }
 
+/* Helper to calculate CPU load percentage */
+static double calc_time_pct(uint64_t cur_time_ns, uint64_t prev_time_ns)
+{
+	double us_elapsed;
+
+	/* Calculate the time elapsed in microseconds */
+	us_elapsed = ((curtime.tv_sec-oldtime.tv_sec)*1000000.0
+		      +(curtime.tv_usec - oldtime.tv_usec));
+
+	/* In the following, nanoseconds must be multiplied by 1000.0 to
+	 * convert to microseconds, then divided by 100.0 to get a percentage,
+	 * resulting in a multiplication by 10.0 */
+	return ((cur_time_ns - prev_time_ns) / 10.0) / us_elapsed;
+}
+
 /* Computes the CPU percentage used for a specified domain */
 static double get_cpu_pct(xenstat_domain *domain)
 {
 	xenstat_domain *old_domain;
-	double us_elapsed;
 
 	/* Can't calculate CPU percentage without a previous sample. */
 	if(prev_node == NULL)
@@ -510,15 +524,8 @@  static double get_cpu_pct(xenstat_domain *domain)
 	if(old_domain == NULL)
 		return 0.0;
 
-	/* Calculate the time elapsed in microseconds */
-	us_elapsed = ((curtime.tv_sec-oldtime.tv_sec)*1000000.0
-		      +(curtime.tv_usec - oldtime.tv_usec));
-
-	/* In the following, nanoseconds must be multiplied by 1000.0 to
-	 * convert to microseconds, then divided by 100.0 to get a percentage,
-	 * resulting in a multiplication by 10.0 */
-	return ((xenstat_domain_cpu_ns(domain)
-		 -xenstat_domain_cpu_ns(old_domain))/10.0)/us_elapsed;
+	return calc_time_pct(xenstat_domain_cpu_ns(domain),
+						 xenstat_domain_cpu_ns(old_domain));
 }
 
 static int compare_cpu_pct(xenstat_domain *domain1, xenstat_domain *domain2)
@@ -878,6 +885,23 @@  static void print_ssid(xenstat_domain *domain)
 	print("%4u", xenstat_domain_ssid(domain));
 }
 
+/* Computes the Xen time stats in percents */
+static void get_xen_time_stats(double *irq_pct, double *hyp_pct)
+{
+	/* Can't calculate CPU percentage without a previous sample. */
+	if(prev_node == NULL)
+	{
+		*irq_pct = 0.0;
+		*hyp_pct = 0.0;
+		return;
+	}
+
+	*irq_pct = calc_time_pct(xenstat_node_irq_time(cur_node),
+							 xenstat_node_irq_time(prev_node));
+	*hyp_pct = calc_time_pct(xenstat_node_hyp_time(cur_node),
+							 xenstat_node_hyp_time(prev_node));
+}
+
 /* Resets default_width for fields with potentially large numbers */
 void reset_field_widths(void)
 {
@@ -943,6 +967,7 @@  void do_summary(void)
 	         crash = 0, dying = 0, shutdown = 0;
 	unsigned i, num_domains = 0;
 	unsigned long long used = 0;
+	double irq_pct, hyp_pct;
 	xenstat_domain *domain;
 	time_t curt;
 
@@ -975,9 +1000,16 @@  void do_summary(void)
 	      xenstat_node_tot_mem(cur_node)/1024, used/1024,
 	      xenstat_node_free_mem(cur_node)/1024);
 
-	print("CPUs: %u @ %lluMHz\n",
+	print("CPUs: %u @ %lluMHz  ",
 	      xenstat_node_num_cpus(cur_node),
 	      xenstat_node_cpu_hz(cur_node)/1000000);
+
+	get_xen_time_stats(&irq_pct, &hyp_pct);
+	print("IRQ Time %.1fs %6.1f%% HYP Time %.1fs %6.1f%%\n",
+		  xenstat_node_irq_time(cur_node) / 1000000000.0,
+		  irq_pct,
+		  xenstat_node_hyp_time(cur_node) / 1000000000.0,
+		  hyp_pct);
 }
 
 /* Display the top header for the domain table */