def __init__(self, directory='.', verbosity='INFO', trim=''): # INFO self.Dir = realpath(directory) if isdir(directory) else critical( 'Error: no or invalid configuration directory specified!') self.Verbosity = verbosity self.Trim = trim self.Config = PxarConfig(join(directory, 'configParameters.dat')) self.TestBoardName = self.Config.get('testboardName') self.ROCType = self.Config.get('rocType') self.NROCs, self.I2Cs = self.find_i2cs() self.Mask = PxarMaskFile(join(directory, self.Config.get('maskfile'))) self.IsAnalogue = self.ROCType == 'psi46v2' # DACs self.TBParameters = self.init_tb_parameters() self.TBMDacs = self.init_tbm() self.ROCDACs = self.init_dacs() self.TrimDACs = self.init_trim_dacs() # SETTINGS self.PowerSettings = self.init_power() self.PGSetup = self.init_pattern_generator() self.HubIDs = [int(i) for i in self.Config.get('hubId', 31).split(',')] self.API = self.init_api() self.set_probes() self.set_decoding_offsets() info('pxar API is now started and configured.')
def find_i2cs(self): words = self.Config.get('nRocs').split('i2c:') n, i2cs = int(words[0]), arange(int( words[0]), dtype='u2') if len(words) == 1 else array( words[1].split(','), 'u2') info(f'Number of ROCs: {n}') info(f'Configured I2Cs: {i2cs}') return n, i2cs
def save(self, hv=None, cur=None): hv, cur = choose(f'-{hv}', '', hv), choose(f'-{cur}', '', cur) with open(f'stats{hv}{cur}_{datetime.now():%m-%d_%H_%M_%S}.ini', 'w') as f: p = ConfigParser() p.read_dict(self) p.write(f) info(f'saved stats in: {f.name}')
def init_pattern_generator(self): pgcal = self.ROCDACs[0].get('wbc') + (6 if 'dig' in self.ROCType else 5) info(f'PGCAL: {pgcal}') if len(self.TBMDacs ) == 0: # Pattern Generator for single ROC operation: return (b'PG_RESR', 25), (b'PG_CAL', pgcal), (b'PG_TRG', 16), (b'PG_TOK', 0) return (b'PG_RESR', 15), (b'PG_CAL', pgcal), (b'PG_TRG', 0)
def set(self, dac, value, prnt=True, name='ROC'): """sets the value of the DAC [dac] to [value]. :returns: old value""" if dac.encode() not in self.AllDACs: return warning(f'The {name} DAC "{dac}" does not exist!') info((f'setting "{dac}" to {value}' if int(value) != self[dac.lower()] else f'{dac} already has a value of {value}'), prnt=prnt) old = self[dac] self[dac] = int(value) return old
def init_trim_dacs(self): dacs = [ PxarTrimConfig( join( self.Dir, f'{self.Config.get("trimParameters")}{self.Trim}_C{i2c}.dat' ), i2c, self.Mask) for i2c in self.I2Cs ] s = array([len(i) for i in dacs]) info(f'There are {s[0]} pixels for all {self.NROCs} ROCs' if all( s == s[0]) else f'ROC pixels: {s}') return dacs
def init_tbm(self): """ Initialise the DACs of the TBMs (TokenBitManager). """ dacs = [ PxarConfig( join(self.Dir, f'{self.Config.get("tbmParameters")}_C{tbm}{i}.dat')) for tbm in range(self.Config.get_int('nTbms')) for i in ['a', 'b'] ] info(f'Found DAC config for {len(dacs)} TBM cores', prnt=len(dacs)) for pars in dacs: pars.show(prnt_file=True, prnt=self.Verbosity != 'INFO') return dacs
def set(self, key, value): if key is not None: if key.lower() in self and self[key.lower()] != value: info( f'{basename(self.FileName)}: overwriting "{key}" from {self[key.lower()]} -> {value}' ) self.change_line(key, value) elif key.lower() not in self: info( f'{basename(self.FileName)}: adding "{key}" key with value {value}' ) self.add_line(key, value) self[key.lower()] = value
def init_power(self): """ Initialise the power settings of the testboard. """ power_settings = { key: float(self.Config.get(key, default)) for key, default in [(b'va', 1.9), (b'vd', 2.6), (b'ia', 1.190), (b'id', 1.10)] } if any(value > 100 for value in power_settings.values()): info('set power settings from [mV] to [V]') power_settings = { key: int(value) / 1000. for key, value in power_settings.items() } return power_settings
def save(self): old_data = genfromtxt(self.FileName, dtype=['i', 'U30', 'i']) for i, (_, key, value) in enumerate(old_data): if key in self and self[key] != value: info( f'{basename(self.FileName)}: overwriting "{key}" from {value} -> {self[key]}' ) old_data[i][-1] = self[key] s = [max(len(str(i)) for i in old_data[a]) for a in ['f0', 'f1', 'f2']] with open(self.FileName, 'r+') as f: f.writelines([ '{0:>{3}} {1:>{4}} {2:>{5}}\n'.format(*list(tup) + s) for tup in old_data ]) f.truncate()
def init_api(self): try: api = PyPxarCore(usbId=self.TestBoardName.encode(), logLevel=self.Verbosity.encode()) info(f'Init API version: {api.getVersion()}') if not api.initTestboard(self.TBParameters.b, self.PowerSettings, self.PGSetup): info('Please check if a new FW version is available') critical('could not init DTB -- possible firmware mismatch.') api.initDUT(self.HubIDs, self.Config.get_b('tbmType', 'tbm08'), byte_dic(self.TBMDacs), self.ROCType.encode(), byte_dic(self.ROCDACs), self.TrimDACs, self.I2Cs) api.testAllPixels(True) return api except RuntimeError as e: critical(e)
def set_decoding_offsets(self): if not any(word in self.ROCType for word in ['dig', 'proc']): b, l1, ub = [ self.Config.get_roc_vector(opt, self.NROCs, 0) for opt in ['blackOffset', 'l1Offset', 'alphas'] ] info('set analogue decoding offset set to: {b}') info('set analogue level1 offset set to: {l1}') info('set analogue alphas set to: {ub}') self.API.setBlackOffsets(b) self.API.setDecodingL1Offsets(l1) self.API.setDecodingAlphas(ub)
def init_tb_parameters(self): pars = TBParameters(join(self.Dir, self.Config.get('tbParameters'))) info( f'tindelay/toutdelay: {pars.get("tindelay")}/{pars.get("toutdelay")}' ) if self.IsAnalogue else f'clk/phase: {pars.get("clk")}/{pars.get("deser160phase")}' return pars