Trusted Solaris 開発ガイド

第 6 章 ラベルのコード例

この章では、第 5 章「ラベル」で説明しているプログラミングインタフェースの使用方法を示すコード例を挙げています。

バージョン文字列の取得

機密ラベル、認可上限などの構成要素、およびプリンタ出力に表示される取り扱い警告は、サイト固有の label_encodings(4) ファイルで指定されます。この章で説明するプログラミングインタフェースの一部は、label_encodings ファイル内の記述にアクセスします。そのため、それぞれのサイトで使用している label_encodings ファイルに応じて、出力が異なります。

次の例は、この章のいくつかのコード例でアクセスする label_encodings ファイルのバージョン文字列を取得し、コマンド行に出力します。

#include <tsol/label.h>

 main()
 {
 	int			retval, length = 0;
 	char			*version = (char *)0;

 	retval = labelvers(&version, length);
 	if(retval > 0)
 		printf("Version string = %s¥n", version);
 }

printf 文によって、次のように出力されます。


Version string = TRUSTED SOLARIS MULTI_LABEL DEMO VERSION - 5.1 96/09/27

バイナリラベルの初期化と型のチェック

次のインタフェースは、ラベルを ADMIN_HIGHADMIN_LOW、および未定義に初期化します。ADMIN_HIGH はもっとも高い格付け番号であり、すべてのコンパートメントとマーキングを含んでいます。ADMIN_HIGH は、システム内のほかのすべてのラベルより完全に優位です。通常のユーザーは、ADMIN_HIGH のファイルの読み書きはできません。

ADMIN_LOW は、コンパートメントもマーキングも含まない 0 の格付けを示します。すべてのユーザーは、機密ラベル ADMIN_LOW のファイルの読み取りまたは実行ができます。しかし、通常のユーザーは ADMIN_LOW のファイルへの書き込みはできません。システム内のほかのすべてのラベルは、ADMIN_LOW より完全に優位です。ADMIN_LOW は、アクセスが公開されているシステムファイルやコマンドに割り当てられます。

未定義は NULL と同様に、無効なラベルを示します。機密ラベルは、ID フィールドが SUN_SL_UN に初期化された場合、未定義になります。未定義のラベルは無効です。CMW ラベルには未定義状態はなく、機密ラベル部と情報ラベル部だけが未定義状態になることがあります。

CMW ラベル、機密ラベルは、ラベル構造の ID フィールドが SUN_CMW_ID または SUN_SL_ID のいずれかに初期化され定義された状態になります。定義済みの CMW ラベルに含まれる機密ラベル部や情報ラベル部は、定義済みの場合と未定義の場合があります。

次の例は、ラベルを未定義、ADMIN_HIGHADMIN_LOW に初期化し、続いてラベルの型をチェックして出力します。

#include <tsol/label.h>

 main()
 {
 	int					retval;
 	
 	bslabel_t					psenslabel;
 	bclabel_t					pCMWlabel;

/* ラベルを初期化する*/
 	bclundef(&pCMWlabel);
 	bslhigh(&psenslabel);
 	
/* ラベルの型を調べる */
 	retval = bltype(&psenslabel, SUN_SL_ID);
 	printf("Is sensitivity label defined? %d¥n", retval);
 	
/* CMW ラベル型を定義済みにする */
 	setbltype(&pCMWlabel, SUN_CMW_ID);
 	retval = bltype(&pCMWlabel, SUN_CMW_ID);
 	printf("Is CMW label defined? %d¥n", retval);
 }

printf 文によって、次のように出力されます。0 以外は true で、0 は false を示します。

Is sensitivity label defined? 1

Is CMW label defined? 0

プロセス CMW ラベルの取得

プロセスの CMW ラベルを取得した際に、CMW ラベルを一単位として処理することも、また、1 つあるいは両方のラベル部を抽出し、ラベル部だけを処理することもできます。次の例では、プロセスの CMW ラベルを取得し、機密ラベル部と情報ラベル部を抽出し、プロセス CMW ラベルを ASCII 文字列に変換し、出力します。

#include <tsol/label.h>

 main()
 {
 	int					retval, length = 0;
 	bclabel_t					pCMWlabel;
 	bslabel_t					psenslabel;
 	bilabel_t					pinflabel;
 	char 					*string;

/* プロセスの CMW ラベルを得る */
 	retval = getcmwplabel(&pCMWlabel);

/* 機密ラベル部と情報ラベル部を得る */
 	getcsl(&psenslabel, &pCMWlabel);
 	getcil(&pinflabel, &pCMWlabel);

/* プロセスの CMW ラベルを ASCII 文字列に変換し、出力する */
 	retval = bcltos(								&pCMWlabel, &string, length, LONG_CLASSIFICATION);
 	printf("Process CMW label = %s¥n", string);
 }

printf 文によって、次のように出力されます。UNCLASSIFIED は情報ラベルを表し、[C] は機密ラベルを表します。この CMW ラベルは、プロセスが、情報ラベル UNCLASSIFIED を使用して、機密レベル Confidential ([C]) で動作していることを示します。この CMW ラベルは、プログラムが動作しているワークスペースから継承されます。プログラムがデータを読み取ると、プロセスの情報ラベルは読み取られるデータの情報ラベルに応じて浮上します。

Process CMW label = UNCLASSIFIED [C]

ASCII 出力は、bcltos(3) に対するフラグパラメータと、label_encodings(4) 内の記述によって異なります。フラグパラメータ値の詳細は、「バイナリから ASCII への変換」を参照してください。

プロセス CMW ラベルの機密ラベル部の設定

次の例は、呼び出し元プロセスの CMW ラベルを取得し、機密ラベル部を昇格して TOP SECRET に設定します。変更された CMW ラベルは、特権プロセスで設定されます。呼び出しプロセスは、機密ラベルを変更するのに有効セット内に proc_setsl 特権が必要です。第 3 章「特権」で説明している特権のブラケット化が必要な位置は、コード内のコメントで示してあります。

#include <tsol/label.h>

 main()
 {
 	int					retval, error, length = 0;
 	bclabel_t					pCMWlabel;
 	bslabel_t					psenslabel;
 	char					*string = "TOP SECRET",  *string1 = (char *)0;

 /* 機密ラベル部の新しい値を CMW ラベルに設定する */
 	retval = stobsl(string, &psenslabel, NEW_LABEL, &error);
 	setcsl(&pCMWlabel, &psenslabel);

 /* プロセスの CMW ラベルを新しい CMW ラベルに設定する */
 /* 有効セット内で proc_setsl をオン (有効)にする */
 	retval = setcmwplabel(&pCMWlabel, SETCL_SL);
 /* proc_setsl をオフ (無効) にする */

 /* プロセスの CMW ラベルを文字列に変換し、出力する */
 /* 有効セット内で sys_trans_label 特権をオン (有効)にする */
 	retval = bcltos(&pCMWlabel, &string1, length, LONG_CLASSIFICATION);
 /* sys_trans_label をオフ (無効) にする */

 	printf("Process CMW label = %s¥n", string1);
 }

printf 文によって、次のように出力されます。TOP SECRET は情報ラベルを表し、[TS] は機密ラベルを表します。

Process CMW label = TOP SECRET [TS]

ASCII 出力は、bcltos(3) のフラグパラメータと、label_encodings(4) 内の記述によって異なります。フラグパラメータ値の詳細は、「バイナリから ASCII への変換」を参照してください。

setcmwplabel(2) に渡される SETCL_SL 値は、CMW ラベルの両方のラベル部を設定します。

ファイル CMW ラベルの取得

ファイルの CMW ラベルを取得した際に、CMW ラベルを一単位として処理することも、機密ラベル部を抽出し、機密ラベル部だけを処理することもできます。

次の例では、ファイルの CMW ラベルを取得し、機密ラベル部を抽出します。ファイル記述子を取得する fgetcmwlabel(2) とシンボリックリンクを取得する lgetcmwlabel(2) ルーチンもこの例と同じ方法で使用できます。

#include <tsol/label.h>

 main()
 {
 		int				retval, length = 0;
 		bclabel_t				fileCMWlabel;
 		 		bslabel_t				fsenslabel;
 		char				*string = (char *)0;

/* ファイルの CMW ラベルを得る */
 	retval = getcmwlabel("/export/home/zelda/afile", &fileCMWlabel);

 /* 機密ラベル部を得る */
 	getcsl(&fsenslabel, &fileCMWlabel);
 	
/* ファイルの CMW ラベルを ASCII 文字列に変換して、出力する */
 	retval = bcltos(								&fileCMWlabel, &string, length, LONG_CLASSIFICATION);
 	printf("File CMW label = %s¥n", string);
 }

File CMW label = CONFIDENTIAL [C]

ファイル CMW ラベルの機密ラベル部の設定

この例では、プロセスは、認可上限 Top Secret を使用して Confidential で実行されています。このプロセスは、ファイルの CMW ラベルの機密ラベル部を Top Secret に昇格します。ラベル昇格では常に特権が必要なため、このプロセスは file_upgrade_sl 特権を必要とします。第 3 章「特権」で説明している特権のブラケット化が必要な位置は、コード内のコメントで示してあります。

プロセスは、オブジェクトの機密ラベルを、プロセス自体の認可上限よりも高いレベルには昇格できません。機密ラベルと照らしてプロセス認可上限をチェックする方法は、「もっとも高いレベルともっとも低いレベルの検索」を参照してください。

ファイルの CMW ラベルが昇格された時に、システムがファイル名を表示しないよう管理者が /etc/system ファイルに設定するか、インストール時に指定した場合、Confidential でログインしたユーザーが、ディレクトリ中のファイルをリストしても昇格されたファイルは表示されません。システム変数の照会の詳細は、「システムセキュリティ構成の照会」を参照してください。


注 -

ASCII からバイナリへの変換では、NEW_LABEL フラグパラメータを使用して新しいラベルを作成します。ASCII からバイナリへのラベル変換およびフラグパラメータの詳細は、「ASCII からバイナリと 16 進への変換」を参照してください。


setcmwlabel(2) システムコールに渡される SETCL_SL 値は、機密ラベル部が設定されることを示します。新しい機密ラベルはファイルを含んでいるファイルシステムのラベルの範囲内になければならず、必要な特権が有効でなければなりません。

#include <tsol/label.h>

 main()
 {
 	int					retval, error;
 	bclabel_t					fileCMWlabel;
 	bslabel_t					fsenslabel;
 	char					*string = "TOP SECRET", *string1 = "TOP SECRET";

 /* 機密ラベルの新しい値を作成する */
 /* 有効セット内で sys_trans_label をオン (有効) にする */
 	retval = stobsl(string, &fsenslabel, NEW_LABEL, &error);
 /* sys_trans_label をオフ (無効) にする */

 /* CMW ラベルの機密ラベル部を新しい値に設定する */
 	setcsl(&fileCMWlabel, &fsenslabel);

 /* ファイルの CMW ラベルを設定する */
 /* 有効セット内で file_upgrade_sl をオン (有効) にする */
 	retval = setcmwlabel(									"/export/home/zelda/afile", &fileCMWlabel, SETCL_SL);
 /* file_upgrade_sl をオフ (無効) にする */
 }

ファイルのラベルの変化をチェックするには、getlabel(1) を使用してください。上記のプログラムが実行される前の afile の CMW ラベルを、次に示します。

%phoenix getlabel afile

afile: CONFIDENTIAL [C]

プログラムの実行後、CMW ラベルは次のようになります。getlabel(1) を Confidential で使用する場合、Top Secret ファイルのラベルを読み取るには sys_trans_label 特権が必要です。

%phoenix getlabel afile

afile: TOP SECRET [TS]

ファイルシステムのラベル範囲

ファイルシステムのラベルの範囲は、ファイルシステムに含まれるデータの機密度の上限と下限を指定します。getcmwfsrange()fgetcmwfsrange() システムコールは、ファイルシステムの機密ラベル範囲の上限と下限を含む構造体を返します。

i ノードまたは vfstab_adjunct(4) 内のファイルシステムのセキュリティ属性を照会する方法は、第 2 章「プログラミングインタフェースの概要」「ファイルシステムのセキュリティ属性の照会」を参照してください。。

次の節では、プログラムがファイルシステムのラベル範囲を取得し、作業を継続する前に、機密ラベルをラベル範囲と照らしてテストする 2 つの事例を説明します。

ファイル CMW ラベルの変更前に範囲を確認する

前述の例で説明しているファイルの CMW ラベルの昇格を行う前に、ファイルの新しい機密ラベルがそのファイルの機密ラベルの範囲内であるか確認することをお勧めします。

次の例は、ASCII 文字列を新しいバイナリの機密ラベルに変換し、ファイルシステムのラベル範囲を取得し、新しい機密ラベルがそのファイルシステムのラベル範囲内であるか調べます。

#include <tsol/label.h>

 main()
 {
 	int					retval, error;
 	bclabel_t					fileCMWlabel;
 	bslabel_t					fsenslabel;
 	brange_t 					range;
 	char					*string = "TOP SECRET";

/* 機密ラベルの新しい値を作成する */
 	retval = stobsl(string, &fsenslabel, NEW_LABEL, &error);
/* ファイルシステムのラベル範囲を得る */
 	retval = getcmwfsrange("/export/home/zelda/afile", range);

/* 機密ラベルがラベル範囲内かどうか調べる */
 	retval = blinrange(&fsenslabel, range);
 	if(retval > 0)
 			{/* ファイル CMW ラベルの昇格を実行する */}
 }

データをデバイスに出力する前に範囲を確認する

Solaris 7 インタフェースを使用してデバイスを割り当てて入力をデバイスに送る場合には、必ずデバイス特殊ファイルのラベル範囲を調べてください。デバイスに送られる入力は、デバイス特殊ファイルのラベル範囲内でなければなりません。

ラベルの関係の確認

アプリケーションが異なる機密ラベルのデータにアクセスする場合、実行前にコード内で検査を行い、プロセスラベルがデータラベルと正しい関係にあるか確認することができます。アクセスがシステムにより許可されるか、それともアクセス制限を無効にする特権が必要かを確認するためには、機密ラベルを調べます。

この節の例では、2 つの機密ラベル間の、関係 (同等、優位、完全な優位のいずれか) を確認する方法を示しています。Trusted Solaris 7 は、プロセスがオブジェクトの機密ラベルを変更する場合や、より高い機密ラベルのオブジェクトに対して書き込みを行う場合、プロセス認可上限を調べます。認可上限と機密ラベル間の関係のテスト方法は、「2 つのレベル間の関係の確認」を参照してください。

2 つのレベル間の関係の確認

レベルとは、機密ラベルの格付けとコンパートメントセットにより設定される認可上限のことで、データ型 blevel_t で定義します。2 つのレベルは、同等、一方が他方より優位、一方が他方より完全に優位のいずれかの関係になります。

次の例は、プロセスの機密ラベルとファイルの機密ラベルの関係をテストします。プロセスとファイルの CMW ラベルの取得、および機密ラベル部の抽出を行うコードは示されていないので、コード例については、「プロセス CMW ラベルの取得」「ファイル CMW ラベルの取得」を参照してください。

この例では、プロセスとファイルの機密ラベルは Confidential です。2 つのラベルの格付けは同等で、プロセスラベルがファイルラベルより優位ですが完全に優位ではありません。

#include <tsol/label.h>

 main()
 {
 	int 					equal, dominate, strictdom, retval;
 	bslabel_t 					plabel, filelabel;
 	bclabel_t 					fileCMWlabel, pCMWlabel;

/* ファイルとプロセスの CMW ラベルを得る */
 	retval = getcmwlabel("/export/home/zelda/afile", &fileCMWlabel);
 	retval = getcmwplabel(&pCMWlabel);

/* 機密ラベルを得る */
 	getcsl(&filelabel, &fileCMWlabel);
 	getcsl(&plabel, &pCMWlabel);

/* 得られた 2 つのラベルが同等か調べる */
 	equal = blequal(&plabel, &filelabel);
 	printf("Process label equals file label? %d¥n", equal);

/* 優位か調べる */
 	dominate = bldominates(&plabel, &filelabel);
 	printf("Process label dominates file label? %d¥n", dominate);

/* 完全に優位か調べる */
 	strictdom = blstrictdom(&plabel, &filelabel);
 	printf("Process label strictly dominates file label? %d¥n", strictdom);
 }

printf 文によって、次のように出力されます。0 を超える値は true で、0 は false です。

Process label equals file label? 1

Process label dominates file label? 1

Process label strictly dominates file label? 0

CMW ラベル部のアクセス

「プロセス CMW ラベルの取得」「ファイル CMW ラベルの取得」の節では、getcsl(3)setcsl(3) ルーチンを使用して、プロセスとファイルの CMW ラベルの機密ラベル部の取得と設定を行なっています。次の例では、CMW ラベルの機密ラベル部にポインタを返すルーチンを使用しています。

#include <tsol/label.h>

 main()
 {
 	bslabel_t 					*senslabel;
 	bclabel_t					*pCMWlabel;
 	blevel_t					*level;
 	int					retval;

 	retval = getcmwplabel(pCMWlabel);

/* CMW ラベルの機密ラベル部を指すポインタを得る */
 	senslabel = bcltosl(pCMWlabel);

 }

バイナリレベルの上下限の確認

次の 2 つの例は、blevel_t 型の 2 つの変数間の最高値と最低値を見つけます。このインタフェースでは、2 つのレベルを比較し、それら 2 つのレベルによって定められた範囲において、blminimum(3) ルーチンにより最高の下限のレベル、blmaximum(3) ルーチンにより最低の上限のレベルを見つけることができます。レベルは、機密ラベル、認可上限、または biltolev() ルーチンでレベルに変換された情報ラベルです。

この例では、senslabel (機密ラベル) は ADMIN_LOW で、plabel (プロセスの機密ラベル) は Confidentialです。このコードは、この 2 つのレベルにより設定される範囲においてもっとも高い下限ともっとも低い上限を見つけます。最初の例では、blmaximum() ルーチンに渡される 2 つの変数のうち、格付けの大きな方、およびすべてのコンパートメントの中でもっとも高いものを見つけ、その値を最初のパラメータに入れます。この処理は、「もっとも低い上限の確認」と言います。それは、ルーチンに渡される 2 つのパラメータ値で指定される元のラベルよりも優位でもっとも低いレベルを見つけるためです。

#include <tsol/label.h>

 main()
 {
 	int			retval, length = 0;
 	char			*string = (char *)0, *string1 = (char *)0;
 	bslabel_t			senslabel, plabel;
 	bclabel_t			pCMWlabel;

/* ラベルを ADMIN_LOW に初期化する */
 	bsllow(&senslabel);

/* プロセスの機密ラベルを得る */
 	retval = getcmwplabel(&pCMWlabel);
 	getcsl(&plabel, &pCMWlabel);

 	blmaximum(&senslabel, &plabel);
 	retval = bsltos(&senslabel, &string, length, LONG_WORDS);
 	printf("Maximum = %s¥n", string);

printf 文によって、次のように出力されます。CONFIDENTIAL は、Confidential と ADMIN_LOW よりも優位なレベルのうち、もっとも低いものです。

Maximum = CONFIDENTIAL

次の例は、 blminimum() ルーチンに渡される 2 つのパラメータの機密ラベルにおいて、他方より低い格付けと両方の機密ラベルに含まれるコンパートメントの中でもっとも低いコンパートメントを見つけ、その値を最初のパラメータに入れます。この処理は、「もっとも高い下限の確認」と言います。それは、ルーチンに渡される 2 つのパラメータ値で指定される元のラベルより優位でなくもっとも低いレベルを見つけるためです。

	bsllow(&senslabel);

 	blminimum(&senslabel, &plabel);
 	retval = bsltos(&senslabel, &string1, length, LONG_WORDS);
 	printf("Minimum = %s¥n", string1);
 }

printf 文によって、次のように出力されます。ADMIN_LOW は、ADMIN_LOW と Confidential よりも劣位の (優位でない) レベルの中でもっとも高いものです。

Minimum = ADMIN_LOW

認可範囲のチェック

機密ラベルがシステムまたはユーザーの認可範囲の中にあるかをチェックするには、blinset() ルーチンを使用してください。システム認可範囲は、ADMIN_HIGHADMIN_LOW など、システムで有効なすべてのラベルです。システムが処理するすべての機密ラベルの格付けとコンパートメントは、システム認可範囲の最下位の機密ラベルよりも優位でなければならず、システム認可範囲の最上位の機密ラベルよりも優位であってはなりません。システム管理者は、システム認可範囲を label_encodings(4) ファイルで定義します。

ユーザー認可範囲は、ユーザーに有効なすべての機密ラベルであり、ADMIN_HIGHADMIN_LOW が含まれることはありません。ユーザーに割り当てられたすべての機密ラベルの格付けとコンパートメントは、システム認可範囲の最下位の機密ラベルよりも優位でなければならず、システム用の認可範囲の最上位の機密ラベルよりも優位であってはなりません。システム管理者は、管理ユーザーインタフェースを使用して、機密ラベル範囲 (ユーザー認可範囲) をユーザーと役割に割り当てます。

次の例では、機密ラベルが、システム認可範囲 (id.type = 1) とユーザー認可範囲 (id.type = 2) の範囲内にあるか検査されます。

#include <tsol/label.h>

 main()
 {
 	char			*string = "CONFIDENTIAL", *string1 = "UNCLASSIFIED";
 	int			sysval, userval, error, retval;
 	bslabel_t			senslabel;
 	set_id			id;

 	retval = stobsl(string, &senslabel, NEW_LABEL, &error);
 	id.type = 1;
 	sysval = blinset(&senslabel, &id);
 	id.type = 2;
 	userval = blinset(&senslabel, &id);

 	printf("System Range? = %d User Range? %d¥n", sysval, userval);
 }

printf 文によって、次のように出力されます。1 は、機密ラベルが範囲内であることを示します。0 は、機密ラベルが有効なラベルでない、指定された範囲内でない、または呼び出し元プロセスの機密ラベルがこの機密ラベルよりも優位でなく、呼び出しプロセスの有効セットに sys_trans_label 特権が含まれていない、のどれかを示します。

System Range? = 1 User Range? = 1

ラベルの妥当性検査

有効なラベルとは、label_encodings ファイルに定義されたラベルのことです。bslvalid(3) ルーチンを使用して、機密ラベルが有効であるかを検査できます。呼び出し元プロセスの機密ラベルは、検査される機密ラベルよりも優位でなければなりません。そうでない場合にこの処理を実行するには、呼び出し元プロセスの有効セットに sys_trans_label 特権を必要とします。

#include <tsol/label.h>

 main()
 {
 	int			retval, error;
 	bslabel_t			senslabel;
 	 	char			*string = "CONFIDENTIAL", *string1 = "UNCLASSIFIED";

 	retval = stobsl(string, &senslabel, NEW_LABEL, &error);
 	retval = bslvalid(&senslabel);
 	printf("Valid Sensitivity Label? = %d¥n", retval);
 }

printf 文によって、次のように出力されます。1 は、ラベルが有効であることを示します。-1 は、label_encodings ファイルがアクセス可能でないことを示します。0 は、ラベルが有効でないか、プロセスの機密ラベルが認可上限より優位でなく、プロセスの有効セット内に sys_trans_label 特権がないことを示します。

Valid Sensitivity Label? = 1

ASCII カラー名の取得

次の例は、bltocolor(3) コールを使用して、特定のレベルの機密ラベルと対応した ASCII カラー名を取得します。ASCII カラー名は、label_encodings(4) ファイルで指定されます。

この例は、Confidential の機密ラベルと対応した ASCII カラー名について照会します。プロセスは Confidential で動作しているので照会で特権は必要になりません。呼び出し元プロセスは、現在のプロセスの機密ラベルよりも優位なラベルについて照会する場合、その有効セットに sys_trans_label 特権を必要とします。

#include <tsol/label.h>

 main()
 {
 	int			retval, error;
 	bslabel_t			senslabel;
 	char			*string = "CONFIDENTIAL";
 	char			*string1;

 	retval = stobsl(string, &senslabel, NEW_LABEL, &error);

 	string1 = bltocolor(&senslabel);
 	printf("Confidential label color = %s¥n", string1);
 }

printf 文によって、次のように出力されます。

Confidential label color = BLUE

ラベルエンコーディング情報

labelinfo(3) ルーチンは、ラベルライブラリのさまざまな文字データフィールドの最大長の値をショート整数 (short integer) で返します。これらの長さは、ラベル情報を含むフィールドを表示するアプリケーションなどで使用します。長さの値は、label_encodings(4) ファイルの実際の内容によって異なります。

#include <tsol/label.h>
 main()
 {
 	int							retval;
 	struct		label_info					info;

 	retval = labelinfo(&info);
 	printf("Max information label length = %d¥n", info.ilabel_len);
 	printf("Max sensitivity label length = %d¥n", info.slabel_len);
 	printf("Max CMW label length = %d¥n", info.clabel_len);
 	printf("Max clearance length = %d¥n", info.clear_len);
 	printf("Max version string length = %d¥n", info.vers_len);
 	printf("Max banner and trailer string length = %d¥n", info.header_len);
 	printf("Max protect as section string length = %d¥n", info.protect_as_len);
 	printf("Max caveats section string length = %d¥n", info.caveats_len);
 	printf("Max handling channels string length = %d¥n", info.channels_len);
 }

printf 文によって、次のように長さが出力されます。

Max information label length = 212

Max sensitivity label length = 45

Max CMW label length = 259

Max clearance length = 76

Max Version String length 56

Max Banner and trailer page string length = 13

Max Protect as section string length = 256

Max Caveats section string length = 62

Max Handling channels section string length = 81

ラベルの変換

すべてのラベルは、バイナリ、ASCII、 16 進のいずれかで表すことができます。カーネル内部では、ラベルはすべてバイナリ形式で格納されます。プログラミングインタフェースとの間でやり取りするラベルに使用される形式は、バイナリです。


注 -

ラベルが、自身の機密レベルよりも低い機密ラベルのファイルに格納される場合、または適切な許可や承認のないユーザーがアクセスできるファイルに格納される場合は、読み取れないように、ラベル名をバイナリまたは 16 進形式で格納してください。ユーザー承認の詳細は、第 4 章「ユーザー承認のチェック」を参照してください。


バイナリと ASCII

ラベルは、バイナリから ASCII に変換し、再び元に戻すことができます。呼び出し元プロセスは、そのプロセスの機密ラベルよりも優位のラベルを変換するには、有効セットに sys_trans_label 特権を必要とします。

バイナリから ASCII への変換

この節の例は、バイナリラベルを ASCII に変換します。この変換では、label_encodings(4) 内のキーワード設定とフラグパラメータ値を使用します。ラベルの種類によって使えるフラグが制限されることはありませんが、すべてのフラグ値が、それぞれのラベルに有効なわけではありません。次の説明は、フラグが使用されるラベルの種類を示します。機密ラベルと情報ラベルに適用される設定は、CMW ラベルにも適用されます。


注 -

「プロセスのセキュリティ属性フラグの取得と設定」 で説明しているラベル表示プロセス属性には、ラベル表示の状態が含まれます。


CMW ラベル

CMW ラベルの ASCII 出力形式を、次に示します。

情報ラベル [機密ラベル]

次の例は、CMW ラベルを ADMIN_HIGH [ADMIN_HIGH] に初期化し、内部表示と外部表示を出力します。このプロセスは ADMIN_HIGH で動作するため、ADMIN_HIGH [ADMIN_HIGH] ラベルを変換するのに特権を必要としません。

#include <tsol/label.h>

 main()
 {
 	int 			retval, length = 0;
 	char 			*string1 = (char *)0, *string2 = (char *)0;
 	bclabel_t			cmwlabel;

 	bclhigh(&cmwlabel);
 	retval = bcltos(&cmwlabel, &string1, length, VIEW_INTERNAL);
 	printf("View Internal = %s¥n", string1);

 	retval = bcltos(&cmwlabel, &string2, length, VIEW_EXTERNAL);
 	printf("View External = %s¥n", string2);
 }

printf 文によって、次のように出力されます。


View Internal = ADMIN_HIGH [ADMIN_HIGH]

View External = TOP SECRET CC SB BRAVO1 BRAVO3 SA ALPHA1 
PROJECT X/PROJECT Y LIMDIS ORCON ORG X/ORG Y D/E ALL EYES 
NOFORN [TS A B SA SB CC]

注 -

bclhigh(3) と、bclmanifest(3) ファミリの他の関数を使用すると CMW ラベルの情報ラベルの値を操作できますが、この値をオブジェクトに対して設定することはできません。デフォルトで、オブジェクトの情報ラベルはすべて ADMIN_LOW です。


機密ラベルと情報ラベル

インタフェースからの機密ラベルと情報ラベルの ASCII 出力形式を、次に示します。区切り文字には空白文字が使用されます。中括弧はオプション項目を示し、ピリオドは語句の繰り返しを示します。語句は、機密ラベルではコンパートメントを表し、情報レベルではコンパートメントとマーキングを表します。

格付け {語句}...

次のコード例は、さまざまなフラグを使用してバイナリの機密ラベルを ASCII に変換します。このプロセスは、TS A B で動作するので、bslhigh(3) に対する呼び出しの後、変換のため sys_trans_label 特権を必要とします。第 3 章「特権」で説明している特権のブラケット化が必要な位置は、コード内のコメントで示してあります。

#include <tsol/label.h>
 main()
 {
 	int				retval, length = 0;
 	char 				*string1 = (char *)0, *string2 = (char *)0,
 					*string3 = (char *)0, *string4 = (char *)0,
 					*string5 = (char *)0, *string6 = (char *)0,
 					*string7 = (char *)0;
 	bclabel_t				cmwlabel;
 	bslabel_t				senslabel;

 	retval = getcmwplabel(&cmwlabel);
 	getcsl(&senslabel, &cmwlabel);

 	retval = bsltos(&senslabel, &string1, length, LONG_WORDS);
 	printf("Retval1 = %d Long Words = %s¥n", retval, string1);

 	retval = bsltos(&senslabel, &string2, length, SHORT_WORDS);
 	printf("Retval2 = %d Short Words = %s¥n", retval, string2);

 	retval = bsltos(&senslabel, &string3, length, LONG_CLASSIFICATION);
 	printf("Retval3 = %d Long Classifications = %s¥n", retval, string3);

 	retval = bsltos(&senslabel, &string4, length, SHORT_CLASSIFICATION);
 	printf("Retval4 = %d Short Classifications = %s¥n", retval, string4);

 	retval = bsltos(&senslabel, &string5, length, NO_CLASSIFICATION);
 	printf("Retval5 = %d No Classification = %s¥n", retval, string5);

 	bslhigh(&senslabel);
/* 有効セット内で sys_trans_label をオン (有効) にする */
 	retval = bsltos(&senslabel, &string6, length, VIEW_INTERNAL);
/* sys_trans_label をオフ (無効) にする */
 	printf("Retval6 = %d View Internal = %s¥n", retval, string6);

 	retval = bsltos(&senslabel, &string7, length, VIEW_EXTERNAL);
 	printf("Retval7 = %d View External = %s¥n", retval, string7);
 }

printf 文により、次のように出力されます。

Long Words = TS A B

Short Words = TS A B

Long Classifications = TOP SECRET A B

Short Classifications = TS A B

No Classification = A B

View Internal = ADMIN_HIGH

View External = TS A B SA SB CC

ASCII からバイナリと 16 進への変換

次の例は、次のフラグ値を使用して、ASCII 文字列をバイナリの CMW ラベル、機密ラベル、または情報ラベルに変換します。

CMW ラベル

ASCII の CMW ラベルに使用できる形式を次に示します。

機密ラベルと情報ラベル

ASCII の機密ラベルと情報ラベルに使用できる形式を次に示します。入力項目は、空白文字、タブ、コンマ、スラッシュ (/) のいずれかで区切ることができます。格付けと語句の名前は、短い形式でも長い形式でもかまいません。

{+} {格付け} {{+|-}語句...}

コード例

次の例は、NEW_LABEL フラグを使用して、ASCII 文字列をバイナリの CMW ラベル、機密ラベル、情報ラベルに変換し、再び元の ASCII に戻します。また、機密ラベルを指定された長さに変換する (クリッピング) 例も示しています。プロセスが SECRET B A [TS] 以上で作動する場合は、ラベル変換に sys_trans_label 特権を必要としません。

#include <tsol/label.h>

 main()
 {
 	int 			retval, error, length = 0;
 	char			*cmwstring ="SECRET A B [TOP SECRET A B]";
 	char 			*sensstring = "TOP SECRET A B";
 	char			*string1 = (char *)0, *string2 = (char *)0,
 				*string3 = (char *)0;
 	bclabel_t			cmwlabel;
 	bslabel_t			senslabel;


 	retval = stobcl(cmwstring, &cmwlabel, NEW_LABEL, &error);
 	retval = bcltos(&cmwlabel, &string1, length, ALL_ENTRIES);
 	retval = stobsl(sensstring, &senslabel, NEW_LABEL, &error);
 	retval = bsltos(&senslabel, &string2, length, ALL_ENTRIES);
 	string3 = sbsltos(&senslabel, 4);
 	
 	printf("CMW label = %s¥nSens label = %s¥nClipped label = %s¥nInf
 			label= %s¥n", string1, string2, string3);
 }

printf 文により、次のように出力されます。Clipped label (クリッピングされたラベル) 中の矢印 <- は、機密ラベル名の文字がクリッピングされたことを示します。

CMW label = SECRET B A [TS A B]

Sen label = TS A B

Clipped label = TS<-

バイナリと 16 進

バイナリから 16 進への変換には、通常ルーチンと再入可能ルーチンの 2 種類のルーチンがあります。どちらのルーチンも変換結果を含んだ文字列のポインタを返し、変換されるラベルがバイナリラベルでない場合は、NULL を返します。

通常ルーチンによるバイナリと 16 進変換

次の例は、バイナリの CMW ラベルを 16 進に変換し、再び元に戻します。機密ラベルの変換と情報ラベルの変換はほとんど同じです。

#include <tsol/label.h>
 #include <stdio.h>

 main()
 {
 	int			retval;
 	bclabel_t			hcmwlabel, hexcmw;
 	char			*string;

 	getcmwplabel(&hcmwlabel);
 	if((string = bcltoh(&hcmwlabel)) != NULL)
 		printf("Hex string = %s¥n", string);

 	retval = htobcl(string, &hexcmw);
 	printf("Return Value = %d¥n", retval);
 }

最初の printf 文により、バイナリ CMW ラベルが次のように 16 進形式で出力されます。

0xClearance hexadecimal value

2 番目の printf 文により、次のように出力されます。0 以外は、変換が成功したことを示します。

Return Value = 1

再入可能ルーチンによるバイナリと 16 進変換

再入可能 (MT-安全、マルチスレッドに対して安全) ルーチン bcleartoh_r(3) は、指定されたタイプの変数に対する記憶領域の割り当てと解放を必要とします。次の例は、記憶領域を割り当て、バイナリ CMW ラベルを 16 進に変換し、最後に記憶領域を解放します。機密ラベルまたは情報ラベルを 16 進に変換するプロセスと、元の形式に戻すプロセスはほとんど同じです。

#include <tsol/label.h>
 #include <stdio.h>

 main()
 {
 	int			retval;
 	bclabel_t			hcmwlabel, hexcmw;
 	char			*string, *hex;

 	getcmwplabel(&hcmwlabel);
 	hex = h_alloc(SUN_CMW_ID);
 	if((string = bcltoh_r(&hcmwlabel, hex)) != NULL)
 		printf("Hex string = %s¥n", string);

 	retval = htobcl(string, &hexcmw);
 	printf("Return Value = %d¥n", retval);
 	h_free(hex);
 }

printf(1) 文により、次のように 16 進形式でバイナリ認可上限が出力されます。


Hex string =0x00000000000000000000000000000000000000000000
00000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000[0x00040c0000000000000000000000
000000000000000000000003ffffffffffff0000]

Return Value = 1

プリンタバナーの情報

bcltobanner(3) ルーチンは、バイナリ CMW ラベルを、プリンタから出力されるバナーページ、トレーラページ、および印刷ジョブの文書ページに表示される ASCII コードのラベルと文字列に変換します。ラベルと文字列は、label_encodings(4) ファイル内の情報から計算されます。このルーチンは、Trusted Solaris 7 の印刷システムにより内部的に使用されるので、ほとんどのアプリケーションはこの変換ルーチンを必要としませんが、印刷サーバーアプリケーションや、印刷システムが使用している外部文字列表示を必要とするアプリケーションなどで使用する場合があります。

次の例では、CMW ラベルは ADMIN_LOW [TS] です。banner_fields (バナーフィールド) の最初の 5 つのフィールドは、文字ポインタです。文字ポインタに事前に記憶領域を割り当てると、次の 5 つのフィールドには、割り当てられた記憶領域長を示すショート整数 (short integer) 値が入ります。この例のように、最初の 5 つの文字ポインタを(char *)0 に初期化する際には、ショート整数値が入るフィールドは初期化する必要はありません。

#include <tsol/label.h>
 main()
 {
 	int				retval;
 	bclabel_t 				cmwlabel;

 	static struct banner_fields banner = {							(char *)0, (char *)0, (char *)0,
 												(char *)0, (char *)0};

 	getcmwplabel(&cmwlabel);

 	retval = bcltobanner(&cmwlabel, &banner, SHORT_WORDS);

 	printf("Top and bottom banner/trailer header = %s¥n", banner.header);
 	printf("Protect as section of banner page = %s¥n", banner.protect_as);
 	printf("Inf. label/top and bottom body pages = %s¥n", banner.ilabel);
 	printf("Caveats section of printer banner page = %s¥n", banner.caveats);
 	printf("Handling channels section of banner page = %s¥n", banner.channels);
 }

printf(1) 文内のテキストは、バナー、トレーラ、文書ページのどこにそれぞれの文字列が現れるかを示します。label_encodings(4) ファイルの printer banner セクションに警告が指定されていないため、警告文字は空です。文字列の計算方法は、『Trusted Solaris のラベル管理』と『コンパートメントモードワークステーションのラベル作成: エンコード形式』を参照してください。


Top and bottom banner/trailer header = TOP SECRET

Protect as section of banner page = TOP SECRET A B

Inf. label/top and bottom body pages = UNCLASSIFIED

Caveats section of printer banner page = 

Handling channels section of banner page = HANDLE VIA (CH B)/(CH A) CHANNELS JOINTLY