のぴぴのメモ

自分用のLinuxとかの技術メモ

LinuxブロックデバイスとNFSとネットワークの関係性

会社でディスク(ブロックデバイス)とNFSの違いはという話題になったので、Linux kernelの中のブロクデバイスNFS(ファイルシステム)、ネットワークの関係をざっくりしたポンチ絵に落としてみました。(簡素化するため箸折っていたり、そもそも私の理解が曖昧な部分もあるので、マジマジ見ると色々気になるかもしれないです)

f:id:nopipi:20180712022708p:plain
Linuxカーネルのブロックデバイスファイルシステム、ネットワークの位置付け

  • 凡例
    • 青色:共通インターフェース
      • VFS(Virtual File system): ファイルシステムを抽象化している層
      • blk:正式な名称がわからないですが、ブロックデバイスを抽象化している層
      • socket:ソケット通信(networkは、ソケット通信で抽象化されている)
    • 緑色:ファイルシステム
    • 黄色:各プロトコル、またはハードに依存しない上位のデバイス
    • 橙色:ハードウェアデバイス、またはハードウェア

EC2+AmazonLinux2にdockerをセットアップする手順

Amazon Linux2上にdocker環境を作った時のメモです。

手順

インスタンスを立ち上げて、sshログインしてからの手順です。

(1)dockerのインストール

sudo yum -y update
sudo yum -y install docker

(2)dockerサービスの起動

最初の"start"でdockerサービスを開始(dockerデーモン起動)します。次のenableでOS起動時のサービス開始を有効化します。

sudo systemctl start docker.service
sudo systemctl enable docker.service

(3)ec2-userユーザへの権限付与

dockerコマンドでの操作を行うには、dockerグループに所属している必要があります。usermodコマンドで、ec2-userのセカンダリグループにdockerグループを追加します。

sudo usermod -a -G docker ec2-user

ログイン中のセッションには設定が反映されないため、一度ログアウト&ログインをおこない、idコマンドで設定を確認します。

ログアウト&ログイン後に、
$ id
uid=1000(ec2-user) gid=1000(ec2-user) groups=1000(ec2-user),4(adm),10(wheel),190(systemd-journal),994(docker)

(4)確認

dockerコマンドを実行して確認する。実行して、ClientとServerの両方の情報が表示されればOKです。

$ docker version
Client:
 Version:      18.03.1-ce
 API version:  1.37
 Go version:   go1.9.6
 Git commit:   3dfb8343b139d6342acfd9975d7f1068b5b1c3d3
 Built:        Fri Jun 15 23:15:12 2018
 OS/Arch:      linux/amd64
 Experimental: false
 Orchestrator: swarm

Server:
 Engine:
  Version:      18.03.1-ce
  API version:  1.37 (minimum version 1.12)
  Go version:   go1.9.6
  Git commit:   7390fc6/18.03.1-ce
  Built:        Fri Jun 15 23:17:24 2018
  OS/Arch:      linux/amd64
  Experimental: false
  • Server側のエラー
    • "Cannot connect to the Docker daemon...”: dockerデーモンが起動していない可能性。(2)とNW設定を見直し
    • "Got permission denied while trying to connect ":権限がない可能性。(3)を見直し

EC2でnetconsoleを使ってカーネルメッセージを取得する

1.はじめに

EC2インスタンスで、netconsoleを使ってカーネルメッセージを別サーバに飛ばして見る方法のメモです。ncatを利用しnetconsoleサーバを一時的に作る方法と、syslogサーバに飛ばす方法の、2つを説明します。*1

2.前提

  • OS: Amazon Linux 2 LTS Candidate 2*2
  • 同一VPC内にnetconsoleのサーバとクライアントのインスタンスを立ててカーネルメッセージを取得
  • netconsoleのサーバを一時的に立てて取得する方法とsyslogに飛ばす方法の両方を試します。

3.netconsole serverを一時的に立てて取得

デバックや再現テストとかで一時的に使いたいという場合はncatコマンドで簡易的なサーバを立ててカーネルメッセージを取得することができます。以下の説明の構成概要は以下の通りです。

3.1 netconsole serverの準備

(1) security group設定

今回の例では、UDPの6666port で受診しますので、以下のようなInbound許可ルールを持つセキュリティーグループを設定して、netconsole serverインスタンスにアタッチします。

方向 タイプ プロトコル ポート ソース
Inbound custom UDPルール UDP 6666 172.31.37.0/24
(2) ncatのパッケージインストール

ncatコマンドは、nmap-ncatパッケージに含まれていますので、このパッケージをインストールします。

sudo yum -y install nmap-ncat
(3) ifconfigでネット設定を確認

ncatコマンドでlistenするIPアドレスと、そのIPアドレスが割り当てられているMACアドレス(クライアントで利用)を控えます。

$ ifconfig 
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 9001
        inet 172.31.37.224  netmask 255.255.240.0  broadcast 172.31.47.255
        inet6 fe80::410:9aff:feda:c3d2  prefixlen 64  scopeid 0x20<link>
        ether 06:10:9a:da:c3:d2  txqueuelen 1000  (Ethernet)
        RX packets 27150  bytes 35693608 (34.0 MiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 10838  bytes 805351 (786.4 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

今回の場合での必要情報は、以下になります。

(4)サーバ起動(フォアグランド実行)

事前にncatコマンドを実行して、netconsoleのパケットの受診ができるようにします。

ncat -l -u 172.31.37.224 6666 | tee ~/netconsole.log
  • オプションの説明
    • "-l" listenモードにするオプション
    • "-u" UDP通信を指定(デフォルトはTCP通信)

3.2 netconsole client実行

カーネルメッセージを出力するサーバの設定です。netconsoleのカーネルモジュールにオプションをつけてローディングすればOKです。一時的な利用を想定して、netconsoleモジュールを手動でロードする手順にしています。

(1)クライアントのネット設定を確認

利用するIPアドレスと、そのIPアドレスが割り当てられているデバイス名を確認します。

eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 9001
        inet 172.31.37.12  netmask 255.255.240.0  broadcast 172.31.47.255
        inet6 fe80::4ca:cdff:fe50:cc8  prefixlen 64  scopeid 0x20<link>
        ether 06:ca:cd:50:0c:c8  txqueuelen 1000  (Ethernet)
        RX packets 26294  bytes 35430311 (33.7 MiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 2764  bytes 318056 (310.6 KiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

確認する情報は以下になります。

(2)netconsoleのローディング

modprobeコマンドを利用してnetconsoleカーネルモジュールをローディングします。"netconsole="以下はこのカーネルモジュールのオプション設定です。

sudo modprobe netconsole 'netconsole=6666@172.31.37.12/eth0,6666@172.31.37.224/06:10:9a:da:c3:d2'

netconsoleオプションの書式は以下の通りです。*3
netconsole=[src-port]@[src-ip]/[<dev>],[tgt-port]@<tgt-ip>/[tgt-macaddr]

  • クライアント側 : [src-port]@[src-ip]/[<dev>]
    • src-port : クライアント側で利用するポート
    • src-ip: クライアント側のIPアドレス
    • <dev>: 上記src-ipが割り当てられているデバイス
  • サーバ側
    • tgt-port: サーバ側でListenしているポート
    • tgt-ip: ターゲット側でListenしているIPアドレス
    • tgt-macaddr : 上記tgt-ipが割り当てられているデバイスMACアドレス

4.syslog serverでカーネルメッセージを取得する

カーネルメッセージを定常的またはある程度の期間取得し続ける場合は、syslogサーバを立てて取得した方が良いかもしれません。ここではsyslogをUDPの514ポートでlistenする構成の手順を記載します。

4.1 rsyslogサーバの設定

(1)rsyslogにUDPでのListenを有効化

UDPの514番ポートでの受信ができるようにrsyslog.confを設定します。
/etc/rsyslog.conf:

# Provides UDP syslog reception
$ModLoad imudp
$UDPServerRun 514
(2)設定の有効化

rsyslogを再起動し、設定を有効化します。

$ sudo systemctl restart rsyslog
(3)設定確認

UDPの514番ポートでrsyslogがListenしているかnetstatで確認します。"0 0.0.0.0:syslog"(IPv4)、"0 [::]:syslog "(IPv6)が表示されればOKです。

$ netstat -l | grep syslog
udp        0      0 0.0.0.0:syslog          0.0.0.0:*
udp6       0      0 [::]:syslog             [::]:*

4.2 クライアント(netconsole)の設定

クライアント側は恒常的なメッセージ収集のため、サーバ起動時にnetconsoleが設定されるように"/etc/sysconfig/netconsole"に送信先となるsyslogサーバのIPアドレス設定を行います。

(1)送信先のsyslogサーバIPとポート設定

/etc/sysconfig/netconsole

# The IP address of the remote syslog server to send messages to
SYSLOGADDR=172.31.37.224

# The listening port of the remote syslog daemon
SYSLOGPORT=514
(2)netconsoleのサービスの再起動

netconsole.serviceを再起動し設定を反映させます。
またOS再起動後も反映されるようい"systemctl enable・・・"でサービスを有効化します。

$ sudo systemctl restart netconsole.service
$ sudo systemctl enable netconsole.service

*1:ちなみに、なんでこんな調査をしたかというと、m4インスタンスlinuxでのテストで、"sysctl -w kernel.panic=0"(パニック発生時にハングする)を設定してハングさせたいという話があったのですが、panic発動させると設定に従わずとどうしても再起動してOSがあがってくる (panic=0が機能しない)という話があり調べたものです。その話はまた別途書きたいと思います。

*2:未検証ですが、Amazon Linux1でも基本一緒だと思います

*3:カーネルソースコードのDocument/netにあるnetconsole.txtに説明があります