2014-06-19 2 views
2

서버가 무한 루프에 빠지면 언젠가 서버 연결을 어떻게 닫을 수 있습니까? 대답은 아무 문제없이 서버에 의해 주어진 경우 위의 코드가 작동얼마 후 소켓 시간 초과

set s [socket $host $port] 
    fconfigure $s -blocking 1 -buffering line 
    after 2000 set end 1 
    vwait end 
    if { $s != "" } { 

      puts -nonewline $s "$msg\n.\n" 
      flush $s 
      fileevent $s readable [set answer [read $s]] 

      puts "$answer" 

      if {[catch {close $s}]} { 
        puts "Server hanged" 
      } 

: 여기

내가 노력하고있는 코드입니다. 서버가 무한 루프가되면 read $s에 매달려 있습니다. 이 read socket을 비 차단 모드로 처리하는 방법에 대한 도움말은 fconfigure과 같습니다.

+2

지금 당장은 대답이 없지만, 'fileevent'를 호출하는 방법은 콜백 스크립트로 [set answer [read $ s]]를 설치하지 않습니다. 그 대신 호출 중에 그 액션 (소켓에서 읽기를 시도하고 결과를'answer'에 할당)을 수행하고 소켓에서 읽은 것을 콜백 스크립트로 설정합니다. 이것은 콜백 스크립트가 의도 한 바 일 가능성이 거의 없습니다. –

+0

시간 초과가 발생했습니다. – xrcwrn

답변

2

블로킹 소켓을 사용하는 경우이 문제가 발생합니다. 채널을 비 블로킹 모드로 설정하는 것이 수정입니다 (시간 제한을 쓰기 위해 after과 함께 사용). 이는 비동기 프로그래밍의 모든 복잡성을 처리해야한다는 것을 의미하지만 여기서 필요한 절충안입니다.

물건을 걸 수있는 두 곳은 연결 설정 및 데이터 생산에 있습니다. 따라서 비동기 연결 및 비 차단 검색을 사용합니다.

set s [socket -async $host $port] 
fconfigure $s -blocking 0 

fileevent $s writeable [list connected $s] 
proc connected {s} { 
    global msg 
    fileevent $s writeable {} 
    puts -nonewline $s "$msg\n.\n" 
    flush $s 
    fileevent $s readable [list accumulateBytes $s] 
} 

set accumulate "" 
proc accumulateBytes {s} { 
    global accumulate end 
    append accumulate [read $s] 
    if {[eof $s]} { 
     set end 0 
    } 
} 

# Longer *total* time to connect and communicate. 
after 5000 set end 1 
vwait end 

catch {close $s} 

if {$end} {puts "timed out"} 
puts "received message: $accumulate" 
+0

Donal .. 감사합니다. 제 요구 사항에 완벽하게 부합합니다. – Tamilan