xref: /sqlite-3.40.0/test/lock_common.tcl (revision e264d983)
1*e264d983Sdan# 2010 April 14
2*e264d983Sdan#
3*e264d983Sdan# The author disclaims copyright to this source code.  In place of
4*e264d983Sdan# a legal notice, here is a blessing:
5*e264d983Sdan#
6*e264d983Sdan#    May you do good and not evil.
7*e264d983Sdan#    May you find forgiveness for yourself and forgive others.
8*e264d983Sdan#    May you share freely, never taking more than you give.
9*e264d983Sdan#
10*e264d983Sdan#***********************************************************************
11*e264d983Sdan# This file contains code used by several different test scripts. The
12*e264d983Sdan# code in this file allows testfixture to control another process (or
13*e264d983Sdan# processes) to test locking.
14*e264d983Sdan#
15*e264d983Sdan
16*e264d983Sdan# Launch another testfixture process to be controlled by this one. A
17*e264d983Sdan# channel name is returned that may be passed as the first argument to proc
18*e264d983Sdan# 'testfixture' to execute a command. The child testfixture process is shut
19*e264d983Sdan# down by closing the channel.
20*e264d983Sdanproc launch_testfixture {} {
21*e264d983Sdan  set prg [info nameofexec]
22*e264d983Sdan  if {$prg eq ""} {
23*e264d983Sdan    set prg [file join . testfixture]
24*e264d983Sdan  }
25*e264d983Sdan  set chan [open "|$prg tf_main.tcl" r+]
26*e264d983Sdan  fconfigure $chan -buffering line
27*e264d983Sdan  return $chan
28*e264d983Sdan}
29*e264d983Sdan
30*e264d983Sdan# Execute a command in a child testfixture process, connected by two-way
31*e264d983Sdan# channel $chan. Return the result of the command, or an error message.
32*e264d983Sdanproc testfixture {chan cmd} {
33*e264d983Sdan  puts $chan $cmd
34*e264d983Sdan  puts $chan OVER
35*e264d983Sdan  set r ""
36*e264d983Sdan  while { 1 } {
37*e264d983Sdan    set line [gets $chan]
38*e264d983Sdan    if { $line == "OVER" } {
39*e264d983Sdan      return $r
40*e264d983Sdan    }
41*e264d983Sdan    if {[eof $chan]} {
42*e264d983Sdan      return "ERROR: Child process hung up"
43*e264d983Sdan    }
44*e264d983Sdan    append r $line
45*e264d983Sdan  }
46*e264d983Sdan}
47*e264d983Sdan
48*e264d983Sdan# Write the main loop for the child testfixture processes into file
49*e264d983Sdan# tf_main.tcl. The parent (this script) interacts with the child processes
50*e264d983Sdan# via a two way pipe. The parent writes a script to the stdin of the child
51*e264d983Sdan# process, followed by the word "OVER" on a line of its own. The child
52*e264d983Sdan# process evaluates the script and writes the results to stdout, followed
53*e264d983Sdan# by an "OVER" of its own.
54*e264d983Sdanset f [open tf_main.tcl w]
55*e264d983Sdanputs $f {
56*e264d983Sdan  set l [open log w]
57*e264d983Sdan  set script ""
58*e264d983Sdan  while {![eof stdin]} {
59*e264d983Sdan    flush stdout
60*e264d983Sdan    set line [gets stdin]
61*e264d983Sdan    puts $l "READ $line"
62*e264d983Sdan    if { $line == "OVER" } {
63*e264d983Sdan      catch {eval $script} result
64*e264d983Sdan      puts $result
65*e264d983Sdan      puts $l "WRITE $result"
66*e264d983Sdan      puts OVER
67*e264d983Sdan      puts $l "WRITE OVER"
68*e264d983Sdan      flush stdout
69*e264d983Sdan      set script ""
70*e264d983Sdan    } else {
71*e264d983Sdan      append script $line
72*e264d983Sdan      append script " ; "
73*e264d983Sdan    }
74*e264d983Sdan  }
75*e264d983Sdan  close $l
76*e264d983Sdan}
77*e264d983Sdanclose $f
78