Important changes to forums and questions
All forums and questions are now archived. To start a new conversation or read the latest updates go to forums.mbed.com.
10 years, 1 month ago.
Ethernet Interface Speed Up
First a brief description of my project:
I am developing a Data Acquisition System that samples 80 sensors with 14 bit resolution @ 2kHz and saves the information to a file. The sampling period could be anywhere from 30 seconds to 30 minutes which requires that I transmit the information off of the mBed utilizing a medium with appropriate data rates as to avoid backing up the system. After some research / calculation / testing, I determined that the Ethernet interface, which according to mBed has been rated to speeds of (5.852) Mbits/s http://developer.mbed.org/users/emilmont/notebook/networking-libraries-benchmark/ , as the ideal data transmission option for my project given that I may need to transmit the data over relatively long distance (25-50 feet). As the project stands now I anticipate needing rates of 2.5Mbits/sec in order to meet my sample rate requirements.
I have, thus far, established an Ethernet based TCP Socket connection utilizing the mBed as a client and my pc running windows 8 as the server (Python coded). I am using a crossover Ethernet cable and static IP on both server and client, and have been able to transmit packets of "dummy" sensor data over the connection (80x16bit values).
Using Wireshark as well as "kludging" the code from the benchmark program in the aforementioned link, it appears to me that it is taking between 1-2mSec to transmit data from the mBed to the server pc. This is well outside my needs which are illustrated in the following "ideal" timing diagram:
And that brings us to my question.
How can I increase my Ethernet transfer speeds between the mBed and my PC running windows 8???
In order to check my data transfer speeds, I took my first stab at utilizing Wireshark, below is a screenshot from my test:
Of note is that I have all of 1 day experience utilizing this tool, and approximately 1 week of experience implementing TCP Sockets/ That being said, reading this wireshark readout I am perplexed by a couple of things. One is that, as mentioned before, the speed appears to be well below the reported speed of the ethernet capability of the mBed. Using what I suppose to be the acknowledgement from the previous packet transfer as a reference, It appears that the following packet takes 800uSec to transfer, which is already way too much time. Additionally, the following packet seems to be 3 data packets combined into one 480 byte packet, that take an additional 1.3 mSec (the content of these packets has historically proven to be transmitted in this exact configuration across every test). Given that my Python code creates a buffer of 160 bytes and that the mBed transmits 80x16 bit packets, it's odd to me that this is occurring and indicates to me a hangup somewhere. This could all however be due to my relatively limited knowledge of Wireshark and my networking setup. Is it possible that other network connections on my PC, such as my active wireless connection, or firewall or other windows interference's, are delaying my transfer?
I am not oblivious to the fact that the second packet (the one containing three separate packets), equates to about 458.6 uSec per packet which approaches my target speed. Which begs the question, would I be better off sending larger packets in order to reduce overhead that may be slowing my transfer down??? My instincts tell me that this would indeed help, however I am interested in optimizing this process as future iterations of this design will require collecting and transferring even more data within the same frequency range. Given that, I am pursuing any and all methods for increasing my speeds.
Below are the code blocks running on both the client (mBed) and the server (PC...and really bare bones Python). Many of the comments are either lines for debugging or are learning reference I made for myself. Any and all suggestions are appreciated.
mbed client side
/*******************************************************************************************\ \*******************************************************************************************/ #include "mbed.h" #include "EthernetInterface.h" //_____________________________________________________________________________Object Dec EthernetInterface eth; //Requisite Ethernet TCPSocketConnection socket; //Requisite TCP/IP Socket Serial pc(USBTX,USBRX); //For debugging Ticker sampleTick; //Signals beginning of sample period typedef struct packetToSent_s{ //Struct for containing data packets uint16_t data[80]; } packetToSend_t; packetToSend_t dataOut; //_____________________________________________________________________________Prototypes void SampleTick(); //_________________________________________________________________________________Global int tFlag=0; int tCount=0; //_______________________________________________________________________________________Main int main(){ char sDurRx [3]; //Incoming Sample Duration int sDur=0; //Sample Duration in integer form int i=0; eth.init("192.168.1.4","255.255.255.0","192.168.1.1"); // Static IP of 192.168.1.4 eth.connect(); socket.connect("192.168.1.5", 1001); //connect to the PC at the given IP address and socket socket.receive_all(sDurRx,2); sDurRx[2]=0; sDur=atoi(sDurRx); //Converts input sample time to integer int endItAll = sDur*2000; sampleTick.attach(&SampleTick, 0.0005); //Initiate Sample Ticker while(tCount!=endItAll){ if(tFlag==1){ tFlag = 0; //lower the tick flag wait_us(150); //Emulates Sampling Process socket.send_all((char*)&dataOut,sizeof(packetToSend_t)); // send the data } } } //_______________________________________________________________________________________ void SampleTick(){ tFlag = 1; //Raises Tick Flag tCount++; //Increments thhe tick Counter }
Python Server Side
#!/usr/bin/env python import socket import timeit from time import time PACKETS_PER_SEC = 2000 TCP_IP = '192.168.1.5' TCP_PORT = 1001 BUFFER_SIZE = 160 # Normally 1024, but we want fast response, needs to be a power 2 # creates new socket (Address family,Socket Type) s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) s.settimeout(None) #Binds the socket to an address (based on type of address family) s.bind((TCP_IP, TCP_PORT)) #listens for connections made to the socket s.listen(1) #Accepts a connection returns conn = socket object and addr which is address of client conn, addr = s.accept() print ('Connection address:', addr) #Get Sample Time sTime = input("Sample Duration (seconds):") conn.sendall(bytes(sTime, 'UTF-8')); print ("Sample Time Sent") print ("Awaiting Data") while 1: #sTime = time() data = conn.recv(BUFFER_SIZE) #Rx Data in 160 byte packages #eTime = time() - sTime if not data: break print ("received data:", data) #print (eTime) #print (duration) #conn.send(data) # echo conn.close()