Kezdőlap › Fórumok › Programozás › TCP mágia
- This topic has 12 hozzászólás, 4 résztvevő, and was last updated 17 years, 5 months telt el by
ds.
-
SzerzőBejegyzés
-
2008-01-16-16:46 #2150528linuxforum wrote:És meglepő módon ezek a kapcsolatok megmaradnak, bár a kliens eszközök lekapcsolódnak.
Biztos, hogy a kliensek rendesen lezárják a kapcsolatot?
linuxforum wrote:Hogyn épülhet ki a kapcsolat, ha az én programom meg sem kapja a kapcsolatot?De megkapja, csak nem az accept(), hanem a connect() hozza létre a kapcsolatot.
3.3. Why does connect() succeed even before my server did an
accept()?From Andrew Gierth (andrew@erlenstar.demon.co.uk):
Once you have done a listen() call on your socket, the kernel is
primed to accept connections on it. The usual UNIX implementation of
this works by immediately completing the SYN handshake for any
incoming valid SYN segments (connection attempts), creating the socket
for the new connection, and keeping this new socket on an internal
queue ready for the accept() call. So the socket is fully open before
the accept is done.http://www.faqs.org/faqs/unix-faq/socket/
linuxforum wrote:Lehetséges egyáltalán hozzáférnem az ilyen kapcsolatokhoz?
Vagy ezek elvesztek a semmibe?Nem lehet hozzáférni az eldobott kapcsolatokhoz, a kernel fogja majd egy idő után halottnak nyilvánítani.
4.2. Why don’t my sockets close?
When you issue the close() system call, you are closing your interface
to the socket, not the socket itself. It is up to the kernel to close
the socket. Sometimes, for really technical reasons, the socket is
kept alive for a few minutes after you close it. It is normal, for
example for the socket to go into a TIME_WAIT state, on the server
side, for a few minutes. People have reported ranges from 20 seconds
to 4 minutes to me. The official standard says that it should be 4
minutes. On my Linux system it is about 2 minutes. This is explained
in great detail in „2.7 Please explain the TIME_WAIT state.”.Tehát ha a ‘létrejött’ (ESTABLISHED) jelzés van a szerver kilépése után is, akkor nincs jól lezárva a socket. Biztos, hogy minden kilépési pontnál lezárod a kapcsolatot (a hibáknál is)?A kliensek esetében a kliens gépen kell megnézni a port állapotát a kliens kilépését követően. A netstat használatakor használd a -p kapcsolót is, úgy biztosan tudni fogod, hogy kilépett-e valamelyik alkalmazás.
Ha többre vagy kíváncsi, használd a wireshark progit.
2008-01-16-16:46 #2150529linuxforum wrote:És meglepő módon ezek a kapcsolatok megmaradnak, bár a kliens eszközök lekapcsolódnak.Biztos, hogy a kliensek rendesen lezárják a kapcsolatot?
linuxforum wrote:Hogyn épülhet ki a kapcsolat, ha az én programom meg sem kapja a kapcsolatot?De megkapja, csak nem az accept(), hanem a connect() hozza létre a kapcsolatot.
3.3. Why does connect() succeed even before my server did an
accept()?From Andrew Gierth (andrew@erlenstar.demon.co.uk):
Once you have done a listen() call on your socket, the kernel is
primed to accept connections on it. The usual UNIX implementation of
this works by immediately completing the SYN handshake for any
incoming valid SYN segments (connection attempts), creating the socket
for the new connection, and keeping this new socket on an internal
queue ready for the accept() call. So the socket is fully open before
the accept is done.http://www.faqs.org/faqs/unix-faq/socket/
linuxforum wrote:Lehetséges egyáltalán hozzáférnem az ilyen kapcsolatokhoz?
Vagy ezek elvesztek a semmibe?Nem lehet hozzáférni az eldobott kapcsolatokhoz, a kernel fogja majd egy idő után halottnak nyilvánítani.
4.2. Why don’t my sockets close?
When you issue the close() system call, you are closing your interface
to the socket, not the socket itself. It is up to the kernel to close
the socket. Sometimes, for really technical reasons, the socket is
kept alive for a few minutes after you close it. It is normal, for
example for the socket to go into a TIME_WAIT state, on the server
side, for a few minutes. People have reported ranges from 20 seconds
to 4 minutes to me. The official standard says that it should be 4
minutes. On my Linux system it is about 2 minutes. This is explained
in great detail in „2.7 Please explain the TIME_WAIT state.”.Tehát ha a ‘létrejött’ (ESTABLISHED) jelzés van a szerver kilépése után is, akkor nincs jól lezárva a socket. Biztos, hogy minden kilépési pontnál lezárod a kapcsolatot (a hibáknál is)?A kliensek esetében a kliens gépen kell megnézni a port állapotát a kliens kilépését követően. A netstat használatakor használd a -p kapcsolót is, úgy biztosan tudni fogod, hogy kilépett-e valamelyik alkalmazás.
Ha többre vagy kíváncsi, használd a wireshark progit.
2008-01-17-08:24 #2150530Köszi, félek, van itt valami, amit nem értek:
Azt írod, a ->connect() kapja meg a kapcsolatot, nem az ->accept()
De az én programomban nincs is ->connect()!Code:$sock = new IO::Socket::INET( LocalHost => IP, LocalPort => PORT, Proto => ‘tcp’, Listen => SOMAXCONN, Reuse => 1);
while( 1 ) {
while( $new_sock = $sock->accept() ) {
if( $child = fork ) {
…Tudnám máshogy is fogadni a kapcsolatot, hogy már a kiépülés után tudjak róla? Vagy a perl korlátoz ebben, és a probléma megoldásához C-ben kellene fogadnom a kapcsolatokat? (Erre ne válaszolj igennel!)
A másik, amit nem értek, az a netstat dolog. Én -p kapcsolóval futtatom, de a kérdéses kapcsolatoknál nincs PID, csak egy – jel. Ebből én arra gondolok, hogy az én programom még egyáltalán nem indulhatott el. Sem az accept, sem a connect.
A kliensek egyébként egyáltalán nem biztos, hogy jól zárják le a kapcsolatot. Sőt! Ezek hardver eszközök, súlyosbítva azzal, hogy az egész kommunikáció mobil hálózaton folyik, ami igen csak fura dolgokat tud művelni a TCP csomagokkal … Tehát nekem a lehető legextrémebb kliens kommunikációra is fel kell készülnöm!
Az én lezárásaim pedig azt hiszem, ebből a szempontból nem fontosak, hiszen el sem indul a programom.
A TIME_WAIT állapotú kapcsolatokkal rendben vagyok. A kérdéses kapcsolataim ESTABLISHED állapotúak.
2008-01-17-08:24 #2150531Köszi, félek, van itt valami, amit nem értek:
Azt írod, a ->connect() kapja meg a kapcsolatot, nem az ->accept()
De az én programomban nincs is ->connect()!Code:$sock = new IO::Socket::INET( LocalHost => IP, LocalPort => PORT, Proto => ‘tcp’, Listen => SOMAXCONN, Reuse => 1);
while( 1 ) {
while( $new_sock = $sock->accept() ) {
if( $child = fork ) {
…Tudnám máshogy is fogadni a kapcsolatot, hogy már a kiépülés után tudjak róla? Vagy a perl korlátoz ebben, és a probléma megoldásához C-ben kellene fogadnom a kapcsolatokat? (Erre ne válaszolj igennel!)
A másik, amit nem értek, az a netstat dolog. Én -p kapcsolóval futtatom, de a kérdéses kapcsolatoknál nincs PID, csak egy – jel. Ebből én arra gondolok, hogy az én programom még egyáltalán nem indulhatott el. Sem az accept, sem a connect.
A kliensek egyébként egyáltalán nem biztos, hogy jól zárják le a kapcsolatot. Sőt! Ezek hardver eszközök, súlyosbítva azzal, hogy az egész kommunikáció mobil hálózaton folyik, ami igen csak fura dolgokat tud művelni a TCP csomagokkal … Tehát nekem a lehető legextrémebb kliens kommunikációra is fel kell készülnöm!
Az én lezárásaim pedig azt hiszem, ebből a szempontból nem fontosak, hiszen el sem indul a programom.
A TIME_WAIT állapotú kapcsolatokkal rendben vagyok. A kérdéses kapcsolataim ESTABLISHED állapotúak.
2008-01-18-17:30 #2150532„De az én programomban nincs is ->connect()”
Hmm, az ‘IO::Socket::INET()’ hivja meg, csak nem látszik.
„Tudnám máshogy is fogadni a kapcsolatot, hogy már a kiépülés után tudjak róla?”
Nem lehet, még C-ben sem, legalábbis hogy gondolod. A kapcsolat kétirányban kiépül, mielőtt az accept() visszaadná a vezérlést, a programodban csak az adatkommunikációt tudod befolyásolni, a kézfogást nem (ez látszik a netstat-ban).„Én -p kapcsolóval futtatom, de a kérdéses kapcsolatoknál nincs PID, csak egy – jel. Ebből én arra gondolok, hogy az én programom még egyáltalán nem indulhatott el.”
Egy szőke nő lehet úgy terhes, hogy a gyereknek nincs apja? 🙂 Ha nincs PID, akkor a progid már kilépett. Mivel forkolod, külön probléma lehet. Kommentezd ki, úgy sorban fogja a progid kezelni a kéréseket, de kiszűrsz egy hibalehetőséget. Lehet hogy minden jó, csak a forkolt rész lép ki túl hamar. Különben ha debugolsz, azonosítani kell megyik folyamatról van szó.
„Az én lezárásaim pedig azt hiszem, ebből a szempontból nem fontosak, hiszen el sem indul a programom.”
Ha így lenne, akkor hibaüzenetet kapnál. Ha a fork() nem megy, akkor neked kellene hibaüzit kreálnod.
„A TIME_WAIT állapotú kapcsolatokkal rendben vagyok. A kérdéses kapcsolataim ESTABLISHED állapotúak.”
A probléma az, hogy PID nélkül nem lenne szabad ESTABLISHED állapotnak lennie.
2008-01-18-17:30 #2150533„De az én programomban nincs is ->connect()”
Hmm, az ‘IO::Socket::INET()’ hivja meg, csak nem látszik.
„Tudnám máshogy is fogadni a kapcsolatot, hogy már a kiépülés után tudjak róla?”
Nem lehet, még C-ben sem, legalábbis hogy gondolod. A kapcsolat kétirányban kiépül, mielőtt az accept() visszaadná a vezérlést, a programodban csak az adatkommunikációt tudod befolyásolni, a kézfogást nem (ez látszik a netstat-ban).„Én -p kapcsolóval futtatom, de a kérdéses kapcsolatoknál nincs PID, csak egy – jel. Ebből én arra gondolok, hogy az én programom még egyáltalán nem indulhatott el.”
Egy szőke nő lehet úgy terhes, hogy a gyereknek nincs apja? 🙂 Ha nincs PID, akkor a progid már kilépett. Mivel forkolod, külön probléma lehet. Kommentezd ki, úgy sorban fogja a progid kezelni a kéréseket, de kiszűrsz egy hibalehetőséget. Lehet hogy minden jó, csak a forkolt rész lép ki túl hamar. Különben ha debugolsz, azonosítani kell megyik folyamatról van szó.
„Az én lezárásaim pedig azt hiszem, ebből a szempontból nem fontosak, hiszen el sem indul a programom.”
Ha így lenne, akkor hibaüzenetet kapnál. Ha a fork() nem megy, akkor neked kellene hibaüzit kreálnod.
„A TIME_WAIT állapotú kapcsolatokkal rendben vagyok. A kérdéses kapcsolataim ESTABLISHED állapotúak.”
A probléma az, hogy PID nélkül nem lenne szabad ESTABLISHED állapotnak lennie.
2008-01-19-11:20 #2150534gabaman wrote:„De az én programomban nincs is ->connect()”Hmm, az ‘IO::Socket::INET()’ hivja meg, csak nem látszik.
mármint a socket -et hívja meg, connect nem kell a szerverben.
a netstat -ot ugye root-ként futtatod (vagy azzal a user-el mint a programot?)
a recv-q (első szám) elég nagy, úgy néz ki mintha a programod nem olvasna az accept után.gabaman wrote:„Tudnám máshogy is fogadni a kapcsolatot, hogy már a kiépülés után tudjak róla?”
Nem lehet, még C-ben sem, legalábbis hogy gondolod. A kapcsolat kétirányban kiépül, mielőtt az accept() visszaadná a vezérlést, a programodban csak az adatkommunikációt tudod befolyásolni, a kézfogást nem (ez látszik a netstat-ban).ha már tcp mágia akkor lehetne raw socket -el a csomag headereket piszkálni 😉
2008-01-19-11:20 #2150535gabaman wrote:„De az én programomban nincs is ->connect()”Hmm, az ‘IO::Socket::INET()’ hivja meg, csak nem látszik.
mármint a socket -et hívja meg, connect nem kell a szerverben.
a netstat -ot ugye root-ként futtatod (vagy azzal a user-el mint a programot?)
a recv-q (első szám) elég nagy, úgy néz ki mintha a programod nem olvasna az accept után.gabaman wrote:„Tudnám máshogy is fogadni a kapcsolatot, hogy már a kiépülés után tudjak róla?”
Nem lehet, még C-ben sem, legalábbis hogy gondolod. A kapcsolat kétirányban kiépül, mielőtt az accept() visszaadná a vezérlést, a programodban csak az adatkommunikációt tudod befolyásolni, a kézfogást nem (ez látszik a netstat-ban).ha már tcp mágia akkor lehetne raw socket -el a csomag headereket piszkálni 😉
2008-01-21-10:05 #2150536Igen, van, amikor az én programom hal el hibával, és ilyenkor valóban nincs PID a netstat sorában, de ez rendben is van.
Kértem egy bővített netstat-ot (igen, root-ként), és az érdekes az, hogy az Inode (amiről csak tippelem, hogy a socket inode száma), minden esetben valami szám, míg a kérdéses esetekben 0.
Ez is azt mutatja nekem, hogy egy olyan kapcsolat épült ki, ami még nincs teljesen kész.
Ráadásul hangsúlyozom, hogy a connect után az első dolog, amit csinálog, egy logbejegyzés, és az sem készül el, tehát én úgy érzem, hogy ezek a kapcsolatok nem jutnak el a programomig, így semilyen eszközt nem látok amivel befolyásolhatnám. Még a raw socket-et sem, hisz nem indul el a programom.
Adtam Timeout-ot a kapcsolatnak, de ezek a mágikus netstat sorok 0/0-ákkal állnak folyamatosan, azaz nem kezd el visszaszámolni az időzítőjük … ergó örökre maradnak! (?)A probléma az, hogy PID nélkül nem lenne szabad ESTABLISHED állapotnak lennie.
Hát, pont ez a probléma … De vannak, ez tény. Miért? És hogyan kezelhetem, hogy ne legyenek?
2008-01-21-10:05 #2150537Igen, van, amikor az én programom hal el hibával, és ilyenkor valóban nincs PID a netstat sorában, de ez rendben is van.
Kértem egy bővített netstat-ot (igen, root-ként), és az érdekes az, hogy az Inode (amiről csak tippelem, hogy a socket inode száma), minden esetben valami szám, míg a kérdéses esetekben 0.
Ez is azt mutatja nekem, hogy egy olyan kapcsolat épült ki, ami még nincs teljesen kész.
Ráadásul hangsúlyozom, hogy a connect után az első dolog, amit csinálog, egy logbejegyzés, és az sem készül el, tehát én úgy érzem, hogy ezek a kapcsolatok nem jutnak el a programomig, így semilyen eszközt nem látok amivel befolyásolhatnám. Még a raw socket-et sem, hisz nem indul el a programom.
Adtam Timeout-ot a kapcsolatnak, de ezek a mágikus netstat sorok 0/0-ákkal állnak folyamatosan, azaz nem kezd el visszaszámolni az időzítőjük … ergó örökre maradnak! (?)A probléma az, hogy PID nélkül nem lenne szabad ESTABLISHED állapotnak lennie.
Hát, pont ez a probléma … De vannak, ez tény. Miért? És hogyan kezelhetem, hogy ne legyenek?
-
SzerzőBejegyzés
- Be kell jelentkezni a hozzászóláshoz.
legutóbbi hsz