On Tue, 23 Nov 2004 04:41:26 -0500, [EMAIL PROTECTED] (Michael G Schwern) wrote:
> With Test::More 0.50 and threads I get an odd error using skip and threads.
>
> [~/tmp/Test-Simple-0.50] perl5.8.5 -Ilib -wle 'use threads; use Test::More
"no_plan"; pass("foo"); SKIP: { skip "this", 1 }'
> ok 1 - foo
> ok 2 # skip this
> 1..2
> # Looks like you failed 1 test of 2.
>
> Internally what's happening is in Test::Builder->skip. On line 721 it
> does this.
>
> $Test_Results[$Curr_Test-1] = &share({
> 'ok' => 1,
> actual_ok => 1,
> name => '',
> type => 'skip',
> reason => $why,
> });
>
> But for some reason &share() is returning an empty hash.
>
> Elsewhere in the code &share() works fine as evidenced by pass() working.
>
> 0.47 did not tickle this threading bug.
>
> Tested with 5.8.1RC3, 5.8.5 and bleadperl on OS X.
>
> I've got a work around that involves a wrapper around share() to make a
> copy of the variable to be shared, share it, then put the data back.
>
> require threads::shared;
>
> *share = sub ([EMAIL PROTECTED]) {
> my $type = ref $_[0];
> my $data;
>
> if( $type eq 'HASH' ) {
> %$data = %{$_[0]};
> }
> elsif( $type eq 'ARRAY' ) {
> @$data = @{$_[0]};
> }
> elsif( $type eq 'SCALAR' ) {
> $$data = ${$_[0]};
> }
> else {
> die "Unknown type: ".$type;
> }
>
> $_[0] = &threads::shared::share($_[0]);
>
> if( $type eq 'HASH' ) {
> %{$_[0]} = %$data;
> }
> elsif( $type eq 'ARRAY' ) {
> @{$_[0]} = @$data;
> }
> elsif( $type eq 'SCALAR' ) {
> ${$_[0]} = $$data;
> }
> else {
> die "Unknown type: ".$type;
> }
>
> return $_[0];
> };
>
> Bleh.
>
This is the same bug/limitation of threads::shared I reported in perlbug #30702.
Then, it was essentially dismissed as being "working as designed":
Nick Ing-Simmons wrote:
> When I 1st did the coding for sharing there was a deliberate policy
> not to do that. In general the contents of an array or hash can
> contain reference loops, so "walking" the contents to share it is
> slightly tricky (it has to be done depth first but breaking loops).
>
> So you are supposed to share the array/hash and then populate it,
> and loops etc. are programmer's problem.
>
> Scalars are shared using raw 'MAGIC' rather than a normal tie, which
> is slightly more efficent, and naturally gives access to the
> original value.
I have to say that I disagree strongly.
Whilst writing code to walk an arbitrary array or hash structure is very
complex to get right, doing it once, properly, in library code *has* to
be better than expecting every user to write their own!
Without the ability to share previously populated datastructures, without
requiring them to be copied manually, (given that shared datastructures are
already duplicated per thread), makes having the notional ability to share
anything other than simple scalers almost useless.
Add to that, that any attempt to lock() individual elements of a shared data
structure fail (upto 5.8.5), and you have a sharing mechnism that is alomost
useless.
njs.
>
> --
> Michael G Schwern [EMAIL PROTECTED] http://www.pobox.com/~schwern/
> Kindly do not attempt to cloud the issue with facts.