Solaris DHCP の管理

第 6 章 DHCP のリファレンス

この章では、ファイルとそれらのファイルを使用するコマンドとの関係について説明します 。コマンドの使用方法については説明していません。

DHCP のコマンド

次の表に、ネットワーク上で DHCP を管理する際に役立つコマンドを示します。

表 6–1 DHCP で使用されるコマンド

コマンド 

説明 

dhtadm

dhcptab 内のオプションやマクロを変更するときに使用する。 このコマンドは、DHCP 情報を自動的に変更するために作成するスクリプトで最も役立つ。dhtadm-P オプションを指定し、その結果を grep コマンドに渡すと、dhcptab 内の特定のオプション値を素早く検索できる

pntadmDHCP ネットワークテーブルを変更するときに使用する。このテーブルでは、クライアント ID と IP アドレスが対応付けられ、オプションとして構成情報と IP アドレスが関連付けられている
dhcpconfigDHCP サーバーや BOOTP リレーエージェントの構成や構成解除を行なったり、データを別のデータへ変換したり、DHCP 構成データのインポートやエクスポートを行うときに使用する
in.dhcpdDHCP サーバーデーモン。システムスクリプトでは、このコマンドを使って DHCP サービスの起動や停止を行う。 デバッグ用の -d のようなデフォルトでないオプションを使用して in.dhcpd を起動できる
dhcpmgrDHCP マネージャは、DHCP サービスの構成や管理を行うグラフィカルツールです。DHCP マネージャは、推奨される Solaris DHCP 管理ツールです。
ifconfigシステムの起動時に使用され、IP アドレスをネットワークインタフェースに割り当てたり、ネットワークインタフェースのパラメータを構成したりする (または、その両方)。Solaris DHCP クライアントでは、ifconfig は DHCP を起動し、IP アドレスなどの、ネットワークインタフェースの構成に必要なパラメータを取得する
dhcpinfoクライアントシステムのシステム起動スクリプトの中で、DHCP クライアントデーモン (dhcpagent) からホスト名などの情報を取得するときに使用する。また、スクリプトやコマンド行で dhcpinfo を使用して、特定のパラメータ値を取得することもできる
snoopネットワークを介して送信されているパケットの内容を獲得および表示するときに使用する。snoop は、DHCP サービスに伴う問題追跡する際に役立つ
dhcpagentDHCP クライアントデーモン。DHCP プロトコルのクライアント側を実装している

スクリプトにおける DHCP コマンドの実行

dhcpconfigdhtadmpntadm コマンドは、スクリプト中での使用に適しています。 特に、pntadm コマンドは大量の IP アドレスエントリを DHCP ネットワークテーブルに作成するときに便利です。次のサンプルスクリプトでは、pntadm をバッチモードで使って、IP アドレスを作成しています。


例 6–1 addclient.ksh スクリプトと pntadm コマンド

#! /usr/bin/ksh
#
# This script utilizes the pntadm batch facility to add client entries
# to a DHCP network table. It assumes that the user has the rights to
# run pntadm to add entries to DHCP network tables.

#
# Based on the nsswitch setting, query the netmasks table for a netmask.
# Accepts one argument, a dotted IP address.
#
get_netmask()
{
	MTMP=`getent netmasks ${1} | awk '{ print $2 }'`
	if [ ! -z "${MTMP}" ]
	then
		print - ${MTMP}
	fi
}

#
# Based on the network specification, determine whether or not network is 
# subnetted or supernetted.
# Given a dotted IP network number, convert it to the default class
# network.(used to detect subnetting). Requires one argument, the
# network number. (e.g. 10.0.0.0) Echos the default network and default
# mask for success, null if error.
#
get_default_class()
{
	NN01=${1%%.*}
	tmp=${1#*.}
	NN02=${tmp%%.*}
	tmp=${tmp#*.}
	NN03=${tmp%%.*}
	tmp=${tmp#*.}
	NN04=${tmp%%.*}
	RETNET=""
	RETMASK=""

	typeset -i16 ONE=10#${1%%.*}
	typeset -i10 X=$((${ONE}&16#f0))
	if [ ${X} -eq 224 ]
	then
		# Multicast
		typeset -i10 TMP=$((${ONE}&16#f0))
		RETNET="${TMP}.0.0.0"
		RETMASK="240.0.0.0"
	fi
	typeset -i10 X=$((${ONE}&16#80))
	if [ -z "${RETNET}" -a ${X} -eq 0 ]
	then
		# Class A
		RETNET="${NN01}.0.0.0"
		RETMASK="255.0.0.0"
	fi
	typeset -i10 X=$((${ONE}&16#c0))
	if [ -z "${RETNET}" -a ${X} -eq 128 ]
	then
		# Class B
		RETNET="${NN01}.${NN02}.0.0"
		RETMASK="255.255.0.0"
	fi
	typeset -i10 X=$((${ONE}&16#e0))
	if [ -z "${RETNET}" -a ${X} -eq 192 ]
	then
		# Class C
		RETNET="${NN01}.${NN02}.${NN03}.0"
		RETMASK="255.255.255.0"
	fi
	print - ${RETNET} ${RETMASK}
	unset NNO1 NNO2 NNO3 NNO4 RETNET RETMASK X ONE
}

#
# Given a dotted form of an IP address, convert it to its hex equivalent.
#
convert_dotted_to_hex()
{
	typeset -i10 one=${1%%.*}
	typeset -i16 one=${one}
	typeset -Z2 one=${one}
	tmp=${1#*.}

	typeset -i10 two=${tmp%%.*}
	typeset -i16 two=${two}
	typeset -Z2 two=${two}
	tmp=${tmp#*.}

	typeset -i10 three=${tmp%%.*}
	typeset -i16 three=${three}
	typeset -Z2 three=${three}
	tmp=${tmp#*.}

	typeset -i10 four=${tmp%%.*}
	typeset -i16 four=${four}
	typeset -Z2 four=${four}

	 hex=`print - ${one}${two}${three}${four} | sed -e 's/#/0/g'`
	 print - 16#${hex}
	 unset one two three four tmp
}

#
# Generate an IP address given the network address, mask, increment.
# 
get_addr()
{
	typeset -i16 net=`convert_dotted_to_hex ${1}`
	typeset -i16 mask=`convert_dotted_to_hex ${2}`
	typeset -i16 incr=10#${3}

	# Maximum legal value - invert the mask, add to net.
	typeset -i16 mhosts=~${mask}
	typeset -i16 maxnet=${net}+${mhosts}

	# Add the incr value.
	let net=${net}+${incr}

	if [ $((${net} < ${maxnet})) -eq 1 ]
	then
		typeset -i16 a=${net}\&16#ff000000
		typeset -i10 a="${a}>>24"

		typeset -i16 b=${net}\&16#ff0000
		typeset -i10 b="${b}>>16"

		typeset -i16 c=${net}\&16#ff00
		typeset -i10 c="${c}>>8"

		typeset -i10 d=${net}\&16#ff
		print - "${a}.${b}.${c}.${d}"
	fi
	unset net mask incr mhosts maxnet a b c d
}

# Given a network address and client address, return the index.
client_index()
{
	typeset -i NNO1=${1%%.*}
	tmp=${1#*.}
	typeset -i NNO2=${tmp%%.*}
	tmp=${tmp#*.}
	typeset -i NNO3=${tmp%%.*}
	tmp=${tmp#*.}
	typeset -i NNO4=${tmp%%.*}

	typeset -i16 NNF1
	let NNF1=${NNO1}
	typeset -i16 NNF2
	let NNF2=${NNO2}
	typeset -i16 NNF3
	let NNF3=${NNO3}
	typeset -i16 NNF4
	let NNF4=${NNO4}
	typeset +i16 NNF1
	typeset +i16 NNF2
	typeset +i16 NNF3
	typeset +i16 NNF4
	NNF1=${NNF1#16\#}
	NNF2=${NNF2#16\#}
	NNF3=${NNF3#16\#}
	NNF4=${NNF4#16\#}
	if [ ${#NNF1} -eq 1 ]
	then
		NNF1="0${NNF1}"
	fi
	if [ ${#NNF2} -eq 1 ]
	then
		NNF2="0${NNF2}"
	fi
	if [ ${#NNF3} -eq 1 ]
	then
		NNF3="0${NNF3}"
	fi
	if [ ${#NNF4} -eq 1 ]
	then
		NNF4="0${NNF4}"
	fi
	typeset -i16 NN
	let NN=16#${NNF1}${NNF2}${NNF3}${NNF4}
	unset NNF1 NNF2 NNF3 NNF4

	typeset -i NNO1=${2%%.*}
	tmp=${2#*.}
	typeset -i NNO2=${tmp%%.*}
	tmp=${tmp#*.}
	typeset -i NNO3=${tmp%%.*}
	tmp=${tmp#*.}
	typeset -i NNO4=${tmp%%.*}
	typeset -i16 NNF1
	let NNF1=${NNO1}
	typeset -i16 NNF2
	let NNF2=${NNO2}
	typeset -i16 NNF3
	let NNF3=${NNO3}
	typeset -i16 NNF4
	let NNF4=${NNO4}
	typeset +i16 NNF1
	typeset +i16 NNF2
	typeset +i16 NNF3
	typeset +i16 NNF4
	NNF1=${NNF1#16\#}
	NNF2=${NNF2#16\#}
	NNF3=${NNF3#16\#}
	NNF4=${NNF4#16\#}
	if [ ${#NNF1} -eq 1 ]
	then
		NNF1="0${NNF1}"
	fi
	if [ ${#NNF2} -eq 1 ]
	then
		NNF2="0${NNF2}"
	fi
	if [ ${#NNF3} -eq 1 ]
	then
		NNF3="0${NNF3}"
	fi
	if [ ${#NNF4} -eq 1 ]
	then
		NNF4="0${NNF4}"
	fi
	typeset -i16 NC
	let NC=16#${NNF1}${NNF2}${NNF3}${NNF4}
	typeset -i10 ANS
	let ANS=${NC}-${NN}
	print - $ANS
}

#
# Check usage.
#
if [ "$#" != 3 ]
then
	print "This script is used to add client entries to a DHCP network"
	print "table by utilizing the pntadm batch facilty.\n"
	print "usage: $0 network start_ip entries\n"
	print "where: network is the IP address of the network"
        print "       start_ip is the starting IP address \n"
        print "       entries is the number of the entries to add\n"
	print "example: $0 129.148.174.0 129.148.174.1 254\n"
	return
fi

#
# Use input arguments to set script variables.
#
NETWORK=$1
START_IP=$2
typeset -i STRTNUM=`client_index ${NETWORK} ${START_IP}`
let ENDNUM=${STRTNUM}+$3
let ENTRYNUM=${STRTNUM}
BATCHFILE=/tmp/batchfile.$$
MACRO=`uname -n`

#
# Check if mask in netmasks table. First try
# for network address as given, in case VLSM
# is in use.
#
NETMASK=`get_netmask ${NETWORK}`
if [ -z "${NETMASK}" ]
then
	get_default_class ${NETWORK} | read DEFNET DEFMASK
	# use the default.
	if [ "${DEFNET}" != "${NETWORK}" ]
	then
		# likely subnetted/supernetted.
		print - "\n\n###\tWarning\t###\n"
		print - "Network ${NETWORK} is netmasked, but no entry was found in the \n
             'netmasks' table; please update the 'netmasks' table in the \n
              appropriate nameservice before continuing. \n 
              (See /etc/nsswitch.conf.) \n">&2
		return 1
	else
		# use the default.
		NETMASK="${DEFMASK}"
	fi
fi

#
# Create a batch file.
#
print -n "Creating batch file "
while [ ${ENTRYNUM} -lt ${ENDNUM} ]
do
	if [ $((${ENTRYNUM}-${STRTNUM}))%50 -eq 0 ]
	then
		print -n "."
	fi

	CLIENTIP=`get_addr ${NETWORK} ${NETMASK} ${ENTRYNUM}`
	print "pntadm -A ${CLIENTIP} -m ${MACRO} ${NETWORK}">> ${BATCHFILE}
	let ENTRYNUM=${ENTRYNUM}+1
done
print " done.\n"

#
# Run pntadm in batch mode and redirect output to a temporary file.
# Progress can be monitored by using the output file.
#
print "Batch processing output redirected to ${BATCHFILE}"
print "Batch processing started."

pntadm -B ${BATCHFILE} -v> /tmp/batch.out 2>&1

print "Batch processing completed."

DHCP のファイル

表 6–2 に、Solaris DHCP に関連するファイルを示します。

表 6–2 DHCP デーモンや DHCP コマンドで使用されるファイル

ファイル/テーブル 

説明 

dhcptab

オプションとその値の組み合わせからなる DHCP 構成情報のテーブルを表す総称的な用語。構成情報はさらにマクロとしてグループ化される。 dhcptab テーブルの名前と位置は、DHCP 情報の格納にどのデータストアを使用するかによって異なる

DHCP ネットワークテーブル 

IP アドレスをクライアント ID と構成オプションに割り当てる。DHCP ネットワークテーブルの名前は、102.21.32.0 など、ネットワークの IP アドレスに基づいて付けられる。dhcp_network というファイルはありません。DHCP ネットワークテーブルの名前と位置は、DHCP 情報の格納にどのデータストアを使用するかによって異なる

dhcpsvc.conf

DHCP デーモンの起動オプションと、dhcptab テーブルおよびネットワークテーブルのデータストアリソースおよび場所を格納している。 このファイルは /etc/inet ディレクトリにある

nsswitch.conf

ネームサービスデータベースの場所と、それらのデータベースをどのような順序で検索してさまざまな情報を入手するかを指定する。nsswitch.conf ファイルは、DHCP サーバーを構成する際に正確な構成情報を入手するために使用される。このファイルは /etc ディレクトリにある

resolv.conf

DNS リゾルバによって使用される情報が入っている。DHCP サーバーの構成中に、このファイルで、DNS ドメインと DNS サーバーに関する情報が調べられる。このファイルは /etc ディレクトリにある

dhcp.interface

ファイル名 (dhcp.qe0 など) で指定されたクライアントのネットワークインタフェースで DHCP が使用されることを示す。dhcp.interface ファイルには、そのクライアント上で DHCP を起動するための ifconfig interface dhcp start option コマンドにオプションとして渡されるコマンドが含まれていることがある。このファイルは、Solaris DHCP クライアントシステムの /etc ディレクトリにある

interface.dhc

DHCP から得られた特定のネットワークインタフェースの構成パラメータが入っている。クライアントは、インタフェースの IP アドレスのリースが削除される際に、現在の構成情報を /etc/dhcp/interface.dhc にキャッシュする。DHCP が次にこのインタフェースで起動するときに、リースの有効期限内であれば、このクライアントはキャッシュされた情報を使用するように要求する。DHCP サーバーがこの要求を拒否すると、クライアントは標準 DHCP リースネゴシエーション手順を開始する

dhcpagent

dhcpagent クライアントデーモンのパラメータ値を設定する。このファイルへのパスは /etc/default/dhcpagent。 パラメータの詳細については、このファイル自体、または dhcpagent(1M) のマニュアルページを参照

DHCP inittab

データタイプなど、DHCP オプションコードのさまざまな要素を定義するとともに、ニーモニックラベルを割り当てる。ファイル構文については、dhcp_inittab のマニュアルページを参照する

クライアント側では、dhcpinfo/etc/dhcp/inittab ファイル中の情報を人が判読可能な情報として提供する。このファイルは、/etc/dhcp/dhcptags ファイルに代わる。この変更については、DHCP オプション情報 を参照する。DHCP サーバーシステムでは、DHCP デーモンと管理ツールがこのファイルから DHCP オプション情報を入手する

DHCP オプション情報

従来、DHCP のオプション情報は、サーバーの dhcptab テーブルやクライアントの dhcptags ファイル、それに in.dhcpdsnoopdhcpinfodhcpmgr の内部テーブルなど、Solaris DHCP の複数の場所に格納されてきました。 そのため、Solaris 8 DHCP 製品では、オプション情報を統合するために /etc/dhcp/inittab ファイルが導入されています。このファイルについての詳細は、dhcp_inittab のマニュアルページを参照してください。

Solaris DHCP クライアントでは、dhcptags ファイルの代わりに DHCP inittab ファイルを使って、DHCP パケットで受信するオプションコードの情報を入手します。DHCP サーバーの in.dhcpdsnoopdhcpmgr プログラムでもこのinittab ファイルを使用します。


注 –

Solaris DHCP を使用するほとんどのサイトでは、この変更による影響はありません。この影響があるのは、Solaris 8 へのアップグレードを計画している場合で、かつ新しい DHCP オプションを以前に作成し、/etc/dhcp/dhcptags ファイルを変更済みで、この変更を保持したい場合だけです。Solaris 8 にアップグレードすると、dhcptags ファイルが変更されているので DHCP inittab ファイルを変更する必要がある旨のメッセージがアップグレードログに書き込まれます。


dhcptagsinittab の違い

inittab ファイルには dhcptags ファイルよりも多くの情報が含まれ、その構文も異なります。

dhcptags のエントリの例は次の通りです。

33 StaticRt - IPList Static_Routes

33 は DHCP パケットで渡される数値コードです。StaticRt はオプション名であり、IPList は期待されるデータが IP アドレスのリストであることを示しています。

inittab ファイルは、これらのオプションを 1 行で表した複数のレコードから構成されています。形式は、dhcptab のシンボルを定義する形式と似ています。 次の表に、inittab の構文について説明します。

表 6–3 DHCP inittab ファイルの構文

オプション 

説明 

option-name

オプションの名前。オプション名は、そのオプションのカテゴリ内部で一意である必要がある。また、Standard、Site、Vendor のカテゴリにある、他のオプション名と重複できない。たとえば、同じ名前を持つ Site オプションを 2 つ持つことはできず、Standard のオプションと同じ名前の Site のオプションは作成できない 

category

オプションが所属する名前空間を特定する。Standard、Site、Vendor、Field、または Internal の 1 つにする必要がある 

code

オプションがネットワーク経由で送信されたときにそのオプションを特定する。多くの場合、カテゴリがなくてもコードはオプションを一意に特定する。ただし、Field や Internal のような内部カテゴリの場合は、コードが他の目的のために使用されていることがあるため、広域的に一意ではないことがある。コードは、オプションのカテゴリ内部では一意であることが必要で、Standard と Site のフィールドにあるコードと重複することはできない 

type

このオプションと関連するデータを記述する。有効なタイプには、IP、Ascii、Octet、Boolean、Unumber8、Unumber16、Unumber32、Unumber64、Snumber8、Snumber16、Snumber32、Snumber64 がある。 数値の場合、最初の U または S はその数値が符号付か符合なしかを表し、終わりの数字はその数値のビット数を表す。タイプには、大文字小文字の区別はない 

granularity

このオプションの値全体を構成するデータの単位数を記述する 

maximum

このオプションについて許容される値全体の数を記述する。0 は、無限大の数を表す 

consumers

この情報を使用できるプログラムを記述する。これには次の sdmi を指定する。

    ssnoop


    din.dhcpd


    mdhcpmgr


    idhcpinfo


inittab のエントリの例は、次の通りです。

StaticRt Standard, 33, IP, 2, 0, sdmi

このエントリは、StaticRt という名前のオプションを記述しています。このオプションは、Standard カテゴリにあり、オプションコード 33 です。データ型が IP、最小値が 2、最大値が無限大 (0) であるため、期待される値は、潜在的には無限の IP アドレスの組です。このオプションを利用するのは sdmi: snoopin.dhcpddhcpmgrdhcpinfo です。

dhcptags エントリの inittab エントリへの変換

以前にエントリを dhcptags ファイルに追加している場合は、新しい inittab ファイルに対応するエントリを追加する必要があります。次の例では、dhcptags エントリの例を inittab フォーマットで表す方法を示しています。

ネットワークに接続されたファックスについて、次の dhcptags エントリを追加したと想定してください。

128 FaxMchn - IP Fax_Machine

コード 128 は、サイトカテゴリになければならないことを意味しており、オプション名は FaxMchn、データタイプは IP です。

対応する inittab エントリは次の通りです。

FaxMchn SITE, 128, IP, 1, 1, sdmi

最小値 1 と最大値 1 は、このオプションについて 1 つの IP アドレスが予想されることを意味しています。