# experiment run control global MIDAS_DataAcquisitionControlServer_Verbose set MIDAS_DataAcquisitionControlServer_Verbose 0 variable MaxTries 20 variable SYS_DataAcquisitionCode 0 variable SYS_PrevDataAcquisitionCode 0 variable SYS_DataAcquisitionArgs 0 variable RunControlDelay1 100 variable RunControlDelay2 50 variable RunControlDelay3 500 variable Options global SpectraHandle -1 variable Supported_Modules {} foreach module $Supported_Modules { set Options(Include.$module) 1 set Options(Histogram.$module) 1 } # list of registers required by the UI variable registerlist set registerlist {} lappend registerlist [list NetVar.EXEC.Action "-n EXEC_Action -t int"] lappend registerlist [list NetVar.EXEC.Parameter "-n EXEC_Parameter -t string"] lappend registerlist [list NetVar.EXEC.ID "-n EXEC_ID -t string"] lappend registerlist [list NetVar.TS_Server "-n TS_Server -t string"] lappend registerlist [list NetVar.TS_Port "-n TS_Port -t int"] lappend registerlist [list NetVar.Xfer_Option "-n Xfer_Option -t int"] lappend registerlist [list NetVar.Format_Option "-n Format_Option -t int"] lappend registerlist [list NetVar.TS2_Server "-n TS2_Server -t string"] lappend registerlist [list NetVar.TS2_Port "-n TS2_Port -t int"] lappend registerlist [list NetVar.RawDataStorage "-n RawDataStorage -t string"] lappend registerlist [list NetVar.EXEC.Response "-n EXEC_Response -t block -a yes -i 0 -l 2048 -f x"] lappend registerlist [list NetVar.EXEC.PID "-n PID_EXEC -t int"] lappend registerlist [list NetVar.DACQ.CAlive "-n DACQ_Alive -t int"] lappend registerlist [list NetVar.DACQ.Ctxenable "-n DACQ_TxEnable -t int"] lappend registerlist [list NetVar.DACQ.Ctx2enable "-n DACQ_Tx2Enable -t int"] lappend registerlist [list NetVar.DACQ.Crdoutenable "-n DACQ_RdOutEnable -t int"] lappend registerlist [list NetVar.DACQ.Chistenable "-n DACQ_HistEnable -t int"] lappend registerlist [list NetVar.DACQ.Chistmode "-n DACQ_HistMode -t int"] lappend registerlist [list NetVar.DACQ.Cspectramapped "-n DACQ_SpectraMapped -t int"] lappend registerlist [list NetVar.DACQ.Ctrace "-n DACQ_Trace -t int"] lappend registerlist [list NetVar.DACQ.Sstate "-n DACQ_State -t int"] lappend registerlist [list NetVar.DACQ.TestMode "-n DACQ_TestMode -t int"] lappend registerlist [list NetVar.DACQ.DebugMode1 "-n DACQ_DebugMode1 -t int"] lappend registerlist [list NetVar.DACQ.DebugMode2 "-n DACQ_DebugMode2 -t int"] lappend registerlist [list NetVar.DACQ.DebugMode3 "-n DACQ_DebugMode3 -t int"] lappend registerlist [list NetVar.DACQ.DebugMode4 "-n DACQ_DebugMode4 -t int"] lappend registerlist [list NetVar.DACQ.ReadOutOption "-n DACQ_ReadOutOption -t int"] lappend registerlist [list NetVar.DACQ.DelayTicks "-n DACQ_DelayTicks -t int"] lappend registerlist [list NetVar.DACQ.PollTicks "-n DACQ_PollTicks -t int"] lappend registerlist [list NetVar.DACQ.StatsTime "-n DACQ_StatsTime -t int"] lappend registerlist [list NetVar.DACQ.Stats0 "-n DACQ_Stats -t block -a yes -i 0 -l 512 -f d"] lappend registerlist [list NetVar.DACQ.Rates0 "-n DACQ_Rates -t block -a yes -i 0 -l 512 -f d"] for {set i 1} {$i <= 24} {incr i} { lappend registerlist [list NetVar.DACQ.Stats$i "-n DACQ_Stats$i -t block -a yes -i 0 -l 512 -f d"] lappend registerlist [list NetVar.DACQ.Rates$i "-n DACQ_Rates$i -t block -a yes -i 0 -l 512 -f d"] } lappend registerlist [list NetVar.UseGroup "-n DACQ_UseGroup -t int"] proc make-UIregisters {} { variable registerlist set rc [catch {ReadNetVar NetVar.EXEC.ID} m] if {$rc == 0} return if {$rc == 1 || $m == 0x10004} { foreach item $registerlist { CreateNetVar [first $item] [second $item] } set rc1 [catch {CreateSigTask SigTask.EXEC.Usr1 "-t EXEC -s USR1"} m1] set rc2 [catch {CreateSigTask SigTask.EXEC.Usr2 "-t EXEC -s USR2"} m2] puts "created SigTask registers $rc1 $m1 $rc2 $m2" puts "Created UI registers" } else { puts "make-UIregisters returns rc=$rc and $m" } } proc Set_Options {} { variable Options LoadOptions if {![info exists Options(Rate.channels)]} {set Options(Rate.channels) 1024} if {![info exists Options(Stat.channels)]} {set Options(Stat.channels) 1024} if {![info exists Options(Stat.shift)]} {set Options(Stat.shift) 0} if {![info exists Options(Stat.offset)]} {set Options(Stat.offset) 0} SaveOptions } proc DataAcqCommand {args} { variable MaxTries variable RunControlDelay2 variable RunControlDelay3 # first action # second message # third parameter # fourth signal number # fifth task name puts "DataAcqCommand [first $args] [second $args]" # step 1 setup action and send message to task if {[llength $args] > 4} then {set TASK [fifth $args]} else {set TASK EXEC} set pid [ReadNetVar NetVar.$TASK.PID] if {[llength $args] > 2} {WriteNetVar NetVar.$TASK.Parameter [third $args]} WriteNetVar NetVar.$TASK.Action [first $args] if {[llength $args] > 3} { WriteSigTaskAttr SigTask.$TASK.Usr[fourth $args] "-t $pid" WriteSigTask SigTask.$TASK.Usr[fourth $args] 0 } else { WriteSigTaskAttr SigTask.$TASK.Usr1 "-t $pid" WriteSigTask SigTask.$TASK.Usr1 0 } after $RunControlDelay2 # step 2 wait for action to be completed and response received if {[llength $args] > 1} {set msg "[second $args]"} else {set msg ""} set tries 1 while {$tries < $MaxTries} { if {[llength $args] == 0} then { puts "Waiting for action to complete ($tries)" } else { if {[llength $args] > 1} then { puts "[second $args] ($tries)" } else { puts "[first $args] ($tries)" } } set z [catch {ReadNetVar NetVar.$TASK.Action} m ] if {$z != 0} then { puts "Unable to confirm state of action\n$m" return 1 } if {$m == 0} then {return 0} incr tries after $RunControlDelay3 } puts "Action has not completed\nGiving up waiting" return 1 } proc CreateSpectrum1D {Name Range} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecNew1D $Name 0 $Range} Wmsg] if {$z == 0} { # puts "SpecNew1D returned: [lindex $Wmsg 5]" set errorCode 0 } else { puts "SpecNew1D failed: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc DeleteSpectrum {Name} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecDelete $Name} Wmsg] if {$z == 0} { # puts "SpecDelete returned: [lindex $Wmsg 5]" set errorCode 0 } else { puts "SpecDelete failed for $Name: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc ZeroSpectrum {Name} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecZero $Name} Wmsg] if {$z == 0} { # puts "SpecZero returned: [lindex $Wmsg 5]" set errorCode 0 } else { puts "SpecZero failed for $Name: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc SpectrumPutTitle {Name Label} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecPutTitle $Name $Label} Wmsg] if {$z == 0} { # puts "SpecPutTitle returned: [lindex $Wmsg 5]" set errorCode 0 } else { puts "SpecPutTitle failed: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc SpectrumGetTitle {Name} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecGetTitle $Name} Wmsg] if {$z == 0} { # puts "SpecGetTitle returned: [lindex $Wmsg 5]" set errorCode 0 return [lindex $Wmsg 5] } else { puts "SpecGetTitle failed: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc SpectrumDetails {Name} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecDetails $Name} Wmsg] if {$z == 0} { # puts "SpecDetails returned: [lindex $Wmsg 5]" set errorCode 0 return [lindex $Wmsg 5] } else { puts "SpecDetails failed: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc SpectrumRead1D {Name Base Range} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecRead1DText $Name $Base $Range} Wmsg] if {$z == 0} { # puts "SpecRead1D returned: [lindex $Wmsg 5]" set errorCode 0 return [lindex $Wmsg 5] } else { puts "SpecRead1D failed: Code= $errorCode; Info= [first [split $errorInfo \n]]" } return $errorCode } proc SpectrumNames {{pattern *}} { global errorCode errorInfo variable Wmsg set z [catch {::namespace inscope ::urn:SpectrumService SpecNames $pattern} Wmsg] if {$z == 0} { # puts "SpecNames returned: [lindex $Wmsg 5]" set errorCode 0 return [lindex $Wmsg 5] } else { puts "SpecNames failed: Code= $errorCode; Info= [first [split $errorInfo \n]]" return $errorCode } } proc map_spectrum {p} { upvar #0 SpectraHandle f puts $f $p } proc map_spectra {} { global env DataAcqCommand 4 "Mapping spectra" [file join $env(MIDASTempDir) SpectraDefs.dat] } proc unmap_spectra {} { DataAcqCommand 8 "Unmapping spectra" } proc delete_spectra {} { set spectra [SpectrumNames] foreach item $spectra { set name [second $item] DeleteSpectrum $name } } proc create_spectra {} { global env variable Options upvar #0 SpectraHandle f set SpectraDefs [file join $env(MIDASTempDir) SpectraDefs.dat] set z [catch {open $SpectraDefs w} f] if {$z != 0} then { puts "Cannot open file $SpectraDefs\n$f" } set range $Options(Stat.channels) set z [catch {CreateSpectrum1D Stat $range} m] map_spectrum "Stat 0 0 0 $Options(Stat.shift)" set range $Options(Rate.channels) set z [catch {CreateSpectrum1D Rate $range} m] Create_1D_Histograms close $f } proc Create_1D_Histograms {} { variable Options variable Supported_Modules foreach module $Supported_Modules { if {$Options(Include.$module) == 1 && $Options(Histogram.$module) == 1} then { create_[set module]_spectra } } } proc DataAcqState {} { set state [expr [ReadNetVar NetVar.DACQ.Sstate] - 1] if {$state < 0 || $state > 9} {set state 8} return $state } proc doSetUp {} { variable Options puts "executing generic doSetUp" Set_Options; make-UIregisters DataAcqCommand 1 "Halt" unmap_spectra delete_spectra create_spectra map_spectra Setup_Electronics DataAcqCommand 3 "Setup" WriteNetVar NetVar.DACQ.PollTicks 100 WriteNetVar NetVar.DACQ.Crdoutenable 1 ;# enable data readout puts "completed generic doSetUp" } proc doReset {} { puts "executing generic doReset" Set_Options; make-UIregisters DataAcqCommand 9 "Reset" Reset_Electronics puts "completed generic doReset" } proc doStop {} { puts "executing generic doStop" Set_Options; make-UIregisters Stop_Electronics DataAcqCommand 1 "Halt" if {[ReadNetVar NetVar.DACQ.Ctxenable] == 1} { DataAcqCommand 1 "disconnect xfer stream #0" 0 2 } if {[ReadNetVar NetVar.DACQ.Ctx2enable] == 1} { DataAcqCommand 2 "disconnect xfer stream #1" 0 2 } puts "completed generic doStop" } proc doGo {} { puts "executing generic doGo" Set_Options; make-UIregisters # DataAcqCommand 13 "set verbose option" 0 2 # DataAcqCommand 14 "unset verbose option" 0 2 if {[ReadNetVar NetVar.DACQ.Ctxenable] == 1} { DataAcqCommand 3 "connect xfer stream #0" 0 2 } if {[ReadNetVar NetVar.DACQ.Ctx2enable] == 1} { DataAcqCommand 6 "connect xfer stream #1" 0 2 } Reset_Electronics DataAcqCommand 2 "Go" Go_Electronics puts "completed generic doGo" } proc Stop_Electronics {} { variable Supported_Modules foreach m $Supported_Modules {[set m]_DAQ-halt} } proc Go_Electronics {} { variable Supported_Modules foreach m $Supported_Modules {[set m]_DAQ-go} } proc Reset_Electronics {} { ;# used by RESET variable Supported_Modules foreach m $Supported_Modules {[set m]_DAQ-reset} } proc Setup_Electronics {} { ;# used by SETUP variable Supported_Modules foreach m $Supported_Modules {[set m]_DAQ-setup} } proc ClearConfig {} {DataAcqCommand 12 "Clear Configuration"} proc DefineConfig {s} {DataAcqCommand 13 "Define Configuration" "$s"} proc DumpRawData {} {} proc TerminateExec {} { unmap_spectra DataAcqCommand 22 "Terminating DataAcq program" 0 2 } proc LoadExec {} {puts "A custom LoadExec is required for this project"}