Hei,
Tämä ongelmahan on varmasti tuttu enemmän ja vähemmän winsockin kanssa pelehtineille, että kun soketin laittaa kuuntelemaan, sulkee, ja avaa uudestaan, on portti käytössä, ja erroria pukkaa. Kuitenkin sen portin tarvii, joten millä sen saa vapautetuksi heti ? voiko soketin laittaa jotenkin uskomaan että sieltä reijästä ei ole enää mitään tulossa? Koska outoahan on, että kun ohjelman sulkee ja avaa uudestaan, porttiin voikin taas yhdistää.....
Winsockia voi käyttää aika monella eri tavalla, ja se kokonaan sulkeminen sitten riippuu siitä miten käytetään.
Ihan aluksi helpottaisi jos tietäisi että käytätkö QBAsicia vai Visual Bascia ja jos VB:tä niin käytätkö kielen mukana tulevaa Winsock -controllia vai suoraan APIa, vai jotain muuta.
Jos olisit laittanut ongelman sisältävän koodin näkösälle, niin nämä asiat olisi voinut toki päätellä siitäkin.
Ainakaan VB6:n vakio Winsock-controllilla ei ollut mitään ongelmaa seuraavassa:
Winsock1.Listen Winsock1.Close Winsock1.Listen Winsock1.Close
(portin olin määritellyt vakioksi)
Jos vakio tarkottaa nollaa, niin kyllä se noin toimii. Mutta koitapa laittaa joku 20110 siihen niin johan jynkkää. Eli visual basic on väline.
No mulla oli 555.
Kokeilin nyt vielä seuraavalla koodilla:
Private Sub Command1_Click() Winsock1.LocalPort = 20110 Winsock1.Listen Logita "Listening to port " & Winsock1.LocalPort Winsock1.Close Logita "Closed port" Winsock1.Listen Logita "Listening to port " & Winsock1.LocalPort Winsock1.Close Logita "Closed port" End Sub Private Sub Logita(msg As String) Debug.Print Format(Timer, "0.000") & " " & msg End Sub
Tulos:
61496,800 Listening to port 20110 61496,800 Closed port 61496,820 Listening to port 20110 61496,820 Closed port
Tosin mä en nyt ihan suoraan sanoen ymmärrä, miksi edes suljet sen välillä...
samaa sokettia käytetään yhdistämiseen ja kuunteluun :P
Eihän sitä niin kuulu tehdä. Eli jos nyt oikein ymmärsin, niin et sulje sitä kuuntelusockettia ollenkaan (toisin kuin väitit). Koska jos requestin saamisen jälkeen ennen acceptia sanoisit close, niin sehän käsittääkseni hylkäis sen pyynnön. Tai vaikka sulkisikin välillä, niin jos et sille acceptaavalle sano että localport on 0, niin silloinhan se varaa sen portin ulos päin liikennöintiin.
kyllähän sen niin voi tehä ja niin just kuuluukin tehä jos osaa... :D mulla on 1 soketti, ja ku tulee pyyntö, niin suljen kuuntelevan soketin ja vastaanotan pyynnön sen jälkeen. toimii vallan vekkulisti. ongelma on vaan se että localportti jää varatuks. sama on kaikkien muidenkin netistä otettujen chattijuttujen kanssa ellei kyseessä oo 3 rivin kivikeppi-viritelmät.
No, mikset vaan laita kahta sokettia? Tai sitten ennen kuin sanot
sock.Accept id
niin sanot
sock.Localport = 0
ja sitten taas ennen listeniä vaihdat sen takaisin.
Huonolla tuurillahan osuu tuossakin tuulettimeen.
setsockoptilla laita SO_REUSEADDR-arvo ykköseksi. Sitten ei pitäis tulla "Address in use" virhettä, vaikka kuuntelijasokettia ei suljettaisi oikein.
Jotenkin vaan terve järki sanoo 2 soketin olevan tuhlausta, jos 1 soketti ajaa saman asian. Koitan värkätä jotain
Hmm, no yleensähän kyllä kuunteleva ohjelma palvelee useampaa käyttäjää yhtä aikaa jos vaan useampi haluaa ottaa yhteyttä, jossa mielessä tuntuisi hölmöltä lopettaa kuuntelu siksi aikaa kun palvellaan toista.
Mutta ei kyllä mulla yhdelläkään soketilla tule mitään ongelmaa:
Private Sub Form_Load() Winsock1.LocalPort = 20110 Winsock1.Listen End Sub Private Sub Winsock1_Close() Winsock1.Close Winsock1.Listen End Sub Private Sub Winsock1_Connect() 'Logita "Connected" End Sub Private Sub Winsock1_ConnectionRequest(ByVal requestID As Long) Winsock1.Close Winsock1.Accept requestID End Sub Private Sub Winsock1_DataArrival(ByVal bytesTotal As Long) Dim sz As String Winsock1.GetData sz, vbString Text1.Text = Text1.Text & sz End Sub
kyseessä on vaan ohjelma, joka muodostaa yhden yhteyden kerrallaan. Tästä terve mielikuva voi olla vaikka suora tcpip kaksinpeli ilman main servua. ja deffille SO_REUSEADDR on udp yhteyttä varten.
Niin, edellä laittamallani koodilla yhtä sokettia käyttäen ei ollut mitään ongelmaa ottaa montaa kertaa yhteyttä samaan porttiin.
ota yhteys tolla kuuntelevalla soketilla välissä
Siis mihin sillä pitää ottaa yhteys? Mutta jos sillä on pakko ottaa välillä yhteys ulos, niin laita ulospäin mennessä localportiksi 0, niin se ei jää killumaan.
Taidan lopettaa neuvomisen tähän kun et vieläkään ole pistänyt koodia millä ongelma esiintyy ja jatkuvasti vaan ongelmakuvaus muuttuu. Eli selvästikään et halua ongelmaa saada ratkaistua vaan vain kuluttaa neuvojien aikaa hukkaan.
ongelma voi olla jossakin proseduurissa tai sen aliproseduurissa, en ajatellut koko koodia tähän laittaa kansan ihmeteltäväksi
edit: ja joo, ei tule tota addres in use ongelmaa, jos localportin laittaa yhdistettäessä nollaksi :) kiitos.
Aihe on jo aika vanha, joten et voi enää vastata siihen.