Perl:IPC :: Shareable和SWIG’ed C对象不同意
对于我的某个Perl项目,我需要几个Perl进程来共享一些位于C库中的资源. (不要问,这不是这个问题的核心,只是背景.)
因此,我试图在这个上下文中钻研两个“新”字段: 在C方面,我写了一个小测试类Rectangle,它带有一个空构造函数,一个set和一个size成员函数. 然后我将该类包装在SWIG生成的Perl包示例中. 在Perl方面,我试过SWIG模块按预期工作: use example; my $testrec = new example::Rectangle; $testrec->set( 6,7 ); print $testrec->size() . "n"; 这样打印“42”. 然后我试着尝试使用IPC :: Shareable.我编写了两个Perl脚本,一个“服务器”和一个“客户端”来测试资源共享. 服务器”: use IPC::Shareable; use example; # v_ for variable,g_ for (IPC) glue my $v_array; my $v_rect; my %options = ( create => 'yes',exclusive => 0,mode => 0644,destroy => 'yes' ); tie $v_array,'IPC::Shareable','g_array',{ %options } or die; tie $v_rect,'g_rect',{ %options } or die; $v_array = [ "0" ]; $v_rect = new example::Rectangle; $v_rect->set( 6,7 ); while ( 1 ) { print "server array: " . join( " - ",@$v_array ) . "n"; print "server rect: " . $v_rect->size() . "n"; sleep 3; } 客户端”: use IPC::Shareable; use example; # v_ for variable,g_ for (IPC) glue my $v_array; my $v_rect; my %options = ( create => 0,destroy => 0 ); tie $v_array,{ %options } or die; my $count = 0; while ( 1 ) { print "client array: " . join( " - ",@$v_array ) . "n"; print "client rect: " . $v_rect->size() . "n"; push( @$v_array,++$count ); $v_rect->set( 3,$count ); sleep 3; } 首先启动“服务器”,然后是“客户端”,我得到“服务器”的输出: server array: 0 server rect: 42 server array: 0 - 1 server rect: 42 server array: 0 - 1 - 2 server rect: 42 而这个输出为“客户端”: client array: 0 client rect: 0 client array: 0 - 1 client rect: 3 client array: 0 - 1 - 2 client rect: 6 显然,数组引用可以共享,但是客户端没有“看到”服务器的示例:: Rectangle,而是在一个(零初始化的)流氓内存上工作,反过来服务器一无所知… 我怀疑我必须为$v_rect做些什么来使这项工作正常,但我在OO Perl中不够坚实,不知道是什么.谁来救援? 解决方法
你想做什么是行不通的.你将不得不咬紧牙关并做一些形式的消息传递.
我不太清楚SWIG如何为Perl包装C()级别的对象,但它很可能是通常的,无可否认的“整数槽指针”策略.在此设置中,它将分配一个C()对象并在Perl标量中存储指向它的指针. Perl对象将成为这个标量的祝福参考.当对Perl对象的所有引用都消失时,Perl类的析构函数将显式释放C()对象.更现代的技术就像XS :: Object :: Magic模块允许你做的那样. 但是包装器的细节甚至都不重要.重要的是该对象对Perl是不透明的!通过联系,IPC :: Shareable无论如何都使用了一些时尚和坦率的脆弱技术.它可能适用于您的Perl对象,也可能不适用.但是当您共享Perl对象时,将不会共享C()对象.怎么可能呢? Perl对此一无所知.它不可能. 你应该做的是在消息传递和序列化方面考虑问题.为了序列化你的C()对象,你需要允许来自C方面的一些合作.看看Storable模块为序列化对象提供的钩子.就消息传递/排队而言,我很高兴使用ZeroMQ,它为您提供了一个简单的类似套接字的接口. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |