The OpenNET Project / Index page

[ новости /+++ | форум | теги | ]

Как создать лок файл на Perl
Для защиты от одновременного запуска нескольких процессов, можно сделать так:

use Fcntl qw(:flock :DEFAULT);
my $cfg_glob_lock="/var/run/myprog/test.pid";

# Проверяем лок.
if (-f $cfg_glob_lock){
      # Лок присутствует. Проверяем не дохлый ли процесс.
      my $lock_pid = 0;
      open(LOCK,"<$cfg_glob_lock");
      # Если удалось заблокировать, значит процесс мертв.
      my $zombie_lock_flag = flock(LOCK,  LOCK_EX|LOCK_NB);
      $lock_pid = <LOCK>;
      close (LOCK);
      chomp ($lock_pid);
      if ($lock_pid > 0 && $zombie_lock_flag == 0){
          # Реакция на зависший процесс.                                        
          die "Proccess locked (pid=$lock_pid)";
      } else {
          # Лок от мертвого процесса.
          unlink("$cfg_glob_lock");
          warn("DeadLock detected ($lock_pid)");
      }
}    
# Записываем pid в новый лок файл.
sysopen(LOCK, $cfg_glob_lock, O_CREAT|O_EXCL|O_WRONLY) or die 'Race condition';

print LOCK "$$\n";
close(LOCK);
# Открываем лок.
open(GLOB_LOCK,"<$cfg_glob_lock");
flock(GLOB_LOCK,  LOCK_EX);

.... рабочий код скрипта

# Закрываем и удаляем лок
flock(GLOB_LOCK, LOCK_UN);
close(GLOB_LOCK);
unlink("$cfg_glob_lock");
 
20.01.2005
Ключи: perl, lock / Лицензия: CC-BY
Раздел:    Корень / Программисту и web-разработчику / Perl / Полезные подпрограммы на Perl / Работа с сетью и IP адресами на Perl

Обсуждение [ RSS ]
  • 1.1, Сергей (??), 17:08, 20/01/2005 [ответить]  
  • +/
    А если чужой файл появился в промежутке между
    if (-f $cfg_glob_lock){
    и
    open(LOCK,">$cfg_glob_lock"); ?

    man 2 open
    /EX

    Все другие варианты, к сожалению, нерабочие ;(

     
     
  • 2.2, Maxim Chirkov (ok), 23:22, 20/01/2005 [^] [^^] [^^^] [ответить]  
  • +/
    >А если чужой файл появился в промежутке между
    >if (-f $cfg_glob_lock){
    >open(LOCK,">$cfg_glob_lock"); ?

    Полностью согласен, поправил в контексте использования sysopen(LOCK,$cfg_glob_lock, O_CREAT|O_EXCL|O_WRONLY), можно также вариант блокировки хардлинками привести.

    Для борьбы с использованием Race Condition в плане безопасности еще хорошо помогает монтирование world writable разделов с nosymfollow и создание локов/временных файлов в недоступных для посторонних местах.


     
     
  • 3.3, Сергей (??), 09:06, 21/01/2005 [^] [^^] [^^^] [ответить]  
  • +/
    Ещё (я не зануда ;-):

    лучше всё-таки использовать символьные константы O_CREAT и прочие, они от юникса к юниксу отличаются, а мы же боремся за переносимость ;)

    И по поводу хардлинков не всё так просто: на монтированных файловых системах, типа той же самбы, их не будет, что приведёт к очевидным проблемам.
    Впрочем, вариант с open тоже имеет трудности на некоторых реализациях NFS, но этим, пожалуй, уж точно можно пренебречь.

     
     
  • 4.4, Maxim Chirkov (ok), 10:01, 21/01/2005 [^] [^^] [^^^] [ответить]  
  • +/
    >лучше всё-таки использовать символьные константы O_CREAT и прочие, они от юникса к
    >юниксу отличаются, а мы же боремся за переносимость ;)

    Поправил.

    >И по поводу хардлинков не всё так просто: на монтированных файловых системах,
    >типа той же самбы, их не будет, что приведёт к очевидным
    >проблемам.
    >Впрочем, вариант с open тоже имеет трудности на некоторых реализациях NFS, но
    >этим, пожалуй, уж точно можно пренебречь.

    А для samba разделов  open лок точно без проблем работает  ? Просто на них тот же File::Find без рукоприкладства ($File::Find::dont_use_nlink=1) неработоспособен.

    Впринципе, для локов хардлинками на CPAM есть готовый модуль File::NFSLock.

     
     
  • 5.5, Сергей (??), 15:12, 21/01/2005 [^] [^^] [^^^] [ответить]  
  • +/
    Да, open точно работает, по крайней мере на C я проверял. Perl тоже должен, обвязка же в итоге сводится к вызову open(2) AFAIK.
    Не работает для платформ DOS-OS2-Win, там только через rename, потому что очень сильно зависит от реализации библиотеки, да и в случае хорошей библиотеки нельзя закладываться на это ;-(
    Мака под рукой нету, VMS тоже, на них не проверял ;-)
     

  • 1.6, Критик (?), 13:50, 24/02/2005 [ответить]  
  • +/
    Пародон, а чем use Proc::Lock::File; уже устарел???
     

     Добавить комментарий
    Имя:
    E-Mail:
    Заголовок:
    Текст:




    Партнёры:
    PostgresPro
    Inferno Solutions
    Hosting by Hoster.ru
    Хостинг:

    Закладки на сайте
    Проследить за страницей
    Created 1996-2024 by Maxim Chirkov
    Добавить, Поддержать, Вебмастеру