Reduce TCP maximum segment size (MSS) in Linux on a socket -
in special application in our server needs update firmware of low-on-resource sensor/tracking devices encountered problem in data lost in remote devices (clients) receiving packets of new firmware. connection tcp/ip on gprs network. devices use sim900 gsm chip network interface.
the problems possibly come because of device receiving data. tried reducing traffic sending packages more error still occured.
we contacted local retailer of sim900 chip responsible giving technical support , possibly contacting chinese manufacturer (simcom) of chip. said @ first should try reduce tcp mss (maximum segment size) of our connection.
in our server did following:
static int create_master_socket(unsigned short master_port) { static struct sockaddr_in master_address; int master_socket = socket(af_inet,sock_stream,0); if(!master_socket) { perror("socket"); throw runtime_error("failed create master socket."); } int tr=1; if(setsockopt(master_socket,sol_socket,so_reuseaddr,&tr,sizeof(int))==-1) { perror("setsockopt"); throw runtime_error("failed set so_reuseaddr on master socket"); } master_address.sin_family = af_inet; master_address.sin_addr.s_addr = inaddr_any; master_address.sin_port = htons(master_port); uint16_t tcp_maxseg; socklen_t tcp_maxseg_len = sizeof(tcp_maxseg); if(getsockopt(master_socket, ipproto_tcp, tcp_maxseg, &tcp_maxseg, &tcp_maxseg_len)) { log_error << "failed tcp_maxseg master socket. reason: " << errno; perror("getsockopt"); } else { log_info << "tcp_maxseg: " << tcp_maxseg; } tcp_maxseg = 256; if(setsockopt(master_socket, ipproto_tcp, tcp_maxseg, &tcp_maxseg, tcp_maxseg_len)) { log_error << "failed set tcp_maxseg master socket. reason: " << errno; perror("setsockopt"); } else { log_info << "tcp_maxseg: " << tcp_maxseg; } if(getsockopt(master_socket, ipproto_tcp, tcp_maxseg, &tcp_maxseg, &tcp_maxseg_len)) { log_error << "failed tcp_maxseg master socket. reason: " << errno; perror("getsockopt"); } else { log_info << "tcp_maxseg: " << tcp_maxseg; } if(bind(master_socket, (struct sockaddr*)&master_address, sizeof(master_address))) { perror("bind"); close(master_socket); throw runtime_error("failed bind master_socket port"); } return master_socket; }
running above code results in:
i0807 ... main.cpp:267] tcp_maxseg: 536 e0807 ... main.cpp:271] failed set tcp_maxseg master socket. reason: 22 setsockopt: invalid argument i0807 ... main.cpp:280] tcp_maxseg: 536
as may see, problem in second line of output: setsockopt returns "invalid argument".
why happen? read constraints in setting tcp_maxseg did not encounter report on such behaviour this.
thanks, dennis
unless otherwise noted, optval pointer int.
but you're using u_int16. don't see saying parameter isn't int.
edit: yeah, here source code , can see:
637 if (optlen < sizeof(int)) 638 return -einval;
Comments
Post a Comment