Skip to Content.
Sympa Menu

ndt-dev - [ndt-dev] [ndt] r843 committed - Adds the missing files, merging ndt-web10g branch into trunk.

Subject: NDT-DEV email list created

List archive

[ndt-dev] [ndt] r843 committed - Adds the missing files, merging ndt-web10g branch into trunk.


Chronological Thread 
  • From:
  • To:
  • Subject: [ndt-dev] [ndt] r843 committed - Adds the missing files, merging ndt-web10g branch into trunk.
  • Date: Tue, 15 Oct 2013 12:40:54 +0000

Revision: 843
Author:

Date: Tue Oct 15 12:40:39 2013 UTC
Log: Adds the missing files, merging ndt-web10g branch into trunk.
http://code.google.com/p/ndt/source/detail?r=843

Added:
/trunk/README_WEB10G
/trunk/src/web10g-util.c

=======================================
--- /dev/null
+++ /trunk/README_WEB10G Tue Oct 15 12:40:39 2013 UTC
@@ -0,0 +1,87 @@
+ ndt-web10g
+
+Required libraries:
+
+Web10G
+Download and install the latest userland and your kernel patch from
+http://web10g.org. You will need the use the Web10G userland-2.0.6.2
+(as at time of writing the newest release).
+
+This is known/expected to work with the following web10g kernel patches:
+Web10G-0.6.2-patches (Linux kernel 3.6, 3.7 & 3.8).
+Web10G-0.4-3.5-patch - You will have to make a small modification
+
+IMPORTANT - Web10G-0.4-3.5-patch modification
+Swap the single occurrence of ktime_to_ns(...) to ktime_to_us(...)
+before applying the patch.
+
+This will not work with the 3.2 kernel patch or earlier. Try running
+the sample applications included in the 2.0.6.2 userland, if these do
+not work the kernel patch your using doesn't support this userland
+and cannot be used.
+
+Although you only need the library installed to build, the patched
+web10g kernel is required to run the server, reading a log file on the
+other hand should be ok with the kernel patch. REMEMBER to modprobe
+tcp_estats_nl first and you'll most likely need sudo permissions to run
+the server.
+
+I2Util
+Grab the copy included in the ndt-3.6.5.1 release in the ndt google
+code project page. https://ndt.googlecode.com/files/ndt-3.6.5.1.tar.gz
+Or from svn here
+Build Instructions:
+
+Should be as simple as
+./bootstrap
+./configure
+make
+
+Web100 is still fully supported and if Web100 libs are found web100srv
+will also be built.
+
+Running:
+Unlike web100srv, web10gsrv doesn't require the variable name file and
+this will be ignored (-f option). Besides that the two work alike.
+
+The client web100clt can be used with both the Web10G and Web100
+servers. Only very minor changes have been made - such that the
+original ndt-web100 client should work correctly with both versions of
+the server.
+
+genplot is for web100 snaps where as genplot10g works with Web10G.
+
+I've tested with Linux 3.5.1 kernel patched with web10g
+Web10G-0.4-3.5-patch(modified)
+- There are some issues with logging Web10G Vars.
+
+Linux 3.8.8 kernel with web10g web10g-0.6.2-3.8.patch.
+- Works well.
+
+Known issues:
+Web10G related
+* Web10g kernel patch not quite right - 3.5 kernel patch need to swap
+ ktime_to_ns to ktime_to_us.
+* Logging using the 3.5 kernel patch doesn't work perfectly. Timestamps
+ and addresses are NOT recorded.
+* Server, Client(C and Java Applet) and genplot have been ported.
+ Other tools don't appear to rely upon the web100/10g library.
+
+Other
+* Running the server without a DNS server can cause tests to timeout and
+ fail. Add the NI_NUMERICHOST flag into the getnameinfo call within
+ _I2AddrSetNodePort() in the I2Util library to fix.
+* MSS incorrectly detecting modification when testing via IPv6??
+* A general ndt problem 10Gig connections may overflow integer values
+ and hence results may not be accurate - let us know if you notice
+ this happening.
+
+Reporting Issues:
+
+The best place to go for help is the

mailing
+list.
+
+Or to myself

(Richard Sanger).
+
+
+My work has been funded by The University of Waikato/The WAND group.
=======================================
--- /dev/null
+++ /trunk/src/web10g-util.c Tue Oct 15 12:40:39 2013 UTC
@@ -0,0 +1,301 @@
+/**
+ * A handful of functions to handle some Web10G specific stuff.
+ * This provides some functions similar to those in the Web100 library
+ * for Web10G.
+ *
+ * Naming conventions
+ * web10g_* for functions added to ndt that extend the Web10G library,
+ * like everything in this file. The actual Web10G library uses
+ * estats_*.
+ *
+ * tcp_stat_* is used for types and functions intended to be used
+ * interchangably between web10g and web100.
+ *
+ * Author: Richard Sanger
+ *

+ */
+
+#include "web100srv.h"
+#include "logging.h"
+#include "utils.h"
+
+/**
+ * Find the web10g connection number related to a given socket.
+ *
+ * @param client A web10g client
+ * @param sockfd The socket file descriptor
+ *
+ * @return The connection number if successful. If an error occurs -1
+ * will be returned.
+ *
+ */
+int web10g_connection_from_socket(tcp_stat_agent* client, int sockfd) {
+ struct sockaddr_storage local_name;
+ struct sockaddr_storage peer_name;
+ socklen_t local_name_len = sizeof(local_name);
+ socklen_t peer_name_len = sizeof(peer_name);
+ int connection_id = -1;
+ struct estats_connection_list* clist = NULL;
+ struct estats_list* list_pos;
+
+ /* Get the ip address of ourself on the localsocket */
+ if (getsockname(sockfd, (struct sockaddr*) &local_name,
+ &local_name_len) == -1) {
+ log_println(1, "getsockname() failed: %s ", strerror(errno));
+ return -1;
+ }
+ /* IPv6 socket connected to IPv4? Convert to a real IPv4 address */
+ ipv4mapped_to_ipv4(&local_name);
+
+ /* Get the ip address of our peer */
+ if (getpeername(sockfd, (struct sockaddr*) &peer_name,
+ &peer_name_len) == -1) {
+ log_println(1, "getpeername() failed: %s ", strerror(errno));
+ return -1;
+ }
+ ipv4mapped_to_ipv4(&peer_name);
+
+ /* We have our sockaddrs so find the match in the Web10g table */
+ estats_connection_list_new(&clist);
+ estats_list_conns(clist, client);
+
+
+ ESTATS_LIST_FOREACH(list_pos, &(clist->connection_head)) {
+ struct estats_connection* cp =
+ ESTATS_LIST_ENTRY(list_pos, estats_connection, list);
+ struct estats_connection_tuple* ct =
+ (struct estats_connection_tuple*) cp;
+
+ if (local_name.ss_family == AF_INET &&
+ peer_name.ss_family == AF_INET &&
+ ct->local_addr[16] == ESTATS_ADDRTYPE_IPV4 &&
+ ct->rem_addr[16] == ESTATS_ADDRTYPE_IPV4) {
+ /* All IPv4 - compare addresses */
+ struct sockaddr_in * ipv4_local =
+ (struct sockaddr_in *) &local_name;
+ struct sockaddr_in * ipv4_peer =
+ (struct sockaddr_in *) &peer_name;
+
+ /* Compare local and remote ports and addresses */
+ if (ct->local_port == ntohs(ipv4_local->sin_port) &&
+ ct->rem_port == ntohs(ipv4_peer->sin_port) &&
+ ((struct in_addr*) ct->rem_addr)->s_addr ==
+ ipv4_peer->sin_addr.s_addr &&
+ ((struct in_addr*) ct->local_addr)->s_addr ==
+ ipv4_local->sin_addr.s_addr ) {
+ /* Found it */
+ connection_id = ct->cid;
+ log_println(2, "Matched socket to web10g IPv4 connection #%d",
+ connection_id);
+ goto Cleanup;
+ }
+ } else if (local_name.ss_family == AF_INET6 &&
+ peer_name.ss_family == AF_INET6 &&
+ ct->local_addr[16] == ESTATS_ADDRTYPE_IPV6 &&
+ ct->rem_addr[16] == ESTATS_ADDRTYPE_IPV6) {
+ /* We are IPv6 - compare addresses */
+ struct sockaddr_in6 * ipv6_local =
+ (struct sockaddr_in6 *) &local_name;
+ struct sockaddr_in6 * ipv6_peer =
+ (struct sockaddr_in6 *) &peer_name;
+
+ /* Compare local and remote ports and addresses */
+ if (ct->local_port == ntohs(ipv6_local->sin6_port) &&
+ ct->rem_port == ntohs(ipv6_peer->sin6_port) &&
+ memcmp(ct->rem_addr, ipv6_peer->sin6_addr.s6_addr,
+ sizeof(struct in6_addr)) == 0 &&
+ memcmp(ct->local_addr, ipv6_local->sin6_addr.s6_addr,
+ sizeof(struct in6_addr)) == 0) {
+ /* Found it */
+ connection_id = ct->cid;
+ log_println(2, "Matched socket to web10g IPv6 connection #%d",
+ connection_id);
+ goto Cleanup;
+ }
+ }
+ }
+
+ Cleanup:
+ estats_connection_list_free(&clist);
+ return connection_id;
+}
+
+/**
+ * Get the remote address given connection number
+ *
+ * @param client Web10g client
+ * @param conn The web10g connection number
+ * @param out A pointer to a character buffer, into which the remote
+ * address will be returned if successful. Upon error the contents are
+ * remain unchanged.
+ * @param size The size of the buffer 'out'.
+ *
+ * @return int 0 if successful otherwise 1 in the event of an error
+ * (The connection could not be found).
+ *
+ */
+int web10g_get_remote_addr(tcp_stat_agent* client,
+ tcp_stat_connection conn, char* out, int size) {
+ struct estats_connection_list* clist = NULL;
+ struct estats_list* list_pos;
+
+ estats_connection_list_new(&clist);
+ estats_list_conns(clist, client);
+ out[0] = 0;
+
+ ESTATS_LIST_FOREACH(list_pos, &(clist->connection_head)) {
+ struct estats_connection* cp =
+ ESTATS_LIST_ENTRY(list_pos, estats_connection, list);
+ struct estats_connection_tuple* ct =
+ (struct estats_connection_tuple*) cp;
+
+ if (ct->cid == conn) {
+ if (ct->local_addr[16] == ESTATS_ADDRTYPE_IPV4) {
+ inet_ntop(AF_INET, &(ct->rem_addr[0]), out, size);
+ log_println(1, "Got remote address IPv4 %s", out);
+ goto Cleanup;
+ } else if (ct->local_addr[16] == ESTATS_ADDRTYPE_IPV6) {
+ inet_ntop(AF_INET6, &(ct->rem_addr[0]), out, size);
+ log_println(1, "Got remote address IPv6 %s", out);
+ goto Cleanup;
+ }
+ }
+ }
+
+ Cleanup:
+ estats_connection_list_free(&clist);
+ return out[0] == 0 ? 1 : 0;
+}
+
+/**
+ * Find the specified web10g variables value within a provided capture.
+ * Similar to web10g_get_val except this works on a previously retrieved
+ * set of data.
+ *
+ * This also handle some special cases to get web100 variables that
+ * no longer exist in web10g namely:
+ * MaxCwnd = MAX(MaxSsCwnd, MaxCaCwnd)
+ * AckSegsIn = SegsIn - DataSegsIn
+ * AckSegsOut = SegsOut - DataSegsOut
+ *
+ * @param data A web10g data capture
+ * @param name The web10g variable name
+ * @param *value A pointer to a web10g value structure. If successful
+ * this will contain the requested value upon return. If an error occurs
+ * its contents will remain untouched.
+ *
+ * @return the type if successful otherwise -1 in the event of an error
+ * (including the case the specified value cannot be found).
+ *
+ */
+int web10g_find_val(const tcp_stat_snap* data, const char* name,
+ struct estats_val* value) {
+ int i;
+
+ if (data == NULL || name == NULL || value == NULL)
+ return -1;
+
+ /* Special cases for old web100 variables that no longer have a direct
+ * mapping (i.e. must be calculated from others) */
+
+ if (strcmp(name, "MaxCwnd") == 0) {
+ /* = MAX(MaxSsCwnd, MaxCaCwnd) */
+ struct estats_val ss = {0};
+ struct estats_val ca = {0};
+ int type;
+ /* Types should be the same, failing that an error (-1) will take
+ * presidence when or'd (uv32's) */
+ type = web10g_find_val(data, "MaxSsCwnd", &ss);
+ type |= web10g_find_val(data, "MaxCaCwnd", &ca);
+ /* Get the max of the two */
+ if (ss.uv32 > ca.uv32) {
+ value->uv64 = ss.uv64;
+ value->masked = ss.masked;
+ } else {
+ value->uv64 = ca.uv64;
+ value->masked = ca.masked;
+ }
+ return type;
+ }
+
+ if (strcmp(name, "AckSegsIn") == 0) {
+ /* = SegsIn - DataSegsIn */
+ struct estats_val si = {0};
+ struct estats_val dsi = {0};
+ int type;
+ /* Both uv32's */
+ type = web10g_find_val(data, "SegsIn", &si);
+ type |= web10g_find_val(data, "DataSegsIn", &dsi);
+
+ value->masked = 0;
+ value->uv32 = si.uv32 - dsi.uv32;
+ return type;
+ };
+
+ if (strcmp(name, "AckSegsOut") == 0) {
+ /* = SegsOut - DataSegsOut */
+ struct estats_val so = {0};
+ struct estats_val dso = {0};
+ int type;
+ /* Both uv32's */
+ type = web10g_find_val(data, "SegsOut", &so);
+ type |= web10g_find_val(data, "DataSegsOut", &dso);
+
+ value->masked = 0;
+ value->uv32 = so.uv32 - dso.uv32;
+ return type;
+ };
+
+ for (i = 0; i < data->length; i++) {
+ if (data->val[i].masked) continue;
+
+ if (strcmp(estats_var_array[i].name, name) == 0) {
+ value->uv64 = data->val[i].uv64;
+ value->masked = data->val[i].masked; /* = 0*/
+ return estats_var_array[i].valtype;
+ }
+ }
+ log_println(0, "WARNING: Web10G failed to find name=%s", name);
+ return -1;
+}
+
+/**
+ * Find the specified web10g variable given a connection at the current
+ * time.
+ * Similar to web10g_find_val except this also retrieves data from web10g
+ * rather than from a provided capture. If many variables are being read
+ * it's probably best to capture the data then use web10g_find_val.
+ *
+ * @param data A web10g data capture
+ * @param name The web10g variable name
+ * @param *value A pointer to a web10g value structure. If successful
+ * this will contain the requested value upon return. If an error occurs
+ * it's contents will remain untouched.
+ *
+ * @return the type if successful otherwise -1 in the event of an error
+ * (including the case the specified value cannot be found).
+ *
+ */
+int web10g_get_val(tcp_stat_agent* client, tcp_stat_connection conn,
+ const char* name, struct estats_val* value) {
+ int ret;
+ estats_error* err;
+ estats_val_data* data = NULL;
+
+ if ((err = estats_val_data_new(&data)) != NULL) {
+ estats_error_print(stderr, err);
+ estats_error_free(&err);
+ return -1;
+ }
+
+ if ((err = estats_read_vars(data, conn, client)) != NULL) {
+ estats_error_print(stderr, err);
+ estats_error_free(&err);
+ estats_val_data_free(&data);
+ return -1;
+ }
+
+ ret = web10g_find_val(data, name, value);
+ estats_val_data_free(&data);
+ return ret;
+}


  • [ndt-dev] [ndt] r843 committed - Adds the missing files, merging ndt-web10g branch into trunk., ndt, 10/15/2013

Archive powered by MHonArc 2.6.16.

Top of Page