Как я делаю не блокирующееся чтение IPC в Windows?

It’s серая область. Эти принципалы предназначены для помощи Вам в Вашей работе при нахождении you’re, работающего на них (т.е. стоящий на пути they’re, и/или Вы находите, что это усложняет Ваш код), тогда you’re приспосабливание слишком трудно, и необходимо отступить.

Делают, это работать на Вас, don’t работает на него.

6
задан Michael Carman 20 October 2009 в 19:26
поделиться

3 ответа

select работает только с сокетами в Windows. Похоже, IPC :: OpenX использует обычные дескрипторы файлов, поэтому вы не сможете использовать select с дескрипторами, которые он создает.

Если вам не нужен тайм-аут / обнаружение активности, выберите предоставляет, вы можете настроить дескрипторы как неблокирующие и просто читать или писать как обычно.

Если вам нужно более тонкое управление, IPC :: Run может вам подойти.

Вы также можете посмотреть на создание пары сокетов и использовать эти дескрипторы со своими дочерними процессами. Более новые Perls (5.8 и выше) поддерживают эмуляцию socketpair в Windows с использованием сокетов TCP.

Если вы попытаетесь клонировать STDOUT и STDERR для запущенной программы без консоли (т.е. запускается с помощью wperl, а не perl), вы не сможете получать данные через STDIO.

На практике это было огромной болью для меня в нескольких проектах. Я обнаружил, что лучше всего работает дочерний процесс для подключения к родительскому серверу через TCP. Если вы не контролируете дочерние процессы, посмотрите IPC :: Run или socketpair .

5
ответ дан 17 December 2019 в 02:30
поделиться

Другой кладж - использовать sysread с большим или маловероятным размером буфера.

    print $cin "$command_for_cleartool\n";
    my ($description, $maxlen, $buffer) = ("", 65336);
    while (my $n = sysread $cout, $buffer, $maxlen) {
        $description .= $buffer;
        last if $n < $maxlen;
    }
    ... do something with $description ...

sysread зависнет, если есть ровно 0 байтов ввода, ожидающих чтения. Таким образом, приведенный выше код зависнет, если cleartool выдаст ровно некоторое количество, кратное 65336 байтам. Если вам известен хороший верхний предел размера вывода программы, вы можете использовать это значение для $ maxlen выше. В противном случае вы могли бы выбрать большое и маловероятное число и помолиться ...

вы можете использовать это значение для $ maxlen выше. В противном случае вы могли бы выбрать большое и маловероятное число и помолиться ...

вы можете использовать это значение для $ maxlen выше. В противном случае вы могли бы выбрать большое и маловероятное число и помолиться ...

1
ответ дан 17 December 2019 в 02:30
поделиться

Неблокирующий ввод-вывод затруднен в Windows. В этом случае вы можете отправить вывод cleartool в обычный файл и использовать seek для сброса флага eof в файле каждый раз при чтении из файла:

my($cin, $cout);
my $somefile = "some/file";
open($cin, "| cleartool > $somefile");
open($cout, '<', $somefile);

...

print $cin "$command_for_cleartool\n";
# if necessary, wait until cleartool finishes with new output
seek $cout, 0, 1;     # clear eof condition from previous read
my @cleartool_output = <$cout>;  # capture recent output
... process output ...

Хотя это, вероятно, не будет работают хорошо, если cleartool буферизует свой вывод.

0
ответ дан 17 December 2019 в 02:30
поделиться
Другие вопросы по тегам:

Похожие вопросы: