def _reset_bpm_offset(): bpms = getElements('BPM') pvs = [] for b in bpms: #print b.pv(tags=['aphla.offset', 'aphla.eput']) pvs.extend(b.pv(tags=['aphla.offset', 'aphla.eput'])) if pvs: caput(pvs, 0.0) _logger.info("Reset the bpm offset")
def _release_lock(tag): if caget('SVR:LOCKED') == 0: raise ValueError("some one already reset the lock") if caget('SVR:LOCKED') != tag: raise ValueError("it is not locked by me, abort") caput('SVR:LOCKED', 0) print "released the lock for userid=%d" % tag
def checkOrbitReproduce(self, bpm, trim): print "checking ..." print " bpm:", len(bpm) print " trim:", trim # skip the masked value itrim, ibpm = [], [] for i, b in enumerate(self.bpm): if b[0] in bpm: ibpm.append(i) for i, t in enumerate(self.trim): if t[0] in trim: itrim.append(i) if len(itrim) == 0: # No trim specified. return kick0 = np.zeros(len(itrim), 'd') for j,jt in enumerate(itrim): # read the setpoint kick0[j] = caget(self.trim[jt][3]) dkick = np.random.rand(len(itrim))*5e-5 + 6e-5 # get the initial orbit x0 = np.zeros(len(ibpm), 'd') for i,ib in enumerate(ibpm): x0[i] = caget(self.bpm[ib][2]) dx = np.zeros(len(ibpm), 'd') for i,ib in enumerate(ibpm): for j,jt in enumerate(itrim): # skip the masked ORM elements if self._mask[ib, jt]: continue dx[i] = dx[i] + self.m[ib, jt]*dkick[j] for j, jt in enumerate(itrim): caput(self.trim[jt][3], kick0[j] + dkick[j]) time.sleep(self.TSLEEP) # get the final orbit x1 = np.zeros(len(ibpm), 'd') for i,ib in enumerate(ibpm): x1[i] = caget(self.bpm[ib][2]) #print x1 # reset the trims for j,jt in enumerate(itrim): caput(self.trim[jt][3], kick0[j]) time.sleep(self.TSLEEP) # return experiment and theory return x0, x1, dx
def checkOrbitReproduce(self, bpm, trim): print("checking ...") print((" bpm:", len(bpm))) print((" trim:", trim)) # skip the masked value itrim, ibpm = [], [] for i, b in enumerate(self.bpm): if b[0] in bpm: ibpm.append(i) for i, t in enumerate(self.trim): if t[0] in trim: itrim.append(i) if len(itrim) == 0: # No trim specified. return kick0 = np.zeros(len(itrim), 'd') for j,jt in enumerate(itrim): # read the setpoint kick0[j] = caget(self.trim[jt][3]) dkick = np.random.rand(len(itrim))*5e-5 + 6e-5 # get the initial orbit x0 = np.zeros(len(ibpm), 'd') for i,ib in enumerate(ibpm): x0[i] = caget(self.bpm[ib][2]) dx = np.zeros(len(ibpm), 'd') for i,ib in enumerate(ibpm): for j,jt in enumerate(itrim): # skip the masked ORM elements if self._mask[ib, jt]: continue dx[i] = dx[i] + self.m[ib, jt]*dkick[j] for j, jt in enumerate(itrim): caput(self.trim[jt][3], kick0[j] + dkick[j]) time.sleep(self.TSLEEP) # get the final orbit x1 = np.zeros(len(ibpm), 'd') for i,ib in enumerate(ibpm): x1[i] = caget(self.bpm[ib][2]) #print x1 # reset the trims for j,jt in enumerate(itrim): caput(self.trim[jt][3], kick0[j]) time.sleep(self.TSLEEP) # return experiment and theory return x0, x1, dx
def restoreBpmStatus(bpmstats): """ restore BPM status from the output of getBpmStatus see also `getBpmStatus` """ for k, v in bpmstats.items(): v0 = caget(v[0]) idx = [i for i in range(len(v[1])) if v[1][i] != v0[i]] pvs = [v[0][i] for i in idx] vals = [v[1][i] for i in idx] try: caput(pvs, vals, throw=True, timeout=5) except: for i, pv in numerate(pvs): caput(pv, vals, timeout=5)
def restoreBpmStatus(bpmstats): """ restore BPM status from the output of getBpmStatus see also `getBpmStatus` """ for k,v in bpmstats.items(): v0 = caget(v[0]) idx = [i for i in range(len(v[1])) if v[1][i] != v0[i]] pvs = [v[0][i] for i in idx] vals = [v[1][i] for i in idx] try: caput(pvs, vals, throw = True, timeout=5) except: for i,pv in numerate(pvs): caput(pv, vals, timeout=5)
def putLattice(h5fname, **kwargs): """ elemflds : list of (elementfam, list_of_fields), e.g. [("COR", ("x", "y"))] nstep : 3, split each setpoint in steps tspan : 3.0, span over tspan seconds when set magnet in several steps. :: >>> putLattice("sr_snapshot.hdf5", elemflds=[("COR", ("x", "y"))]) """ nstep = kwargs.get("nstep", 3) tspan = kwargs.get("tspan", 3.0) elemflds = kwargs.get("elemflds", []) lat = machines._lat pvspl, pvs = [], [] for elfam, flds in elemflds: el = lat.getElementList(elfam, virtual=False) for fld in flds: pvs.extend( reduce(lambda a, b: a + b, [e.pv(field=fld) for e in el])) pvspl.extend( reduce(lambda a, b: a + b, [e.pv(field=fld, handle="setpoint") for e in el])) import h5py h5f = h5py.File(h5fname, 'r') grp = h5f[lat.name] if not pvspl: print "Please select element family and fields in this snapshot:" for famflds in grp.attrs.get("_query_", []): m = re.match(r"([^(]+)\((.+)\)", famflds) if not m: print famflds continue print m.group(1), m.group(2).split(",") #print grp.attrs.get("_query_", []) else: vals = [grp[pv].value for pv in pvspl] dv = [(vals[j] - v) / nstep for j, v in enumerate(caget(pvspl))] for i in range(nstep): t0 = datetime.now() vi = [vals[j] - (nstep - 1 - i) * dv[j] for j in range(len(vals))] caput(pvspl, vi, timeout=tspan) dt = (datetime.now() - t0).total_seconds() if dt < tspan * 1.0 / nstep: time.sleep(tspan * 1.0 / nstep - dt + 0.1) h5f.close()
def putLattice(h5fname, **kwargs): """ elemflds : list of (elementfam, list_of_fields), e.g. [("COR", ("x", "y"))] nstep : 3, split each setpoint in steps tspan : 3.0, span over tspan seconds when set magnet in several steps. :: >>> putLattice("sr_snapshot.hdf5", elemflds=[("COR", ("x", "y"))]) """ nstep = kwargs.get("nstep", 3) tspan = kwargs.get("tspan", 3.0) elemflds = kwargs.get("elemflds", []) lat = machines._lat pvspl, pvs = [], [] for elfam,flds in elemflds: el = lat.getElementList(elfam, virtual=False) for fld in flds: pvs.extend( reduce(lambda a,b: a+b, [e.pv(field=fld) for e in el])) pvspl.extend( reduce(lambda a,b: a+b, [e.pv(field=fld, handle="setpoint") for e in el])) import h5py h5f = h5py.File(h5fname, 'r') grp = h5f[lat.name] if not pvspl: print "Please select element family and fields in this snapshot:" for famflds in grp.attrs.get("_query_", []): m =re.match(r"([^(]+)\((.+)\)", famflds) if not m: print famflds continue print m.group(1), m.group(2).split(",") #print grp.attrs.get("_query_", []) else: vals = [grp[pv].value for pv in pvspl] dv = [(vals[j] - v) / nstep for j,v in enumerate(caget(pvspl))] for i in range(nstep): t0 = datetime.now() vi = [vals[j] - (nstep - 1 - i)*dv[j] for j in range(len(vals))] caput(pvspl, vi, timeout=tspan) dt = (datetime.now() - t0).total_seconds() if dt < tspan * 1.0 / nstep: time.sleep(tspan * 1.0 / nstep - dt + 0.1) h5f.close()
def fput(elemfld_vals, **kwargs): """set elements field values for a family Parameters ----------- elemfld_vals : list or tuple. A list of (element, field, value) wait_readback : True/False. default False. Waiting until readback agrees timeout : int, optional, default 5, in seconds. unitsys : None or str, default "phy", unit system. epsilon : float, list or tuple. default None. verbose : int, verbose Examples --------- >>> cors = getElements("COR") >>> elemfld = [(cors[0], 'x', 0.0), (cors[0], 'y')] >>> fput(elemfld, wait_readback = True, epsilon=[0.1, 0.1]) If epsilon is not provided, use system configured. """ # timeout = kwargs.pop('timeout', 5) unitsys = kwargs.pop('unitsys', "phy") wait_readback = kwargs.pop('wait_readback', False) epsilon = kwargs.pop("epsilon", None) # a list of (pv, spval, elem, field) pvl = [] if epsilon is None: epsl = [e.getEpsilon(fld) for e,fld,v in elemfld_vals] elif isinstance(epsilon, (list, tuple)): epsl = epsilon else: epsl = [epsilon] * len(elemfld_vals) for i,r in enumerate(elemfld_vals): elem, fld, val = r valrec = [val, val - epsl[i], val + epsl[i]] if unitsys is not None: valrec = [elem.convertUnit(fld, v, unitsys, None) for v in valrec] pvsp = elem.pv(field=fld, handle="setpoint") pvrb = elem.pv(field=fld, handle="readback") for j,pv in enumerate(zip(pvsp, pvrb)): pvl.append([elem, fld, pv[0], pv[1]] + valrec) pvsp = [v[2] for v in pvl] pvrb = [v[3] for v in pvl] vals = [v[4] for v in pvl] ret = caput(pvsp, vals, **kwargs) if wait_readback: vallo, valhi = [v[5] for v in pvl], [v[6] for v in pvl] try: caWaitStable(pvrb, vals, vallo, valhi, **kwargs) except: _logger.error("failed setting {0}={1}".format(pvsp, vals)) raise
def _wait_for_lock(tag, maxwait=60): """ wait until the virtual accelerator is available to me. """ print "# Locking the mathine for userid=%d" % tag if tag == 0: raise ValueError("you tag (=%d) must be > 0." % tag) t0 = time.time() while caget('SVR:LOCKED') > 0: print "# waiting ... for user %d ..." % int(caget('SVR:LOCKED')) time.sleep(1) if time.time() - t0 > maxwait: break if caget('SVR:LOCKED') == 0: caput('SVR:LOCKED', tag) else: raise ValueError("can not get the writting permission to virtual accelerator")
def fput(elemfld_vals, **kwargs): """set elements field values for a family Parameters ----------- elemfld_vals : list or tuple. A list of (element, field, value) wait_readback : True/False. default False. Waiting until readback agrees timeout : int, optional, default 5, in seconds. unitsys : None or str, default "phy", unit system. epsilon : float, list or tuple. default None. verbose : int, verbose Examples --------- >>> cors = getElements("COR") >>> elemfld = [(cors[0], 'x', 0.0), (cors[0], 'y')] >>> fput(elemfld, wait_readback = True, epsilon=[0.1, 0.1]) If epsilon is not provided, use system configured. """ # timeout = kwargs.pop('timeout', 5) unitsys = kwargs.pop('unitsys', "phy") wait_readback = kwargs.pop('wait_readback', False) epsilon = kwargs.pop("epsilon", None) # a list of (pv, spval, elem, field) pvl = [] if epsilon is None: epsl = [e.getEpsilon(fld) for e, fld, v in elemfld_vals] elif isinstance(epsilon, (list, tuple)): epsl = epsilon else: epsl = [epsilon] * len(elemfld_vals) for i, r in enumerate(elemfld_vals): elem, fld, val = r valrec = [val, val - epsl[i], val + epsl[i]] if unitsys is not None: valrec = [elem.convertUnit(fld, v, unitsys, None) for v in valrec] pvsp = elem.pv(field=fld, handle="setpoint") pvrb = elem.pv(field=fld, handle="readback") for j, pv in enumerate(zip(pvsp, pvrb)): pvl.append([elem, fld, pv[0], pv[1]] + valrec) pvsp = [v[2] for v in pvl] pvrb = [v[3] for v in pvl] vals = [v[4] for v in pvl] ret = caput(pvsp, vals, **kwargs) if wait_readback: vallo, valhi = [v[5] for v in pvl], [v[6] for v in pvl] try: caWaitStable(pvrb, vals, vallo, valhi, **kwargs) except: _logger.error("failed setting {0}={1}".format(pvsp, vals)) raise
def _wait_for_lock(tag, maxwait=60): """ wait until the virtual accelerator is available to me. """ print "# Locking the mathine for userid=%d" % tag if tag == 0: raise ValueError("you tag (=%d) must be > 0." % tag) t0 = time.time() while caget('SVR:LOCKED') > 0: print "# waiting ... for user %d ..." % int(caget('SVR:LOCKED')) time.sleep(1) if time.time() - t0 > maxwait: break if caget('SVR:LOCKED') == 0: caput('SVR:LOCKED', tag) else: raise ValueError( "can not get the writting permission to virtual accelerator")
def _reset_trims(verbose=False): """reset all trims in group *HCOR* and *VCOR* """ trimx = machines._lat.getGroupMembers(['*', 'HCOR'], op='intersection') trimy = machines._lat.getGroupMembers(['*', 'VCOR'], op='intersection') pv = [] for e in trimx: pv.extend(e.pv(field='x', handle='setpoint')) for e in trimy: pv.extend(e.pv(field='y', handle='setpoint')) if not pv: raise ValueError("no pv for trims found") if verbose: for p in pv: print p, caget(p), caput(p, 0.0, wait=True) print caget(p) else: caput(pv, 0.0) _logger.info("reset all trims")
def _brBpmScrub(**kwargs): """ waveforms - list of Tbt, Fa and Adc """ lat = machines.getLattice() if lat.name != "BR": raise RuntimeError("the current lattice is not 'BR': %s" % lat.name) waveforms = kwargs.get("waveforms", ["Tbt", "Fa", "Adc"]) bpms = getElements("BPM") # did not consider the 'ddrTbtWfEnable' PV for bpm in bpms: pvx = bpm.pv(field="x")[0] pv = pvx.replace("Pos:X-I", "Trig:TrigSrc-SP") # 0 - internal, 1 - external caput(pv, 0, wait=True) pv = pvx.replace("Pos:X-I", "DDR:WfmSel-SP") for fld in waveforms: pv = pvx.replace("Pos:X-I", "ddr%sWfEnable" % fld) caput(pv, 0, wait=True) # offset pv = pvx.replace("Pos:X-I", "ddr%sOffset" % fld) caput(pv, 0, wait=True) time.sleep(2) for bpm in bpms: pvx = bpm.pv(field="x")[0] pv = pvx.replace("Pos:X-I", "Trig:TrigSrc-SP") # 0 - internal, 1 - external caput(pv, 1, wait=True) pv = pvx.replace("Pos:X-I", "DDR:WfmSel-SP") for fld in waveforms: pv = pvx.replace("Pos:X-I", "ddr%sWfEnable" % fld) caput(pv, 1, wait=True) time.sleep(2)
def resetBrBpms(wfmsel=1): """ reset the BPMs to external trigger and Tbt waveform. Offset is 0 for all Adc, Tbt and Fa waveforms. """ pvprefs = [ bpm.pv(field="x")[0].replace("Pos:X-I", "") for bpm in getElements("BPM") ] for i, pvx in enumerate(pvprefs): pvs = [pvx + "Trig:TrigSrc-SP" for pvx in pvprefs] caput(pvs, 1, wait=True) # 0 - Adc, 1 - Tbt, 2 - Fa pvs = [pvx + "DDR:WfmSel-SP" for pvx in pvprefs] caput(pvs, wfmsel, wait=True) # enable all three waveforms pvs = [pvx + "ddrAdcWfEnable" for pvx in pvprefs] caput(pvs, 1, wait=True) pvs = [pvx + "ddrTbtWfEnable" for pvx in pvprefs] caput(pvs, 1, wait=True) pvs = [pvx + "ddrFaWfEnable" for pvx in pvprefs] caput(pvs, 1, wait=True) # pvs = [pvx + "ddrAdcOffset" for pvx in pvprefs] caput(pvs, 0, wait=True) pvs = [pvx + "ddrTbtOffset" for pvx in pvprefs] caput(pvs, 0, wait=True) pvs = [pvx + "ddrFaOffset" for pvx in pvprefs] caput(pvs, 0, wait=True)
def correctBrOrbit(kker, m, **kwarg): """correct the resp using kker and response matrix. Parameters ------------ kker : PV list of the controllers, e.g. corrector m : response matrix where :math:`m_{ij}=\Delta orbit_i/\Delta kker_j` scale : scaling factor applied to the calculated kker ref : the targeting value of orbit rcond : the rcond for cutting singular values. check : stop if the orbit gets worse. wait : waiting (seconds) before check. Returns -------- err : converged or not checked (0), error (>0). msg : error message or None """ scale = kwarg.get('scale', 0.68) ref = kwarg.get('ref', None) check = kwarg.get('check', True) wait = kwarg.get('wait', 6) rcond = kwarg.get('rcond', 1e-2) verb = kwarg.get('verbose', 0) bc = kwarg.get('bc', None) wfmslice = kwarg.get("wfmslice", (10, 100)) wfm = kwarg.pop("waveform", "Fa") exrows = kwarg.pop("exclude_rows", []) test = kwarg.pop("test", False) #u, s, v = np.linalg.svd(m) #plt.semilogy(s/s[0], 'x-') #plt.show() i0, i1 = wfmslice nbpm, ncor = np.shape(m) mask_row = np.ones(nbpm, 'i') for i in exrows: mask_row[i] = 0 m = np.compress(mask_row, m, axis=0) print "New m shape:", np.shape(m) name, x0, y0, Isum0, ts, offset = getBrBpmData(waveform=wfm, trig=0) # save initial orbit in vx0 vl0 = np.compress(mask_row, np.vstack((x0, y0)), axis=0) v0 = np.average(vl0[:, i0:i1], axis=1) if np.max(v0) > 10000 or np.min(v0) < -10000: plt.plot(v0) plt.show() raise RuntimeError("orbit is not stable, too large: %.2f, %.2f" % (np.min(v0), np.max(v0))) if ref is not None: v0 = v0 - ref if len(v0) != len(m): raise RuntimeError("inconsistent BPM and ORM size") # the initial norm norm0 = np.linalg.norm(v0) # solve for m*dk + (v0 - ref) = 0 dk, resids, rank, s = np.linalg.lstsq(m, -1.0 * v0, rcond=rcond) norm1 = np.linalg.norm(m.dot(dk * scale) + v0) # get the DC kicker kl0 = np.array(caget(kker), 'd') k0 = np.average(kl0, axis=1) print np.shape(kl0) #print k0, dk, scale k1 = k0 + dk * scale vk1 = [[k] * len(kl0[i]) for i, k in enumerate(k1)] plt.plot(k0, 'r-', label="initial") plt.plot(k1, 'b-', label="new") plt.legend() plt.show() if not test: caput(kker, vk1, wait=True) else: for i, pv in enumerate(kker): print i, pv, k1[i], "dk=", dk[i] time.sleep(wait) name, x1, y1, Isum1, ts, offset = getBrBpmData(waveform=wfm, trig=0) vl1 = np.compress(mask_row, np.vstack((x1, y1)), axis=0) v1 = np.average(vl1[:, i0:i1], axis=1) print norm0, "predicted norm= ", norm1, "realized:", np.linalg.norm(v1) return v0, v1, k0, k1
def _brBpmTrigData(pvprefs, waveform, **kwargs): """ """ offset = kwargs.pop("offset", 0) sleep = kwargs.pop("sleep", 0.5) tc = kwargs.get("timeout", 6) verbose = kwargs.get("verbose", 0) t0 = datetime.now() # prepare the triggers pv_evg = "BR-BI{BPM}Evt:Single-Cmd" pv_trig = [] pv_wfmsel, pv_adcwfm, pv_tbtwfm, pv_fawfm = [], [], [], [] pv_adcoffset, pv_tbtoffset, pv_faoffset = [], [], [] pv_ddrts = [] # timestamp pv_ts, pv_tsns = [], [] # timestamp second and nano sec pv_trigts, pv_trigtsns = [], [] # trigger timestamp # did not consider the 'ddrTbtWfEnable' PV for i, pvx in enumerate(pvprefs): #print bpm.name, pvh, caget(pvh) pv_trig.append(pvx + "Trig:TrigSrc-SP") pv_wfmsel.append(pvx + "DDR:WfmSel-SP") pv_ddrts.append(pvx + "TS:DdrTrigDate-I") pv_adcwfm.append(pvx + "ddrAdcWfEnable") pv_tbtwfm.append(pvx + "ddrTbtWfEnable") pv_fawfm.append(pvx + "ddrFaWfEnable") # pv_adcoffset.append(pvx + "ddrAdcOffset") pv_tbtoffset.append(pvx + "ddrTbtOffset") pv_faoffset.append(pvx + "ddrFaOffset") pv_ts.append(pvx + "Trig:TsSec-I") pv_tsns.append(pvx + "Trig:TsOff-I") pv_trigts.append(pvx + "Trig:TsSec-I") pv_trigtsns.append(pvx + "Trig:TsOff-I") # # save initial val wfsel0 = caget(pv_wfmsel, timeout=tc) trig0 = caget(pv_trig, timeout=tc) # set the trigger internal, TBT waveform prf = "" if waveform == "Adc": caput(pv_wfmsel, 0, wait=True) caput(pv_adcwfm, 1, wait=True) caput(pv_adcoffset, offset, wait=True) pv_ddroffset = pv_adcoffset prf = "" elif waveform == "Tbt": caput(pv_wfmsel, 1, wait=True) caput(pv_tbtwfm, 1, wait=True) caput(pv_tbtoffset, offset, wait=True) pv_ddroffset = pv_tbtoffset prf = "TBT" elif waveform == "Fa": caput(pv_wfmsel, 2, wait=True) caput(pv_fawfm, 1, wait=True) caput(pv_faoffset, offset, wait=True) pv_ddroffset = pv_faoffset prf = "FA" else: raise RuntimeError("unknow waveform '%s'" % waveform) time.sleep(1.5) pv_x, pv_y, pv_S = [], [], [] pv_A, pv_B, pv_C, pv_D = [], [], [], [] for i, pvx in enumerate(pvprefs): pv_x.append(pvx + "%s-X" % prf) pv_y.append(pvx + "%s-Y" % prf) pv_S.append(pvx + "%s-S" % prf) pv_A.append(pvx + "%s-A" % prf) pv_B.append(pvx + "%s-B" % prf) pv_C.append(pvx + "%s-C" % prf) pv_D.append(pvx + "%s-D" % prf) # set 0 - internal trig, 1 - external trig caput(pv_trig, 0, wait=True, timeout=tc) # set the event caput(pv_evg, 1, wait=True) time.sleep(sleep) # check timestamp n = 0 while True: tss_r = caget(pv_trigts, timeout=tc) tss = [t - min(tss_r) for t in tss_r] tsns = caget(pv_trigtsns, timeout=tc) ts = [s + 1.0e-9 * tsns[i] for i, s in enumerate(tss)] mdt = max(ts) - min(ts) ddrts0 = caget(pv_ddrts) mdt_s = _maxTimeSpan(caget(pv_ddrts, timeout=tc)) n = n + 1 if mdt < 1.0 and mdt_s < 1.0: #print "Max dt=", mdt, mdt_s, "tried %d times" % n break time.sleep(0.6) # quit if failed too many times if n > 20: caput(pv_trig, [1] * len(pv_trig), wait=True) raise RuntimeError("BPMs are not ready after %d trials" % n) if verbose > 0: print "Trials: %d, Trig=%.2e, DDR Trig=%.2e seconds." % (n, mdt, mdt_s) # redundent check ddrts0 = caget(pv_ddrts, timeout=tc) mdt = _maxTimeSpan(ddrts0) if mdt > 1.0: print "ERROR: Timestamp does not agree (max dt= %f), wait ..." % mdt ddroffset = caget(pv_ddroffset, timeout=tc) data = (caget(pv_x), caget(pv_y), caget(pv_S)) # data = np.array(data, 'd') # set 0 - internal trig, 1 - external trig caput(pv_trig, 1, wait=True) return data[0], data[1], data[2], ddrts0, ddroffset
def measBrCaRmCol(kker, **kwargs): """measure the response matrix column between PVs (DC) kker - SP PV for corrector (waveform) waveform - "Fa" or "Tbt" timeout - 6 sec, EPICS CA timeout npoints - number of orbits for each kick. dxlst - a list of kick (raw unit), overwrite the choice of dxmax dxmax - range of kick [-dxmax, dxmax] ndx - default 4. Specify kicks in [-dxmax, dxmax]. wait - default 1.5 second output - save the results verbose - default 0 return the output file name. The output will be in HDF5 file format. """ timeout = kwargs.pop("timeout", 6) wait = kwargs.pop("wait", 1.5) verbose = kwargs.pop("verbose", 0) npt = kwargs.pop("npoints", 4) wfm = kwargs.pop("waveform", "Fa") t0 = datetime.now() dxlst, x0 = [], np.array(caget(kker, timeout=timeout), 'd') if "dxlst" in kwargs: dxlst = kwargs.get("dxlst") elif "dxmax" in kwargs: dxmax = np.abs(kwargs.get("dxmax")) nx = kwargs.pop("ndx", 4) dxlst = list(np.linspace(-dxmax, dxmax, nx)) else: raise RuntimeError("need input for at least of the parameters: " "dxlst, xlst, dxmax") # use the provided filename or default datetimed filename output_file = kwargs.pop( "output", os.path.join(machines.getOutputDir(), t0.strftime("%Y_%m"), "orm", t0.strftime("orm_%Y_%m_%d_%H%M%S.hdf5"))) # save dx list h5f = h5py.File(output_file) grp = h5f.create_group(kker) grp.attrs["orm_t0"] = t0.strftime("%Y_%m_%d_%H:%M:%S.%f") grp["dxlst"] = dxlst h5f.close() # save the initial orbit getBrBpmData(waveform=wfm, verbose=verbose-1, output_file=output_file, h5group="%s/%s0" % (kker, wfm), **kwargs) n1 = len(dxlst) for i,dx in enumerate(dxlst): if verbose > 0: print "%d/%d: Setting %s " % (i, n1, kker), dx sys.stdout.flush() try: nx0 = len(x0) xi = [x0i + dx for x0i in x0] except: # should never happen for booster xi = x0 + dx caput(kker, xi, wait=True, timeout=timeout) time.sleep(wait*3) for j in range(npt): obt, fname = getBrBpmData( waveform=wfm, verbose=verbose-1, output_file=output_file, h5group="%s/%s_dx%d__pt%d" % (kker, wfm, i, j), **kwargs) if verbose > 1: name, x, y, Is, ts, ddroffset = obt print " %d/%d" % (j,npt), np.average(x[0]), np.std(x[0]) sys.stdout.flush() time.sleep(wait) time.sleep(wait) caput(kker, x0, wait=True, timeout=timeout) t1 = datetime.now() h5f = h5py.File(output_file) h5f[kker].attrs["orm_t1"] = t1.strftime("%Y_%m_%d_%H:%M:%S.%f") h5f.close() return output_file
def measKickedTbtData(idriver, ampl, **kwargs): """ take turn-by-turn BPM data after kicking the beam. Parameters ----------- idriver : int which driver used to kick the beam: injection kicker 3(3) or 4(4), vertical pinger(5), horizontal pinger(6), both H/V pingers(7). ampl : float, tuple kicking amplitude. bpms : list of element objects. provide the BPMs to take data from, default ["BPM" or "UBPM"] count : int number of turns. output : str, True, False output file name, or default (True), or no output (False) verbose : int it will set kicker/pinger and wait 100sec or readback-setpoint agree. event code 47 will be used for kicker 3 and 4, 35 used for pingers. Same returns as `getSrBpmData` Examples --------- >>> (name, x, y, Isum, ts, offset) = measKickedTbtData(7, (0.15, 0.2)) >>> (name, x, y, Isum, ts, offset), output = measKickedTbtData(7, (0.15, 0.2), output=True) """ verbose = kwargs.get("verbose", 0) output = kwargs.get("output", True) sleep = kwargs.get("sleep", 5) count = kwargs.get("count", 2000) bpms = [ b for b in kwargs.get("bpms", getGroupMembers(["BPM", "UBPM"], op="union")) if b.isEnabled() ] bpmstats = getBpmStatus(bpms) kpvsp, kpvrb = None, None # 0 - both off, 1 - V-on, 2-H-on, 3-both-on pv_pinger_mode = "SR:C21-PS{Pinger}Mode:Trig-Sel" if idriver in [3, 4, 5, 6]: if idriver in [3, 4]: kpvsp = 'SR:IS-PS{Kick:%d}V-Sp' % idriver kpvrb = 'SR:IS-PS{Kick:%d}Hvps-V-Rb-1st' % idriver kpvon = 'SR:IS-PS{Kick:%d}HvpsOnOff_Cmd' % idriver elif idriver in [ 5, ]: # vertical pinger kpvsp = 'SR:C21-PS{Pinger:V}V-Sp' kpvrb = 'SR:C21-PS{Pinger:V}Setpoint-Rb.VALA' kpvon = 'SR:C21-PS{Pinger:V}HvpsOnOff_Cmd' caput(pv_pinger_mode, 1) elif idriver in [ 6, ]: # horizontal pinger kpvsp = 'SR:C21-PS{Pinger:H}V-Sp' kpvrb = 'SR:C21-PS{Pinger:H}Setpoint-Rb.VALA' kpvon = 'SR:C21-PS{Pinger:H}HvpsOnOff_Cmd' caput(pv_pinger_mode, 2) # caput(kpvsp, 0.0) for i in range(100): if caget(kpvrb, count=1) < 0.001: break time.sleep(1) caput(kpvon, 1) elif idriver in [ 7, ]: # both pinger kpvsp = ['SR:C21-PS{Pinger:H}V-Sp', 'SR:C21-PS{Pinger:V}V-Sp'] kpvrb = [ 'SR:C21-PS{Pinger:H}Setpoint-Rb.VALA', 'SR:C21-PS{Pinger:V}Setpoint-Rb.VALA' ] kpvon = [ 'SR:C21-PS{Pinger:H}HvpsOnOff_Cmd', 'SR:C21-PS{Pinger:V}HvpsOnOff_Cmd' ] caput(pv_pinger_mode, 3) caput(kpvsp, [0.0, 0.0]) for i in range(100): rb = caget(kpvrb, count=1) if rb[0] < 0.001 and rb[1] < 0.001: break time.sleep(0.5) caput(kpvon, [1, 1]) # set the kicker/pinger voltage caput(kpvsp, ampl, wait=True) #(name, x, y, Isum, ts, offset), output = ap.nsls2.getSrBpmData( # trig=1, count=5000, output=True, h5group="k_%d" % idriver) h5g = "k_%d" % idriver Idcct0 = caget('SR:C03-BI{DCCT:1}I:Total-I') time.sleep(sleep) # request an injection: if idriver in [ 3, 4, ]: resetSrBpm(bpms=bpms, evcode=47) time.sleep(1) caput('ACC-TS{EVG-SSC}Request-Sel', 1) elif idriver in [5, 6, 7]: resetSrBpms(bpms=bpms, evcode=35) # do it twice caput('SR:C21-PS{Pinger}Ping-Cmd', 1) time.sleep(1) caput('SR:C21-PS{Pinger}Ping-Cmd', 1) time.sleep(2) Idcct1 = caget('SR:C03-BI{DCCT:1}I:Total-I') bpmdata = getSrBpmData(trig=1, bpms=bpms, count=count, output=output, h5group=h5g) # record pinger wave, V-chan1, H-chan2 pinger_delay, pinger_wave, pinger_mode = None, None, None if idriver in [5, 6, 7]: pinger_wave = caget([ "SR:C21-PS{Dig:Png1}TimeScale-I", "SR:C21-PS{Dig:Png1}Data:Chan2-I", "SR:C21-PS{Dig:Png1}Data:Chan1-I" ]) pinger_delay = caget( ["SR:C21-PS{Pinger:H}Delay-SP", "SR:C21-PS{Pinger:V}Delay-SP"]) pinger_mode = caget("SR:C21-PS{Pinger}Mode:Trig-Sts") # repeat_value=True caput(kpvon, 0) caput(kpvsp, 0.0) if output: (name, x, y, Isum, ts, offset), output = bpmdata f = h5py.File(output) g = f[h5g] g["I"] = Idcct1 g["I"].attrs["dI"] = Idcct1 - Idcct0 g["RF_SP"] = float(caget('RF{Osc:1}Freq:SP')) g["RF_I"] = float(caget('RF{Osc:1}Freq:I')) g.attrs["ampl"] = ampl g.attrs["idriver"] = idriver g.attrs["pvsp"] = kpvsp g.attrs["pvrb"] = kpvrb g.attrs["pvon"] = kpvon if pinger_wave is not None: g["pinger_wave"] = np.array(pinger_wave, 'd').transpose() if pinger_delay is not None: g["pinger_delay"] = pinger_delay if pinger_mode is not None: g["pinger_mode"] = pinger_mode f.close() # restore restoreBpmStatus(bpmstats) return bpmdata
def resetBrBpms(wfmsel = 1): """ reset the BPMs to external trigger and Tbt waveform. Offset is 0 for all Adc, Tbt and Fa waveforms. """ pvprefs = [bpm.pv(field="x")[0].replace("Pos:X-I", "") for bpm in getElements("BPM")] for i,pvx in enumerate(pvprefs): pvs = [ pvx + "Trig:TrigSrc-SP" for pvx in pvprefs] caput(pvs, 1, wait=True) # 0 - Adc, 1 - Tbt, 2 - Fa pvs = [ pvx + "DDR:WfmSel-SP" for pvx in pvprefs] caput(pvs, wfmsel, wait=True) # enable all three waveforms pvs = [ pvx + "ddrAdcWfEnable" for pvx in pvprefs] caput(pvs, 1, wait=True) pvs = [ pvx + "ddrTbtWfEnable" for pvx in pvprefs] caput(pvs, 1, wait=True) pvs = [ pvx + "ddrFaWfEnable" for pvx in pvprefs] caput(pvs, 1, wait=True) # pvs = [ pvx + "ddrAdcOffset" for pvx in pvprefs] caput(pvs, 0, wait=True) pvs = [ pvx + "ddrTbtOffset" for pvx in pvprefs] caput(pvs, 0, wait=True) pvs = [ pvx + "ddrFaOffset" for pvx in pvprefs] caput(pvs, 0, wait=True)
def resetSrBpms(wfmsel = None, name = "BPM", evcode = None, verbose=0, bpms=None, trigsrc = None): """ reset the BPMs to external trigger and Tbt waveform. Offset is 0 for all Adc, Tbt and Fa waveforms. The Wfm size is set to 1,000,000 for ADC, 100,000 for Tbt and 9,000 for Fa. Parameters ----------- wfmsel : int, None Waveform selection: Adc(0), Tbt(1), Fa(2). default None, keep old values. name : str, list of element object Element name, group name or list of objects, as in ``getElements`` bpms : list of element object overwrite `name` if presents. evcode : int Event code: - 15(LINAC), 32(1Hz, sync acquisition), 33(SR RF BPM trigger), 47(SR first turn), 66(Booster extraction), 35(pinger). trigsrc : int, None None - default, keep original values. 0 - internal, 1 - external """ elems = bpms if bpms else [e for e in getElements(name) if e.pv(field="x")] pvprefs = [bpm.pv(field="x")[0].replace("Pos:XwUsrOff-Calc", "") for bpm in elems] if verbose: print "resetting {0} BPMS: {1}".format(len(elems), elems) if trigsrc is not None: pvs = [ pvx + "Trig:TrigSrc-SP" for pvx in pvprefs ] caput(pvs, [trigsrc] * len(pvs), wait=True) if wfmsel is not None: # 0 - Adc, 1 - Tbt, 2 - Fa pvs = [ pvx + "DDR:WfmSel-SP" for pvx in pvprefs] caput(pvs, [wfmsel] * len(pvs), wait=True) # enable all three waveforms #pvs = [ pvx + "ddrAdcWfEnable" for pvx in pvprefs] #caput(pvs, 1, wait=True) #pvs = [ pvx + "ddrTbtWfEnable" for pvx in pvprefs] #caput(pvs, 1, wait=True) #pvs = [ pvx + "ddrFaWfEnable" for pvx in pvprefs] #caput(pvs, 1, wait=True) # pvs = [ pvx + "ddrAdcOffset" for pvx in pvprefs] caput(pvs, [0] * len(pvs), wait=True) pvs = [ pvx + "ddrTbtOffset" for pvx in pvprefs] caput(pvs, [0] * len(pvs), wait=True) pvs = [ pvx + "ddrFaOffset" for pvx in pvprefs] caput(pvs, [0] * len(pvs), wait=True) # pvs = [ pvx + "Burst:AdcEnableLen-SP" for pvx in pvprefs] caput(pvs, [1000000] * len(pvs), wait=True) pvs = [ pvx + "Burst:TbtEnableLen-SP" for pvx in pvprefs] caput(pvs, [100000] * len(pvs), wait=True) pvs = [ pvx + "Burst:FaEnableLen-SP" for pvx in pvprefs] caput(pvs, [9000] * len(pvs), wait=True) # pvs = [ pvx + "ERec:AdcEnableLen-SP" for pvx in pvprefs] #if verbose: print pvs caput(pvs, [100000] * len(pvs), wait=True) pvs = [ pvx + "ERec:TbtEnableLen-SP" for pvx in pvprefs] #if verbose: print pvs caput(pvs, [100000] * len(pvs), wait=True) pvs = [ pvx + "ERec:FaEnableLen-SP" for pvx in pvprefs] #if verbose: print pvs caput(pvs, [9000] * len(pvs), wait=True) # if evcode is not None: pvs = [ pvx + "Trig:EventNo-SP" for pvx in pvprefs] caput(pvs, evcode, wait=True)
def _brBpmTrigData(pvprefs, waveform, **kwargs): """ """ offset = kwargs.pop("offset", 0) sleep = kwargs.pop("sleep", 0.5) tc = kwargs.get("timeout", 6) verbose = kwargs.get("verbose", 0) t0 = datetime.now() # prepare the triggers pv_evg = "BR-BI{BPM}Evt:Single-Cmd" pv_trig = [] pv_wfmsel, pv_adcwfm, pv_tbtwfm, pv_fawfm = [], [], [], [] pv_adcoffset, pv_tbtoffset, pv_faoffset = [], [], [] pv_ddrts = [] # timestamp pv_ts, pv_tsns = [], [] # timestamp second and nano sec pv_trigts, pv_trigtsns = [], [] # trigger timestamp # did not consider the 'ddrTbtWfEnable' PV for i,pvx in enumerate(pvprefs): #print bpm.name, pvh, caget(pvh) pv_trig.append( pvx + "Trig:TrigSrc-SP") pv_wfmsel.append(pvx + "DDR:WfmSel-SP") pv_ddrts.append( pvx + "TS:DdrTrigDate-I") pv_adcwfm.append(pvx + "ddrAdcWfEnable") pv_tbtwfm.append(pvx + "ddrTbtWfEnable") pv_fawfm.append( pvx + "ddrFaWfEnable") # pv_adcoffset.append(pvx + "ddrAdcOffset") pv_tbtoffset.append(pvx + "ddrTbtOffset") pv_faoffset.append( pvx + "ddrFaOffset") pv_ts.append( pvx + "Trig:TsSec-I") pv_tsns.append(pvx + "Trig:TsOff-I") pv_trigts.append( pvx + "Trig:TsSec-I") pv_trigtsns.append(pvx + "Trig:TsOff-I") # # save initial val wfsel0 = caget(pv_wfmsel, timeout=tc) trig0 = caget(pv_trig, timeout=tc) # set the trigger internal, TBT waveform prf = "" if waveform == "Adc": caput(pv_wfmsel, 0, wait=True) caput(pv_adcwfm, 1, wait=True) caput(pv_adcoffset, offset, wait=True) pv_ddroffset = pv_adcoffset prf = "" elif waveform == "Tbt": caput(pv_wfmsel, 1, wait=True) caput(pv_tbtwfm, 1, wait=True) caput(pv_tbtoffset, offset, wait=True) pv_ddroffset = pv_tbtoffset prf = "TBT" elif waveform == "Fa": caput(pv_wfmsel, 2, wait=True) caput(pv_fawfm, 1, wait=True) caput(pv_faoffset, offset, wait=True) pv_ddroffset = pv_faoffset prf = "FA" else: raise RuntimeError("unknow waveform '%s'" % waveform) time.sleep(1.5) pv_x, pv_y, pv_S = [], [], [] pv_A, pv_B, pv_C, pv_D = [], [], [], [] for i,pvx in enumerate(pvprefs): pv_x.append( pvx + "%s-X" % prf) pv_y.append( pvx + "%s-Y" % prf) pv_S.append( pvx + "%s-S" % prf) pv_A.append( pvx + "%s-A" % prf) pv_B.append( pvx + "%s-B" % prf) pv_C.append( pvx + "%s-C" % prf) pv_D.append( pvx + "%s-D" % prf) # set 0 - internal trig, 1 - external trig caput(pv_trig, 0, wait=True, timeout=tc) # set the event caput(pv_evg, 1, wait=True) time.sleep(sleep) # check timestamp n = 0 while True: tss_r = caget(pv_trigts, timeout=tc) tss = [t - min(tss_r) for t in tss_r] tsns = caget(pv_trigtsns, timeout=tc) ts = [s + 1.0e-9*tsns[i] for i,s in enumerate(tss)] mdt = max(ts) - min(ts) ddrts0 = caget(pv_ddrts) mdt_s = _maxTimeSpan(caget(pv_ddrts, timeout=tc)) n = n + 1 if mdt < 1.0 and mdt_s < 1.0: #print "Max dt=", mdt, mdt_s, "tried %d times" % n break time.sleep(0.6) # quit if failed too many times if n > 20: caput(pv_trig, [1] * len(pv_trig), wait=True) raise RuntimeError("BPMs are not ready after %d trials" % n) if verbose > 0: print "Trials: %d, Trig=%.2e, DDR Trig=%.2e seconds." % (n, mdt, mdt_s) # redundent check ddrts0 = caget(pv_ddrts, timeout=tc) mdt = _maxTimeSpan(ddrts0) if mdt > 1.0: print "ERROR: Timestamp does not agree (max dt= %f), wait ..." % mdt ddroffset = caget(pv_ddroffset, timeout=tc) data = (caget(pv_x), caget(pv_y), caget(pv_S)) # data = np.array(data, 'd') # set 0 - internal trig, 1 - external trig caput(pv_trig, 1, wait=True) return data[0], data[1], data[2], ddrts0, ddroffset
def measKickedTbtData(idriver, ampl, **kwargs): """ take turn-by-turn BPM data after kicking the beam. Parameters ----------- idriver : int which driver used to kick the beam: injection kicker 3(3) or 4(4), vertical pinger(5), horizontal pinger(6), both H/V pingers(7). ampl : float, tuple kicking amplitude. bpms : list of element objects. provide the BPMs to take data from, default ["BPM" or "UBPM"] count : int number of turns. output : str, True, False output file name, or default (True), or no output (False) verbose : int it will set kicker/pinger and wait 100sec or readback-setpoint agree. event code 47 will be used for kicker 3 and 4, 35 used for pingers. Same returns as `getSrBpmData` Examples --------- >>> (name, x, y, Isum, ts, offset) = measKickedTbtData(7, (0.15, 0.2)) >>> (name, x, y, Isum, ts, offset), output = measKickedTbtData(7, (0.15, 0.2), output=True) """ verbose = kwargs.get("verbose", 0) output = kwargs.get("output", True) sleep = kwargs.get("sleep", 5) count = kwargs.get("count", 2000) bpms = [ b for b in kwargs.get("bpms", getGroupMembers(["BPM", "UBPM"], op="union")) if b.isEnabled()] bpmstats = getBpmStatus(bpms) kpvsp, kpvrb = None, None # 0 - both off, 1 - V-on, 2-H-on, 3-both-on pv_pinger_mode = "SR:C21-PS{Pinger}Mode:Trig-Sel" if idriver in [3,4,5,6]: if idriver in [3, 4]: kpvsp = 'SR:IS-PS{Kick:%d}V-Sp' % idriver kpvrb = 'SR:IS-PS{Kick:%d}Hvps-V-Rb-1st' % idriver kpvon = 'SR:IS-PS{Kick:%d}HvpsOnOff_Cmd' % idriver elif idriver in [5,]: # vertical pinger kpvsp = 'SR:C21-PS{Pinger:V}V-Sp' kpvrb = 'SR:C21-PS{Pinger:V}Setpoint-Rb.VALA' kpvon = 'SR:C21-PS{Pinger:V}HvpsOnOff_Cmd' caput(pv_pinger_mode, 1) elif idriver in [6,]: # horizontal pinger kpvsp = 'SR:C21-PS{Pinger:H}V-Sp' kpvrb = 'SR:C21-PS{Pinger:H}Setpoint-Rb.VALA' kpvon = 'SR:C21-PS{Pinger:H}HvpsOnOff_Cmd' caput(pv_pinger_mode, 2) # caput(kpvsp, 0.0) for i in range(100): if caget(kpvrb, count=1) < 0.001: break time.sleep(1) caput(kpvon, 1) elif idriver in [7,]: # both pinger kpvsp = ['SR:C21-PS{Pinger:H}V-Sp', 'SR:C21-PS{Pinger:V}V-Sp'] kpvrb = ['SR:C21-PS{Pinger:H}Setpoint-Rb.VALA', 'SR:C21-PS{Pinger:V}Setpoint-Rb.VALA'] kpvon = ['SR:C21-PS{Pinger:H}HvpsOnOff_Cmd', 'SR:C21-PS{Pinger:V}HvpsOnOff_Cmd'] caput(pv_pinger_mode, 3) caput(kpvsp, [0.0, 0.0]) for i in range(100): rb = caget(kpvrb, count=1) if rb[0] < 0.001 and rb[1] < 0.001: break time.sleep(0.5) caput(kpvon, [1, 1]) # set the kicker/pinger voltage caput(kpvsp, ampl, wait=True) #(name, x, y, Isum, ts, offset), output = ap.nsls2.getSrBpmData( # trig=1, count=5000, output=True, h5group="k_%d" % idriver) h5g = "k_%d" % idriver Idcct0 = caget('SR:C03-BI{DCCT:1}I:Total-I') time.sleep(sleep) # request an injection: if idriver in [3,4,]: resetSrBpm(bpms=bpms, evcode=47) time.sleep(1) caput('ACC-TS{EVG-SSC}Request-Sel', 1) elif idriver in [5,6,7]: resetSrBpms(bpms=bpms, evcode=35) # do it twice caput('SR:C21-PS{Pinger}Ping-Cmd', 1) time.sleep(1) caput('SR:C21-PS{Pinger}Ping-Cmd', 1) time.sleep(2) Idcct1 = caget('SR:C03-BI{DCCT:1}I:Total-I') bpmdata = getSrBpmData(trig=1, bpms=bpms, count=count, output=output, h5group=h5g) # record pinger wave, V-chan1, H-chan2 pinger_delay, pinger_wave, pinger_mode = None, None, None if idriver in [5,6,7]: pinger_wave = caget(["SR:C21-PS{Dig:Png1}TimeScale-I", "SR:C21-PS{Dig:Png1}Data:Chan2-I", "SR:C21-PS{Dig:Png1}Data:Chan1-I"]) pinger_delay = caget(["SR:C21-PS{Pinger:H}Delay-SP", "SR:C21-PS{Pinger:V}Delay-SP"]) pinger_mode = caget("SR:C21-PS{Pinger}Mode:Trig-Sts") # repeat_value=True caput(kpvon, 0) caput(kpvsp, 0.0) if output: (name, x, y, Isum, ts, offset), output = bpmdata f = h5py.File(output) g = f[h5g] g["I"] = Idcct1 g["I"].attrs["dI"] = Idcct1 - Idcct0 g["RF_SP"] = float(caget('RF{Osc:1}Freq:SP')) g["RF_I"] = float(caget('RF{Osc:1}Freq:I')) g.attrs["ampl"] = ampl g.attrs["idriver"] = idriver g.attrs["pvsp"] = kpvsp g.attrs["pvrb"] = kpvrb g.attrs["pvon"] = kpvon if pinger_wave is not None: g["pinger_wave"] = np.array(pinger_wave, 'd').transpose() if pinger_delay is not None: g["pinger_delay"] = pinger_delay if pinger_mode is not None: g["pinger_mode"] = pinger_mode f.close() # restore restoreBpmStatus(bpmstats) return bpmdata
def measBrCaRmCol(kker, **kwargs): """measure the response matrix column between PVs (DC) kker - SP PV for corrector (waveform) waveform - "Fa" or "Tbt" timeout - 6 sec, EPICS CA timeout npoints - number of orbits for each kick. dxlst - a list of kick (raw unit), overwrite the choice of dxmax dxmax - range of kick [-dxmax, dxmax] ndx - default 4. Specify kicks in [-dxmax, dxmax]. wait - default 1.5 second output - save the results verbose - default 0 return the output file name. The output will be in HDF5 file format. """ timeout = kwargs.pop("timeout", 6) wait = kwargs.pop("wait", 1.5) verbose = kwargs.pop("verbose", 0) npt = kwargs.pop("npoints", 4) wfm = kwargs.pop("waveform", "Fa") t0 = datetime.now() dxlst, x0 = [], np.array(caget(kker, timeout=timeout), 'd') if "dxlst" in kwargs: dxlst = kwargs.get("dxlst") elif "dxmax" in kwargs: dxmax = np.abs(kwargs.get("dxmax")) nx = kwargs.pop("ndx", 4) dxlst = list(np.linspace(-dxmax, dxmax, nx)) else: raise RuntimeError("need input for at least of the parameters: " "dxlst, xlst, dxmax") # use the provided filename or default datetimed filename output_file = kwargs.pop( "output", os.path.join(machines.getOutputDir(), t0.strftime("%Y_%m"), "orm", t0.strftime("orm_%Y_%m_%d_%H%M%S.hdf5"))) # save dx list h5f = h5py.File(output_file) grp = h5f.create_group(kker) grp.attrs["orm_t0"] = t0.strftime("%Y_%m_%d_%H:%M:%S.%f") grp["dxlst"] = dxlst h5f.close() # save the initial orbit getBrBpmData(waveform=wfm, verbose=verbose - 1, output_file=output_file, h5group="%s/%s0" % (kker, wfm), **kwargs) n1 = len(dxlst) for i, dx in enumerate(dxlst): if verbose > 0: print "%d/%d: Setting %s " % (i, n1, kker), dx sys.stdout.flush() try: nx0 = len(x0) xi = [x0i + dx for x0i in x0] except: # should never happen for booster xi = x0 + dx caput(kker, xi, wait=True, timeout=timeout) time.sleep(wait * 3) for j in range(npt): obt, fname = getBrBpmData(waveform=wfm, verbose=verbose - 1, output_file=output_file, h5group="%s/%s_dx%d__pt%d" % (kker, wfm, i, j), **kwargs) if verbose > 1: name, x, y, Is, ts, ddroffset = obt print " %d/%d" % (j, npt), np.average(x[0]), np.std(x[0]) sys.stdout.flush() time.sleep(wait) time.sleep(wait) caput(kker, x0, wait=True, timeout=timeout) t1 = datetime.now() h5f = h5py.File(output_file) h5f[kker].attrs["orm_t1"] = t1.strftime("%Y_%m_%d_%H:%M:%S.%f") h5f.close() return output_file
def correctBrOrbit(kker, m, **kwarg): """correct the resp using kker and response matrix. Parameters ------------ kker : PV list of the controllers, e.g. corrector m : response matrix where :math:`m_{ij}=\Delta orbit_i/\Delta kker_j` scale : scaling factor applied to the calculated kker ref : the targeting value of orbit rcond : the rcond for cutting singular values. check : stop if the orbit gets worse. wait : waiting (seconds) before check. Returns -------- err : converged or not checked (0), error (>0). msg : error message or None """ scale = kwarg.get('scale', 0.68) ref = kwarg.get('ref', None) check = kwarg.get('check', True) wait = kwarg.get('wait', 6) rcond = kwarg.get('rcond', 1e-2) verb = kwarg.get('verbose', 0) bc = kwarg.get('bc', None) wfmslice = kwarg.get("wfmslice", (10, 100)) wfm = kwarg.pop("waveform", "Fa") exrows = kwarg.pop("exclude_rows", []) test = kwarg.pop("test", False) #u, s, v = np.linalg.svd(m) #plt.semilogy(s/s[0], 'x-') #plt.show() i0, i1 = wfmslice nbpm, ncor = np.shape(m) mask_row = np.ones(nbpm, 'i') for i in exrows: mask_row[i] = 0 m = np.compress(mask_row, m, axis=0) print "New m shape:", np.shape(m) name, x0, y0, Isum0, ts, offset = getBrBpmData(waveform=wfm, trig=0) # save initial orbit in vx0 vl0 = np.compress(mask_row, np.vstack((x0, y0)), axis=0) v0 = np.average(vl0[:,i0:i1], axis=1) if np.max(v0) > 10000 or np.min(v0) < -10000: plt.plot(v0) plt.show() raise RuntimeError("orbit is not stable, too large: %.2f, %.2f" % ( np.min(v0), np.max(v0))) if ref is not None: v0 = v0 - ref if len(v0) != len(m): raise RuntimeError("inconsistent BPM and ORM size") # the initial norm norm0 = np.linalg.norm(v0) # solve for m*dk + (v0 - ref) = 0 dk, resids, rank, s = np.linalg.lstsq(m, -1.0*v0, rcond = rcond) norm1 = np.linalg.norm(m.dot(dk*scale) + v0) # get the DC kicker kl0 = np.array(caget(kker), 'd') k0 = np.average(kl0, axis=1) print np.shape(kl0) #print k0, dk, scale k1 = k0 + dk*scale vk1 = [[k] * len(kl0[i]) for i,k in enumerate(k1)] plt.plot(k0, 'r-', label="initial") plt.plot(k1, 'b-', label="new") plt.legend() plt.show() if not test: caput(kker, vk1, wait=True) else: for i,pv in enumerate(kker): print i, pv, k1[i], "dk=", dk[i] time.sleep(wait) name, x1, y1, Isum1, ts, offset = getBrBpmData(waveform=wfm, trig=0) vl1 = np.compress(mask_row, np.vstack((x1, y1)), axis=0) v1 = np.average(vl1[:,i0:i1], axis=1) print norm0, "predicted norm= ", norm1, "realized:", np.linalg.norm(v1) return v0, v1, k0, k1
def _srBpmTrigData(pvprefs, waveform, **kwargs): """ """ offset = kwargs.pop("offset", 0) sleep = kwargs.pop("sleep", 0.5) count = kwargs.pop("count", 0) tc = kwargs.get("timeout", 6) verbose = kwargs.get("verbose", 0) t0 = datetime.now() # prepare the triggers pv_evg = "SR-BI{BPM}Evt:Single-Cmd" pv_trig = [] pv_wfmsel, pv_adcwfm, pv_tbtwfm, pv_fawfm = [], [], [], [] pv_adcoffset, pv_tbtoffset, pv_faoffset = [], [], [] # available data points pv_adclen, pv_tbtlen, pv_falen = [], [], [] # available data points in CA pv_adccalen, pv_tbtcalen, pv_facalen = [], [], [] # pv_bbaxoff, pv_bbayoff = [], [] pv_ddrts = [] # timestamp pv_ts, pv_tsns = [], [] # timestamp second and nano sec pv_trigts, pv_trigtsns = [], [] # trigger timestamp pv_ddrtx = [] # DDR transfer busy pv_evtcode = [] # did not consider the 'ddrTbtWfEnable' PV for i, pvx in enumerate(pvprefs): #print bpm.name, pvh, caget(pvh) # pv_bbaxoff.append(pvx + "BbaXOff-SP") pv_bbayoff.append(pvx + "BbaYOff-SP") # pv_trig.append(pvx + "Trig:TrigSrc-SP") pv_wfmsel.append(pvx + "DDR:WfmSel-SP") pv_ddrts.append(pvx + "TS:DdrTrigDate-I") #pv_adcwfm.append(pvx + "ddrAdcWfEnable") #pv_tbtwfm.append(pvx + "ddrTbtWfEnable") #pv_fawfm.append( pvx + "ddrFaWfEnable") # pv_adcoffset.append(pvx + "ddrAdcOffset") pv_tbtoffset.append(pvx + "ddrTbtOffset") pv_faoffset.append(pvx + "ddrFaOffset") pv_trigts.append(pvx + "Trig:TsSec-I") pv_trigtsns.append(pvx + "Trig:TsOff-I") # pv_adclen.append(pvx + "Burst:AdcEnableLen-SP") pv_tbtlen.append(pvx + "Burst:TbtEnableLen-SP") pv_falen.append(pvx + "Burst:FaEnableLen-SP") # pv_adccalen.append(pvx + "ERec:AdcEnableLen-SP") pv_tbtcalen.append(pvx + "ERec:TbtEnableLen-SP") pv_facalen.append(pvx + "ERec:FaEnableLen-SP") pv_ddrtx.append(pvx + "DDR:TxStatus-I") pv_evtcode.append(pvx + "Trig:EventNo-I") # save initial val wfsel0 = caget(pv_wfmsel, timeout=tc) trig0 = caget(pv_trig, timeout=tc) # set the trigger internal, TBT waveform prf = "" if waveform == "Adc": caput(pv_wfmsel, 0, wait=True) #caput(pv_adcwfm, 1, wait=True) caput(pv_adcoffset, 0, wait=True) pv_ddroffset = pv_adcoffset prf = "" elif waveform == "Tbt": caput(pv_wfmsel, 1, wait=True) #caput(pv_tbtwfm, 1, wait=True) caput(pv_tbtoffset, 0, wait=True) pv_ddroffset = pv_tbtoffset prf = "TBT" elif waveform == "Fa": caput(pv_wfmsel, 2, wait=True) #caput(pv_fawfm, 1, wait=True) caput(pv_faoffset, 0, wait=True) pv_ddroffset = pv_faoffset prf = "FA" else: raise RuntimeError("unknow waveform '%s'" % waveform) pv_x, pv_y, pv_S = [], [], [] pv_A, pv_B, pv_C, pv_D = [], [], [], [] for i, pvx in enumerate(pvprefs): pv_x.append(pvx + "%s-X" % prf) pv_y.append(pvx + "%s-Y" % prf) pv_S.append(pvx + "%s-S" % prf) pv_A.append(pvx + "%s-A" % prf) pv_B.append(pvx + "%s-B" % prf) pv_C.append(pvx + "%s-C" % prf) pv_D.append(pvx + "%s-D" % prf) # set 0 - internal trig, 1 - external trig caput(pv_trig, 0, wait=True, timeout=tc) # set the event caput(pv_evg, 1, wait=True) time.sleep(1.2) # check timestamp n = 0 while any(caget(pv_ddrtx, timeout=tc)) and n < 20: time.sleep(0.5) n += 1 tss_r = caget(pv_trigts, timeout=tc) tss = [t - min(tss_r) for t in tss_r] tsns = caget(pv_trigtsns, timeout=tc) ts = [s * 1e9 + tsns[i] for i, s in enumerate(tss)] mdt = max(ts) - min(ts) if mdt > 8.0: raise RuntimeError("BPMs are not ready after {0} trials, dt={1}: " "{2}\n{3}".format(n, mdt, ts, caget(pv_ddrtx))) if verbose > 0: print "Trials: %d, Trig=%.2e ns." % (n, mdt) print "Sec:", tss_r print "dSec: ", [s - min(tss) for s in tss] print "dNsec:", [s - min(tsns) for s in tsns] print "NSec", tsns # redundent check #ddrts0 = caget(pv_ddrts) ddrts0 = [ datetime.fromtimestamp(v).strftime("%m/%d/%Y,%H:%M:%S") + ".%09d" % tsns[i] for i, v in enumerate(tss_r) ] ddroffset = caget(pv_ddroffset, timeout=tc) data = (caget(pv_x, count=count), caget(pv_y, count=count), caget(pv_S, count=count)) xbbaofst = caget(pv_bbaxoff, timeout=tc) ybbaofst = caget(pv_bbayoff, timeout=tc) # # set 0 - internal trig, 1 - external trig #caput(pv_trig, 1, wait=True) caput(pv_wfmsel, wfsel0, wait=True, timeout=tc) caput(pv_trig, trig0, wait=True, timeout=tc) ext_data = { "ddr_timestamp": ddrts0, "ddr_offset": ddroffset, "bba_xoffset": xbbaofst, "bba_yoffset": ybbaofst, "event_code": caget(pv_evtcode) } #return data[0], data[1], data[2], ddrts0, ddroffset, ts return (data[0], data[1], data[2], ext_data)
def resetSrBpms(wfmsel=None, name="BPM", evcode=None, verbose=0, bpms=None, trigsrc=None): """ reset the BPMs to external trigger and Tbt waveform. Offset is 0 for all Adc, Tbt and Fa waveforms. The Wfm size is set to 1,000,000 for ADC, 100,000 for Tbt and 9,000 for Fa. Parameters ----------- wfmsel : int, None Waveform selection: Adc(0), Tbt(1), Fa(2). default None, keep old values. name : str, list of element object Element name, group name or list of objects, as in ``getElements`` bpms : list of element object overwrite `name` if presents. evcode : int Event code: - 15(LINAC), 32(1Hz, sync acquisition), 33(SR RF BPM trigger), 47(SR first turn), 66(Booster extraction), 35(pinger). trigsrc : int, None None - default, keep original values. 0 - internal, 1 - external """ elems = bpms if bpms else [e for e in getElements(name) if e.pv(field="x")] pvprefs = [ bpm.pv(field="x")[0].replace("Pos:XwUsrOff-Calc", "") for bpm in elems ] if verbose: print "resetting {0} BPMS: {1}".format(len(elems), elems) if trigsrc is not None: pvs = [pvx + "Trig:TrigSrc-SP" for pvx in pvprefs] caput(pvs, [trigsrc] * len(pvs), wait=True) if wfmsel is not None: # 0 - Adc, 1 - Tbt, 2 - Fa pvs = [pvx + "DDR:WfmSel-SP" for pvx in pvprefs] caput(pvs, [wfmsel] * len(pvs), wait=True) # enable all three waveforms #pvs = [ pvx + "ddrAdcWfEnable" for pvx in pvprefs] #caput(pvs, 1, wait=True) #pvs = [ pvx + "ddrTbtWfEnable" for pvx in pvprefs] #caput(pvs, 1, wait=True) #pvs = [ pvx + "ddrFaWfEnable" for pvx in pvprefs] #caput(pvs, 1, wait=True) # pvs = [pvx + "ddrAdcOffset" for pvx in pvprefs] caput(pvs, [0] * len(pvs), wait=True) pvs = [pvx + "ddrTbtOffset" for pvx in pvprefs] caput(pvs, [0] * len(pvs), wait=True) pvs = [pvx + "ddrFaOffset" for pvx in pvprefs] caput(pvs, [0] * len(pvs), wait=True) # pvs = [pvx + "Burst:AdcEnableLen-SP" for pvx in pvprefs] caput(pvs, [1000000] * len(pvs), wait=True) pvs = [pvx + "Burst:TbtEnableLen-SP" for pvx in pvprefs] caput(pvs, [100000] * len(pvs), wait=True) pvs = [pvx + "Burst:FaEnableLen-SP" for pvx in pvprefs] caput(pvs, [9000] * len(pvs), wait=True) # pvs = [pvx + "ERec:AdcEnableLen-SP" for pvx in pvprefs] #if verbose: print pvs caput(pvs, [100000] * len(pvs), wait=True) pvs = [pvx + "ERec:TbtEnableLen-SP" for pvx in pvprefs] #if verbose: print pvs caput(pvs, [100000] * len(pvs), wait=True) pvs = [pvx + "ERec:FaEnableLen-SP" for pvx in pvprefs] #if verbose: print pvs caput(pvs, [9000] * len(pvs), wait=True) # if evcode is not None: pvs = [pvx + "Trig:EventNo-SP" for pvx in pvprefs] caput(pvs, evcode, wait=True)
def _srBpmTrigData(pvprefs, waveform, **kwargs): """ """ offset = kwargs.pop("offset", 0) sleep = kwargs.pop("sleep", 0.5) count = kwargs.pop("count", 0) tc = kwargs.get("timeout", 6) verbose = kwargs.get("verbose", 0) t0 = datetime.now() # prepare the triggers pv_evg = "SR-BI{BPM}Evt:Single-Cmd" pv_trig = [] pv_wfmsel, pv_adcwfm, pv_tbtwfm, pv_fawfm = [], [], [], [] pv_adcoffset, pv_tbtoffset, pv_faoffset = [], [], [] # available data points pv_adclen, pv_tbtlen, pv_falen = [], [], [] # available data points in CA pv_adccalen, pv_tbtcalen, pv_facalen = [], [], [] # pv_bbaxoff, pv_bbayoff = [], [] pv_ddrts = [] # timestamp pv_ts, pv_tsns = [], [] # timestamp second and nano sec pv_trigts, pv_trigtsns = [], [] # trigger timestamp pv_ddrtx = [] # DDR transfer busy pv_evtcode = [] # did not consider the 'ddrTbtWfEnable' PV for i,pvx in enumerate(pvprefs): #print bpm.name, pvh, caget(pvh) # pv_bbaxoff.append( pvx + "BbaXOff-SP") pv_bbayoff.append( pvx + "BbaYOff-SP") # pv_trig.append( pvx + "Trig:TrigSrc-SP") pv_wfmsel.append(pvx + "DDR:WfmSel-SP") pv_ddrts.append( pvx + "TS:DdrTrigDate-I") #pv_adcwfm.append(pvx + "ddrAdcWfEnable") #pv_tbtwfm.append(pvx + "ddrTbtWfEnable") #pv_fawfm.append( pvx + "ddrFaWfEnable") # pv_adcoffset.append(pvx + "ddrAdcOffset") pv_tbtoffset.append(pvx + "ddrTbtOffset") pv_faoffset.append( pvx + "ddrFaOffset") pv_trigts.append( pvx + "Trig:TsSec-I") pv_trigtsns.append(pvx + "Trig:TsOff-I") # pv_adclen.append( pvx + "Burst:AdcEnableLen-SP") pv_tbtlen.append( pvx + "Burst:TbtEnableLen-SP") pv_falen.append( pvx + "Burst:FaEnableLen-SP") # pv_adccalen.append(pvx + "ERec:AdcEnableLen-SP") pv_tbtcalen.append(pvx + "ERec:TbtEnableLen-SP") pv_facalen.append( pvx + "ERec:FaEnableLen-SP") pv_ddrtx.append(pvx + "DDR:TxStatus-I") pv_evtcode.append(pvx + "Trig:EventNo-I") # save initial val wfsel0 = caget(pv_wfmsel, timeout=tc) trig0 = caget(pv_trig, timeout=tc) # set the trigger internal, TBT waveform prf = "" if waveform == "Adc": caput(pv_wfmsel, 0, wait=True) #caput(pv_adcwfm, 1, wait=True) caput(pv_adcoffset, 0, wait=True) pv_ddroffset = pv_adcoffset prf = "" elif waveform == "Tbt": caput(pv_wfmsel, 1, wait=True) #caput(pv_tbtwfm, 1, wait=True) caput(pv_tbtoffset, 0, wait=True) pv_ddroffset = pv_tbtoffset prf = "TBT" elif waveform == "Fa": caput(pv_wfmsel, 2, wait=True) #caput(pv_fawfm, 1, wait=True) caput(pv_faoffset, 0, wait=True) pv_ddroffset = pv_faoffset prf = "FA" else: raise RuntimeError("unknow waveform '%s'" % waveform) pv_x, pv_y, pv_S = [], [], [] pv_A, pv_B, pv_C, pv_D = [], [], [], [] for i,pvx in enumerate(pvprefs): pv_x.append( pvx + "%s-X" % prf) pv_y.append( pvx + "%s-Y" % prf) pv_S.append( pvx + "%s-S" % prf) pv_A.append( pvx + "%s-A" % prf) pv_B.append( pvx + "%s-B" % prf) pv_C.append( pvx + "%s-C" % prf) pv_D.append( pvx + "%s-D" % prf) # set 0 - internal trig, 1 - external trig caput(pv_trig, 0, wait=True, timeout=tc) # set the event caput(pv_evg, 1, wait=True) time.sleep(1.2) # check timestamp n = 0 while any(caget(pv_ddrtx, timeout=tc)) and n < 20: time.sleep(0.5) n += 1 tss_r = caget(pv_trigts, timeout=tc) tss = [t - min(tss_r) for t in tss_r] tsns = caget(pv_trigtsns, timeout=tc) ts = [s*1e9 + tsns[i] for i,s in enumerate(tss)] mdt = max(ts) - min(ts) if mdt > 8.0: raise RuntimeError("BPMs are not ready after {0} trials, dt={1}: " "{2}\n{3}".format(n, mdt, ts, caget(pv_ddrtx))) if verbose > 0: print "Trials: %d, Trig=%.2e ns." % (n, mdt) print "Sec:", tss_r print "dSec: ", [s - min(tss) for s in tss] print "dNsec:", [s - min(tsns) for s in tsns] print "NSec", tsns # redundent check #ddrts0 = caget(pv_ddrts) ddrts0 = [datetime.fromtimestamp(v).strftime("%m/%d/%Y,%H:%M:%S") + ".%09d" % tsns[i] for i,v in enumerate(tss_r)] ddroffset = caget(pv_ddroffset, timeout=tc) data = (caget(pv_x, count=count), caget(pv_y, count=count), caget(pv_S, count=count)) xbbaofst = caget(pv_bbaxoff, timeout=tc) ybbaofst = caget(pv_bbayoff, timeout=tc) # # set 0 - internal trig, 1 - external trig #caput(pv_trig, 1, wait=True) caput(pv_wfmsel, wfsel0, wait=True, timeout=tc) caput(pv_trig, trig0, wait=True, timeout=tc) ext_data = { "ddr_timestamp": ddrts0, "ddr_offset": ddroffset, "bba_xoffset": xbbaofst, "bba_yoffset": ybbaofst, "event_code": caget(pv_evtcode)} #return data[0], data[1], data[2], ddrts0, ddroffset, ts return (data[0], data[1], data[2], ext_data)