For most embedded systems, particularly for consumer electronics like smartphone systems, to reduce the wait time of system power on or start up, the system must be fast enough.
Most embedded devices have strict time limits from power on to showing graphic UI, so speeding the boot time should be considered an important feature.
The following are the basic methods to speed system booting:
Disable unused features and functions in all booting components (bootloader, Linux kernel, system, and applications) of an embedded Linux system. This means let the system perform less but necessary jobs.
Some initialization procedures can be deferred to the background after the device has booted to a basically workable state.
If a multicore CPU is being used, parallize the boot process with multithreads.
Based on the considerations of power-cost optimization, set CPU frequency, bus frequency, memory frequency, and even external device working frequency (such as EMMC) as high as possible.
Measure the boot procedure and find out the time-cost bottlenecks.
Bootchart (http://www.bootchart.org/) is for performance analysis and visualization of the Linux boot process; it can be used for boot speedup optimization.
Android does include the
init method's built-in
bootchartd support, but requires the
init application to be rebuilt; for more details, visit http://elinux.org/Using_Bootchart_on_Android.
In our example, we introduce the BusyBox built-in
bootchartd support to measure the Android system boot procedure.
Configure Bootchart in BusyBox:
First, enable the Bootchart applet in BusyBox.
Init Utilities ---> [*] bootchartd [*] Compatible, bloated header [*] Support bootchartd.conf
Install BusyBox with
Then, copy the
busyboxbinary to Android
ramdisk.img, create a link
busybox, and create a
$ cd ramdisk/ $ ln -sf busybox /bootchartd $ mkdir var/log
ramdisk.imgwith the following:
$ find . | cpio -H newc -o | gzip -9 > ../ramdisk.img
The link is for directly using
var/logdirectory is for saving the boot log generated by
Measure the Android system booting with BusyBox
Now start the Android emulator.
$ emulator @busybox-avd -shell -show-kernel -kernel ./zImage \ -ramdisk ./ramdisk.img \ -qemu -append "rdinit=/bootchartd bootchard_init=/init"
-qemu -appendoptions allow us to pass extra arguments to the Linux kernel; the preceding
rdinit=/bootchartdsupport replaces the default ramdisk
bootchartd, and then
bootchartdto start the real
Get the bootchartd measuring log:
After a while, the Android UI will be started and a new file will be created to save the boot logs.
shell@android # ls -l /var/log total 72 -rw-r--r-- 1 0 0 73334 Jul 5 17:24 bootlog.tgz
Then, pull the logfile into our development system.
$ adb pull /var/log/bootlog.tgz
pybootchartgui, and analyze it.
Analyze the boot log with
pybootchartgui. This tool can generate a readable graphic output based on the previous boot logfile. In Ubuntu, we can install it simply with the following:
$ sudo apt-get install bootchart pybootchartgui
Then draw a graph with it.
$ bootchart ./bootlog.tgz
It may generate an error, such as the header file format is not compatible with the original larger version of the bootchart:
File "/usr/lib/pymodules/python2.7/pybootchartgui/draw.py", line 341, in draw_header txt = headertitle + ': ' + mangle(headers.get(headerkey)) TypeError: cannot concatenate 'str' and 'NoneType' objects
To work around it, just let the
pybootchartguiignore the errors with except handling.
$ vim /usr/lib/pymodules/python2.7/pybootchartgui/draw.py 338 for (headerkey, headertitle, mangle) in toshow: 339 header_y += ctx.font_extents() 340 try: 341 txt = headertitle + ': ' + mangle(headers.get(headerkey)) 342 except: 343 continue 344 draw_text(ctx, txt, TEXT_COLOR, off_x, header_y)
If there are no other issues, we should get results successfully, as shown in the following screenshot:
At last, it's time to analyze the graph.
A bootchart picture will have a few of different bits of information that are of interest, especially the CPU and disk load graphs at the top.
There is a timeline running from left to right, with processes shown starting (and sometimes stopping) underneath it. The process CPU loads are indicated by the coloration of its process bar. The things to look for are the start and stop times of the different processes, and their CPU load. Long gaps with low load may mean a timeout or some other issue.
Once you have found out which processes are consuming time during the initialization, we can further check these by looking at the system logs with the logcat tool of Android; running them with strace, a profile (of Android), or perf; and reviewing the corresponding source code.
To speed system booting means to reduce the time cost at the system booting stage and also to increase the working frequency of all related devices and meanwhile reduce time cost resources. But, in real practice, the maximal frequency of the devices should be limited to reduce the power cost.
The whole booting procedure of an embedded system includes bootloader startup, kernel decompression and bootup,
init process launching, and system booting.
bootchartd is mainly for optimization of the booting stage after the
init process launches.