ネットワーク備忘録

アラフォーエンジニアのネットワーク系の備忘録。twitter:@deigo25374582

続・LVS検証(DSR)

前回の検証からちょっと追加で確認

↓が前回のやつ

klock-3rd.hatenablog.com

 

前回は、Web1、Web2にWRRで分散していたけど、以下の2点が気になった
1.普段はWeb1のみにアクセスさせ、Web1が死んだ時のみWeb2へアクセスさせる。

2.DSR方式でLeast Connectionしたらどういう風になるんだろ?

 

1.普段はWeb1のみにアクセスさせ、Web1が死んだ時のみWeb2へアクセスさせる。

Active/Standby方式をLVSでやる場合をちょっと調べてみた。
Big-IPとかだと、PriorityGroup機能、NetScalerだとBackupServer機能が↑に近い事を実現させられそうだけど、LVSではどうなんだろう・・・と

 

まず、単純にWeb2の重みを0にすればいいんじゃね? という発想
ただし、この場合は、Web1が死ぬとWeb1&Web2が0になるため、クライアントからのアクセスがエラーになる可能性大

 

web_servers.conf

virtual_server_group web_servers {
192.168.10.110 80
}

virtual_server group web_servers {
delay_loop 3
lvs_sched wrr
lvs_method DR
protocol TCP

real_server 192.168.10.103 80 {
weight 1
inhibit_on_failure
HTTP_GET {
url {
path /health_check.html
status_code 200
}
connect_port 80
connect_timeout 3
}
}
real_server 192.168.10.104 80 {
weight 0
inhibit_on_failure
HTTP_GET {
url {
path /health_check.html
status_code 200
}
connect_port 80
connect_timeout 3
}
}
}

 この状態でLVSの状態確認

[root@LVS1 ]# ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port              Forward Weight ActiveConn InActConn
TCP 192.168.10.110:80 wrr
-> 192.168.10.103:80      Route     1         0                  9
-> 192.168.10.104:80      Route     0         0                  0

これは想定どおり。 実際Weightを0にしたところには振り分けられず。
そして、「.103」のサーバのhttpdをstopして確認。

[root@LVS1 keepalived]# ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port     Forward Weight ActiveConn InActConn
TCP 192.168.10.110:80 wrr
-> 192.168.10.103:80      Route   0    0    0
-> 192.168.10.104:80      Route   0    0    0

この状態でWebでアクセスすると・・・・・やはりアクセスできない。
一応、前回と同様にCiscoのshow ip arpで確認したら、ARPテーブルにはVIPがいたから、やはりLVSでDropしてるっぽい。

 

そこで、sorryでやってみる。

web_servers.conf

virtual_server_group web_servers {
192.168.10.110 80
}

virtual_server group web_servers {
delay_loop 3
lvs_sched wrr
lvs_method DR
protocol TCP

sorry_server 192.168.10.104 80

real_server 192.168.10.103 80 {
weight 1
inhibit_on_failure
HTTP_GET {
url {
path /health_check.html
status_code 200
}
connect_port 80
connect_timeout 3
}
}
#real_server 192.168.10.104 80 {
#weight 1
#inhibit_on_failure
#HTTP_GET {
#url {
#path /health_check.html
#status_code 200
#}
#connect_port 80
#connect_timeout 3
#}
#}
}

 

この設定で、LVSの状態を確認

[root@LVS1 keepalived]# ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port      Forward Weight ActiveConn InActConn
TCP 192.168.10.110:80 wrr
-> 192.168.10.103:80       Route  1    0     0

勿論、これだと「.103」にしかパケットは転送されない。
この状態もう一度「.103」のhttpdを落とす。

[root@LVS1 keepalived]# ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port      Forward Weight ActiveConn InActConn
TCP 192.168.10.110:80 wrr
-> 192.168.10.103:80       Route  0    0     0
-> 192.168.10.104:80       Route  1    0     0

Sorry_serverで設定した項目が浮上してきた。
一応これだと、Active/Standbyチックな動きは出来る。
(ただ、Standby側についてはLVSでは監視していないことになる。)

 

2.DSR方式でLeast Connectionしたらどういう風になるんだろ?

F5や、CitrixでのLB構築がほとんどだったので、大体負荷分散方式といえばLeast Connectionだった。 ただし、これらアプライアンスはセッションを管理できたから実現できるけど、LVSのDSR方式だとサーバからの戻りのパケットがLVSを経由しないため、セッション管理は出来ないのではないか?という想定

そんなわけで、「lvs_sched lc」に変えて、別PCからWeb1の実IPアドレス宛てにHTTPアクセス(F5連打)しつつ、HTTPのVIPにアクセスしてみた。

 

[root@LVS1 keepalived]# ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port     Forward Weight ActiveConn InActConn
TCP 192.168.10.110:80 lc
-> 192.168.10.103:80      Route   1    0    19
-> 192.168.10.104:80      Route   1    0    20
[root@LVS1 keepalived]#

 

検証に作ったのは静的ページという点と、HTTPはコネクションを張りっぱなしというわけではないから、検証としては完璧ではないにしろ、VIPへのアクセスが均等に割り振られている事も考えると、DSR方式ではセッション管理は出来ていないような雰囲気。 

 

とりあえず検証おわり

LVS(DSR) 検証

LVS(DSR)の動作検証

LinuxLVSでのロードバランサを構築することになったので、メモ
Keepalivedで冗長構成したLVSで、DSR(Direct Server Return)方式での負荷分散を構築

 

  • 検証構成
    今回は、WebサーバをLVSで負荷分散させる。
    LVS1&2はKeepalivedで冗長構成を実施し、Webサーバ用VIPを保持
    PCからは「http://192.168.10.110/」へアクセス
     ※各サーバのIP(第4オクテットは下記図へ記載)

     f:id:klock_3rd:20160124154002p:plain

  • 通信の流れ
    PCからLVS上のVIP(110)へアクセス
    LVSにて負荷分散先のリアルサーバへ転送
     →LVSから受信したリアルサーバは、LVSを経由することなく直接PCへ返送
  • 各サーバの設定
    LVS1&2
     1.keepalived.conf

    global_defs {
    notification_email {
    }
    router_id LVS_DEVEL
    }

    vrrp_instance VI_1 {
    state BACKUP
    interface eth0
    virtual_router_id 51
    priority 120
    advert_int 1
    authentication {
    auth_type PASS
    auth_pass 1111
    }
    virtual_ipaddress {
    192.168.10.110
    }
    }

    include web_servers.conf

     2.web_servers.conf

    virtual_server_group web_servers {
    192.168.10.110 80
    }

    virtual_server group web_servers {
    delay_loop 3
    lvs_sched wrr
    lvs_method DR
    protocol TCP

    real_server 192.168.10.103 80 {
    weight 1
    inhibit_on_failure
    HTTP_GET {
    url {
    path /health_check.html
    status_code 200
    }
    connect_port 80
    connect_timeout 3
    }
    }
    real_server 192.168.10.104 80 {
    weight 1
    inhibit_on_failure
    HTTP_GET {
    url {
    path /health_check.html
    status_code 200
    }
    connect_port 80
    connect_timeout 3
    }
    }
    }

     3.sysctl.conf を編集してカーネルパラメータ変更

    # Controls IP packet forwarding
    net.ipv4.ip_forward = 1

     Web1&2
    1.loopbackインターフェースを作成し、VIP用のアドレスを割り当てる
    2.sysctl.conf を編集してカーネルパラメータ変更

    net.ipv4.conf.all.arp_ignore = 1
    net.ipv4.conf.all.arp_announce = 2 

 
まぁ、LVSのDSRは割と良くある方式らしいので、他を調べればいいのがあるはず。

個人的にはこっからが本当に気になる点
自分が気になったのはルータのARPテーブルがどうなっているかという点。

1、KeepalivedVRRPパケットは仮想MAC
2、リアルサーバのループバックIPはARPテーブルに載るのか?


そんなわけで、ルータをCiscoで確認
Router#sh ip arp
Protocol Address Age (min) Hardware Addr Type Interface
Internet 192.168.10.110 30 000c.293e.???? ARPA Vlan10
→これは、LVS1のMACアドレス

 

どうやら、KeepalivedVRRPパケットはCiscoVRRPとはちょっと違い、仮想MACを作らない模様。 となると、Keepalivedでの切り替わりはGARPを送出する事で代用しているっぽい。

IPsecトンネル間でのダイナミックルーティング(IPsec VTI)

IPsecトンネル間はユニキャスト通信しか通さないためダイナミックルーティングを使う場合は、GRE over IPsecGREトンネルを必ず使うと思ってたけどそれ以外の方法でも出来ると知ったのでメモ

f:id:klock_3rd:20150418171827p:plain

構成は上記ケースで検証(1812J)

まずは、GRE over IPsecの場合のConfig
#R1&R2のループバックアドレスのセグメントの広告で確認

R1
fa0→10.1.1.1/24
tun0→172.16.1.1/24
loop0→192.168.1.1/24

R2

fa0→10.1.1.2/24
tun0→172.16.1.2/24
loop0→192.168.2.1/24

<R1>
crypto isakmp policy 1
authentication pre-share
group 2
crypto isakmp key cisco address 10.1.1.2
!
!
crypto ipsec transform-set TRANSFORM esp-des esp-sha-hmac
!
crypto map MAP 1 ipsec-isakmp
set peer 10.1.1.2
set transform-set TRANSFORM
match address 100!
interface Loopback0
ip address 192.168.1.1 255.255.255.0
ip ospf network point-to-point
ip ospf 1 area 0
!
interface Tunnel0
ip address 172.16.1.1 255.255.255.0
ip ospf 1 area 0
tunnel source FastEthernet0
tunnel destination 10.1.1.2
crypto map MAP
!
interface FastEthernet0
ip address 10.1.1.1 255.255.255.0
duplex auto
speed auto
crypto map MAP
!
access-list 100 permit gre host 10.1.1.1 host 10.1.1.2

<R2> crypto isakmp policy 1
authentication pre-share
group 2
crypto isakmp key cisco address 10.1.1.1
!
!
crypto ipsec transform-set TRANSFORM esp-des esp-sha-hmac
!
crypto map MAP 1 ipsec-isakmp
set peer 10.1.1.1
set transform-set TRANSFORM
match address 100
!
interface Loopback0
ip address 192.168.2.1 255.255.255.0
ip ospf network point-to-point
ip ospf 1 area 0
!
interface Tunnel0
ip address 172.16.1.2 255.255.255.0
ip ospf 1 area 0
tunnel source FastEthernet0
tunnel destination 10.1.1.1
crypto map MAP
!
interface FastEthernet0
ip address 10.1.1.2 255.255.255.0
duplex auto
speed auto
crypto map MAP
!
access-list 100 permit gre host 10.1.1.2 host 10.1.1.1

 ↑でGRE over IPsecのトンネルを張りOSPFの経路がやり取りされる。
これはWebで調べれば色々見つかる

 

IPsec VTIを使う場合
#R1&R2のループバックアドレスのセグメントで広告を確認

R1
fa0→10.1.1.1/24
tun0→172.16.1.1/24
loop1192.168.1.1/24
R2
fa0→10.1.1.2/24
tun0→172.16.1.2/24
loop1→192.168.2.1/24

<R1>
crypto isakmp policy 1
authentication pre-share
group 2
crypto isakmp key cisco address 10.1.1.2
!
!
crypto ipsec transform-set TRANSFORM esp-des esp-sha-hmac
!
crypto ipsec profile VTI
set transform-set TRANSFORM
!
interface Loopback1
ip address 192.168.1.1 255.255.255.0
ip ospf network point-to-point
ip ospf 1 area 0
!
interface Tunnel0
ip address 172.16.1.1 255.255.255.0
ip ospf 1 area 0
tunnel source FastEthernet0
tunnel mode ipsec ipv4
tunnel destination 10.1.1.2
tunnel protection ipsec profile VTI
!
interface FastEthernet0
ip address 10.1.1.1 255.255.255.0
duplex auto
speed auto
!
ip route 0.0.0.0 0.0.0.0 Tunnel0

<R2>
!
crypto isakmp policy 1
authentication pre-share
group 2
crypto isakmp key cisco address 10.1.1.1
!
!
crypto ipsec transform-set TRANSFORM esp-des esp-sha-hmac
!
crypto ipsec profile VTI
set transform-set TRANSFORM
!
interface Loopback1
ip address 192.168.2.1 255.255.255.0
ip ospf network point-to-point
ip ospf 1 area 0
!
interface Tunnel0
ip address 172.16.1.2 255.255.255.0
ip ospf 1 area 0
tunnel source FastEthernet0
tunnel mode ipsec ipv4
tunnel destination 10.1.1.1
tunnel protection ipsec profile VTI
!
interface FastEthernet0
ip address 10.1.1.2 255.255.255.0
duplex auto
speed auto
!
ip route 0.0.0.0 0.0.0.0 Tunnel0

 確認

R1>show ip ospf neighbor

Neighbor ID  Pri  State   Dead Time   Address   Interface
172.16.1.2   0  FULL/ -   00:00:37   172.16.1.2  Tunnel0
→ちゃんとネイバーを認識できてる。

 

R1>sho ip route ospf

O     192.168.2.0/24 [110/1001] via 172.16.1.2, 01:35:20, Tunnel0

→R2のLoop1のアドレスを受理している。

 

IPsec VTIのConfigが個人的にはとっつきやすいかなぁ・・・
とはいえ、GRE over IPSecも必須だろうけど。

 

Catalyst QoS(cos)

備忘

 

PC1-----(fa0/24)3550(fa0/23)-----PC2

 

上記、構成で3550のPC1&2を収容しているポートのConfigは以下の状態

 

interface FastEthernet0/23
switchport trunk encapsulation dot1q
switchport mode trunk
end

interface FastEthernet0/24
switchport trunk encapsulation dot1q
switchport mode trunk
end


この状態で、PC1から「cos=6」の値のパケットを送出し、PC2でキャプチャしてみた結果は以下の通り
Wireshark抜粋>
110. .... .... .... = Priority: Voice, < 10ms latency and jitter (6)
# cosが「6」のままで、PC2で受信している

 

ここで、QoSを有効化し、再度パケットを送出

Switch(config)#mls qos

Wireshark抜粋>
000. .... .... .... = Priority: Best Effort (default) (0)
cosが「0」に書き換わり、PC2で受信している。


fa0/24のIFにて、cosを信頼する


Switch(config)#int fa0/24
Switch(config-if)#mls qos trust cos
Wireshark抜粋>
110. .... .... .... = Priority: Voice, < 10ms latency and jitter (6)
cosが「6」のままで、PC2で受信している。


fa0/24のIFにて、IP Precedenceを信頼する
Switch(config)#int fa0/24
Switch(config-if)# mls qos trust ip-precedence
Wireshark抜粋>
000. .... .... .... = Priority: Best Effort (default) (0)
cosが「0」に書き換わり、PC2で受信している。
# 因みに、IP PrecedenceをTrust状態で、「mls qos cos 3」等でcosの書き換えを
# 行っても同様の結果

 

今回はこれまで

 

ECMPでの負荷分散(CEF)

CEFの整理

 

f:id:klock_3rd:20150311010155p:plain

上記構成で、ループバックIF&Faの全てでOSPFを有効にすると、対向先のループバックIFへの経路はOSPFによるECMPとなる。
R1→loop0(1.1.1.1/32),loop1(1.1.1.2/32)

R2→loop0(2.2.2.1/32),loop1(2.2.2.2/32)

<R1のルーティングテーブル>

R1#sho ip route ospf
2.0.0.0/32 is subnetted, 2 subnets
O 2.2.2.2 [110/2] via 10.1.2.2, 00:19:14, FastEthernet0/1
     [110/2] via 10.1.1.2, 00:19:14, FastEthernet0/0
O 2.2.2.1 [110/2] via 10.1.2.2, 00:19:14, FastEthernet0/1
     [110/2] via 10.1.1.2, 00:19:14, FastEthernet0/0

R1→R2へPingを打った後、IFのカウンタを確認

R1#ping 2.2.2.2 source 1.1.1.1 repeat 50
R1#sho int stats
FastEthernet0/0
 Switching path Pkts In Chars In Pkts Out Chars Out
 Processor   52    5888  54    308
 Route cache  0     0   0    0
 Total     52    5888  54   308
FastEthernet0/1
 Switching path Pkts In Chars In Pkts Out Chars Out
 Processor   2    188   4   6265
 Route cache  0    0    0    0
 Total     2    188   4   6265

→Fa0/1に偏っているのがわかる。

show ip routeの結果では、等コストロードバランスになっているが送出IFがFa1に偏っているのはCEFの機能によるもの。

R1#show ip cef exact-route 1.1.1.1 2.2.2.2
1.1.1.1 -> 2.2.2.2 : FastEthernet0/0 (next hop 10.1.1.2)

送信元が1.1.1.1、あて先2.2.2.2の場合はFa0/0から送出することがわかる。
実際、Pingコマンド実施時、loop0(1.1.1.1)を指定して実施している。

では、この状態であて先を2.2.2.1に変えてみる。
R1#show ip cef exact-route 1.1.1.1 2.2.2.1
1.1.1.1 -> 2.2.2.1 : FastEthernet0/1 (next hop 10.1.2.2)
→おそらくFa0/1側のカウンタがUpすると想定

R1#ping 2.2.2.1 source 1.1.1.1 repeat 50
R1#sho int stats
FastEthernet0/0
 Switching path Pkts In Chars In Pkts Out Chars Out
 Processor    2    188   4    308
 Route cache   0    0    0    0
 Total      2    188   4    308
FastEthernet0/1
 Switching path Pkts In Chars In Pkts Out Chars Out
 Processor    51   5794   54   6008
 Route cache   0    0    0    0
 Total      51   5794   54   6008
→想定どおり


CEFでの負荷分散は、フロー単位ではなく、パケット単位でも分散可能だけどその場合はパケット追い越しが発生する可能性もあるため、今回は省略


Proxy ARP

たまに、他のベンダが構築したCiscoをみると、Proxy ARPが有効なままの機器があったりするけど、個人的にはあんまりProxy ARPは使いたくない。

 以下で確認

f:id:klock_3rd:20150222184234p:plain

上記構成で検証

PCのIPが 「/24のネットマスク & デフォルトGW未設定」
R1のPC側IF()が「10.1.1.127/25」
R2のloop0を「10.1.1.129/25」
R1&R2の全IFでOSPFを有効

⇒PC側のサブネットマスクの設定誤り


本来であれば、10.1.1.129は上図からもわかるとおり、PCとは別セグメントにいるため、デフォルトGWを設定していないPCからは通信は出来ないはずなんだけど、Proxy ARPの設定が有効な場合はこの場合でも通信できてしまう。

 

<PCのipconfig結果>
接続固有の DNS サフィックス . . . :
IPv4 アドレス . . . . . . . . . . : 10.1.1.1
サブネット マスク . . . . . . . . : 255.255.255.0
デフォルト ゲートウェイ . . . . . :


Ping結果>
10.1.1.129 に ping を送信しています 32 バイトのデータ:
10.1.1.129 からの応答: バイト数 =32 時間 =1ms TTL=254
10.1.1.129 からの応答: バイト数 =32 時間 =1ms TTL=254

<trace結果>
10.1.1.129 へのルートをトレースしています。経由するホップ数は最大 30 です

1 <1 ms <1 ms <1 ms 10.1.1.126
2 1 ms <1 ms <1 ms 10.1.1.129

 

これは、R1のIFでProxy ARPが有効になっていることが原因

R1のPC側IF(Fa0)でProxy ARPを無効にしてから、再度Ping確認

 

interface FastEthernet1
ip address 10.1.1.126 255.255.255.128
no ip proxy-arp
ip ospf 1 area 0
duplex auto
speed auto
end

 

Ping結果>
10.1.1.129 に ping を送信しています 32 バイトのデータ:
10.1.1.1 からの応答: 宛先ホストに到達できません。
10.1.1.1 からの応答: 宛先ホストに到達できません。

 

設計にもよるだろうけど、Proxy ARPは上記のようなケースがあったりするから、あんまり個人的には使いたくない機能・・・・というかデフォルトで無効になってて欲しい。

 

EIGRPのスプリットホライズン

OSPFと比べ、EIGRPは仕事で触る事が少ないのでメモ

EIGRPはsplit horizonに注意

f:id:klock_3rd:20150220232655p:plain

EIGRPはRIP同様ディスタンスベクタプロトコルなのでMBMAネットワークでは、スプリットホライズンに注意

上記構成にてハブ接続セグメントを192.168.1.0/24とし、それぞれ下記IPを振りEIGRPを有効化

R2→vlan1 192.168.1.1/24
R3→fa0 192.168.1.3/24
R4→fa0 192.168.1.4/24

(フレームリレーのネットワーク環境を用意できなかった為、EIGRPのneighborコマンドで代用)

それぞれのEIGRPのConfigは以下のとおり

<R2>
router eigrp 1
network 2.2.2.2 0.0.0.0
network 192.168.1.0
neighbor 192.168.1.3 Vlan1
neighbor 192.168.1.4 Vlan1

 

<R3>
router eigrp 1
network 3.3.3.3 0.0.0.0
network 192.168.1.0
neighbor 192.168.1.2 FastEthernet0

 

<R4>
router eigrp 1
network 4.4.4.4 0.0.0.0
network 192.168.1.0
neighbor 192.168.1.2 FastEthernet0

 

上記の設定投入後、R3、R4でのsho ip routeにて、それぞれR4、R3のloop0のアドレスが広告されているか確認

<R3>
2.0.0.0/32 is subnetted, 1 subnets

D 2.2.2.2 [90/156160] via 192.168.1.2, 00:32:20, FastEthernet0

<R4>
2.0.0.0/32 is subnetted, 1 subnets
D 2.2.2.2 [90/156160] via 192.168.1.2, 00:32:43, FastEthernet0

 

いずれも、R2の経路しか知らない

 

ここでR2にてスプリットホライズンを無効化

 

<R2>

interface Vlan1
no ip split-horizon eigrp 1
end

 

その後、再びR3,R4のshow ip route結果

<R3>
2.0.0.0/32 is subnetted, 1 subnets
D 2.2.2.2 [90/156160] via 192.168.1.2, 00:34:34, FastEthernet0
4.0.0.0/32 is subnetted, 1 subnets
D 4.4.4.4 [90/158720] via 192.168.1.2, 00:00:44, FastEthernet0

 

<R4>
2.0.0.0/32 is subnetted, 1 subnets
D 2.2.2.2 [90/156160] via 192.168.1.2, 00:35:53, FastEthernet0
3.0.0.0/32 is subnetted, 1 subnets
D 3.3.3.3 [90/158720] via 192.168.1.2, 00:01:07, FastEthernet0

 

ちゃんと、R3,R4のloop0のアドレスを受信している

 

EIGRPはOSPFと比べると仕事で触る機会が少ないから、注意だなぁ