#!/usr/bin/env python # # $Id:$ # # hd_pxi_disk_monitor.py # # This script helps make sure the PXI system is recording data # on gluonraid1, signaling the alarm system if it is not. # # This can be run from any computer with /gluonraid1 mounted. # Typically though, it should be run from gluonraid1 itself # so we know where to look for the process in order to kill it. # Run it from the HDOPS account like this: # # > $DAQ_HOME/tools/raidutils/hd_pxi_disk_monitor.py # # This script will check that a recent ROOT file exists in the # /raid/Users/pxi directory. It will update an EPICS heartbeat # variable to which an alarm is attached. If this script stops # running, or does not detect a recent ROOT file, the heartbeat # stops and an alarm is raised. # # Because this is only needed when the solenoid is on, then the # hearbeat is automatically updated if the solenoid current is # reported as less then 100A by EPICS. # # The EPICS variable giving the directory to check is EPICS_PXI_DIR # The EPICS variable to update as a heartbeat is given in EPICS_HEARTBEAT # The EPICS variable to read the solenoid current from is EPICS_SOLENOID # The period in which to check is PERIOD and is given in seconds # # If a directory is given on the command line using the "-d dir" # option then it is used and EPICS_PXI_DIR is ignored # # This file is kept under version control at the following location: # # https://halldsvn.jlab.org/repos/trunk/online/daq/tools/raidutils/hd_pxi_disk_monitor.py # # # --- RUN THIS ON GLUONRAID1 --- # import os import sys import time import datetime import getopt from epics import caget, caput PXI_DIR = '/gluonraid1/Users/pxi' # directory to check for ROOT files VERBOSE = False EPICS_PXI_DIR = 'pxiroot:ctrl:file_dir' EPICS_HEARTBEAT = 'pxiroot:ctrl:raid:heartbeat' EPICS_SOLENOID = 'HallD-PXI:Data:I_Shunt' PERIOD = 2 # seconds between checks (and heartbeats) PXI_DIR_OVERRIDE = None def Usage(err): print 'Usage:' print ' hd_pxi_disk_monitor.py [-v] [-p period_secs] [-d directory]' print ' ' sys.exit(err) # Parse command line arguments try: opts, args = getopt.getopt(sys.argv[1:], 'p:d:vh', ['pause=','dir=','verbose','help']) except getopt.GetoptError: Usage(2) for opt,arg in opts: if opt in ("-h", "--help") : Usage(0) if opt in ("-p", "--pause") : PERIOD = int(arg) if opt in ("-d", "--dir") : PXI_DIR_OVERRIDE = arg if opt in ("-v", "--verbose") : VERBOSE = True # Loop forever first_iteration = True heartbeat = 0 while True: # Get directory to check from EPICS, allowing user to override if PXI_DIR_OVERRIDE==None: PXI_DIR = caget('pxiroot:ctrl:file_dir') else: PXI_DIR = PXI_DIR_OVERRIDE # If EPICS variable was not available, then PXI_DIR will be None if PXI_DIR==None: PXI_DIR='/could/not/get/dir/from/epics' # Make sure PXI_DIR exists if not os.path.exists(PXI_DIR) : print '-------------------------------------' print 'path "%s" does not exist!' % PXI_DIR print 'hd_pxi_disk_monitor.py exiting ..' print '-------------------------------------' break # Get list of root files in PXI_DIR files = [os.path.join(PXI_DIR, f) for f in os.listdir(PXI_DIR) if os.path.isfile(os.path.join(PXI_DIR, f))] rootfiles = [f for f in files if f.endswith('.root')] if len(rootfiles) >= 1 : # Find most recently modified rootfile t_latest = 0 f_latest = 'none' for f in rootfiles: t = os.path.getmtime(f) if t>t_latest: t_latest = t f_latest = f # Time since modification in seconds t_diff = time.time() - t_latest # Solenoid current isolenoid = caget(EPICS_SOLENOID) if isolenoid == None : isolenoid = 199.0 # Print info only on first iteration if first_iteration : print '-------------------------------------' print 'hd_pxi_disk_monitor.py starting' print '' print ' VERBOSE: %s' % VERBOSE print ' PERIOD: %d' % PERIOD print ' PXI_DIR: %s' % PXI_DIR print ' EPICS PV names: %s' % EPICS_SOLENOID print ' %s' % EPICS_HEARTBEAT print 'newest root file: %s (%f minutes old)' % (f_latest, t_diff/60.0) print ' Isolenoid: %f' % isolenoid print '-------------------------------------' first_iteration = False # Update heartbeat if file is less than 30 minutes old # or solenoid is less than 100A if t_diff<30*60 or isolenoid<100.0: # Update heartbeat myheartbeat = caget(EPICS_HEARTBEAT) if myheartbeat == None: print 'Failed to read hearbeat value from EPICS variable: %s setting to %d' % (EPICS_HEARTBEAT, heartbeat) else: heartbeat = myheartbeat heartbeat += 1 if heartbeat>1: heartbeat = 0 caput(EPICS_HEARTBEAT, heartbeat) if VERBOSE : print '%s : %f min old' % (f_latest, t_diff/60.0) # Sleep time.sleep(PERIOD)