在 CubieTruck 上安裝 GeoIP 取得 IP 位址地理位置

每天看 log,都會看到一堆 IP 位址想要來入侵 CubieTruck 小系統,但都不知道這些 IP 位址到底是位於何方?所以只能安裝 GeoIP 套件來反查其地理位置。首先來安裝套件

# apt-get install geoip-bin

然後就可以輸入 ip 位置反查

# geoiplookup 61.174.51.215
GeoIP Country Edition: CN, China

這樣就可以大約查出他的位置是從中國來的(果然不出所料),但如果要更深入一點知道在中國哪裡,那你得下載更完整的資料庫,

GeoIP下載位置

下載完解壓縮之後你可以得到一個約18MB大小的 GeoLiteCity.dat 的資料庫,先把它放在自己的家目錄裡面(或是放在 /usr/share/GeoIP 目錄也行 )。之後用這個資料庫再來反查

# geoiplookup -f ~/GeoLiteCity.dat 61.174.51.215
GeoIP City Edition, Rev 1: CN, 02, Zhejiang, Huzhou, N/A, 30.870300, 120.093300, 0, 0

你就可以更正確知道這個 61.174.51.215 IP位址是從中國浙江省湖州市來的,經緯度是在 30.870300, 120.093300附近。

如何取消 Ubuntu 的 check-new-release

每天接近中午的時候,我這台 CubieTruck 都會背景自動執行 check-new-release。你一定很好奇,既然是背景,你怎麼會知道呢?實在是太耗效能了,所以才會察覺,二來這台 Server 也不可能利用這種方式去升級,升級是一件大事情,我怎麼可能背景自動去更新呢?所以二話不說,就把這個功能給取消掉了吧!

#apt-get remove ubuntu-release-upgrader-core

來移除套件,但事實上會移除兩個套件的,選擇 Yes 就是了,但是即便如此,還是會有殘留的套件在系統裡面,保險起見,再執行一次

#apt-get autoremove

可以再多移除兩三個無用且相關的套件。

幫 Dovecot 手動加上 Logrotate

安裝了收信套件 dovecot,記錄檔案在 /var/log/dovecot.log,但卻發現這個記錄檔案異常的大,原來 LogRotate 沒有把這個檔案做處理,所以任由它增大下去,所以只好手動幫 dovecot 寫一個 Logrotate 的腳本。

先到 /etc/logrotate.d 目錄底下

# cd /etc/logrotate.d
# touch dovecot
# nano dovecot

然後編輯這個檔案,寫上

/var/log/dovecot*.log {
  weekly
  missingok
  copytruncate
  rotate 7
  compress
  notifempty
  sharedscripts
  postrotate
  if [ -f /var/run/dovecot/master.pid ]; then \
    /etc/init.d/dovecot reload > /dev/null 2>&1 || true ; \
  fi;
  endscript
}

存檔,這樣系統就可以自動每週幫 /var/log/dovecot.log Logrotate 一次了。如果要測試一次,可以手動讓 logrotate 執行一次

# logrotate -vf /etc/logrotate.conf

這樣就可以知道這個腳本是否有正確運行。

/proc/sys/net目錄解說

所有的TCP/IP的參數都位於/proc/sys/net虛擬目錄下(請注意,對/proc/sys/net目錄下內容的修改都是臨時的,任何修改在系統重啟後都會丟失)。

參數(路徑) 描述 默認值 優化值
/proc/sys/net/core/rmem_default 默認的TCP資料接收窗口大小(位元組)。 229376 256960
/proc/sys/net/core/rmem_max 最大的TCP資料接收窗口(位元組)。 131071 513920
/proc/sys/net/core/wmem_default 默認的TCP資料發送窗口大小(位元組)。 229376 256960
/proc/sys/net/core/wmem_max 最大的TCP資料發送窗口(位元組)。 131071 513920
/proc/sys/net/core/netdev_max_backlog 在每個網路接口接收資料包的速率比核心處理這些包的速率快時,允許送到隊列的資料包的最大數目。 1000 2000
/proc/sys/net/core/somaxconn 定義了系統中每一個通訊埠最大的監聽隊列的長度,這是個全局的參數。 128 2048
/proc/sys/net/core/optmem_max 表示每個套接字所允許的最大緩衝區的大小。 20480 81920
/proc/sys/net/ipv4/tcp_mem 確定TCP緩衝區應該如何反映記憶體使用,每個值的單位都是記憶體頁(通常是4KB)。第一個值是記憶體使用的下限;第二個值是記憶體壓力模式開始對緩衝區使用應用壓力的上限;第三個值是記憶體使用的上限。在這個層次上可以將封包丟棄,從而減少對記憶體的使用。對於較大的BDP可以增大這些值(注意,其單位是記憶體頁而不是位元組)。 94011 125351 188022 131072 262144 524288
/proc/sys/net/ipv4/tcp_rmem 為自動調優定義socket使用的記憶體。第一個值是為socket接收緩衝區分配的最少位元組數;第二個值是默認值(該值會被rmem_default覆蓋),緩衝區在系統負載不重的情況下可以增長到這個值;第三個值是接收緩衝區空間的最大位元組數(該值會被rmem_max覆蓋)。 4096 87380 4011232 8760 256960 4088000
/proc/sys/net/ipv4/tcp_wmem 為自動調優定義socket使用的記憶體。第一個值是為socket發送緩衝區分配的最少位元組數;第二個值是默認值(該值會被wmem_default覆蓋),緩衝區在系統負載不重的情況下可以增長到這個值;第三個值是發送緩衝區空間的最大位元組數(該值會被wmem_max覆蓋)。 4096 16384 4011232 8760 256960 4088000
/proc/sys/net/ipv4/tcp_keepalive_time TCP發送keepalive探測消息的間隔時間(秒),用於確認TCP連接是否有效。 7200 1800
/proc/sys/net/ipv4/tcp_keepalive_intvl 探測消息未獲得響應時,重發該消息的間隔時間(秒)。 75 30
/proc/sys/net/ipv4/tcp_keepalive_probes 在認定TCP連接失效之前,最多發送多少個keepalive探測消息。 9 3
/proc/sys/net/ipv4/tcp_sack 啟用有選擇的回應(1表示啟用),通過有選擇地回應亂序接收到的封包來提高性能,讓發送者只發送丟失的封包段,(對於廣域網通信來說)這個選項應該啟用,但是會增加對CPU的佔用。 1 1
/proc/sys/net/ipv4/tcp_fack 啟用轉發回應,可以進行有選擇回應(SACK)從而減少擁塞情況的發生,這個選項也應該啟用。 1 1
/proc/sys/net/ipv4/tcp_timestamps TCP時間戳(會在TCP包頭增加12個位元組),以一種比重發超時更精確的方法(參考RFC 1323)來啟用對RTT 的計算,為實現更好的性能應該啟用這個選項。 1 1
/proc/sys/net/ipv4/tcp_window_scaling 啟用RFC 1323定義的window scaling,要支持超過64KB的TCP窗口,必須啟用該值(1表示啟用),TCP窗口最大至1GB,TCP連接雙方都啟用時才生效。 1 1
/proc/sys/net/ipv4/tcp_syncookies 表示是否打開TCP同步標籤(syncookie),核心必須打開了CONFIG_SYN_COOKIES項進行編譯,同步標籤可以防止一個套接字在有過多試圖連接到達時引起過載。 1 1
/proc/sys/net/ipv4/tcp_tw_reuse 表示是否允許將處於TIME_WAIT狀態的socket(TIME_WAIT的通訊埠)用於新的TCP連接 。 0 1
/proc/sys/net/ipv4/tcp_tw_recycle 能夠更快地回收TIME_WAIT套接字。 0 1
/proc/sys/net/ipv4/tcp_fin_timeout 對於本端斷開的socket連接,TCP保持在FIN_WAIT_2狀態的時間(秒)。對方可能會斷開連接或一直不結束連接或不可預料的行程死亡。 60 30
/proc/sys/net/ipv4/ip_local_port_range 表示TCP/UDP協議允許使用的本地通訊埠號 32768 61000 1024 65000
/proc/sys/net/ipv4/tcp_max_syn_backlog 對於還未獲得對方確認的連接請求,可保存在隊列中的最大數目。如果伺服器經常出現過載,可以嘗試增加這個數字。 2048 2048
/proc/sys/net/ipv4/tcp_low_latency 允許TCP/IP緩衝區適應在高吞吐量情況下低延時的情況,這個選項應該禁用。 0
/proc/sys/net/ipv4/tcp_westwood 啟用發送者端的擁塞控制算法,它可以維護對吞吐量的評估,並試圖對頻寬的整體利用情況進行優化,對於WAN 通信來說應該啟用這個選項。 0
/proc/sys/net/ipv4/tcp_bic 為快速長距離網路啟用Binary Increase Congestion,這樣可以更好地利用以GB速度進行操作的鏈接,對於WAN通信應該啟用這個選項。 1

在 CubieTruck 上如何增加 Apache 和 MySQL 連結數目

這台 CubieTruck 剛安裝完 Ubuntu 之後才發現,即便 Ubuntu 伺服器版本,Apache 預設最大連結數目只有 100 個, 資料庫 MySQL 只有 50 個。換言之,只能支援最多 50 個人同時可以同時查詢 MySQL。老實說,我不知道這台 CubieTruck 的能耐倒底到哪裡,同時50個人查詢會不會造成問題,我只是覺得有點少,所以打算把這個數目增加到 100 個。

Apache 的設定在 /etc/apache2/apache2.conf 檔案裡面

# nano /etc/apache2/apache2.conf

修改這一行

MaxKeepAliveRequests 100

MySQL 的設定在 /etc/mysql/my.cnf 檔案裡面

# nano /etc/mysql/my.cnf

然後找到這一行改為

max_connections = 100

然後重啟兩個服務即可

# service apache2 restart
# service mysql restart

這些數值僅供參考,作為一台伺服器,同時提供 200 人服務應該是沒有什麼問題才是。

如何縮短網路連結關閉時間

我們使用 netstat 指令觀看網路連結時候,常常會看到一堆 TIME_WAIT 的 socket 等待被關閉,而這些 socket 必須等待一段時間後才會被釋放重新被使用,底下是一張 TCP 完整的機制圖(state machine)。

1

一般而言,網路 socket 關閉時比建立時還要複雜很多,原因很多,其中一個是等待 keepalive 再次送訊息來,但是事實上很多時候 socket 是可以被關閉了,所以會有很多 TIME_WAIT 的 socket 殘留在系統中,這一篇我們來說說怎麼修改這些時間,縮短時間,好讓這些 socket 被釋放讓系統可以重新使用。

在 Linux 裡面,這些參數都不是寫死在系統裡面,相反的而是在 /proc/sys/net/ipv4 虛擬檔案目錄裡面,在 /etc/sysctl.conf 裡面可以有其對應的數值,只要修改這個數值,socket 結束的等待時間就可以被改變了。

# nano /etc/sysctl.conf

在檔案後面增加

net.ipv4.netfilter.ip_conntrack_generic_timeout = 120
net.ipv4.tcp_tw_recycle = 1 ; socket 可以重新被使用
net.ipv4.tcp_tw_reuse = 1 ; socket 可以重新被使用
net.ipv4.netfilter.ip_conntrack_tcp_timeout_established = 180
net.ipv4.netfilter.ip_conntrack_tcp_timeout_time_wait = 30
net.ipv4.netfilter.ip_conntrack_tcp_timeout_close_wait = 60
net.ipv4.netfilter.ip_conntrack_tcp_timeout_fin_wait = 120
net.ipv4.tcp_keepalive_intvl = 30 ; 預設值是75,建議在15-30秒內
net.ipv4.tcp_keepalive_probes = 5 ; 預設值是9,建議可以試探5次即可。
net.ipv4.tcp_timestamps = 0 
net.ipv4.tcp_sack = 1 
net.ipv4.tcp_window_scaling = 1

這些數值都是可以修改的,是有關於 socket 的狀態時限的。修改完可以輸入下面命令立刻生效。重新開機後也會自動被載入。

# sysctl -p

注意:每個系統都有其獨特性,所以上面數值僅供參考。一般而言,我們當伺服器的話,當然希望無用的 socket 趕快結束重新可以被使用,相反的如果是當做桌機,這些數值就沒有那麼敏感了。

如何增大 Apache 上傳檔案大小限制

之前架設 ownCloud 時,雖然 ownCloud 已經把上傳檔案大小限制改為 512MB,但是有時候還是上傳不了,後來查了一下原來在 PHP5裡面是有限制的,必須修改一下,設定檔案在 /etc/php5/apache2/php.ini 裡面。

# nano /etc/php5/apache2/php.ini

找到下面兩行,改成你要的檔案大小,

upload_max_filesize = 512M ;預設值是 2M
post_max_size= 512M ;預設值是 2M

然後重新啟動 Apache2 服務即可。

# service apache2 restart

如何取消 CubieTruck IPv6 的功能

雖然去年已經正式啟動了 IPv6 的協議,但是這台 CubieTruck 我估計用到除役前,IPv6也還不會流行,所以索性把它給取消了,取消的方法很簡單,在 /etc/ 目錄下的 sysctl.conf 有一些設定

# nano /etc/sysctl.conf

在這個檔案後面增加

net.ipv6.conf.all.disable_ipv6 = 1
net.ipv6.conf.br0.disable_ipv6 = 1
net.ipv6.conf.eth0.disable_ipv6 = 1
net.ipv6.conf.lo.disable_ipv6 = 1
net.ipv6.conf.wlan0.disable_ipv6 = 1

然後再命令中輸入

# sysctl -p

讓它立刻生效即可!然後在 /etc/modprobe.d 目錄下編輯 blacklist.conf 檔案

# nano /etc/modprobe.d/blacklist.conf

然後在檔案後面增加一行

blacklist ipv6

然後重新開機方能生效。如果要查看是否真的取消 IPv6功能,則可以在命令列輸入

# ip a | grep inet6

如果沒有任何輸出文字,那就代表你真的取消了 IPv6 的功能了。

CubieTruck簡易式阻擋DDoS防禦方式

DDoS是一種討厭的攻擊方式,駭客會在短時間內利用建立新連線方式阻擋他人連線的一種攻擊手法。這種攻擊手法相當難防禦,殊不見各大Server常常碰到此類型跳板式的DDoS攻擊,所以這裡用iptables做一個最簡易的防禦方式。

iptables -N WEB_SRV_DOS
iptables -A INPUT -p tcp -m multiport --dports 80,443 -j WEB_SRV_DOS
iptables -A WEB_SRV_DOS -p tcp --syn -m multiport --dports 80,443 -m recent --rcheck --second 20 --hitcount 100 -j LOG --log-prefix "[Possible DOS Attack]"
iptables -A WEB_SRV_DOS -p tcp --syn -m multiport --dports 80,443 -m recent --rcheck --second 20 --hitcount 100 -j REJECT
iptables -A WEB_SRV_DOS -p tcp --syn -m multiport --dports 80,443 -m recent --set
iptables -A WEB_SRV_DOS -p tcp -m multiport --dports 80,443 -j ACCEPT

上面這段會把80/443(HTTP/HTTPS)Port新連線記錄下,最近20秒內如果想要建立連線超過100次,則會記錄下來並且丟棄封包進而阻擋DoS,因為  hitcount 超過 20,所以請參考這一篇文章來加大 xt_recent 的數值,以方便偵測。

如何限制CubieTruck對某個IP對HTTP Port只能有一定量的連線數目

CubieTruck是一台很小的伺服器,裡面的配備與資源相當陽春,所以經不起很多人同時連線,更遑論要阻擋DDoS了,所以我打算要用 iptables 來限制某個IP對HTTP/HTTPS Port只能有限定數量的連線,超過這個數目就丟棄封包不理會,算是一種最陽春的DDoS的阻擋了吧!

HTTP 80 Port,只要同一個IP超過10個連線就丟棄封包。

iptables -I INPUT -p tcp --dport 80 -m connlimit --connlimit-above 10 -j REJECT

HTTPS 443 Port,只要同一個IP超過10個連線就丟棄封包。

iptables -I INPUT -p tcp --dport 443 -m connlimit --connlimit-above 10 -j REJECT

但如果你的 Apache 服務器掛載很多種引擎,例如 ownCloud私有雲,常用來上傳和下載檔案,那這個數字 10 要自己拿捏好,不要阻擋了自己合法連線而拖慢速度。

另外,還有一點必須考量的是,這個被限制的IP位址可能是某個Proxy Server的IP位址,意味著Proxy Server後面可能有很多的電腦在後面,那麼10個連線就有點太少了。