Openwrt 初探

 

最近想研究一下Openwrt,因而開始搭建openwrt環境,雖然如今沒有現成的板子,可是html

能夠先編譯起來。linux

 

openwrt的特色是基於下載 -> patch -> 編譯 的一個工做模式,openwrt整個包一開始下載下來也不是很大,由於裏面git

基本上沒有源碼,要在編譯的時候下載。github

 

 

看了別人的帖子,都推薦使用svn從官網下載源碼,json

svn co svn://svn.openwrt.org/openwrt/trunk/

可是實際測試發現它的速度太慢了,爲了獲得官方的源碼,從github上找到了它:ubuntu

https://github.com/openwrt-mirror/openwrt

 

將它下載下來以後,要安裝一些必要的包來編譯它,我使用的是ubuntu12.04.網絡

sudo apt-get install flex g++ gawk zlib1g-dev libncurses5-dev libssl-dev subversion

 

先看一下它的目錄樹:架構

tree -d -L 2
.
├── config
├── docs
├── include
│   └── site
├── package
│   ├── base-files
│   ├── boot
│   ├── devel
│   ├── firmware
│   ├── kernel
│   ├── libs
│   ├── network
│   ├── system
│   └── utils
├── scripts
│   ├── config
│   └── flashing
├── target
│   ├── imagebuilder
│   ├── linux
│   ├── sdk
│   └── toolchain
├── toolchain 
│   ├── binutils
│   ├── gcc
│   ├── gdb
│   ├── glibc
│   ├── insight
│   ├── kernel-headers
│   ├── musl
│   ├── uClibc
│   └── wrapper
└── tools 
    ├── autoconf
    ├── automake
    ├── b43-tools
    ├── bc
    ├── bison
    ├── ccache
    ├── cloog
    ├── cmake
    ├── dosfstools
    ├── e2fsprogs
    ├── elftosb
    ├── findutils
    ├── firmware-utils
    ├── flex
    ├── flock
    ├── genext2fs
    ├── gengetopt
    ├── gmp
    ├── include
    ├── libelf
    ├── libtool
    ├── lzma
    ├── lzma-old
    ├── m4
    ├── missing-macros
    ├── mkimage
    ├── mklibs
    ├── mm-macros
    ├── mpc
    ├── mpfr
    ├── mtd-utils
    ├── mtools
    ├── padjffs2
    ├── patch
    ├── patchelf
    ├── patch-image
    ├── pkg-config
    ├── ppl
    ├── qemu
    ├── quilt
    ├── scons
    ├── sed
    ├── sparse
    ├── squashfs
    ├── squashfs4
    ├── sstrip
    ├── upslug2
    ├── upx
    ├── wrt350nv2-builder
    ├── xz
    └── yaffs2

 

 

 

 

 

 

首先是更新一下feed:app

./scripts/feeds update -a
./scripts/feeds install -a

 

這裏的-a表示更新全部的feed,那麼這裏有哪些feed呢,能夠從log裏面看出來:less

tan@love:~/openwrt-git/openwrt$ scripts/feeds update -a
Updating feed 'packages' from 'https://github.com/openwrt/packages.git' ...
Cloning into './feeds/packages'...
remote: Counting objects: 3682, done.
remote: Compressing objects: 100% (2941/2941), done.
remote: Total 3682 (delta 488), reused 3055 (delta 247), pack-reused 0
Receiving objects: 100% (3682/3682), 2.00 MiB | 24 KiB/s, done.
Resolving deltas: 100% (488/488), done.
Create index file './feeds/packages.index' 
Collecting package info: done
Collecting target info: done
Updating feed 'luci' from 'https://github.com/openwrt/luci.git' ...
Cloning into './feeds/luci'...
remote: Counting objects: 11683, done.
remote: Compressing objects: 100% (6278/6278), done.
remote: Total 11683 (delta 3832), reused 9770 (delta 2394), pack-reused 0
Receiving objects: 100% (11683/11683), 8.42 MiB | 85 KiB/s, done.
Resolving deltas: 100% (3832/3832), done.
Create index file './feeds/luci.index' 
Collecting package info: done
Collecting target info: done
Updating feed 'routing' from 'https://github.com/openwrt-routing/packages.git' ...
Cloning into './feeds/routing'...
remote: Counting objects: 441, done.
remote: Compressing objects: 100% (343/343), done.
Receiving objects: 100% (441/441), 242.46 KiB | 58 KiB/s, done.
remote: Total 441 (delta 81), reused 330 (delta 38), pack-reused 0
Resolving deltas: 100% (81/81), done.
Create index file './feeds/routing.index' 
Collecting package info: done
Collecting target info: done
Updating feed 'telephony' from 'https://github.com/openwrt/telephony.git' ...
Cloning into './feeds/telephony'...
remote: Counting objects: 268, done.
remote: Compressing objects: 100% (222/222), done.
remote: Total 268 (delta 51), reused 211 (delta 22), pack-reused 0
Receiving objects: 100% (268/268), 140.49 KiB | 102 KiB/s, done.
Resolving deltas: 100% (51/51), done.
Create index file './feeds/telephony.index' 
Collecting package info: done
Collecting target info: done
Updating feed 'management' from 'https://github.com/openwrt-management/packages.git' ...
Cloning into './feeds/management'...
remote: Counting objects: 40, done.
remote: Compressing objects: 100% (28/28), done.
remote: Total 40 (delta 7), reused 27 (delta 2), pack-reused 0
Unpacking objects: 100% (40/40), done.
Create index file './feeds/management.index' 
Collecting package info: done
Collecting target info: done
Updating feed 'targets' from 'https://github.com/openwrt/targets.git' ...
Cloning into './feeds/targets'...
remote: Counting objects: 137, done.
remote: Compressing objects: 100% (95/95), done.
remote: Total 137 (delta 17), reused 122 (delta 16), pack-reused 0
Receiving objects: 100% (137/137), 130.80 KiB | 44 KiB/s, done.
Resolving deltas: 100% (17/17), done.
Create index file './feeds/targets.index' 
Collecting package info: done
Collecting target info: done

能夠從上面的網址看出來更新的feed。

 

 

更新feed後目錄樹的變化:

.
├── config
├── docs
├── feeds
│   ├── luci
│   ├── luci.tmp
│   ├── management
│   ├── management.tmp
│   ├── packages
│   ├── packages.tmp
│   ├── routing
│   ├── routing.tmp
│   ├── targets
│   ├── targets.tmp
│   ├── telephony
│   └── telephony.tmp
├── include
│   └── site
├── package
│   ├── base-files
│   ├── boot
│   ├── devel
│   ├── feeds
│   ├── firmware
│   ├── kernel
│   ├── libs
│   ├── network
│   ├── system
│   └── utils
├── scripts
│   ├── config
│   └── flashing
├── staging_dir
│   └── host
├── target
│   ├── imagebuilder
│   ├── linux
│   ├── sdk
│   └── toolchain
├── tmp
│   └── info
├── toolchain
│   ├── binutils
│   ├── gcc
│   ├── gdb
│   ├── glibc
│   ├── insight
│   ├── kernel-headers
│   ├── musl
│   ├── uClibc
│   └── wrapper
└── tools
    ├── autoconf
    ├── automake
    ├── b43-tools
    ├── bc
    ├── bison
    ├── ccache
    ├── cloog
    ├── cmake
    ├── dosfstools
    ├── e2fsprogs
    ├── elftosb
    ├── findutils
    ├── firmware-utils
    ├── flex
    ├── flock
    ├── genext2fs
    ├── gengetopt
    ├── gmp
    ├── include
    ├── libelf
    ├── libtool
    ├── lzma
    ├── lzma-old
    ├── m4
    ├── missing-macros
    ├── mkimage
    ├── mklibs
    ├── mm-macros
    ├── mpc
    ├── mpfr
    ├── mtd-utils
    ├── mtools
    ├── padjffs2
    ├── patch
    ├── patchelf
    ├── patch-image
    ├── pkg-config
    ├── ppl
    ├── qemu
    ├── quilt
    ├── scons
    ├── sed
    ├── sparse
    ├── squashfs
    ├── squashfs4
    ├── sstrip
    ├── upslug2
    ├── upx
    ├── wrt350nv2-builder
    ├── xz
    └── yaffs2

 

 

 

 

而後使用:

make menuconfig
make

編譯的過程會持續好幾個小時,由於編譯的時候還須要在線下載工具包,若是網絡慢的話就會

更慢了。

 

關於make的做用,README是這樣說的:

 

Simply running "make" will build your firmware.
It will download all sources, build the cross-compile toolchain, 
the kernel and all choosen applications.

 

中文手冊是這樣說的:

OpenWrt選擇了另外一種方式來生成固件:下載,打補丁,編譯,一切從零開始,即便交叉編譯鏈也是如此。

一開始下載openwrt源碼的時候,也就大約300MB,可是裏面基本上沒有代碼,大部分

都是配置文件。

 

 

 

 

 openwrt的英文文檔以下:

 

https://downloads.openwrt.org/kamikaze/docs/openwrt.html

 

 

 

在編譯過程當中,使用make -j V=99 能夠加快編譯速度,而且顯示全部信息,

在編譯的時候,個人swap被佔滿,而且報錯,多是由於屏幕上刷的太快致使的:

virtual memory exhaustedvirtual memory exhausted

 

 

不打開V=99的狀況下,個人編譯log以下:

tan@ubuntu:~/openwrt$ make -j4
 make[1] world
 make[2] target/compile
 make[2] package/cleanup
 make[3] -C target/linux compile
 make[2] package/compile
 make[3] -C package/system/opkg host-compile
 make[3] -C package/libs/toolchain compile
 make[3] -C package/kernel/gpio-button-hotplug compile
 make[3] -C package/libs/ncurses host-compile
 make[3] -C package/libs/libnl-tiny compile
 make[3] -C package/utils/lua compile
 make[3] -C package/libs/libjson-c compile
 make[3] -C package/libs/lzo compile
 make[3] -C package/libs/zlib compile
 make[3] -C package/libs/ncurses compile
 make[3] -C package/boot/uboot-ar71xx compile
 make[3] -C package/firmware/linux-firmware compile
 make[3] -C package/libs/ocf-crypto-headers compile
 make[3] -C package/network/utils/iw compile
 make[3] -C package/network/services/dropbear compile
 make[3] -C package/libs/libpcap compile
 make[3] -C package/network/utils/linux-atm compile
 make[3] -C package/network/utils/resolveip compile
 make[3] -C package/utils/busybox compile
 make[3] -C package/libs/libubox compile
 make[3] -C package/utils/util-linux compile
 make[3] -C package/kernel/linux compile
 make[3] -C package/libs/openssl compile
 make[3] -C package/system/ubus compile
 make[3] -C package/system/uci compile
 make[3] -C package/utils/jsonfilter compile
 make[3] -C package/system/mtd compile
 make[3] -C package/system/opkg compile
 make[3] -C package/network/config/netifd compile
 make[3] -C package/system/ubox compile
 make[3] -C package/utils/ubi-utils compile
 make[3] -C package/network/services/hostapd compile
 make[3] -C package/network/config/swconfig compile
 make[3] -C package/network/services/odhcpd compile
 make[3] -C package/network/utils/iwinfo compile
 make[3] -C package/system/procd compile
 make[3] -C package/system/fstools compile
 make[3] -C package/base-files compile
 make[3] -C package/boot/uboot-envtools compile
 make[3] -C package/kernel/mac80211 compile
 make[3] -C package/network/utils/iptables compile
 make[3] -C package/network/services/dnsmasq compile
 make[3] -C package/network/ipv6/odhcp6c compile
 make[3] -C package/network/services/ppp compile
 make[3] -C package/network/config/firewall compile
 make[2] package/install
 make[3] package/preconfig
 make[2] target/install
 make[3] -C target/linux install
 make[2] package/index

最終會生成下面的文件(在bin文件夾內):

因爲我使用默認的配置,生成的文件太多,這裏只給一個部分的截圖

 

初次下載源代碼,爲了理解openwrt的架構和編譯過程,下面作一下簡要的分析:

 

openwrt是基於linux kernel的,而且使用uclibc做爲c庫。

 注意到編譯過程當中生成了三個文件夾,那麼他們分別是幹什麼的呢?

dl

build_dir

staging_dir

 

dl是在編譯的時候下載文件的目錄,這些文件都是編譯所須要的,下面是它們的的一部分:

├── ath10k-firmware-da0f85d924226ee30c46e037120621c9e192b39e.tar.bz2
├── autoconf-2.69.tar.xz
├── automake-1.15.tar.xz
├── bc-1.06.95.tar.bz2
├── binutils-linaro-2.24.0-2014.09.tar.xz
├── bison-3.0.2.tar.xz
├── broadcom-wl-4.150.10.5.tar.bz2
├── broadcom-wl-5.100.138.tar.bz2
├── busybox-1.23.2.tar.bz2
├── cmake-2.8.12.2.tar.gz
├── compat-wireless-2015-03-09.tar.bz2
├── dnsmasq-2.72.tar.gz
├── dropbear-2014.65.tar.bz2
├── e2fsprogs-1.42.8.tar.gz
├── findutils-4.4.2.tar.gz
├── firewall-2015-02-26-165029cb8c0f1545628f44143aec965e64cef021.tar.gz
├── flex-2.5.39.tar.bz2
├── fstools-2015-03-30-a5fa5b6144253726dcd7e769197eed787a723f5f.tar.gz
├── gcc-linaro-4.8-2014.04.tar.xz
├── gdb-linaro-7.6-2013.05.tar.bz2
├── genext2fs-1.4.1.tar.gz
├── gengetopt-2.22.6.tar.gz
├── gmp-5.1.3.tar.xz
├── hostapd-2015-03-25.tar.bz2
├── iptables-1.4.21.tar.bz2
├── ipw2100-fw-1.3.tgz
├── ipw2200-fw-3.1.tgz
├── iw-3.17.tar.xz
├── json-c-0.12.tar.gz
├── jsonfilter-2014-06-19-cdc760c58077f44fc40adbbe41e1556a67c1b9a9.tar.gz
├── libelf-0.8.13.tar.gz
├── libiwinfo-2015-03-23-40f2844fadc05f4a4de7699dbc12fee295b7057b.tar.gz
├── libpcap-1.5.3.tar.gz
├── libtool-2.4.tar.gz
├── libubox-2015-03-22-b8d9b382e39823850331edc2a92379173daf1be3.tar.gz
├── linux-3.18.10.tar.xz
├── linux-atm-2.5.2.tar.gz
├── linux-firmware-2015-03-20-f404336ba808cbd57547196e13367079a23b822c.tar.bz2
├── lua-5.1.5.tar.gz

 

注意到,這些都是從網上下載的,要注意保留,之後編譯的時候就不用上網下載了。

build_dir的做用就是存放上述這些壓縮包的解壓路徑,也就是說,dl的包會解壓到build_dir裏面,

而且編譯這些包。

其中,這裏有三個目錄:

tan@ubuntu:~/openwrt$ tree build_dir/ -d -L 1
build_dir/
├── host
├── target-mips_34kc_uClibc-0.9.33.2
└── toolchain-mips_34kc_gcc-4.8-linaro_uClibc-0.9.33.2

 

host目錄是爲了編譯一些tools用於協助生成openwrt image

target目錄是爲目標主機編譯用的,能夠在目錄上看到CPU的架構和所用的c庫

toolchain是用來編譯交叉編譯器的

 

 

在staging_dir下面能夠看到相似的三個目錄:

tan@ubuntu:~/openwrt$ tree staging_dir/ -d -L 1
staging_dir/
├── host
├── target-mips_34kc_uClibc-0.9.33.2
└── toolchain-mips_34kc_gcc-4.8-linaro_uClibc-0.9.33.2

 

host目錄下存放了一些編譯主機上的一些工具(tools)

target 目錄主要存放編譯出來的firmware,是給目標機器用的

toolchain目錄包含了交叉編譯器,你能夠在裏面寫一個簡單的c文件,而且使用交叉編譯器編譯它,

生成的程序能夠在目標機器上運行。

 

雖然不徹底如此,能夠將staging_dir的每一個文件夾對應理解成build_dir的產物

 

這裏有編譯過程的大致介紹:

http://wiki.openwrt.org/doc/howto/build
http://downloads.openwrt.org/docs/buildroot-documentation.html

 

openwrt是一個高度定製版的buildroot,官網有它的介紹:

http://wiki.openwrt.org/about/toolchain

使用這個系統,能夠基本作到全自動的編譯過程。

 

 

bin目錄下面的文件粗看能夠分爲兩類:

openwrt-ar71xx-generic-a02-rb-w300n-squashfs-factory.bin
openwrt-ar71xx-generic-a02-rb-w300n-squashfs-sysupgrade.bin

其中這兩個的區別是(轉自http://see.sl088.com/wiki/Openwrt_factory%E5%9B%BA%E4%BB%B6/%E4%B8%BA%E4%BD%95%E5%85%88%E5%88%B7factory):

 

factory是用來從原廠固件升級到openwrt用的。 sysupgrade是用來給openwrt升級用的

不管你是升級仍是從官方方刷openwrt,openwrt-XXXXXXX-factory.bin的固件都是適用的。 而openwrt-XXXXXXX-sysupgrade.bin.固件只能用來升級用。如TTL救磚就不能用sysupgrade的固件。

 

其中這裏又進一步說明了:

http://www.cnblogs.com/siikee/p/4224086.html

 

 

bin文件下還有不少ipk文件,這些文件是opkg包管理系統的文件,在openwrt

運行起來的時候可使用opkg安裝,用起來和debian的deb差很少。

 

另外,openwrt 官方說了,the bootloader is not part of OpenWrt

http://wiki.openwrt.org/doc/techref/bootloader

並且,bootloader對於每個路由器都是不同的,負責將最底層開起來。廠家也不見得會將最底層的

代碼開源。

目前有不少賣修改好的openwrt路由器,一個賣點就是不死uboot,就是說

你的firmware無論怎麼刷均可以恢復,它包括一個網頁接口,能夠上傳firmware

到路由器上,這樣大大方便了openwrt的調試。

 

 

 

 

openwrt的menuconfig是定製好的,項目在config**.in裏面:

 

 最後看看openwrt 的patch系統

 

package的不少子目錄都包含這兩個東西,patches 是一些patch,Makefile包含了下載地址和其餘的一些信息。

當發現這些用戶空間軟件出問題的時候,爲其加patch就能夠了,

實際上linux kernel出問題時,也能夠這樣相似地對其加一些patch進去。

相關文章
相關標籤/搜索