Fix vnet_interface_counters API definition

The api specification had u8 as data type, which caused the python
binding to fail.
Fixes VPP-642

Change-Id: I9ba97959740d44c8f4a12db9356d0d1bcd709a73
Signed-off-by: Aloys Augustin <aloys.augustin@polytechnique.org>
Signed-off-by: Ole Troan <ot@cisco.com>
diff --git a/src/vat/api_format.c b/src/vat/api_format.c
index 495b660..efb71ef 100644
--- a/src/vat/api_format.c
+++ b/src/vat/api_format.c
@@ -2098,17 +2098,21 @@
   vam->combined_interface_counters[vnet_counter_type][sw_if_index] = counter;
 }
 
-static void vl_api_vnet_interface_counters_t_handler
-  (vl_api_vnet_interface_counters_t * mp)
+static void vl_api_vnet_interface_simple_counters_t_handler
+  (vl_api_vnet_interface_simple_counters_t * mp)
 {
   /* not supported */
 }
 
-static void vl_api_vnet_interface_counters_t_handler_json
-  (vl_api_vnet_interface_counters_t * mp)
+static void vl_api_vnet_interface_combined_counters_t_handler
+  (vl_api_vnet_interface_combined_counters_t * mp)
 {
-  interface_counter_t counter;
-  vlib_counter_t *v;
+  /* not supported */
+}
+
+static void vl_api_vnet_interface_simple_counters_t_handler_json
+  (vl_api_vnet_interface_simple_counters_t * mp)
+{
   u64 *v_packets;
   u64 packets;
   u32 count;
@@ -2118,31 +2122,38 @@
   count = ntohl (mp->count);
   first_sw_if_index = ntohl (mp->first_sw_if_index);
 
-  if (!mp->is_combined)
+  v_packets = (u64 *) & mp->data;
+  for (i = 0; i < count; i++)
     {
-      v_packets = (u64 *) & mp->data;
-      for (i = 0; i < count; i++)
-	{
-	  packets =
-	    clib_net_to_host_u64 (clib_mem_unaligned (v_packets, u64));
-	  set_simple_interface_counter (mp->vnet_counter_type,
-					first_sw_if_index + i, packets);
-	  v_packets++;
-	}
+      packets = clib_net_to_host_u64 (clib_mem_unaligned (v_packets, u64));
+      set_simple_interface_counter (mp->vnet_counter_type,
+				    first_sw_if_index + i, packets);
+      v_packets++;
     }
-  else
+}
+
+static void vl_api_vnet_interface_combined_counters_t_handler_json
+  (vl_api_vnet_interface_combined_counters_t * mp)
+{
+  interface_counter_t counter;
+  vlib_counter_t *v;
+  u32 first_sw_if_index;
+  int i;
+  u32 count;
+
+  count = ntohl (mp->count);
+  first_sw_if_index = ntohl (mp->first_sw_if_index);
+
+  v = (vlib_counter_t *) & mp->data;
+  for (i = 0; i < count; i++)
     {
-      v = (vlib_counter_t *) & mp->data;
-      for (i = 0; i < count; i++)
-	{
-	  counter.packets =
-	    clib_net_to_host_u64 (clib_mem_unaligned (&v->packets, u64));
-	  counter.bytes =
-	    clib_net_to_host_u64 (clib_mem_unaligned (&v->bytes, u64));
-	  set_combined_interface_counter (mp->vnet_counter_type,
-					  first_sw_if_index + i, counter);
-	  v++;
-	}
+      counter.packets =
+	clib_net_to_host_u64 (clib_mem_unaligned (&v->packets, u64));
+      counter.bytes =
+	clib_net_to_host_u64 (clib_mem_unaligned (&v->bytes, u64));
+      set_combined_interface_counter (mp->vnet_counter_type,
+				      first_sw_if_index + i, counter);
+      v++;
     }
 }
 
@@ -4118,8 +4129,10 @@
   vat_json_object_add_uint (node, "table_index", ntohl (mp->table_index));
 }
 
-
-
+#define vl_api_vnet_interface_simple_counters_t_endian vl_noop_handler
+#define vl_api_vnet_interface_simple_counters_t_print vl_noop_handler
+#define vl_api_vnet_interface_combined_counters_t_endian vl_noop_handler
+#define vl_api_vnet_interface_combined_counters_t_print vl_noop_handler
 #define vl_api_vnet_ip4_fib_counters_t_endian vl_noop_handler
 #define vl_api_vnet_ip4_fib_counters_t_print vl_noop_handler
 #define vl_api_vnet_ip6_fib_counters_t_endian vl_noop_handler
@@ -4539,7 +4552,8 @@
 
 #define foreach_standalone_reply_msg					\
 _(SW_INTERFACE_SET_FLAGS, sw_interface_set_flags)                       \
-_(VNET_INTERFACE_COUNTERS, vnet_interface_counters)                     \
+_(VNET_INTERFACE_SIMPLE_COUNTERS, vnet_interface_simple_counters)       \
+_(VNET_INTERFACE_COMBINED_COUNTERS, vnet_interface_combined_counters)   \
 _(VNET_IP4_FIB_COUNTERS, vnet_ip4_fib_counters)                         \
 _(VNET_IP6_FIB_COUNTERS, vnet_ip6_fib_counters)                         \
 _(VNET_IP4_NBR_COUNTERS, vnet_ip4_nbr_counters)                         \
diff --git a/src/vnet/interface.api b/src/vnet/interface.api
index 9df63f1..14ff6d5 100644
--- a/src/vnet/interface.api
+++ b/src/vnet/interface.api
@@ -206,21 +206,42 @@
   u32 vrf_id;
 };
 
-/** \brief Stats counters structure 
+typeonly manual_print manual_endian define vlib_counter
+{
+  u64 packets;			/**< packet counter */
+  u64 bytes;			/**< byte counter  */
+};
+
+/** \brief Simple stats counters structure
     @param vnet_counter_type- such as ip4, ip6, punts, etc
-    @param is_combined - rx & tx total (all types) counts   
     @param first_sw_if_index - first sw index in block of index, counts
-    @param count - number of interfaces this stats block includes counters for
-    @param data - contiguous block of vlib_counter_t structures 
+    @param count - number of counters, equal to the number of interfaces in
+      this stats block
+    @param data - contiguous block of u64 counters
 */
-define vnet_interface_counters
+manual_print manual_endian define vnet_interface_simple_counters
 {
   /* enums - plural - in vnet/interface.h */
   u8 vnet_counter_type;
-  u8 is_combined;
   u32 first_sw_if_index;
   u32 count;
-  u8 data[count];
+  u64 data[count];
+};
+
+/** \brief Combined stats counters structure
+    @param vnet_counter_type- such as ip4, ip6, punts, etc
+    @param first_sw_if_index - first sw index in block of index, counts
+    @param count - number of counters, equal to the number of interfaces in
+      this stats block
+    @param data - contiguous block of vlib_counter_t structures
+*/
+manual_print manual_endian define vnet_interface_combined_counters
+{
+  /* enums - plural - in vnet/interface.h */
+  u8 vnet_counter_type;
+  u32 first_sw_if_index;
+  u32 count;
+  vl_api_vlib_counter_t data[count];
 };
 
 /** \brief Set unnumbered interface add / del request
diff --git a/src/vpp/stats/stats.c b/src/vpp/stats/stats.c
index 4309cd5..38821da 100644
--- a/src/vpp/stats/stats.c
+++ b/src/vpp/stats/stats.c
@@ -45,12 +45,13 @@
 #include <vpp/api/vpe_all_api_h.h>
 #undef vl_printfun
 
-#define foreach_stats_msg                               \
-_(WANT_STATS, want_stats)                               \
-_(VNET_INTERFACE_COUNTERS, vnet_interface_counters)     \
-_(VNET_IP4_FIB_COUNTERS, vnet_ip4_fib_counters)         \
-_(VNET_IP6_FIB_COUNTERS, vnet_ip6_fib_counters)         \
-_(VNET_IP4_NBR_COUNTERS, vnet_ip4_nbr_counters)         \
+#define foreach_stats_msg						\
+_(WANT_STATS, want_stats)						\
+_(VNET_INTERFACE_SIMPLE_COUNTERS, vnet_interface_simple_counters)	\
+_(VNET_INTERFACE_COMBINED_COUNTERS, vnet_interface_combined_counters)	\
+_(VNET_IP4_FIB_COUNTERS, vnet_ip4_fib_counters)				\
+_(VNET_IP6_FIB_COUNTERS, vnet_ip6_fib_counters)				\
+_(VNET_IP4_NBR_COUNTERS, vnet_ip4_nbr_counters)				\
 _(VNET_IP6_NBR_COUNTERS, vnet_ip6_nbr_counters)
 
 /* These constants ensure msg sizes <= 1024, aka ring allocation */
@@ -127,7 +128,7 @@
 static void
 do_simple_interface_counters (stats_main_t * sm)
 {
-  vl_api_vnet_interface_counters_t *mp = 0;
+  vl_api_vnet_interface_simple_counters_t *mp = 0;
   vnet_interface_main_t *im = sm->interface_main;
   api_main_t *am = sm->api_main;
   vl_shmem_hdr_t *shmem_hdr = am->shmem_hdr;
@@ -155,9 +156,8 @@
 
 	    mp = vl_msg_api_alloc_as_if_client
 	      (sizeof (*mp) + items_this_message * sizeof (v));
-	    mp->_vl_msg_id = ntohs (VL_API_VNET_INTERFACE_COUNTERS);
+	    mp->_vl_msg_id = ntohs (VL_API_VNET_INTERFACE_SIMPLE_COUNTERS);
 	    mp->vnet_counter_type = cm - im->sw_if_counters;
-	    mp->is_combined = 0;
 	    mp->first_sw_if_index = htonl (i);
 	    mp->count = 0;
 	    vp = (u64 *) mp->data;
@@ -182,7 +182,7 @@
 static void
 do_combined_interface_counters (stats_main_t * sm)
 {
-  vl_api_vnet_interface_counters_t *mp = 0;
+  vl_api_vnet_interface_combined_counters_t *mp = 0;
   vnet_interface_main_t *im = sm->interface_main;
   api_main_t *am = sm->api_main;
   vl_shmem_hdr_t *shmem_hdr = am->shmem_hdr;
@@ -206,9 +206,8 @@
 
 	    mp = vl_msg_api_alloc_as_if_client
 	      (sizeof (*mp) + items_this_message * sizeof (v));
-	    mp->_vl_msg_id = ntohs (VL_API_VNET_INTERFACE_COUNTERS);
+	    mp->_vl_msg_id = ntohs (VL_API_VNET_INTERFACE_COMBINED_COUNTERS);
 	    mp->vnet_counter_type = cm - im->combined_sw_if_counters;
-	    mp->is_combined = 1;
 	    mp->first_sw_if_index = htonl (i);
 	    mp->count = 0;
 	    vp = (vlib_counter_t *) mp->data;
@@ -943,13 +942,13 @@
 }
 
 static void
-vl_api_vnet_interface_counters_t_handler (vl_api_vnet_interface_counters_t *
-					  mp)
+  vl_api_vnet_interface_simple_counters_t_handler
+  (vl_api_vnet_interface_simple_counters_t * mp)
 {
   vpe_client_registration_t *reg;
   stats_main_t *sm = &stats_main;
   unix_shared_memory_queue_t *q, *q_prev = NULL;
-  vl_api_vnet_interface_counters_t *mp_copy = NULL;
+  vl_api_vnet_interface_simple_counters_t *mp_copy = NULL;
   u32 mp_size;
 
 #if STATS_DEBUG > 0
@@ -958,110 +957,154 @@
   int i;
 #endif
 
-  mp_size = sizeof (*mp) + (ntohl (mp->count) *
-			    (mp->is_combined ? sizeof (vlib_counter_t) :
-			     sizeof (u64)));
+  mp_size = sizeof (*mp) + (ntohl (mp->count) * sizeof (u64));
 
   /* *INDENT-OFF* */
   pool_foreach(reg, sm->stats_registrations,
-  ({
-    q = vl_api_client_index_to_input_queue (reg->client_index);
-    if (q)
-      {
-        if (q_prev && (q_prev->cursize < q_prev->maxsize))
-          {
-            mp_copy = vl_msg_api_alloc_as_if_client(mp_size);
-            clib_memcpy(mp_copy, mp, mp_size);
-            vl_msg_api_send_shmem (q_prev, (u8 *)&mp);
-            mp = mp_copy;
-          }
-        q_prev = q;
-      }
-  }));
+	       ({
+		 q = vl_api_client_index_to_input_queue (reg->client_index);
+		 if (q)
+		   {
+		     if (q_prev && (q_prev->cursize < q_prev->maxsize))
+		       {
+			 mp_copy = vl_msg_api_alloc_as_if_client(mp_size);
+			 clib_memcpy(mp_copy, mp, mp_size);
+			 vl_msg_api_send_shmem (q_prev, (u8 *)&mp);
+			 mp = mp_copy;
+		       }
+		     q_prev = q;
+		   }
+	       }));
   /* *INDENT-ON* */
 
 #if STATS_DEBUG > 0
   count = ntohl (mp->count);
   sw_if_index = ntohl (mp->first_sw_if_index);
-  if (mp->is_combined == 0)
-    {
-      u64 *vp, v;
-      vp = (u64 *) mp->data;
+  u64 *vp, v;
+  vp = (u64 *) mp->data;
 
-      switch (mp->vnet_counter_type)
-	{
-	case VNET_INTERFACE_COUNTER_DROP:
-	  counter_name = "drop";
-	  break;
-	case VNET_INTERFACE_COUNTER_PUNT:
-	  counter_name = "punt";
-	  break;
-	case VNET_INTERFACE_COUNTER_IP4:
-	  counter_name = "ip4";
-	  break;
-	case VNET_INTERFACE_COUNTER_IP6:
-	  counter_name = "ip6";
-	  break;
-	case VNET_INTERFACE_COUNTER_RX_NO_BUF:
-	  counter_name = "rx-no-buff";
-	  break;
-	case VNET_INTERFACE_COUNTER_RX_MISS:
-	  , counter_name = "rx-miss";
-	  break;
-	case VNET_INTERFACE_COUNTER_RX_ERROR:
-	  , counter_name = "rx-error (fifo-full)";
-	  break;
-	case VNET_INTERFACE_COUNTER_TX_ERROR:
-	  , counter_name = "tx-error (fifo-full)";
-	  break;
-	default:
-	  counter_name = "bogus";
-	  break;
-	}
-      for (i = 0; i < count; i++)
-	{
-	  v = clib_mem_unaligned (vp, u64);
-	  v = clib_net_to_host_u64 (v);
-	  vp++;
-	  fformat (stdout, "%U.%s %lld\n", format_vnet_sw_if_index_name,
-		   sm->vnet_main, sw_if_index, counter_name, v);
-	  sw_if_index++;
-	}
+  switch (mp->vnet_counter_type)
+    {
+    case VNET_INTERFACE_COUNTER_DROP:
+      counter_name = "drop";
+      break;
+    case VNET_INTERFACE_COUNTER_PUNT:
+      counter_name = "punt";
+      break;
+    case VNET_INTERFACE_COUNTER_IP4:
+      counter_name = "ip4";
+      break;
+    case VNET_INTERFACE_COUNTER_IP6:
+      counter_name = "ip6";
+      break;
+    case VNET_INTERFACE_COUNTER_RX_NO_BUF:
+      counter_name = "rx-no-buff";
+      break;
+    case VNET_INTERFACE_COUNTER_RX_MISS:
+      , counter_name = "rx-miss";
+      break;
+    case VNET_INTERFACE_COUNTER_RX_ERROR:
+      , counter_name = "rx-error (fifo-full)";
+      break;
+    case VNET_INTERFACE_COUNTER_TX_ERROR:
+      , counter_name = "tx-error (fifo-full)";
+      break;
+    default:
+      counter_name = "bogus";
+      break;
+    }
+  for (i = 0; i < count; i++)
+    {
+      v = clib_mem_unaligned (vp, u64);
+      v = clib_net_to_host_u64 (v);
+      vp++;
+      fformat (stdout, "%U.%s %lld\n", format_vnet_sw_if_index_name,
+	       sm->vnet_main, sw_if_index, counter_name, v);
+      sw_if_index++;
+    }
+#endif
+  if (q_prev && (q_prev->cursize < q_prev->maxsize))
+    {
+      vl_msg_api_send_shmem (q_prev, (u8 *) & mp);
     }
   else
     {
-      vlib_counter_t *vp;
-      u64 packets, bytes;
-      vp = (vlib_counter_t *) mp->data;
-
-      switch (mp->vnet_counter_type)
-	{
-	case VNET_INTERFACE_COUNTER_RX:
-	  counter_name = "rx";
-	  break;
-	case VNET_INTERFACE_COUNTER_TX:
-	  counter_name = "tx";
-	  break;
-	default:
-	  counter_name = "bogus";
-	  break;
-	}
-      for (i = 0; i < count; i++)
-	{
-	  packets = clib_mem_unaligned (&vp->packets, u64);
-	  packets = clib_net_to_host_u64 (packets);
-	  bytes = clib_mem_unaligned (&vp->bytes, u64);
-	  bytes = clib_net_to_host_u64 (bytes);
-	  vp++;
-	  fformat (stdout, "%U.%s.packets %lld\n",
-		   format_vnet_sw_if_index_name,
-		   sm->vnet_main, sw_if_index, counter_name, packets);
-	  fformat (stdout, "%U.%s.bytes %lld\n",
-		   format_vnet_sw_if_index_name,
-		   sm->vnet_main, sw_if_index, counter_name, bytes);
-	  sw_if_index++;
-	}
+      vl_msg_api_free (mp);
     }
+}
+
+static void
+  vl_api_vnet_interface_combined_counters_t_handler
+  (vl_api_vnet_interface_combined_counters_t * mp)
+{
+  vpe_client_registration_t *reg;
+  stats_main_t *sm = &stats_main;
+  unix_shared_memory_queue_t *q, *q_prev = NULL;
+  vl_api_vnet_interface_combined_counters_t *mp_copy = NULL;
+  u32 mp_size;
+
+#if STATS_DEBUG > 0
+  char *counter_name;
+  u32 count, sw_if_index;
+  int i;
+#endif
+
+  mp_size = sizeof (*mp) + (ntohl (mp->count) * sizeof (vlib_counter_t));
+
+  /* *INDENT-OFF* */
+  pool_foreach(reg, sm->stats_registrations,
+	       ({
+		 q = vl_api_client_index_to_input_queue (reg->client_index);
+		 if (q)
+		   {
+		     if (q_prev && (q_prev->cursize < q_prev->maxsize))
+		       {
+			 mp_copy = vl_msg_api_alloc_as_if_client(mp_size);
+			 clib_memcpy(mp_copy, mp, mp_size);
+			 vl_msg_api_send_shmem (q_prev, (u8 *)&mp);
+			 mp = mp_copy;
+		       }
+		     q_prev = q;
+		   }
+	       }));
+  /* *INDENT-ON* */
+
+#if STATS_DEBUG > 0
+  count = ntohl (mp->count);
+  sw_if_index = ntohl (mp->first_sw_if_index);
+
+  vlib_counter_t *vp;
+  u64 packets, bytes;
+  vp = (vlib_counter_t *) mp->data;
+
+  switch (mp->vnet_counter_type)
+    {
+    case VNET_INTERFACE_COUNTER_RX:
+      counter_name = "rx";
+      break;
+    case VNET_INTERFACE_COUNTER_TX:
+      counter_name = "tx";
+      break;
+    default:
+      counter_name = "bogus";
+      break;
+    }
+  for (i = 0; i < count; i++)
+    {
+      packets = clib_mem_unaligned (&vp->packets, u64);
+      packets = clib_net_to_host_u64 (packets);
+      bytes = clib_mem_unaligned (&vp->bytes, u64);
+      bytes = clib_net_to_host_u64 (bytes);
+      vp++;
+      fformat (stdout, "%U.%s.packets %lld\n",
+	       format_vnet_sw_if_index_name,
+	       sm->vnet_main, sw_if_index, counter_name, packets);
+      fformat (stdout, "%U.%s.bytes %lld\n",
+	       format_vnet_sw_if_index_name,
+	       sm->vnet_main, sw_if_index, counter_name, bytes);
+      sw_if_index++;
+    }
+
 #endif
   if (q_prev && (q_prev->cursize < q_prev->maxsize))
     {
@@ -1305,6 +1348,10 @@
   return 0;
 }
 
+#define vl_api_vnet_interface_simple_counters_t_endian vl_noop_handler
+#define vl_api_vnet_interface_simple_counters_t_print vl_noop_handler
+#define vl_api_vnet_interface_combined_counters_t_endian vl_noop_handler
+#define vl_api_vnet_interface_combined_counters_t_print vl_noop_handler
 #define vl_api_vnet_ip4_fib_counters_t_endian vl_noop_handler
 #define vl_api_vnet_ip4_fib_counters_t_print vl_noop_handler
 #define vl_api_vnet_ip6_fib_counters_t_endian vl_noop_handler
@@ -1342,7 +1389,8 @@
 #undef _
 
   /* tell the msg infra not to free these messages... */
-  am->message_bounce[VL_API_VNET_INTERFACE_COUNTERS] = 1;
+  am->message_bounce[VL_API_VNET_INTERFACE_SIMPLE_COUNTERS] = 1;
+  am->message_bounce[VL_API_VNET_INTERFACE_COMBINED_COUNTERS] = 1;
   am->message_bounce[VL_API_VNET_IP4_FIB_COUNTERS] = 1;
   am->message_bounce[VL_API_VNET_IP6_FIB_COUNTERS] = 1;
   am->message_bounce[VL_API_VNET_IP4_NBR_COUNTERS] = 1;