SiteGuard Server EditionでIPアドレスベースのアクセス制限を行う
SiteGuard Server Editionを使って、IPアドレスベースのアクセス制限を行えると聞いたので検証してみます。
検証環境
- Vagrant(vbox)
- apache2.4
- SiteGuard Server Edition 5.00-1
インストール
マニュアルに従ってインストールします。
Vagrant.configure("2") do |config| config.vm.box = "bento/centos-7" config.vm.synced_folder "./data", "/vagrant" config.vm.network "private_network", ip: "192.168.56.10" config.vm.provision "shell", inline: <<-SHELL yum -y update yum -y install kernel-headers kernel-devel gcc httpd glibc perl wget unzip openssl make file java-1.8.0-openjdk java-1.8.0-openjdk-devel fontconfig policycoreutils-python mod_ssl timedatectl set-timezone Asia/Tokyo localectl set-locale LANG=ja_JP.utf8 systemctl start httpd cd /vagrant/ && yum localinstall -y ./siteguard-server-edition.rpm cd /opt/jp-secure/siteguardlite/ && echo y | sudo ./setup.sh SHELL end
(dockerで作ってもよかったかも)
カスタムシグネチャの設定
デフォルトで設定してあるカスタムシグネチャのサンプルを参考に設定してみます。
設定ファイル /opt/jp-secure/siteguardlite/conf
はこんな感じ
ON FILTER:60 sample-02 PATH PCRE_CASELESS,COUNTER(10:3) /login\.php 頻度判定で、パスワードアタックを行う接続元をフィルタする
この設定では、 /login.php
へ10秒間に3回以上アクセスするとブロックされるようになります。
ブロックしてみる
ローカルのURL https://192.168.56.10/login.php
に10秒間に3回以上アクセスしてみます。
こんな感じでブロックされました。
ログにはこんな感じで書き込まれます。
1655071402.297996 0 192.168.56.1 TCP_MISS/000 0 GET http://192.168.56.10/login.php - DIRECT/192.168.56.10 - DETECT-STAT:WAF:RULE_SIG/PART_PATH//CUSTOM//sample-02::/login.php:: ACTION:FILTER: JUDGE:FILTER:0: SEARCH-KEY:1655071402.297996.0:
まとめ
今回はローカルでSiteGuard Server EditionのインストールとIPアドレスベースのアクセス制限を行う検証をしました。 カスタムシグネチャを一つ追加するだけで簡単に設定できることがわかりました。
今回はこの辺で
【Docker Desktopの代替】Docker Daemonを自分で立ててみた
みなさんご存知だとは思うのですが、Docker Desktopが有料化されるようですね。
そこで代替できるツールがないか調べてみたところ・・・
など、色々候補が上がりましたが、結局やりたいことってdockerデーモンの代替をどこに立てるか?ということだけなんだよな・・・と思い、今回はシンプルに自分で立ててみました。
ちなみに、Docker Machine
は非推奨、hyperkit + minikube
はマウントしたファイルの書き込み・読み込みが遅く、私が使っているアプリケーションでは実用に耐えられるレベルではありませんでした。
Podman
、lima + docker
はまだ検証してません。
今回実現したいこと
- dockerコマンドでdockerの一通りの操作ができること
- Docker Composeが使えること
- 開発しているWebアプリケーション(Ruby, PHP)が設定変更なしにそのまま動作すること(権限周りなどは除く)
構成
ひとまず手元にあってシュッと使えそうなVagrant(Virtualbox)を使いました。
- ホストOS: MacOS
- ゲストOS: Ubuntu 20.10
- VM: Vagrant(Virtualbox)
設定
- Vagrantfile
Dockerデーモンの乗ったサーバを作る
Vagrant.configure("2") do |config| config.vm.box = "bento/ubuntu-20.10" config.vm.box_version = "202103.19.0" config.vm.network "private_network", ip: "192.168.56.100" config.vm.provision "file", source: "./override.conf", destination: "/tmp/override.conf" repo_names.each do |repo_name| config.vm.synced_folder "#{ENV['HOME']}", "#{ENV['HOME']}",create:"true" end config.vm.provision "shell", inline: <<-SHELL apt update apt -y upgrade apt install -y docker.io mkdir -p /etc/systemd/system/docker.service.d/ cp /tmp/override.conf /etc/systemd/system/docker.service.d/override.conf systemctl daemon-reload systemctl restart docker.service SHELL end
- override.conf
[Service] ExecStart= ExecStart=/usr/bin/dockerd -H tcp://192.168.56.100:2375 --tls=false
- Dockerデーモンへのアクセス
環境変数 DOCKER_HOST
にDockerデーモンの乗っているサーバのIPアドレスを指定すると使えるようになります。
export DOCKER_HOST="tcp://192.168.56.100:2375"
常時使う際は、これを .bash_profile
などに設定しておくと良いかと思います。
設定のポイント
dockerクライアントとTCPで疎通させる
デフォルトではSocketを使った通信となりますが、起動時の設定を変えることでTCPでのやりとりができるようになります。
設定方法は次の項目で
Systemdの設定をオーバーライドした
/etc/systemd/system/docker.service.d/
以下に設定でファイルを置くとsystemdの設定を上書きすることができます。
今回はTCPで起動したかったので、ExecStart=/usr/bin/dockerd -H tcp://192.168.56.100:2375 --tls=false
で上書きしました。
※TLSは今回はfalseにしていますが、必要に応じて設定すると良いかと思います。
ホスト側と同じディレクトリ構成でVMマウントした
Dockerマウントが必要なディレクトリについてはMacとVMとで同じディレクトリ構成でマウントすることで、ホスト側のファイルが直接Dockerマウントされているように見せています。
使ってみた所感
Docker Desktopより速い
これまでDocker Desktopで立ち上げていたWebアプリケーションで試してみましたが、 今までより動きが速くなったことが体感レベルで感じられました。Docker Desktopはマウント周りが遅めなようなので、それが要因な気がします。
※アプリケーションのソースコードをマウントして使っていました。
パーミッションの設定を見直す必要がある
Docker Desktopはマウントしたファイルのパーミッションををいい感じにホスト側に合わせてくれます。 今回試したアプリケーションはDocker Desktop前提で作られており、アプリケーションから書き込みする権限がなかったので、適宜パーミッションの変更や空ボリュームを設定するなどの対応が必要でした。
ただ、NativeなDockerと同じ挙動となるので、個人的にはこれで良いかと。
まとめ
ファイルマウントやパーミッションについてはやや設定が面倒になりましたが、十分実用できそうで個人的には合格レベルでした。 もっと良い方法などあれば教えてください。
参考
MacでDocker Desktopを入れずにDocker CLI+Multipassで代替してみる
GitHub - 1021ky/self_dockermachine: 自前のdocker serverをVagrant+VirtualBoxで構築する
minioを使ってローカルにS3互換の環境を立ち上げてみた
ローカル環境でS3のテストを行うときに例えば以下の問題が考えられます。
- 回線やサービスなどローカル環境以外の影響を受けることになるので障害時にテストすることができなくなる
- 課金されてしまう
- 公開したくないファイルをあげてしまう恐れがある
この問題を解決するために、ローカル環境でS3互換の環境を立ててくれるものはないか探してみたところ、以下のプロダクトが見つかりました。
これをDocker使って環境構築したところ、いくつか工夫すべきポイントがあったのでメモしておきます。
Dockerイメージ
minio公式のイメージを使いました。
Bitnami製もありこちらの方が環境変数で色々やってくれるので便利そうでしたが、
2021年9月時点での新しいバージョンのminioで使われている環境変数 MINIO_ROOT_USER
MINIO_ROOT_PASSWORD
を使用するとクラッシュしてしまうので公式イメージを使いました。
docker compose 設定
version: '3' services: minio: image: minio/minio:latest container_name: "mybucket.minio" entrypoint: sh -c " mkdir -p /data/mybucket; mkdir -p /data/.minio.sys/buckets/mybucket; minio server /data --console-address ':37135'" ports: - 37135:37135 # 管理画面のポート - 9000:9000 # APIのポート environment: - MINIO_ROOT_USER=minio # 管理画面のユーザ、APIのアクセスキー - MINIO_ROOT_PASSWORD=password # 管理画面のパスワード、APIのシークレット - MINIO_DOMAIN=minio volumes: - minio:/data volumes: minio:
- container_name, MINIO_DOMAIN
こちらの設定は、2種類のアドレスモデル path-style
と virtual-hosted style
両方に対応できるようにしています。
container_nameで、mybucket.minio
、サービス名に minio
を設定することで、
dockerのネットワークから http://mybucket.minio:9000
, http://minio:9000
両方でアクセスできるようになります。
- entrypoint
ここではバケットの作成と管理画面のポートを指定しています。
mkdirでディレクトリを作成することで、バケットを作成することができます。
また、管理画面のポートはランダムできまるので、サービスを立ち上げる際に、--console-address ':37135'
を指定することで 37135
で管理画面のポートを設定しています。
- MINIO_ROOT_USER, MINIO_ROOT_PASSWORD
これは管理画面のユーザ、パスワードです。またAPIのアクセスキー、シークレットにも使えます。
- volumes
データを永続化するため、ボリューム設定しています。
使ってみる
- aws s3コマンド
# aws s3 --endpoint-url http://127.0.0.1:9000 ls --profile minio 2021-09-27 00:00:00 mybucket
- s3cmd
こちらはXMLのパースエラーになってしまいました...
今回、コードは載せませんがファイルアップロードが成功したことを確認しました。
使ってみて何かあれば改めてエントリーを立てようと思います。今回はここまで。
ペネトレーションテストの教科書を読んだ
読んだ動機・目的
- セキュリティテストの中でWebアプリケーションの脆弱性診断については、自分でも実施できるレベルになっているが、ペネトレーションテストについては概要レベルでしか理解できていなかったため
- 実際の攻撃では具体的にどのようなツールを使っているのか興味があったため
- セキュリティ対策をする上でも、実際にどのようなツールを使って攻撃されているのかがわかると一歩踏み込んで考えられると思ったから
書籍の目次
以下のURLをご参照ください https://scan.netsecurity.ne.jp/article/2021/08/04/46074.html
なるほどーと思ったツールや記事
evilginx2
フィッシングツール。リバースプロキシとして動作する。 二要素認証のフィッシングを行うことが可能
nuclei
テンプレートを用いたセキュリティスキャナー。既知の脆弱性や設定不備がないかをチェックすることができる。
git-all-secrets
指定した組織、組織の属するユーザのリポジトリ、gistから機密情報を探索するツール
metasploit
サーバサイドテンプレートインジェクション テンプレートエンジンの特定方法
以下に記載されているフローで、どのテンプレートエンジンが使われているのかが特定できるとのこと。
まとめ
ペネトレーションテストではどのような工程を踏んで行われているのか理解できたとともに、実際に使われているツール、またその使い方の概要を知ることができセキュリティ、特に攻撃に関する知見が広がって良かった。 今回は、一気に流し読みしてしまったので、次は各ツールを実際に使って試していこうと思う。
ARPスプーフィングしてNintendo Switchの通信を覗いてみた
Nintendo Switchある対戦ゲームで、ふと、どのような通信が行われているか気になったので、Wiresharkで通信を覗いてみました。
まだ、Wiresharkは使いこなせていないので、今回はパケットが来ていることを確認するところまでやります。
パケットキャプチャするための機材は持ち合わせていなかったので、ARPスプーフィングでノートPCから通信の内容を覗くことにしました。
事前準備
- Nintendo Switch
- ルータ
- PC(OSはUbuntuを使いました)
参考
こちらの記事を参考にさせていただきました https://www.kdryblog.com/arp-spoofing/#toc12
設定・インストール(PC)
ufwでポートを制限していたので、一時的に止めます。
sudo systemctl stop ufw
カーネルパラメータ net.ipv4.ip_forward
を有効にします。
sudo sysctl -w net.ipv4.ip_forward=1
arpspoofコマンドをインストールします。(dsniffパッケージに含まれています)
sudo apt install dsniff
設定・インストール(Nintendo Switch)
IPアドレスが変わらないように固定にします。
ARPスプーフィングを行う
Nintendo SwitchのIPアドレスを 192.168.100.200
とし、ルータのIPアドレスを 192.168.100.254
をします。
Nintendo Switchに向けて
sudo arpspoof -i eth0 -t 192.168.100.200 192.168.100.254
ルータに向けて
sudo arpspoof -i eth0 -t 192.168.100.254 192.168.100.200
実行すると、こんな感じで、継続的にターゲットへ偽の情報を送り続けます。
XX:XX:XX:XX:XX:XX XX:XX:XX:XX:XX:XX 0806 42: arp reply 192.168.100.254 is-at YY:YY:YY:YY:YY:YY XX:XX:XX:XX:XX:XX XX:XX:XX:XX:XX:XX 0806 42: arp reply 192.168.100.254 is-at YY:YY:YY:YY:YY:YY XX:XX:XX:XX:XX:XX XX:XX:XX:XX:XX:XX 0806 42: arp reply 192.168.100.254 is-at YY:YY:YY:YY:YY:YY XX:XX:XX:XX:XX:XX XX:XX:XX:XX:XX:XX 0806 42: arp reply 192.168.100.254 is-at YY:YY:YY:YY:YY:YY XX:XX:XX:XX:XX:XX XX:XX:XX:XX:XX:XX 0806 42: arp reply 192.168.100.254 is-at YY:YY:YY:YY:YY:YY
Wiresharkで確認する
Nintendo Switchで実際にゲームをしてみて、パケットが送信されていることを確認します。
確認したゲームでは、対戦時P2Pでそれぞれ対戦相手のSwitchとUDPで直接やりとりしているようですね。(ルーターのNAT超えをしている模様)
まとめ
このような形で、簡単に通信Nintendo Switch通信を覗くことができました。 実際にやってみて、改めて暗号化された通信の重要性を感じました・・・ではでは。
iPhoneのHTTPリクエスト/レスポンスをキャプチャする
ふと、あるアプリがどのような形でサーバとやりとりしているのかが気になったので、iPhoneのHTTPリクエスト/レスポンスをキャプチャできるように設定してみました。
必要な機器・ソフト
1. Burp Suiteのインストール(PCで操作)
Proxyサーバとして動かすため、以下からBurp Suiteをダウンロード・インストールします。 無償版であるCommunity EditionでOKです。
https://portswigger.net/burp/releases/professional-community-2021-4-2?requestededition=community
2. Burp Suiteの設定(PCで操作)
- Proxy -> Interceptをoff
- Proxy -> Proxy Listeners -> All interfacesを選択
- Portは任意で設定してください。今回は
8082
にします。
- Portは任意で設定してください。今回は
3. PCに外部からアクセスを許可する(PCで操作)
- パーソナルファイアウォール等を開け外部からアクセスできるようにします。
- プライベートIPアドレスを調べる
- ipconfigなどでプライベートIPアドレスを調べ控えておきます。(固定にしちゃっても良いかも)
4. Proxyを設定する(iPhoneで操作)
5. 証明書を設定する(iPhoneで操作)
こちらの手順に沿って行います。
https://portswigger.net/support/installing-burp-suites-ca-certificate-in-an-ios-device
6. 動作確認をしてみる(PC、iPhoneで操作)
適当なサイトにアクセスして、ちゃんとProxyを経由しているか確認します。
Proxy -> HTTP historyにアクセスした履歴が残っていればOKです。
まとめ
こちらの手順でiPhoneのHTTPリクエスト/レスポンスが取得できるようになりました。 リクエストを改ざんして色々試したいときにも役に立つと思います。
今日はこの辺で
参考
【メモ】CronJobについてざっくり概要を見ていった
業務で今VMのCronで動いているあるバッチをKubernetesのCronJobに移せないか検証するため、まずはCronJobについてざっくり概要を学んでいきたいと思います。
構築時に気をつけておきたい設定などをメモしていきます。
Kubernetesドキュメント
- https://kubernetes.io/ja/docs/concepts/workloads/controllers/cron-jobs/
- https://kubernetes.io/docs/tasks/job/automated-tasks-with-cron-jobs/
cronジョブは一度のスケジュール実行につき、 おおよそ 1つのジョブオブジェクトを作成します。ここで おおよそ と言っているのは、ある状況下では2つのジョブが作成される、もしくは1つも作成されない場合があるためです。通常、このようなことが起こらないようになっていますが、完全に防ぐことはできません。したがって、ジョブは 冪等 であるべきです。
まずは、移行対象のジョブが冪等であるか確認した方が良さそう。
Google Kubernetes Engineドキュメント
concurrencyPolicyがForbidに設定されている場合、前回のスケジュールがまだ実行中にCronJobをスケジュールしようとすると、CronJobは作成されません。
同時実行ポリシーは、Allow, Forbid, Replace何が適切なのかは構築前に検証した方がよいですね。
Kubernetes道場 14日目 - Job / CronJobについて
Jobが失敗して再起動処理を無限に続けないように、 backoffLimit というフィールドで制限回数を設けることが出来る。デフォルトは6回となっている。Podが失敗してbackoffする際に指数関数的に遅延を入れてから再度実行される。 Podが失敗してbackoffする際に指数関数的に遅延を入れてから再度実行される。
リトライどうするか設計もしなくては。
メルカリのエンジニアブログ Kubernetes CronJobと仲良くなりたい
failedJobsHistoryLimitは失敗終了したJobを指します。Jobが残るということはPodも残るので、特に失敗したJobからPodを特定しログを見ることで失敗原因を掴むことができます。
failedJobsHistoryLimitはデフォルト1のようですが、失敗原因を調べるのに情報が多い方が良いと思うので、増やしておいても良いかも。
100回スケジュールされる時間が経つと、CronJobはJobを生成できなくなるためCronJobの再作成が必要になります。
これは注意ですね。 動いていることを検知する仕組みがないと、動かないまま放置されてしまいそう。
ざっくり見て行ったので、次回は実際に手元で動かしてきます。