summaryrefslogtreecommitdiff
path: root/db-4.8.30/test/sec002.tcl
blob: b5c8e355fc9e0ec72865499dd6c3dbec28bb8696 (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
# See the file LICENSE for redistribution information.
#
# Copyright (c) 1999-2009 Oracle.  All rights reserved.
#
# $Id$
#
# TEST	sec002
# TEST	Test of security interface and catching errors in the
# TEST  face of attackers overwriting parts of existing files.
proc sec002 { } {
	global errorInfo
	global errorCode
	global has_crypto

	source ./include.tcl

	# Skip test if release does not support encryption.
	if { $has_crypto == 0 } {
		puts "Skipping test sec002 for non-crypto release."
		return
	}

	set testfile1 $testdir/sec002-1.db
	set testfile2 $testdir/sec002-2.db
	set testfile3 $testdir/sec002-3.db
	set testfile4 $testdir/sec002-4.db

	puts "Sec002: Test of basic encryption interface."
	env_cleanup $testdir

	set passwd1 "passwd1"
	set passwd2 "passwd2"
	set key "key"
	set data "data"
	set pagesize 1024

	#
	# Set up 4 databases, two encrypted, but with different passwords
	# and one unencrypt, but with checksumming turned on and one
	# unencrypted and no checksumming.  Place the exact same data
	# in each one.
	#
	puts "\tSec002.a: Setup databases"
	set db_cmd "-create -pagesize $pagesize -btree "
	set db [eval {berkdb_open} -encryptaes $passwd1 $db_cmd $testfile1]
	error_check_good db [is_valid_db $db] TRUE
	error_check_good dbput [$db put $key $data] 0
	error_check_good dbclose [$db close] 0

	set db [eval {berkdb_open} -encryptaes $passwd2 $db_cmd $testfile2]
	error_check_good db [is_valid_db $db] TRUE
	error_check_good dbput [$db put $key $data] 0
	error_check_good dbclose [$db close] 0

	set db [eval {berkdb_open} -chksum $db_cmd $testfile3]
	error_check_good db [is_valid_db $db] TRUE
	error_check_good dbput [$db put $key $data] 0
	error_check_good dbclose [$db close] 0

	set db [eval {berkdb_open} $db_cmd $testfile4]
	error_check_good db [is_valid_db $db] TRUE
	error_check_good dbput [$db put $key $data] 0
	error_check_good dbclose [$db close] 0

	#
	# If we reopen the normal file with the -chksum flag, there
	# should be no error and checksumming should be ignored.
	# If we reopen a checksummed file without the -chksum flag,
	# checksumming should still be in effect.  [#6959]
	#
	puts "\tSec002.b: Inheritance of chksum properties"
	puts "\t\tSec002.b1: Reopen ordinary file with -chksum flag"
	set db [eval {berkdb_open} -chksum $testfile4]
	error_check_good open_with_chksum [is_valid_db $db] TRUE
	set retdata [$db get $key]
	error_check_good testfile4_get [lindex [lindex $retdata 0] 1] $data
	error_check_good dbclose [$db close] 0

	puts "\t\tSec002.b2: Reopen checksummed file without -chksum flag"
	set db [eval {berkdb_open} $testfile3]
	error_check_good open_wo_chksum [is_valid_db $db] TRUE
	set retdata [$db get $key]
	error_check_good testfile3_get [lindex [lindex $retdata 0] 1] $data
	error_check_good dbclose [$db close] 0

	#
	# First just touch some bits in the file.  We know that in btree
	# meta pages, bytes 92-459 are unused.  Scribble on them in both
	# an encrypted, and both unencrypted files.  We should get
	# a checksum error for the encrypted, and checksummed files.
	# We should get no error for the normal file.
	#
	set fidlist {}
	set fid [open $testfile1 r+]
	lappend fidlist $fid
	set fid [open $testfile3 r+]
	lappend fidlist $fid
	set fid [open $testfile4 r+]
	lappend fidlist $fid

	puts "\tSec002.c: Overwrite unused space in meta-page"
	foreach f $fidlist {
		fconfigure $f -translation binary
		seek $f 100 start
		set byte [read $f 1]
		binary scan $byte c val
		set newval [expr ~$val]
		set newbyte [binary format c $newval]
		seek $f 100 start
		puts -nonewline $f $newbyte
		close $f
	}
	puts "\tSec002.d: Reopen modified databases"
	set stat [catch {berkdb_open_noerr -encryptaes $passwd1 $testfile1} ret]
	error_check_good db:$testfile1 $stat 1
	error_check_good db:$testfile1:fail \
	    [is_substr $ret "metadata page checksum error"] 1

	set stat [catch {berkdb_open_noerr -chksum $testfile3} ret]
	error_check_good db:$testfile3 $stat 1
	error_check_good db:$testfile3:fail \
	    [is_substr $ret "metadata page checksum error"] 1

	set stat [catch {berkdb_open_noerr $testfile4} db]
	error_check_good db:$testfile4 $stat 0
	error_check_good dbclose [$db close] 0

	# Skip the remainder of the test for Windows platforms.
	# Forcing the error which causes DB_RUNRECOVERY to be
	# returned ends up leaving open files that cannot be removed.
	if { $is_windows_test == 1 } {
		cleanup $testdir NULL 1
		puts "Skipping remainder of test for Windows"
		return
	}

	puts "\tSec002.e: Replace root page in encrypted w/ encrypted"
	set fid1 [open $testfile1 r+]
	fconfigure $fid1 -translation binary
	set fid2 [open $testfile2 r+]
	fconfigure $fid2 -translation binary
	seek $fid1 $pagesize start
	seek $fid2 $pagesize start
	fcopy $fid1 $fid2 -size $pagesize
	close $fid1
	close $fid2

	set db [berkdb_open_noerr -encryptaes $passwd2 $testfile2]
	error_check_good db [is_valid_db $db] TRUE
	set stat [catch {$db get $key} ret]
	error_check_good dbget $stat 1
	error_check_good db:$testfile2:fail1 \
	    [is_substr $ret "checksum error"] 1
	set stat [catch {$db close} ret]
	error_check_good dbclose $stat 1
	error_check_good db:$testfile2:fail2 [is_substr $ret "DB_RUNRECOVERY"] 1

	puts "\tSec002.f: Replace root page in encrypted w/ unencrypted"
	set fid2 [open $testfile2 r+]
	fconfigure $fid2 -translation binary
	set fid4 [open $testfile4 r+]
	fconfigure $fid4 -translation binary
	seek $fid2 $pagesize start
	seek $fid4 $pagesize start
	fcopy $fid4 $fid2 -size $pagesize
	close $fid4
	close $fid2

	set db [berkdb_open_noerr -encryptaes $passwd2 $testfile2]
	error_check_good db [is_valid_db $db] TRUE
	set stat [catch {$db get $key} ret]
	error_check_good dbget $stat 1
	error_check_good db:$testfile2:fail \
	    [is_substr $ret "checksum error"] 1
	set stat [catch {$db close} ret]
	error_check_good dbclose $stat 1
	error_check_good db:$testfile2:fail [is_substr $ret "DB_RUNRECOVERY"] 1

	cleanup $testdir NULL 1
}