Я пытаюсь изменить размер буфера отправки сокета по умолчанию на небольшой размер, , чтобы узнать, как влияет пропускная способность UDP для небольших дейтаграмм UDP. Для этого я использую функцию setsockopt
с опцией SO_SNDBUF
и . Я пытаюсь установить размер буфера 64 байта. Я также использую getsockopt
, чтобы увидеть результат функции setsockopt
.Есть ли способ уменьшить минимальный нижний предел размера буфера отправки сокета?
Вот код, я использую:
int sock_fd;
struct sockaddr_in server_addr;
static int target_port = PORT;
int curr_snd_buff = 0;
int sk_snd_buff = 64;
socklen_t optlen;
if((sock_fd=socket(AF_INET,SOCK_DGRAM,0)) == -1)
fatal("in socket (client_udp)");
memset(&server_addr, 0, sizeof(struct sockaddr_in));
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr=inet_addr(args->a_ip);
server_addr.sin_port=htons(target_port);
if (sk_snd_buff > 0) >{
optlen = sizeof(sk_snd_buff);
// get the default socketh send buffer size
if (getsockopt(sock_fd, SOL_SOCKET, SO_SNDBUF, &curr_snd_buff, &optlen) == -1) {
fatal("getting the socket send buffer");
}
printf("* default socket send buffer: %d\n", curr_snd_buff);
printf("* attempting to change it to: %d\n", sk_snd_buff);
if (setsockopt(sock_fd, SOL_SOCKET, SO_SNDBUF, &sk_snd_buff, optlen) == -1) {
fatal("changing the socket send buffer");
}
if (getsockopt(sock_fd, SOL_SOCKET, SO_SNDBUF, &curr_snd_buff, &optlen) == -1) {
fatal("getting the socket send buffer");
}
printf("* new socket send buffer: %d\n", curr_snd_buff);
}
Но то, что я вижу в том, что существует нижний предел размера буфера, установленного в 4608 байт каждый раз, когда я пытаюсь установить небольшое значение. Вот выход из приведенного выше кода:
- по умолчанию буфера сокета: 212992
- пытается изменить его на: 2304
- новый сокет буфер посылки: 4608
Пробуя различные размеры , Я обнаружил, что это происходит для размеров < = 2304. Для больших размеров, например 2305, я получаю больший размер:
- по умолчанию сокет отправить буфер: 212992
- пытается изменить его на: 2305
- новый сокет отправить буфер: 4610
и для некоторых больших размеров , например 3000, удвоенная размера, что у меня есть запрошенную:
- по умолчанию буфера сокета: 212992
- пытается изменить его на: 3000
- новый сокет отправить буфер: 6000
Просматривая сеть, я обнаружил, что Linux удваивает значение в пределах ядра при его установке и возвращает удвоенное значение, когда вы его запрашиваете: Understanding set/getsockopt SO_SNDBUF
Есть ли способ уменьшить минимальную нижнюю границу размера буфера отправки сокета? Например, чтобы установить его на 64 байта?
'printf (" * попытка изменить его на:% d \ n ", sk_snd_buff);' <- Whoa! Почему эта печать 2304, если sk_snd_buff была инициализирована до 64 и не изменилась после этого? У вас где-то есть повреждение памяти? Вы должны сначала отладить это. – immibis
Минимальный размер фиксируется на 2048 (удваивается). Максимум может быть установлен в '/ proc/sys/net/core/wmem_max'. Я предполагаю, что единственный способ изменить это - взломать ядро. –
Чтобы добавить комментарий, написанный @immibis, что говорит valgrind? – Sebivor