class TestCase::ThreadSafe {
use Point;
use TestCase::Util::Thread;
use TestCase::Util::Thread::ID;
use TestCase::Util::Thread::ThisThread;
use TestCase::Operator::Data::Weaken;
static method assign : int () {
# undef
{
my $point_ref = [(Point)undef];
my $thread = TestCase::Util::Thread->new([$point_ref : Point[]] method : void () {
for (my $i = 0; $i < 10000; $i++) {
my $point = Point->new;
$point_ref->[0] = $point;
}
});
my $thread2 = TestCase::Util::Thread->new([$point_ref : Point[]] method : void () {
for (my $i = 0; $i < 10000; $i++) {
$point_ref->[0] = undef;
}
});
$thread->join;
$thread2->join;
}
# All patterns
{
my $point_ref = [(Point)undef];
my $thread = TestCase::Util::Thread->new([$point_ref : Point[]] method : void () {
for (my $i = 0; $i < 10000; $i++) {
my $point = Point->new;
$point_ref->[0] = $point;
$point_ref->[0] = $point;
$point_ref->[0] = Point->new;
$point_ref->[0] = undef;
$point_ref->[0] = Point->new;
}
});
my $thread2 = TestCase::Util::Thread->new([$point_ref : Point[]] method : void () {
for (my $i = 0; $i < 10000; $i++) {
my $point = Point->new;
$point_ref->[0] = $point;
$point_ref->[0] = $point;
$point_ref->[0] = Point->new;
$point_ref->[0] = undef;
$point_ref->[0] = Point->new;
}
});
$thread->join;
$thread2->join;
unless ($point_ref->[0] is_type Point) {
return 0;
}
}
return 1;
}
static method weaken : int () {
my $object1 = new TestCase::Operator::Data::Weaken;
$object1->{x} =1;
my $object2 = new TestCase::Operator::Data::Weaken;
$object2->{x} = 2;
# Circular reference
$object2->{data_weaken} = $object1;
$object1->{data_weaken} = $object2;
{
my $object_ref = [(TestCase::Operator::Data::Weaken)$object1, $object2];
my $thread = TestCase::Util::Thread->new([$object_ref : TestCase::Operator::Data::Weaken[]] method : void () {
for (my $i = 0; $i < 10000; $i++) {
my $object = $object_ref->[0];
weaken $object->{data_weaken};
$object->{data_weaken} = $object->{data_weaken};
unweaken $object->{data_weaken};
$object->{data_weaken} = $object->{data_weaken};
isweak $object->{data_weaken};;
}
});
my $thread2 = TestCase::Util::Thread->new([$object_ref : TestCase::Operator::Data::Weaken[]] method : void () {
for (my $i = 0; $i < 10000; $i++) {
my $object = $object_ref->[0];
weaken $object->{data_weaken};
$object->{data_weaken} = $object->{data_weaken};
unweaken $object->{data_weaken};
$object->{data_weaken} = $object->{data_weaken};
isweak $object->{data_weaken};;
}
});
$thread->join;
$thread2->join;
unless ($object1->{x} == 1 && $object2->{x} == 2) {
return 0;
}
weaken $object1->{data_weaken};
}
return 1;
}
}