第3回 アクセス制御の実装は“巧妙”かつ“大胆”に


海外 浩平
日本SELinuxユーザ会
2007/10/12


 SE-PostgreSQLによるSQLクエリーの検査

 SE-PostgreSQLは入力されたSQLクエリーを検査し、次に参照されるテーブルやカラム、あるいは呼び出されようとしているSQL関数を抽出していきます。そして、クライアントがこれらのデータベースオブジェクトに対して必要な権限を持っているかどうか、SELinuxに問い合わせて確認します。その結果、必要な権限が不足していれば、現在のトランザクションは即座にアボートされ、クライアントにはエラーが返却されます。また、必要に応じてアクセス拒否ログも生成されます。

 例1:シンプルなSQLに必要な権限を検査する

 それでは、具体的なSQLクエリーの検査例を見ていきましょう。

【注1】
SE-PostgreSQLがSQLクエリーを検査する際に、どういった権限が評価されているかを確認するには、条件変数sepgsql_enable_auditallowの利用が便利です。この条件変数は「アクセスが許可された」ことを示す監査ログを生成し、以下のようにして有効化することができます(デフォルトでは無効化されています)。

[root@masu ~]# setsebool -P sepgsql_enable_auditallow on

詳しくは、連載第2回を参照してください。

 次のシンプルなSQL文は、drinkテーブルからいくつかのカラムを読み出します。その際、priceカラムの値を5%増し(1.05倍)として表示します。

SELECT name, price * 1.05 FROM drink
WHERE id in (3,4);

 クライアントがこのSQLクエリーを実行するには、以下の権限が必要になります。

・nameカラム db_column:{ select }権限
・priceカラム db_column:{ select }権限
・idカラム db_column:{ use }権限
・drinkテーブル db_table:{ select use }権限
・numeric_mul関数 db_procedure:{ execute }権限
・int4eq関数 db_procedure:{ execute }権限

【注2】
「<オブジェクトクラス>:{<パーミッション>}」というのは、SELinuxの権限の表記法です。「db_column:{ select }」とあった場合、データベースのカラムを意味するdb_columnクラスのselect権限という意味になります。

 このSQLクエリーではname、priceカラムを読み出しているため、これらのカラムに対するselect権限が必要です。また、WHERE句の中でidカラムによる絞り込みを行っているため、idカラムに対するuse権限が必要です。どちらの権限もカラムを参照しているという点では同様ですが、WHERE句の中で使われている場合など、カラムに含まれるデータを直接クライアントに返却しない場合はuse権限が適用されます。

 そして、drinkテーブルに対してはselectとuseの2つの権限が必要です。これは、drinkテーブル内のカラムに対して、selectとuseの2種類の操作を行っているために、その和として2つの権限を評価しています。

 残りのnumeric_mul関数とint4eq関数というのは一体何でしょう? 実は、PostgreSQLは演算子をSQL関数として実装しており、numeric_mul関数は「price * 1.05」を計算するため、int4eq関数は「id in (3,4)」条件を評価するために内部的に呼び出されています。

 SQL関数が実行されるという点では、SQL関数を直接クエリーに記述した場合でも、演算子の利用の延長でSQL関数が呼ばれる場合でも、結果は同じですので、SE-PostgreSQLはこのようにSQL関数を実行するために必要なexecute権限をチェックします。

 例2:UPDATE文の実行に必要な権限を検査する

 次の例はやや複雑です。drinkテーブルを更新し、nameを変更、priceを2倍にしています。

UPDATE drink SET name =‘sake’, price = 2 * price
WHERE id = 3;

 SE-PostgreSQLは、このSQLクエリーに対してクライアントが以下の権限を持っているかどうか検査します。

・nameカラム db_column:{ update }権限
・priceカラム db_column:{ select update }権限
・idカラム db_column:{ use }権限
・drinkテーブル db_table:{ use select update }権限
・int4mul関数 db_procedure:{ execute }権限
・int4eq関数 db_procedure:{ execute }権限

 単純に値をセットしているnameカラムにはupdate権限だけが必要ですが、カラムから読み出した値を用いて演算を行い、その値を再びセットしているpriceカラムに対しては、読み出しと更新を同時に行っていると考えることができるため、selectとupdateの2つの権限が同時に必要です。

 先ほどと同じく、idカラムは条件句の評価のみに使われているためにuse権限が必要となり、drinkテーブルに対しては、これらの各カラムの和であるuse、select、update権限が必要となります。

 2つのSQL関数は、先ほどと同じように演算子の実装として呼び出されるものです。int4mul関数は「2 * price」を計算するため、int4eq関数は「id = 3」条件を評価するために呼び出され、SE-PostgreSQLはSQL関数のexecute権限をチェックします。

【注3】
なお、オブジェクトクラスとパーミッションの一覧は、「The Security-Enhanced PostgreSQL security guide」の「3.DBオブジェクトとパーミッション」を参照してください。

2/3

Index
アクセス制御の実装は“巧妙”かつ“大胆”に
  Page1
PostgreSQLのクエリー処理手順を理解する
SE-PostgreSQLによる拡張
Page2
SE-PostgreSQLによるSQLクエリーの検査
例1:シンプルなSQLに必要な権限を検査する
例2:UPDATE文の実行に必要な権限を検査する
  Page3
行レベルのアクセス制御
特殊ケース(OUTER JOIN)への対応
参考情報:Fedora 8 以降での SE-PostgreSQL


SE-PostgreSQLによるセキュアDB構築 連載インデックス


Security&Trust フォーラム 新着記事
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Security & Trust 記事ランキング

本日 月間