JVM 缓存对 DNS 的影响

迁移了 DNS 之后,大部分机器表现正常,但是跑 jvm 的机器由于其自身的 DNS cache 问题,仍然在向旧的机器请求。默认情况下,除非重启进程,否则 JVM 会一直的使用原有的 DNS 解析。可以通过在配置文件里面固定或者通过在命令行里面加参数的方式修改。
修改配置文件:
我们安装的 java 版本都在这个下面:
/usr/lib/jvm/java-sun/jre/lib/security

主要是下面这两个:
networkaddress.cache.ttl (default: -1)
networkaddress.cache.negative.ttl (default: 10)

命令行中加启动参数:
sun.net.inetaddr.ttl 这个对应于上面的 networkaddress.cache.ttl
sun.net.inetaddr.negative.ttl 这个对应于上面的 networkaddress.cache.negative.ttl

ref:
http://stackoverflow.com/questions/1256556/any-way-to-make-java-honor-the-dns-caching-timeout-ttl

*NIX 下 CPU 的能耗控制

BIOS 里面的设置开始谈起。可以在 BIOS 里面看到关于 profile 的几个选项中,跟 CPU power management 相关的如下:

1. Performance Per Watt(DAPC): System DBPM(DAPC)
该模式是无法加载任何的 module 的:
# cpuspeed
Error: Could not find any CPUFreq controlled CPU cores to manage
# /etc/init.d/cpuspeed status
cpuspeed is stopped


2. Performance Per Watt(OS): OS DBPM
启动后可以发现,系统自动的加载了 acpi_cpufreq:
# lsmod | grep cpu
cpufreq_ondemand       10544  24
acpi_cpufreq            7891  1
freq_table              4881  2 cpufreq_ondemand,acpi_cpufreq
mperf                   1557  1 acpi_cpufreq

# /etc/init.d/cpuspeed status
Frequency scaling enabled using ondemand governor


3. Performance: Maximum Performance
该模式同样无法加在任何的 module 的


4. Dense Configuration: System DBPM(DAPC)


5. Custom: System DBPM(DAPC), Maximum Performance, OS DBPM

System DBPM(DAPC) 以及 Maximum performance  表示将 CPU 电源管理移交给 BIOS 负责;而 OS DBPM 则表示的是 OS 负责 CPU 的电源管理,主要包括 processor frequency, performance states(P-states: P0, P1…), processor clock throtting(T-states: T0, T1…)

注:
DAPC: Dell Advanced Power controller
DBPM: demand‐based power management

Continue reading

openvpn 证书吊销(revoke)的问题

执行的命令很简单:
# ./revoke-full test_1

revoke 之后,index.txt 对应的条目会由 V 变成 R。另外,会在 keys/ 下面生成 crl.pem 的 CRL。
在使用过程中发现,需要将其 ln 到 /etc/openvpn 下面:
# mv /etc/openvpn/keys/crl.pem /etc/openvpn/.
# cd /etc/openvpn/keys
# ln -s /etc/openvpn/crl.pem .

还需要在配置文件里面指明其位置:
crl-verify crl.pem

否则会出现权限错误等问题:
CRL: cannot read: /etc/openvpn/keys/crl.pem: Permission denied (errno=13)
Exiting

重启即可。


在用 build-key 生成证书的过程如,如果后面的 CN(common name) 跟之前的一样,那么或出现下面的问题:
Certificate is to be certified until Jun 10 06:58:00 2023 GMT (3650 days)
Sign the certificate? [y/n]:y
failed to update database
TXT_DB error number 2

自然不推荐使用同样的 CN,如果一定要使用,可以将 index.txt.attr 文件里面的 unique_subject = yes 改成 unique_subject = no。这样在 index.txt 里面看到的就是两个了:
# tail index.txt -n 2
V 230810065719Z   46  unknown /C=US/ST=CA/L=SanFrancisco/O=Fort-Funston/CN=test_1/emailAddress=[email protected]
V 230810070508Z   47  unknown /C=US/ST=CA/L=SanFrancisco/O=Fort-Funston/CN=test_1/emailAddress=[email protected]

这个时候如果需要 revoke,需要单独的对每一个 test_1 进行 revoke,注意不要把两个 CN 的证书搞混淆了。

最后,如果蛋疼的想 unrevoke 证书,可以参考这里

RH 6.2 关闭 gro

先了解几个术语。
tso(tcp segmentation offload)
利用网卡分割大数据包,减小 CPU 负荷的一种技术。这个需要硬件的支持。
gso(generic segmentation offload)
将 tso 的技术一般化,通过 gso 的技术实现。比 tso 更通用,不需要硬件的分片就可以实现。

lro(large receive offload)
它通过将多个 TCP 数据聚合在一个 skb 结构,在稍后的某个时刻作为一个大数据包交付给上层的网络协议栈,以减少上层协议栈处理 skb 的开销,提高系统接收 TCP 数据包的能力。
gro(generic receive offload)
lro 有不少问题,后续的驱动,都应该使用 GRO 的接口,而不是 LRO。

详细的解释可以看看这个文档,从 TSO 到 GSO,从 LRO 到 GRO。

6.2 的机器如果部署有 LVS,需要关闭 gro,否则其性能会异常的低:
# ethtool  -k em1
Offload parameters for em1:
rx-checksumming: off
tx-checksumming: on
scatter-gather: on
tcp-segmentation-offload: on
udp-fragmentation-offload: off
generic-segmentation-offload: on
generic-receive-offload: on
large-receive-offload: off

# ethtool -K eth0 gro off

6.2 版本之前由于有 bug,无法在 ETHTOOL_OPTS 里面加上多个参数。包括 6.2 在内的以后的版本可以直接在 /etc/sysconfig/network-scripts/ifcfg-em1 里面指定:
ETHTOOL_OPTS="-K ${DEVICE} tso on; -G ${DEVICE} rx 256 tx 128"

而对于 6.2 之前的,方法有二:
1. 将 ethtool 放到 rc.local 里面,但此时如果使用 service network restar 就无法生效了
2. 建立  /sbin/ifup-local 文件,将需要操作的脚本写到这个里面,并将其可执行

munin 以及 zabbix 的聚合(aggregate)

这类需求应该是评估监控系统是否合适的一个重要因素了。
munin 虽然具备,不过实现起来并不是很智能,需要人肉书写。以 mongo 的为例,我们需要聚合分布在不同机器上的 instance 上的 shard 的状态。
在 munin.conf 里面 include 一个名叫 mongo 的目录专门用来做聚合。先定义涉及到的 host:
[dc_shard;jaseywang-db9]
    address 192.168.1.43
    use_node_name yes

[dc_shard;jaseywang-db10]
        address 192.168.1.83
        use_node_name yes

[dc_shard;DailyCounter]
        update no

接下来就是定义需要聚合的 item 了,这个需要每个 host 都有对应的 plugin,比如这里叫 mongo_ops_xxx,xxx 是起 REST 端口:
dc_shard.graph_title DailyCounter
dc_shard.graph_category DailyCounter
dc_shard.graph_total total
dc_shard.total.graph no
dc_shard.graph_order insert update delete getmore
dc_shard.insert.label insert
dc_shard.insert.sum \
  jaseywang-db9:mongo_ops_28701.insert \
  jaseywang-db10:mongo_ops_28711.insert \
  jaseywang-db10:mongo_ops_28716.insert
dc_shard.update.label update
dc_shard.update.sum \
  jaseywang-db9:mongo_ops_28701.update \
  jaseywang-db10:mongo_ops_28711.update \
  jaseywang-db10:mongo_ops_28716.update

有点需要注意的是,需要严格遵循其语法,该是句号的使用句号,使用冒号的用冒号。

zabbix 的相对比较简单,既然是需要聚合的,划分到同一个 hostgroup,接着就是用其原生支持的 "Zabbix aggragate" 这个 Type 就好了。建立好了 item,trigger、graph 之类的就都有了,还是很简单的。顺便说下 Cacti,只要熟悉 rrdtool,问题也很好解决。
 

zabbix 监控 ipvs(lvs) 运行状态

要监控 ipvs 的状态,无外乎从下面两个地方入手:
1. ipvsadm 命令
2. /proc/net/ip_vs* 下面的文件

其中 1 应该也是从 2 获取到的数据,因此比较直接的方式还是直接从 /proc 下面拿到数据。

虽然通过 low level discovery 可以自动的实现 rs 的增删减操作,但是仔细想想没有必要那么复杂,多定义几个 item 就可以替代上面的操作了。

同一时间只有会有一台 dr 进行工作,因此,完全可以在两台 dr 上部署一模一样的监控,最后通过 aggregate 相加起来。

以 ipvsadm 这个命令为例,要拿到当前 InActConn 总和,直接几个 pipe 就可以搞定:
# ipvsadm -L -n | grep Route | tr -s ' ' '\t'  | awk '{print $6}' | awk 'BEGIN{sum=0}{sum+=$1}END{print sum}'

而如果是通过读取文件来做,需要处理下进至问题,如果不愿意在这里处理,可以直接在新建 item 的时候,以 "hex" 做为 Data Type。以 ip_vs_stats 这个文件为例,主要就是 in/out/total 三个大的参数:
# cat /proc/net/ip_vs_stats
   Total Incoming Outgoing         Incoming         Outgoing
   Conns  Packets  Packets            Bytes            Bytes
     D53    11514        0           886EF0                0

 Conns/s   Pkts/s   Pkts/s          Bytes/s          Bytes/s
       2       24        0             11C7                0

下面这个就能拿到当前的 total/in/out 的 delta(conns, pkts, Bytes/s) 值了:
# tail -1 /proc/net/ip_vs_stats | /usr/bin/awk '{print strtonum("0x"$1), strtonum("0x"$2), strtonum("0x"$3), strtonum("0x"$4), strtonum("0x"$5)}'
0 11 0 1445 0

LVS tcp 的状态还是看 proc 下面的文件:
# grep -i es  /proc/net/ip_vs_conn | cut -d' ' -f8  | grep -v ^$ | uniq -c

至于其他的诸如每个 rs 上的连结数,当前的 rs 的个数,rs 的健康状况,dr 有没有被 keepalived failover 等问题,参照上面的思路,应该都很好解决。不过对于第一个,每个 rs 上的连接数,用 low level discovery 来完成会更优雅些,具体的做法可以参考我之前写的一个 mongo instance,只不过是把 port 变成了 ip:port 而已,其他的都没有大的变化。

这个(1, 2) 脚本也可以做类似的事情,不过需要开 SNMP,多一分服务多一份担心,最终还是没采用,而是自己写简单的脚本实现。

上面的 item 都写好了,定义 trigger、graph 是不是就很简单了,综合起来搞套 template 就具有通用性了。

ref:
http://www.austintek.com/LVS/LVS-HOWTO/HOWTO/LVS-HOWTO.monitoring_lvs.html