summaryrefslogtreecommitdiffstats
path: root/tests/mode-test
blob: 81780cd66e066096cb607d074f788ba36e27f7fd (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
#!/bin/bash
#
# Test mode compatibility, check input + kernel and cryptsetup cipher status
#
[ -z "$CRYPTSETUP_PATH" ] && CRYPTSETUP_PATH=".."
CRYPTSETUP=$CRYPTSETUP_PATH/cryptsetup
DEV_NAME=dmc_test
HEADER_IMG=mode-test.img
PASSWORD=3xrododenron
PASSWORD1=$PASSWORD
KEY="7c0dc5dfd0c9191381d92e6ebb3b29e7f0dba53b0de132ae23f5726727173540"
FAST_PBKDF2="--pbkdf pbkdf2 --pbkdf-force-iterations 1000"

# cipher-chainmode-ivopts:ivmode
CIPHERS="aes twofish serpent"
MODES="cbc lrw xts"
IVMODES="null benbi plain plain64 essiv:sha256"

LOOPDEV=$(losetup -f 2>/dev/null)

if [ -n "$CRYPTSETUP_TESTS_RUN_IN_MESON" ]; then
	CRYPTSETUP_VALGRIND=$CRYPTSETUP
else
	CRYPTSETUP_VALGRIND=../.libs/cryptsetup
	CRYPTSETUP_LIB_VALGRIND=../.libs
fi

dmremove() { # device
	udevadm settle >/dev/null 2>&1
	dmsetup remove --retry $1 >/dev/null 2>&1
}

cleanup() {
	[ -b /dev/mapper/"$DEV_NAME"_tstdev ] && dmremove "$DEV_NAME"_tstdev
	[ -b /dev/mapper/$DEV_NAME ] && dmremove $DEV_NAME
	losetup -d $LOOPDEV >/dev/null 2>&1
	rm -f $HEADER_IMG >/dev/null 2>&1
}

fail()
{
	[ -n "$1" ] && echo "$1"
	echo "FAILED backtrace:"
	while caller $frame; do ((frame++)); done
	cleanup
	exit 100
}

skip()
{
	[ -n "$1" ] && echo "$1"
	exit 77
}

function valgrind_setup()
{
	command -v valgrind >/dev/null || fail "Cannot find valgrind."
	[ ! -f $CRYPTSETUP_VALGRIND ] && fail "Unable to get location of cryptsetup executable."
	[ ! -f valg.sh ] && fail "Unable to get location of valg runner script."
	if [ -z "$CRYPTSETUP_TESTS_RUN_IN_MESON" ]; then
		export LD_LIBRARY_PATH="$CRYPTSETUP_LIB_VALGRIND:$LD_LIBRARY_PATH"
	fi
}

function valgrind_run()
{
	INFOSTRING="$(basename ${BASH_SOURCE[1]})-line-${BASH_LINENO[0]}" ./valg.sh ${CRYPTSETUP_VALGRIND} "$@"
}


add_device() {
	cleanup
	dd if=/dev/zero of=$HEADER_IMG bs=1M count=6 >/dev/null 2>&1
	sync
	losetup $LOOPDEV $HEADER_IMG >/dev/null 2>&1
	dmsetup create $DEV_NAME --table "0 10240 linear $LOOPDEV 8" >/dev/null 2>&1
}

dmcrypt_check() # device outstring
{
	X=$(dmsetup table $1 2>/dev/null | sed 's/.*: //' | cut -d' '  -f 4)
	if [ "$X" = $2 ] ; then
		echo -n "[table OK]"
	else
		echo "[table FAIL]"
		echo " Expecting $2 got $X."
		fail
	fi

	X=$($CRYPTSETUP status $1 | grep cipher: | sed s/\.\*cipher:\\s*//)
	if [ $X = $2 ] ; then
		echo -n "[status OK]"
	else
		echo "[status FAIL]"
		echo " Expecting $2 got \"$X\"."
		fail
	fi

	dmremove $1
}

dmcrypt_check_sum() # cipher device
{
	EXPSUM="c036cbb7553a909f8b8877d4461924307f27ecb66cff928eeeafd569c3887e29"
	# Fill device with zeroes and reopen it
	dd if=/dev/zero of=/dev/mapper/$2 bs=1M count=6 >/dev/null 2>&1
	sync
	dmremove $2

	echo $PASSWORD | $CRYPTSETUP create -h sha256 -c $1 -s 256 $2 /dev/mapper/$DEV_NAME >/dev/null 2>&1
	ret=$?
	VSUM=$(sha256sum /dev/mapper/$2 | cut -d' ' -f 1)
	if [ $ret -eq 0 -a "$VSUM" = "$EXPSUM" ] ; then
		echo -n "[OK]"
	else
		echo "[FAIL]"
		echo " Expecting $EXPSUM got $VSUM."
		fail
	fi

	dmremove $2
}

dmcrypt()
{
	OUT=$2
	[ -z "$OUT" ] && OUT=$1
	printf "%-31s" "$1"

	echo $PASSWORD | $CRYPTSETUP create -h sha256 -c $1 -s 256 "$DEV_NAME"_tstdev /dev/mapper/$DEV_NAME >/dev/null 2>&1
	if [ $? -eq 0 ] ; then
		echo -n -e "PLAIN:"
		dmcrypt_check "$DEV_NAME"_tstdev $OUT
	else
		echo -n "[n/a]"
	fi

	echo $PASSWORD | $CRYPTSETUP luksFormat --type luks1 $FAST_PBKDF2 -c $1 -s 256 /dev/mapper/$DEV_NAME >/dev/null 2>&1
	if [ $? -eq 0 ] ; then
		echo -n -e " LUKS1:"
		echo $PASSWORD | $CRYPTSETUP luksOpen /dev/mapper/$DEV_NAME "$DEV_NAME"_tstdev >/dev/null 2>&1 || fail
		dmcrypt_check "$DEV_NAME"_tstdev $OUT
	fi

	echo $PASSWORD | $CRYPTSETUP luksFormat --type luks2 --pbkdf pbkdf2 $FAST_PBKDF2 -c $1 -s 256 --offset 8192 /dev/mapper/$DEV_NAME >/dev/null 2>&1
	if [ $? -eq 0 ] ; then
		echo -n -e " LUKS2:"
		echo $PASSWORD | $CRYPTSETUP luksOpen /dev/mapper/$DEV_NAME "$DEV_NAME"_tstdev >/dev/null 2>&1 || fail
		dmcrypt_check "$DEV_NAME"_tstdev $OUT
	fi

	# repeated device creation must return the same checksum
	echo $PASSWORD | $CRYPTSETUP create -h sha256 -c $1 -s 256 "$DEV_NAME"_tstdev /dev/mapper/$DEV_NAME >/dev/null 2>&1
	if [ $? -eq 0 ] ; then
		echo -n -e " CHECKSUM:"
		dmcrypt_check_sum "$1" "$DEV_NAME"_tstdev
	fi
	echo
}

[ $(id -u) != 0 ] && skip "WARNING: You must be root to run this test, test skipped."
[ -z "$LOOPDEV" ] && skip "Cannot find free loop device, test skipped."
[ ! -x "$CRYPTSETUP" ] && skip "Cannot find $CRYPTSETUP, test skipped."
[ -n "$VALG" ] && valgrind_setup && CRYPTSETUP=valgrind_run

add_device

# compatibility modes
dmcrypt aes aes-cbc-plain
dmcrypt aes-plain aes-cbc-plain

# empty cipher
PASSWORD=""
dmcrypt null cipher_null-ecb
dmcrypt cipher_null cipher_null-ecb
dmcrypt cipher_null-ecb

PASSWORD=$PASSWORD1
# codebook doesn't support IV at all
for cipher in $CIPHERS ; do
	dmcrypt "$cipher-ecb"
done

for cipher in $CIPHERS ; do
	for mode in $MODES ; do
		for ivmode in $IVMODES ; do
			dmcrypt "$cipher-$mode-$ivmode"
		done
	done
done

dmcrypt xchacha12,aes-adiantum-plain64
dmcrypt xchacha20,aes-adiantum-plain64

echo -n "CAPI format:"
echo $PASSWORD | $CRYPTSETUP create -h sha256 -c 'capi:xts(aes)-plain64' -s 256 "$DEV_NAME"_tstdev /dev/mapper/$DEV_NAME || fail
$CRYPTSETUP close "$DEV_NAME"_tstdev || fail
echo $PASSWORD | $CRYPTSETUP create -h sha256 -c 'capi:xts(ecb(aes-generic))-plain64' -s 256 "$DEV_NAME"_tstdev /dev/mapper/$DEV_NAME 2>/dev/null && fail
dmsetup create "$DEV_NAME"_tstdev --table "0 8 crypt capi:xts(ecb(aes-generic))-plain64 $KEY 0 /dev/mapper/$DEV_NAME 0" || fail
$CRYPTSETUP status "$DEV_NAME"_tstdev 2>/dev/null | grep "type:" | grep -q "n/a" || fail
$CRYPTSETUP close "$DEV_NAME"_tstdev 2>/dev/null || fail
echo [OK]

cleanup