xref: /OK3568_Linux_fs/device/rockchip/common/scripts/mk-image.sh (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun#!/bin/bash
2*4882a593Smuzhiyun
3*4882a593Smuzhiyun# Prefer using buildroot host tools for compatible.
4*4882a593Smuzhiyunif [ -n "$RK_BUILDROOT_CFG" ]; then
5*4882a593Smuzhiyun    HOST_DIR="$SDK_DIR/buildroot/output/$RK_BUILDROOT_CFG/host"
6*4882a593Smuzhiyun    export PATH=$HOST_DIR/usr/sbin:$HOST_DIR/usr/bin:$HOST_DIR/sbin:$HOST_DIR/bin:$PATH
7*4882a593Smuzhiyun    echo "Using host tools in $HOST_DIR"
8*4882a593Smuzhiyunelse
9*4882a593Smuzhiyun    "$(dirname "$(realpath "$0")")/check-mkimage.sh"
10*4882a593Smuzhiyunfi
11*4882a593Smuzhiyun
12*4882a593Smuzhiyunfatal()
13*4882a593Smuzhiyun{
14*4882a593Smuzhiyun    echo -e "FATAL: " $@
15*4882a593Smuzhiyun    exit 1
16*4882a593Smuzhiyun}
17*4882a593Smuzhiyun
18*4882a593Smuzhiyunusage()
19*4882a593Smuzhiyun{
20*4882a593Smuzhiyun    echo $@
21*4882a593Smuzhiyun    fatal "Usage: $0 <src_dir> <target_image> <fs_type> <size(M|K)|auto(0)> [label]"
22*4882a593Smuzhiyun}
23*4882a593Smuzhiyun
24*4882a593Smuzhiyun[ ! $# -lt 4 ] || usage "Not enough args${@+: $0 $@}"
25*4882a593Smuzhiyun
26*4882a593Smuzhiyunexport SRC_DIR=$1
27*4882a593Smuzhiyunexport TARGET=$2
28*4882a593SmuzhiyunFS_TYPE=$3
29*4882a593SmuzhiyunSIZE=$4
30*4882a593SmuzhiyunLABEL=$5
31*4882a593Smuzhiyun
32*4882a593Smuzhiyuncase $SIZE in
33*4882a593Smuzhiyun    auto)
34*4882a593Smuzhiyun        SIZE_KB=0
35*4882a593Smuzhiyun        ;;
36*4882a593Smuzhiyun    *K)
37*4882a593Smuzhiyun        SIZE_KB=$(( ${SIZE%K} ))
38*4882a593Smuzhiyun        ;;
39*4882a593Smuzhiyun    *)
40*4882a593Smuzhiyun        SIZE_KB=$(( ${SIZE%M} * 1024 )) # default is MB
41*4882a593Smuzhiyun        ;;
42*4882a593Smuzhiyunesac
43*4882a593Smuzhiyun
44*4882a593Smuzhiyunecho $SIZE_KB | grep -vq [^0-9] || usage "Invalid size: $SIZE_KB"
45*4882a593Smuzhiyun
46*4882a593SmuzhiyunTEMP=$(mktemp -u)
47*4882a593Smuzhiyun
48*4882a593Smuzhiyun[ -d "$SRC_DIR" ] || usage "No such src dir: $SRC_DIR"
49*4882a593Smuzhiyun
50*4882a593Smuzhiyuncopy_to_ntfs()
51*4882a593Smuzhiyun{
52*4882a593Smuzhiyun    DEPTH=1
53*4882a593Smuzhiyun    while true;do
54*4882a593Smuzhiyun        find $SRC_DIR -maxdepth $DEPTH -mindepth $DEPTH -type d|grep -q "" \
55*4882a593Smuzhiyun            || break
56*4882a593Smuzhiyun        find $SRC_DIR -maxdepth $DEPTH -mindepth $DEPTH -type d \
57*4882a593Smuzhiyun            -exec sh -c 'ntfscp $TARGET "$1" "${1#$SRC_DIR}"' sh {} \; || \
58*4882a593Smuzhiyun	    fatal "Detected non-buildroot ntfscp(doesn't support dir copy)"
59*4882a593Smuzhiyun        DEPTH=$(($DEPTH + 1))
60*4882a593Smuzhiyun    done
61*4882a593Smuzhiyun
62*4882a593Smuzhiyun    find $SRC_DIR -type f \
63*4882a593Smuzhiyun        -exec sh -c 'ntfscp $TARGET "$1" "${1#$SRC_DIR}"' sh {} \; || \
64*4882a593Smuzhiyun            fatal "Failed to do ntfscp!"
65*4882a593Smuzhiyun}
66*4882a593Smuzhiyun
67*4882a593Smuzhiyuncopy_to_image()
68*4882a593Smuzhiyun{
69*4882a593Smuzhiyun    ls $SRC_DIR/* &>/dev/null || return 0
70*4882a593Smuzhiyun
71*4882a593Smuzhiyun    echo "Copying $SRC_DIR into $TARGET (root permission required)"
72*4882a593Smuzhiyun    mkdir -p $TEMP || return 1
73*4882a593Smuzhiyun    sudo mount $TARGET $TEMP || return 1
74*4882a593Smuzhiyun
75*4882a593Smuzhiyun    cp -rp $SRC_DIR/* $TEMP
76*4882a593Smuzhiyun    RET=$?
77*4882a593Smuzhiyun
78*4882a593Smuzhiyun    sudo umount $TEMP
79*4882a593Smuzhiyun    rm -rf $TEMP
80*4882a593Smuzhiyun
81*4882a593Smuzhiyun    return $RET
82*4882a593Smuzhiyun}
83*4882a593Smuzhiyun
84*4882a593Smuzhiyuncheck_host_tool()
85*4882a593Smuzhiyun{
86*4882a593Smuzhiyun    which $1|grep -wq buildroot
87*4882a593Smuzhiyun}
88*4882a593Smuzhiyun
89*4882a593Smuzhiyunmkimage()
90*4882a593Smuzhiyun{
91*4882a593Smuzhiyun    echo "Making $TARGET from $SRC_DIR with size(${SIZE_KB}KB)"
92*4882a593Smuzhiyun    rm -rf $TARGET
93*4882a593Smuzhiyun    dd of=$TARGET bs=1K seek=$SIZE_KB count=0 &>/dev/null || \
94*4882a593Smuzhiyun        fatal "Failed to dd image!"
95*4882a593Smuzhiyun    case $FS_TYPE in
96*4882a593Smuzhiyun        ext[234])
97*4882a593Smuzhiyun            if mke2fs -h 2>&1 | grep -wq "\-d"; then
98*4882a593Smuzhiyun                mke2fs -t $FS_TYPE $TARGET -d $SRC_DIR \
99*4882a593Smuzhiyun                    || return 1
100*4882a593Smuzhiyun            else
101*4882a593Smuzhiyun                echo "Detected old mke2fs(doesn't support '-d' option)!"
102*4882a593Smuzhiyun                mke2fs -t $FS_TYPE $TARGET || return 1
103*4882a593Smuzhiyun                copy_to_image || return 1
104*4882a593Smuzhiyun            fi
105*4882a593Smuzhiyun            # Set max-mount-counts to 0, and disable the time-dependent checking.
106*4882a593Smuzhiyun            tune2fs -c 0 -i 0 $TARGET ${LABEL:+-L $LABEL}
107*4882a593Smuzhiyun            ;;
108*4882a593Smuzhiyun        msdos|fat|vfat)
109*4882a593Smuzhiyun            # Use fat32 by default
110*4882a593Smuzhiyun            mkfs.vfat -F 32 $TARGET ${LABEL:+-n $LABEL} && \
111*4882a593Smuzhiyun                MTOOLS_SKIP_CHECK=1 \
112*4882a593Smuzhiyun                mcopy -bspmn -D s -i $TARGET $SRC_DIR/* ::/
113*4882a593Smuzhiyun            ;;
114*4882a593Smuzhiyun        ntfs)
115*4882a593Smuzhiyun            # Enable compression
116*4882a593Smuzhiyun            mkntfs -FCQ $TARGET ${LABEL:+-L $LABEL}
117*4882a593Smuzhiyun            if check_host_tool ntfscp; then
118*4882a593Smuzhiyun                copy_to_ntfs
119*4882a593Smuzhiyun            else
120*4882a593Smuzhiyun                copy_to_image
121*4882a593Smuzhiyun            fi
122*4882a593Smuzhiyun            ;;
123*4882a593Smuzhiyun        ubi|ubifs)
124*4882a593Smuzhiyun            mk_ubi_image
125*4882a593Smuzhiyun            ;;
126*4882a593Smuzhiyun    esac
127*4882a593Smuzhiyun}
128*4882a593Smuzhiyun
129*4882a593Smuzhiyunmkimage_auto_sized()
130*4882a593Smuzhiyun{
131*4882a593Smuzhiyun    tar cf $TEMP $SRC_DIR &>/dev/null
132*4882a593Smuzhiyun    SIZE_KB=$(du -k $TEMP|grep -o "^[0-9]*")
133*4882a593Smuzhiyun    rm -rf $TEMP
134*4882a593Smuzhiyun    echo "Making $TARGET from $SRC_DIR (auto sized)"
135*4882a593Smuzhiyun
136*4882a593Smuzhiyun    MAX_RETRY=10
137*4882a593Smuzhiyun    RETRY=0
138*4882a593Smuzhiyun
139*4882a593Smuzhiyun    while true;do
140*4882a593Smuzhiyun        EXTRA_SIZE=$(($SIZE_KB / 50))
141*4882a593Smuzhiyun        SIZE_KB=$(($SIZE_KB + ($EXTRA_SIZE > 4096 ? $EXTRA_SIZE : 4096)))
142*4882a593Smuzhiyun        mkimage && break
143*4882a593Smuzhiyun
144*4882a593Smuzhiyun        RETRY=$[RETRY+1]
145*4882a593Smuzhiyun        [ $RETRY -gt $MAX_RETRY ] && fatal "Failed to make image!"
146*4882a593Smuzhiyun        echo "Retring with increased size....($RETRY/$MAX_RETRY)"
147*4882a593Smuzhiyun    done
148*4882a593Smuzhiyun}
149*4882a593Smuzhiyun
150*4882a593Smuzhiyunmk_ubi_image()
151*4882a593Smuzhiyun{
152*4882a593Smuzhiyun    TARGET_DIR="${RK_OUTDIR:-$(dirname "$TARGET")}"
153*4882a593Smuzhiyun    UBI_VOL_NAME=${LABEL:-ubi}
154*4882a593Smuzhiyun
155*4882a593Smuzhiyun    # default page size 2KB
156*4882a593Smuzhiyun    UBI_PAGE_SIZE=${RK_UBI_PAGE_SIZE:-2048}
157*4882a593Smuzhiyun    # default block size 128KB
158*4882a593Smuzhiyun    UBI_BLOCK_SIZE=${RK_UBI_BLOCK_SIZE:-0x20000}
159*4882a593Smuzhiyun
160*4882a593Smuzhiyun    UBIFS_LEBSIZE=$(( $UBI_BLOCK_SIZE - 2 * $UBI_PAGE_SIZE ))
161*4882a593Smuzhiyun    UBIFS_MINIOSIZE=$UBI_PAGE_SIZE
162*4882a593Smuzhiyun
163*4882a593Smuzhiyun    UBIFS_IMAGE="$TARGET_DIR/$UBI_VOL_NAME.ubifs"
164*4882a593Smuzhiyun    UBINIZE_CFG="$TARGET_DIR/${UBI_VOL_NAME}-ubinize.cfg"
165*4882a593Smuzhiyun
166*4882a593Smuzhiyun    UBIFS_MAXLEBCNT=$(( $SIZE_KB * 1024 / $UBIFS_LEBSIZE ))
167*4882a593Smuzhiyun
168*4882a593Smuzhiyun    mkfs.ubifs -x lzo -e $UBIFS_LEBSIZE -m $UBIFS_MINIOSIZE \
169*4882a593Smuzhiyun        -c $UBIFS_MAXLEBCNT -d $SRC_DIR -F -v -o $UBIFS_IMAGE || return 1
170*4882a593Smuzhiyun
171*4882a593Smuzhiyun    echo "[ubifs]" > $UBINIZE_CFG
172*4882a593Smuzhiyun    echo "mode=ubi" >> $UBINIZE_CFG
173*4882a593Smuzhiyun    echo "vol_id=0" >> $UBINIZE_CFG
174*4882a593Smuzhiyun    echo "vol_type=dynamic" >> $UBINIZE_CFG
175*4882a593Smuzhiyun    echo "vol_name=$UBI_VOL_NAME" >> $UBINIZE_CFG
176*4882a593Smuzhiyun    echo "vol_size=${SIZE_KB}KiB" >> $UBINIZE_CFG
177*4882a593Smuzhiyun    echo "vol_alignment=1" >> $UBINIZE_CFG
178*4882a593Smuzhiyun    echo "vol_flags=autoresize" >> $UBINIZE_CFG
179*4882a593Smuzhiyun    echo "image=$UBIFS_IMAGE" >> $UBINIZE_CFG
180*4882a593Smuzhiyun    ubinize -o $TARGET -m $UBIFS_MINIOSIZE -p $UBI_BLOCK_SIZE \
181*4882a593Smuzhiyun        -v $UBINIZE_CFG
182*4882a593Smuzhiyun}
183*4882a593Smuzhiyun
184*4882a593Smuzhiyunrm -rf $TARGET
185*4882a593Smuzhiyuncase $FS_TYPE in
186*4882a593Smuzhiyun    ext[234]|msdos|fat|vfat|ntfs|ubi|ubifs)
187*4882a593Smuzhiyun        if [ $SIZE_KB -eq 0 ]; then
188*4882a593Smuzhiyun            mkimage_auto_sized
189*4882a593Smuzhiyun        else
190*4882a593Smuzhiyun            mkimage && echo "Generated $TARGET"
191*4882a593Smuzhiyun        fi
192*4882a593Smuzhiyun        ;;
193*4882a593Smuzhiyun    squashfs)
194*4882a593Smuzhiyun        [ $SIZE_KB -eq 0 ] || fatal "$FS_TYPE: fixed size not supported."
195*4882a593Smuzhiyun        mksquashfs $SRC_DIR $TARGET -noappend -comp lz4
196*4882a593Smuzhiyun        ;;
197*4882a593Smuzhiyun    jffs2)
198*4882a593Smuzhiyun        [ $SIZE_KB -eq 0 ] || fatal "$FS_TYPE: fixed size not supported."
199*4882a593Smuzhiyun        mkfs.jffs2 -r $SRC_DIR -o $TARGET 0x10000 --pad=0x400000 -s 0x1000 -n
200*4882a593Smuzhiyun        ;;
201*4882a593Smuzhiyun    *)
202*4882a593Smuzhiyun        usage "File system: $FS_TYPE not supported."
203*4882a593Smuzhiyun        ;;
204*4882a593Smuzhiyunesac
205