LINUX.ORG.RU

Номера дескрипторов и select

 ,


0

3

Есть приложение, которое открывает больше 1000 дескрипторов файлов\сокетов.

В этом приложении используется сторонняя библиотека, которая вызывает select. Библиотека может открывать и закрывать сокеты по ходу работы.

В select есть баг (документированный), что он не работает с сокетами, дескриптор которого больше 1024 - man select, BUGS.

Можно ли как-то исхитриться, чтобы «зарезервировать» нижние номера дескрипторов для этой библиотеки (т.е. когда библиотека открывает сокет внутри себя, чтобы этому сокету достался дескриптор из «пула», с номером меньше 1024)?

Вариант отдельного процесса понятен. Есть ли другие варианты?

★★★

В select есть баг (документированный), что он не работает с сокетами, дескриптор которого больше 1024 - man select, BUGS.

Нет там бага, ты невнимательно читал ман. select умеет мониторить любые дескрипторы. Проблема у него в другом - он принципиально медленный если у тебя много сокетов.

Аргументы селекта - это битовые маски, а их длина (в битах) указана в первом аргументе. fd_set и макросы к нему - обёртка из glibc, ей вообще не обязательно пользоваться.

Но поддержу вышеотписавшихся - вместо того чтоб фиксить эту библиотеку, лучше найди другую или напиши свою.

firkax ★★★★★
()
Последнее исправление: firkax (всего исправлений: 1)
int move1k(int fd) {
    if (fd == -1) return -1;
    int newfd = fcntl(fd, F_DUPFD, 1024);
    close(fd);
    return newfd;
}
int open1k(const char *path, int flags, mode_t mode) {
    return move1k(open(path, flags, mode));
}
int socket1k(int domain, int type, int protocol) {
    return move1k(socket(domain, type, protocol));
}
int accept1k(int listenfd, struct sockaddr *addr, socklen_t *addrlen) {
    return move1k(accept(listenfd, addr, addrlen));
}

Используй в программе вместо open(), socket(), accept(), а библиотека продолжит использовать обычные open(), socket(), accept().

iliyap ★★★★★
()

Конкретные номера дескрипторов - это детали реализации и ядра, и если приложению нужно лезть в эти детали, что-то фундаментальное не то с таким приложением. Относительно уверенным можно только быть о номерах стандартных ввода/вывода/ошибок.

seiken ★★★★★
()

Отдельный процесс, или меняйте линукс на солярку - там ограничение порядка 65000 с чем-то для select. Или замените select на poll - почти то же самое будет, и тогда ограничение снимется.

anonymous
()
  1. выбросить библиотеку
  2. разбить её на несколько инстансов, тредов, процессов.

Учитывая какая она плохая, скорее всего у неё внутри глобальная переменная, поэтому просто тред не будет работать.

Вполне возможно завести пачку форков по 300 сокетов в каждом и там селектить, а потом собирать всё в нормальном коде.

Короче, есть возможность сделать монструозно сложную и интересную конструкцию, а можно грустно и нудно подпатчить библиотеку или её продавцу сунуть в нос то, что надо переделать на нормальное.

max_lapshin ★★★★★
()