G'day Stackoverflowers,
Я автор Perl autodie pragma, который изменяет встроенные в Perl блокировки исключений при сбое. Он похож на Fatal, но с лексической областью, расширяемой моделью исключений, более интеллектуальной проверкой возврата и гораздо более приятными сообщениями об ошибках. Он будет заменять модуль Fatal
в будущих выпусках Perl (временно 5.10.1+), но в настоящее время может быть загружен из CPAN для Perl 5.8.0 и выше.
В следующей версии autodie
будет добавлена специальная обработка для вызовов flock
с опцией LOCK_NB
(неблокирующая). Хотя неудачный вызов flock
обычно приводит к исключению в autodie
, неудачный вызов flock
с использованием LOCK_NB
будет просто возвращать значение false, если возвращаемое errno ($!
) равно EWOULDBLOCK
.
Причиной этого является то, что люди могут продолжать писать код вроде:
use Fcntl qw(:flock);
use autodie; # All perl built-ins now succeed or die.
open(my $fh, '<', 'some_file.txt');
my $lock = flock($fh, LOCK_EX | LOCK_NB); # Lock the file if we can.
if ($lock) {
# Opportuntistically do something with the locked file.
}
В приведенном выше коде блокировка, которая терпит неудачу, потому что кто-то еще имеет заблокированный файл (EWOULDBLOCK
), не считается жесткой ошибкой, поэтому autodying flock
просто возвращает значение false. В ситуации, когда мы работаем с файловой системой, которая не поддерживает файловые блокировки, или сетевая файловая система и сеть просто умерли, тогда autodying flock
генерирует соответствующее исключение, когда видит, что наша ошибка не EWOULDBLOCK
.
Это отлично работает в моей dev-версии на Unix-ароматизированных системах, но это ужасно терпит неудачу под Windows. Похоже, что хотя Perl под Windows поддерживает параметр LOCK_NB
, он не определяет EWOULDBLOCK
. Вместо этого возвращаемое errno равно 33 ( "Ошибка домена" ), когда произойдет блокировка.
Очевидно, я могу жестко записать это как константу в autodie
, но это не то, что я хочу сделать здесь, потому что это означает, что я ввернута, если errno когда-либо изменяет (или изменилось). Мне бы хотелось сравнить его с эквивалентом Windows POSIX::EWOULDBLOCK
, но я не могу в жизни меня найти, где такое будет определено. Если вы можете помочь, сообщите мне.
Ответы, которые я конкретно не хочу:
- Предложения жестко закодировать его как константу (или, что еще хуже, оставить плавающее магическое число).
- Не поддерживает
LOCK_NB
функциональность вообще под Windows. - Предполагая, что любой сбой вызова
LOCK_NB
наflock
должен возвращать только false. - Предложения, которые я задаю на p5p или perlmonks. Я уже знаю о них.
- Объяснение того, как
flock
, или исключения, илиFatal
работают. Я уже знаю. Тесно.