博文

Wav文件格式解析

参考资料:
https://en.wikipedia.org/wiki/WAV
http://www-mmsp.ece.mcgill.ca/Documents/AudioFormats/WAVE/WAVE.html
http://www.lightlink.com/tjweber/StripWav/Canon.html

Wav是RIFF的一种音频格式,所以
开始的4个字节一定是RIFF这4个char
接下来4个字节是接下来的文件的总长度,加上之前的RIFF占了8字节,所以文件目测总长度应该是这个字节的数值+8,在Wav中所有的数值类的值都是int,字节序为little endian
接下来4个字节是WAVE这个4个Char
接下来4个字节是fmt 这4个Char,是的,是4个,后面有个空格别漏了
        但是,也有例外,如果这个地方出现的不是fmt 这个字符串,那么可能还会有别的信息继续被放在了文件头,但是它一定是如下的格式:
        4个字节的信息头名称,我这里见过的有(JUNK和FAKE)
        4个字节的附加信息头长度(int)
        对应长度的chunk信息
        在这之后一定还会出现fmt 这4个char的组合,即回到正轨
接下来4个字节是整个Wave文件fmt头的长度, 类型是int,可选择的是16、18或者40
接下来4个字节是WAVE文件的编码方式,类型是int,一般来说是1、3、6、7或者65534,1代表PCM,3代表IEEE浮点,6代表8-bit ITU-T G.711 A-law,8代表8-bit ITU-T G.711 μ-law,65534代表在后面的subFormat中定义,除了1之外,后面的都没有见过实例,也无法得知它的实际是个什么样子了,PCM也是用得最多的
接下来2个字节是音频的声道数量,类型是short,1=单声道,2=stereo=立体声,其他多声道的可能也有,但是我暂时没看到实例
接下来4个字节是采样率数值,类型是int,一般都是44100,代表一秒钟记录多少个信息
接下来4个字节是一个能自己算出来的数值了,类型为int,它应该被理解为每秒钟有多少个byte,它的数值等于采样率 * 单位Chunk长度(楼下这个值)
接下来2个字节同样是一个能自己算出来的数值,类型为sho…

CentOS7中自动清理/tmp文件夹的策略

CentOS7中设置了target来负责每日定时清理/tmp文件夹,这个target的名字是:systemd-tmpfiles-clean.timer(在CentOS6中负责干这个的是 /etc/cron.daily/tmpwatch)

    默认的策略是Boot之后15分钟后清空它和每周清理1天未活动的文件

    可以通过这个命令查看每次的执行结果:

   journalctl  -u systemd-tmpfiles-clean

远程记录OpenWRT日志

默认的OpenWRT日志放在/tmp/log下,这样有个问题就是每次重启就会丢失全部的日志,于是公司的路由器每次重启之后连为什么重启都不知道

于是就想办法把日志迁移出来,好在OpenWRT本身就附带了远程日志打印功能,于是直接在内网中开一个rsyslog服务器就可以了

在/etc/rsyslog.d/下新建一个router.conf

内容如下:

module(load="imtcp")
module(load="imudp")

input(type="imudp"
     port="514"
     ruleset="routerSet")

input(type="imtcp"
     port="514"
     ruleset="routerSet")

# rsyslog RuleSets
ruleset(name="routerSet") {
    action(type="omfile"
        File="/var/log/router.log")

}

(这个配置文件可以在 http://www.rsyslog.com/rsyslog-configuration-builder/ 生成)
接下来启动一下rsyslog服务就可以了

systemctl restart rsyslog

在OpenWRT端需要做的工作:
vim /etc/config/system

在config system下增加这么几行

        option log_remote '1'
        option log_ip '192.168.0.13'  # 你的日志i服务器内网IP
        option log_port '514'
        option log_size '0'  # 如果不加这个可能会丢失部分日志

最后那个log_size其实是日志缓冲区的意思,如果使用它默认的,那么它基本上就不向远程提交任何日志了,因为其实生成的日志大小非常小,所以它一…

2016读书总结

2016感觉干了不少的事情,做了不少的尝试,但是感觉下笔写点总结似乎没太多可以写的,于是就总结一下看了些什么书吧

技术类
《Java编程思想(第四版)》
    看第二遍了,不过感觉就算是看第二遍也没看得很深入,这个东西毕竟不能光靠看和背就能融会贯通的
《微服务设计》
    感觉书的内容比较宏观,不涉及细节的可以先去补习一下微服务的基础知识再来看,这书是给设计人员做宏观指导的,并不是一本讲具体实践的书
《Java 8实战》
    非常实用的一本书,相比更多的理论,这本书相当的务实,介绍了许多Java8的新特性与应用场景,其实偶尔也充满了作者对Java8一些未实现功能的怨念,不过还是非常值得看的书
《大型分布式网站架构设计与实践》
    感觉是一本什么都写到了的一本书,从怎么用tailf查日志说到互联网安全方面,感觉无所不包的样子,但是并不是想象中的那么浅薄,只能说更加偏向于实用性多一些,这会让很多人批判作者没深度吧,其实真正来深度的又看不懂选择不看(比如TAOCP),还不如看点实用的能用得上的
《The Swift Programming language》
    官方教程,为了给我的iPhone写个软件而花了三天时间看完了,被其巨复杂的字符串操作所震惊了,也对其optical的实用性所惊叹了
《Java Web高级编程》
    在读中,虽然说是高级编程,感觉却很基础,才刚刚看完JSP的部分,就当是系统回顾吧。
《Java 性能权威指南》
    很新的一本书,针对的Java版本很新,所以也相当的具有实用性,不过更多的是立足于性能测试员的视角
《Python源代码剖析》
    基本上是Python国内最强的一本书了,花了很久终于读完了,不过也只是囫囵吞枣而已,据说要针对Python3.6出个新版本了,值得期待一下

非技术类
今年的杂书基本上都是在Kindle上看的了,除了《猎魔人》这种没有电子版的书之外了
《大国大城》
    很有意思的一本书,这年头谈论中国经济和发展现状的书我真是读得少,不得不说这本书提起了我对看这类书的兴趣
《教父》
    在读中,经典的电影,小说比电影还要经典
《欧洲中世纪史》
    很有意思的一本书,讲述欧洲中世纪宗教与皇权的各种斗争,对一个从来就没有什么宗教概念的我来说确实很新颖
《猎魔人》
    在读中,巫师系列游戏的原…

Java 8的For与Stream的性能差距到底有多大?

Java 8开始引入了Stream流式操作,终于稍微可以像写Python一样写代码了,不用满大街写For语句了,但是因为这篇文章的缘故,导致我对它的性能一直抱有怀疑态度。

但是仔细分析示例中的代码,其实会发现虽然它的示例代码中使用了Stream但是其实那个很慢的结果真正大部分的时间都花在了Integer的自动装、拆箱操作上,真正的Java 8应该是怎么写这个代码呢,还是自己动手试验一下好了。


package org.acgeek; import java.util.ArrayList; import java.util.List; import java.util.Random; import java.util.stream.IntStream; public class ForVsStream { public static void main(String[] args) { List<long> forTest = new ArrayList<>(); List<long> streamTest = new ArrayList<>(); IntStream.range(0, 100).forEach(n -> { int[] a = new Random().ints(5000000, 1, 99999999).toArray(); int e = a.length; int m = Integer.MIN_VALUE; long thisTime = System.nanoTime(); for (int i = 0; i < e; i++) if (a[i] > m) m = a[i]; System.out.println("MAX is " + m); Long testRes = System.nanoTime() - thisTime; forTest.add(testRes);…

Centos7下安装ceph

本来ceph这货的安装简直是傻瓜到一塌糊涂的,但是仰仗于国内伟大的GFW,这安装过程变得极其曲折

以下仅列出最后所使用的手法:


删除Centos 7自带的的repo(都太慢)
rm -rf /etc/yum.repos.d/*.repo使用阿里云的repo
wget -O /etc/yum.repos.d/CentOS-Base.repo http://mirrors.aliyun.com/repo/Centos-7.repo
wget -O /etc/yum.repos.d/epel.repo http://mirrors.aliyun.com/repo/epel-7.repo
注意,epel源一定要打开,因为ceph依赖snappy之类的都在epel里面添加一个用于安装ceph-deploy的源
vim /etc/yum.repos.d/ceph.repo
添加以下内容:
[ceph]
name=Ceph packages for $basearch
baseurl=http://mirrors.aliyun.com/ceph/rpm-jewel/el7/$basearch
enabled=1
gpgcheck=1
type=rpm-md
gpgkey=https://download.ceph.com/keys/release.ascyum makecacheyum install ceph-deploy接下来就按照官方的教程走就好了,就不大可能出现一大堆诡异的什么无法安装的错误了,这安装流程也异常的简单,唯一注意的:当使用ceph-deploy install的时候,务必这样用:ceph-deploy install --repo-url http://mirrors.aliyun.com/ceph/rpm-jewel/el7 ceph-deploy install admin-node node1 node2 node3(官方的方法是:ceph-deploy install admin-node node1 node2 node3)因为这个ceph-deploy在安装过程中会自动帮你修改repo,所以需要用--repo-url来拒绝这个改动,我安装的是jewel发行版,可根据实际需要修改为最新的值得注意的是,从Jewel发行版开始,ceph-osd会拒绝在ext4分区上启动,因…

利用letsencrypt.sh脚本来获取Let'sEncrypt的SSL证书

Let's Encrypt是个好项目,但是问题是它的客户端太臃肿了,而且到目前为止还只支持Apache,相比之下github上letsencrypt.sh只用sh脚本就实习了足够的功能了。还能适配nginx。但是,它也有它的问题——文档太少且支离破碎,根本没有成体系的手册,只能自己看代码摸索。我也是花了老半天的时间才搞定它。

首先先clone下这个项目
git clone git@github.com:lukas2511/letsencrypt.sh.git

默认有两种办法在ACME服务器上获取授权注册,我用的是配合Nginx的HTTP模式
在nginx的对应的domain server字段下添加以下设置

location /.well-known/acme-challenge {
alias /var/www/letsencrypt;
}

这个在http或者https下都没问题,哪怕你https的证书有问题也可以被识别,但是如果是第一次申请,还是老老实实地放http上省得麻烦

指向的地址是需要用的WELLKNOWN变量地址

在仓库下新建一个config.sh文件,内容如下:

#CA="https://acme-staging.api.letsencrypt.org/directory"
CA="https://acme-v01.api.letsencrypt.org/directory"
WELLKNOWN=/var/www/letsencrypt

第一行的CA地址是调试用的,基本上你搞这个一次是很难搞定的,用调试地址可以有效的避免被远端屏蔽
 WELLKNOWN就指向我们刚才nginx中设置的地址

继续新建一个domains.txt,格式类似

aaa.com www.aaa.com b.aaa.com
bbb.com ccc.bbb.com www.bbb.com rr.bbb.com

一行一个域名,每个子域名空一格

 接着运行

 ./letsencrypt.sh -c --config config.sh

你会看到类似这样的输出
+ Signing domains...
+ Generating private key...
+ Generating signing request...
+ Requesting …