Linuxでは、openat
システムコールを使用してファイルを生成し、ファイルが存在するかどうかをテストできます。 C / C ++メモリモデルに関する限り、ファイルを生成してその存在を確認すると、同期関係が生成されます。私が知る必要があるのは、これらの同期がすべて順次一貫しているかどうかです。 (確かにそうしたいのですが、実際にこの内容がどこでも文書化されているのを見たことはありません。)
たとえば、プロセスp1とp2、パスAとBがあるとします。
p1が次のことを行う場合:生成(A)を作成してから生成(B)
p2 は次のことを行います。開こうとした後(B)、開こうとします(A)。
そして、AやBを妨げる他のプロセスがない場合、p2がBを正常に開いたが、Aが見つからない可能性はありますか?
むしろ、すべてのタスクがファイルシステム内にあると仮定できます。
答え1
すべての基本ディスクとマルチコアCPU最適化では、2つのプロセス間の作業順序の厳密な順序を決定することはできません。これが時間依存動作の可能性がある場合、セマフォを使用する理由です。
答え2
同じディレクトリにあるファイルでのみ機能します。
読み取りアクセス。ロックルール:呼び出し側は、私たちがアクセスしているディレクトリをロックします。ロックは共有されます。
オブジェクトの作成。ロックルール:上記と同じですが、ロックは排他的です。
オブジェクトの削除。ロックルール:呼び出し元は親をロックし、被害者を見つけ、被害者をロックし、メソッドを呼び出します。ロックは排他的です。
rename()
それはいいえディレクトリ全体にわたって。ロックルール:呼び出し側は親エントリをロックし、ソースと宛先を見つけます。交換する場合はRENAME_EXCHANGE
両方ともロックします(flag引数を使用)。それにもかかわらず、ターゲットがすでに存在する場合はロックされます。ソースがディレクトリでない場合はロックされます。両方をロックするには、inodeポインタの順序でロックします。次に、メソッドを呼び出します。すべてのロックは排他的です。注:共有ソース(およびスワップの場合はターゲット)をロックできます。リンクの作成。ロックルール:
親ロック
ソースがディレクトリではないことを確認してください。
ロックソース
このメソッドを呼び出します。すべてのロックは排他的です。
ディレクトリ間の名前変更。全体の群れの中で最も大変です。ロックルール:
ファイルシステムのロック
親項目を「先祖優先」順にロックします。
ソースとターゲットを見つけてください。
前の親がターゲットと同じか、ターゲットの子である場合は失敗します。
ENOTEMPTY
新しい親がソースと同じか、ソースの子である場合は失敗します。
ELOOP
スワップの場合は、ソースとターゲットをロックします。
ターゲットがあればロックします。ソースがディレクトリでない場合はロックされます。両方をロックするには、inodeポインタの順序で実行します。
このメソッドを呼び出します。すべて
->i_rwsem
排他的に撮影されました。同様に、共有ソース(およびスワップの場合はターゲット)をロックできます。上記のルールは、メソッドによって読み込まれ、変更または削除されたすべてのディレクトリが呼び出し元によってロックされることを保証します。
ロック力の線形化による動作単一のディレクトリに完全に順番です。ただし、読み取りアクセス(1)、オブジェクトの作成(2)、およびオブジェクトの削除(3)はディレクトリロックよりも広いロックを使用しないため、他のディレクトリでのディレクトリ操作の順序は保証されません。他のオブザーバー ' の線形歴史は、さまざまな方法で交差します。