LINUX.ORG.RU

Проблема с таймаутом :(((


0

0

Нужно сделать таймаут на функцию коннект. Делаю так. struct sigaction act;

bzero(&act, sizeof(act));

act.sa_handler = sig_alarm;

act.sa_flags = SA_ONESHOT;

if(sigaction(SIGALRM, &act, 0) != 0){

perror("Could not set up timeout");

}

else{

alarm(timeout);

}

if (connect (session->socket, (struct sockaddr *) &smtp_sock,sizeof(smtp_sock) ) < 0){ if(errno == EINTR){ printf("Can't connect to host: Timed out!\n"); } else { perror("connect to host "); } return -1; }

На моей машине все работает. Но на сервере программы при окончании таймаута прога сваливается с сообщением Alarm clock

Моя машина SuSE 8.0, gcc 2.95.3, kernel 2.4.18

На сервере РХ 7.1 кернел 2.4.9 gcc 2.96

Прога многопоточная, поэтому если валится один поток то и вся программа тоже.

Подскажите плиз что делать.

Заранее благодарен за любую помощь

★★★★

Попробуй использовать неблокирующий сокет, а таймаут устанавливай при вызове select(). Тогда вообще не надо будет alarm делать.

svd
()

>Попробуй использовать неблокирующий сокет, а таймаут устанавливай при >вызове select(). Тогда вообще не надо будет alarm делать.

Про не блокирующий сокет я уже думал :) попробую. Только как туда прикрутить select? на какое событие его устанавливать? Доступен для записи или как? На recv и send я уже коннекты сделал с помощью pool, но я думал, что на connect это работать не будет?

А вобще -- спасибо за помощь :-)

Dead ★★★★
() автор топика

Читать надо man внимательнее: EINPROGRESS The socket is non-blocking and the connection cannot be completed immediately. It is possible to select(2) or poll(2) for completion by selecting the socket for writing. After select indicates writability, use getsockopt(2) to read the SO_ERROR option at level SOL_SOCKET to determine whether connect completed successfully (SO_ERROR is zero) or unsuccessfully (SO_ERROR is one of the usual error codes listed here, explaining the reason for the failure).

aa5779
()

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

Dead ★★★★
() автор топика

Всем спасибо. Все заработало. Правда приходится сначала сокет блокировать, а затем разблокировать. А так довольно-таки стабильно :)))

Dead ★★★★
() автор топика

Ну, работает, дык и хорошо.
Все же кину пару комментариев:

get/set sockopt() не очень портабильна, особенно, если приходится иметь дело
с соляркой или переносимостью между разными либс.

Я делаю так:
делаю пайп, запускаю нитку с коннектом, и ПОСЛЕ коннекта пишу в пайп.
А в ДРУГОЙ нитке запускаю select на второй конец пайпа, с таймаутом.
Если таймаут наступил - коннект не справился, нитку с ним можно грохать.

Die-Hard ★★★★★
()

2Die-Hard : Тоже нормально :) Правда мне кажется, что во многих сетевых функциях не хватает параметра таймаут. Вот и приходися изголяться, блокировать, разблокировать, сигналы посылать, а ведь помоему эта проблема не такая уж и редкая.

Кстати а нити под линуксом портабельны для солярки?

Dead ★★★★
() автор топика
Ответ на: комментарий от Dead

Dead (*) (2002-10-29 19:05:02.767):
> Кстати а нити под линуксом портабельны для солярки?
Нет.

Честно говоря, я вообще не использую нитки, в первую очередь из-за проблем с
портабильностью. В описанной мной схеме я пользую fork(). Мне просто никогда
не требовалось быстро поднимать дочерние процессы, и я не совсем представляю
себе ситуацию, когда бы это потребовалось.

Die-Hard ★★★★★
()

У меня дело было не в быстроте, а в том что трэды должны юзать общие данные, в том числе и для записи. В этом весь их рулез. Форком так не сделаешь. Да и создаются они по логике действительно быстрее.

А в солярке есть сис. вызов clone?

Dead ★★★★
() автор топика
Ответ на: комментарий от Dead

Dead (*) (2002-10-30 14:03:23.502):
> ...трэды должны юзать общие данные, в том числе и для записи. В этом весь их рулез.
> Форком так не сделаешь.
Еще как сделаешь - расшариваешь память и - вперед!

В 99 случаях из 100 необходимость бесконтрольного юзания общих данных
связана с логическими ошибками в архитектуре проекта. Кроме того, накладные расходы
(как рантайм, так и при разработке) на синхронизацию ниток, как правило, выше, чем
на расшаривание памяти. Впрочем, вышесказанное - IMHO.

> Да и создаются они по логике действительно быстрее.
Дык - не на много!
Кроме того, в тех случаях, когда необходимо ДЕЙСТВИТЕЛЬНО быстро поднимать
параллельную ветку (например, выбсервер), используется пул ниток/процессов, т.е.
время старта вообще ни на что не влияет.

> А в солярке есть сис. вызов clone?
Нет, clone - линух-специфик. А хорошее изобретение! ;)

Кстати, в Солярке нитки НАСТОЛЬКО наворочены... У них своя родная подсистема
для ниток (правда, посикс тоже есть).

Die-Hard ★★★★★
()

А каким макаром можно память расшарить? И ведь тоже надо будет как-то синхронизировать совместный доступ к данным.

Dead ★★★★
() автор топика
Ответ на: комментарий от Dead

Dead (*) (2002-10-30 19:33:32.431):
> А каким макаром можно память расшарить?
Почитай любую книжку по программированию на Юнихе/Линухе, два способа,
System V IPC (man shmget);
BSD mmap (man mmap) - (anonymous mmap расшарит память сквозь fork)

Подробно и с примерами:
http://www.cs.cf.ac.uk/Dave/C/node27.html

> И ведь тоже надо будет как-то синхронизировать совместный доступ к данным.
Ессно! Семофоры в зубы и - вперед! :) Зато надо заботиться только о том,
что тебе действительно нужно, и не бояться, что сегфолт в маленьком левом
кем-то написанном обработчике свалит твой сервер.
Интересная дискуссия на эту тему:
http://www.tldp.org/HOWTO/Parallel-Processing-HOWTO-2.html#ss2.2
(в начале)

Die-Hard ★★★★★
()
Ответ на: комментарий от Dead

Да, замечу, семафорные функции тоже НЕ ОЧЕНЬ портабильны :( Особенно union semun, требующийся для semctl.

Die-Hard ★★★★★
()

Мне просто заказали именно с потоками... чтоб без форков... Заказчик не шарит просто, а мне надоело ему объяснять, что без разницы что форк что нить. Ну нити так нити, разницы особой нет. Просто я думаю если активно юзаются общая память, то лучше имхо потоки юзать, там нужно только с семафорами чтение/запись разрулить, а в форке еще и память надо расшаривать.

Dead ★★★★
() автор топика

[OT] А вот последнее замечание представляется мне крайне интересным. Я имею в виду, что заказчик требует нити. У меня такая же ситуация. Тенденция однако....

aa5779
()

Тут такое дело...
(IMHO, разумеется) - в принципе, вопрос о том, надо ли расшаривать все (используя нитки),
или же только то, что надо (используя процессы через форк), в достаточной степени
религиозный. Ежели меня попросят (заплатив бабки ;)) слабАть халтурку на Линухе 2.4xx с
условием no forks, only threads, то я и не вякну; как просили - так и слабАем.

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

А вот сейчас у меня круче судьба поворачивается. Тяжелый проект, написанный
на корявых сях, имеет место быть распараллеленным на крутой SMP компутер (через MPI).
И некий "спец", не написАвший сам ни файла, упирает на то, что надо все через треды
переписАть.

Вот здесь я точно упрусь всеми лапами. Конечно, можно, загубив пару-тройку лет,
переписать все thread-safety, но - смысл?

Die-Hard ★★★★★
()

[OT] Я разовью свою мысль: мне представляется, что повальное увлечение тредами в *nix (я имею в виду, со стороны людей, которые по сути соображают очень слабо) есть (IMHO) неприятный симптом скрытого влияния форточек на Unix. В форточках-то forkа нет, да и IPC там куда как геморройнее, чем в *nix

aa5779
()
Ответ на: комментарий от aa5779

aa5779 (*) (2002-11-01 15:57:25.28):
> ...повальное увлечение тредами в *nix ... есть (IMHO) неприятный симптом скрытого
> влияния форточек на Unix.
Согласен.

К сожалению, треды - только одно проявление такого влияния. За последние
несколько лет (в связи с экспансией M$) многие хорошо известные азбучные истины
перестали быть таковыми. "Прогрессивные" решения от M$, внедренные в силу
технической безграмотности мелкомягких девелоперов, становятся стандартом.
Дешевле оказывается перестроить общественное мнение, чем переделать оказавшееся
не очень удачным техническое решение

Die-Hard ★★★★★
()

Что-то я разочаровался немного в трэдах. Просто прога валится после 30 и более минут интенсивной работы. Делает более 100 тыс. конектов, а потом валится segmentation fault. Задолбался уже искать ошибку. Уже второй день ищу. В случае с форками, если свалится дочерний процесс, то родититель живой останется, а thread один свалится, то валится и вся прога :((( Знал бы что будут такие глюки писал бы через форки :((

Dead ★★★★
() автор топика
Ответ на: комментарий от Dead

Dead (*) (2002-11-02 18:00:30.022):
> Знал бы что будут такие глюки писал бы через форки :((
:-)
Теперь понимаешь, почему я нитки не люблю?

Die-Hard ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.