标签 Arch Linux 下的文章

基于 redsocks 实现全局 TCP 流量代理

在 Arch Linux 上使用 Shadowsocks, redsocks, iptables, pcap-dnsproxy 搭建一个舒适的科学上网环境~

对于我来说, 系统安装好之后的第一件事就是翻墙. 我们使用 shadowsocks + redsocks + iptables + pcap-dnsproxy 来实现全局自动代理.

yaourt -S shadowsocks redsocks-git pcap-dnsproxy-git

以上命令同时安装了三个软件. iptables 已经自带不需要安装.

接着到 /etc/shadowsocks 文件夹下创建一个新的配置文件, 配置你的 shadowsocks. 然后

sudo systemctl start shadowsocks@配置文件名
sudo systemctl enable shadowsocks@配置文件名

然后我们配置 redsocks. redsocks 的作用是把全部的 TCP 流量转发到 shadowsocks 上面去, iptables 的话则是拦截这一层, 我们可以在 iptables 配置说如果访问的是中国 ip 则不流向 shadowsocks. 我对 redsocks 了解并不多, 这里只说下我是如何配置的.

redsocks 的配置文件在 /etc/redsocks.conf , 编辑它, 把 redudp 和 dnstc 全部注释掉. redsocks 配置除去注释其实只有这五行:

redsocks {
  local_ip = 127.0.0.1;
  local_port = 31338; # redsocks 运行端口
  ip = 127.0.0.1;
  port = 1080;  # shadowsocks 端口
  type = socks5;
}

根据你的情况需要修改的修改.

接着修改 /etc/iptables/redsocks.rules 文件, 然后把你的 shadowsocks 服务器 IP 地址以及中国 IP 地址加进来, 格式如下:

-A REDSOCKS -d your_ip -j RETURN

国内 IP 列表可以从 apnic 获取得到, 你也可以看我整理的: china.rules

然后, 运行以下命令开启

sudo touch /etc/iptables/iptables.rules # 如果没有这个文件就创建它
sudo systemctl start  redsocks.service iptables.service
sudo systemctl enable  redsocks.service iptables.service
sudo iptables-restore < /etc/iptables/redsocks.rules # 导入规则

然后配置 pcap-dnsproxy. 以上虽然把发往国外的 TCP 流量发到自己的 shadowsocks 服务器上面处理, 这是一种突破 GFW 的方式, 但是这不能避免 DNS 污染的问题, 所以接下来我们配置的 pcap-dnsproxy 来解决.

Arch Linux 安装 pcap-dnsproxy 之后其实我们并不需要做什么, 直接启动就可以用了. 但是要知道的是 pcap-dnsproxy 提供了非常丰富的配置, 你可以自定义, 比如默认 pcap-dnsproxy 是没有局域网解析的, 可以编辑 /etc/pcap-dnsproxy/Config.conf 把 Listen['Operation Mode'] 改为 Server. 如果你需要自定义 Host 的话就修改 /etc/pacp-dnsproxy/Hosts.conf 文件.

直接启动 pcap-dnsproxy

sudo systemctl start pcap-dnsproxy
sudo systemctl enable pcap-dnsproxy

然后编辑 /etc/resolv.conf 文件, 确保首行的 nameserver 为 127.0.0.1. 然后运行

yaourt -S dnsutils # 为了使用 dig 命令
dig www.google.com

如果结果是类似以下形式, 表示 pcap-dnsproxy 已经正常运行.

2017-05-13 15-21-44 的屏幕截图.png

只要看下域名是否被大小写混淆过即可. 如果没有的话可以运行 systemctl status pcap-dnsproxy 或者 journalctl -xe 查看错误日志.

如果还是不行, 可以把 /etc/iptables/redsocks.rules 下所有内容复制粘贴到 /etc/iptables/iptables.rules 下. 然后重启下 iptables.

如果你打开浏览器并且已经可以成功的访问 Google 或者 Y2B, 再访问 ip.cn 这个网站查看当前显示的 IP 是否为你国内的 IP. 如果不是那你的中国 IP 过滤设置还有问题.

- 阅读剩余部分 -

Arch Linux 安装和配置小记

本文章涉及 Arch Linux 的安装, 常用软件和配置. 适用于在 UEFI 上面进行引导安装.

安装

  • 联网

    第一件事当然是联网啦, 如果是无线网络的话使用 wifi-menu.

  • 分区和挂载

    新手安装 Linux 可能会在分区这里感到很疑惑. 其实很简单, 通常我们只考虑为 Linux 分三个或四个区, 三个区的情况分别为 boot 分区, 根分区, home 分区以及交换分区.

    boot 分区是存放启动和引导的; home 分区是存放用户个人文件夹的, 它不是必选的, 但是如果有专门的 home 分区的话以后迁移会很方便; 交换分区主要用途是当虚拟内存用, 如果想要有休眠功能必须要有交换分区(或交换文件), 同样也是可选的; 根分区是必须有的, 以上所有分区都挂载到根分区中.

    Linux 的文件系统格式流行的有两种, 一种是 Ext4, 另一种是 Btrfs. Ext4 是用得最多的. Btrfs 相比 Ext4 支持写时复制以及快照, 子卷等.

    你可以运行 lsblk 命令查看当前的硬盘, 看仔细了别选错了. 假设你要安装的是 /dev/sda 上.

    • 方案一: 使用 Ext4 文件系统

    以下创建三个分区, boot 分区, swap 分区以及 / 分区. 如果需要 home 分区把 / 分区拆成两部分即可.

    parted /dev/sda
    mklabel gpt
    mkpart ESP fat32 1M 513M # Boot 分区
    set 1 boot on
    mkpart primary ext4 513M 8.5G # 交换分区
    mkpart primary ext4 8.5G 100% # 根分区
    quit

    接着运行下格式化以及设置交换分区操作.

    mkfs.fat -F32 /dev/sda1
    mkswap /dev/sda2
    swapon /dev/sda2
    mkfs.ext4 /dev/sda3

    分区就完成了. 接下来我们要进行挂载.

    mount /dev/sda3 /mnt
    mkdir /mnt/{boot,home}
    mount /dev/sda1 /mnt/boot

    这样就完成挂载了.

    • 方案二: 使用 Btrfs 文件系统

    Btrfs 不支持交换分区, 所以就不用设置了, 以下创建两个分区, boot 分区和 / 分区. Btrfs 对 SSD 提供了优化, 如果你没有用 SSD, 那么把后面的挂载参数中的 ssddiscard 都去掉.

    parted /dev/sda
    mklabel gpt
    mkpart ESP fat32 1M 513M # Boot 分区
    set 1 boot on
    mkpart primary btrfs 513M 100% # 根分区
    quit

    接着我们要在根分区创建两个子卷, 具体如下:

    mount -o defaults,ssd,discard,noatime,compress=lzo,space_cache,autodefrag /dev/sda2 /mnt
    cd /mnt
    btrfs subvolume create arch # arch 卷作为 / 分区
    btrfs subvolume create home # home 卷作为 home 分区
    umount /mnt

    接着挂载刚才创建的子卷

    mount -o subvol=arch,defaults,ssd,discard,noatime,compress=lzo,space_cache,autodefrag /dev/sda2 /mnt
    mkdir /mnt/{boot,home}
    mount -o subvol=home,defaults,ssd,discard,noatime,compress=lzo,space_cache,autodefrag /dev/sda2 /mnt/home
    mount /dev/sda1 /mnt/boot

- 阅读剩余部分 -

Linux I/O 调度器

Linux I/O 调度器

Linux I/O 调度器是控制内核提交读写请求给磁盘的方式. Linux 支持三种 I/O 电梯调度算法, 分别为 CFQ, Noop, Deadline 三种. 简单介绍下这三种.

CFQ (Completely Faire Scheduler)

完全公平调度器 (CFQ) 自 kernel2.6.18 后成为了 Linux 默认的 I/O 调度器, 它也是大多数 Linux 发行版的默认调度器. CFQ 调度器的目的是为所有请求 I/O 操作的进程提供一个公平的磁盘 I/O 带宽分配.

CFQ 调度器为每个进程单独创建一个同步 I/O 队列来管理其同步的请求然后为每个队列分配访问磁盘的时间片. 时间片长度和队列允许提交的请求数取决于其进程的 I/O 优先级. 以此保证每个进程的 I/O 资源占用是公平的.

CFQ 算法的特点是按照 I/O 请求的地址进行排序, 而不是按照先来后到的顺序进行响应. 这样减少了不必要的磁盘寻道, 提高了吞吐量. 但也意味着, 先来的 I/O 请求可能不能尽快得到响应, 可能出现饿死现象.

Deadline

Deadline 调度器主要目的是保证请求的启动服务时间. 它在所有的 I/O 请求上加上一个期限来防止请求饿死. 除了本身提供的 I/O 排队队列之外, Deadline 额外分为为读 I/O 和写 I/O 提供了 FIFO 队列. 排序队列按照按照扇区数排序, FIFO 队列按照截止时间排序. FIFO 队列优先级高于排队队列, 读队列优先级高于写队列. 排序队列使用红黑树结构, 而 FIFO 使用链表结构. 读 FIFO 队列的最大等待时间为 500ms, 写FIFO队列的最大等待时间为 5s.

Deadline 算法会在写队列没有发生饥饿的情况下处理读队列, 在进入读队列处理时, 会首先检查 FIFO 读队列查看是否有过期请求, 如果有就优先处理它. 如果前面写队列出现饥饿, 意即 FIFO 写队列有过期请求, 它就会进入写队列处理然后处理 FIFO 中过期的写请求.

Deadline 本质还是基于 CFQ 的, 只不过加了两个 FIFO 队列来避免饿死问题.

Deadline 调度器更适合用于多线程处理环境和数据库环境. 避免了 CFQ 调度器的饿死问题.

Noop

Noop 调度器非常简单, 它提供了一个最简单的 FIFO 队列并对请求进行简单的合并处理. 当确定不需要根据扇区号来对请求排序时, 这个调度器是非常高效的. 比较适合在 SSD 上面应用.

总的来看, Noop 更适合固态硬盘. Deadline 适合需要优先保证读操作且避免饿死的情况如数据库场景. CFQ 比较复杂, 容易出现饿死问题, 但保证了尽可能的公平. 推荐固态硬盘下可以考虑把默认的 CFQ 调度器改为 Noop 调度器或者 Deadline 调度器.

更换 Linux I/O 调度器

可以通过如下命令查看你当前的 I/O 调度器:

cat /sys/block/sda/queue/scheduler

如果想修改的话, 可以先进入 su 然后执行:

echo noop > /sys/block/sda/queue/scheduler

可以把 noop 换位 cfq 或者 deadline.

这个更改会立即生效, 但重启会失效. 如果想设为永久, 在 Arch Linux 上面可以如下操作:

% cat /etc/udev/rules.d/60-scheduler.rules
# Set deadline scheduler for non-rotational disks
ACTION=="add|change", KERNEL=="sd[a-z]", TEST!="queue/rotational", ATTR{queue/scheduler}="deadline"
ACTION=="add|change", KERNEL=="sd[a-z]", ATTR{queue/rotational}=="0", ATTR{queue/scheduler}="deadline"

/etc/udev/rules.d/60-scheduler.rules (没有的话新建) 加上上面两行, 然后再运行该命令:

mkinitcpio -p linux

这样就可以了~

- 阅读剩余部分 -