blackadder has asked for the wisdom of the Perl Monks concerning the following question:

O’ Holy ones

I has been such a long day, although it’s a fairly easy problem……

I have the following script
#! c:/perl/bin -slw use Win32::Registry; use vars qw/%data @source @target/; if ($HKEY_LOCAL_MACHINE->Connect($ARGV[0], my $root)) { print "\nSuccessfully connect to remote registry on $ARGV[0]\n"; if ($root->Open("Software\\Microsoft\\Windows\\CurrentVersion\\Unin +stall", my $Key)) { print "Obtaining software information....Please wait\n"; my @keys; $Key->GetKeys( \@keys ); for my $subkey ( @keys ) { $Key->Open( $subkey, my $x ) or die $^E; my %vals; my $rec; $x->GetValues(\%vals ); for my $item (keys %vals) { $rec->{app} = $vals{$item}[2] if ($item=~ /DisplayName/i); $rec->{path} = $vals{$item}[2] if ($item=~ /InstallSource/ +i); print "$rec->{app} : $rec->{path}\n"; #push (@source, $rec); } } } }
I am trying to capture only the applications ‘DisplayName’ and the ‘InstallSource’ off a remote Win32 registry. However, I do not want any empty entries from the Registry – because I will be piping the results into Excel and I want to avoid any errors – Ultimately I would like to create an array of anonymous hashes contaning this information, but I am not able to do this for some reason, …I tried and tried! Can someone please help? Thanks.

Replies are listed 'Best First'.
Re: capturing entries from the Registry
by eric256 (Parson) on Jun 10, 2004 at 17:01 UTC

    Some explanation of what you ARE getting would be very helpful. Other than that you obviously have the push commented out, so it wont work. If it isn't commented out though it looks like you are pushing the _same_ reference to $rec over and over. Move the my $ref; down into the next loop and it should work as expected. I'm not sure why you are looping over the keys though. It looks like you could just do hash lookups instead of the for my $item (keys %vals) loop.

    $rec->{app} = $vals{DisplayName}[2] if ( exists $vals{DisplayName}); $rec->{path} = $vals{InstallSource}[2] if ( exists $vals{InstallSource +});

    ___________
    Eric Hodges
      Because $rec is declared within the loop the hash/reference storage with the array is OK.(if uncommented as you said)

      Initially when I tried to prove this I saw the same memory address printed each iteration - so I thought you were onto something. I always thought declaration of a lexical within a loop meant new memory was allocated at that declaration, but apparently perl is smart enough that if you're not storing a reference away of the variable that it doesn't allocate new space for it on the next iteration.

      Simply storing away a reference to the variable though changes all that though.

      my @array; for ( 0 .. 5) { my $foo; $foo->{x} = $_; print "$foo->{x} - (Foo = " . $foo . ")\n"; push @array, $foo if (defined($ARGV[0])); } for (my $y = 0; $y < scalar(@array); $y++) { print "Stored Value at $y: $array[$y]->{x}\n"; } =pod When run without $ARGV[0] being defined: 0 - (Foo = HASH(0x182f168)) 1 - (Foo = HASH(0x182f168)) 2 - (Foo = HASH(0x182f168)) 3 - (Foo = HASH(0x182f168)) 4 - (Foo = HASH(0x182f168)) 5 - (Foo = HASH(0x182f168)) and with it defined: 0 - (Foo = HASH(0x182f168)) 1 - (Foo = HASH(0x1825490)) 2 - (Foo = HASH(0x18254d8)) 3 - (Foo = HASH(0x1825520)) 4 - (Foo = HASH(0x1825568)) 5 - (Foo = HASH(0x18255b0)) Stored Value at 0: 0 Stored Value at 1: 1 Stored Value at 2: 2 Stored Value at 3: 3 Stored Value at 4: 4 Stored Value at 5: 5 =cut

        His my needs to be inside the loop though. Here is his

        my $rec; $x->GetValues(\%vals ); for my $item (keys %vals) {

        He then assigns stuff to $rec inside the for loop, not to $item, if it where $item then he would be fine. So the my $rec needs moved down a few lines like..

        $x->GetValues(\%vals ); for my $item (keys %vals) { my $rec;

        But this still doesn't get the desired results because he is looping over the hash keys instead of just looking up the values like i showed in my last post.


        ___________
        Eric Hodges