Модераторы: feodorv

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Sockets: address already in use, как закрыть? 
:(
    Опции темы
Rickert
  Дата 16.3.2007, 07:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Ситхи не пройдут!
****


Профиль
Группа: Комодератор
Сообщений: 3356
Регистрация: 11.7.2006
Где: Лакрима

Репутация: нет
Всего: 52



Был открыт сокет на определённом порту, программа работала - работала, потом случилось так, что программе понадобилось открыть новое соединение на этом порту, но предыдущее - закрыть не представляется возможным (данные о дескрипторе сокета отсутствуют). При попытке забиндиться программа вернёт "address already in use" есесно.
Вопрос: как мне закрыть старую сессию знаю порт?
Машина локальная.


--------------------
Ни что не внушает сна крепче, чем день приисполненный трудов!
PM MAIL WWW Skype GTalk   Вверх
ptr
Дата 16.3.2007, 18:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 661
Регистрация: 31.5.2006
Где: Новосибирск

Репутация: 9
Всего: 14



Цитата(Rickert @  16.3.2007,  10:32 Найти цитируемый пост)
(данные о дескрипторе сокета отсутствуют).

Это как? Про это поподробнее.


--------------------
Единственный способ определить границы возможного - это выйти за эти границы, в невозможное.
Артур Кларк.
PM MAIL ICQ   Вверх
SparF
Дата 16.3.2007, 20:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 387
Регистрация: 14.9.2006
Где: Санкт-Петербург/М осква

Репутация: нет
Всего: 18



желательно с кодом


--------------------
Люди, не пользуйтесь пиратским программным обеспечением - переходите на Linux!
PM MAIL ICQ   Вверх
Dude03
Дата 17.3.2007, 12:39 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 257
Регистрация: 28.4.2006

Репутация: нет
Всего: 6



Могу предложить грязненький хак:
можно перебрать все идентификаторы сокетов и для каждого получить порт. Если порт - тот самый - действуем...=)
PM MAIL   Вверх
Rickert
Дата 17.3.2007, 13:41 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Ситхи не пройдут!
****


Профиль
Группа: Комодератор
Сообщений: 3356
Регистрация: 11.7.2006
Где: Лакрима

Репутация: нет
Всего: 52



Цитата(ptr @  16.3.2007,  18:49 Найти цитируемый пост)
Это как? Про это поподробнее.

Был дескриптор, потом, например, программу перезапустили, незакрыв сокет - он остался в системе. Через некоторое время ОСь конечно сама его закроет, но меня интересует возможность закрыть самому.


--------------------
Ни что не внушает сна крепче, чем день приисполненный трудов!
PM MAIL WWW Skype GTalk   Вверх
Dude03
Дата 17.3.2007, 15:59 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 257
Регистрация: 28.4.2006

Репутация: нет
Всего: 6



В винде такой проблемы нету=). Указывай в следующий раз свою операционную систему. smile 
PM MAIL   Вверх
Rickert
Дата 17.3.2007, 17:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Ситхи не пройдут!
****


Профиль
Группа: Комодератор
Сообщений: 3356
Регистрация: 11.7.2006
Где: Лакрима

Репутация: нет
Всего: 52



 dude
Альт Линукс


--------------------
Ни что не внушает сна крепче, чем день приисполненный трудов!
PM MAIL WWW Skype GTalk   Вверх
SparF
Дата 17.3.2007, 19:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 387
Регистрация: 14.9.2006
Где: Санкт-Петербург/М осква

Репутация: нет
Всего: 18



Цитата(Rickert @  17.3.2007,  13:41 Найти цитируемый пост)
потом, например, программу перезапустили

ну можно и "ручками" (в смысле - в программе учесть) его закрыть в этот момент

Цитата(Rickert @  17.3.2007,  13:41 Найти цитируемый пост)
незакрыв сокет - он остался в системе. Через некоторое время ОСь конечно сама его закроет

По идее освобождение ресурсов происходит сразу же, при закрытии сокета. Но тут можете сыграть злую шутку tcp - сетевая подсистема будет ждать какого-то события, а потом закроет, наконец, соединение по тайм-ауту. Что говорят
Код

#lsof -i -n -P
#netstat -tua
?
Покажите код, а то на пальцах рассуждаем....


--------------------
Люди, не пользуйтесь пиратским программным обеспечением - переходите на Linux!
PM MAIL ICQ   Вверх
Rickert
Дата 18.3.2007, 07:54 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Ситхи не пройдут!
****


Профиль
Группа: Комодератор
Сообщений: 3356
Регистрация: 11.7.2006
Где: Лакрима

Репутация: нет
Всего: 52



Цитата(SparF @  17.3.2007,  19:14 Найти цитируемый пост)
ну можно и "ручками" (в смысле - в программе учесть) его закрыть в этот момент

В деструкторе есесно всё прописано, но я имею ввиду аварийную принудительную остановку.
Цитата(SparF @  17.3.2007,  19:14 Найти цитируемый пост)
Покажите код, а то на пальцах рассуждаем....

Какую его часть именно? создание сокета? Попытка connect()'а?


--------------------
Ни что не внушает сна крепче, чем день приисполненный трудов!
PM MAIL WWW Skype GTalk   Вверх
SparF
Дата 18.3.2007, 08:34 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 387
Регистрация: 14.9.2006
Где: Санкт-Петербург/М осква

Репутация: нет
Всего: 18



Цитата(Rickert @  18.3.2007,  07:54 Найти цитируемый пост)
аварийную принудительную остановку

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

kill pid_процесса

всего навсего посылает процессу сигнал SIGTERM, а на него можно повесить обработчик, который уже будет закрывать соединение и т.д. и т.п., иными словами - грамотно освобождать ресурсы.
Если же прога ну совсем висит, то решение одно:
Код

kill -9 pid_процесса

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



--------------------
Люди, не пользуйтесь пиратским программным обеспечением - переходите на Linux!
PM MAIL ICQ   Вверх
Rickert
Дата 18.3.2007, 10:38 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Ситхи не пройдут!
****


Профиль
Группа: Комодератор
Сообщений: 3356
Регистрация: 11.7.2006
Где: Лакрима

Репутация: нет
Всего: 52



Да нет, ты меня не понял. Во время выполнения программы нажимаю ctrl + z и всё.
И вообще - это не имеет значения вопрос-то: как закрыть уже открытый сокет, не имея его дескриптора, но зная порт?


--------------------
Ни что не внушает сна крепче, чем день приисполненный трудов!
PM MAIL WWW Skype GTalk   Вверх
SparF
Дата 18.3.2007, 13:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 387
Регистрация: 14.9.2006
Где: Санкт-Петербург/М осква

Репутация: нет
Всего: 18



Цитата(Rickert @  18.3.2007,  10:38 Найти цитируемый пост)
Во время выполнения программы нажимаю ctrl + z и всё.

Так это не должно завершать процесс. Это просто останавливает его, и убирает в фон! (В случае если используется bash)
man bash
Цитата

To facilitate the implementation of the user interface to job control, the operating  system
       maintains  the notion of a current terminal process group ID.  Members of this process group
       (processes whose process group ID is equal to the current terminal process group ID) receive
       keyboard-generated  signals  such  as  SIGINT.   These processes are said to be in the fore-
       ground.  Background processes are those whose process group ID differs from the  terminal's;
       such  processes  are  immune  to  keyboard-generated signals.  Only foreground processes are
       allowed to read from or write to the terminal.  Background processes which attempt  to  read
       from  (write  to)  the  terminal are sent a SIGTTIN (SIGTTOU) signal by the terminal driver,
       which, unless caught, suspends the process.

       If the operating system on which bash is running supports job control, bash contains facili-
       ties  to  use it.  Typing the suspend character (typically ^Z, Control-Z) while a process is
       running causes that process to be stopped and returns control to bash.
  Typing  the  delayed
       suspend  character  (typically  ^Y,  Control-Y)  causes  the  process  to be stopped when it
       attempts to read input from the terminal, and control to be returned to bash.  The user  may
       then  manipulate  the  state  of  this job, using the bg command to continue it in the back-
       ground, the fg command to continue it in the foreground, or the kill command to kill it.   A
       ^Z  takes  effect  immediately, and has the additional side effect of causing pending output
       and typeahead to be discarded.

А это значит, что процесс остается запущенным (просто остановленным) и занимает сокет на законных основаниях.

Цитата(Rickert @  18.3.2007,  10:38 Найти цитируемый пост)
как закрыть уже открытый сокет, не имея его дескриптора, но зная порт? 

посмотреть какой процесс открыл соединение на данном порту и грохнуть процесс.
Цитата

# netstat -atuwnp

выдаст даст PID, который надо убить)


--------------------
Люди, не пользуйтесь пиратским программным обеспечением - переходите на Linux!
PM MAIL ICQ   Вверх
Rickert
Дата 19.3.2007, 04:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Ситхи не пройдут!
****


Профиль
Группа: Комодератор
Сообщений: 3356
Регистрация: 11.7.2006
Где: Лакрима

Репутация: нет
Всего: 52



Нет, ты не прав. Даже грохнув процесс - некоторые сокеты всё равно не могут открыться. "Already in use" и всё.

Это сообщение отредактировал(а) Rickert - 20.3.2007, 05:49


--------------------
Ни что не внушает сна крепче, чем день приисполненный трудов!
PM MAIL WWW Skype GTalk   Вверх
ptr
Дата 21.3.2007, 18:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 661
Регистрация: 31.5.2006
Где: Новосибирск

Репутация: 9
Всего: 14



Так господа давайте по-порядку.
Если сокет используется несколькими процессами, то он закроется, только когда его закроет последний процесс. Поэтому, чтобы освободить сокет нужно убить процессы, использующие этот сокет.

Цитата(Rickert @  19.3.2007,  07:46 Найти цитируемый пост)
 Даже грохнув процесс - некоторые сокеты всё равно не могут открыться.

Читаем и просвещаемся про TCP и сокеты, а также про SO_REUSEADDR (setsockopt). Например, в Стивенсе и Снейдере.


--------------------
Единственный способ определить границы возможного - это выйти за эти границы, в невозможное.
Артур Кларк.
PM MAIL ICQ   Вверх
SparF
Дата 21.3.2007, 20:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 387
Регистрация: 14.9.2006
Где: Санкт-Петербург/М осква

Репутация: нет
Всего: 18



ptr, за SO_REUSEADDR спасибо -  не знал.
А в это время в манах все русским по белому написано))
man 7 ip
Цитата

...
A TCP local socket address that has been bound is unavailable for some time  after  closing,
unless  the SO_REUSEADDR flag has been set.  Care should be taken when using this flag as it
makes TCP less reliable.
...

man 7 socket
Цитата

...
SO_REUSEADDR
              Indicates that the rules used in validating addresses  supplied  in  a  bind(2)  call
              should  allow  reuse of local addresses. For PF_INET sockets this means that a socket
              may bind, except when there is an active listening socket bound to the address.  When
              the  listening socket is bound to INADDR_ANY with a specific port then it is not pos-
              sible to bind to this port for any local address.
...
       Linux will only allow port re-use with the SO_REUSEADDR option when this option was set both
       in the previous program that performed a bind() to the port and in the program that wants to
       re-use the port.  This differs from some implementations  (e.g.,  FreeBSD)  where  only  the
       later program needs to set the SO_REUSEADDR option.  Typically this difference is invisible,
       since, for example, a server program is designed to always set this option.
...



--------------------
Люди, не пользуйтесь пиратским программным обеспечением - переходите на Linux!
PM MAIL ICQ   Вверх
Ответ в темуСоздание новой темы Создание опроса
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Сети | Следующая тема »


 




[ Время генерации скрипта: 0.0845 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.