TELNETクライアント(簡易版)
TELNETクライアントの簡易版です。オプション交渉は必要最低限ですが、通常のTELNETサーバーならば接続できると思います。
<制限事項>
- Stabilizer ver3.00以降で実行してください。
- Stabilizer がエスケープシーケンスの処理に対応していないため、完全なTELNETクライアントとして動作させるのには難があります。スクリプトのサンプルとしてのご利用にとどめてください。
-------------------------------------------------
-- TELNETクライアント(簡易版)
-------------------------------------------------
-- TELNETコマンド
IAC = 255
DONT = 254 -- 送り手は受け手にオプションを無効にさせたい。
DO = 253 -- 送り手は受け手にオプションを有効にさせたい。
WONT = 252 -- 送り手はオプションを無効にしたい。
WILL = 251 -- 送り手はオプションを有効にしたい。
SB = 250 -- サブオプション開始
SE = 240 -- サブオプション終了
-- オプションID
OPT_ECHO = 1 -- echo
OPT_GA = 3 -- suppress go ahead
OPT_TYPE = 24 -- terminal type
-- オプション交渉状態ステータス
STS_IDLE = 0 -- アイドル状態
STS_IAC = 1 -- IAC受信
STS_DONT = 2 -- DONT受信
STS_DO = 3 -- DO受信
STS_WONT = 4 -- WONT受信
STS_WILL = 5 -- WILL受信
STS_SB = 6 -- サブオプション開始
-- TELNETステータス
TEL_NONE = 0 -- 未接続
TEL_NEG = 1 -- オプション交渉
TEL_ONLINE = 2 -- TELNET接続中
-- 変数定義
local g_optsts = STS_IDLE -- オプション交渉状態ステータス
local g_telsts = TEL_NONE -- TELNETステータス
local g_connect = false -- 接続監視
local g_cur_echo -- ローカルエコー設定
-------------------------------------------------
-- 受信ハンドラ
-------------------------------------------------
function rx_handler( buf, len )
-- オプション交渉
if g_telsts == TEL_NEG or g_telsts == TEL_NONE then
do_negotiation( buf, len )
end
return 1
end
-------------------------------------------------
-- オプション交渉
-------------------------------------------------
function do_negotiation( buf, len )
for i=1, len, 1 do
local c = string.byte( buf, i )
if g_optsts == STS_IDLE then
if do_opt_idle( c ) then
break
end
elseif g_optsts == STS_IAC then
do_opt_iac( c )
elseif g_optsts == STS_DONT then
do_opt_dont( c )
elseif g_optsts == STS_DO then
do_opt_do( c )
elseif g_optsts == STS_WONT then
do_opt_wont( c )
elseif g_optsts == STS_WILL then
do_opt_will( c )
elseif g_optsts == STS_SB then
if c == OPT_TYPE then
do_opt_type( buf, i, len )
end
end
end
end
-------------------------------------------------
-- アイドル時の処理
-------------------------------------------------
neg_buf = {}
neg_idx = 1
function do_opt_idle( c )
if c == IAC then
neg_idx = 1
g_optsts = STS_IAC
else
if c == "l" then
neg_idx = 1
end
neg_buf[ neg_idx ] = c
neg_idx = neg_idx + 1
if neg_idx >= 7 then
-- login移行でオプション交渉終了
if string.find( Tbl2Str( neg_buf ), "login" ) ~= nil then
g_telsts = TEL_ONLINE
else
neg_idx = 1
end
end
end
return ( g_telsts == TEL_ONLINE )
end
-------------------------------------------------
-- IAC
-------------------------------------------------
function do_opt_iac( c )
if c == DONT then
g_optsts = STS_DONT
elseif c == DO then
g_optsts = STS_DO
elseif c == WONT then
g_optsts = STS_WONT
elseif c == WILL then
g_optsts = STS_WILL
elseif c == SB then
g_optsts = STS_SB
else
g_optsts = STS_IDLE
end
end
-------------------------------------------------
-- DONT
-- DONTに対しては、OK(WONT)と応答しなければなりません。
-------------------------------------------------
function do_opt_dont( c )
sendbuf = { IAC, WONT, c }
SendData( sendbuf )
g_optsts = STS_IDLE
end
-------------------------------------------------
-- DO
-------------------------------------------------
function do_opt_do( c )
sendbuf = {}
sendbuf[ 1 ] = IAC
-- クライアントエコーはNO
if c == OPT_ECHO then
sendbuf[ 2 ] = WONT
-- 進行抑止
elseif c == OPT_GA then
sendbuf[ 2 ] = WILL
-- ターミナルタイプ
elseif c == OPT_TYPE then
sendbuf[ 2 ] = WILL
-- その他はNO
else
sendbuf[ 2 ] = WONT
end
sendbuf[ 3 ] = c
SendData( sendbuf )
g_optsts = STS_IDLE
end
-------------------------------------------------
-- WONT
-- WONTに対しては、OK(DONT)と応答しなければなりません。
-------------------------------------------------
function do_opt_wont( c )
sendbuf = { IAC, DONT, c }
SendData( sendbuf )
g_optsts = STS_IDLE
end
-------------------------------------------------
-- WILL
-------------------------------------------------
function do_opt_will( c )
sendbuf = {}
sendbuf[ 1 ] = IAC
-- サーバーエコー
if c == OPT_ECHO then
sendbuf[ 2 ] = DO
-- 進行抑止
elseif c == OPT_GA then
sendbuf[ 2 ] = DO
-- その他はOK
else
sendbuf[ 2 ] = DO
end
sendbuf[ 3 ] = c
SendData( sendbuf )
g_optsts = STS_IDLE
end
-------------------------------------------------
-- ターミナルタイプ
-------------------------------------------------
function do_opt_type( buf, pos, len )
if pos+3 <= len and
string.byte( buf, pos+1 ) == 1 and
string.byte( buf, pos+2 ) == IAC and
string.byte( buf, pos+3 ) == SE then
sendbuf = { IAC, SB, OPT_TYPE, 0, "IBMPC", IAC, SE }
SendData( sendbuf )
g_optsts = STS_IDLE
end
end
-------------------------------------------------
-- 1秒タイマ(接続監視)
-------------------------------------------------
function timer_handler()
connect = IsConnect( 0 )
-- 未接続の場合
if g_connect == false then
if connect then
g_connect = true
-- オプション交渉へ移行
g_telsts = TEL_NEG
g_optsts = STS_IDLE
-- DOut( "Connected.\n" )
end
-- 接続中
else
if connect == false then
g_connect = false
-- TELNETステータスリセット
g_telsts = TEL_NONE
-- DOut( "Disconnected.\n" )
end
end
end
-------------------------------------------------
-- 初期化
-------------------------------------------------
function init()
-- ShowMon( true )
-- ClrMon()
local rtn = false
-- 動作モードをTCPに設定
run_mode = GetRunModeParam()
if run_mode ~= 1 then
rtn = false
SetRunModeParam( 1, 3 )
end
-- TCPクライアントの設定確認
mode, s_port, s_valid_ip, s_ip, c_port, c_ip, c_valid_lport, c_lport,
c_valid_lip, c_lip = GetTcpParam( 0 )
if mode ~= 1 then
ShowMessageDlg( "TCPの動作はクライアントに設定してください。",
"ネットワーク設定エラー", false )
elseif c_port ~= 23 then
ShowMessageDlg( "接続先ポート番号を23に設定してください。",
"ネットワーク設定エラー", false )
else
rtn = true
end
return rtn
end
-------------------------------------------------
-- 終了処理
-------------------------------------------------
function exit_handler()
CloseTcp( 0 )
SetNetAutoCtrl( true )
-- パラメータを元に戻す
SetLocalEcho( g_cur_echo )
end
-------------------------------------------------
-- メイン
-------------------------------------------------
-- ローカルエコー状態取得
g_cur_echo = GetLocalEcho()
if init() then
-- [オプション] - [送信] の設定で、入力文字送信あり、
-- 入力後すぐに送信 に設定しておきます。
-- 実行中は、ネットワーク自動制御を無効にします。
SetNetAutoCtrl( false )
-- 受信ハンドラ登録
SetRxHandler( "rx_handler" )
-- タイマハンドラ登録
StartTimer( 1, 1000, "timer_handler" )
-- 終了ハンドラ登録
SetExitHandler( "exit_handler" )
-- TCPは再オープンします。
CloseTcp( 0 )
Wait( 1000 )
OpenTcp( 0 )
end