需求
-
制作一個全平台通用的燒錄鏡像
-
用戶可自行調整root空間大小
-
存在一個分區,可以全平台讀寫
解壓鏡像
tina系統一鍵打包后為Phoenix img, 不是常規的分區鏡像,因此需要PhoenixCard解壓鏡像到sd卡中。
完成后分區情況如下
Device Start End Sectors Size Type
/dev/sdb1 49152 49663 512 256K Microsoft basic data
/dev/sdb2 49664 61951 12288 6M Microsoft basic data
/dev/sdb3 61952 225791 163840 80M Microsoft basic data
/dev/sdb4 225792 553471 327680 160M Microsoft basic data
/dev/sdb5 553472 980991 427520 208.8M Microsoft basic data
最后一個是phoenix燒錄后自動拓展的UDISK分區,不管它。
由於gpt分區表存在於頭部和尾部,所以gpt分區的克隆實際上十分麻煩,先慢慢嘗試下吧,也許最后可以修復。
這里實際上需要的數據只有sda1到sda4,所以需要計算下復制的數據大小。
計算數據大小
可以看到sectors大小為bytes
Disk /dev/sdb: 480 MiB, 503316480 bytes, 983040 sectors
Disk model: SD Card Reader
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
扇區大小和磁盤大小換算:983040*512(Bytes)=503316480(Bytes)/1024(KiB)/1024(MiB)=480(MiB)
所以復制到sdb4末尾,所需的字節數為
553472*512=283377664bytes。並且還需要1024k大小儲存gpt分區信息。
bs=bytes:同時設置讀入/輸出的塊大小為bytes個字節。
count=blocks:僅拷貝blocks個塊,塊大小等於ibs指定的字節數。
塊和字節數后可能帶有以下的一個或多個后綴:
c =1, w =2, b =512, kB =1000, K =1024, MB =1000x1000, M =1024x1024, xM =M
GB =1000x1000x1000, G =1024x1024x1024, and so on for T, P, E, Z, Y.
如果將bs設置為1M,則count=283377664/1024/1024+1024K/1M=271.25,顯然是不允許小數的,但是sdb5扇區上的數據是我們不需要的,多出一些扇區無關緊要,最后設置count為272。
克隆dd鏡像
dd if=/dev/sdb bs=1M count=272 of=./image.img status=progress
克隆完畢后查看分區情況
fdisk -l image.img
Disk image.img: 272 MiB, 285212672 bytes, 557056 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x00000000
Device Boot Start End Sectors Size Id Type
image.img1 1 4294967295 4294967295 2T ee GPT
可以看到分區表已經損壞,需要重建分區表。
修復分區
新建gpt分區表
parted /dev/sdb
mklabel gpt
yes
quit
恢復分區
/home/lithromantic/Desktop]$ fdisk image.img
Command (m for help): n
Partition number (1-128, default 1):
First sector (34-557022, default 2048): 49152
Last sector, +/-sectors or +/-size{K,M,G,T,P} (49152-557022, default 557022): 49663
Created a new partition 1 of type 'Linux filesystem' and of size 256 KiB.
Command (m for help): n
Partition number (2-128, default 2):
First sector (34-557022, default 51200): 49664
Last sector, +/-sectors or +/-size{K,M,G,T,P} (49664-557022, default 557022): 61951
Created a new partition 2 of type 'Linux filesystem' and of size 6 MiB.
Command (m for help): n
Partition number (3-128, default 3):
First sector (34-557022, default 63488): 61952
Last sector, +/-sectors or +/-size{K,M,G,T,P} (61952-557022, default 557022): 225791
Created a new partition 3 of type 'Linux filesystem' and of size 80 MiB.
Command (m for help): n
Partition number (4-128, default 4):
First sector (34-557022, default 227328): 225792
Last sector, +/-sectors or +/-size{K,M,G,T,P} (225792-557022, default 557022): 553471
Created a new partition 4 of type 'Linux filesystem' and of size 160 MiB.
Partition #4 contains a ext4 signature.
Do you want to remove the signature? [Y]es/[N]o: n
Command (m for help): p
Disk image.img: 272 MiB, 285212672 bytes, 557056 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: gpt
Disk identifier: 6024F1DE-D798-471C-AC53-16FD356C178C
Device Start End Sectors Size Type
image.img1 49152 49663 512 256K Linux filesystem
image.img2 49664 61951 12288 6M Linux filesystem
image.img3 61952 225791 163840 80M Linux filesystem
image.img4 225792 553471 327680 160M Linux filesystem
Command (m for help): w
The partition table has been altered.
Syncing disks.
然后掛載到loop下
losetup -P /dev/loop404 image.img
掛載分區查看信息是否一致
mkdir /tmp/test && mount /dev/loop404p4 /tmp/test
可見文件系統都在
[/home/lithromantic/Desktop]$ cd /tmp/test
[/tmp/test]$ ls
bin dev etc home lib lost+found mnt overlay proc pseudo_init rdinit rom root run sbin sys tmp usr var
卸載分區,卸載鏡像
umount /tmp/test && losetup -D /dev/loop404
現在我們有了一個可用的dd鏡像,在進行其他步驟前,需要先測試下鏡像是否可用。
結果令人失望,V831沒有任何反應。
猜測是重建gpt分區時破壞了啟動文件。
為了防止設備不兼容gpt分區,通常gpt分區表會內嵌一個mbr分區表,嘗試重構分區。
重構mbr分區
重新dd鏡像,這次直接使用fdisk編輯分區
/home/lithromantic/Desktop]$ fdisk image.img
Welcome to fdisk (util-linux 2.36.1).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): p
Disk image.img: 272 MiB, 285212672 bytes, 557056 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: gpt
Disk identifier: 6024F1DE-D798-471C-AC53-16FD356C178C
Command (m for help): n
Partition number (1-128, default 1):
First sector (34-557022, default 2048): 49152
Last sector, +/-sectors or +/-size{K,M,G,T,P} (49152-557022, default 557022): 49663
Created a new partition 1 of type 'Linux filesystem' and of size 256 KiB.
Command (m for help): n
Partition number (2-128, default 2):
First sector (34-557022, default 51200): 49664
Last sector, +/-sectors or +/-size{K,M,G,T,P} (49664-557022, default 557022): 61951
Created a new partition 2 of type 'Linux filesystem' and of size 6 MiB.
Command (m for help): n
Partition number (3-128, default 3):
First sector (34-557022, default 63488): 61952
Last sector, +/-sectors or +/-size{K,M,G,T,P} (61952-557022, default 557022): 225791
Created a new partition 3 of type 'Linux filesystem' and of size 80 MiB.
Command (m for help): n
Partition number (4-128, default 4):
First sector (34-557022, default 227328): 225792
Last sector, +/-sectors or +/-size{K,M,G,T,P} (225792-557022, default 557022): 553471
Created a new partition 4 of type 'Linux filesystem' and of size 160 MiB.
Partition #4 contains a ext4 signature.
Do you want to remove the signature? [Y]es/[N]o: n
Command (m for help): w
The partition table has been altered.
Syncing disks.
上電,正常啟動
__ ___ _ __ _ / |/ /__ _(_)_ __ / / (_)__ __ ____ __ / /|_/ / _ `/ /\ \ / / /__/ / _ \/ // /\ \ //_/ /_/\_,_/_//_\_\ /____/_/_//_/\_,_//_\_\ ----------------------------------------------root@sipeed:/#
查看分區表:
root@sipeed:/# fdisk -l
Disk /dev/mmcblk0: 29.4 GiB, 31609323520 bytes, 61736960 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x4139124f
Device Boot Start End Sectors Size Id Type
/dev/mmcblk0p1 49152 49663 512 256K 83 Linux
/dev/mmcblk0p2 49664 61951 12288 6M 83 Linux
/dev/mmcblk0p3 61952 225791 163840 80M 83 Linux
/dev/mmcblk0p4 225792 553471 327680 160M 83 Linux
可見分區為dos能正常引導。
但是對該分區表修改沒什么用,實際上還是沒法修改任何信息。
重新dd鏡像
這次嘗試克隆完整鏡像。dd if=/dev/sdb of=./img.img status=progress
創建一個大小為1G的鏡像
dd if=/dev/zero bs=4M count=256 of=test.img status=progress
掛載,並克隆v831鏡像
losetup -P /dev/loop404 test.img
dd if=img.img of=/dev/loop404 status=progress
檢查鏡像,會有錯誤提示
fdisk -l /dev/loop404GPT PMBR size mismatch (983039 != 2097151) will be corrected by write.The backup GPT table is not on the end of the device.Disk /dev/loop404: 1 GiB, 1073741824 bytes, 2097152 sectors
不管,燒錄到鏡像中查看結果
正常啟動,但是會報GPT錯誤,也不管
root@sipeed:/# fdisk -lGPT PMBR size mismatch (983039 != 61736959) will be corrected by w(rite).Disk /dev/mmcblk0: 29.4 GiB, 31609323520 bytes, 61736960 sectorsUnits: sectors of 1 * 512 = 512 bytesSector size (logical/physical): 512 bytes / 512 bytesI/O size (minimum/optimal): 512 bytes / 512 bytesDisklabel type: gptDisk identifier: AB6F3888-569A-4926-9668-80941DCB40BC
新建分區后,磁盤恢復正常
root@sipeed:/# fdisk -l
Disk /dev/mmcblk0: 29.4 GiB, 31609323520 bytes, 61736960 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: gpt
Disk identifier: AB6F3888-569A-4926-9668-80941DCB40BC
Device Start End Sectors Size Type
/dev/mmcblk0p1 49152 49663 512 256K Microsoft basic data
/dev/mmcblk0p2 49664 61951 12288 6M Microsoft basic data
/dev/mmcblk0p3 61952 225791 163840 80M Microsoft basic data
/dev/mmcblk0p4 225792 553471 327680 160M Microsoft basic data
/dev/mmcblk0p5 553472 61736956 61183485 29.2G Linux filesystem
嘗試制作更小的鏡像
497 /home/lithromantic » `dd if=img.img bs=1M count=272 of=/dev/loop404 status=progress`
498 /home/lithromantic » fdisk -l /dev/loop404
GPT PMBR size mismatch (983039 != 573439) will be corrected by write.
Disk /dev/loop404: 280 MiB, 293601280 bytes, 573440 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x00000000
果然,分區表錯誤,並且由於丟失了磁盤末尾的數據,分區也無法查看
Device Boot Start End Sectors Size Id Type/dev/loop404p1 1 573439 573439 280M ee GPT
既然知道數據存在於最后1M字節中,那也dd過來會如何?
515 /home/lithromantic » dd if=img.img skip=980992 of=/dev/loop404 seek=571392 status=progress
516 /home/lithromantic » fdisk /dev/loop404
Welcome to fdisk (util-linux 2.36.1).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): p
Disk /dev/loop404: 280 MiB, 293601280 bytes, 573440 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x00000000
沒任何用。
看來gpt分區情況下,小的可以往大的克隆,大的不能往小的克隆。所以制作鏡像時,切記使用小磁盤制作。
拓展root分區大小
文件系統存在於/dev/mmcblk0p4中,需要調整大小就需要修改此分區大小。
在此之前需要先刪除/dev/mmcblk0p4和以后的分區
假設需要增加到1G,則end扇區為2048*1024+225792=2322944
或者直接+1G
root@sipeed:~# fdisk /dev/mmcblk0
Welcome to fdisk (util-linux 2.25.2).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): d
Partition number (1-4, default 4):
Partition 4 has been deleted.
Command (m for help): n
Partition number (4-8, default 4):
First sector (225792-61736956, default 227328): 225792
Last sector, +sectors or +size{K,M,G,T,P} (225792-61736956, default 61736956): +1G
Created a new partition 4 of type 'Linux filesystem' and of size 1023.8 MiB.
Command (m for help): W
W: unknown command
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
重啟后發現進不去系統了。
在電腦上查看,文件系統沒問題。
重新燒錄一張卡,然后用電腦擴容,啟動
root@sipeed:/# df -h
Filesystem Size Used Available Use% Mounted on
/dev/root 1014.0M 109.4M 888.7M 11% /
tmpfs 29.4M 12.0K 29.4M 0% /tmp
none 29.3M 0 29.3M 0% /dev
/dev/root 1014.0M 109.4M 888.7M 11% /root
基本沒問題。
對比后發現fdisk刪除分區時把Name也刪掉了。
試試加上Name
root@sipeed:/# fdisk /dev/mmcblk0
Command (m for help): x
Expert command (m for help): n
Partition number (1-4, default 4):
New name: rootfs
Partition name changed from '' to 'rootfs'.
Expert command (m for help): r
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
重啟后,正常啟動。
查看分區大小
root@sipeed:/# fdisk -l
Disk /dev/mmcblk0: 29.4 GiB, 31609323520 bytes, 61736960 sectors
Device Start End Sectors Size Type
/dev/mmcblk0p1 49152 49663 512 256K Microsoft basic data
/dev/mmcblk0p2 49664 61951 12288 6M Microsoft basic data
/dev/mmcblk0p3 61952 225791 163840 80M Microsoft basic data
/dev/mmcblk0p4 225792 4419583 4193792 2G Linux filesystem
查看掛載情況
root@sipeed:/# df
Filesystem 1K-blocks Used Available Use% Mounted on
/dev/root 1038360 111984 909992 11% /
tmpfs 30100 12 30088 0% /tmp
none 30028 0 30028 0% /dev
/dev/root 1038360 111984 909992 11% /root
可以看到大小對不上。
resize一下
root@sipeed:/# resize2fs /dev/root
resize2fs 1.42.12 (29-Aug-2014)
Filesystem at /dev/root is mounted on /; on-line resizing required
old_desc_blocks = 1, new_desc_blocks = 1
resize2fs: Read-only file system While checking for on-line resizing support
有問題,失敗。
實際上,這里提示Read-only file system
是因為之前umount過,分區變成了只讀分區,重新掛載下即可。
試試修復下磁盤
root@sipeed:/# e2fsck -f /dev/mmcblk0p4
e2fsck 1.42.12 (29-Aug-2014)
Pass 1: Checking inodes, blocks, and sizes
Inode 7, i_size is 62963712, should be 67174400. Fix<y>? yes
Pass 2: Checking directory structure
Pass 3: Checking directory connectivity
Pass 4: Checking reference counts
Pass 5: Checking group summary information
/dev/mmcblk0p4: ***** FILE SYSTEM WAS MODIFIED *****
/dev/mmcblk0p4: ***** REBOOT LINUX *****
/dev/mmcblk0p4: 4005/24064 files (0.0% non-contiguous), 30550/262144 blocks
修復完成,重啟測試下。
root@sipeed:/# resize2fs /dev/root
resize2fs 1.42.12 (29-Aug-2014)
Filesystem at /dev/root is mounted on /; on-line resizing required
old_desc_blocks = 1, new_desc_blocks = 1
The filesystem on /dev/root is now 524224 (4k) blocks long.
root@sipeed:/# df -h
Filesystem Size Used Available Use% Mounted on
/dev/root 2.0G 109.4M 1.9G 5% /
tmpfs 29.4M 12.0K 29.4M 0% /tmp
none 29.3M 0 29.3M 0% /dev
/dev/root 2.0G 109.4M 1.9G 5% /root
正常使用了。
警告!擴大root分區后不要直接減小分區,否則會導致塊異常而導致無法啟動!並且無法修復!
制作全平台通用分區
實際上就是新建一個Fat格式的分區。
新建分區,直接拉滿。
root@sipeed:/# fdisk /dev/mmcblk0
Command (m for help): n
Partition number (5-8, default 5):
First sector (4419584-61736956, default 4419584):
Last sector, +sectors or +size{K,M,G,T,P} (4419584-61736956, default 61736956):
Created a new partition 5 of type 'Linux filesystem' and of size 27.3 GiB.
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
格式化分區
root@sipeed:/# mkfs.vfat /dev/mmcblk0p5
mkfs.vfat: can't open '/dev/mmcblk0p5': No such file or directory
看樣子需要重啟生效下,reboot。
驗證分區
插電腦上,可以看到windows成功讀取了一個27.3G大小的U盤(H:),
但是同時會多出一個需要格式化的U盤 (G:),這是我們不想看到的。
插上設備,看看是哪里出了問題。
Device Start End Sectors Size Type
/dev/mmcblk0p1 49152 49663 512 256K Microsoft basic data
/dev/mmcblk0p2 49664 61951 12288 6M Microsoft basic data
/dev/mmcblk0p3 61952 225791 163840 80M Microsoft basic data
/dev/mmcblk0p4 225792 4419583 4193792 2G Linux filesystem
/dev/mmcblk0p5 4419584 61736956 57317373 27.3G Linux filesystem
很明顯,4和5分別是G和H磁盤,唯一不一樣的就是文件系統格式,一個是ext4,一個是fat。可以注意到,前三個磁盤並不會被電腦讀取,后兩個和前兩個的type不同,修改下試試。
root@sipeed:/# fdisk /dev/mmcblk0
Welcome to fdisk (util-linux 2.25.2).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): t
Partition number (1-5, default 5):
Partition type (type L to list all types): l
6 Microsoft basic data EBD0A0A2-B9E5-4433-87C0-68B6B72699C7
Partition type (type L to list all types): 6
Changed type of partition 'Linux filesystem' to 'Microsoft basic data'.
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
不能用。
同時注意到新燒錄的鏡像不會出現此問題,上電腦對比下。
可以注意到修改大小后,rootfs的Flags丟失了,添加回來先。
上電后依然無法使用,原因在於Windows已經給此分區分配盤符,手動刪除即可,
但並不是我們所期望的,我們希望用戶拿到鏡像后什么都不干就能用。
找一張新卡復現下。
發現在使用fdisk只修改了分區/dev/mmcblk0p4
后,沒問題。
使用fdisk只修改了分區/dev/mmcblk0p5
后,沒問題。
在修改了GUID后,兩者都不在分配盤符。
root@sipeed:/# fdisk /dev/mmcblk0
Welcome to fdisk (util-linux 2.25.2).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Expert command (m for help): u
Partition number (1-5, default 5): 4
New UUID (in 8-4-4-4-12 format): A0085546-4166-744A-A353-FCA9272B8E48
Partition UUID changed from 3A22EC04-4B57-4945-A295-773995BDA2B0 to A0085546-4166-744A-A353-FCA9272B8E48.
Expert command (m for help): u
Partition number (1-5, default 5): 5
New UUID (in 8-4-4-4-12 format): A0085546-4166-744A-A353-FCA9272B8E49
Partition UUID changed from 742380B9-389D-4908-91F7-2FA2CB6E7195 to A0085546-4166-744A-A353-FCA9272B8E49.
Expert command (m for help): r
Command (m for help): w
把分區5的UUID修改后,就可以正常讀取了。
注意到使用Phoenix card燒錄的UDISK也無法讀取,嘗試修改UUID,發現沒用,同時手動分配盤符時,會提示系統找不到指定的文件,應該是多種參數共同作用的結果,以后再探討。
掛載分區
分區5在電腦上可讀后,還需要再Linux下可讀。
root@sipeed:/# df -h
Filesystem Size Used Available Use% Mounted on
/dev/root 2.0G 109.4M 1.9G 5% /
tmpfs 29.4M 12.0K 29.4M 0% /tmp
none 29.3M 0 29.3M 0% /dev
/dev/root 2.0G 109.4M 1.9G 5% /root
可以看到,現在磁盤還沒掛載。
root@sipeed:/# mount /dev/mmcblk0p5 /mnt
root@sipeed:/# df -h
Filesystem Size Used Available Use% Mounted on
/dev/root 2.0G 109.4M 1.9G 5% /
tmpfs 29.4M 12.0K 29.4M 0% /tmp
none 29.3M 0 29.3M 0% /dev
/dev/root 2.0G 109.4M 1.9G 5% /root
/dev/mmcblk0p5 27.3G 64.0K 27.3G 0% /mnt
掛載后即可使用。
但是手動掛載不是我們想要的,我們期望系統啟動后自動掛載。
實際上,在/etc/init.d/rcS
中,存在by-name掛載磁盤的代碼。
if [ x"$src" == x/dev/by-name/UDISK ]; then
mount -t vfat "$fs_src" "$fs_mntpt" 2>/dev/null
if [ "$?" -ne "0" ]; then
mkfs.vfat "$fs_src" > /dev/null
mount -t vfat "$fs_src" "$fs_mntpt" 2>/dev/null
fi
所以我們只需要修改分區5的name即可。
root@sipeed:/# fdisk /dev/mmcblk0
Welcome to fdisk (util-linux 2.25.2).
Command (m for help): x
Expert command (m for help): n
Partition number (1-5, default 5):
New name: UDISK
Partition name changed from '' to 'UDISK'.
Expert command (m for help): r
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
重啟,成功掛載。
Filesystem Size Used Available Use% Mounted on
/dev/root 2.0G 109.4M 1.9G 5% /
tmpfs 29.4M 12.0K 29.4M 0% /tmp
none 29.3M 0 29.3M 0% /dev
/dev/mmcblk0p5 27.3G 64.0K 27.3G 0% /mnt/UDISK
/dev/mmcblk0p5 27.3G 64.0K 27.3G 0% /root
制作腳本
用戶可選的參數應該有
Filesystem | size | 備注 |
---|---|---|
/dev/root | 用戶指定 | 在沒有/dev/mmcblk0p5的情況下才能調節 |
/dev/mmcblk0p5 | 磁盤剩余所有空間 |
首先要有個選擇菜單
#!/bin/sh
menu()
{
echo "choose you want do:
1):UDISK
2):root
"
read -p "defult 1):" task
task=${task:-1}
if [ "$task" = "2" ];then
read -p "+size{K,M,G,T,P} , such as: +1G
default all size:" size
else
fi
}
引導用戶選擇UDISK后,就要創建UDISK分區了。
創建分區手動方法如下
root@sipeed:/# fdisk /dev/mmcblk0 #打開fdisk
Command (m for help): n #新建分區
Partition number (5-8, default 5): #分區5
First sector (4419584-61736956, default 4419584): #默認大小
Last sector, +sectors or +size{K,M,G,T,P} (4419584-61736956, default 61736956):
Command (m for help): x #擴展功能
Expert command (m for help): n #修改名字
Partition number (1-5, default 5): #分區5
New name: UDISK #新名字
Expert command (m for help): r #退出
Command (m for help): w #保存
顯然不可能引導用戶手動完成這部分,這里可以借助linux管道
echo "n
5
x
n
5
UDISK
r
w
" | fdisk /dev/mmcblk0
顯然這樣寫腳本太不美觀了,我們可以使用 -e來轉譯特殊符號,每個\n即是一個換行符。
echo -e "n\n5\n\n\nx\nn\n5\nUDISK\nr\nw\n" | fdisk /dev/mmcblk0
下一步需要的就是格式化分區為fat,這里牽扯到重啟系統。
我們希望重啟后腳本自動執行,並且下次重啟后腳本不在自動執行。
我們需要先備份一個開機腳本,移除執行權限
cd /etc/init.d
cp rc.final rc.final.bak
chmod -x rc.final.bak
然后rc.final 末尾添加執行我們這個腳本的命令
echo "sh /resize.sh mkfs" >> /etc/init.d/rc.final
其中mkfs是向腳本傳遞參數,可以通過傳入的參數來判斷運行情況。
這時候在我們的菜單外面套一層if [ "$1" != "mkfs" ];then fi
即可確保下次不執行。
重啟后,腳本執行格式化UDISK,並且移除開機自啟動。
mkfs_udisk()
{
mkfs.vfat /dev/mmcblk0p5
cd /etc/init.d
rm rc.final
mv rc.final.bak rc.final
chmod +x rc.final
echo "all ok"
}
然后在我們的菜單中添加該分支
elif [ "$1" = "mkfs" ];then
mkfs_udisk
放入根目錄,執行即可。
在內部調試時,我們可能需要更大的根目錄分區,這時候就要擴大根目錄分區。
在擴容根目錄前,要先刪除UDISK,並且提示用戶,防止文件丟失
detele_udisk()
{
if [ -e /dev/by-name/UDISK ]; then
echo "Warning, UDISK already exists, do you want to delete it?"
read -p "Y(es) or N(o),defult: Y"del_yn
del_yn=${del_yn:-y}
if [ $del_yn = "Y" -o $del_yn = "y" ];then
echo -e "d\n5\nw\n"|fdisk /dev/mmbclk0
else
echo "now stop task"
exit 0
}
然后編寫擴容根目錄的腳本
resize_root()
{
echo -e "d\n4\nn\n4\n225792\n$size\nx\nn\n4\nrootfs\nu\n4\nA0085546-4166-744A-A353-FCA9272B8E49\nr\nw\n"|fdisk /dev/mmbclk0
cd /etc/init.d
cp rc.final rc.final.bak
chmod -x rc.final.bak
echo "sh /resize.sh resize" >> /etc/init.d/rc.final
reboot
}
然后使擴容空間生效
resize2fs_root()
{
resize2fs /dev/root
cd /etc/init.d
rm rc.final
mv rc.final.bak rc.final
chmod +x rc.local
echo "change root size ok"
}
添加函數進菜單選項
elif [ "$select" = "resize" ];then
resize2fs_root
完整腳本如下:
#!/bin/sh
select=$1
select=${select:-begin}
detele_udisk()
{
if [ -e /dev/by-name/UDISK ]; then
echo "Warning, UDISK already exists, do you want to delete it?"
read -p "Y(es) or N(o),defult: Y" del_yn
del_yn=${del_yn:-y}
if [ $del_yn = "Y" -o $del_yn = "y" ];then
echo -e "d\n5\nw\n"|fdisk /dev/mmcblk0
else
echo "now stop task"
exit 0
fi
fi
}
create_UDISK()
{
echo -e "n\n5\n\n\nx\nn\n5\nUDISK\nr\nw\n" | fdisk /dev/mmcblk0
cd /etc/init.d
cp rc.final rc.final.bak
chmod -x rc.final.bak
echo "sh /resize.sh mkfs" >> /etc/init.d/rc.final
reboot
}
mkfs_udisk()
{
mkfs.vfat /dev/mmcblk0p5
cd /etc/init.d
rm rc.final
mv rc.final.bak rc.final
chmod +x rc.final
echo "all ok"
}
resize_root()
{
echo -e "d\n4\nn\n4\n225792\n$size\nx\nn\n4\nrootfs\nu\n4\nA0085546-4166-744A-A353-FCA9272B8E49\nr\nw\n"|fdisk /dev/mmcblk0
cd /etc/init.d
cp rc.final rc.final.bak
chmod -x rc.final.bak
echo "sh /resize.sh resize" >> /etc/init.d/rc.final
reboot
}
resize2fs_root()
{
resize2fs /dev/root
cd /etc/init.d
rm rc.final
mv rc.final.bak rc.final
chmod +x rc.final
echo "change root size ok"
}
menu()
{
echo "your input $select"
if [ "$select" = "begin" ];then
echo "choose you want do:
1):UDISK
2):root
If you want to view your disks on different platforms,you should do 1
IF you just want expand your root filesystem,do 2
maybe you all want,then do 2 before do 1
You will can't change the size of your root filesystem after you get UDISK
"
read -p "defult 1):" task
task=${task:-1}
echo "You choose $task;"
if [ "$task" = "2" ];then
read -p "+size{K,M,G,T,P} , such as: +1G
default all size:" size
detele_udisk
resize_root
else
create_UDISK
fi
elif [ "$select" = "mkfs" ];then
mkfs_udisk
elif [ "$select" = "resize" ];then
resize2fs_root
fi
}
menu
后續補充
在后續使用時發現,完全擴展root分區后,resize會報
resize2fs: Operation not permitted While trying to add group #3
這是由於文件系統中的journal
限制了塊數量
此時需要重新創建journal
umount /dev/sdb4
tune2fs -O ^has_journal /dev/sdb4
tune2fs -j /dev/sdb4
e2fsck -fy /dev/sdb4
resize /dev/sdb4
此時插上板子后root分區才會正常,並且可以繼續增加大小。
但是需要注意的是,以上操作是在電腦端進行的,在831上執行會出問題,暫且不談。
嘗試在dd鏡像時就修改特性。
losetup -P /dev/loop404 test.img
Desktop losetup -P /dev/loop404 test.img
Desktop fdisk /dev/loop404
Welcome to fdisk (util-linux 2.36.1).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): d
Partition number (1-5, default 5):
Partition 5 has been deleted.
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
Syncing disks.
Desktop e2fsck -fyC 0 /dev/loop404p4
e2fsck 1.45.7 (28-Jan-2021)
/dev/loop404p4: recovering journal
Pass 1: Checking inodes, blocks, and sizes
Pass 2: Checking directory structure
Pass 3: Checking directory connectivity
Pass 4: Checking reference counts
Pass 5: Checking group summary information
Padding at end of inode bitmap is not set. Fix? yes
/dev/loop404p4: ***** FILE SYSTEM WAS MODIFIED *****
/dev/loop404p4: 4009/6016 files (0.0% non-contiguous), 29384/51200 blocks
Desktop resize2fs -p /dev/loop404p4
resize2fs 1.45.7 (28-Jan-2021)
The filesystem is already 51200 (4k) blocks long. Nothing to do!
失敗
考慮給root擴容下試試
Desktop losetup -P /dev/loop404 test.img
Desktop fdisk /dev/loop404
Welcome to fdisk (util-linux 2.36.1).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): d
Partition number (1-4, default 4):
Partition 4 has been deleted.
Command (m for help): n
Partition number (4-8, default 4):
First sector (225792-983036, default 227328): 225792
Last sector, +/-sectors or +/-size{K,M,G,T,P} (225792-983036, default 983036): +300M
Created a new partition 4 of type 'Linux filesystem' and of size 299.8 MiB.
Partition #4 contains a ext4 signature.
Do you want to remove the signature? [Y]es/[N]o: y
The signature will be removed by a write command.
Command (m for help): x
Expert command (m for help): n
Partition number (1-4, default 4):
New name: rootfs
Partition name changed from '' to 'rootfs'.
Expert command (m for help): r
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
Syncing disks.
Desktop e2fsck -fyC 0 /dev/loop404p4
e2fsck 1.45.7 (28-Jan-2021)
ext2fs_open2: Bad magic number in super-block
e2fsck: Superblock invalid, trying backup blocks...
Backing up journal inode block information.
Pass 1: Checking inodes, blocks, and sizes
Pass 2: Checking directory structure
Pass 3: Checking directory connectivity
Pass 4: Checking reference counts
Pass 5: Checking group summary information
Free blocks count wrong (0, counted=21816).
Fix? yes
Free inodes count wrong (0, counted=2007).
Fix? yes
/dev/loop404p4: ***** FILE SYSTEM WAS MODIFIED *****
/dev/loop404p4: 4009/6016 files (0.0% non-contiguous), 29384/51200 blocks
Desktop resize2fs -p /dev/loop404p4
resize2fs 1.45.7 (28-Jan-2021)
Resizing the filesystem on /dev/loop404p4 to 76736 (4k) blocks.
The filesystem on /dev/loop404p4 is now 76736 (4k) blocks long.
Desktop losetup -d /dev/loop404
可以使用了
需要注意的是,Last sector, +/-sectors or +/-size{K,M,G,T,P} (225792-983036, default 983036): +300M
這里,如果使用default,會導致windows下燒錄鏡像異常。
制作dd腳本
由於牽扯到電腦端預處理,所以寫個腳本批處理下。
腳本期望功能如下
輸入參數 | 輸出 | 備注 |
---|---|---|
源鏡像位置 | 壓縮包鏡像 | 可以指定任意位置 |
輸出鏡像位置 | 燒錄信息 | 可以指定任意名稱 |
創建接口,存儲輸入參數,同時提醒用戶檢查路徑是否正確
#!/bin/sh
input_addr=$1
output_addr=$2
name=$3
input_addr=${input_addr:-/dev/sdb}
output_addr=${output_addr:-./}
name=${name:-sipeed.img}
read -p "Please confirm the path and image size,must be 512MiB!
Y(es) or other,defult<n>" sure_path
if [ "$sure_path" != "y" -a "$sure_path" != "Y" ];then
echo "exit"
exit 0
fi
然后dd鏡像,並掛載到loop設備中修改並壓縮
sudo dd if=$input_addr status=progress of=/tmp/$name &&\
sudo losetup -d /dev/loop404
sudo losetup -P /dev/loop404 /tmp/$name &&\
sleep 2
echo -e "\n\nd\n5\nd\n4\nn\n4\n225792\n+300M\nx\nn\n4\nrootfs\nr\nw\n"|sudo fdisk /dev/loop404 &&\
sudo e2fsck -fyC 0 /dev/loop404p4 &&\
sleep 2
sudo resize2fs -p /dev/loop404p4
sudo losetup -d /dev/loop404
addr=$(pwd) &&\
cd /tmp &&\
echo "Compressing the mirror takes some time, and you can use <progress -m> at other terminals to see progress" &&\
sudo xz -z -k $name --threads=0 &&\
cd $addr &&\
sudo mv /tmp/$name.xz $output_addr &&\
sudo rm /tmp/$name
實際上,fdisk無法以腳本方式刪除signature,所以分區部分還需要手動執行。
Do you want to remove the signature? [Y]es/[N]o: y
Partition #4 contains a ext4 signature.
簡化腳本,只保留修改分區大小部分。
#!/bin/sh
input_addr=$1
output_addr=$2
name=$3
input_addr=${input_addr:-dd.img}
output_addr=${output_addr:-./}
name=${name:-sipeed.img}
echo "input_addr=$input_addr,output_addr=$output_addr, name is $name
you can run xx.sh <intputaddr> <outputaddr> <name> to specify them or use defult
Such as
dd.sh ./dd.img /root test.img
or
dd.sh ./dd.img"
sudo cp $input_addr /tmp/$name
sudo losetup -d /dev/loop404
sudo losetup -P /dev/loop404 /tmp/$name &&\
sudo e2fsck -fyC 0 /dev/loop404p4 &&\
sleep 2
sudo resize2fs -p /dev/loop404p4
echo -e "\nx\nn\n4\nrootfs\nu\n4\nA0085546-4166-744A-A353-FCA9272B8E48\nr\nw\n"|sudo fdisk /dev/loop404p4
sudo losetup -d /dev/loop404
addr=$(pwd) &&\
cd /tmp &&\
echo "Compressing the mirror takes some time, and you can use <progress -m> at other terminals to see progress" &&\
sudo xz -z -k $name --threads=0 &&\
cd $addr &&\
sudo mv /tmp/$name.xz $output_addr &&\
sudo rm /tmp/$name
echo "all ok,use xz -dc $name.xz |sudo dd of=/dev/sdb bs=1M status=progress oflag=direct to create a tf Startup Disk"
同時人工需要執行的命令如下:
~sudo dd if=/dev/sdb of=dd.img status=progress
~ fdisk dd.img
Welcome to fdisk (util-linux 2.36.1).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): d
Partition number (1-5, default 5):
Partition 5 has been deleted.
Command (m for help): d
Partition number (1-4, default 4): 4
Partition 4 has been deleted.
Command (m for help): n
Partition number (4-8, default 4):
First sector (225792-983036, default 227328): 225792
Last sector, +/-sectors or +/-size{K,M,G,T,P} (225792-983036, default 983036): +300M
Created a new partition 4 of type 'Linux filesystem' and of size 299.8 MiB.
Partition #4 contains a ext4 signature.
Do you want to remove the signature? [Y]es/[N]o: y
The signature will be removed by a write command.
Command (m for help): w
The partition table has been altered.
Syncing disks.
解決。