1#!/bin/sh
2
3PERSIST_BLK='/dev/block/by-name/persist'
4EFS_BLK='/dev/block/by-name/efs'
5MNT_BASE='/mnt/product'
6MNT_OLD="$MNT_BASE/convert_old"
7MNT_NEW="$MNT_BASE/convert_new"
8
9function log() {
10	if [ ! -z "$1" ]; then
11		echo "partition_convert: $1" > /dev/kmsg
12	fi
13}
14
15function check_success() {
16	RES=$?
17	if [ $RES -ne 0 ]; then
18		log "Failed: $1"
19	else
20		log "Success: $1"
21	fi
22	return $RES
23}
24
25function get_fs_type()
26{
27	BLOCK=$1
28	EXT4_MAGIC=$(xxd $BLOCK -s 0x438 -l 2 -p)
29	if [ "$EXT4_MAGIC" = "53ef" ]; then
30		 echo "ext4"
31	else
32		F2FS_MAGIC=$(xxd $BLOCK -s 0x400 -l 4 -p)
33		if [ "$F2FS_MAGIC" = "1020f5f2" ]; then
34			echo "f2fs"
35		else
36			echo "unknown"
37		fi
38	fi
39}
40
41# Flow:
42# 1. If persist is f2fs we need to make efs ext4 and copy out the files. Once files are copied
43# successfully, format persist as ext4 to mark completion of step.
44# 2. If persist is ext4 and efs is ext4, we need to copy from efs to persist (use dd). Once
45# everything is copied successfully, erase efs to allow it to be formatted to f2fs later.
46# 3. If persist is ext4 and efs is not ext4, we have already migrated - do nothing.
47
48# If persist is already ext4 and efs is not ext4 we have already migrated.
49PERSIST_FS=$(get_fs_type $PERSIST_BLK)
50EFS_FS=$(get_fs_type $EFS_BLK)
51if [ "$PERSIST_FS" = "ext4" ]; then
52	if [ "$EFS_FS" != "ext4" ]; then
53		log "persist ext4 migration already done"
54		exit 0
55	fi
56fi
57
58if [ "$PERSIST_FS" = "unknown" ]; then
59	log "persist partition hasn't been initialized"
60	exit 0
61fi
62
63RETRIES=10
64while [[ $RETRIES -gt 0 ]]; do
65	# Sleep for 1 second here, as other failure points will trigger continue
66	sleep 1
67	RETRIES=$((RETRIES-1))
68
69	# If persist is still f2fs, we need to copy to efs.
70	if [ "$PERSIST_FS" = "f2fs" ]; then
71		# Format efs as ext4
72		/system/bin/mke2fs -t ext4 -b 4096 $EFS_BLK
73		check_success "/system/bin/mke2fs -t ext4 -b 4096 $EFS_BLK"
74		if [ $? -ne 0 ]; then
75			continue
76		fi
77
78		#Create directory to mount persist partition
79		mkdir -p $MNT_OLD
80		check_success "mkdir $MNT_OLD"
81		if [ $? -ne 0 ]; then
82			continue
83		fi
84
85		# Create directory to mount efs partition
86		mkdir -p $MNT_NEW
87		check_success "mkdir $MNT_NEW"
88		if [ $? -ne 0 ]; then
89			rm -rf $MNT_OLD
90			continue
91		fi
92
93		# Mount persist
94		mount -t f2fs $PERSIST_BLK $MNT_OLD
95		check_success "mount -t f2fs $PERSIST_BLK $MNT_OLD"
96		if [ $? -ne 0 ]; then
97			rm -rf $MNT_NEW
98			rm -rf $MNT_OLD
99			continue
100		fi
101
102		# Mount efs
103		mount -t ext4 $EFS_BLK $MNT_NEW
104		check_success "mount -t ext4 $EFS_BLK $MNT_NEW"
105		if [ $? -ne 0 ]; then
106			umount $MNT_OLD
107			rm -rf $MNT_NEW
108			rm -rf $MNT_OLD
109			continue
110		fi
111
112		cp -rp $MNT_OLD/.* $MNT_NEW/
113		cp -rp $MNT_OLD/* $MNT_NEW/
114		check_success "cp -rp $MNT_OLD/* $MNT_NEW/"
115		if [ $? -ne 0 ]; then
116			umount $MNT_NEW
117			umount $MNT_OLD
118			rm -rf $MNT_NEW
119			rm -rf $MNT_OLD
120			continue
121		fi
122
123		# Calculate md5sum of all files and compare between persist and efs
124		(cd $MNT_NEW; find . -type f | xargs md5sum | sort) > $MNT_BASE/new.md5sums
125		(cd $MNT_OLD; find . -type f | xargs md5sum | sort) > $MNT_BASE/old.md5sums
126		diff $MNT_BASE/new.md5sums $MNT_BASE/old.md5sums
127		check_success "diff $MNT_BASE/new.md5sums $MNT_BASE/old.md5sums"
128		RES=$?
129		rm $MNT_BASE/new.md5sums $MNT_BASE/old.md5sums
130
131		umount $MNT_NEW
132		umount $MNT_OLD
133		rm -rf $MNT_NEW
134		rm -rf $MNT_OLD
135
136		if [ $RES -ne 0 ]; then
137			continue
138		fi
139
140		/system/bin/mke2fs -t ext4 -b 4096 $PERSIST_BLK
141		check_success "/system/bin/mke2fs -t ext4 -b 4096 $PERSIST_BLK"
142		if [ $? -ne 0 ]; then
143			continue
144		fi
145
146		PERSIST_FS="ext4"
147	fi
148
149	# copy efs to persist
150	dd if=$EFS_BLK of=$PERSIST_BLK
151	check_success "dd if=$EFS_BLK of=$PERSIST_BLK"
152	if [ $? -ne 0 ]; then
153		continue
154	fi
155
156	sync
157	check_success "sync"
158	if [ $? -ne 0 ]; then
159		continue
160	fi
161
162	# compare md5sum for integrity
163	EFS_MD5SUM=$(dd if=$EFS_BLK 2>/dev/null | md5sum)
164	PERSIST_MD5SUM=$(dd if=$PERSIST_BLK 2>/dev/null | md5sum)
165	if [ "$PERSIST_MD5SUM" != "$EFS_MD5SUM" ]; then
166		log "dd md5sum mismatch"
167		continue
168	fi
169
170	dd if=/dev/zero of=$EFS_BLK bs=1M count=64
171	check_success "dd if=/dev/zero of=$EFS_BLK bs=1M count=64"
172	if [ $? -ne 0 ]; then
173		continue
174	fi
175
176	log "Migration succeeded"
177	break
178done
179