source: fact/tools/PyDimCtrl/ScriptsForPyDimCtrl.py@ 14460

Last change on this file since 14460 was 14460, checked in by neise, 12 years ago
deleted more overhead
File size: 27.3 KB
Line 
1#!/usr/bin/python -tti
2
3import time
4from factdimserver import *
5import numpy as np
6import types
7
8last_drive_kwargs = {}
9last_drive_method = None
10
11bias_calibration = {}
12
13report_length = None
14
15def wait_nice(self, state_num, timeout=None):
16 if not hasattr(self, 'stn'):
17 raise TypeError(self.name+' has no CMD called STATE')
18 if timeout == None:
19 timeout = float('inf')
20 else:
21 timeout = float(timeout)
22 start = time.time()
23 intermed = time.time()-1.
24 while not self.stn == state_num:
25 time.sleep(0.1)
26 if time.time() - intermed >= 1.:
27 report = str(fad_control.events()[0]) + ' events @ ' +
28 str( ftm_control.trigger_rates()[3]) + ' Hz'
29 if report_length:
30 print '\b'*report_length,
31 print report,
32 report_length = len(report)
33 intermed = time.time()
34
35 if time.time() >= start+timeout:
36 print
37 return False
38 print
39 return True
40
41fad_control.wait_nice = types.MethodType( wait_nice, fad_control)
42
43
44def FadConnectCrate( crate ):
45 cratenum = None
46
47 if crate == 'all':
48 print "connecting to all crates"
49 for i in range( 40 ):
50 time.sleep(3.8)
51 fad_control.connect(i)
52 print "... done"
53 else:
54 try:
55 cratenum = int(crate)
56 except ValueError as e:
57 print "cannot convert crate parameter to integer. crate=", crate
58 print e
59 raise
60
61 if cratenum != None:
62 print "connecting to crate", cratenum
63 for i in range(cratenum*10, (cratenum+1)*10 ):
64 time.sleep(3.8)
65 fad_control.connect(i)
66 print "... done"
67
68
69def FadDisconnectCrate( crate ):
70 cratenum = None
71
72 if crate == 'all':
73 print "connecting to all crates"
74 for i in range( 40 ):
75 fad_control.disconnect(i)
76 print "... done"
77 else:
78 try:
79 cratenum = int(crate)
80 except ValueError as e:
81 print "cannot convert crate parameter to integer. crate=", crate
82 print e
83 raise
84
85 if cratenum != None:
86 print "connecting to crate", cratenum
87 for i in range(cratenum*10, (cratenum+1)*10 ):
88 print 'disconnecting from i', time.time()
89 fad_control.disconnect(i)
90 print "... done"
91
92
93
94def IsReadyForDataTaking():
95 """ Checking the system statuses if they are ready for data taking
96 """
97
98 print "--------------------------------------"
99 print "Checking the system statuses of:"
100 print "FEEDBACK, BIAS and FAD"
101 print "--------------------------------------"
102
103 print "...waiting for FEEDBACK"
104 print " to be in state 12: CurrentControl"
105 feedback.wait(12)
106
107 print "...waiting for BIAS_CONTROL"
108 print " to be in state 9: VoltageOn"
109 bias_control.wait(9)
110
111 print "...waiting for FAD_CONTROL"
112 print " to be in state 4: Connected"
113 fad_control.wait(4)
114
115 print "...system statuses OK"
116 print "--------------------------------------"
117
118def NotReadyForDataTaking( servers_n_targets = [ (feedback, 12),
119 (bias_control, 9),
120 (fad_control, 4) ] ):
121 """ Checking the system statuses if they are ready for data taking
122 return list of servers, which are NOT ready for Data Taking
123 so one can use this function like this
124 if not NotReadyForDataTaking():
125 # freak out
126 else:
127 # start data taking
128 """
129 not_ready = []
130
131 print "--------------------------------------"
132 print "Checking the system statuses of:"
133 for server,target in servers_n_targets:
134 print server.__name__ , ','
135 print
136 print "--------------------------------------"
137
138 for n, server, target in enumerate(servers_n_targets):
139 if server.stn != target:
140 print server.__name__, "NOT in state ", target
141 not_ready.apppend((server,target))
142
143 return not_ready
144
145
146
147def IsTracking():
148 """ Name is misleading, it actually *waits* until Drive is in Tracking
149 original comment: Checking if Drive is in Status Tracking
150 """
151
152 #return drive_control.stn == 8
153 drive_control.wait(8)
154
155
156def PrepareBiasForDataTaking():
157 """ should have the original behaviour, no new fancy features
158 check feedback state before switching BIAS ON and ramping up to nominal Voltage
159 """
160
161 start = time.time()
162 while (feedback.stn != 12):
163 time.sleep(0.1)
164 if time.time() > start + 10.:
165 print "==================================================="
166 print " feedback is not in state 'CurrentControl' "
167 print " OPERATOR: "
168 print " goto feedback console and check the state of "
169 print " feedback by typing [st] to find out what the"
170 print " current state means and maybe needs to be done"
171 print " this script will wait for state 'CurrentControl'"
172 print "==================================================="
173 feedback.wait(12)
174
175 bias_control.set_global_dac(1)
176
177 start = time.time()
178 while (bias_control.stn != 9):
179 time.sleep(0.1)
180 if time.time() > start + 10.:
181 print '==================================================='
182 print ' switching on bias not successfull'
183 print ' biasctrl is not in state "VoltageOn"'
184 print ''
185 print ' OPERATOR:'
186 print ' goto biasctrl console and check the state of'
187 print ' biasctrl by typing [st] to find out what the'
188 print ' current state means and maybe needs to be done'
189 print ''
190 print ' this script will wait for state "VoltageOn"'
191 print '==================================================='
192 bias_control.wait(9)
193
194 bias_control.wait(5)
195 bias_control.wait(9)
196
197 print "bias is on, and feedback-program is working, but we wait 45sec for the current readings..."
198 time.sleep(45)
199 print "...done"
200
201
202def StopTracking():
203 """ should have the original behaviour, no new fancy features
204 stop drivectrl tracking the current source
205 """
206 drive_control.stop()
207 drive_control.wait(6) #Armed
208
209 print "Drive Armed"
210 print "Tracking Stopped"
211
212
213def SwitchOnBias():
214 """ should have the original behaviour, no new fancy features
215 bring Feedback to state CurrentControIdle and switch on Bias
216 """
217 print ' switching on current controll feedback'
218 feedback.stop()
219 print ' ... starting current control feedback '
220 feedback.start_current_control(0.)
221 feedback.enable_output(1) # 1 means True here ... this needs improvement.
222
223 print ' ...waiting for FEEDBACK to be in state 9: CurrentCtrlIdle'
224 feedback.wait(9)
225 print '... feedback is running.'
226
227 print ' switching bias on by, setting DAC to 1 globally'
228 bias_control.set_global_dac(1)
229
230 print ' ...waiting for BIAS to be in state 9: VoltageOn'
231 bias_control.wait(9)
232 print ' ...1 DAC globally set'
233
234
235 print ' ...waiting for BIAS to be in state 5: Ramping'
236 bias_control.wait(5)
237 print ' ...ramping to nominal voltage'
238
239 print ' ...waiting for BIAS to be in state 9: VoltageOn'
240 bias_control.wait(9)
241 print ' ...bias on'
242
243 print ' waiting 45sec for the current control to stabilize...'
244 time.sleep(45.)
245 print ' ... done, bias on'
246
247
248 # the feedback should be in state 'CurrentCtrlIdle'(9) now since 30.05.12
249 # if feedback.stn != 9:
250 # print "feedback is in state:", feedback.sts , "(", feedback.stn, ")"
251 # print "but is should be in state CurrentCtrlIdle (9)"
252 # print "aborting"
253 # return
254
255
256
257def WaitForTracking( verbose = False):
258 """ Wait for drivectrl to reply that its tracking the given source
259 """
260 if verbose:
261 print "...waiting for DRIVE_CONTROL"
262 print " to be in state 7: Moving"
263 drive_control.wait(7)
264 if verbose:
265 print "...moving"
266
267 if verbose:
268 print "...waiting for DRIVE_CONTROL"
269 print " to be in state 8: Tracking"
270 drive_control.wait(8)
271 if verbose:
272 print "...tracking requested wobble position"
273
274 if verbose:
275 print "waiting 10 sec for drive to calm down"
276 print "and tracking beeing stable"
277 time.sleep(10)
278
279
280
281def Take( time, num_events, runtype, verbose=False):
282 """ more general version of e.g. TakePedestalOnRun
283 Note: One has to check, if Ready for *Take* by oneself
284 """
285 runtype += '\0'
286 # check if all subsystems are in the correct state
287 #IsReadyForDataTaking()
288
289 if verbose:
290 print ' taking', runtype,'. ', num_events, 'events in', time, 'seconds'
291 mcp.start(time, num_events, runtype)
292
293 if verbose:
294 print '...waiting for FAD to be in state 8: Writing Data'
295 fad_control.wait(8) # Writing Data
296 if verbose:
297 print '...waiting for FAD to be in state 4: Connected'
298 fad_control.wait_nice(4) # Connected
299 if verbose:
300 print '... done'
301
302
303def TakeData():
304 """ taking a Data Set (1x Pedestal On, 1x LPext, 4x5min DataRun)
305 """
306 # take a Pedestal run
307 IsTracking()
308 IsReadyForDataTaking()
309 print 'taking External Light Pulser with BIAS on 1000 ...'
310 Take(-1, 1000, 'pedestal')
311
312 # take a ExtLP run
313 IsTracking()
314 IsReadyForDataTaking()
315 print 'taking External Light Pulser with BIAS on 1000 ...'
316 Take(-1, 1000, 'light-pulser-ext')
317
318 #Data Taking with Full Trigger Area (4x5min)
319 for run in range(4):
320 print 'taking data run', run+1, 'out of 4'
321 IsTracking()
322 IsReadyForDataTaking()
323 Take( 300, -1, 'data')
324
325
326def TakeDrsCalibration():
327 """ script for DRS-Calibration before Data taking
328 """
329 print 'script for DRS-Calibration before Data taking'
330 print 'starting up...'
331
332 feedback.enable_output(1)
333 # Making sure bias is off, before the DRS calibration starts
334 bias_control.set_zero_voltage()
335 print '...ramping Voltage down'
336 print ' ...waiting for BIAS to be in state 7: Voltage Off'
337 bias_control.wait(7) #VoltageOff
338 print '...BIAS voltage is switched off'
339
340 # starting the DRS calibration
341 fad_control.start_drs_calibration()
342
343 # taking first DRS:Pedestal with 1000 Events and ROI 1024
344 print 'taking DRS:Pedestal 1000 ...'
345 fad_control.wait(4) #Connected
346 Take(-1, 1000, 'drs-pedestal')
347
348 # taking DRS:Gain with 1000 Events and ROI 1024
349 print ' taking DRS:Gain 1000 ...'
350 fad_control.wait(4) #Connected
351 Take(-1, 1000, 'drs-gain')
352
353 # taking DRS:Pedestal 1000 Events and ROI 1024
354 print 'taking DRS:Pedestal 1000 ...'
355 fad_control.wait(4) #Connected
356 Take(-1, 1000, 'drs-pedestal')
357
358 print ' ... done'
359
360 # taking again a DRS:Pedestal with 1000 Events and ROI 1024 for a crosscheck of calculated calibrations constants
361 print ' taking crosscheck DRS:Pedestal 1000 ...'
362 fad_control.set_file_format(2)
363 fad_control.wait(4) #Connected
364 Take(-1, 1000, 'drs-pedestal')
365
366
367 # taking DRS:Time with 1000 Events and ROI 1024
368 print ' taking DRS:Time 1000 ...'
369 fad_control.wait(4) #Connected
370 Take(-1, 1000, 'drs-time')
371
372
373 # taking DRS:Time upshifted 1000 Events and ROI 1024
374 print 'taking DRS:Time upshifted 1000 ...'
375 fad_control.wait(4) #Connected
376 Take(-1, 1000, 'drs-time-upshifted')
377
378 # taking a Pedestal with 1000 Events and ROI 300 for secondary baseline...
379 print 'taking Pedestal 1000 for secondary baseline... with ROI=300'
380 fad_control.reset_secondary_drs_baseline()
381 fad_control.wait(4) #Connected
382 Take(-1, 1000, 'pedestal')
383
384 # taking crosscheck Pedestal 1000 Events and ROI 300
385 print ' taking crosscheck Pedestal 1000 ...with ROI=300'
386 fad_control.set_file_format(2)
387 fad_control.wait(4) #Connected
388 Take(-1, 1000, 'pedestal')
389
390 print '----------------------------------------------------'
391 print 'This is the end of the'
392 print 'DRS-Calibration before Data taking'
393 print '----------------------------------------------------'
394
395
396def FirstDrsCalib( SkipCurrentCalib=False ):
397 """ performs the everything, which is done in the FirstDrsCalib Script as well .
398 """
399 # As a First step we want to calibrate the current, which are read from the bias crate,
400 # and not take a DRS calibration, as it is mentioned in the data taking page...
401 # so for this we should get the feedback and biasctrl programs into known states
402 # I think it is good to try a RECONNECT to the bias, and make sure the voltage is off
403 # Since we do not know, what the feedback program is doing at the moment, we should as well,
404 # tell it to keep its mouth shut ... just to be sure, we know whats going on
405 print "stopping feedback"
406 feedback.stop()
407
408 time.sleep(2)
409 # stopping should always be possible, and end in state 'Connected'(6)
410 print " ...waiting for FEEDBACK to be in state 6: Connected"
411 feedback.wait(6)
412 print "..done"
413
414 #BIAS_CONTROL/RECONNECT
415 # If we were disconnected, and this was the first try of the night, the bias_ctrl should
416 # be in state 'VoltageOff'(7) more or less immediately
417 #.s BIAS_CONTROL 3
418 #.s BIAS_CONTROL 7 5000
419 # if these assumptions are all wrong, then we might have been properly connected anyway,
420 # and just have to ramp down... lets do it, but wait forever, in case it does not work
421 print " switching off bias"
422 bias_control.set_zero_voltage()
423 time.sleep(2)
424 print " ...waiting for BIAS to be in state 7: VoltageOff"
425 bias_control.wait(7)
426 print " ...done"
427
428 if not SkipCurrentCalib:
429 # in case we reach this line, the voltages are all off, and the feedback does not do anything
430 # So lets do the current calibration, therefor we tell the bias crate to ramp up just 1 single DAC count(~22mV)
431 # the result of this action is, to get bias_ctrl into the state 'VoltageOn'(9), but since we only go one DAC count it shouldn't take long
432 print " setting bias globally to 1 DAC"
433 bias_control.set_global_dac(1)
434
435 time.sleep(2)
436 print " ...waiting for BIAS to be in state 9: VoltageOn"
437 bias_control.wait(9)
438 print " ...done"
439
440 # now we may tell the feedback program to calibrate the currents ...
441 # I do not understand, if I have to explicitely allow the feedback program to generate output,
442 # or if it just produces output...
443 # As far as I understand, the feedback output enable status is the same,
444 # as it was before I send the STOP command... so it is unknown at this point.
445 # and in addition enabling or disabling the output, when STOPed is not possible as far as I know...
446 # I try to enable it anyway.
447 print " enabling output for feedback"
448 feedback.enable_output(1)
449 time.sleep(2)
450 print " ...done"
451
452 print " calibrating bias crate current readings..."
453 feedback.calibrate_currents()
454 time.sleep(5)
455 # in order to find out when the calibration ends, we have to wait for the transistion from state
456 # 'Calibrating'(13) back to 'Connected'(6)
457 print " ...waiting for FEEDBACK to be in state 13: Calibrating"
458 feedback.wait(13)
459 print " ...waiting for FEEDBACK to be in state 6: Connected"
460 feedback.wait(6)
461
462 # Thomas Bretz told me, that the feedback, after this is step has disabled its output
463 # and is in the mode, we might call 'temperature control' even there is no temerature beeing controlled.
464 # I don't know where the voltage is ... in order to perform the calibration, the feedback had to
465 # ramp up to 2V below the operational voltage, i.e. about 1V below the breakdown voltage
466
467 # We want to take a DRS amplitude calibration so we have to ramp down the bias voltage.
468 # this 10sec wait is needed in order for the bias not to disconect all the time...
469 print " ... current calibration done"
470 time.sleep(10)
471
472 print " switching off bias"
473 bias_control.set_zero_voltage()
474 time.sleep(5)
475 print " ...waiting for BIAS to be in state 7: VoltageOff"
476 bias_control.wait(7)
477 print " ...done"
478
479 # So now we can take the 3 runs, which are called DRS amplitude calibration:
480 # A pedestal run with ROI=1024
481 # A gain calibration run with ROI=1024
482 # and a second pedestal run, with the same ROI as our next data will be, i.e. ROI=300 in this case
483 print "taking DRS:Pedestal 1000 ..."
484 print "==================================================="
485 print "OPERATOR: "
486 print "observe Events tab and make sure there are no patches "
487 print "with strange behaviour, which can be caused "
488 print "by DRS-CHIP Problems"
489 print "==================================================="
490
491 fad_control.start_drs_calibration()
492 time.sleep(0.5)
493 Take( -1, 1000, 'drs-pedestal')
494
495 print "taking DRS:Gain 1000 ..."
496 Take( -1, 1000, 'drs-gain')
497
498 time.sleep(2)
499 if GetDrsCalibGainRms():
500 print
501 print 'First DRS Calib Script will be aborted'
502 print 'operator, please power cycle FACT'
503 return False
504
505 print "taking Pedestal 1000 ..."
506 Take( -1, 1000, 'pedestal')
507
508 # okay this is the DRS calibration for the next few runs.
509 # we are now asked to take again a pedestal run, which can be used, to
510 # calculate the electronics noise for instance ... since the shutter is closed and the
511 # voltage is off .. there should not be alot of signal in it :-)
512 print "taking crosscheck Pedestal 1000 ..."
513 fad_control.set_file_format(2)
514 Take(-1, 1000, 'pedestal')
515
516 # now we want to take a run, with dark counts events
517 # so we need to ramp up the voltage
518 # we want to use the 'current control' more so we give the commands for this...
519 print "switching on current controll feedback ..."
520 feedback.stop()
521 feedback.start_current_control(0.0)
522 feedback.enable_output(1)
523 # the feedback should be in state 'CurrentControl'(12) now
524 # the feedback should be in state 'CurrentCtrlIdle'(9) now since 30.05.12
525 print "...waiting for FEEDBACK to be in state 9: CurrentCtrlIdle"
526 feedback.wait(9)
527 print "... done"
528 print "switching on bias"
529 # now we give the feedback a hint, that it may ramp ...
530 bias_control.set_global_dac(1)
531 # after this command the bias_ctrl should be in state 'VoltageOn'(9) after a second or so
532 print "...waiting for BIAS to be in state 9: VoltageOn"
533 bias_control.wait(9)
534 print "...1 DAC globally set"
535 # then usually it takes some time until the feedback has enough information to really start controlling the voltage
536 # when the feedback actually kicks in, the bias is first in state 'Ramping'(5) for some seconds and finally in 'VoltageOn'(9)
537 # again
538 print "...waiting for BIAS to be in state 5: Ramping"
539 bias_control.wait(5)
540 print "...ramping to nominal voltage"
541 print "...waiting for BIAS to be in state 9: VoltageOn"
542 bias_control.wait(9)
543 print "...bias on"
544 # here we should wait 45 sec in order for the current control to get enough current readings and temp readings to stabilize..
545 print "waiting 45sec for the current control to stabilize..."
546 time.sleep(45)
547 print "... done"
548
549 # so now we can take the dark count run ...
550 # this might be changed in the future ... either the number of events or the the ROI might be changed
551 # then the DRS calibration above, and the pedestal run in between have to be changed as well.
552 print "taking Pedestal with BIAS on 3000 ..."
553 Take(-1, 3000, 'pedestal')
554
555 # at the end the bias voltage should be ramped down, since in a few seconds a shifter wit ha flashlight
556 # will come out to open the shutter...
557 print "switching OFF bias ..."
558 bias_control.set_zero_voltage()
559 print "...waiting for BIAS to be in state 7: VoltageOff"
560 bias_control.wait(7)
561 print "...done"
562 print "This is the end of First DRS Calibration"
563 print "----------------------------------------------------"
564 print ">"
565
566def Ratescan( ra=None, dec=None, sourcename=None):
567 """
568# call it by: .x ScriptsForDimCtrl/Ratescan.dim mode=<trackmode> ra=<Right ascension> dec=<Declination> source=<source_name>
569# mode=0: Manual tracking Mode: set tracking in drivectrl manually
570# mode=1: Coordinate Mode: scripts sends tracking command to drivectrl with the given RaDec coordinates
571# mode=2: source Mode: scripts sends tracking command to drivectrl with the given source_name
572
573 """
574 print '======================================'
575 print 'RATESCAN'
576 print '======================================'
577 print 'Preparing Drive'
578
579
580 if None == ra and None == dec and None == sourcename:
581 print 'Manual tracking Mode'
582 print '---------------------'
583 print 'OPERATOR'
584 print 'change tracking in drivectrl manually'
585 print 'script will wait for drive'
586 print 'to be in state tracking'
587 elif None != ra or None != dec:
588 try:
589 ra = float(ra)
590 dec = float(dec)
591 except TypeError:
592 raise
593
594 print '...stop tracking'
595 StopTracking()
596 print '...change tracking of telescope to:'
597 print '...Ra = ', ra
598 print '...Dec = ', dec
599 drive_control.track( ra, dec)
600 elif None != sourcename:
601 print '...stop tracking'
602 StopTracking()
603 print '...change tracking of telescope to:', sourcename
604 sourcename += '\0'
605 drive_control.track_source( 0, 0, sourcename)
606 else:
607 print 'type(ra)', type(ra), '\tra', ra
608 print 'type(dec)', type(dec), '\tdec', dec
609 print 'type(sourcename)', type(sourcename), '\tsourcename', sourcename
610 raise ValueError('RateScan does not know what to do with its parameters. Bug!')
611 return False
612
613 IsTracking()
614 IsReadyForDataTaking()
615
616 print 'Starting Ratescan'
617 print '...waiting for Ratescan'
618 print ' to be in state 4: Connected'
619
620
621 if not rate_scan.wait(4, timeout=5.): #Connected
622 # we went into timeout!
623 print 'Rate_Scan not in correct state'
624 print 'OPERATOR:'
625 print '+ check connection to ftm control'
626 print 'we went into to 5sec. timeout while waiting for RATE_SCAN to be in state Connected'
627 print 'aborting'
628 return False
629
630 rate_scan.start_threshold_scan( 50, 1000, -10)
631 if not rate_scan.wait( 6, timeout=10.): # Statename???
632 # we went into timeout
633 print 'ratescan not started'
634 print 'we went into 10sec. timeout while waiting for RATE_SCAN to start the Scan'
635 print 'aborting'
636 return False
637
638 print '...processing ratescan'
639 if not rate_scan.wait( 4, timeout=2700.): # Connected
640 # we went into timeout
641 print 'we went into 2700sec. timeout while waiting for RATE_SCAN to finish'
642 print 'aborting'
643 return False
644
645 print 'Ratescan finished successfully'
646 return True
647
648
649def ResetCrate( crate_num ):
650 """ Reset Crate
651 crate_num = 0,1,2 or 3 the number of the crate to reset.
652 crate_num = 'all' is NOT YET SUPPORTED
653 """
654 c = int(crate_num)
655
656 print '======================================'
657 print 'Crate-Reset for crate ', c
658 print '======================================'
659
660 print '...resetting MCP'
661 mcp.reset()
662 time.sleep(5.)
663 print '...diconnecting FAD boards of crate ', c
664 FadDisconnectCrate( c )
665 time.sleep(2.)
666
667 print '...disconnecting All FTUs'
668 ftm_control.enable_ftu( -1, 0) # -1 for all, and 0 for False
669 time.sleep(2.)
670
671 print '...checking state of FTM_Control'
672 print '...waiting for state 3: Idle'
673 if not ftm_control.wait(3, 2.): # Idle
674 print '...stopping trigger'
675 ftm_control.stop_trigger()
676 ftm_control.wait(3) # wait for Idle endlessly
677
678 print '...resetting crate'
679 ftm_control.reset_crate( c )
680 time.sleep(2.)
681
682 print '...connecting All FTUs'
683 ftm_control.enable_ftu( -1, 1) # -1 for all, and 1 for yes, or True
684 time.sleep(4.)
685
686 print '...pinging FTUs'
687 ftm_control.ping()
688
689 print '...connecting FAD boards of crate', c
690 FadConnectCrate(c)
691 print '======================================'
692 print 'Crate-Reset for crate', c, 'finished'
693 print '======================================'
694
695def GetDrsCalibGainRms():
696#drs_calibration(self) method of factdimserver.FAD_CONTROL instance
697#DESC in SERVICE_DESC is empty ?!
698#I:1;I:3;F:1474560;F:1474560;F:1474560;F:1474560;F:1474560;F:1474560;F:163840;F:163840
699 data = fad_control.drs_calibration()
700 N1 = data[0]
701 N3 = data[1:4]
702 OffsetMean = np.array(data[4:4+1024*1440]).reshape(1440,1024)
703 OffsetRms = np.array(data[4+1024*1440:4+1024*1440*2]).reshape(1440,1024)
704 GainMean = np.array(data[4+1024*1440*2:4+1024*1440*3]).reshape(1440,1024)
705 GainRms = np.array(data[4+1024*1440*3:4+1024*1440*4]).reshape(1440,1024)
706
707 gr = GainRms.mean(axis=1)
708 lala = np.zeros(len(gr)/9)
709 for i,v in enumerate(lala):
710 lala[i] = gr[i*9:(i+1)*9].mean()
711
712 # outliers
713 mean = lala.mean()
714 std = lala.std()
715
716 print 'Mean DRS GainRms value:', mean
717 print 'std:', std
718 outs = np.where( lala > mean+7*std)[0]
719 if len(outs) > 0:
720 print 'WARNING possible DRS underflow detected!!!'
721 for out in outs:
722 out = int(out)
723 crate= out/40
724 board = (out-40*crate)/4
725 chip = out-40*crate-4*board
726 print 'possible DRS underflow in DRS:', crate, board, chip, '--> Mean-GainRms:', lala[out]
727 return outs
728 else:
729 return False
730
731
732
733
734def GetBiasCalibration():
735 cali = feedback.calibration()
736 bias_calibration['Time'] = time.time()
737 bias_calibration['Calibration'] = cali
738
739def GetBiasCurrent(verbose = False):
740 """ return median, std, max and min current
741 """
742 if 'Time' in bias_calibration:
743 cali = bias_calibration['Calibration']
744 else:
745 GetBiasCalibration()
746 cali = bias_calibration['Calibration']
747
748 r = np.array(cali[2*416:2*416+320])
749
750 bias = bias_control
751
752 I = np.array(bias.current()[0:320], dtype=float)
753 II = I/4096. * 5000
754 V = np.array(bias.voltage()[0:320])
755 if len(sys.argv) > 1:
756 i = int(sys.argv[1])
757 else: i=0
758# print 'I:', I[i], 'dac\t', II[i], 'uA'
759# print 'V:', V[i]
760# print ''
761# print 'GUI offset:', V[i]/r[i]*1e6
762# print 'GUI feedback:', II[0] - V[0]/r[0]*1e6
763
764 GUII = II-V/r*1e6
765 if verbose:
766 print 'median', np.median(GUII)
767 print 'mean', GUII.mean()
768 # print 'rms', ((GUII- GUII.mean())**2).sum()
769 print 'std', GUII.std()
770 print 'max', GUII.max()
771 print 'min', GUII.min()
772
773 return GUII.mean(), GUII.std(), GUII.max(), GUII.min()
774
775
776
777
778def TrackSourceWobbleX( sourcename, wobble_pos ):
779 """ general Tracking function
780 """
781 wp = int(wobble_pos)
782 if wp != 1 and wp != 2:
783 raise ValueError('wobble_pos *must* be 1 or 2')
784
785 if sourcename not in sourcedict:
786 print sourcedict.keys()
787 raise ValueError('sourcename: '+ sourcename +' must be in sourcedict.')
788
789 print 'moving telescope to wobble position ', wp, 'of ', sourcename
790 print '...waiting for DRIVE_CONTROL'
791 print ' to be in state 6: Armed'
792
793 drive_control.wait(6) #Armed
794 print 'DRIVE: ARMED'
795 time.sleep(5.)
796
797 wobble_offset = sourcedict[sourcename]['wobble_offset']
798 wobble_angle = sourcedict[sourcename]['wobble_angle'+str(wp)]
799 sourcename += '\0'
800
801 last_drive_method = drive_control.track_source
802 last_drive_kwargs = { 'wobble_offset' : wobble_offset,
803 'wobble_angle' : wobble_angle,
804 'source_name' : sourcename }
805 kwa = last_drive_kwargs
806 last_drive_method(kwa['wobble_offset'], kwa['wobble_angle'], kwa['source_name'])
807
808 print '... done'
809
810source_list = [
811 ['Crab', 0.6 , 50, -130],
812 ["1ES 2344+51.4", 0.6 , 90, -90 ],
813 ["Mrk 501", 0.6, -22, -22+180 ],
814 ["Mrk 421", 0.6, 90, -90 ],
815 ["1ES 1218+304", 0.6, -5, -5+180 ],
816 ["1ES 1959+650", 0.6, 155, 155-180 ],
817 ["Dark Patch 2", 0.6 , 90, -90 ],
818 ["Dark Patch 3", 0.6 , 90, -90 ],
819 ["H 1426+428", 0.6 , 90, -90 ],
820 ["IC 310", 0.6, -18, -18+180 ],
821 ["PKS 2155-304", 0.6, 90, -90 ] ]
822
823sourcedict = {}
824
825def make_sourcedict():
826 for s in source_list:
827 sourcedict[s[0]] = {}
828 sourcedict[s[0]]['wobble_offset'] = s[1]
829 sourcedict[s[0]]['wobble_angle1'] = s[2]
830 sourcedict[s[0]]['wobble_angle2'] = s[3]
831
832
833def TakeSource( name ):
834 if name not in sourcedict:
835 print name, 'not in dict of sources, possible sources are:'
836 print sorted(sourcedict.keys())
837 raise ValueError('wrong source name')
838
839 TrackSourceWobbleX( name, 1) # Track Wobble pos 1 of source
840 WaitForTracking()
841 # Take a DRS-Calibration before beginning to take physics Data
842 TakeDrsCalibration()
843 # check feedback state before switching BIAS ON and ramping up to nominal Voltage
844 PrepareBiasForDataTaking()
845 # taking a Data Set (1x Pedestal 1000 Bias On, 1x LPext 1000, 4x5min DataRun)
846 TakeData()
847 StopTracking()
848
849 TrackSourceWobbleX( name, 2) # Track Wobble pos 2 of source
850 WaitForTracking()
851 # taking a Data Set (1x Pedestal 1000 Bias On, 1x LPext 1000, 4x5min DataRun)
852 TakeData()
853
854 StopTracking()
855
856def PrintCurrents( x = 1.0):
857 while True:
858 time.sleep( x )
859 print time.strftime('%d %b %Y %H:%M:%S UTC', time.gmtime()), GetBiasCurrent()
860
861
862if __name__ == '__main__':
863 print 'Welcome to PyDimCtrl'
864 make_sourcedict()
865 print
866 print 'possible sources:'
867 print sorted( sourcedict.keys() )
Note: See TracBrowser for help on using the repository browser.