在运维工作中很多时候我们需要裁剪Linux系统,减少系统性能的消耗,提升系统服务的性能,以往通过光盘安装的Linux都是比较臃肿的,但出现这样的需求后,我可以对Linux进行重新编译再busybox工具移植即可实现,接下来我们一步一步实现kernel编译+busybox定制Linux系统--实现ssh远程登录+web服务:


实现过程如下:

一.规划子主机的磁盘存储规划

1.添加一个大小为10G的硬盘

2.查询系统硬件信息参数:

# lspci 
00:00.0 Host bridge: Intel Corporation 440BX/ZX/DX - 82443BX/ZX/DX Host bridge (rev 01)
00:01.0 PCI bridge: Intel Corporation 440BX/ZX/DX - 82443BX/ZX/DX AGP bridge (rev 01)
00:07.0 ISA bridge: Intel Corporation 82371AB/EB/MB PIIX4 ISA (rev 08)
00:07.1 IDE interface: Intel Corporation 82371AB/EB/MB PIIX4 IDE (rev 01)
00:07.3 Bridge: Intel Corporation 82371AB/EB/MB PIIX4 ACPI (rev 08)
00:07.7 System peripheral: VMware Virtual Machine Communication Interface (rev 10)
00:0f.0 VGA compatible controller: VMware SVGA II Adapter
00:10.0 SCSI storage controller: LSI Logic / Symbios Logic 53c1030 PCI-X Fusion-MPT Dual Ultra320 SCSI (rev 01)

#在真实生产环境中执行内核编译之前我们必须了解系统硬件参数信息。

3.分区格式化挂载以及安装grub

创建3个分区大小为:50M 512M 256M(swap)

Command (m for help): n
Command action
   e   extended
   p   primary partition (1-4)
p
Partition number (1-4): 1
First cylinder (1-1305, default 1): 
Using default value 1
Last cylinder, +cylinders or +size{K,M,G} (1-1305, default 1305): +50M

Command (m for help): n
Command action
   e   extended
   p   primary partition (1-4)
p
Partition number (1-4): 2
First cylinder (8-1305, default 8): 
Using default value 8
Last cylinder, +cylinders or +size{K,M,G} (8-1305, default 1305): +512M

Command (m for help): n
Command action
   e   extended
   p   primary partition (1-4)
p
Partition number (1-4): 3
First cylinder (74-1305, default 74): 
Using default value 74
Last cylinder, +cylinders or +size{K,M,G} (74-1305, default 1305): +256M

Command (m for help): t
Partition number (1-4): 3
Hex code (type L to list codes): 82
Changed system type of partition 3 to 82 (Linux swap / Solaris)

格式化分区

# mke2fs -t ext4 /dev/sdb1
# mke2fs -t ext4 /dev/sdb2
# mkswap /dev/sdb3

创建挂载目录并挂载

# mkdir -p /mnt/{boot,sysroot}
# mount /dev/sdb1 /mnt/boot/
# mount /dev/sdb2 /mnt/sysroot/
# cd /mnt/sysroot/
# mkdir -p etc/rc.d/init.d bin sbin root home dev proc sys lib lib64 var/log usr/{local,share,lib64} boot etc/sysconfig media mnt tmp

安装grub

# grub-install --root-directory=/mnt/ /dev/sdb
Probing devices to guess BIOS drives. This may take a long time.
Installation finished. No error reported.
This is the contents of the device map /mnt//boot/grub/device.map.
Check if this is correct or not. If any of the lines is incorrect,
fix it and re-run the script `grub-install'.

(fd0)    /dev/fd0
(hd0)    /dev/sda
(hd1)    /dev/sdb

验证bootloader是否安装成功

# cd /mnt/boot/
# ls
grub  lost+found

有以上文件证明安装成功。


二.内核编译环境的配置以及下载内核源码包至系统中编译内核

1.yum安装编译环境开发组包

# yum -y groupinstall "Development tools"

2.防止在编译安装配置.config文件时无法启用tui界面,同时也要安装ncurses,以及ncurses-devel

# yum -y install ncurses-devel

3.解压内核源码至/usr/src目录并且创建软连接为linux,方便后期编译使用

# tar xf linux-3.13.6.tar.xz -C /usr/src/
# cd /usr/src/
# ln -sv linux-3.13.6 linux
`linux' -> `linux-3.13.6'
# cd linux

4.清空内核编译所有配置选择

# make allnoconfig
  HOSTCC  scripts/basic/fixdep
  HOSTCC  scripts/kconfig/conf.o
  SHIPPED scripts/kconfig/zconf.tab.c
  SHIPPED scripts/kconfig/zconf.lex.c
  SHIPPED scripts/kconfig/zconf.hash.c
  HOSTCC  scripts/kconfig/zconf.tab.o
  HOSTLD  scripts/kconfig/conf
scripts/kconfig/conf --allnoconfig Kconfig
#
# configuration written to .config
#

5.编译内核选择配置

# make menuconfig

wKioL1chhJPAU4mlAAZcrTFJlos680.jpg

内核编译选项介绍:

1.第【1】项,此项设置该系统为64位的操作系统(此项必须选择,如果编译32位系统,那么库文件可能会出现不兼容的现象)

2.第【2】项,为通用设置选择并进入进行配置,配置如下:

wKioL1chh0PycVrqAAbh0XnRjtY247.jpg

选项1表示自定义系统内核的名称,(回车后就可以进入设置了,我定义了opensamlee-201109)
选项2表示支持进程间通信。这个也是必须开启的


3.第【3】项,为启动加载模块支持选项。进入并且选择。相应选项。选项如下:

wKioL1chiLTAzB5lAAUY1-ybW4Y571.jpg

意思是支持模块卸载以及强制卸载模块(这里解释一下,为什么要支持这个功能,我们明明都是将所有功能都直接配置到了内核为什么还要启动这个模块功能呢,答案是为了以后可以更好的扩展,假如有新的硬件添加进来呢,那我们岂不是有点难为自己了,又要重新编译内核一遍)


4.【4】项,此项表示开启块设备支持,此项默认打开。其他版本的内核源码默认没有打开,需要自己打开。不然的话,无法支持块存储设备。比如我们接下来要设置的scsi接口的块存储设备。


5.【5】项,此项表示选择cpu的架构以及调整一些cpu的参数。

wKiom1chpJeyJkyxAAdw9zWTd00003.jpg

选项1是开启对称多处理器支持

选项2是cpu的型号品牌选择进入选择如下图,表示cpu是AMD系列的,如果不清楚cpu类型及品牌就可以选择"Generic-x86-64" (操作系统版本为:64所示)

wKiom1chpcbiYXjFAAOC3MByHdo106.jpg

选项3是第一项一旦开启此项就会默认开启,此项便是开启多核心调度


6.第【6】项是总线支持的配置选择并进入

wKiom1chrF-BMWJYAAdm0fU9aG4638.jpg

3项分别代表的意思是,开启pci总线支持,开启pci-e的支持


7,第【7】项,表示默认可执行文件的格式。(这项很重要,不开启那么就ELF二进制程序就不支持)

wKiom1chrf7Azmb6AAUmTNTeeao148.jpg

## 主要选择这三项,如果选择第一项,默认第二项会被选择
## 第一项和第二项表示内核支持ELF二进制可执行程序,
## 第三项,(这个很重要)这个表示支持以#!开头脚本文件。
## 其实就是shell脚本。没有选择这个,你的脚本写出来,内核无法解释。


8.第【8】项,表示网络功能的开启。这项是支持网络功能的必备选项。

wKioL1chsb_C7ekJAAYXDA9J8LA762.jpg

1项,是网络功能的选项,等会进入进行设置,主要是开启tcp/ip的支持。
2项,这个无线网的支持,默认是开启的,但是我们要把它关闭,因为咱们这个是虚拟机,没有无线网卡,开启这个选项,很增加编译负担,既然是最小化编译,那么就应该只买合用的不买没有的。
进入第一项的二级子目录,开始配置tcp/ip的支持。

wKioL1chs6_i7ECcAAbUdD6HQeI419.jpg

选项1:开启基于UNIX域的进程通信。不同主机进程利用tcp/ip 来支持通信,而内部则是利用UNIX domain来实现。

选项2:开启tcp/ip networking网络支持。

选项3:开启路由扩展支持

选项4:是对路由扩展功能的设置,这里我们选择的是,支持策略路由。

选项5:在内核上支持,网络属性的自动配置,旗下有很多的子选项,可以看见,dhcp协议,bootp协议的支持。

wKiom1chtGGxoVbYAAcJUMbJ1tI667.jpg

选项6:开启tcp syn的支持

选项7:关闭ipv6协议支持


9.第【9】项,配置内核支持各种硬件设备。

wKiom1chtkvD8S12AAcb4_8KaAU555.jpg

wKiom1cht4TSmajrAAXkM-1xxCQ108.jpg

wKioL1chuGaij7jEAAaZUkc4qmc000.jpg
选项应用介绍:

选项1:通用设置进入后如下所示:

wKiom1chuMzC27ekAAZVINFMdmw674.jpg

选项1:自动生成设备文件,在内核挂载根文件系统之后,同时挂载设备文件系统到/dev目录下。


选项2:开启支持scsi设备的支持,进入选项后如下:

wKiom1chuq6iBMv5AAb6YwEfxVU561.jpg

选项3:开启对 Fusion MPT设备的支持,这主要是对scsi硬盘一些功能上的支持。

wKiom1chvSDyo6VPAAVns5FOcFQ772.jpg

表示支持主机驱动的spi。以及启用Fusion MPT logging facility"。MPT代表"Message Passing Technology"(消息传递技术)。Fusion驱动是由LSI Logic公司开发。MPT一种进程间使用的特定消息策略。


选项4:主要是网络设备的支持。选择进入,关闭wireless,只选择以太网设备的驱动,选择如下:

wKioL1chwm-jTni-AAeyOUU7Fms241.jpg

选项5:主要是输入设备的设备配置。

wKiom1chwimDTczqAAYY66vApDU649.jpg

选项6主要是usb接口的设置

wKiom1chwwGy8u4JAAdKbNAvs64660.jpg

10.第【10】项,这是开启内核对于文件系统的支持。

wKiom1chw2LAJubLAAawFEb0gyM269.jpg

到此内核编译的配置过程已经好了!

开始编译过程:

# make bzImage    #只编译核心


配置子主机配置文件:

# cp arch/x86/boot/bzImage /mnt/boot/    #把内核复制到boot目录下
# cd /mnt/boot/grub/                      #建立grub配置文件
# vim grub.conf
default=0
timeout=3
title opensamlee-201109
    root (hd0,0)
    kernel /bzImage ro root=/dev/sda2


三,编译busybox,以及提供系统正常运行的一些配置文件,运行子linux系统:

安装配置编译环境,这里需要glibc-static包的支持,还有libmcrpt-devel的支持,以及下载busybox解压源码包

实现过程如下:

# yum -y install libmcrypt-devel glibc-static
# tar xf busybox-1.22.1.tar.bz2 -C /usr/src/
# cd /usr/src/busybox-1.22.1/
# make menuconfig
Busybox Settings  --->
    Build Options  --->
        [*] Build BusyBox as a static binary (no shared libs)
#只要配置这一项就可以了,其他的都不要动。这个表示编译成静态可执行程序,
#简单说就是不需要依赖系统上的#一些库,因为我们是最小化的系统,
#这个系统很多库文件是没有的。如果不设置这个选项,依赖动态库的话,这
#个程序很有可能因为系统上缺少某类库而无法正常运行,甚至是不能运行。
# make && make install
--------------------------------------------------
You will probably need to make your busybox binary
setuid root to ensure all configured applets will
work properly.
-------------------------------------
#以上表示编译成功
# cp -a -d _install/* /mnt/sysroot/
# cd !$
# ls
bin  linuxrc  lost+found  sbin  usr
# rm -f linuxrc 
#因为这是链接文件,在sbin目录下,有个init文件同样也是链接指向busybox的,
#所以这个不需要。我们只需要init就可以做系统启动时所要的文件了。
# vim /mnt/boot/grub/grub.conf              #开始测试一下busybox是否可用
timeout 5
default 0
title T800-kernel.1.version
root (hd0,0)
kernel /bzImage ro root=/dev/sda2 init=/sbin/init
#sync;sync;sync;sync 
#同步文件到磁盘上

挂起主机,启动子主机测试:

wKioL1ch3KijL3k3AACRhTKJGSs656.jpg

子主机启动结果如下:

wKioL1ch3lbRFmw5AANF_oT2w8Q769.jpg

##基本的命令都可以使用,ls,ifconifg,等等常用命令都是可以的了。说明我们的busybox已经可以使用了,但是执行ifconfig的时候出现了一个错误,这是网络设备在内核中没有生成,后面我们会设置通过mdev -s来自动生成设备文件。


接下来我们通过创建系统配置文件:grub.conf,fstab,inittab,rc.d/rc.sysinit,完善子系统功能:

编辑grub.conf的文件去掉init这个选项,再编写了rc.sysinit初始化脚本程序:

[root@mysql etc]# vim /mnt/boot/grub/grub.conf 
default=0
timeout=3
title opensamlee-201109
        root (hd0,0)
        kernel /bzImage ro root=/dev/sda2 quiet    # 去掉init选项利用下面的rc.sysinit来初始化,加上quiet减少初始化信息输出
                 
# vim /mnt/sysroot/etc/fstab                  ###配置开机挂载文件系统
/dev/sda1    /boot    ext4    defaults    0 0
proc        /proc    proc    defaults    0 0
sysfs        /sys    sysfs    defaults    0 0
/dev/sda2    /    ext4    defaults    0 0
/dev/sda3    swap    swap    defaults    0 0

创建子主机系统配置文件及系统初始化脚本:

# vim /mnt/sysroot/etc/rc.d/rc.sysinit
#!/bin/sh
#
echo -e "\tWelcome to \033[34mopensamlee Mini System\033[0m Linux"


echo "mounting sysfs filesystem....."
mount -n -o remount,rw /dev/sda2 /
echo "mounting proc filesystem....."
mount -t proc proc /proc

echo "mounting sysfs filesystem....."
mount -t sysfs sysfs /sys

mdev -s                            # 自动生成设备文件

ifconfig lo 127.0.0.1
ifconfig eth0 172.16.100.8

mount -a

mount
# chmod +x /mnt/sysroot/etc/rc.d/rc.sysinit    #赋予执行权限

创建系统初始化配置inittab文件:

# vim /mnt/sysroot/etc/inittab
::sysinit:/etc/rc.d/rc.sysinit
console::respawn:-/bin/sh
::ctrlaltdel:/bin/reboot
::shutdown:/bin/umount -a -r

创建脚本复制程序命令脚本,用于复制命令至子系统中:

脚本内容如下:

[root@localhost ~]# vim  bincp.sh
#!/bin/bash
#
target=/mnt/sysroot

clearCmd() {
  if which $cmd &> /dev/null; then
        cmdPath=`which --skip-alias $cmd`
  else
        echo "No such command"
        return 5
  fi
}

cmdCopy() {
        cmdDir=`dirname $1`
        [ -d ${target}${cmdDir} ] || mkdir -p ${target}${cmdDir}
        [ -f ${target}${1} ] || cp $1 ${target}${cmdDir}
}

libCopy() {
        for lib in `ldd $1 | grep -o "/[^[:space:]]\{1,\}"`; do
                libDir=`dirname $lib`
                [ -d ${target}${libDir} ] || mkdir -p ${target}${libDir}
                [ -f ${target}${lib} ] || cp $lib ${target}${libDir}
        done
}

while true; do
  read -p "Enter a command: " cmd
  if [ "$cmd" == 'quit' ] ;then
        echo "quit"
        exit 0
  fi
  clearCmd $cmd
  [ $? -eq 5 ] && continue

  cmdCopy $cmdPath
  libCopy $cmdPath
done

# ./bincp.sh             #这是一个脚本程序,这个程序的功能是复制可执行程序同时也会复制依赖
Enter a command: bash    #bash的库
Enter a command: quit    #这里表示移植bash程序。busybox里面是没有bash的但是兼容bash
#默认支持的是ash,所以bash还是要移植的。

检测子主机使用环境是否有错误:

# chroot /mnt/sysroot/
bash-4.1# pwd
/
bash-4.1# ls
bin         dev         home        lib64       media       proc        sbin        tmp         var
boot        etc         lib         lost+found  mnt         root        sys         usr
bash-4.1# ifconfig 
ifconfig: /proc/net/dev: No such file or directory
eth0      Link encap:Ethernet  HWaddr 00:0C:29:23:35:1B  
          inet addr:172.16.100.7  Bcast:172.16.255.255  Mask:255.255.0.0
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1

lo        Link encap:Local Loopback  
          inet addr:127.0.0.1  Mask:255.0.0.0
          UP LOOPBACK RUNNING  MTU:16436  Metric:1

bash-4.1# exit
exit
#以上检测无错误显示,说明是正常的!

启动子主机,如下所示:

wKioL1ch7m2Sg9dPAAMAUKUdDiE887.jpg

看到此景,证明我们已经完成了一个简单Linux系统定制了!嘻嘻



编译安装dropbear提供远程ssh登录方式

1.实现ssh登录的前提,你最起码要支持本地登录吧。所以首先得实现本地登录。配置如下:

#创建用户数据库文件:passwd,密码影子文件:shadow,用户组文件:group

# touch /mnt/sysroot/etc/{passwd,shadow,group}
# vim /mnt/sysroot/etc/passwd
root:x:0:0:root:/root:/bin/bash
opensamlee:x:500:500:samlee test:/home/samlee:/bin/bash

#生成用户密码
# openssl passwd -1 -salt `openssl rand -hex 4`
Password: 
$1$c4a375d4$e53cXyHuwv4E3O.MI07de0
# openssl passwd -1 -salt `openssl rand -hex 4`
Password: 
$1$44b86f2b$8FzshSRcyoI9RtOZsmvL/.

# vim /mnt/sysroot/etc/shadow
root:$1$c4a375d4$e53cXyHuwv4E3O.MI07de0:16690:0:99999:7:::
opensamlee:$1$44b86f2b$8FzshSRcyoI9RtOZsmvL/.:16990:0:99999:7:::
# chmod go= /mnt/sysroot/etc/shadow

# vim /mnt/sysroot/etc/group            
root:x:0:
opensamlee:x:500

# vim /mnt/sysroot/etc/sysconfig/network    #设置主机名
HOSTNAME=www#samlee#com                    #  #号代表.
# vim /mnt/sysroot/etc/inittab             #添加控制台程序
::sysinit:/etc/rc.d/rc.sysinit            
::respawn:/sbin/getty 19200 tty1            #必须调用getty实现login登录。
::respawn:/sbin/getty 19200 tty2
::respawn:/sbin/getty 19200 tty3
::respawn:/sbin/getty 19200 tty4
::respawn:/sbin/getty 19200 tty5
::respawn:/sbin/getty 19200 tty6
::ctrlaltdel:/bin/reboot
::shutdown:/bin/umount -a -r

设置PS1变量,显示开机提示符欢迎信息,在命令行显示主机名:

# vim /mnt/sysroot/etc/profile
export PATH=/bin:/sbin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin
export PS1='[\u@\h \W]\$' 
-------------------------------------------------------------------------------
# vim /mnt/sysroot/etc/issue
OpenSamlee Mini System(201109)
Kernel \r on an \m

Welcome to my Opensamlee Home!!
--------------------------------------------------------------------------------
# vim /mnt/sysroot/etc/rc.d/rc.sysinit
#!/bin/sh
#
echo -e "\tWelcome to \033[34mopensamlee Mini System\033[0m Linux"
echo "mounting sysfs filesystem....."
mount -n -o remount,rw /dev/sda2 /
echo "mounting proc filesystem....."
mount -t proc proc /proc
echo "mounting sysfs filesystem....."
mount -t sysfs sysfs /sys
mdev -s
ifconfig lo 127.0.0.1
ifconfig eth0 172.16.100.8
mount -a
[ -r /etc/sysconfig/network ] && source /etc/sysconfig/network
[ -z "$HOSTNAME" -o "$HOSTNAME" == '(none)' ] && hostname localhost || hostname $HOSTNAME
#倒数一二行表示,开机读取主机名的脚

挂起宿主机,启动子主机,第1个tty1无法登录,我们需要切换其他tty登录:

wKiom1ciuR_D-pO_AADnLMTonjc652.jpg

实现登陆了,但是有个报错,I have no name,刚才我已经在network中设置了主机名,怎么会没有呢?其实是我们登陆使用的是bash,bash是利用nsswitch来进行用户名对应UID实现名称解析,busybox弄人支持shell是ash,我们却换至ash环境:

wKioL1ciu1LjXIm_AAECZYP-fq8484.jpg

接下来我们给bash提供依赖名称解析功能,补充缺少的名称解析库,通过bash的nsswitch实现主机名解析功能:

# cp -d /lib64/libnss* /mnt/sysroot/lib64/
# cp -d /usr/lib64/libnss* /mnt/sysroot/usr/lib64/
# ls /mnt/sysroot/usr/lib64/ /mnt/sysroot/lib64/
/mnt/sysroot/lib64/:
ld-linux-x86-64.so.2   libnss_compat.so.2    libnss_files.so.2      libnss_nisplus-2.12.so  libnss_winbind.so.2
libc.so.6              libnss_dns-2.12.so    libnss_hesiod-2.12.so  libnss_nisplus.so.2     libnss_wins.so.2
libdl.so.2             libnss_dns.so.2       libnss_hesiod.so.2     libnss_nis.so.2         libtinfo.so.5
libnss_compat-2.12.so  libnss_files-2.12.so  libnss_nis-2.12.so     libnss_sss.so.2

/mnt/sysroot/usr/lib64/:
libnss3.so                   libnss_compat.so  libnss_files.so    libnsspem.so       libnss_wins.so
libnssckbi.so                libnssdbm3.chk    libnss_hesiod.so   libnsssysinit.so
libnss_compat_ossl.so.0      libnssdbm3.so     libnss_nisplus.so  libnssutil3.so
libnss_compat_ossl.so.0.0.0  libnss_dns.so     libnss_nis.so      libnss_winbind.so
# cp /etc/nsswitch.conf /mnt/sysroot/etc/

为用户提供家目录:

# mkdir /mnt/sysroot/home/samlee

挂起主机,启动子主机:

wKioL1ciwSmAuA3gAAFpVdaRv5E260.jpg

到此为止说明我们已经成功实现Linux本地登录了。

编译安装dropbear

安装:

# wget http://matt.ucc.asn.au/dropbear/releases/dropbear-2013.58.tar.bz2
# tar xf dropbear-2013.58.tar.bz2
# cd dropbear-2013.58
# ./configure
# make PROGRAMS="dropbear dbclient dropbearkey scp"
# make PROGRAMS="dropbear dbclient dropbearkey scp" install

生成dropbear密钥文件

# mkdir /etc/dropbear
# dropbearkey -t dss -f /etc/dropbear/dropbear_dss_host_key  
#生成私钥信息
# dropbearkey -t rsa -s 2048 -f /etc/dropbear/dropbear_rsa_host_key
#生成公钥信息

测试dropbear是否可以启动

[root@iptablesrouter ~]# dropbear -p 22022 -F -E        #开启程序然后在前台监测运行信息
[31503] Apr 25 15:39:43 Not backgrounding               #标准输出在前台监听22022端口
[31507] Apr 25 15:40:03 Child connection from 172.16.0.1:57811
[31507] Apr 25 15:40:14 Password auth succeeded for 'root' from 172.16.0.1:57811
# ss -tnl | grep 22022                                    #端口监听正常
LISTEN     0      20                       :::22022                   :::*     
LISTEN     0      20                        *:22022                    *:*

移植dropbear至子主机:

# ./bincp.sh 
Enter a command: dropbear
Enter a command: dropbearkey
Enter a command: dhclient
Enter a command: quit
# cp /usr/local/bin/scp /mnt/sysroot/usr/local/bin/
# mkdir /mnt/sysroot/etc/dropbear
# dropbearkey -t dss -f /mnt/sysroot/etc/dropbear/dropbear_dss_host_key
# dropbearkey -t rsa -s 2048 -f /mnt/sysroot/etc/dropbear/dropbear_rsa_host_key 
# mkdir /mnt/sysroot/var/run    #创建dropbear运行时生成的pidfile存放的目录
# vim /mnt/sysroot/etc/shells     #因为dropbear在登录的时候会检查合法shell
/bin/ash
/bin/bash
/bin/hush
/sbin/nologin
/bin/sh

##dropbear是需要nsswitch支持,因为前面我们已经移植nsswitch依赖库及配置文件。
# tty
/dev/pts/5    #远程登录的会在/dev/pts下生成以数字命名的伪终端设备,现在需要实现该功能。
# vim /mnt/sysroot/etc/fstab 
/dev/sda1    /boot    ext4    defaults    0 0
proc        /proc    proc    defaults    0 0
sysfs        /sys    sysfs    defaults    0 0
devpts        /dev/pts    devpts    defaults 0 0
/dev/sda2    /    ext4    defaults    0 0
/dev/sda3    swap    swap    defaults    0 0
#默认情况下/dev/pts不存在的,在系统初始化时mdev -s 后让其生成此目录。
修改系统初始化配置文件--添加mkdir /dev/pts:
# vim /mnt/sysroot/etc/rc.d/rc.sysinit
#!/bin/sh
#
echo -e "\tWelcome to \033[34mopensamlee Mini System\033[0m Linux"
 
 
echo "mounting sysfs filesystem....."
mount -n -o remount,rw /dev/sda2 /
echo "mounting proc filesystem....."
mount -t proc proc /proc
 
echo "mounting sysfs filesystem....."
mount -t sysfs sysfs /sys
 
mdev -s                            
mkdir /dev/pts
 
ifconfig lo 127.0.0.1
ifconfig eth0 172.16.100.8
 
mount -a
[ -r /etc/sysconfig/network ] && source /etc/sysconfig/network
[ -z "$HOSTNAME" -o "$HOSTNAME" == '(none)' ] && hostname localhost || hostname $HOSTNAME
for i in /etc/rc.start/*;do
        $i start
done    #开机初始化基本程序

复制函数库:

# cp /etc/init.d/functions /mnt/sysroot/etc/rc.d/init.d/
# mkdir /mnt/sysroot/etc/init.d/

创建dropber启动脚本程序。

# vim /mnt/sysroot/etc/rc.d/init.d/dropbear
#!/bin/bash
#
# description: dropbear ssh daemon
# chkconfig: 2345 66 33
#
dsskey=/etc/dropbear/dropbear_dss_host_key
rsakey=/etc/dropbear/dropbear_rsa_host_key
lockfile=/var/lock/subsys/dropbear
pidfile=/var/run/dropbear.pid
dropbear=/usr/local/sbin/dropbear
dropbearkey=/usr/local/bin/dropbearkey

[ -r /etc/rc.d/init.d/functions ] && . /etc/rc.d/init.d/functions

[ -r /etc/sysconfig/dropbear ] && . /etc/sysconfig/dropbear

keysize=${keysize:-1024}
port=${port:-22}

gendsskey() {
    [ -d /etc/dropbear ] || mkdir /etc/dropbear
    echo -n "Starting generate the dss key: "
    $dropbearkey -t dss -f $dsskey &> /dev/null
    RETVAL=$?
    if [ $RETVAL -eq 0 ]; then
        success
        echo
        return 0
    else
        failure
        echo
        return 1
    fi    
}

genrsakey() {
    [ -d /etc/dropbear ] || mkdir /etc/dropbear
    echo -n "Starting generate the rsa key: "
    $dropbearkey -t rsa -s $keysize -f $rsakey &> /dev/null
    RETVAL=$?
    if [ $RETVAL -eq 0 ]; then
        success
        echo
        return 0
    else
        failure
        echo
        return 1
    fi    
}

start() {
    [ -e $dsskey ] || gendsskey
    [ -e $rsakey ] || genrsakey

    if [ -e $lockfile ]; then
        echo -n "dropbear daemon is already running: "
        success
        echo 
        exit 0
    fi

    echo -n "Starting dropbear: "
    daemon --pidfile="$pidfile" $dropbear -p $port -d $dsskey -r $rsakey
    RETVAL=$?
    echo 

    if [ $RETVAL -eq 0 ]; then
        touch $lockfile
        return 0
    else
        rm -f $lockfile $pidfile
        return 1
    fi
}

stop() {
    if [ ! -e $lockfile ]; then
        echo -n "dropbear service is stopped: "
        success
        echo
        exit 1
    fi

    echo -n "Stopping dropbear daemon: "
    killproc dropbear
    RETVAL=$?
    echo
    
    if [ $RETVAL -eq 0 ]; then
        rm -f $lockfile $pidfile
        return 0
    else
        return 1
    fi
}

status() {
    if [ -e $lockfile ]; then
        echo "dropbear is running..."
    else
        echo "dropbear is stopped..."
    fi
}

usage() {
    echo "Usage: dropbear {start|stop|restart|status|gendsskey|genrsakey}"
}

case $1 in 
start)
    start ;;
stop)
    stop ;;
restart)
    stop
    start 
    ;;
status)
    status
    ;;
gendsskey)
    gendsskey
    ;;
genrsakey)
    genrsakey
    ;;

*)
    usage
    ;;
esac

赋予脚本执行权限,创建dropbear程序配置文件:

# chmod +x /mnt/sysroot/etc/rc.d/init.d/dropbear

dropbear配置文件:
# vim /mnt/sysroot/etc/sysconfig/dropbear
keysize=2048
port=22

创建链接系统配置文件链接:

# cd /mnt/sysroot/etc/init.d/
# cp /etc/rc.d/init.d/functions /mnt/sysroot/etc/rc.d/init.d/
# mkdir /mnt/sysroot/etc/rc.d/rc3.d
# cd /mnt/sysroot/etc/rc.d/rc3.d
# ln -sv ../init.d/dropbear S70dropbear
# cd /mnt/sysroot/etc/rc.d/
# ln -sv init.d/dropbear dropbear.start
# ln -sv init.d/dropbear dropbear.stop
------------------------------------------------------------------------------------------
# vim /mnt/sysroot/etc/rc.d/rc.sysinit
#!/bin/sh
#
echo -e "\tWelcome to \033[34mopensamlee Mini System\033[0m Linux"
  
echo "mounting sysfs filesystem....."
mount -n -o remount,rw /dev/sda2 /
echo "mounting proc filesystem....."
mount -t proc proc /proc
 
echo "mounting sysfs filesystem....."
mount -t sysfs sysfs /sys
 
mdev -s                            
mkdir /dev/pts
 
ifconfig lo 127.0.0.1
ifconfig eth0 172.16.100.8
 
mount -a
mount -n -o remount,rw  /
[ -r /etc/sysconfig/network ] && source /etc/sysconfig/network
[ -z "$HOSTNAME" -o "$HOSTNAME" == '(none)' ] && hostname localhost || hostname $HOSTNAME

/etc/rc.d/*.start start
------------------------------------------------------------------------------------------
# vim /mnt/sysroot/etc/rc.d/rc.sysdown
#!/bin/sh
#
sync
sleep 2
sync
/etc/rc.d/*.stop stop
/bin/umount -a -r 
poweroff
# chmod +x /mnt/sysroot/etc/rc.d/rc.sysdown
-----------------------------------------------------------------------------------------
# vim /mnt/sysroot/etc/inittab
::sysinit:/etc/rc.d/rc.sysinit            
::respawn:/sbin/getty 19200 tty1            
::respawn:/sbin/getty 19200 tty2
::respawn:/sbin/getty 19200 tty3
::respawn:/sbin/getty 19200 tty4
::respawn:/sbin/getty 19200 tty5
::respawn:/sbin/getty 19200 tty6
::ctrlaltdel:/bin/reboot
::shutdown:/etc/rc.d/rc.sysdown

dropbear开机自动启动设置成功,这样的话我们开机就可以直接使用ssh连接子主机。


实现子主机nginx服务web功能

首先配置好/mnt/sysroot/etc/rc.d/rc.sysinit文件如下:

# vim /mnt/sysroot/etc/rc.d/rc.sysinit 
#!/bin/sh
#
echo -e "\tWelcome to \033[34mopensamlee Mini System\033[0m Linux"
 
 
echo "mounting sysfs filesystem....."
mount -n -o remount,rw /dev/sda2 /
echo "mounting proc filesystem....."
mount -t proc proc /proc
 
echo "mounting sysfs filesystem....."
mount -t sysfs sysfs /sys
 
mdev -s                            
mkdir /dev/pts
 
ifconfig lo 127.0.0.1
ifconfig eth0 172.16.100.8
 
mount -a
mount -n -o remount,rw /
[ -r /etc/sysconfig/network ] && source /etc/sysconfig/network
[ -z "$HOSTNAME" -o "$HOSTNAME" == '(none)' ] && hostname localhost || hostname $HOSTNAME

for i in /etc/rc.d/*.start;do
    $i stop
    sleep 1
 done
for i in /etc/rc.d/*.start;do
    $i start
    sleep 1
 done

编译安装nginx

# yum -y install pcre-devel
# tar xf nginx-1.4.7.tar.gz 
# groupadd -r nginx
# useradd -r -g nginx nginx
# cd nginx-1.4.7
# ./configure --prefix=/usr/local --conf-path=/etc/nginx/nginx.conf --error-log-path=/var/log/nginx/error.log --http-log-path=/var/log/nginx/access.log --user=nginx --group=nginx --without-pcre --without-http_rewrite_module --without-http_geo_module --without-http_uwsgi_module --without-http_fastcgi_module --without-http_scgi_module --without-http_memcached_module
# make && make install
# /usr/local/sbin/nginx        #启动nginx程序
# ss -tnl | grep 80            #查看监听端口

移植nginx至子主机

# cp -r /etc/nginx/ /mnt/sysroot/etc/
# cp -r /usr/local/nginx/ /mn
# sync
# grep "^nginx" /etc/passwd >> /mnt/sysroot/etc/passwd 
# grep "^nginx" /etc/group >> /mnt/sysroot/etc/group 
# grep "^nginx" /etc/shadow >> /mnt/sysroot/etc/shadow 
# mkdir /mnt/sysroot/usr/local/html
# mkdir /mnt/sysroot/var/log/nginx/
# mkdir /mnt/sysroot/usr/local/logs/
# mkdir /mnt/sysroot/var/lock/subsys/
# vim /mnt/sysroot/usr/local/html/index.html
<h1>Welcome to my opensamlee home!!</h1>
##建立nginx自启动脚本
# vim /mnt/sysroot/etc/rc.d/init.d/nginx
#!/bin/sh
#
# nginx - this script starts and stops the nginx daemon
#
# chkconfig:   - 85 15 
# description:  Nginx is an HTTP(S) server, HTTP(S) reverse \
#               proxy and IMAP/POP3 proxy server
# processname: nginx
# config:      /etc/nginx/nginx.conf
# config:      /etc/sysconfig/nginx
# pidfile:     /var/run/nginx.pid
 
# Source function library.
. /etc/rc.d/init.d/functions
 
# Source networking configuration.
. /etc/sysconfig/network
 
# Check that networking is up.
[ "$NETWORKING" = "no" ] && exit 0
 
nginx="/usr/local/sbin/nginx"
prog=$(basename $nginx)
 
NGINX_CONF_FILE="/etc/nginx/nginx.conf"
 
[ -f /etc/sysconfig/nginx ] && . /etc/sysconfig/nginx
 
lockfile=/var/lock/subsys/nginx
 
make_dirs() {
   # make required directories
   user=`nginx -V 2>&1 | grep "configure arguments:" | sed 's/[^*]*--user=\([^ ]*\).*/\1/g' -`
   options=`$nginx -V 2>&1 | grep 'configure arguments:'`
   for opt in $options; do
       if [ `echo $opt | grep '.*-temp-path'` ]; then
           value=`echo $opt | cut -d "=" -f 2`
           if [ ! -d "$value" ]; then
               # echo "creating" $value
               mkdir -p $value && chown -R $user $value
           fi
       fi
   done
}
 
start() {
    [ -x $nginx ] || exit 5
    [ -f $NGINX_CONF_FILE ] || exit 6
    make_dirs
    echo -n $"Starting $prog: "
    daemon $nginx -c $NGINX_CONF_FILE
    retval=$?
    echo
    [ $retval -eq 0 ] && touch $lockfile
    return $retval
}
 
stop() {
    echo -n $"Stopping $prog: "
    killproc $prog -QUIT
    retval=$?
    echo
    [ $retval -eq 0 ] && rm -f $lockfile
    return $retval
}
 
restart() {
    configtest || return $?
    stop
    sleep 1
    start
}
 
reload() {
    configtest || return $?
    echo -n $"Reloading $prog: "
    killproc $nginx -HUP
    RETVAL=$?
    echo
}
 
force_reload() {
    restart
}
 
configtest() {
  $nginx -t -c $NGINX_CONF_FILE
}
 
rh_status() {
    status $prog
}
 
rh_status_q() {
    rh_status >/dev/null 2>&1
}
 
case "$1" in
    start)
        rh_status_q && exit 0
        $1
        ;;
    stop)
        rh_status_q || exit 0
        $1
        ;;
    restart|configtest)
        $1
        ;;
    reload)
        rh_status_q || exit 7
        $1
        ;;
    force-reload)
        force_reload
        ;;
    status)
        rh_status
        ;;
    condrestart|try-restart)
        rh_status_q || exit 0
            ;;
    *)
        echo $"Usage: $0 {start|stop|status|restart|condrestart|try-restart|reload|force-reload|configtest}"
        exit 2
esac

# chmod +x /mnt/sysroot/etc/rc.d/init.d/nginx        #给脚本赋予执行权限
# cd /mnt/sysroot/etc/rc.d/
# ln -sv init.d/nginx nginx.start
# ln -sv init.d/nginx nginx.stop
# cd /mnt/sysroot/etc/rc.d/
# ln -sv init.d/nginx nginx.start
# ln -sv init.d/nginx nginx.stop
# ./bincp.sh 
Enter a command: nginx
Enter a command: consoletype

以上步骤完成后,我们挂起主机,开启子主机瞧瞧:

wKioL1ckK_2DERnNAAIxC0g0F30221.jpg

我们可以看到dropbear和nginx服务都已经启动了

wKioL1ckLGOCPgeIAAGV9kNGdo8378.jpg

测试如下:

wKiom1ckLGKgX--IAADcyC2oYpQ103.jpg

wKioL1ckLTuwzCoZAAIdb-cZR3M488.jpg

以上是使用kernel编译+busybox定制Linux系统--实现ssh远程登录+web服务的迷你主机所有内容

还可以移植至树莓派中使用的啊!嘻嘻