in reply to communication across threads using hash of hashes

....the thing to remember with shared hashes, is that only the first level hash keys get shared by default.... deeper keys must be explicitly shared as BrowserUk showed

I'm not really a human, but I play one on earth.
Old Perl Programmer Haiku
  • Comment on Re: communication across threads using hash of hashes

Replies are listed 'Best First'.
Re^2: communication across threads using hash of hashes
by stevehicks (Sexton) on Dec 21, 2009 at 10:45 UTC

    Thanks very much for your help guys. I'vd spent a while messing around with this and it does appear that it is because of the seperate package. To make things simpler I've used a scalar. This is the scene :

    I declare the shared var in the main program :
    use threads; use threads::shared; my $sharedTestVar :shared;
    I then "require" at rumtime the plugin name(which equates to a module) that was passed as a parameter to the program :
    ... if(! GetOptions ('plugin=s' => \$plugin,'config=s' => \$instanceName,' +debug' => \$debug, 'interface=s' => \$interface, 'mcastAddress=s' => +\$mcastAddress, 'mcastPort=s' => \$mcastPort, 'file=s' => \$snoopf, ' +remotePcapForwarder=s' => \$remotePCF, 'netprobe=s' => \$netprobe)) { usage(); xit("incorrect options specification", 99); } if($debug) { msg("info : turning on debug"); $ENV{TRACE}=1; $DEBUG=1; } if(! $plugin) { usage(); xit("you must supply a plugin name", 98); } msg("info : plugin \"$plugin\" will be connected"); eval (require "$PALIBDIR/$plugin.pm");
    I then assign a value to the test scalar :
    $sharedTestVar=6; $DEBUG && msg("init : set sharedTestVar == $sharedTestVar");
    I then create a thread and detach it :
    $mcastReaderThread=threads->new(\&doMcastSubscription, $interface,$mca +stAddress,$mcastPort); $mcastReaderThread->detach;
    In the doMcastSubscription sub I increment the scalar :
    sub doMcastSubscription { ... while(1) { my($message,$peer); $drop=1 unless $peer=recv($sock,$message,1400,0); if($drop == 1) { $DEBUG && msg("recv failed"); #sleep(2); } else { $actualPlugin->processMessage("$message"); } $sharedTestVar++; msg("in doMcastSubscription set sharedTestVar == $sharedTestVa +r"); $drop=0; } $DEBUG && msg("leaving doMcastSubscription()"); }
    meanwhile I look at the scalar in the main loop of the program :
    while(1) { ... msg("in main while loop, sharedTestVar == $sharedTestVar"); ... sleep(5); }
    When I do the above, it works fine, i.e the thread updates the shared scalar with no issue. However, when I move the code that increments the scalar to the file that I "required" at runtime it doesn't work. Here's what the thread is doing now :
    sub doMcastSubscription { ... while(1) { my($message,$peer); $drop=1 unless $peer=recv($sock,$message,1400,0); if($drop == 1) { $DEBUG && msg("recv failed"); #sleep(2); } else { $actualPlugin->processMessage("$message"); } $drop=0; } }
    and here's the processMessage sub in UTP.pm :
    sub processMessage { ... if($FeedAgent::sendRateStats) { $sharedTestVar++; msg("in processMessage set sharedTestVar == $sharedTestVar"); + } ... }

    I've tried declaring the shared scalar with "our" instead of "my" but this doesn't help either and not not sure what else to do as this is way past my understanding : * (

    Any ideas ?? My only thought for a workaround is to use shared memory but I'd rather not

    Once again thanks for trying to help, I really appreciate it !!

      I've fixed it, at least in terms of the shared scalar : )

      If I declare the scalar with "our", and then update it in the processMessage sub using "$FeedAgent::sharedTestVar++;" then it works.

      not sure why this works, but it does !!

      Once again thanks very much for your help guys, I'm going to need to share the deeper levels of the shared hash of hashes as you mentioned before

        If I declare the scalar with "our"

        ...see perl global vars in subroutines and Why is 'our' good?

        ....also, get into the habit of locking your shared variables...... i fell into the lazy habit of not locking shared variables on my single cpu machine, and it would work for me, but not on the increasingly common multi-cpu machines


        I'm not really a human, but I play one on earth.
        Old Perl Programmer Haiku