linux最小系统的制作(嵌入式第一节课)

2019-07-12 23:40发布

class="markdown_views prism-atom-one-light">

准备工作

硬件工具:
电脑(安装了linux虚拟机(UBuntu或者CentOS),需要提供一个平台环境)
一块板子(我这里是使用讯为提供的Cortex-A9 4412精英板) 软件工具:
1.busybox
2.linux_tools.tgz
3.arm-linux-gcc编译器 其中busybox可以到官网下载,linux_tools.tgz 可到我 {MOD}下载
{MOD}链接:http://pan.baidu.com/s/1c2IU8Nm
arm-linux-gcc编译器的安装和配置可以按照我的另一篇文章来配置
文章链接:http://blog.csdn.net/coolwriter/article/details/77775847

busybox介绍

Busybox工具(https://busybox.NET/):目前的最新版本是:busybox-1.27.2.tar.bz2(2017年8月17日)
Busybox工具就是一个集成了100多个Linxu常用命令和工具的软件,可以称为Linux里面的瑞士军刀吧,它是开源的,同时在不断更新,我们接下来就是用它来搭建我们的最小Linux系统。
网址:https://busybox.net/ BusyBox combines tiny versions of many common UNIX utilities into a single small executable. It provides replacements for most of the utilities you usually find in GNU fileutils, shellutils, etc. The utilities in BusyBox generally have fewer options than their full-featured GNU cousins; however, the options that are included provide the expected functionality and behave very much like their GNU counterparts. BusyBox provides a fairly complete environment for any small or embedded system. 百度机器翻译:BusyBox结合许多常见的UNIX工具小版本到一个单一的小的可执行文件。它提供了你最经常发现在GNU FileUtils,shellutils公用事业等替代,BusyBox的事业通常比功能齐全的GNU的表兄弟更少的选择;然而,选项,包括提供预期的功能和行为很像他们的GNU同行。BusyBox为小或嵌入式系统提供了比较完善的环境。
板子板运行一个完整的操作系统需要四个文件“u-boot-iTOP-4412.bin”,“zImage”,“ramdisk-uboot.img”,“system.img”,文件“u-boot-iTOP-4412.bin”不用烧写,出厂前就有的,是通用的。如果你是不同板子估计也有类似东西。

下载解压busybox

进入网址网址:https://busybox.net/ 官网下载busybox
这里写图片描述
下载好的busybox-1.27.2.tar.bz2拷贝到ubuntu系统的/home/minilinux下:我用的是virtualbox 装的ubantu16.04,拷贝文件用的共享文件夹。接下来解压它, sudo tar -xvf busybox-1.27.2.tar.bz2 这里写图片描述 解压成功,cd到该文件夹里 cd busybox-1.27.2/

配置busybox

下面开始配置Busybox: make menuconfig 进入失败可能是没有sudo,没有安装gcc编译器,没有安装ncurses-devel.在ubuntu中ncurses-devel的名字叫libncurses5-dev
解决方法 sudo apt-get install gcc sudo apt-get install gcc-c++ sudo apt-get install libncurses5-dev sudo make menuconfig 配置之前 su root进入root省去不少麻烦。
这里写图片描述 选中Busybox Settings,然后按回车进入到Busybox Settings 界面,如下图:
这里写图片描述
在Busybox Settings 配置选项里面需要修改两个地方,第一个是Build Optiions-> CrossCompiler prefix,它是指定用什么编译器来编译Busybox,选中Build Options 如下图: 这里写图片描述
按回车,进入到Build Options 配置界面,选中Build Options 配置界面的Cross Compiler prefix然后回车;如下图:
这里写图片描述
输入使用的交叉编译工具arm-none-linux-gnueabi-,如下图:
这里写图片描述
按回车返回到Build Options 配置界面,这时可以看到刚才设置的交叉编译工具,如下图:
这里写图片描述
使用键盘的左右按键选中Exit,并且回车,如下图: 这里写图片描述 回到Busybox Settings 设置界面,如下图:
这里写图片描述
选中Installation Options ,然后按回车,进入Installation Options 配置界面,如下图:
这里写图片描述
选中BusyBox installation prefix 如上图所示,然后按回车进入BusyBox installationprefix 配置界面(这个界面是设置编译完Busybox,把最终生成的二进制文件安装到哪个目录下面),修改为../system
(最终生成的二进制文件会安装到当前目录的上一级目录下的system 目录里面),如下图:
这里写图片描述
回车,回到上一界面Busybox Settings:
接下来继续Tab键选择Exit,然后按回车,返回到Busybox Configuration:
继续使用键盘向右的方向键移动光标到“Exit”,然后回车选择yes保存:
这里写图片描述
没有报错的情况下,结果是这个
这里写图片描述
报错的原因一般是没有安装arm-linux-gcc编译器。
安装安装arm-linux-gcc编译器教程我下期再说,因为单单安装arm-linux-gcc编译器需要很长篇幅。

编译busybox

下面我们继续吧,接下来是编译和安装Busybox了,因为前面我们花了那么久终于配置好了:
busybox-1.27.2目录下执行: make 编译报错:
这里写图片描述 解决方法
MTD_FILE_MODE_RAW在/usr/include/mtd/mtd-abi.h中定义,于是将/usr/include/mtd/mtd-abi.h拷贝到busybox的include文件中,然后在nandwrite.c文件中包含该头文件 cd /usr/include/mtd/ sudo cp mtd-abi.h /home/minilinux/busybox-1.27.2/include (配图没有给权限sudo,普通用户需要权限执行cp,root用户不用) 这里写图片描述 到/busybox-1.27.1/miscutils下找到nandwrite.c
编辑nandwrite.c的代码 cd /home/minilinux/busybox-1.27.2/miscutils vim nandwrite.c或者是 gedit nandwrite.c 添加头文件#include “mtd-abi.h” 保存并关闭
注意 #include “mtd-abi.h” 的位置顺序,in出路头文件顺序不能错,#include “mtd-abi.h” 在中间 这里写图片描述
三个#include顺序必须与上图一样,顺序不一样还是错误。比如三行include让#include “mtd-abi.h”加到最后还是出错,需要加到中间。 cd .. 然后继续make 编译
继续报错:util-linux/blkdiscard.c: In function ‘blkdiscard_main’:
这里写图片描述
解决办法:
BLKSECDISCARD在/usr/include/linux/fs.h中定义,方法如上所述,将/usr/include/linux/fs.h拷贝到busybox的include文件夹中,然后修改util-linux/blkdiscard.c中头文件包含: cd /usr/include/linux/ sudo cp fs.h /home/minilinux/busybox-1.27.2/include 这里写图片描述
退回目录cd .. 执行make ,重新编译
接着继续出错
这里写图片描述
解决办法:
make menuconfig
Linux System Utilities—>nsenter,去掉该选项,重新编译make。
这里写图片描述 重新编译,妈的智障,又双叒叕出错了。
这里写图片描述 解决办法:和前面很类似了,其实这些错误我们应该会很熟悉的,都是这些乱七八糟的错误,慢慢解决就好: make menuconfig
Coreutils—>sync选项去掉,保存退出,
make重新编译
这里写图片描述
编译成功,松一口气。别高兴太早,还没结束呢,后面还有好多步骤呢。

安装生成system

接下来我们需要把编译生成的二进制文件安装到刚才我们指定的../system 目录里面,
使用命令“make install”命令安装二进制文件到“../system”目录。
这里写图片描述 root@zzz:/home/minilinux/busybox-1.27.2# cd .. root@zzz:/home/minilinux# ls busybox-1.27.2 busybox-1.27.2.tar.bz2 system root@zzz:/home/minilinux# cd system/ root@zzz:/home/minilinux/system# ls bin linuxrc sbin usr root@zzz:/home/minilinux/system#

完善最小系统

接下来开始很关键的完善最小Linux系统:
首先制作的文件系统还需要dev,etc,lib,mnt,proc,sys,tmp,var 文件夹,使用命令“mkdir dev etc lib mnt proc sys tmp var”
创建上述所有目录,然后ls查看: root@zzz:/home/minilinux/system# mkdir dev etc lib mnt proc sys tmp var root@zzz:/home/minilinux/system# ls bin dev etc lib linuxrc mnt proc sbin sys tmp usr var root@zzz:/home/minilinux/system# cd到刚刚创建的etc下,在etc 目录下使用命令vim建立eth0-setting 文件,并在eth0-setting 文件里输入下面的内容: IP=192.168.1.230 Mask=255.255.255.0 Gateway=192.168.1.1 DNS=192.168.1.1 MAC=08:90:90:90:90:90 修改权限755 chmod 755 eth0-setting 同理,在etc目录下创建init.d目录,并且cd到init.d下面去,在init.d 目录下面创建ifconfig-eth0 文件: [root@promote etc]# mkdir init.d [root@promote etc]# cd init.d/ [root@promote init.d]# vim ifconfig-eth0 #!/bin/bash echo -n Try to bring eth0 interface up......>/dev/ttySAC2 if [ -f /etc/eth0-setting ] then source /etc/eth0-setting if grep -q "^/dev/root / nfs " /etc/mtab then echo -n NFS root ... > /dev/ttySAC2 else ifconfig eth0 down ifconfig eth0 hw ether $MAC ifconfig eth0 $IP netmask $Mask up route add default gw $Gateway fi echo nameserver $DNS > /etc/resolv.conf else if grep -q "^/dev/root / nfs " /etc/mtab then echo -n NFS root ... > /dev/ttySAC2 else /sbin/ifconfig eth0 192.168.1.106 netmask 255.255.255.0 up fi fi echo Done > /dev/ttySAC2 把它们的权限修改为755。 chmod 755 ifconfig-eth0 同理,再次在init.d目录下面创建rcs文件: #! /bin/sh PATH=/sbin:/bin:/usr/sbin:/usr/bin:/usr/local/bin: runlevel=S prevlevel=N umask 022 export PATH runlevel prevlevel # # Trap CTRL-C &c only in this shell so we can interrupt subprocesses. # trap ":" INT QUIT TSTP /bin/hostname iTOP-4412 #/bin/mount -n -t proc none /proc #/bin/mount -n -t sysfs none /sys #/bin/mount -n -t usbfs none /proc/bus/usb #/bin/mount -t ramfs none /dev [ -e /proc/1 ] || /bin/mount -n -t proc none /proc [ -e /sys/class ] || /bin/mount -n -t sysfs none /sys [ -e /dev/tty ] || /bin/mount -t ramfs none /dev echo /sbin/mdev > /proc/sys/kernel/hotplug /sbin/mdev -s "rcS" 70L, 1898C 1,1 顶端 #! /bin/sh PATH=/sbin:/bin:/usr/sbin:/usr/bin:/usr/local/bin: runlevel=S prevlevel=N umask 022 export PATH runlevel prevlevel # # Trap CTRL-C &c only in this shell so we can interrupt subprocesses. # trap ":" INT QUIT TSTP /bin/hostname iTOP-4412 #/bin/mount -n -t proc none /proc #/bin/mount -n -t sysfs none /sys #/bin/mount -n -t usbfs none /proc/bus/usb #/bin/mount -t ramfs none /dev #! /bin/sh PATH=/sbin:/bin:/usr/sbin:/usr/bin:/usr/local/bin: runlevel=S prevlevel=N umask 022 export PATH runlevel prevlevel # # Trap CTRL-C &c only in this shell so we can interrupt subprocesses. # trap ":" INT QUIT TSTP /bin/hostname iTOP-4412 #/bin/mount -n -t proc none /proc #/bin/mount -n -t sysfs none /sys #/bin/mount -n -t usbfs none /proc/bus/usb #/bin/mount -t ramfs none /dev [ -e /proc/1 ] || /bin/mount -n -t proc none /proc [ -e /sys/class ] || /bin/mount -n -t sysfs none /sys [ -e /dev/tty ] || /bin/mount -t ramfs none /dev echo /sbin/mdev > /proc/sys/kernel/hotplug /sbin/mdev -s #/bin/hotplug # mounting file system specified in /etc/fstab mkdir -p /dev/pts mkdir -p /dev/shm /bin/mount -n -t devpts none /dev/pts -o mode=0622 /bin/mount -n -t tmpfs tmpfs /dev/shm #/bin/mount -n -t ramfs none /tmp #/bin/mount -n -t ramfs none /var mkdir -p /var/empty mkdir -p /var/log mkdir -p /var/log/boa mkdir -p /var/lock mkdir -p /var/run mkdir -p /var/tmp ln -sf /dev/ttyS2 /dev/tty2 ln -sf /dev/ttyS2 /dev/tty3 ln -sf /dev/ttyS2 /dev/tty4 syslogd /etc/rc.d/init.d/netd start echo " " > /dev/tty1 echo "Starting networking..." > /dev/tty1 #sleep 1 #/etc/rc.d/init.d/httpd start #echo " " > /dev/tty1 #echo "Starting web server..." > /dev/tty1 #sleep 1 #/etc/rc.d/init.d/leds start #echo " " > /dev/tty1 #echo "Starting leds service..." > /dev/tty1 #echo " " #sleep 1 #echo "*************************************" > /dev/ttySAC2 #echo " http://www.topeet.com.cn " > /dev/ttySAC2 #echo "*************************************" > /dev/ttySAC2 #echo "*************************************" #echo " http://www.topeet.com.cn " #echo "*************************************" mkdir /mnt/disk sleep 1 /sbin/ifconfig lo 127.0.0.1 /etc/init.d/ifconfig-eth0 修改权限755
在etc 目录下创建rc.d目录:
cd进入rc.d目录下,创建init.d目录,cd到init.d目录下:
在此时init.d目录下创建netd文件 [root@promote init.d]# vim netd #!/bin/sh base=inetd # See how we were called. case "$1" in start) /usr/sbin/$base ;; stop) pid=`/bin/pidof $base` if [ -n "$pid" ]; then kill -9 $pid fi ;; esac exit 0 和前面一样修改权限为755
接下来cd ../../../返回到system目录下面:
cd到lib目录下面:
因为使用的交叉编译环境和编译内核的相同,所以编译器是/home/minilinux/arm-2009q3,(编译器arm-2009q3是拷贝过去的)
Busybox 编译生成的二进制文件十一动态链接库的形式运行,所以我们需要拷贝编译器里面的
库文件到lib 目录,使用下面的命令:
“cp /usr/local/arm/arm-2009q3/arm-none-linux-gnueabi/libc/lib/* ./” cp /usr/local/arm/arm-2009q3/arm-none-linux-gnueabi/libc/lib/* ./ 这里写图片描述 即从arm-linux-gcc编译器库里把所有库文件/*拷贝库到最小系统lib库(system/lib)里面。
拷贝完成后返回到system目录,cd到var目录:
使用“mkdir lib lock log run tmp”命令在var 目录下建立lib,lock,log,run,
tmp 五个目录: mkdir lib lock log run tmp 到此,文件系统所需文件都建立好了,cd回到system目录的上一级目录:
这里写图片描述 到了这一步,制作好的文件夹“system”,可以在视频教程对应的目录下找到。如果发现
后面的操作命令出现了问题,可以对照着修改文件,看看问题出在什么地方。

打包和编译

打包工具 make_ext4fs 可以文件系统制作成二进制文件,先来安装一下 make_ext4fs 工
具。这个工具是在第一步准备工作的 {MOD}里“linux_tools.tgz”压缩文件。
拷贝压缩包“linux_tools.tgz”到 Ubuntu 系统的“/”目录下,注意目录是“/” 。
使用解压命令“tar -vxf linux_tools.tgz”解压 。 tar -vxf linux_tools.tgz 这里写图片描述
安装好打包编译工具“make_ext4fs”之后。
使用命令“cd /home/minilinux/”进入目录“/home/minilinux/”,
使用命令“make_ext4fs -s -l 314572800 -a root -L linux system.img system”生成 system.img文件系统镜像 。 cd /home/minilinux/ make_ext4fs -s -l 314572800 -a root -L linux system.img system 报错:
这里写图片描述
解决方法:安装lib32stdc++6 apt-get install lib32stdc++6 然后在/home/minilinux下重新输入 make_ext4fs -s -l 314572800 -a root -L linux system.img system 这里写图片描述
接着可以使用 ls 命令查看一下生成的 system.img 。
到此为止,已经完成了 linux 最小文件系统的制作 。
撒花!