LINUX.ORG.RU

PHP: Imagick & pcntl_fork

 ,


0

1

Всех приветствую! Пишу многопоточный скрипт на php, который анализирует изображения. Он создаёт ресурс изображения (в моём случае это Imagick), потом делится с помощью pcntl_fork(), потом вызывает на этом ресурсе какой-нибудь фильтр (например, despeckle). Так вот странно то, что если используется работа в один поток, то время применения фильтра около 0.14 сек, а на двух потоках - уже 1.14 (внутри каждого). На трёх уже больше 2.5 сек. Не могу понять, что происходит, за какие ресурсы между потоками может происходить конкуренция? Вроде у каждого процесса своя память (общей памяти между процессами в php нет, shmop не в счёт). Диск тоже не задействуется (изображение уже прочитано в память). Видеокарта простаивает. Какие-то взаимные блокировки?

Вот кусок кода для ориентировки:

$sketchFile = '/path/to/file.jpg';

$tmpMagick = new \Imagick();
$tmpMagick->setResolution(300, 300);
$tmpMagick->readImage($sketchFile);

$threads = 3;

$workerPids = array();

for($i = 1; $i < $threads; $i++){ 
    $pid = pcntl_fork();
    if($pid == -1){
        throw new \Exception('Couldn\'t fork()!');
    }elseif($pid > 0){
        //parent
        $workerPids[] = $pid;
    }else{
        //child
        break;
    }
}

$start = microtime(true);
$tmpMagick->despeckleImage();
$duration = round(microtime(true) - $start, 4);
fwrite(\STDERR, 'time: '.$duration.' sec'."\n");

Нелогичность применения одного и того же фильтра в разных потоках на ресурсе одного и того же изображения прошу не озвучивать. :) Это может быть оправдано при нескольких страницах изображений внутри одного Imagick, где каждый поток выполняет фильтр к своей странице. Просто случайно столкнулся вот с такими «тормозами» и не могу понять, откуда у них ноги растут. Буду признателен за любые предположения!

P.S.: физических ядер у меня шесть, если что. Это к тому, что не за процессор идёт конкуренция.