recd008.tcl
上传用户:tsgydb
上传日期:2007-04-14
资源大小:10674k
文件大小:6k
源码类别:

MySQL数据库

开发平台:

Visual C++

  1. # See the file LICENSE for redistribution information.
  2. #
  3. # Copyright (c) 1996, 1997, 1998, 1999, 2000
  4. # Sleepycat Software.  All rights reserved.
  5. #
  6. # $Id: recd008.tcl,v 1.22 2000/12/07 19:13:46 sue Exp $
  7. #
  8. # Recovery Test 8.
  9. # Test deeply nested transactions and many-child transactions.
  10. proc recd008 { method {breadth 4} {depth 4} args} {
  11. global kvals
  12. source ./include.tcl
  13. set args [convert_args $method $args]
  14. set omethod [convert_method $method]
  15. if { [is_record_based $method] == 1 } {
  16. puts "Recd008 skipping for method $method"
  17. return
  18. }
  19. puts "Recd008: $method $breadth X $depth deeply nested transactions"
  20. # Create the database and environment.
  21. env_cleanup $testdir
  22. set dbfile recd008.db
  23. puts "tRecd008.a: create database"
  24. set db [eval {berkdb_open -create} $args $omethod $testdir/$dbfile]
  25. error_check_good dbopen [is_valid_db $db] TRUE
  26. # Make sure that we have enough entries to span a couple of
  27. # different pages.
  28. set did [open $dict]
  29. set count 0
  30. while { [gets $did str] != -1 && $count < 1000 } {
  31. if { [string compare $omethod "-recno"] == 0 } {
  32. set key [expr $count + 1]
  33. } else {
  34. set key $str
  35. }
  36. if { $count == 500} {
  37. set p1 $key
  38. set kvals($p1) $str
  39. }
  40. set ret [$db put $key $str]
  41. error_check_good put $ret 0
  42. incr count
  43. }
  44. close $did
  45. error_check_good db_close [$db close] 0
  46. set txn_max [expr int([expr pow($breadth,$depth)])]
  47. if { $txn_max < 20 } {
  48. set txn_max 20
  49. }
  50. puts "tRecd008.b: create environment for $txn_max transactions"
  51. set eflags "-mode 0644 -create -txn_max $txn_max 
  52.     -txn -home $testdir"
  53. set env_cmd "berkdb env $eflags"
  54. set dbenv [eval $env_cmd]
  55. error_check_good env_open [is_valid_env $dbenv] TRUE
  56. reset_env $dbenv
  57. set rlist {
  58. { {recd008_parent abort ENV DB $p1 TXNID 1 1 $breadth $depth}
  59. "Recd008.c: child abort parent" }
  60. { {recd008_parent commit ENV DB $p1 TXNID 1 1 $breadth $depth}
  61. "Recd008.d: child commit parent" }
  62. }
  63. foreach pair $rlist {
  64. set cmd [subst [lindex $pair 0]]
  65. set msg [lindex $pair 1]
  66. op_recover abort $testdir $env_cmd $dbfile $cmd $msg
  67. recd008_setkval $dbfile $p1
  68. op_recover commit $testdir $env_cmd $dbfile $cmd $msg
  69. recd008_setkval $dbfile $p1
  70. }
  71. puts "tRecd008.e: Verify db_printlog can read logfile"
  72. set tmpfile $testdir/printlog.out
  73. set stat [catch {exec $util_path/db_printlog -h $testdir 
  74.     > $tmpfile} ret]
  75. error_check_good db_printlog $stat 0
  76. fileremove $tmpfile
  77. }
  78. proc recd008_setkval { dbfile p1 } {
  79. global kvals
  80. source ./include.tcl
  81. set db [berkdb_open $testdir/$dbfile]
  82. error_check_good dbopen [is_valid_db $db] TRUE
  83. set ret [$db get $p1]
  84. set kvals($p1) [lindex [lindex $ret 0] 1]
  85. }
  86. # This is a lot like the op_recover procedure.  We cannot use that
  87. # because it was not meant to be called recursively.  This proc
  88. # knows about depth/breadth and file naming so that recursive calls
  89. # don't overwrite various initial and afterop files, etc.
  90. #
  91. # The basic flow of this is:
  92. # (Initial file)
  93. # Parent begin transaction (in op_recover)
  94. # Parent starts children
  95. # Recursively call recd008_recover
  96. # (children modify p1)
  97. # Parent modifies p1
  98. # (Afterop file)
  99. # Parent commit/abort (in op_recover)
  100. # (Final file)
  101. # Recovery test (in op_recover)
  102. proc recd008_parent { op env db p1key parent b0 d0 breadth depth } {
  103. global kvals
  104. source ./include.tcl
  105. #
  106. # Save copy of original data
  107. # Acquire lock on data
  108. #
  109. set olddata $kvals($p1key)
  110. set ret [$db get -rmw -txn $parent $p1key]
  111. set Dret [lindex [lindex $ret 0] 1]
  112. error_check_good get_parent_RMW $Dret $olddata
  113. #
  114. # Parent spawns off children
  115. #
  116. set ret [recd008_txn $op $env $db $p1key $parent 
  117.     $b0 $d0 $breadth $depth]
  118. puts "Child runs complete.  Parent modifies data."
  119. #
  120. # Parent modifies p1
  121. #
  122. set newdata $olddata.parent
  123. set ret [$db put -txn $parent $p1key $newdata]
  124. error_check_good db_put $ret 0
  125. #
  126. # Save value in kvals for later comparison
  127. #
  128. switch $op {
  129. "commit" {
  130. set kvals($p1key) $newdata
  131. }
  132. "abort" {
  133. set kvals($p1key) $olddata
  134. }
  135. }
  136. return 0
  137. }
  138. proc recd008_txn { op env db p1key parent b0 d0 breadth depth } {
  139. global log_log_record_types
  140. global kvals
  141. source ./include.tcl
  142. for {set d 1} {$d < $d0} {incr d} {
  143. puts -nonewline "t"
  144. }
  145. puts "Recd008_txn: $op parent:$parent $breadth $depth ($b0 $d0)"
  146. # Save the initial file and open the environment and the file
  147. for {set b $b0} {$b <= $breadth} {incr b} {
  148. #
  149. # Begin child transaction
  150. #
  151. set t [$env txn -parent $parent]
  152. error_check_bad txn_begin $t NULL
  153. error_check_good txn_begin [is_valid_txn $t $env] TRUE
  154. set startd [expr $d0 + 1]
  155. set child $b:$startd:$t
  156. set olddata $kvals($p1key)
  157. set newdata $olddata.$child
  158. set ret [$db get -rmw -txn $t $p1key]
  159. set Dret [lindex [lindex $ret 0] 1]
  160. error_check_good get_parent_RMW $Dret $olddata
  161. #
  162. # Recursively call to set up nested transactions/children
  163. #
  164. for {set d $startd} {$d <= $depth} {incr d} {
  165. set ret [recd008_txn commit $env $db $p1key $t 
  166.     $b $d $breadth $depth]
  167. set ret [recd008_txn abort $env $db $p1key $t 
  168.     $b $d $breadth $depth]
  169. }
  170. #
  171. # Modifies p1.
  172. #
  173. set ret [$db put -txn $t $p1key $newdata]
  174. error_check_good db_put $ret 0
  175. #
  176. # Commit or abort
  177. #
  178. for {set d 1} {$d < $startd} {incr d} {
  179. puts -nonewline "t"
  180. }
  181. puts "Executing txn_$op:$t"
  182. error_check_good txn_$op:$t [$t $op] 0
  183. for {set d 1} {$d < $startd} {incr d} {
  184. puts -nonewline "t"
  185. }
  186. set ret [$db get -rmw -txn $parent $p1key]
  187. set Dret [lindex [lindex $ret 0] 1]
  188. switch $op {
  189. "commit" {
  190. puts "Command executed and committed."
  191. error_check_good get_parent_RMW $Dret $newdata
  192. set kvals($p1key) $newdata
  193. }
  194. "abort" {
  195. puts "Command executed and aborted."
  196. error_check_good get_parent_RMW $Dret $olddata
  197. set kvals($p1key) $olddata
  198. }
  199. }
  200. }
  201. return 0
  202. }