EV (Perl)로 합성 파일 핸들 사용
문제
이렇게 작성된 FileHandle 객체가 있습니다 (명확성을 위해 약간 편집) :
sub TIEHANDLE
{
return $_[0] if ref($_[0]);
my $class = shift;
my $self = bless Symbol::gensym(), $class;
return $self;
}
sub new
{
my ($class, $fh, $chunk, $interval, $cb) = @_;
my $self = bless Symbol::gensym(), ref($class) || $class;
tie *$self, $self;
my $data = {
fh => $fh,
};
${*$self}{'data'} = $data;
return $self;
}
sub fileno
{
my $self = $_[0];
return ${*$self}{'data'}->{'fh'}->fileno();
}
*FILENO = \&fileno;
.
AnyEvent
와 함께 사용하고 싶습니다.그것은 AnyEvent::Impl::Perl
이지만 실패 함
AnyEvent::Impl::EV
.나는 EV
에서이 메소드로 그것을 추적했다고 생각합니다.
static int
s_fileno (SV *fh, int wr)
{
dTHX;
SvGETMAGIC (fh);
if (SvROK (fh))
{
fh = SvRV (fh);
SvGETMAGIC (fh);
}
if (SvTYPE (fh) == SVt_PVGV)
return PerlIO_fileno (wr ? IoOFP (sv_2io (fh)) : IoIFP (sv_2io (fh)));
if (SvOK (fh) && (SvIV (fh) >= 0) && (SvIV (fh) < 0x7fffffffL))
return SvIV (fh);
return -1;
}
.
나는 그것이 SvTYPE (fh) == SVt_PVGV
테스트를 실패하고 있다고 생각합니다. Devel::Peek
덤프 () 메소드 :
SV = PVMG(0x9c98460) at 0x44313b0
REFCNT = 1
FLAGS = (PADMY,ROK)
IV = 0
NV = 0
RV = 0x9c21d00
SV = PVGV(0x9c35510) at 0x9c21d00
REFCNT = 1
FLAGS = (OBJECT,RMG,MULTI)
MAGIC = 0x9a68ee0
MG_VIRTUAL = &PL_vtbl_backref
MG_TYPE = PERL_MAGIC_backref(<)
MG_OBJ = 0x9c217a8
STASH = 0x4374440 "MetadataStream"
NAME = "GEN5"
NAMELEN = 4
GvSTASH = 0x25d01c8 "Symbol"
GP = 0x9a43d50
SV = 0x0
REFCNT = 1
IO = 0x9c214a8
FORM = 0x0
AV = 0x0
HV = 0x9c21ce8
CV = 0x0
CVGEN = 0x0
LINE = 102
FILE = "/usr/share/perl5/Symbol.pm"
FLAGS = 0x2
EGV = 0x9c21d00 "GEN5"
PV = 0x9c21d00 ""
CUR = 0
LEN = 0
.
이 테스트를 통과 할 수 있도록 내 손잡이의 생성을 어떻게 조정할 수 있는지에 대한 도움이 될 것입니다.
해결책
묶여있는 파일 핸들은 Perl에서 부분적으로 만 구현되며 작동하지 않습니다. ev와 함께. 묶여있는 핸들은 이벤트 라이브러리와 함께 일할 수 없습니다. 일반 : 일부 특정 사례가 작동하지만 대부분의 경우 묶여있는 경우 핸들이 사용되므로 준비 상태 알림이므로 작동 할 수 없습니다. 기본 파일 디스크립터는 준비 알림과 관련되지 않습니다 묶인 핸들.
목표가 실제 파일 주위에 래퍼를 낭비하는 것입니다. 설명자, 한 가지 방법은 IO :: 핸들 및 / 또는 FileHandle (매우 추악하지만 Perl에서 작동하는 유일한 방법) 또는 사용 그들을 기본 수업으로 이것은 당신이 흥미로운 일을 할 수 없습니다 훅처럼 읽기 및 쓰기와 같은 경우 그러나 기회가 그들을 연결하고 있습니다. 이벤트 라이브러리와 호환되지 않습니다.
다른 방법은 Perlio 레이어 (Perlio :: Via)를 구현하는 것입니다. 내에서 경험,이 모듈은 조금 깨지기 쉽지만 모든 것을 제공합니다. 옵션. 다시, 버퍼링 또는 흥미로운 것들을 소개하는 경우 실제 I / O로부터 파일 디스크립터를 분리 한 다음, 일.
마지막으로 새 유형의 핸들을 추가하려면 만들 수 있습니다. 새로운 감시자 유형. 이것은 기능을 갖는 것만 큼 간단 할 수 있습니다 귀하의 핸들을 취하고, 준비 상태를 확인하는 my_handle_io_watcher 및 필요한 저급 감시자의 종류를 만듭니다.