close
volání pouze označí zavřený soket TCP. Není již použitelný procesem. Ale jádro může stále po určitou dobu uchovávat nějaké zdroje (TIME_WAIT, 2MLS atd.).
Nastavení SO_REUSEADDR by mělo odstranit problémy s vázáním.
Ujistěte se tedy, že hodnota true
je při volání setsockopt
skutečně nenulové (chyba přetečení jej může přepsat):
true = 1;
setsockopt(sock,SOL_SOCKET,SO_REUSEADDR,&true,sizeof(int))
Existuje pid
proměnná je váš kód. Pokud používáte fork
(pro zahájení procesů zpracování připojení), pak byste měli zavřít sock
také v procesu, který to nepotřebuje.
Nejprve k pojmenování, takže všichni pojmenováváme stejné věci stejně:
Strana serveru:
Soket předán do listen()
a poté na accept()
nazvěme naslouchání socket.Soket vrácený accept()
nazvěme přijaté zásuvka.
Strana klienta:
Soket předán do connect()
nazvěme připojování/připojeno zásuvka.
K vašemu problému:
Chcete-li ukončit accept()
ed připojení zavřete přijato zásuvka (co nazýváte připojeno) volitelně nejprve pomocí shutdown()
následuje close ()
.
Chcete-li přijmout novou smyčku připojení těsně před voláním na accept()
, ne přejděte přes bind()
a listen()
znovu.
Pouze vypnout a zavřete poslech zásuvky, pokud se chcete zbavit nevyřízených connect()
s vydané po accept()
vráceno.
Připojení je stále aktivní, protože jste zapomněli uzavřít připojenou zásuvku. Zavřením poslechového konektoru se automaticky nezavře připojený konektor.
//necessary code
close(connected); // <---- add this line
close(sock);
goto label;
Nejsem si však jistý, proč dostáváte EADDRINUSE. Kód fungoval dobře na linuxu i mac os.