For Programmers: Free Programming Magazines  


Home > Archive > PERL Programming > June 2005 > how to define a SAFEARRAY in perl









You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

 

Author how to define a SAFEARRAY in perl
Scott

2005-06-03, 3:56 am

Hello All

we are trying to call (COM method via IIS and SOAP)

STDMETHODIMP CSoapReciever::PutDetails(SAFEARRAY **int_args, SAFEARRAY
**string_args)

from perl via soap


we are trying to define and load the SAFEARRAY's in perl as follows.

sub soapPutClientDetails {
# Setup SOAP:
my $soap = SOAP::Lite
-> service($serviceUrl);

my $IntArray;
my $StrArray;

$IntArray->[0] = 826;
$IntArray->[1] = 3;

$StrArray->[0] = 'string';
$StrArray->[1] = 'string2';
$StrArray->[2] = 'string3';
$StrArray->[3] = 'string4';
$StrArray->[4] = 'string5';

# call PutClientDetails. We use $cgi->param (not $R) to ensure
only use first value of any multi value entries
my $regClientRes = $soap->PutDetails ($IntArray, $StrArray);
}

This results in errors, we have no trouble returning a SAFEARRAY and
parsing the values but have trouble passing one in. The method above
simply reverses the method we use to parse the returned SAFEARRAY.

I can call this COM method successfully in C++ and I am logging
arguments to file. But it seems I never actually get into the function
body via soap. This leads me to believe there is some error in the
array declaration in perl or soap type conversion of the arguments
(SAFEARRAY).

Can anyone see where I am going wrong ?

Thanks


tlviewer

2005-06-04, 3:57 am


"Scott" <sthoma12@bigpond.net> wrote in message
news:umnv91l3ph79ijei627aepkv0leu72v5kn@
4ax.com...
>
> we are trying to define and load the SAFEARRAY's in perl as follows.
>
> sub soapPutClientDetails {
> # Setup SOAP:
> my $soap = SOAP::Lite
> -> service($serviceUrl);
>
> my $IntArray;
> my $StrArray;
>
> $IntArray->[0] = 826;
> $IntArray->[1] = 3;
>
> $StrArray->[0] = 'string';
> $StrArray->[1] = 'string2';
> $StrArray->[2] = 'string3';
> $StrArray->[3] = 'string4';
> $StrArray->[4] = 'string5';
>
> # call PutClientDetails. We use $cgi->param (not $R) to ensure
> only use first value of any multi value entries
> my $regClientRes = $soap->PutDetails ($IntArray, $StrArray);
> }


Here's a sample WMI script that allocates for Variant arrays, aka SAFEARRAY.
Notice the calls to
Variant()
Check out the Win32::OLE docs for more details.

regards,
tlviewer


#!/usr/bin/perl -w
use Win32::OLE::Variant qw(:DEFAULT nothing);

my $HKLM = 0x80000002;
(my $machine = shift @ARGV || "." ) =~ s/^[\\\/]+//;

my $locator = Win32::OLE->new('WbemScripting.SWbemLocator')
or die "Cannot access WMI on local machine: ", Win32::OLE->LastError;

my $WMIServices = $locator->ConnectServer('.', "root\\default")
or die "Cannot access WMI on remote machine: ", Win32::OLE->LastError;

my ($objRegistry, $sValue, $sKey);
$objRegistry= $WMIServices->Get("StdRegProv") or
die "Cannot create Registry Object :", Win32::OLE->LastError;

# init as integer
my $iRC = 0;

# allocate space for Variant BSTR
my $sout = Variant(VT_BSTR | VT_BYREF, "");

my $sPath = " SOFTWARE\\Microsoft\\Windows\\CurrentVer
sion";

# yours is not to do or Die (for once, haha )
$iRC= $objRegistry->GetStringValue($HKLM, $sPath,
"ProductId", $sout ); # or die( "failed \n" , Win32::OLE->LastError);
print $sout, " \n";

# allocate for variant_array_of_variants (vartype 8204)
my $arr = Variant( VT_ARRAY | VT_VARIANT | VT_BYREF , [1,1] );

$sPath = " SOFTWARE\\Microsoft\\Windows\\CurrentVer
sion\\Uninstall";

# Do not use Die for this method
$iRC = $objRegistry->EnumKey($HKLM, $sPath, $arr); # or die "Cannot fetch
registry key :", Win32::OLE->LastError;

foreach my $item ( in( $arr->Value ) )
{
print "$item \n";
} # end foreach

__END__





Sponsored Links







Also available: Server administration forum archive | Web Design forum archive | Software forum archive | Hardware reviews archive

Copyright 2008 codecomments.com