インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

IOTS2019
2019/12/6

sshr: ユーザに変更を要求せずにシステム変化に追従可能な SSH プロキシサーバ
鶴田 博文†1,a)

松本 亮介†1,b)

概要：Web サービスを支えるインフラは，ユーザからの多様な要求に応えるために，ユーザにシステムの構成情報やその変更を意識させることなく，迅速かつ柔軟にシステム構成を変更することが求められる．一方，サーバへのリモート接続サービスとして利用されている SSH では，ユーザが利用するサーバの IP ア
ドレスまたはホスト名を指定して接続要求を送るため，サーバの IP アドレスまたはホスト名に変更があった場合，ユーザは変更後の情報を知る必要がある．この問題を解決するために，gcloud コマンドのようなクライアントツールがサーバごとの一意のラベル情報をもとに接続先の IP アドレス等を取得する手法があるが，この手法ではユーザに用いるツールの制限や変更を要求する．別の手法として，SSH Piper のようなプロキシサーバがユーザ名をもとに接続先の IP アドレス等取得する手法があるが，既存のプロキシサー
バではその動作を変更するためにはソースコードを直接変更しなければならない．本論文では，ユーザに用いるクライアントツールの制限や変更を要求せず，システム管理者が組み込み可能なフック関数を用いてシステム変化に追従できる SSH プロキシサーバを提案する．提案手法は，組み込むフック関数のみの修正でプロキシサーバの動作を自由に変えられるため，システムの仕様変更に対して高い拡張性を有している．さらに実験から，提案手法を導入した場合の SSH セッション確立のオーバーヘッドは 20 ミリ秒程度であり，ユーザがサーバに SSH ログインする際に遅延を感じないほど短い時間であることを確認した．

sshr: An SSH Proxy Server
for Responding to System Changes without Forcing Users to Change
Hiforumi Tsuruta†1,a)

Ryosuke Matsumoto†1,b)

Abstract: The infrastructure of Web services is required to change the system configuration quickly andflexibly without making the user aware of the system configuration in order to respond to various requests
from users. On the other hand, since SSH used as a secure remote connection service to a server needs tosend a connection request by specifying the IP address or host name of the server, the user needs to know thechanged information when the IP address or host name is changed. In order to solve this problem, there is amethod in which a client tool such as gcloud command obtains the IP address or host name of the destination
based on the unique label information of each server. However, this method requires restrictions and changes
to the tools used by client-side. Another method is to use a proxy server, such as SSH Piper, to obtains the
IP address or host name of the connection destination based on the user name. However, in the existing
SSH proxy server, the source code must be changed directly to change the behavior of a proxy server. In
this paper, we propose an SSH proxy server that can respond to system changes using hook functions thatcan be incorporated by system administrators without requiring restrictions or changes to the clients. The
proposed method has high extensibility for system changes because the behavior of proxy server can be easilychanged by only modifying the hook function to be incorporated. Furthermore, when using the proposed
method, it was confirmed that the overhead of establishing an SSH session is about 20 milliseconds which isa short time that the user does not feel a delay when logging into the server with SSH.

ⓒ 2019 Information Processing Society of Japan87

インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

1. はじめにWeb サービスのようなインターネットを介して利用す

IOTS2019
2019/12/6

伴いクライアントツールの動作にも変更が生じた場合に，全ユーザに変更を要求することになる．
他の手法として，クライアントとサーバの間に導入したるサービスが世の中に普及し，その利用者数が増大していプロキシサーバがリクエストの情報をもとに接続先の IP

る．その結果，システム管理者は，サービス利用者からのアドレスまたはホスト名を取得する手法がある．これを実多様な要求に応えるために，管理するシステムの構成を状現できる既存の SSH プロキシサーバとして，SSH Piper[6]況に応じて迅速かつ柔軟に変化させることが求められていというオープンソース実装が存在する．ユーザは，SSH

る [1]．例えば，Web サービスの利用状況に基づき，サーバ

Piper を介して SSH 接続することで，用いるクライアント

をスケールアウト・スケールイン [2] することが要求されツールの制限や変更を要求されない，かつシステムの構成

る．Web サービスへの突発的なアクセス集中に対してサー情報やその変更を意識することなく，ユーザ名を用いて透バをスケールアウトさせ，アクセスが減少するとスケール過的に目的のサーバに SSH 接続ができる．しかしながら，インすることで，サービスの機会損失の低減や運用コスト

SSH Piper は接続先サーバを決定するロジックをシステムの削減を行うことができる．また，サービスの機能拡張や管理者が自由に組み込むことや変更することができず，ロ

規模拡大に伴い，新規サーバを導入 [3] していくことも要ジックを変更するためにはソースコードに直接変更を加え求される．市場変化をいち早く察知し，サービスそのもの

なければならないため，システムの仕様変更に対する拡張を変化させていくことは，サービスの競争力を維持・向上

性が低い．

させることにつながる．こうしたサービスを取り巻く環境

本論文では，ユーザに用いるクライアントツールの制限の変化やサービスそのものの規模の変化に対して，迅速かや変更を要求せず，システム管理者が自由に組み込み可能

つ柔軟にシステム構成を変化させながら対応していくことなフック関数を用いてシステム変化に追従できる SSH プ

は，サービス成長を加速させる上での重要な要素となる．

ロキシサーバを提案する．提案する SSH プロキシサーバ

システム管理者が迅速に変化に対応するためには，シスは sshr[7] と名付けた．sshr は，ユーザ名から接続先サーバ

テム内のサーバ等のリソースを使用するユーザに対して，を決定するためのフック関数をシステム管理者が自由に実システム変更が起きるたびに変更後の情報を提供すること

装・導入可能である．これにより，ユーザ名を用いて透過なく，自由にシステム構成を変更させられることが必要で的に目的のサーバに SSH 接続できるため，接続先サーバのある．一方，サーバへの安全なリモート接続サービスとしIP アドレスやホスト名に変更があった場合でも，管理者はて広く利用されている SSH（Secure Shell）[4] は，ユーザ各ユーザへ変更後の情報を知らせる必要がなく，ユーザもが利用するサーバの IP アドレスまたはホスト名を指定し変更に追従する必要がない．さらに，sshr は SSH のセッて接続要求を送る必要があるため，ユーザは自分が利用しション確立に必要なユーザ認証の処理を拡張するための関たいサーバの IP アドレスまたはホスト名を把握しておか数も備えている．例えば，sshr がユーザから公開鍵認証のなければならない．そのため，もしサーバの IP アドレス

リクエストを受けた際に，ユーザの公開鍵を検索する処理やホスト名に変更があった場合，管理者は各ユーザへ変更

をフック関数として組み込み可能である．これにより，シ後の情報を知らせる必要があり，ユーザはその変更に追従

ステム管理者がユーザの公開鍵をデータベースなどの自由しなければならない．

なデータ形式で管理することができる．このように，sshr

現在，ユーザが接続するサーバの IP アドレス・ホスト
名やその変更を意識することなく SSH 接続ができる手法

では SSH 特有の認証に対しても，プログラマブルに制御するための仕組みをとっている．

がいくつか存在する．一つは，クライアントツールがサー

本稿の構成を述べる．2 章では，既存手法とその課題にバごとの一意のラベル情報をもとに接続先の IP アドレスついて言及する．3 章では，本論文での提案を述べる．4

またはホスト名を取得する手法であり，例として，GCP

章では，提案手法を用いたユースケースについて具体例を（Google Cloud Platform）の gcloud コマンド [5] が挙げら挙げて説明する．5 章では，提案手法の性能評価の結果をれる．この手法を用いると，ユーザはシステムの構成情報述べる．最後に，6 章でまとめとする．

やその変更を意識することなく，サーバに紐づいたラベル
情報のみを用いて透過的に目的のサーバに SSH 接続がで

2. 既存手法とその課題

きる．しかしながら，この手法では，ユーザに用いるクラサービスへの多様な要求に応じてシステム構成を迅速に

イアントツールを強制する，かつシステム側の仕様変更に変更していくことが求められる状況においては，システム

†1

a)
b)

さくらインターネット株式会社 さくらインターネット研究所
SAKURA internet Research Center, SAKURA internet Inc.,
Akasaka, Chuo-ku, Fukuoka 810-0042 Japan
hi-tsuruta@sakura.ad.jp
r-matsumoto@sakura.ad.jpⓒ 2019 Information Processing Society of Japan

の運用管理も変更に追従できる必要がある．一方，サーバへのリモート接続サービスとして用いられる SSH では，通常サーバの IP アドレスやホスト名に変更があった場合，管理者は各ユーザへ変更後の情報を知らせる必要があり，
88インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

IOTS2019
2019/12/6

ユーザはその変更に追従しなければならない．本章では，ザ側ではなく，プロキシサーバ側に持たせたことで，ユー

この SSH の課題を解決する既存手法を整理し，それらのザが用いるツールの制限や変更を課す必要がない．しか特徴と課題について述べる．

し，一方で，ユーザ名から接続先サーバを決定するロジッ
クをシステム管理者が自由に開発・導入することができな

2.1 クライアントツールによる接続先の決定

い．これにより，接続先の決定に用いるユーザとサーバのgcloud は GCP 上のリソースを操作する主要なコマンド

紐付け情報を管理するデータ形式を自由に設計できない．

ラインツールである．「gcloud compute ssh」コマンド [8]例えば，ユーザとサーバの紐付け情報をデータベースで管にインスタンス名を指定することで，対象のインスタンスに理したい場合，SSH Piper 側が指定したスキーマのテーブ

SSH 接続が可能である．「gcloud compute ssh」は ssh(1)ルを用意する必要がある．もし，このような接続先決定のコマンド [9] のラッパーであり，SSH のリクエストを送る

ロジックを既存の仕組みから拡張したい場合には，ソース

前にインスタンス名をキーに GCP が管理している構成情

コードに直接変更を加えなければならない．

報から IP アドレスを取得する機能を有している．これにまた，SSH Piper のような接続先の決定が可能な SSH プ

より，ユーザは自身で定義したサーバごとに一意のインス

ロキシサーバを構築する手法の一つとして，sshd[12] を拡

タンス名を知っていれば，対象サーバの IP アドレスの情張する手法が挙げられる．sshd は，現在最も広く利用され報やその変更を意識することなく透過的に SSH 接続が可ている SSH サーバのデーモンプログラムである．プロキ

能である．

シサーバを一から実装する場合と比べて，sshd を拡張する

また，他の手法として，HashiCorp が開発するクラスタ

ことで，認証の仕組みを独自に実装する必要がなく，sshd

管理ツールである Consul[10] を用いた手法が挙げられる．

の信頼性の高い認証の仕組みを再利用できる点がメリット

Consul はクラスタ内のメンバー管理機能と，そのメンバーである．しかしながら，sshd はモジュールによる機能拡情報を参照するための HTTP API を有している．これら張の仕組みをサポートしていないため，その機能を拡張すを活用すると，ユーザが定義したサービス名やタグ情報をるためには，ソースコードに直接変更を加えなければなら

もとに特定サーバの IP アドレスを取得することができる

ない．

ため，この取得した情報をもとに SSH リクエストを送る
ようなクライアントツール [11] を作成可能である．

いずれの手法においても，ユーザが用いるツールの制限や変更を課す必要がなく，ユーザ名を用いて目的のサーバ

いずれの手法においても，ユーザはサーバごとにラベルに透過的な SSH 接続が可能である．もし，目的のサーバの情報を持たせられるため，同一ユーザで複数のサーバに対IP アドレス等に変更があった場合でも，ユーザはその変更

して，ラベル情報を用いた透過的な SSH 接続が可能であを意識することなく，プロキシサーバが変更に追従する役

る．もし，目的のサーバの IP アドレス等に変更があった場

割を担うことができる．一方，接続先決定のためのラベル

合でも，ユーザはその変更を意識することなく，クライア

情報として用いられるものがユーザ名に限られるため，同ントツールが変更に追従する役割を担うことができる．一

一ユーザは 1 サーバにしか紐づかない点は，プロキシサー

方，これらの手法は，ユーザ側に独自の SSH クライアント

バを用いた場合の制約となる．また，既存のプロキシサー

ツールの使用を強制する．そのため，システム側の仕様変バを構築する手法は，機能拡張の仕組みをサポートしてい更などに伴いクライアントツールの動作にも変更が生じた

ないため，仕様変更に対する拡張性が低いことが課題とし場合に，全ユーザが使用しているツールに対してバージョて挙げられる．

ンアップ等の変更を課す．したがって，ユーザがシステム側の仕様変更を意識する必要があることや，その変更に対して追従しなければならない点が課題として挙げられる．

3. 提案手法
2.1 節で述べた通り，システムの構成変更に追従する役
割をクライアントツール側が担う場合は，ユーザに用いる

2.2 プロキシサーバによる接続先の決定

クライアントツールの制限や変更を要求することが課題で

SSH Piper[6] は，GitHub 上でオープンソースソフトウェ

ある．一方，2.2 節で述べた通り，変更に追従する役割をアとして開発されている SSH のプロキシサーバである．

プロキシサーバが担う場合は，ユーザに制限や変更を要求

SSH Piper の特徴は，SSH のリクエストを受けた際に，そしないが，仕様変更に対するプロキシサーバの機能の拡張のユーザ名から利用する接続先サーバを決定できる点であ性が低いことが課題である．これらの課題を解決するためる．SSH 接続に SSH Piper を介することで，ユーザはプに，ユーザに用いるクライアントツールの制限や変更を要

ロキシサーバの IP アドレスまたはホスト名さえ知ってい求せず，システム管理者が自由に組み込み可能なフック関れば，接続するサーバの IP アドレス・ホスト名やその変数を用いてシステム変化に追従できる SSH プロキシサーバ

更を意識することなく，ユーザ名に紐づいたサーバに SSHを提案する．提案手法では，システム側に仕様変更があっ接続ができる．SSH Piper では接続先の決定の役割をユーた場合でも，ユーザにその変更を意識させることなく，プⓒ 2019 Information Processing Society of Japan89

インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

IOTS2019
2019/12/6

import ("github.com/tsurubee/sshr/sshr""log")

図 1: 提案手法の概要図

ロキシサーバに組み込むフック関数のみの修正でプロキシ
サーバの動作を拡張し，変更に対応可能である．

3.1 アーキテクチャの概要

func main() {confFile := "/etc/sshr/example.toml"s, _ := sshr.NewSSHServer(confFile)// 独自に実装した接続先サーバ決定のための関数を渡す
s.ProxyConfig.FindUpstreamHook = findUpstreamHook
if err := s.Run(); err != nil {log.Fatal(err)}}

図 2: 接続先の決定処理を組み込むためのサンプルコード

アント間とサーバ間の 2 つの SSH セッションを保持して提案手法では，SSH のプロキシサーバに対して，システ

おり，当然ながらそれぞれ異なるセッション ID を有してム管理者が実行したい処理を自由に実装し，フック関数といる．このため，プロキシサーバを介した公開鍵認証を行して組み込めるアーキテクチャをとった．図 1 は，提案手

いたい場合，クライアント・プロキシサーバ間およびプロ法の概要図である．SSH のプロキシサーバがクライアント

キシサーバ・SSH サーバ間の 2 段階で認証を行う必要がからの接続要求を受け取り，接続するサーバを決定するこある．

とで，ユーザはプロキシサーバの IP アドレスまたはホスト提案手法では，SSH プロキシサーバに対して，特定の役名さえ知っていれば，プロキシサーバより後方のシステム

割をもつ複数のフック関数を組み込み可能であり，それらの構成やその変更を意識する必要がなくなる．システム管の関数が SSH リクエストの処理の過程で順次実行される理者の視点では，ユーザに事前に提供するプロキシサーバ

仕組みをとっている．組み込み可能なフック関数として，の IP アドレスまたはホスト名の情報にさえ変更が起きな

SSH のリクエストを受けた際にユーザ名をもとに接続先

ければ，ユーザに知らせることなく自由にシステムの構成

サーバの IP アドレスまたはホスト名を取得する関数があ変更を行うことが可能となる．そこで，プロキシサーバのる．その他に，決定した接続先サーバとクライアント間の前段に構築したロードバランサに仮想 IP アドレスを割り

公開鍵認証を拡張するためのフック関数も備えている．具当て，ユーザからの SSH 接続を全て同じ IP アドレスで受

体的には，クライアント・プロキシサーバ間の認証においけ付けるようにすることが有効である．これにより，プロて，クライアントの公開鍵を検索する関数，およびプロキ

キシサーバの IP アドレスに変更が起きる場合や，プロキ

シサーバ・SSH サーバ間の認証に用いる秘密鍵を検索する

シサーバをスケールアウトしたい場合などに対してもユー関数がある．これらを用いると，SSH プロキシサーバにおザ側に変更を要求する必要がなくなる．

ける接続先の決定および公開鍵認証をプログラマブルに拡SSH でサーバに接続する場合，ユーザが目的のサーバ

張でき，システム管理者はユーザとサーバの紐付け情報や，を利用する権限をもっているかどうかを確認するために，認証に用いる鍵をデータベースなど自由なデータ形式で管ユーザ認証を行う必要がある [13]．提案手法では，認証方理することが可能となる．

式としてパスワード認証および公開鍵認証をサポートしている．プロキシサーバを介してユーザ認証を行う場合にプ

3.2 アーキテクチャの実装

ロキシサーバがクライアント・サーバ間の認証をどのよう提案するアーキテクチャを実現するために，Go 言語 [14]に仲介するかは用いる認証方式で異なる．パスワード認証

を用いて sshr[7] という SSH プロキシサーバを実装する．

の場合，プロキシサーバはクライアントから受けた認証リ

sshr を実装するための要件を整理すると，まず sshr は複数クエストを解釈することなく，SSH サーバにそのままリクのクライアントから同時に受けたリクエストを並行で処理

エストパケットを送り，SSH サーバ側で認証を行うことができる必要がある．また，sshr が SSH のリクエストを処できる．一方，公開鍵認証を用いた場合，プロキシサーバ

理するためには，SSH 特有の認証の仕組みをサポートしなは認証を SSH サーバに任せることはできない．なぜなら，ければならない．Go 言語は，並行処理の記述が容易であ

SSH セッションはセッション ID[13] と呼ばれるセッショ

るという特徴を有するため，1 つ目の要件を満たす．さらンごとに一意の識別子を有しており，公開鍵認証では，こに，Go 言語は，豊富な機能をもつ SSH パッケージ [15] がのセッション ID を含めたデータを秘密鍵で暗号し，認証存在するため，SSH プロキシサーバを実装する上で必要なリクエストを送るためである．プロキシサーバは，クライ認証等の多くの機能の実装に，SSH パッケージに備わってⓒ 2019 Information Processing Society of Japan90

インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

IOTS2019
2019/12/6

いる機能を利用できる．これらの実装面の要件に加えて，管理することが可能となる．次に，sshr サーバ・SSH サー

運用面の要件も存在する．sshr はシステムの多様な変更に

バ間において，sshr サーバはクライアントの秘密鍵を有し合わせて動作を変更することが想定されるため，その変更ていないため，別の秘密鍵を用いる必要がある．クライアから本番環境への適用が容易に行える必要がある．Go 言

ントが目的のサーバに SSH 接続をする妥当性については，

語ではソースコードをビルドした結果の実行ファイルとし一段階目のクライアント・sshr サーバ間で認証を行っていて，シングルバイナリが作成される．これにより，サーバ

るため，sshr サーバ・SSH サーバ間については，sshr サーへのデプロイが容易であることや，デプロイ先のサーバにバが有している特定の秘密鍵を SSH サーバで全て許可す特別な実行環境を必要としないなどのメリットがある．そるようにすることで，2 段階目の認証を行っている．こののため，例えばコード管理を Git で行い，リモートリポジ

際に，sshr サーバが SSH サーバへの認証に用いる秘密鍵

トリへのプッシュを起点に，ビルド，デプロイ，実行までを検索するためのフック関数として FetchPrivateKeyHookの一連の処理を CI ツールで容易に自動化できる．このよを備えている．このような認証方式を用いることによるセ

うにプログラムの修正から実行までを開発プロセスに組みキュリティリスクについては次節で言及する．

込むことで，保守性や開発効率を向上させることが可能でプロキシサーバを介した認証に成功し，SSH セッションある．これらの実装面および運用面の理由から sshr の実装を確立した後の sshr の動作について説明する．sshr で実に Go 言語を採用した．

行できるフック関数は，全て SSH セッション確立前に実sshr は，システム管理者が Go 言語で実装した関数を組

行されるものである．セッション確立後は，sshr はクライ

み込んでビルドすることで，プロキシサーバの機能を拡張

アントおよびサーバから受け取るパケットを解釈することできる仕組みをとっている．図 2 は，接続先の決定処理をはなく，パケットをそのまま転送するのみである．このた組み込むためのサンプルコードである．図中の sshr パッめ，sshr を用いた場合，セッション確立時にフック関数のケージの FindUpstreamHook に対してシステム管理者側

実行によるオーバーヘッドが発生する．この点ついては，

で独自に実装した関数を渡すことでフック関数として組み5 章で評価する．

込むことができる．このような仕組みを採用することで，システム管理者が実装したフック関数も含めてシングルバ

3.3 セキュリティリスクとその対策

イナリが作成できるため，前述のようなデプロイの容易性

sshr を用いた場合における第三者から不正アクセスを受や開発の効率化などのメリットを享受できる．sshr では，けるリスクについて議論する．認証方式としてパスワード

以下の三つのフック関数をサポートしている．

認証を用いた場合，sshr サーバはパスワードを読み取る(1) FindUpstreamHook

ことなく，SSH サーバにパケットを転送する．すなわち，(2) FetchAuthorizedKeysHook

ユーザのパスワードを知っていて，認証を行うことができ(3) FetchPrivateKeyHook

るのは SSH サーバのみであるため，sshr サーバを用いた（1）は，ユーザ名をもとに接続先サーバの IP アドレス

場合でも認証を突破されるリスクは変わらない．

またはホスト名を取得するための関数である．
（2）
・
（3）は

公開鍵認証を用いた場合，クライアント・プロキシサー

公開鍵認証を用いる場合に必要なフック関数である．（2）バ間およびプロキシサーバ・SSH サーバ間のセッションごは，ユーザの公開鍵を検索するための関数である．（3）は，とに 2 段階で認証を行う必要がある．sshr の認証の仕組み

sshr から接続先サーバに対して認証を行うために利用するは，3.2 章で述べた通り，sshr サーバから SSH サーバへの秘密鍵を検索するための関数である．（2）・（3）の用途に

公開鍵認証に特定の秘密鍵を全て受け入れるような設定をついては後述する．

SSH サーバに行っている．このため，sshr サーバのセキュ

SSH のプロキシサーバを実装する上での重要な課題としリティの問題や sshr デーモンの脆弱性などが原因で，sshrて，プロキシサーバを介したクライアント・サーバ間の認サーバが有している秘密鍵が流出した場合や，sshr サー

証をいかにして行うかという点が挙げられる．3.1 節で述バから秘密鍵を利用した任意のコマンドが実行される場

べた通り，公開鍵認証を用いた場合，クライアント・sshr

合，SSH サーバへの全ての SSH 接続を許してしまうこと

サーバ間および sshr サーバ・SSH サーバ間の 2 段階で認となる．

証を行う必要がある．まず，クライアント・sshr サーバ間

これらのリスクを最小化するための対策を sshr サーバ

において，sshr サーバはクライアントの公開鍵認証を行う

側と SSH サーバ側のそれぞれについて述べる．まず，sshr

ために，クライアントの公開鍵を検索するためのフック関サーバでは，保有している秘密鍵の流出を防ぐためにサー数である FetchAuthorizedKeysHook を備えている．これ

バのセキュリティを堅牢にする必要がある．例えば，sshr

は，sshd の AuthorizedKeysCommand[16] に相当する機能

サーバではログイン可能なユーザ数や権限を最小限に留めである．これを用いることで，システム管理者はユーザのることや，アクセスが可能な IP を組織内のネットワーク

公開鍵をデータベースなどの自由なデータ形式で一元的にのみ絞ることが有効である．次に，sshr を経由して任意のⓒ 2019 Information Processing Society of Japan91

インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

IOTS2019
2019/12/6

type Response struct {Username string ‘json:"username"‘
Hostname string ‘json:"hostname"‘
PublicKey string ‘json:"publickey"‘}

図 3: システム構成の例

func findUpstreamHook(username string) (string, error) {requestURL := "http://sshr.jp/upstream/username"resp, _ := http.Get(requestURL)
defer resp.Body.Close()b, _ := ioutil.ReadAll(resp.Body)var decoded = new(Response)
if err := json.Unmarshal(b, &decoded); err != nil {return "", err}
return decodedBody.Hostname, nil}

図 5: Web API 経由での接続先取得のサンプルコード

る sshd[12] などが想定される．DB ロールは，sshr を利用するユーザやサーバが増えてきた場合，それらの管理を行うデータベースサーバである．図 4 は，テーブルスキーマ
図 4: テーブルスキーマの例の例である．提案手法は，ユーザ名に紐づいたサーバに対して SSH 接続できる仕組みであるため，データベースではコマンドが実行される場合に備えて，sshr デーモンは root

ユーザ名とサーバのホスト名の紐付けを管理する．また，権限を持たないユーザで実行しておく．この対策は，任意

sshr にてユーザの公開鍵認証を行うために，ユーザ名およのコマンドが実行された場合に sshr サーバに対する操作を

びホスト名に併せて公開鍵をデータベースで管理すること制限することには有効であるが，コマンドが sshr デーモンが有効である．このテーブルの情報を sshr から直接参照すと同じ権限で実行されているため，SSH サーバに対する操ることも可能であるが，Web API を介してデータベース

作は可能となる．

に格納されている情報を参照することも可能である．この次に，SSH サーバにおけるセキュリティ対策について述ようにデータの取得方法を自由に選択できることは，sshr

べる．まず，SSH サーバでは root でリモートログインをが実行するフック関数をプログラマブルに拡張できる仕組

許可しない設定をすることが必要である．例えば，sshd でみを採用していることのメリットの一つである．

は sshd config の PermitRootLogin[17] を使って root での最後に，sshr ロールでは実行可能なフック関数を 3 つ

リモートログインを制限することが可能である．これによ備えているため，それぞれについて想定される処理を解り，SSH サーバに対する操作の権限を制限することがで説する．まず，接続先の決定に用いる FindUpstreamHook

きる．また，sshr サーバが有する秘密鍵が外部に流出したは，HTTP クライアントとして Web API から情報を取場合に備えて，接続元 IP の制限を行うことが有効である．

得する処理を行う．図 5 は，Web API 経由での接続先取

例えば，sshd の authorized keys ファイルでは公開鍵ごと得のためのサンプルコードである．Web API から取得しにオプションを記述することができる．このオプションのた JSON 形式のデータを構造体にデコードし，ホスト名

中の接続元 IP の制限機能 [16] を用いて，sshr サーバの IPを取り出している．次に，ユーザの公開鍵検索に用いる

アドレスからの接続のみを許可することで，秘密鍵が外部

FetchAuthorizedKeysHook は，前述の通りユーザの公開鍵に流出した際の被害を防ぐことができる．

をデータベースで管理するため，FindUpstreamHook と同

4. 提案手法の適用例

様に HTTP クライアントとして Web API から情報を取得する処理を行う．最後に sshr から接続先サーバに対し

図 3 は提案手法を採用したシステム構成の例である．そて認証を行うために利用する秘密鍵を検索する FetchPri-

れぞれのロールについて説明する．Client ロールは，用vateKeyHook は，秘密鍵をデータベースで管理してネッいるツールの制限がないため，OpenSSH に備わっている

トワーク経由で取得することは，流出のリスクを高めるた

ssh(1) コマンド [9] や，Tera Term[18] など GUI ベースのめ，sshr サーバのローカルストレージに保管されている秘SSH クライアントが想定される．Server ロールについても

密鍵を参照する処理を行うことなどが想定される．

用いるツールの制限がないため，代表的な SSH サーバであⓒ 2019 Information Processing Society of Japan

このようなシステムを構築した場合，システムの変更に
92インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019

IOTS2019
2019/12/6

表 1: 実験環境
ClientServersshr

DB

図 6: 実験環境の概要図

対してどのような方法で追従可能であるかを例を挙げて説明する．想定されるシステムの変更として，以下の 3 つを

項目

仕様

CPU

Intel Xeon CPU E5-2650 v3 2.30GHz 1core

Memory1 GBytes

SSH Client

OpenSSH 7.9

CPUIntel Xeon CPU E5-2650 v3 2.30GHz 1core

Memory1 GBytes

SSH Server

OpenSSH 7.9

CPUIntel Xeon CPU E5-2650 v3 2.30GHz 1core

Memory1 GBytes

sshr

sshr v0.1.6

CPUIntel Xeon CPU E5-2650 v3 2.30GHz 1core

Memory1 GBytes

Database

MySQL 5.7.27# クライアント・サーバのみの場合
time ssh <username>@<SSH server IP> uname# 提案手法（sshr）の場合
time ssh <username>@<sshr server IP> uname

図 7: 実行時間測定のためのコマンド例

例に挙げる．

(1) ユーザが用いるサーバを変更したい(2) DB ロールのテーブル構成を変更したい(3) Web API の仕様を変更したい

5. 性能評価
これまで示したように，クライアント・サーバ間の SSH（1）の場合，データベースの情報を更新するだけで良接続に対して sshr が介入することで接続先の決定処理やい．sshr はリクエストのたびにユーザとそのユーザが用い認証処理をプログラマブルに拡張でき，その結果，システ

るサーバの紐付け情報をデータベースから参照するため，

ムの変更に対して，ユーザに変更を要求することなく追従

データベースの情報を更新するだけで，ユーザの接続先を可能となる．一方，セッション確立時に実行されるフック

切り替えることが可能である．（2）の場合，Web API の処関数により，通信のオーバーヘッドが発生する．このオー

理を変更するだけで良い．このようにビジネスロジックを

バーヘッドを測定することで，提案する sshr の導入が SSH

Web API 側に持たせることで，sshr の変更を行う必要がな

接続の処理時間に与える影響を評価し，sshr が想定されう

くなる．
（3）の場合，sshr のフック関数に変更を加える必る実用的な環境に耐えうるか議論する．

要がある．システム管理者が Go 言語で実装したフック関

図 6 に用いた実験環境の概要図を示す．実験は，sshr を

数を Web API の仕様変更に合わせて修正し，再度ビルド

介さないクライアントとサーバの通常の SSH 接続と，提案することで得られたシングルバイナリをデプロイする．デ手法である sshr を介した SSH 接続で比較を行う．表 1 は，

プロイは CI ツールで行うなど，開発プロセスに組み込む

各ロールの性能と用いたソフトウェアのバージョンを示ことで開発者の手を介さず自動で行うことが有効である．

している．各ロールの OS は全て CentOS 7.6.1810 Kernel

また，Server::Starter[19] を用いることで，実行中のプロキ

3.10.0 である．評価においては，公開鍵認証を通してクラシサーバを停止させることなく，デプロイした変更後のバ

イアント・サーバ間のセッションを確立し，uname コマ

イナリを適用することができる．

ンド [20] の実行結果が返ってくるまでの時間を time コマ

プログラマブルに組み込み可能なフック関数を用いて柔ンド [21] で測定する．図 7 に実行時間を測定するための軟にプロキシサーバの動作を制御可能にしたことで，シスコマンド例を示す．それぞれ 100 回測定を行い，平均値をテム管理者がユーザやサーバの情報を自由なデータ形式で算出した．sshr が実行するフック関数は，接続先の決定処管理できることや，そのデータ取得方法を自由に選択でき

理（FindUpstreamHook）およびユーザの公開鍵検索の処る．また，提案手法は想定される様々なシステムの変更に理（FetchAuthorizedKeysHook）のいずれにおいても，別対して，プロキシサーバ自体に変更を要しない，もしくはサーバ上のデータベースから参照するものとする．データ

関数の修正のみで無停止で動作を切り替えられるためシス

ベースには目的のレコード以外を含まないものとする．

テムの変更に対して高い拡張性を有する．

表 2 は，実験結果を示している．クライアント・サーバ
間の SSH 接続に対して sshr を介した場合のオーバヘッドⓒ 2019 Information Processing Society of Japan93

インターネットと運用技術シンポジウム 2019
Internet and Operation Technology Symposium 2019
表 2: 実験結果
環境

実行時間/msec（100 回平均）

クライアント・サーバのみ

448

提案手法（sshr）

470

IOTS2019
2019/12/6

課題を解決するために，sshr にプラグイン機構の導入を検討していく予定である．また，今後は sshr を利用した実用的なシステムの構築を通して，sshr の有用性を評価していきたい．sshr の接続先決定のフック関数を用いて，ユーザが利用可能な複数のサーバ群から，周囲の状況に応じて最は 22 ミリ秒であることが分かった．これは，SSH セッショも適したサーバを選択し，提供することが有効ではないか

ン確立時にユーザが遅延を感じないほど短い時間 [22] であと考える．例えば，機械学習などを用いてサーバの負荷状

る．そのため，複数のユーザが複数のサーバ群の中から特況を精緻に把握し，最も負荷が低いサーバをユーザに提供

定のサーバに対して SSH ログインし，サーバの操作を行するといったことも可能である．

うようなシステム管理を想定した場合，sshr のオーバヘッ
ドは実用に十分に耐えうるほど小さい．一方，SSH 経由で

参考文献

大量のファイルを転送する場合など，サーバに対して大量[1]にセッションを確立する必要があるケースでは，約 20 ミ
リ秒のオーバーヘッドが積み重なって，許容できない遅延時間になる可能性がある．また，sshr サーバはデータベー[2]

スサーバに対して 2 回クエリを実行しているため，クエリの応答時間が sshr を介した場合のオーバヘッドに大きく影響を与える．そのため，参照するテーブルのレコード数が[3]

膨大な場合などは，データベース側にクエリの応答時間を短くする対策を行う必要がある．

[4]

6. まとめ[5]

本論文では，ユーザに用いるクライアントツールの制限[6]

や変更を要求せず，システム管理者が自由に組み込み可能なフック関数を用いてシステム変化に追従できる sshr と

[7]
[8]

いう SSH プロキシサーバを提案した．システム管理者は，

sshr に対してユーザ名から接続先サーバを決定するための[9]フック関数を自由に実装・導入可能である．これにより，[10]

ユーザ名を用いて透過的に目的のサーバに SSH 接続できるため，接続先サーバの IP アドレスやホスト名に変更が[11]あった場合でも，管理者は各ユーザへ変更後の情報を知ら[12]せる必要がなく，ユーザも変更に追従する必要がない．さらに，sshr は，公開鍵認証の際にユーザの公開鍵を検索す[13]

るためのフック関数を組み込めるなど，SSH 特有のユーザ[14]

認証もプログラマブルに拡張できる仕組みを採用している
ため，システム管理者がユーザの公開鍵をデータベースな[15]

どの自由なデータ形式で管理することが可能である．さら

[16]
[17]

に実験から，クライアント・サーバ間に sshr を導入した場
合の SSH セッション確立のオーバーヘッドは 20 ミリ秒程度であり，ユーザが特定のサーバに SSH ログインする際に遅延を感じないほど短い時間 [22] であることを示した．
今後の展望として，まず sshr により汎用的な拡張の仕組みを実装することを考えている．現在の sshr では，システム管理者が Go 言語で実装した関数を組み込み，ビルドすることで，sshr の機能を拡張できる．これにより，拡張
コードも含めてシングルバイナリが作成できるメリットがあるが，Go 言語での実装を強制することや，実装した拡張コードを配布・再利用できないなどの課題がある．このⓒ 2019 Information Processing Society of Japan

[18]
[19]
[20]
[21]
[22]

G. Galante and L. C. E. d. Bona: A Survey on Cloud
Computing Elasticity, 2012 IEEE/ACM Fifth International Conference on Utility and Cloud Computing, pp.
263–270 2012.
T. Lorido-Botran, J. Miguel-Alonso, and J. A. Lozano:
A Review of Auto-scaling Techniques for Elastic Applications in Cloud Environments, Journal of Grid Computing, Vol. 12, No. 4, pp. 559–592 2014.
B. Furht and A. Escalante: Handbook of Cloud Computing, chapter Service Scalability Over the Cloud, Springer
2010.
T. Ylonen: The Secure Shell (SSH) Protocol Architecture, Technical report, RFC 4251 2006.
Google Cloud Platform: gcloud command-line tool
overview, https://cloud.google.com/sdk/gcloud/.
Boshi Lian: SSH Piper, https://github.com/tg123/
sshpiper/.
H. Tsuruta: sshr, https://github.com/tsurubee/sshr.
Google Cloud Platform: gcloud compute ssh, https://cloud.google.com/sdk/gcloud/reference/compute/ssh.
The OpenBSD Foundation: ssh – OpenSSH SSH client,https://man.openbsd.org/ssh.1.
HashiCorp:
Consul, https://github.com/hashicorp/
consul.
Outbrain:Consult, https://github.com/outbrain/
consult.
The OpenBSD Foundation: sshd – OpenSSH SSH daemon, https://man.openbsd.org/sshd.8.
T. Ylonen: The Secure Shell (SSH) Authentication Protocol, Technical report, RFC 4252 2006.
Golang.org: The Go Programming Language, http://golang.org.
golang: crypto/ssh, https://github.com/golang/crypto/
tree/master/ssh.
川本安武：OpenSSH［実践］入門，技術評論社 2014.
The OpenBSD Foundation: sshd config – OpenSSH SSH
daemon configuration file, https://man.openbsd.org/
sshd config.
TeraTerm Project: Tera Term, https://ttssh2.osdn.jp/
index.html.en.
K. Oku: Server::Starter, https://github.com/kazuho/
p5-Server-Starter.
uname command – print Unix system information,
https://www.unixtutorial.org/commands/uname.
time – system resource usage for running a Unix command, https://www.unixtutorial.org/commands/time.
J. Nielsen: Usability Engineering, chapter Response
Times: The 3 Important Limits, Morgan Kaufmann
Publishers 1993.

94