2013-09-23 43 views
1

我在Perl新的,並試圖瞭解這個鱈鏈接:http://codepaste.ru/1374/but我理解這部分代碼的一些問題:襪子5代理Perl的

while($client || $target) { 
    my $rin = ""; 
    vec($rin, fileno($client), 1) = 1 if $client; 
    vec($rin, fileno($target), 1) = 1 if $target; 
    my($rout, $eout); 
    select($rout = $rin, undef, $eout = $rin, 120); 
    if (!$rout && !$eout) { return; } 
    my $cbuffer = ""; 
    my $tbuffer = ""; 

    if ($client && (vec($eout, fileno($client), 1) || vec($rout, fileno($client), 1))) { 
    my $result = sysread($client, $tbuffer, 1024); 
    if (!defined($result) || !$result) { return; } 
    } 

    if ($target && (vec($eout, fileno($target), 1) || vec($rout, fileno($target), 1))) { 
    my $result = sysread($target, $cbuffer, 1024); 
    if (!defined($result) || !$result) { return; } 
    } 

    if ($fh && $tbuffer) { print $fh $tbuffer; } 

    while (my $len = length($tbuffer)) { 
    my $res = syswrite($target, $tbuffer, $len); 
    if ($res > 0) { $tbuffer = substr($tbuffer, $res); } else { return; } 
    } 

    while (my $len = length($cbuffer)) { 
    my $res = syswrite($client, $cbuffer, $len); 
    if ($res > 0) { $cbuffer = substr($cbuffer, $res); } else { return; } 
    } 
} 

任何機構可以解釋我到底什麼發生在這些行:

vec($rin, fileno($client), 1) = 1 if $client; 
vec($rin, fileno($target), 1) = 1 if $target; 

select($rout = $rin, undef, $eout = $rin, 120); 

回答

1

基本上,selectÒ perator用於查找哪些文件描述符已準備好(可讀,可寫或有錯誤情況)。它將等待,直到其中一個文件描述符準備就緒或超時。

select RBITS, WBITS, EBITS, TIMEOUT 

RBITS是一個位掩碼,通常保存爲一個字符串,表示一組文件描述符select將等待可讀性。 RBITS的每一位代表一個文件描述符,並且該位掩碼中文件描述符的偏移量應該是系統中的文件描述符編號。因此,您可以使用vec來生成此位掩碼。

vec EXPR, OFFSET, BITS 

vec函數提供存儲無符號整數列表。 EXPR是一個位串,OFFSETEXPR中位的偏移量,BITS指定了您正在讀取/寫入到EXPR的每個元素的寬度。

所以這兩條線:

vec($rin, fileno($client), 1) = 1; 
vec($rin, fileno($target), 1) = 1; 

他們提出了一個位掩碼串$rin與設置,其偏移等於$client文件描述符號位,還有的$target之一。

把它放進select操作:

select($rout = $rin, undef, $eout = $rin, 120); 

然後select將監控兩個文件處理程序($client$target)的可讀性,如果其中一人已準備就緒,select將返回。或者如果沒有人準備好,它會在120s後返回。

WBITS,EBITS使用相同的方法。所以你可以推斷,當兩個文件處理程序有任何異常時,上面的select行也會返回。