Stephen Hemminger's congestion control patch for Linux
Этот коммит содержится в:
родитель
1d560e15c4
Коммит
62bb2588af
2
AUTHORS
2
AUTHORS
@ -27,4 +27,4 @@ Andrew Gallatin <gallatin@gmail.com>
|
||||
* threading fix and non Linux performance improvements
|
||||
|
||||
Stephen Hemminger <shemminger@linux-foundation.org>
|
||||
* Linux scheduler selection and theading improvements
|
||||
* Linux congestion control selection and theading improvements
|
||||
|
@ -170,6 +170,7 @@ typedef struct thread_Settings {
|
||||
iperf_sockaddr local;
|
||||
Socklen_t size_local;
|
||||
nthread_t mTID;
|
||||
char* mCongestion;
|
||||
#if defined( HAVE_WIN32_THREAD )
|
||||
HANDLE mHandle;
|
||||
#endif
|
||||
@ -208,6 +209,7 @@ typedef struct thread_Settings {
|
||||
#define FLAG_NOMULTREPORT 0x00080000
|
||||
#define FLAG_SINGLECLIENT 0x00100000
|
||||
#define FLAG_SINGLEUDP 0x00200000
|
||||
#define FLAG_CONGESTION 0x00400000
|
||||
|
||||
#define isBuflenSet(settings) ((settings->flags & FLAG_BUFLENSET) != 0)
|
||||
#define isCompat(settings) ((settings->flags & FLAG_COMPAT) != 0)
|
||||
@ -233,6 +235,7 @@ typedef struct thread_Settings {
|
||||
// end Active Low
|
||||
#define isSingleClient(settings) ((settings->flags & FLAG_SINGLECLIENT) != 0)
|
||||
#define isSingleUDP(settings) ((settings->flags & FLAG_SINGLEUDP) != 0)
|
||||
#define isCongestionControl(settings) ((settings->flags & FLAG_CONGESTION) != 0)
|
||||
|
||||
#define setBuflenSet(settings) settings->flags |= FLAG_BUFLENSET
|
||||
#define setCompat(settings) settings->flags |= FLAG_COMPAT
|
||||
@ -256,6 +259,7 @@ typedef struct thread_Settings {
|
||||
#define setNoMultReport(settings) settings->flags |= FLAG_NOMULTREPORT
|
||||
#define setSingleClient(settings) settings->flags |= FLAG_SINGLECLIENT
|
||||
#define setSingleUDP(settings) settings->flags |= FLAG_SINGLEUDP
|
||||
#define setCongestionControl(settings) settings->flags |= FLAG_CONGESTION
|
||||
|
||||
#define unsetBuflenSet(settings) settings->flags &= ~FLAG_BUFLENSET
|
||||
#define unsetCompat(settings) settings->flags &= ~FLAG_COMPAT
|
||||
@ -279,6 +283,7 @@ typedef struct thread_Settings {
|
||||
#define unsetNoMultReport(settings) settings->flags &= ~FLAG_NOMULTREPORT
|
||||
#define unsetSingleClient(settings) settings->flags &= ~FLAG_SINGLECLIENT
|
||||
#define unsetSingleUDP(settings) settings->flags &= ~FLAG_SINGLEUDP
|
||||
#define unsetCongestionControl(settings) settings->flags &= ~FLAG_CONGESTION
|
||||
|
||||
|
||||
#define HEADER_VERSION1 0x80000000
|
||||
|
@ -162,6 +162,7 @@ Client specific:\n\
|
||||
-L, --listenport # port to recieve bidirectional tests back on\n\
|
||||
-P, --parallel # number of parallel client threads to run\n\
|
||||
-T, --ttl # time-to-live, for multicast (default 1)\n\
|
||||
--linux-congestion <algo> set TCP congestion control algorithm (Linux only)\n\
|
||||
\n\
|
||||
Miscellaneous:\n\
|
||||
-h, --help print this message and quit\n\
|
||||
|
@ -90,6 +90,21 @@ void SetSocketOptions( thread_Settings *inSettings ) {
|
||||
setsock_tcp_windowsize( inSettings->mSock, inSettings->mTCPWin,
|
||||
(inSettings->mThreadMode == kMode_Client ? 1 : 0) );
|
||||
|
||||
if ( isCongestionControl( inSettings ) ) {
|
||||
#ifdef TCP_CONGESTION
|
||||
Socklen_t len = strlen( inSettings->mCongestion ) + 1;
|
||||
int rc = setsockopt( inSettings->mSock, IPPROTO_TCP, TCP_CONGESTION,
|
||||
inSettings->mCongestion, len);
|
||||
if (rc == SOCKET_ERROR ) {
|
||||
fprintf(stderr, "Attempt to set '%s' congestion control failed: %s\n",
|
||||
inSettings->mCongestion, strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
#else
|
||||
fprintf( stderr, "The -Z option is not available on this operating system\n");
|
||||
#endif
|
||||
}
|
||||
|
||||
// check if we're sending multicast, and set TTL
|
||||
if ( isMulticast( inSettings ) && ( inSettings->mTTL > 0 ) ) {
|
||||
int val = inSettings->mTTL;
|
||||
|
@ -120,6 +120,7 @@ const struct option long_options[] =
|
||||
{"single_udp", no_argument, NULL, 'U'},
|
||||
{"ipv6_domian", no_argument, NULL, 'V'},
|
||||
{"suggest_win_size", no_argument, NULL, 'W'},
|
||||
{"congestion", required_argument, NULL, 'Z'},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
@ -162,12 +163,13 @@ const struct option env_options[] =
|
||||
{"IPERF_SINGLE_UDP", no_argument, NULL, 'U'},
|
||||
{"IPERF_IPV6_DOMAIN", no_argument, NULL, 'V'},
|
||||
{"IPERF_SUGGEST_WIN_SIZE", required_argument, NULL, 'W'},
|
||||
{"IPERF_CONGESTION_CONTROL", required_argument, NULL, 'Z'},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
#define SHORT_OPTIONS()
|
||||
|
||||
const char short_options[] = "1b:c:df:hi:l:mn:o:p:rst:uvw:x:y:B:CDF:IL:M:NP:RS:T:UVW";
|
||||
const char short_options[] = "1b:c:df:hi:l:mn:o:p:rst:uvw:x:y:B:CDF:IL:M:NP:RS:T:UVWZ:";
|
||||
|
||||
/* -------------------------------------------------------------------
|
||||
* defaults
|
||||
@ -664,6 +666,17 @@ void Settings_Interpret( char option, const char *optarg, thread_Settings *mExtS
|
||||
fprintf( stderr, "The -W option is not available in this release\n");
|
||||
break;
|
||||
|
||||
case 'Z':
|
||||
#ifdef TCP_CONGESTION
|
||||
setCongestionControl( mExtSettings );
|
||||
mExtSettings->mCongestion = new char[strlen(optarg)+1];
|
||||
strcpy( mExtSettings->mCongestion, optarg);
|
||||
#else
|
||||
#error fix includes
|
||||
fprintf( stderr, "The -Z option is not available on this operating system\n");
|
||||
#endif
|
||||
break;
|
||||
|
||||
default: // ignore unknown
|
||||
break;
|
||||
}
|
||||
|
Загрузка…
x
Ссылка в новой задаче
Block a user