diff --git a/src/analysis.py b/src/analysis.py index 4000da6..c4659e3 100644 --- a/src/analysis.py +++ b/src/analysis.py @@ -3,6 +3,7 @@ Analysis class """ from collections import OrderedDict from datetime import datetime +import heapq import logging import math import os @@ -81,7 +82,8 @@ class AnalysisProcedure(QObject): self.simulation = False self.accelerator = self.ring_cyclotron self.harmonic_no = 6 - self.injector2_current = 0 + self.entry_current = 0 + self.exit_current = 0 self.n_turns = None # self.t_stepsize = 0.000000019750043 #0.00000002 self.rf_freq = 50.6328 # 10**6 @@ -90,6 +92,8 @@ class AnalysisProcedure(QObject): self.t_stepsize = 1/(self.rf_sample*10**9) self.t_interval = math.ceil(self.pulse_stepsize/self.t_stepsize) + self.correlation_peak_diff = 0.0 + self.dt_cable = 44 # ns self.dn_pickup = -1 self.mod_freq = 500 # GHz @@ -125,10 +129,9 @@ class AnalysisProcedure(QObject): self.input_data = input_data self.all_data['Input data'] = self.input_data - print('==>Initialize Input Parameters') + print(self.input_data) - print('==>Initialized Input Parameters') - + if 'debug' in self.input_data.keys(): self.debug = self.input_data['debug'] @@ -241,10 +244,10 @@ class AnalysisProcedure(QObject): ambient_data['Time in seconds'] = int(ambient_data['Time in seconds']) try: - ambient_data['I_Inj2'] = float(ambient_data['I_Inj2']) - self.injector2_current = ambient_data['I_inj2'] + ambient_data['I Exit'] = float(ambient_data['I Exit']) + self.exit_current = ambient_data['I Exit'] except KeyError: - self.injector2_current = 0.0 + self.exit_current = 0.0 self.parent.from_hdf = True @@ -268,7 +271,8 @@ class AnalysisProcedure(QObject): ambient_data = { 'Time in seconds': int(time_in_seconds), 'Time stamp': self.time_stamp, - 'I_Inj2': 0, + 'I Entry': 0, + 'I Exit': 0, } self.logger.debug(f'Ambient data = {ambient_data}') @@ -298,14 +302,8 @@ class AnalysisProcedure(QObject): self.trigger_progressbar.emit(PROGRESS_THREAD_ERROR) return {} - # Retrieve I_INJ2 - mwc2_ist_2 = self.cafe.getCache('MWC2:IST:2') - if mwc2_ist_2 is not None: - ambient_data['I_Inj2'] = mwc2_ist_2 - - #mA - self.injector2_current = ambient_data['I_Inj2'] - + + pv_list = [] for key, value in self.settings.data['PV'][self.accelerator].items(): @@ -331,21 +329,43 @@ class AnalysisProcedure(QObject): self.check_status_list(_pymodule, 'getScalarList', pv_list, status_list, utils.line_no()) + + + # Retrieve + pv_entry_current = self.settings.data['PV'][self.accelerator]['IEntry'] + + entry_current = self.cafe.getCache(pv_entry_current) + ambient_data['I Entry'] = entry_current/1000 \ + if entry_current is not None else 0.0 + #mA if divied by 1000 above + self.entry_current = ambient_data['I Entry'] + + # Retrieve + pv_exit_current = self.settings.data['PV'][self.accelerator]['IExit'] + exit_current = self.cafe.getCache(pv_exit_current) + ambient_data['I Exit'] = exit_current/1000 \ + if exit_current is not None else 0.0 + #mA if divied by 1000 above + self.exit_current = ambient_data['I Exit'] + + pv_daq_ready = self.pv_dict['daqReady'] - + ''' self.daq_ready = self.cafe.getCache(pv_daq_ready) if self.daq_ready is None: stat = self.cafe.getStatus(pv_daq_ready) self.check_status(_pymodule, 'getCache', pv_daq_ready, stat, utils.line_no()) - + ''' pv_daq_error_count = self.pv_dict['daqErrorCount'] - + ''' daq_error_count = self.cafe.getCache(pv_daq_error_count) if daq_error_count is None: stat = self.cafe.getStatus(pv_daq_error_count) self.check_status(_pymodule, 'getCache', pv_daq_error_count, stat, utils.line_no()) + ''' + # Put values in dictionary for inspection for i, (dict_key) in enumerate(self.pv_value_dict.keys()): @@ -354,10 +374,17 @@ class AnalysisProcedure(QObject): if self.debug: print(f'EPICS PVS==> {self.pv_value_dict}', flush=True) - #In GUI - #self.cafe.monitor(pv_daq_ready) - #Not in GUI - self.cafe.monitor(pv_daq_error_count) + #Monitored in GUI + if not self.cafe.getMonitorIDs(pv_daq_ready): + print("MONITOR STARTED FOR ", pv_daq_ready, flush=True) + self.cafe.monitor(pv_daq_ready) + + + if not self.cafe.getMonitorIDs(pv_daq_error_count): + #Now in GUI + print("MONITOR STARTED FOR ", pv_daq_error_count, flush=True) + self.cafe.monitor(pv_daq_error_count) + return ambient_data @@ -368,9 +395,14 @@ class AnalysisProcedure(QObject): height = 50.0 else: height = 0.005 - + y1_peaks_pre = signal.find_peaks(self.y1_sample, height=height, distance=10) + + print("peak length==>", len(y1_peaks_pre[1]['peak_heights'])) + if len(y1_peaks_pre[1]['peak_heights']) < 2: + return False + ##y1_peaks_avg = np.average(y1_peaks_pre[1]['peak_heights']) min_y1_p = np.min(y1_peaks_pre[1]['peak_heights']) max_y1_p = np.max(y1_peaks_pre[1]['peak_heights']) @@ -390,9 +422,9 @@ class AnalysisProcedure(QObject): print(f'AVG = {y1_height}, {y2_height}', flush=True) y1_peaks = signal.find_peaks( - self.y1_sample, height=y1_height, distance=5) + self.y1_sample, height=y1_height, distance=10) y2_peaks = signal.find_peaks( - self.y2_sample, height=y2_height, distance=5) + self.y2_sample, height=y2_height, distance=10) print((f'PEAKS==> {y1_peaks}, {y2_peaks},' + f'{len(y1_peaks[0])}, {len(y2_peaks[0])}'), flush=True) print(y1_peaks[1]['peak_heights'], flush=True) @@ -401,6 +433,12 @@ class AnalysisProcedure(QObject): self.y1_pulse = (y1_peaks[1]['peak_heights']) self.y2_pulse = (y2_peaks[1]['peak_heights']) + #peak_heights = y2_peaks_pre[1]['peak_heights'] + #peak_indices = y2_peaks_pre[0] + #second_highest_peak_index = peak_indices[np.argpartition(peak_heights,-2)[-2]] + #print("2nd highest peak", np.argpartition(peak_heights,-2)) + return True + def measure(self): ''' Enable DAQ and read in the collected data from EPICS ''' @@ -448,7 +486,7 @@ class AnalysisProcedure(QObject): stat = self.cafe.set(pv_daq_trigger, 8) self.check_status(_pymodule, 'set', pv_daq_trigger, stat, utils.line_no()) - time.sleep(0.2) + time.sleep(0.5) stat = self.cafe.set(pv_daq_trigger, 0) self.check_status(_pymodule, 'set', pv_daq_trigger, stat, utils.line_no()) @@ -465,7 +503,7 @@ class AnalysisProcedure(QObject): value = self.cafe.getCache(pv_daq_ready) - print('present cnt', value, flush=True) + print('present cnt', icount, flush=True) if value is None: stat = self.cafe.getStatus(pv_daq_ready) @@ -514,9 +552,9 @@ class AnalysisProcedure(QObject): print(f'y1 sample length = {len(self.y1_sample)}') print(f'y2 sample length = {len(self.y2_sample)}', flush=True) - series = pd.Series(self.y1_sample) + #series = pd.Series(self.y1_sample) #self.y1_sample = (series * (-1)).tolist() - self.y1_sample = (series).tolist() + #self.y1_sample = (series).tolist() self.t_sample = [None] * len(self.y1_sample) self.t_sample[0] = 0 @@ -539,7 +577,13 @@ class AnalysisProcedure(QObject): self.trigger_progressbar.emit(60) extract_raw_data() - self.extract_peak_data() + peaks_found = self.extract_peak_data() + if not peaks_found: + mess = ('No peaks found! ' + + f'Measuremenmg procedure aborted.') + self.parent.trigger_log_message.emit( + MsgSeverity.ERROR.name, _pymodule, utils.line_no(), mess, {}) + if self.abort: self.aborting(utils.line_no()) return None @@ -590,9 +634,18 @@ class AnalysisProcedure(QObject): len(self.normalized_amplitude_envelope_2), len(self.normalized_amplitude_envelope_1), mode='full') + + self.lag_full = int(self.lags_full_array[np.argmax(self.corr_full)]) #self.delay = self.lag_full * self.t_stepsize*self.t_interval self.delay = float(self.lag_full * self.pulse_stepsize) + + print('peak height', np.max(self.corr_full)) + top_peak_values = heapq.nlargest(2, self.corr_full) + print('1st peak height', top_peak_values[0]) + print('2nd peak height', top_peak_values[1]) + self.correlation_peak_diff = top_peak_values[0] - top_peak_values[1] + print(f'peak significance = {self.correlation_peak_diff:.3f}') print('lag', self.lag_full) print('delay', self.delay, flush=True) print('dTcable', self.dt_cable, flush=True) @@ -619,7 +672,8 @@ class AnalysisProcedure(QObject): 't_stepsize': self.pulse_stepsize, 'lag': self.lag_full, 'delay': self.delay, - 'nturns': self.n_turns + 'nturns': self.n_turns, + 'peak_diff': self.correlation_peak_diff } return proc_data @@ -627,12 +681,26 @@ class AnalysisProcedure(QObject): def make_figs(self): ''' Figure construction with matplotlib ''' + is_suspect = True if self.correlation_peak_diff < \ + self.parent.correlation_peak_diff_min_value else False + if is_suspect: + fontweight_main='normal' + fontweight='light' + color='red' + alpha = 0.4 + else: + fontweight_main='bold' + fontweight='normal' + color='black' + alpha = 1.0 + fig, (ax) = plt.subplots(nrows=2, ncols=1, figsize=(18, 9), layout='tight') fig2, (ax2) = plt.subplots(nrows=1, ncols=1, figsize=(18, 9)) fig.patch.set_facecolor('#FAF9F6') fig2.patch.set_facecolor('#FAF9F6') + ln = 500 # 500 off = 0 # 10000 s = off @@ -677,18 +745,35 @@ class AnalysisProcedure(QObject): ax2.plot([self.lag_full, self.lag_full], [line_start, line_end], ':', color='r') ax2.set_ylim(line_start, line_end) + text = f'No of Turns = {self.n_turns:0.0f}' - plt.figtext(0.65, 0.82, self.accelerator, weight='bold', fontsize=16) - plt.figtext(0.65, 0.77, text, weight='bold', fontsize=16) - if self.injector2_current != 0: - inj_current_text = f'I Inj2 = {self.injector2_current:.3f} mA' - plt.figtext(0.80, 0.85, inj_current_text, weight='normal', + plt.figtext(0.65, 0.82, self.accelerator, fontweight='bold', + fontsize=16, color='black') + + plt.figtext(0.65, 0.77, text, fontweight=fontweight_main, fontsize=16, + color=color, alpha=alpha) + + if self.entry_current != 0: + current_text = f'I(entry) = {self.entry_current:.3f} mA' + plt.figtext(0.80, 0.86, current_text, fontweight='normal', fontsize=10) + if self.exit_current != 0: + current_text = f'I(exit) = {self.exit_current:.3f} mA' + plt.figtext(0.8075, 0.84, current_text, fontweight='normal', + fontsize=10) + + + plt.figtext(0.7, 0.72, f'lag = {self.lag_full}', fontweight=fontweight, + fontsize=14, color=color, alpha=alpha) - plt.figtext(0.7, 0.72, f'lag = {self.lag_full}', weight='normal', - fontsize=14) text = f'delay = {self.delay*10**6:.3f} \u00B5s' - plt.figtext(0.7, 0.67, text, weight='normal', fontsize=14) + plt.figtext(0.7, 0.67, text, fontweight=fontweight, fontsize=14, + color=color, alpha=alpha) + + if is_suspect: + plt.figtext(0.80, 0.72, "Suspect!", fontweight='normal', fontsize=16, + color='blue', alpha=1.0, rotation=45) + if self.settings.data['GUI']['showDate'] == 1: plt.figtext(0.75, 0.12, self.time_stamp, size='small') diff --git a/src/gui.py b/src/gui.py index 65787fd..12ff99d 100644 --- a/src/gui.py +++ b/src/gui.py @@ -48,6 +48,7 @@ class AppGui(QWidget): self.gui_frame.operator_wgt.setFixedHeight(640) self.gui_frame.expert_wgt.setFixedHeight(240) + #DAQ self.daq_wgt = self.daq_group_qtabwidget(widget_type='QStackedWidget') self.gui_frame.measurement_layout.addWidget( self.daq_wgt, 0, 1, 1, 1, alignment=Qt.AlignTop) @@ -55,11 +56,23 @@ class AppGui(QWidget): self.daq_wgt.setCurrentIndex(self.parent.default_idx) self.daq_wgt.currentChanged.emit(self.parent.default_idx) + #Accelerator Current + self.current_wgt = self.accelerator_current_group_qtabwidget( + widget_type='QStackedWidget') + self.gui_frame.measurement_layout.addWidget( + self.current_wgt, 1, 1, 1, 1, alignment=Qt.AlignTop) + + self.current_wgt.setCurrentIndex(self.parent.default_idx) + self.current_wgt.currentChanged.emit(self.parent.default_idx) + + #On change Injector/Cyclotron self.gui_frame.line_sender_dict[ 'accelerator'].currentChanged.connect(self.cb_accelerator) - + + def cb_accelerator(self, idx): self.daq_wgt.setCurrentIndex(idx) + self.current_wgt.setCurrentIndex(idx) def daq_group_qtabwidget(self, widget_type='QStackedWidget'): accel_wgt_dict = {} @@ -85,7 +98,7 @@ class AppGui(QWidget): accel_wgt_dict[accel] = self.daq_group(accel) accel_tab_widget.addWidget(accel_wgt_dict[accel]) - accel_tab_widget.setFixedWidth(300) + accel_tab_widget.setFixedWidth(320) accel_tab_widget.setFixedHeight(160) return accel_tab_widget @@ -98,24 +111,27 @@ class AppGui(QWidget): pv_daq = [] pv_daq.append(self.settings.data['PV'][accel]['daqTrigger']) pv_daq.append(self.settings.data['PV'][accel]['daqReady']) - + pv_daq.append(self.settings.data['PV'][accel]['daqErrorCount']) self.cafe.openPrepare() self.cafe.open(pv_daq) self.cafe.openNowAndWait(1.0) - pv1 = CAQLabel(self, pv_name=pv_daq[0]) - pv2 = CAQLabel(self, pv_name=pv_daq[1]) - pv1.setFixedWidth(40) - pv2.setFixedWidth(40) vbox.addWidget(QLabel('DAQ Trigger:'), 0, 0) vbox.addWidget(QLabel('DAQ Ready:'), 1, 0) - vbox.addWidget(pv1, 0, 1) - vbox.addWidget(pv2, 1, 1) + vbox.addWidget(QLabel('Error Count:'), 2, 0) + + pv_widget = [None] * len(pv_daq) + for i, pv in enumerate(pv_daq): + pv_widget[i] = CAQLabel(self, pv_name=pv) + vbox.addWidget(pv_widget[i], i, 1) + fwidth = 40 if 'ERR-CNT' not in pv else 60 + pv_widget[i].setFixedWidth(fwidth) + vbox.setContentsMargins(9, 19, 9, 9) vbox.setSpacing(5) vbox.setAlignment(Qt.AlignTop | Qt.AlignHCenter) - group_box.setFixedWidth(268) - group_box.setFixedHeight(100) + group_box.setFixedWidth(220) + group_box.setFixedHeight(140) group_box.setFont(self.font_gui) group_box.setAlignment(int(Qt.AlignTop | Qt.AlignHCenter)) group_box.setLayout(vbox) @@ -126,3 +142,73 @@ class AppGui(QWidget): qw.setLayout(grid) return qw + + + def accelerator_current_group_qtabwidget( + self, widget_type='QStackedWidget'): + accel_wgt_dict = {} + + if 'QTabWidget' in widget_type: + accel_tab_widget = QTabWidget() + accel_tab_widget.setFont(self.font_gui) + accel_tab_widget.setStyleSheet('QTabBar {font-size: 10pt;}') + accel_tab_widget.tabBar().setShape(QTabBar.TriangularNorth) + + for i, accel in enumerate(self.accelerator_list): + accel_wgt_dict[accel] = self.accelerator_current_group(accel) + + accel_tab_widget.addTab(accel_wgt_dict[accel], accel) + color = self.settings.data['Parameters']['accelerator']['data'][ + 'color'][i] + accel_tab_widget.tabBar().setTabTextColor(i, QColor(color)) + + else: + accel_tab_widget = QStackedWidget() + + for i, accel in enumerate(self.accelerator_list): + accel_wgt_dict[accel] = self.accelerator_current_group(accel) + accel_tab_widget.addWidget(accel_wgt_dict[accel]) + + accel_tab_widget.setFixedWidth(320) + accel_tab_widget.setFixedHeight(180) + return accel_tab_widget + + + def accelerator_current_group(self, accel): + group_box = QGroupBox(f'{accel} Current') + obj_name = 'CYCLOTRON' if self.parent.ring_cyclotron in accel else \ + 'INJECTOR' + group_box.setObjectName(obj_name) + vbox = QGridLayout() + pv_name = [] + pv_name.append(self.settings.data['PV'][accel]['IEntry']) + pv_name.append(self.settings.data['PV'][accel]['IExit']) + self.cafe.openPrepare() + self.cafe.open(pv_name) + self.cafe.openNowAndWait(1.0) + + vbox.addWidget(QLabel('I at Entry:'), 0, 0) + vbox.addWidget(QLabel('I at Exit:'), 1, 0) + + pv_widget = [None] * len(pv_name) + for i, pv in enumerate(pv_name): + pv_widget[i] = CAQLabel(self, pv_name=pv, show_units=True) + vbox.addWidget(pv_widget[i], i, 1) + fwidth = 120 + pv_widget[i].setFixedWidth(fwidth) + + vbox.setContentsMargins(9, 19, 9, 9) + vbox.setSpacing(5) + vbox.setAlignment(Qt.AlignTop | Qt.AlignHCenter) + group_box.setFixedWidth(220) + group_box.setFixedHeight(100) + group_box.setFont(self.font_gui) + group_box.setAlignment(int(Qt.AlignTop | Qt.AlignHCenter)) + group_box.setLayout(vbox) + + qw = QWidget() + grid = QGridLayout() + grid.addWidget(group_box, 0, 0) + qw.setLayout(grid) + + return qw diff --git a/tina.json b/tina.json index 230b79a..0e614b3 100755 --- a/tina.json +++ b/tina.json @@ -17,16 +17,20 @@ "PV" : {"Injector": {"nturns": "PV-INJ:NTURNS", "daqTrigger": "PV-INJ:TRG", "daqReady": "PV-INJ:READY", - "daqErrorCount": "PV-INJ:ERR_CNT", + "daqErrorCount": "PV-INJ:ERR-CNT", "wfEntry": "PV-INJ:WF-ENTRY", - "wfExit": "PV-INJ:WF-EXIT" + "wfExit": "PV-INJ:WF-EXIT", + "IEntry": "ENTRY:IST:1", + "IExit": "EXIT:IST:1" }, "Cyclotron": {"nturns": "ZTEST-CPSI-TCRING:TURN-NUM", "daqTrigger": "ZTEST-CPSI-TCRING:SCOPE-TRG", "daqReady": "ZTEST-CPSI-TCRING:SCOPE-READY", "daqErrorCount": "ZTEST-CPSI-TCRING:ERR-CNT", "wfEntry": "ZTEST-CPSI-TCRING:SCOPE-CH0", - "wfExit": "ZTEST-CPSI-TCRING:SCOPE-CH1" + "wfExit": "ZTEST-CPSI-TCRING:SCOPE-CH1", + "IEntry": "MNC3:IST:2", + "IExit": "MHC1:IST:2" } }, "HIPA": ["Injector", "Ring"], @@ -67,5 +71,6 @@ "subResultsTabTitle" : ["Correlations", "Raw Data"], "resultsSeq" : [1, 1], "showDate" : 1 - } + }, + "MeasurementGridLayout" : [0, 0, 3, 1] } diff --git a/tina.py b/tina.py index 6fea897..c83c9d7 100644 --- a/tina.py +++ b/tina.py @@ -53,6 +53,8 @@ class StartMain(BaseWindow): self.injector_2 # self.from_hdf = False in base class self.message = '' + self.correlation_peak_diff_min_value = 0.010 + self.gui = AppGui(self) def prepare_results_message(self): @@ -62,6 +64,7 @@ class StartMain(BaseWindow): self.no_turns = self.all_data['Processed data']['nturns'] lag_full = self.all_data['Processed data']['lag'] delay = self.all_data['Processed data']['delay'] + self.peak_diff = self.all_data['Processed data']['peak_diff'] except KeyError: self.message = '' self.message_elog = '' @@ -127,6 +130,29 @@ class StartMain(BaseWindow): QApplication.processEvents() return False + + if self.input_parameters['simulation']: + return True + + return True + + injector_current = self.cafe.getCache("MWC2:IST:2") + if not injector_current: + stat = self.cafe.getStatus("MWC2:IST:2") + self.check_status(_pymodule, 'getCache', injector_current, stat, + utils.line_no()) + mess = ('Unable to read Injector 2 current\n' + + 'Please try again.') + QMessageBox.information(self, 'Cyclotron', mess, QMessageBox.Ok) + QApplication.processEvents() + return False + elif injector_current < 0.001: + mess = ('Injector 2 current is below threshold.\n' + + 'Measurememt cannot be untertaken at the present time.') + QMessageBox.information(self, 'Cyclotron', mess, QMessageBox.Ok) + QApplication.processEvents() + return False + return True @Slot() @@ -288,6 +314,17 @@ class StartMain(BaseWindow): QApplication.processEvents() return False + if self.peak_diff < self.correlation_peak_diff_min_value: + mess = (f'Measurement is suspect as difference in top two peak \n' + + 'values of ' + + f'{self.peak_diff:0.3f} is less than accepted minimum ' + + f'of {self.correlation_peak_diff_min_value:0.3f}. \n' + + f'Analysis result is not saved to EPICS!') + QMessageBox.information(self, 'EPICS', mess, QMessageBox.Ok) + + QApplication.processEvents() + return False + simulation = self.input_parameters['simulation'] if not simulation: diff --git a/tina.sh b/tina.sh index 978da05..be6467d 100755 --- a/tina.sh +++ b/tina.sh @@ -67,7 +67,7 @@ echo "PYTHON_VERSION $PYTHON_VERSION" export PYTHONPATH=$PYTHON_PATH echo $PYTHONPATH -export EPICS_CA_ADDR_LIST=129.129.140.173 +#export EPICS_CA_ADDR_LIST=129.129.140.173 STDOUT_DIR="/tmp" #Set to 0 if you do not wish std::out to write to logger diff --git a/tina_office.sh b/tina_office.sh new file mode 100755 index 0000000..978da05 --- /dev/null +++ b/tina_office.sh @@ -0,0 +1,122 @@ +#!/bin/bash +cd /hipa/bd/applications/tina/devl + +# For use if script is sourced rather than executed +appNameDefault="tina.sh" + +module unload gcc +module load gcc/7.5.0 + +if [ -z "$PS1" ] # no prompt? +### if [ -v PS1 ] # On Bash 4.2+ ... +then + # non-interactive + echo "Non-interactive script" +else + # interactive + echo "Interactive/sourced script" +fi + +_EPICS_HOST_ARCH=${RHREL}-x86_64 + + +# Select Python Version here. Currently one of 3.5, 3.7, 3.8 and 3.10 +PYTHON_VERSION=3.10 +#cafe-1.20.0-gcc-7.5.0 +PYTHON_PATH=.:/opt/gfa/cafe/python/pycafe/cafe-1.21.0/lib/${_EPICS_HOST_ARCH}:/hipa/bd/applications/deps/apps4ops/v1.12.0 + +if [ "$1" ]; then + + if [ "$1" == "3.5" -o "$1" == "35" ]; then + echo "Using default version $PYTHON_VERSION" + elif [ "$1" == "3.7" -o "$1" == "37" ]; then + PYTHON_VERSION=3.7 + #cafe-1.20.0-gcc-7.3.0 + PYTHON_PATH=.:/opt/gfa/cafe/python/pycafe/cafe-1.21.0/lib/${_EPICS_HOST_ARCH}:/hipa/bd/applications/deps/apps4ops/v1.12.0 + #module unload gcc + #module load gcc/10.4.0 + + elif [ "$1" == "3.8" -o "$1" == "38" ]; then + PYTHON_VERSION=3.8 + #cafe-1.19.3 + PYTHON_PATH=.:/opt/gfa/cafe/python/pycafe/cafe-1.21.0/lib/${_EPICS_HOST_ARCH}:/hipa/bd/applications/deps/apps4ops/v1.12.0 + #module unload gcc + #module load gcc/7.5.0 + + elif [ "$1" == "3.10" -o "$1" == "310" ]; then + PYTHON_VERSION=3.10 + #cafe-1.20.0-gcc-7.5.0 + PYTHON_PATH=.:/opt/gfa/cafe/python/pycafe/cafe-1.21.0/lib/${_EPICS_HOST_ARCH}:/hipa/bd/applications/deps/apps4ops/v1.12.0 + #module unload gcc + #module load gcc/7.5.0 + else + echo "Requested Python version is not supported" + echo "Using default version $PYTHON_VERSION" + fi + +fi + + +echo "PYTHON_VERSION $PYTHON_VERSION" + +. /opt/gfa/python $PYTHON_VERSION + +#C_EXT version for Py 3.5, 3.7. 3.8, 3.10: + +#export PYTHONPATH=.:/opt/gfa/cafe/python/pycafe/cafe-1.19.3/lib/${_EPICS_HOST_ARCH}:/hipa/bd/applications/deps/apps4ops/v1.11.0 + +export PYTHONPATH=$PYTHON_PATH +echo $PYTHONPATH +export EPICS_CA_ADDR_LIST=129.129.140.173 + +STDOUT_DIR="/tmp" +#Set to 0 if you do not wish std::out to write to logger +STDOUT_FLAG=1 + +if [ "$#" -gt "0" ]; then + appName=$0 + if [ "$appName" == "-bash" ]; then + appName=$appNameDefault + fi +else +appName=$appNameDefault +fi + +#echo "$appName $@ $#" +baseName="${appName##*/}" +name=$(echo "$baseName" | cut -f 1 -d '.') +nameLog=${name}-$USER +echo "Application: $name" +echo "nameLog: $nameLog" + +#Configuration files can be overwritten +#python ${name}.py -s="/sf/bd/deps/pyqtacc/common/config/style.json" -f="/hipa/bd/applications/deps/apps4ops/v1.10.0/apps4ops/qrc_resources/facility/hipa/config/base.json" -q="/sf/bd/deps/pyqtacc/common/config/acc.qss" & + +python wakeup.py 00:00 & + +if [ "${STDOUT_FLAG}" -gt "0" ] ; then +#if changing the std::out destination, remember to also change it in your json config file (for reading) + if test -f "$STDOUT_DIR/${nameLog}.log---"; then + rm -f $STDOUT_DIR/${nameLog}.log--- + fi + if test -f "$STDOUT_DIR/${nameLog}.log--"; then + cp $STDOUT_DIR/${nameLog}.log-- $STDOUT_DIR/${nameLog}.log--- + rm -f $STDOUT_DIR/${nameLog}.log-- + fi + if test -f "$STDOUT_DIR/${nameLog}.log-"; then + cp $STDOUT_DIR/${nameLog}.log- $STDOUT_DIR/${nameLog}.log-- + rm -f $STDOUT_DIR/${nameLog}.log- + fi + if test -f "$STDOUT_DIR/${nameLog}.log"; then + cp $STDOUT_DIR/${nameLog}.log $STDOUT_DIR/${nameLog}.log- + rm -f $STDOUT_DIR/${nameLog}.log + fi + + python ${name}.py -u ${name}.json >> $STDOUT_DIR/${nameLog}.log 2>&1 & + chmod 777 $STDOUT_DIR/${nameLog}.log +else +#Run instead without std::out + python ${name}.py -u ${name}.json & +fi + +