문제

다음 서브 루틴으로 40 개 또는 스레드를 실행하고 있습니다.

my $app = shift;
my $ua = LWP::UserAgent->new();
$ua->timeout(5);
my $response = $ua->get($$app{'watch_url'});
my $new_md5;
if ($response->is_success()) {
    $new_md5 = md5_hex($response->content());
}
return ($$app{'short_name'}, $$app{'watch_md5'}, $new_md5);

코어 덤프는 시간의 약 3/4로 이어집니다. lwp와 lwp :: useragent는 순수한 perl이므로 이것에 의해 오프 가드가 잡혔습니다. lwp :: useragent가 스레드-안전하지 않습니까?

업데이트:

다음은 문제를 재현하기위한 최소 버전입니다.

use strict;
use warnings;
use threads;
use LWP::UserAgent;

sub check_app {
    my $ua = LWP::UserAgent->new();
    $ua->timeout(5);
    $ua->get('http://www.flatdoc.com/?' . rand(10));
}

my @threads;
for (my $i = 0; $i < 40; $i++) {
    my $thread = threads->create(\&check_app);
    push(@threads, $thread);
}
foreach (@threads) {
    $_->join();
}
도움이 되었습니까?

해결책

비 스레드 Safe Safe Pure-Perl 코드는 segfault를 유발하지 않습니다 (실제로 순수한 Perl 코드는 segfault를 유발하지 않아야합니다). Perl의 버그는 segfault를 유발합니다. 그리고 Perl의 실은 역사적으로 매우 버그가 많지만 훨씬 나아졌습니다.

당신의 코드는 5.10.1에서 잘 실행되며 http :: lite는 아마도 당신이 뛸 수있는 펄 버그를 간질이게하지 않을 것입니다. 아마도 새로운 버전의 Perl을 사용하면됩니다. 더 오래되고 Redhat에 가까울수록 덜 안정적인 스레드가 있습니다. 스레드를 사용하려면 손을 잡을 수있는 최신 Perl을 사용하십시오.

스레드의 대안으로 다음과 같은 것을 사용할 수 있습니다. 병렬 :: 포크 매너, lwp :: 병렬 또는 놀랍도록 포크 포크를 사용하여 스레드를 에뮬레이션하는 모듈.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top