3

一言で言えば:flock()を使用してPerlスクリプトを作成しました。Linuxでは、期待どおりに動作します。AIXでは、flock()を使用するスクリプトの別のインスタンスがロックファイルの排他ロックを保持している必要がある場合でも、flock()は常に1を返します。

プログラムを再起動するためのBashスクリプトを出荷し、flock(1)を使用して、同時再起動によって複数のプロセスが作成されるのを防ぎます。最近、AIXにデプロイしました。この場合、flock(1)はデフォルトでは提供されず、管理者によって提供されません。物事を単純に保つことを望んで、私は次のようにflockと呼ばれるPerlスクリプトを書きました。

#!/usr/bin/perl

use Fcntl ':flock';
use Getopt::Std 'getopts';

getopts("nu:x:");

%switches = (LOCK_EX => $opt_x, LOCK_UN => $opt_u, LOCK_NB => $opt_n);

my $lockFlags = 0;

foreach $key (keys %switches) {
    if($switches{$key}) {$lockFlags |= eval($key)};
}

$fileDesc = $opt_x || $opt_u;

open(my $lockFile, ">&=$fileDesc") ||  die "Can't open file descriptor: $!";
flock($lockFile, $lockFlags) || die "Can't change lock - $!\n";;

(flock -n -x 200; sleep 60)200> lockfileを2つのターミナルタブからほぼ同時に2回実行して、スクリプトをテストしました。

Linuxでは、予想どおり、2回目の実行は「リソースが一時的に利用できません」で終了します。

AIXでは、2回目の実行でロックが取得され、flock()は1を返しますが、これは間違いなく予期されていません。

flock()は、flock(1)を使用するLinuxバージョンとfcntl(1)を使用するAIXバージョンの2つのシステムで異なる方法で実装されていることを理解しています。これが私の問題をどのように引き起こし、どのように解決するかを理解するのに十分な専門知識がありません。

アドバイスをありがとうございます。

4

2 に答える 2

2

異なるコマンドについてではないと思います。それは、AIXとLinuxのグローバルな違いに関するものです。

POSIXシステムでは、ファイルロックは助言的です。各プログラムはファイルの状態をチェックしてから、ファイルで何をしなければならないかを再考することができます。明示的なチェックなし=ロックなし。

ただし、Linuxシステムでは、必須のロックを強制することを試みることができますが、ドキュメント自体は、それに依存するのは賢明ではないと述べています。実装にはバグがあります(おそらくこれからもそうなるでしょう)。

したがって、スクリプト自体にこのようなアドバイザリフラグのチェックを実装することをお勧めします。

それについての詳細:man 2 fcntlman2flock

于 2012-04-27T09:40:15.360 に答える
1

これはAIXとは何の関係もありません。スクリプトのopen()呼び出しは正しくありません。

次のようなものにする必要があります:

open (my $lockfile, ">>", $fileDesc) # for LOCK_EX, must be write

で「dup()以前に開いたファイルハンドル」構文を使用し>&=ていましたが、スクリプトは複製するファイルを開いていませんでした。

私のクイックテストは正しい動作を示しています(デバッグが追加されました)

first window:
$ ./flock.pl -n -x lockfile
opened lockfile
locked
second window:
$./flock.pl -n -x lockfile
opened lockfile
Can't change lock - Resource temporarily unavailable
$
于 2012-04-27T22:24:47.590 に答える