Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/perl/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
无法向Perl中的Win32::API调用传递压缩句柄数组_Perl_Winapi_Pack - Fatal编程技术网

无法向Perl中的Win32::API调用传递压缩句柄数组

无法向Perl中的Win32::API调用传递压缩句柄数组,perl,winapi,pack,Perl,Winapi,Pack,我正在尝试使用Win32::API从Perl调用Win32 API函数,并将句柄数组传递给它。特定的函数是WaitForMultipleObjects,它不喜欢我向它提供参数的方式。以下是它在Perl中的定义: # DWORD WaitForMultipleObjects(DWORD nCount, HANDLE* handles, BOOL, DWORD) $WaitForMultipleObjects = new Win32::API::More('kernel32',

我正在尝试使用Win32::API从Perl调用Win32 API函数,并将句柄数组传递给它。特定的函数是
WaitForMultipleObjects
,它不喜欢我向它提供参数的方式。以下是它在Perl中的定义:

 # DWORD WaitForMultipleObjects(DWORD nCount, HANDLE* handles, BOOL, DWORD)
 $WaitForMultipleObjects = new Win32::API::More('kernel32',
                                                'WaitForMultipleObjects', 'NPNN', 'N');
然后是句柄数组。所有这些都已确认有效,并且在分别传递到
WaitForSingleObject
时,它们都有效。 以下是我如何打包参数:

   my @handles; 
   ...
   my $n = scalar(@handles);
   my $handlePack = pack "L*", @handles; # also tried 'L1', 'L2', etc.
   $rc = $WaitForMultipleObjects->Call($n, $handlePack, 0, 0xffffffff); # fails
此操作失败,GetLastError()报告错误6(句柄无效)。 但是,如果我只传递一个句柄,它将起作用:

   my $handlePack = pack "L", $handles[0];
   $rc = $WaitForMultipleObjects->Call(1, $handlePack, 0, 0xffffffff); # works

显然,Win32::API无法在第二个参数中正确传递句柄数组,但就我对文档()的理解而言,应该是这样的。还是我使用的
pack()
有误?如果需要的话,我使用的是64位Perl

问题是64位。在64位Windows(以及64位Perl)上,sizeof(HANDLE)=8个字节。因此,如果程序在64位Perl中运行,它将加载64位DLL,并且必须使用
Q
(即64位整数)打包句柄。使用
L
将不起作用,因为它包含32位整数。以下内容修复了该问题:

use Config qw( %Config );

my $ptr_size = $Config{ptrsize};
my $ptr_format =
   $ptr_size == 4 ? "L" :
   $ptr_size == 8 ? "Q" :
   die("Unsupported pointer size $ptr_size\n");

my $handlePack = pack $ptr_format."*", @handles; 

$rc = $WaitForMultipleObjects->Call($n, $handlePack, 0, 0xffffffff);
请注意,即使在64位Perl中,
pack('I')
仍然可以生成32位(取决于编译器)
pack('J')
(Perl的内部int)也不合适,因为它至少与指针一样大,但也可能更大(例如,使用
-duse64bit
构建的32位Perl)