Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S933173Ab2KESB2 (ORCPT ); Mon, 5 Nov 2012 13:01:28 -0500 Received: from smtp-outbound-1.vmware.com ([208.91.2.12]:54321 "EHLO smtp-outbound-1.vmware.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1754545Ab2KESBY (ORCPT ); Mon, 5 Nov 2012 13:01:24 -0500 Subject: [PATCH 4/6] VSOCK: statistics implementation. To: netdev@vger.kernel.org, linux-kernel@vger.kernel.org, georgezhang@vmware.com, virtualization@lists.linux-foundation.org From: George Zhang Cc: pv-drivers@vmware.com, vm-crosstalk@vmware.com, davem@davemloft.net, gregkh@linuxfoundation.org Date: Mon, 05 Nov 2012 10:01:23 -0800 Message-ID: <20121105180119.21472.15700.stgit@promb-2n-dhcp175.eng.vmware.com> In-Reply-To: <20121105175730.21472.99155.stgit@promb-2n-dhcp175.eng.vmware.com> References: <20121105175730.21472.99155.stgit@promb-2n-dhcp175.eng.vmware.com> User-Agent: StGit/0.15 MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: 7bit Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Length: 8211 Lines: 285 VSOCK stats for VMCI Stream Sockets protocol. Signed-off-by: George Zhang --- net/vmw_vsock/stats.c | 37 ++++++++ net/vmw_vsock/stats.h | 219 +++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 256 insertions(+), 0 deletions(-) create mode 100644 net/vmw_vsock/stats.c create mode 100644 net/vmw_vsock/stats.h diff --git a/net/vmw_vsock/stats.c b/net/vmw_vsock/stats.c new file mode 100644 index 0000000..2d172d5 --- /dev/null +++ b/net/vmw_vsock/stats.c @@ -0,0 +1,37 @@ +/* + * VMware vSockets Driver + * + * Copyright (C) 2009-2012 VMware, Inc. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the Free + * Software Foundation version 2 and no later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + */ + +/* + * stats.c -- + * + * Linux stats for the VMCI Stream Sockets protocol. + */ + +#include + +#include +#include /* for NULL */ +#include + +#include "af_vsock.h" +#include "stats.h" + +#ifdef VSOCK_GATHER_STATISTICS +u64 vsock_stats_ctl_pkt_count[VSOCK_PACKET_TYPE_MAX]; +u64 vsock_stats_consume_queue_hist[VSOCK_NUM_QUEUE_LEVEL_BUCKETS]; +u64 vsock_stats_produce_queue_hist[VSOCK_NUM_QUEUE_LEVEL_BUCKETS]; +atomic64_t vsock_stats_consume_total; +atomic64_t vsock_stats_produce_total; +#endif diff --git a/net/vmw_vsock/stats.h b/net/vmw_vsock/stats.h new file mode 100644 index 0000000..2f9d44c --- /dev/null +++ b/net/vmw_vsock/stats.h @@ -0,0 +1,219 @@ +/* + * VMware vSockets Driver + * + * Copyright (C) 2009-2012 VMware, Inc. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the Free + * Software Foundation version 2 and no later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + */ + +/* + * stats.h -- + * + * Stats functions for Linux vsock module. + */ + +#ifndef __STATS_H__ +#define __STATS_H__ + +#include + +#include "vsock_common.h" +#include "vsock_packet.h" + +/* + * Define VSOCK_GATHER_STATISTICS to turn on statistics gathering. Currently + * this consists of 3 types of stats: 1. The number of control datagram + * messages sent. 2. The level of queuepair fullness (in 10% buckets) whenever + * data is about to be enqueued or dequeued from the queuepair. 3. The total + * number of bytes enqueued/dequeued. + */ + +#ifdef VSOCK_GATHER_STATISTICS + +#define VSOCK_NUM_QUEUE_LEVEL_BUCKETS 10 +extern u64 vsock_stats_ctl_pkt_count[VSOCK_PACKET_TYPE_MAX]; +extern u64 vsock_stats_consume_queue_hist[VSOCK_NUM_QUEUE_LEVEL_BUCKETS]; +extern u64 vsock_stats_produce_queue_hist[VSOCK_NUM_QUEUE_LEVEL_BUCKETS]; +extern atomic64_t vsock_stats_consume_total; +extern atomic64_t vsock_stats_produce_total; + +#define VSOCK_STATS_STREAM_CONSUME_HIST(vsk) \ + vsock_vmci_stats_update_queue_bucket_count((vsk)->qpair, \ + (vsk)->consume_size, \ + vmci_qpair_consume_buf_ready((vsk)->qpair), \ + vsock_stats_consume_queue_hist) +#define VSOCK_STATS_STREAM_PRODUCE_HIST(vsk) \ + vsock_vmci_stats_update_queue_bucket_count((vsk)->qpair, \ + (vsk)->produce_size, \ + vmci_qpair_produce_buf_ready((vsk)->qpair), \ + vsock_stats_produce_queue_hist) +#define VSOCK_STATS_CTLPKT_LOG(pkt_type) \ + do { \ + ++vsock_stats_ctl_pkt_count[pkt_type]; \ + } while (0) +#define VSOCK_STATS_STREAM_CONSUME(bytes) \ + atomic64_add(&vsock_stats_consume_total, bytes) +#define VSOCK_STATS_STREAM_PRODUCE(bytes) \ + atomic64_add(&vsock_stats_produce_total, bytes) +#define VSOCK_STATS_CTLPKT_DUMP_ALL() vsock_vmci_stats_ctl_pkt_dump_all() +#define VSOCK_STATS_HIST_DUMP_ALL() vsock_vmci_stats_hist_dump_all() +#define VSOCK_STATS_TOTALS_DUMP_ALL() vsock_vmci_stats_totals_dump_all() +#define VSOCK_STATS_RESET() vsock_vmci_stats_reset() + +/* + * + * vsock_vmci_stats_update_queue_bucket_count -- + * + * Given a queue, determine how much data is enqueued and add that to the + * specified queue level statistic bucket. + * + * Results: None. + * + * Side effects: None. + */ + +static inline void +vsock_vmci_stats_update_queue_bucket_count(vmci_qpair *qpair, + u64 queue_size, + u64 data_ready, + u64 queue_hist[]) +{ + u64 bucket = 0; + u32 remainder = 0; + + /* + * We can't do 64 / 64 = 64 bit divides on linux because it requires a + * libgcc which is not linked into the kernel module. Since this code + * is only used by developers we just limit the queue_size to be less + * than MAX_UINT for now. + */ + ASSERT(queue_size <= MAX_UINT32); + Div643264(data_ready * 10, queue_size, &bucket, &remainder); + ASSERT(bucket < VSOCK_NUM_QUEUE_LEVEL_BUCKETS); + ++queue_hist[bucket]; +} + +/* + * + * vsock_vmci_stats_ctl_pkt_dump_all -- + * + * Prints all stream control packet counts out to the console using the + * appropriate platform logging. + * + * Results: None. + * + * Side effects: None. + */ + +static inline void vsock_vmci_stats_ctl_pkt_dump_all(void) +{ + int index; + + ASSERT_ON_COMPILE(VSOCK_PACKET_TYPE_MAX == + ARRAY_SIZE(vsock_stats_ctl_pkt_count)); + + for (index = 0; index < ARRAY_SIZE(vsock_stats_ctl_pkt_count); + index++) { + pr_info("Control packet: Type = %u, Count = %" FMT64 + "u\n", index, vsock_stats_ctl_pkt_count[index]); + } +} + +/* + * + * vsock_vmci_stats_hist_dump_all -- + * + * Prints the produce and consume queue histograms to the console. + * + * Results: None. + * + * Side effects: None. + */ + +static inline void vsock_vmci_stats_hist_dump_all(void) +{ + int index; + +#define VSOCK_DUMP_HIST(strname, name) do { \ + for (index = 0; index < ARRAY_SIZE(name); index++) { \ + printk(strname " Bucket count %u = %"FMT64"u\n", \ + index, name[index]); \ + } \ + } while (0) + + VSOCK_DUMP_HIST("Produce Queue", vsock_stats_produce_queue_hist); + VSOCK_DUMP_HIST("Consume Queue", vsock_stats_consume_queue_hist); + +#undef VSOCK_DUMP_HIST +} + +/* + * + * vsock_vmci_stats_totals_dump_all -- + * + * Prints the produce and consume totals. + * + * Results: None. + * + * Side effects: None. + */ + +static inline void vsock_vmci_stats_totals_dump_all(void) +{ + pr_info("Produced %" FMT64 "u total bytes\n", + atomic64_read(&vsock_stats_produce_total)); + pr_info("Consumed %" FMT64 "u total bytes\n", + atomic64_read(&vsock_stats_consume_total)); +} + +/* + * + * vsock_vmci_stats_reset -- + * + * Reset all VSock statistics. + * + * Results: None. + * + * Side effects: None. + */ + +static inline void vsock_vmci_stats_reset(void) +{ + int index; + +#define VSOCK_RESET_ARRAY(name) do { \ + for (index = 0; index < ARRAY_SIZE(name); index++) { \ + name[index] = 0; \ + } \ + } while (0) + + VSOCK_RESET_ARRAY(vsock_stats_ctl_pkt_count); + VSOCK_RESET_ARRAY(vsock_stats_produce_queue_hist); + VSOCK_RESET_ARRAY(vsock_stats_consume_queue_hist); + +#undef VSOCK_RESET_ARRAY + + atomic64_set(&vsock_stats_consume_total, 0); + atomic64_set(&vsock_stats_produce_total, 0); +} + +#else +#define VSOCK_STATS_STREAM_CONSUME_HIST(vsk) +#define VSOCK_STATS_STREAM_PRODUCE_HIST(vsk) +#define VSOCK_STATS_STREAM_PRODUCE(bytes) +#define VSOCK_STATS_STREAM_CONSUME(bytes) +#define VSOCK_STATS_CTLPKT_LOG(pkt_type) +#define VSOCK_STATS_CTLPKT_DUMP_ALL() +#define VSOCK_STATS_HIST_DUMP_ALL() +#define VSOCK_STATS_TOTALS_DUMP_ALL() +#define VSOCK_STATS_RESET() +#endif + +#endif -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/