#author("2018-03-11T21:49:39+09:00","default:nowsky","nowsky")
#author("2018-03-12T00:04:54+09:00","default:nowsky","nowsky")
*gdnsd [#p9c99800]
オープンソースのグローバルロードバランサー(GSLB)
ソースコード量が少なく、高速動作と脆弱性の発生しにくさが特長となっている。
ただし、ソースコードを減らす為にプログラムのロギング機能が省略されていたり、
細かいヘルスチェックはスクリプトを別途作成する必要がある為、
フル機能を使いこなすには知識・技術が必要なソフトウェアである。
 
gdnsdは通信事業者レベルでの採用実績がある。
また、ソースコードが少ない割には整理されている為、機能追加も比較的楽に出来る。
~
*参考サイト [#h651c013]
-[[gdnsd:+http://gdnsd.org/]]
-[[GitHub gdnsd:+https://github.com/gdnsd]]
-[[gdnsdでかんたんGSLB:+https://qiita.com/jh1vxw/items/7ce5d14e9f964f001257]]
~
* 構築環境 [#f4cf0e44]
-[[配布サイト:+https://github.com/gdnsd/gdnsd/releases/]]
-[[公式ドキュメント:+https://github.com/gdnsd/gdnsd/wiki]]
 
#block
|LEFT:80|LEFT:180|LEFT:180|c
|CENTER:~Parameter|CENTER:~DNS-A|CENTER:~DNS-B|h
|&color(#2020ff){OS};|openSUSE Leap 42.3|openSUSE Leap 42.3|
|&color(#2020ff){GIP};|1.1.0.1|1.1.0.2|
|&color(#2020ff){IP};|10.0.0.1|10.0.0.2|
|&color(#2020ff){A-RR};|ns1.gslb.test.org|ns2.gslb.test.org|
|&color(#2020ff){USER};|>|gdnsd|
|&color(#2020ff){VERSION};|>|v2.4.0|
|&color(#2020ff){PREFIX};|>|/usr/lcoal/gdnsd-2.4.0|
|&color(#2020ff){CONFIG};|>|/usr/lcoal/gdnsd/etc/gdnsd/config|
|&color(#2020ff){ZONE};|>|/usr/lcoal/gdnsd/etc/gdnsd/zones/gslb.test.org|
 
|LEFT:80|LEFT:180|LEFT:180|c
|CENTER:~Parameter|CENTER:~SERVER-A|CENTER:~SERVER-B|h
|&color(#2020ff){IP};|192.168.0.1|192.168.0.2|
|&color(#2020ff){A-RR};|sv1.gslb.test.org|sv2.gslb.test.org|
#block(next)
#ref(Linux/Source/gdnsd/wiki_gdnsd_01.png,45%,left,nowrap)
#block(end)
~
* インストール [#g603a033]
-&size(16){&font(b){1. インストール};};
gdnsdの最新機能を利用する為、今回はソースからビルドする。
ソースビルド時でもバージョン管理が行える様に、
prefix指定を変更した上でシンボリックリンクを張る事でプログラムの参照先を切り替える。
 # zypper install libev4 libev-devel ragel
 # wget https://github.com/gdnsd/gdnsd/archive/v2.4.0.tar.gz
 # tar zxvf gdnsd-2.4.0.tar.gz
 # cd gdnsd-2.4.0
 # ./configure --prefix=/usr/local/gdnsd-2.4.0
 # make
 # make install
 
-&size(16){&font(b){2. 起動準備};};
gdnsdを動かす為の実行ユーザを作成した上で起動スクリプトも準備する。
gdnsdはsystemd起動に最適化されている為、
従来のinitスクリプトでは無くサービスファイルから起動を行う。
 # cd /usr/local
 # ln -s /usr/local/gdnsd-2.4.0 gdnsd
 # cd /etc
 # ln -s /usr/local/gdnsd/etc/gdnsd gdnsd
 # vi /usr/lib/systemd/system/gdnsd.service
 ---
 [Unit]
 Description=gdnsd Authoritative GSLB type DNS Server
 After=local-fs.target network.target
 
 [Install]
 WantedBy=multi-user.target
 
 [Service]
 Type=notify
 NotifyAccess=all
 ExecStart=/usr/local/gdnsd/sbin/gdnsd -c /etc/gdnsd -f start
 ExecStop=/usr/local/gdnsd/sbin/gdnsd -c /etc/gdnsd stop
 
 ## Security Setting
 MountFlags=slave
 DevicePolicy=closed
 PrivateDevices=true
 PrivateTmp=true
 ProtectSystem=full
 ProtectHome=true
 
-&size(16){&font(b){3. コンフィグ};};
gdnsdのコンフィグは、&color(#ff0000){[${PREFIX}/etc/config]};から固定参照で読み込んでいるので、
gdnsdのコンフィグは、&color(#ff0000){[${PREFIX}/etc/gdnsd/config]};から固定参照で読み込んでいるので、
上記設定に合わせてコンフィグを作成しないと、プログラムの起動に失敗する。
今回はprefixをシンボリックリンクで[/usr/local/gdnsd]に変更している為、
作成するコンフィグファイル名も&color(#ff0000){[/usr/local/gdnsd/etc/config]};になる。
作成するコンフィグファイル名も&color(#ff0000){[/usr/local/gdnsd/etc/gdnsd/config]};になる。
コンフィグファイルにはgdnsdのヘルスチェック条件も書く必要があるが、
権威DNSサーバ機能のみ利用するならば、optionsのみ記載すればプログラムを起動出来る。
なお、コンフィグのコメント接頭文字は『#(シャープ)』となる。
 # vi /usr/local/gdnsd/etc/config
 # vi /usr/local/gdnsd/etc/gdnsd/config
 ---
 options => {
     username       => gdnsd,
     chaos_response => "GSLB",
     listen         => 0.0.0.0:53,
     http_listen    => 0.0.0.0:3506,
     log_stats      => 3600,
 #   tcp_threads    => 2,
 #   udp_threads    => 2,
 
     include_optional_ns    => true,
     disable_text_autosplit => false,
     zones_strict_data      => false,
     zones_strict_startup   => true,
     zones_rfc1035_auto     => false,
 
     state_dir              => /var/lib/gdnsd,
     run_dir                => /var/run/gdnsd,
     plugin_search_path     => /usr/local/gdnsd/lib64/gdnsd,
 }
#region(&color(#ff0000){設定の解説};)
詳細はgdnsdの[[公式ドキュメント:+https://github.com/gdnsd/gdnsd/wiki/GdnsdConfig]]に書いてある。
細かい設定パラメータも存在するので、作り込む場合は内容を一読した方が良い。
 username               => #gdnsdの実行ユーザ
 chaos_response         => #DNSのchaosクラス変更
 listen                 => #gdnsdのLISTENアドレス、ポート番号
 http_listen            => #ヘルスチェック画面のLISTENアドレス、ポート番号
 log_stats              => #gdnsdのクエリ統計データ出力秒
 tcp_threads            => #TCPクエリの実行スレッド数
 udp_threads            => #UDPクエリの実行スレッド数
 include_optional_ns    => #AUTHORITY-SECTIONにオプションのNSレコード注入
 disable_text_autosplit => #TXTレコードを255バイト毎に自動分割
 zones_strict_data      => #DNSゾーンデータのワーニングを無視
 zones_rfc1035_auto     => #DNSゾーンデータ変更時の自動リロード(RFC1035)の有効化
 state_dir              => #gdnsd一次フォルダ
 run_dir                => #gdnsdのPIDファイル保存先
 plugin_search_path     => #ヘルスチェックモジュール保存先
全オプションはgdnsdの[[公式ドキュメント:+https://github.com/gdnsd/gdnsd/wiki/GdnsdConfig]]を確認する。
最低限の動作を行う場合、下記オプションを参考に設定を行う。
|LEFT:200|LEFT:600|c
|CENTER:~OPTIONS HASH|CENTER:~DESCRIPTION|h
|&color(#2020ff){username};|gdnsdを実行するユーザ名&br;グループ名はユーザに紐付いている物が自動適用される|
|&color(#2020ff){chaos_response};|CHクラスの応答内容&br;権威DNSのバージョン確認クエリに、設定した文字列を返す|
|&color(#2020ff){listen};|gdnsdの待ち受けIPアドレス・ポート番号&br;複数IPを待ち受けする場合はリスト構造にする|
|&color(#2020ff){http_listen};|gdnsdヘルスチェック画面の待ち受けIPアドレス・ポート番号&br;複数IPを待ち受けする場合はリスト構造にする|
|&color(#2020ff){log_stats};|DNSクエリの統計ログ出力間隔&br;値を"0"にすると、統計ログ出力が無効化される|
|&color(#2020ff){tcp_threads};|リスナーアドレスに対して作成されるスレッド数&br;マルチコアCPUの場合、CPUコアの2~4倍にするとパフォーマンスが上がる|
|&color(#2020ff){udp_threads};|リスナーアドレスに対して作成されるスレッド数&br;マルチコアCPUの場合、CPUコアの2~4倍にするとパフォーマンスが上がる|
|&color(#2020ff){include_optional_ns};|DNSのAuthoritySectionにオプションのNSレコードを含めて応答する&br;応答速度とクエリサイズ最小化を優先する時は無効化(false)にする|
|&color(#2020ff){disable_text_autosplit};|TXTレコードを255バイト毎に自動分割する設定を切り替える&br;通常は自動分割させる為、&color(#ff0000){自動分割を無効(false)};に設定する|
|&color(#2020ff){zones_strict_data};|DNSゾーンファイルで重要度低のエラーが発生してもデーモンを起動する&br;"zones_strict_startup"の設定に依存する|
|&color(#2020ff){zones_strict_startup};|gdnsd起動時にDNSゾーンファイルが正しく読めない時は起動停止させる&br;無効化(false)の場合、読込み失敗したDNSゾーンをスキップして起動させる|
|&color(#2020ff){zones_rfc1035_auto};|DNSゾーンファイルの書き換えを検出し、DNSレコードに自動適用する&br;ファイル変更による意図しない適用が発生しやすいので無効(false)を推奨|
|&color(#2020ff){state_dir};|gdnsdのデーモン起動情報を外部プログラムと連携する際に使用&br;ディレクトリが存在しない時は自動生成される|
|&color(#2020ff){run_dir};|gdnsdのPIDファイル保存フォルダ&br;systemdからプロセス操作を行う際に必須となる|
|&color(#2020ff){plugin_search_path};|ヘルスチェックモジュールの保存先ディレクトリ&br;基本的にPREFIX配下となる&color(#ff0000){"${PREFIX}/lib64/gdnsd"};を設定する|
#endregion
 
-&size(16){&font(b){4. ゾーンファイル};};
gdnsdのDNSゾーンはレコード登録したいORIGINと同じ実ファイル名で作成する必要がある。
"gslb.test.org"のゾーンを作成する場合、
DNSゾーンファイルは「/usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org」となる。
通常のDNSレコードの書式はBINDのゾーン記法と同じな為、今回は解説を割愛する。
DNSゾーンファイルは、権威DNSとしてレコードを登録したいORIGINと同じファイル名にする。
例えば、[gslb.test.org]のゾーンを作成する場合、
DNSゾーンファイルは&color(#ff0000){[/usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org]};となる。
ファイルの書式は基本的にBINDのゾーン記法と同じだが、
ヘルスチェックを元にした可変レコードの箇所のみ、gdnsd特有の設定を行う必要がある。
GSLBの特性上TTLを短くする必要がある為、ゾーンファイル内でTTLを明記して設定を切り替える。
参考として、DNSゾーンファイルの例を構築例に従って作成してみる。
 # vi /usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org
 ---
 $ORIGIN gslb.test.org.
 $TTL    3600
 @       IN  SOA  ns1.gslb.test.org.  root.gslb.test.org. (
                                         2018010101  ; serial
                                         3600        ; refresh
                                         1200        ; retry
                                         1209600     ; expire
                                         3600        ; minimum
                                      )
 
 ;; GLUE RECORD
 ;;
         IN  NS      ns1.gslb.test.org.
         IN  NS      ns2.gslb.test.org.
 ns1     IN  A       10.0.0.1
 ns2     IN  A       10.0.0.2
 
 ;; CONTENTS
 sv1     IN  A       192.168.0.1
 sv2     IN  A       192.168.0.2
 
 ;; GSLB
 ;;
 $TTL    10
 ;; この箇所にGSLBの可変レコードを記載
 
-&size(16){&font(b){5. 起動};};
事前に作成したサービスファイルを用いてgdnsdを起動させる。
gdnsdのログはsyslogのdaemonファシリティに出力されるので、
エラーで起動しない時は該当ログを確認する。
 # systemctl unmask gdnsd.service
事前に作成したサービスファイルを用いてgdnsdを起動する。
ログはsyslogのdaemonファシリティに出力されるので、起動しない時は該当ログを確認する。
 # systemctl unmask gdnsd
 # systemctl enable gdnsd
 # systemctl start gdnsd
~
* ヘルスチェック [#g6be9422]
ヘルスチェックを元にした広域負荷分散処理が、GSLBの本質機能となる。
gdnsdにもヘルスチェック機能が搭載されている為、単体でGSLBとして十分に稼働させる事が可能である。
GSLBは下位サーバに対してヘルスチェックを行い、ステータスに応じた可変レコード応答が特徴となる。
負荷分散(ラウンドロビン)、冗長化(アクティブ・スタンバイ)など様々な構成を取る事が出来る。
gdnsdにもヘルスチェックが搭載されており、基本的なGSLBとして機能するようになっている。
また、標準のヘルスチェックで機能不足の場合、ヘルスチェックで外部コマンドを実行する事で、
環境に応じた機能拡張を行う事も出来る。
 
ヘルスチェックの挙動はコンフィグファイルに書いた後、
DNSゾーンファイルで特殊なレコード設定を行う事によりDNSレコードを動的に変更する事が出来る。
gdnsd用の特殊レコードのDYNA/DYNCレコードを設定する事で、ヘルスチェックに基づいた可変応答が可能となる。
Aレコードを応答させる場合はDYNAレコード、CNAMEの場合はDYNCレコードを使用する。
gdnsdのヘルスチェックを利用する時は、gdnsdのconfigファイルにヘルスチェック定義を設定した後、
DNSゾーンファイルで専用の可変レコードを設定する事により利用可能となる。
可変レコードは&color(#ff0000){Aレコードを定義するDYNAレコード};と、&color(#ff0000){CNAMEを定義するDYNCレコード};の2種類が存在する。
ただし、利用出来る可変レコードはプラグイン毎に制限されている為、詳細は公式ドキュメントを確認する。
 
DYNA/DYNCレコードは&color(#ff0000){["プラグイン種別"!"応答レコード定義名"]};で設定する。
DNSゾーンファイルには下記の様なレコードを追記する事となる。
 www    10  DYNA  multifo!tcp_80
 blog   10  DYNA  weighted!tcp_443
 cname  10  DYNC  weighted!tcp_cname
 
-&size(16){&font(b){ラウンドロビン};};
#region(&color(#ff0000){設定内容};)
ヘルスチェックを行いつつ、バックグランドへラウンドロビンで振り分ける方法。
コンテンツサーバ側で「TCP:80」を待ち受けている環境を想定して設定。
gdnsdのヘルスチェック設定は既存のconfigに追記を行う。
ヘルスチェックを行いつつ、コンテンツサーバにラウンドロビンで振り分ける。
コンテンツサーバでWEB(TCP:80)を待ち受けている環境を想定して作成する。
gdnsdのヘルスチェック設定は、既存のconfigファイルに追記を行う事で定義する。
 # vi /usr/lcoal/gdnsd/etc/gdnsd/config
 ---
 service_types   => {
     tcp_80_http => {
         plugin      => http_status,
         port        => 80,
         url_path    => /check,
         url_path    => /,
         ok_codes    => [ 200, 301 ],
         up_thresh   => 10,
         ok_thresh   => 5,
         down_thresh => 5,
         interval    => 5,
         timeout     => 4,
     }
 }
 
 plugins     => {
     multifo => {
         tcp_80 => {
             service_types => tcp_80_http,
             up_thresh     => 0.001,
             SERVERA       => 192.168.0.1
             SERVERB       => 192.168.0.2
             SERVERA       => 192.168.0.1,
             SERVERB       => 192.168.0.2,
         }
     }
 }
 
DNSゾーンファイルにはDYNAレコードを登録する。
Parameterには["プラグイン"!"サービスタイプ"]の順番で登録を行う
 # vi /usr/lcoal/gdnsd/etc/gdnsd/zones/gslb.test.org
DNSゾーンファイルには、Aレコード・CNAMEの応答内容に従って可変レコードを記載する。
例えば、Aレコードとして可変応答させる場合は下記の様になる。
 # vi /usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org
 ---
         IN  NS     ns1.gslb.test.org.
         IN  NS     ns2.gslb.test.org.
 ns1     IN  A      192.168.0.1
 ns2     IN  A      192.168.0.2
 
 test    10  DYNA   multifo!tcp_80
 ;; DNSゾーンに追記
 $TTL    10
 www     10  DYNA   multifo!tcp_80
#endregion
 
-&size(16){&font(b){重み付け応答};};
#region(&color(#ff0000){設定内容};)
重み付け応答を行う場合、上記のラウンドロビン設定を修正するだけで実装出来る。
変更箇所はpluginsフィールドのみで、service_typesは書き換えなくて良い。
下記では、SERVER-Aを1、SERVER-Bを3とした場合の重み付け応答となる。
重み付けに応じて応答するレコードを変更する場合、ラウンドロビン設定内のIP指定部分をリストに変更する。
変更箇所はpluginsフィールド内のみで、service_typesは書き換えなくて良い。
下記設定では、SERVER-Aを1、SERVER-Bを3とした場合の重み付け応答となる。
 # vi /usr/lcoal/gdnsd/etc/gdnsd/config
 ---
 plugins     => {
     multifo => {
 plugins      => {
     weighted => {
         tcp_80 => {
             service_types => tcp_80_http,
             up_thresh     => 0.001,
             SERVERA       => [ 192.168.0.1, 1 ]
             SERVERB       => [ 192.168.0.2, 3 ]
             multi         => false,
             SERVERA       => [ 192.168.0.1, 1],
             SERVERB       => [ 192.168.0.2, 3],
         }
     }
 }
 
重み付け応答にする為、監視モジュールを[multifo]から[weighted]に切り替えている為、
DNSゾーンファイルのDYNAレコード設定も変更する。
 # vi /usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org
 ---
 ;; DNSゾーンに追記
 $TTL    10
 www     10  DYNA   weighted!tcp_80
#endregion
 
-&size(16){&font(b){ping死活監視};};
#region(&color(#ff0000){設定内容};)
gdnsdのモジュールにはping死活監視モジュールが存在しない。
その為、ping死活で振り分けを変更する場合、外部コマンドモジュールを利用する。
gdnsdのヘルスチェックには、ping死活監視モジュールが存在しない。
その為、ping死活で応答レコードを変更する場合、外部コマンドモジュールを利用してpingを直接実行する。
 
外部コマンドにIPアドレスを引き渡す場合、特殊変数の[%%ITEM%%]を指定する。
また、パラメータ内で利用するコマンド自体のタイムアウト秒数が、
外部コマンドに監視対象のIPアドレスを引き渡す場合、特殊変数の&color(#ff0000){"%%ITEM%%"};を指定する。
"%%ITEM%%"変数を指定する事で、configファイルの応答IPアドレスを監視対象としてスクリプトに引き渡す。
外部コマンドモジュールを利用する場合、パラメータ内で利用するコマンドのタイムアウト秒数が、
gdnsdヘルスチェックのタイムアウト秒数以上にならない様に注意する。
 # vi /usr/lcoal/gdnsd/etc/gdnsd/config
 ---
 service_types    => {
     icmp_monitor => {
     icmp_command => {
         plugin      => extmon,
         cmd         => ["/usr/sbin/fping", "-t 3", "%%ITEM%%"],
         interval    => 10,
         timeout     => 4,
         up_thresh   => 6,
         ok_thresh   => 3,
         down_thresh => 3,
     }
 }
 
 plugins     => {
     multifo => {
         tcp_80 => {
             service_types => icmp_monitor,
         icmp_check => {
             service_types => icmp_command,
             up_thresh     => 0.001,
             SERVERA       => 192.168.0.1
             SERVERB       => 192.168.0.2
             SERVERA       => 192.168.0.1,
             SERVERB       => 192.168.0.2,
         }
     }
 }
 
ヘルスチェックの定義はgdnsdのconfigファイルで行っている為、
DNSゾーンファイルは既存設定から変更しない。
 # vi /usr/lcoal/gdnsd/etc/gdnsd/zones/gslb.test.org
DNSゾーンファイルの内容も設定に応じて書き換える。
外部コマンドを利用しているが、DYNAレコードに影響のあるpluginsは大きく変更していない為、
従来通りの書式に従ってDYNAレコード設定を変更する。
 # vi /usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org
 ---
         IN  NS     ns1.gslb.test.org.
         IN  NS     ns2.gslb.test.org.
 ns1     IN  A      192.168.0.1
 ns2     IN  A      192.168.0.2
 
 test    10  DYNA   multifo!tcp_80
 ;; DNSゾーンに追記
 $TTL    10
 www     10  DYNA   multifo!icmp_check
#endregion
 
-&size(16){&font(b){NAT配下の監視};};
-&size(16){&font(b){NAT配下監視};};
#region(&color(#ff0000){設定内容};)
クラウド環境では、グローバルIPとインスタンス内のプライベートIPを、
NATで紐付けて動的制御している場合が多い。
クラウドではグローバルIPとインスタンス内部アドレスを、NATで紐付けてアドレスを割り当てている場合が多い。
この時、NAT装置がNATループバック(ヘアピンNAT)に対応していない場合、
gdnsd側でグローバルIP・プライベートIP両方で監視出来るように設定変更する必要がある。
グローバルIPからインスタンス内部アドレスに変換が出来ず、&color(#ff0000){グローバルIPでヘルスチェックが出来なくなる。};
解決方法は複数存在するが、楽な方法としては外部コマンドヘルスチェックを応用する事で、
インスタンス内部アドレスで監視しつつ、DNSの応答レコードをグローバルIPにする事が出来る。
 
プライベートIP・グローバルIP毎に応答レコードを変更する場合、
キャッシュDNSも併用した形で細工が必要となるが、
全てグローバルIPで応答する形で良いならば、外部コマンドを利用する事で制御出来る。
下記では、TCP:80番への死活監視とNAT配下の設定例を作成する。
下記は、Web(TCP:80)への死活監視をインスタンス内部アドレス(SERVER-A/B)で行いつつ、
DNSレコードとしてはグローバルIP(NAT)を応答する設定例となる。
 # vi /usr/lcoal/gdnsd/etc/gdnsd/config
 ---
 service_types    => {
     icmp_monitor => {
 service_types  => {
     script_mon => {
         plugin      => extmon,
         cmd         => ["/usr/local/bin/gdnsd_monitor.pl", "%%ITEM%%", "80"],
         cmd         => ["/usr/local/bin/script_mon.pl", "%%ITEM%%", "80"],
         interval    => 10,
         timeout     => 4,
         up_thresh   => 6,
         ok_thresh   => 3,
         down_thresh => 3,
     }
 }
 
 plugins     => {
     multifo => {
         tcp_80 => {
             service_types => icmp_monitor,
             service_types => script_mon,
             up_thresh     => 0.001,
             SERVERA       => 1.1.0.1
             SERVERB       => 1.1.0.2
             SERVERA       => 1.1.0.1,
             SERVERB       => 1.1.0.2,
         }
     }
 }
 
参考までに、実環境で利用している外部コマンド例を開示。
筆者はperlが一番慣れているので、下記例はperlを使っているが、
該当ポートへの接続性確認等ができれば、どの言語・スクリプトを利用しても問題無い。
 # vi /usr/local/bin/gdnsd_tcp_mon.pl 
DNSゾーンファイルは今までと同じように、plugins/service_typesを設定する。
この時、重み付け応答を行いたい場合、設定に合わせてDYNAレコードを修正する。
 # vi /usr/local/gdnsd/etc/gdnsd/zones/gslb.test.org
 ---
 ;; DNSゾーンに追記
 $TTL    10
 www     10  DYNA   multifo!tcp_80
 
外部コマンドは様々は作成方法があるが、筆者が作成したperlの作例を公開。
応答性重視の監視スクリプトとして利用する為、例外処理は全部省いている。
 # vi /usr/local/bin/script_mon.pl
 ---
 #!/usr/bin/perl
 
 $GLOBAL = $ARGV[0];
 $PORT   = $ARGV[1];
 %LOCAL;
 $LOCAL{'1.1.0.1'} = "10.0.0.1";
 $LOCAL{'1.1.0.2'} = "10.0.0.2";
 $GIP  = $ARGV[0];
 $PORT = $ARGV[1];
 %LIP;
 $LIP{'1.1.0.1'} = "10.0.0.1";
 $LIP{'1.1.0.2'} = "10.0.0.2";
 
 $STATUS = system("/usr/bin/nc -w 1 $LOCAL{$GLOBAL} -z ${PORT}");
 $STATUS = $STATUS >> 8;
 $STAT = system("/usr/bin/nc -w 1 $LIP{$GIP} -z ${PORT}");
 $STAT = $STAT >> 8;
 
 exit $STATUS;
 exit $STAT;
#endregion
 
-&size(16){&font(b){アクティブ・スタンバイ};};
#region(&color(#ff0000){設定内容};)
作成中...
#endregion