예제 #1
0
class BPMSignal:
	"""
		This class delivers the average value for coordinate x and y 
	"""
	def __init__(self):
		self.bunchtwissanalysis = BunchTwissAnalysis()
		self.xAvg = 0.0
		self.yAvg = 0.0
		self.xpAvg = 0.0
		self.ypAvg = 0.0
		

		
	def analyzeSignal(self, bunch):
		
		self.bunchtwissanalysis.analyzeBunch(bunch)

		# if mpi operations are enabled, this section of code will
		# determine the rank of the present node
		rank = 0  # default is primary node
		mpi_init = orbit_mpi.MPI_Initialized()
		comm = orbit_mpi.mpi_comm.MPI_COMM_WORLD
		if (mpi_init):
			rank = orbit_mpi.MPI_Comm_rank(comm)

		# only the primary node needs to output the calculated information
		if (rank == 0):
			self.xAvg = self.bunchtwissanalysis.getAverage(0)
			self.xpAvg = self.bunchtwissanalysis.getAverage(1)
			self.yAvg = self.bunchtwissanalysis.getAverage(2)
			self.ypAvg = self.bunchtwissanalysis.getAverage(3)
			
	def getSignalX(self):
		return self.xAvg
		
	def getSignalXP(self):
		return self.xpAvg
	
	def getSignalY(self):
		return self.yAvg
	
	def getSignalYP(self):
		return self.ypAvg
예제 #2
0
class BPMSignal:
    """
		This class delivers the average value for coordinate x and y 
	"""
    def __init__(self):
        self.bunchtwissanalysis = BunchTwissAnalysis()
        self.xAvg = 0.0
        self.yAvg = 0.0
        self.xpAvg = 0.0
        self.ypAvg = 0.0

    def analyzeSignal(self, bunch):

        self.bunchtwissanalysis.analyzeBunch(bunch)

        # if mpi operations are enabled, this section of code will
        # determine the rank of the present node
        rank = 0  # default is primary node
        mpi_init = orbit_mpi.MPI_Initialized()
        comm = orbit_mpi.mpi_comm.MPI_COMM_WORLD
        if (mpi_init):
            rank = orbit_mpi.MPI_Comm_rank(comm)

        # only the primary node needs to output the calculated information
        if (rank == 0):
            self.xAvg = self.bunchtwissanalysis.getAverage(0)
            self.xpAvg = self.bunchtwissanalysis.getAverage(1)
            self.yAvg = self.bunchtwissanalysis.getAverage(2)
            self.ypAvg = self.bunchtwissanalysis.getAverage(3)

    def getSignalX(self):
        return self.xAvg

    def getSignalXP(self):
        return self.xpAvg

    def getSignalY(self):
        return self.yAvg

    def getSignalYP(self):
        return self.ypAvg
예제 #3
0
class MonitorTEAPOT(NodeTEAPOT):
    """
	Monitor TEAPOT element.
	"""
    def __init__(self, name="Monitor no name"):
        """
		Constructor. Creates the aperutre element.
		"""
        NodeTEAPOT.__init__(self, name)
        self.setType("monitor teapot")
        self.twiss = BunchTwissAnalysis()

    def track(self, paramsDict):
        """
		The bunchtuneanalysis-teapot class implementation of the AccNodeBunchTracker class track(probe) method.
		"""
        length = self.getLength(self.getActivePartIndex())
        bunch = paramsDict["bunch"]
        self.twiss.analyzeBunch(bunch)
        self.addParam("xAvg", self.twiss.getAverage(0))
        self.addParam("xpAvg", self.twiss.getAverage(1))
        self.addParam("yAvg", self.twiss.getAverage(2))
        self.addParam("ypAvg", self.twiss.getAverage(3))
예제 #4
0
def bunchCentering(bunch):
    """
	Bunch center after generating can have small deviation from the (0,0,0,0,0,0)
	This function will force centering the bunch.
	"""
    twiss_analysis = BunchTwissAnalysis()
    twiss_analysis.analyzeBunch(bunch)
    #-----------------------------------------------
    # let's center the beam
    (x_avg, y_avg) = (twiss_analysis.getAverage(0),
                      twiss_analysis.getAverage(2))
    (xp_avg, yp_avg) = (twiss_analysis.getAverage(1),
                        twiss_analysis.getAverage(3))
    (z_avg, dE_avg) = (twiss_analysis.getAverage(4),
                       twiss_analysis.getAverage(5))
    for part_id in range(bunch.getSize()):
        bunch.x(part_id, bunch.x(part_id) - x_avg)
        bunch.y(part_id, bunch.y(part_id) - y_avg)
        bunch.xp(part_id, bunch.xp(part_id) - xp_avg)
        bunch.yp(part_id, bunch.yp(part_id) - yp_avg)
        bunch.z(part_id, bunch.z(part_id) - z_avg)
        bunch.dE(part_id, bunch.dE(part_id) - dE_avg)
    #-----------------------------------------------
    return (x_avg, y_avg, dE_avg)
예제 #5
0
bunch_tmp.addPartAttr('ParticlePhaseAttributes')

#----------------------------------------------------
# Define twiss analysis and output dictionary
#----------------------------------------------------
bunchtwissanalysis = BunchTwissAnalysis() #Prepare the analysis class that will look at emittances, etc.
get_dpp = lambda b, bta: np.sqrt(bta.getCorrelation(5,5)) / (b.getSyncParticle().gamma()*b.mass()*b.getSyncParticle().beta()**2)
get_bunch_length = lambda b, bta: 4 * np.sqrt(bta.getCorrelation(4,4)) / (speed_of_light*b.getSyncParticle().beta())
get_eps_z = lambda b, bta: 1e9 * 4 * pi * bta.getEmittance(2) / (speed_of_light*b.getSyncParticle().beta())

output = Output_dictionary()
output.addParameter('turn', lambda: turn)
output.addParameter('intensity', lambda: bunchtwissanalysis.getGlobalMacrosize())
output.addParameter('n_mp', lambda: bunchtwissanalysis.getGlobalCount())
output.addParameter('gamma', lambda: bunch.getSyncParticle().gamma())
output.addParameter('mean_x', lambda: bunchtwissanalysis.getAverage(0))
output.addParameter('mean_xp', lambda: bunchtwissanalysis.getAverage(1))
output.addParameter('mean_y', lambda: bunchtwissanalysis.getAverage(2))
output.addParameter('mean_yp', lambda: bunchtwissanalysis.getAverage(3))
output.addParameter('mean_z', lambda: bunchtwissanalysis.getAverage(4))
output.addParameter('mean_dE', lambda: bunchtwissanalysis.getAverage(5))
output.addParameter('epsn_x', lambda: bunchtwissanalysis.getEmittanceNormalized(0))
output.addParameter('epsn_y', lambda: bunchtwissanalysis.getEmittanceNormalized(1))
output.addParameter('eps_z', lambda: get_eps_z(bunch, bunchtwissanalysis))
output.addParameter('bunchlength', lambda: get_bunch_length(bunch, bunchtwissanalysis))
output.addParameter('dpp_rms', lambda: get_dpp(bunch, bunchtwissanalysis))

if frozen or slicebyslice:
        output.addParameter('BE_intensity1', lambda: sc_params1['intensity'])
        output.addParameter('BE_epsn_x1', lambda: sc_params1['epsn_x'])
        output.addParameter('BE_epsn_y1', lambda: sc_params1['epsn_y'])
예제 #6
0
class TrajectoryCorrection:
    """
	Class to perform correction of the trajectory in the linac type lattice
	or in the part of it. To correct trajectories the Linac DCorrectorH and
	DCorrectorV objects will be used. The trajectory is defined by BPMs nodes
	that specifically defined for this trajectory correction. The correction
	algorithm will build response matrix for correctors (assuming no tilt) and
	apply the correctors field to provide the best correction to the target
	values for each BPM. By default the goal for all BPMs is 0., but user can
	redefine these values and set of BPMs. User also can redefine what
	dipole correctors will be used.
	"""
    def __init__(self, lattice, start_node=None, stop_node=None):
        #---- change in the corrector field
        self.deltaB = 0.001
        #----------------------------------
        self.lattice = lattice
        self.start_node = start_node
        self.stop_node = stop_node
        self.bpm_node_arr = []
        self.transvBPM_arr = []
        self.dch_node_arr = []
        self.dcv_node_arr = []
        #-------------------------
        self.quad_node_arr = []
        self.quad_transvBPM_arr = []
        #-------------------------
        self._updateBPM_Nodes()
        self._updateDC_Nodes(None, DCorrectorH)
        self._updateDC_Nodes(None, DCorrectorV)
        self._updateQuad_Nodes()
        #-------------------------
        self.twiss_analysis = BunchTwissAnalysis()

    def setStartStopNodes(self, start_node=None, stop_node=None):
        self.start_node = start_node
        self.stop_node = stop_node
        self._updateBPM_Nodes()
        self._updateDC_Nodes(None, DCorrectorH)
        self._updateDC_Nodes(None, DCorrectorV)
        self._updateQuad_Nodes()

    def _getStartStopIndexes(self):
        """
		Returns the start and stop indexes of the start and stop nodes
		"""
        start_ind = -1
        if (self.start_node != None):
            start_ind = self.lattice.getNodeIndex(self.start_node)
        stop_ind = -1
        if (self.stop_node != None):
            stop_ind = self.lattice.getNodeIndex(self.stop_node)
        return (start_ind, stop_ind)

    def _returnFilteredNodes(self, nodes):
        """
		Returns list of nodes between start and stop nodes.
		"""
        (start_ind, stop_ind) = self._getStartStopIndexes()
        nodes_tmp = []
        for node in nodes:
            ind = self.lattice.getNodeIndex(node)
            res = True
            if (start_ind >= 0):
                if (ind < start_ind):
                    res = False
            if (stop_ind >= 0):
                if (ind > stop_ind):
                    res = False
            if (res):
                nodes_tmp.append(node)
        return nodes_tmp

    def _updateBPM_Nodes(self, bpms=None):
        """
		Updates BPM nodes between start_node and stop_node.
		Returns array of bpm nodes.
		"""
        node_pos_dict = self.lattice.getNodePositionsDict()
        self.cleanBPM_Nodes()
        self.bpm_node_arr = []
        bpm_nodes = []
        if (bpms == None):
            markers = self.lattice.getNodesOfClass(MarkerLinacNode)
            for node in markers:
                if (node.getName().find("BPM") >= 0):
                    bpm_nodes.append(node)
        else:
            bpm_nodes = bpms
        self.bpm_node_arr = self._returnFilteredNodes(bpm_nodes)
        for bpm in self.bpm_node_arr:
            (start_pos, end_pos) = node_pos_dict[bpm]
            transvBPM = TransverseBPM(self, bpm)
            transvBPM.setPosition(start_pos)
            bpm.addChildNode(transvBPM, AccNode.ENTRANCE)
            self.transvBPM_arr.append(transvBPM)
        return self.bpm_node_arr

    def _updateDC_Nodes(self, nodes=None, class_type=None):
        """
		Updates DCorrector nodes that we use for orbit correction
		"""
        if (class_type == None): return
        dc_node_arr = None
        if (class_type == DCorrectorH):
            dc_node_arr = self.dch_node_arr
        if (class_type == DCorrectorV):
            dc_node_arr = self.dcv_node_arr
        if (dc_node_arr == None): return
        del dc_node_arr[:]
        if (nodes == None):
            dc_node_arr += self.lattice.getNodesOfClass(class_type)
        else:
            for node in nodes:
                if (isinstance(node, class_type)):
                    dc_node_arr.append(node)
        node_arr = self._returnFilteredNodes(dc_node_arr)
        del dc_node_arr[:]
        dc_node_arr += node_arr
        return dc_node_arr

    def _updateQuad_Nodes(self, nodes=None):
        """
		Updates Quad nodes with TransverseBPM instances
		"""
        node_pos_dict = self.lattice.getNodePositionsDict()
        self.cleanQuad_Nodes()
        self.quad_node_arr = []
        quad_arr = []
        if (nodes == None):
            quad_arr = self.lattice.getNodesOfClass(Quad)
        else:
            quad_arr = nodes
        quad_arr = self._returnFilteredNodes(quad_arr)
        for quad in quad_arr:
            (start_pos, end_pos) = node_pos_dict[quad]
            transvBPM = TransverseBPM(self, quad, "_entrance")
            transvBPM.setPosition(start_pos)
            quad.addChildNode(transvBPM, AccNode.ENTRANCE)
            self.quad_transvBPM_arr.append(transvBPM)
            transvBPM = TransverseBPM(self, quad, "_exit")
            transvBPM.setPosition(end_pos)
            quad.addChildNode(transvBPM, AccNode.EXIT)
            self.quad_transvBPM_arr.append(transvBPM)
        self.quad_node_arr = quad_arr
        return self.quad_node_arr

    def setBPMs(self, bpms):
        """
		Sets custom bpm array for analysis.
		In reality they can be any nodes.
		Returns array of bpm nodes.
		"""
        return self._updateBPM_Nodes(bpms)

    def getBPMs(self):
        """
		Returns array of bpm nodes.
		"""
        return self.bpm_node_arr

    def setDCHs(self, dchs):
        """
		Sets the DCorrectorHs
		"""
        self._updateDC_Nodes(dchs, DCorrectorH)
        return self.dch_node_arr

    def getDCHs(self):
        """
		Returns DCorrectorHs array
		"""
        return self.dch_node_arr

    def setDCHVs(self, dchs):
        """
		Sets the DCorrectorVs
		"""
        self._updateDC_Nodes(dchs, DCorrectorV)
        return self.dcv_node_arr

    def getDCVs(self):
        """
		Returns DCorrectorVs array
		"""
        return self.dcv_node_arr

    def setQuads(self, quads):
        """
		Sets Quads
		"""
        self._updateQuad_Nodes(quads)
        return self.quad_node_arr

    def getQuads(self):
        """
		Returns Quads array
		"""
        return self.quad_node_arr

    def getTransverseBPMs(self):
        return self.transvBPM_arr

    def getQuadTransverseBPMs(self):
        return self.quad_transvBPM_arr

    def getTransverseBPMforBPM(self, bpm):
        """
		Retuns the TransverseBPM instance for particular BPM.
		"""
        for child in bpm.getChildNodes(AccNode.ENTRANCE):
            if (isinstance(child, TransverseBPM)):
                return child
        return None

    def cleanBPM_Nodes(self):
        """
		Removes TransverseBPM child nodes from BPM nodes
		"""
        for bpm in self.bpm_node_arr:
            child_arr = bpm.getChildNodes(AccNode.ENTRANCE)
            transvBPM = None
            for child in child_arr:
                if (isinstance(child, TransverseBPM)):
                    transvBPM = child
                    break
            if (transvBPM != None):
                child_arr.remove(transvBPM)
        self.transvBPM_arr = []

    def cleanQuad_Nodes(self):
        """
		Removes TransverseBPM child nodes from Quad nodes
		"""
        for node in self.quad_node_arr:
            for place in [AccNode.ENTRANCE, AccNode.EXIT]:
                child_arr = node.getChildNodes(place)
                transvBPM = None
                for child in child_arr:
                    if (isinstance(child, TransverseBPM)):
                        transvBPM = child
                        break
                if (transvBPM != None):
                    child_arr.remove(transvBPM)
        self.quad_transvBPM_arr = []

    def correctTrajectory(self, bunch_initial):
        """
		This method will calculate and applyes fields to dipole correctors
		to achive minimal beam deviation from the center at all BPMs.
		LSQM method is used.
		"""
        bunch_in = self.makeOneParticleBunch(bunch_initial)
        #--------------------------
        bunch_init = Bunch()
        bunch_in.copyEmptyBunchTo(bunch_init)
        #---- add one particle to the bunch_init
        x0 = 0.
        xp0 = 0.
        y0 = 0.
        yp0 = 0.
        z0 = 0.
        dE = 0.
        bunch_init.addParticle(x0, xp0, y0, yp0, z0, dE)
        #----------------------------------
        n_bpms = len(self.bpm_node_arr)
        n_corrs_hor = len(self.dch_node_arr)
        n_corrs_ver = len(self.dcv_node_arr)
        horResponceMtrx = Matrix(n_bpms, n_corrs_hor)
        verResponceMtrx = Matrix(n_bpms, n_corrs_ver)
        self._calculatBPM_Matrix(bunch_init,
                                 horResponceMtrx,
                                 self.dch_node_arr,
                                 axis=0)
        self._calculatBPM_Matrix(bunch_init,
                                 verResponceMtrx,
                                 self.dcv_node_arr,
                                 axis=1)
        #printM(horResponceMtrx)
        horResponceMtrxTr = horResponceMtrx.copy()
        horResponceMtrxTr.transpose()
        verResponceMtrxTr = verResponceMtrx.copy()
        verResponceMtrxTr.transpose()
        horAmtrx = (horResponceMtrxTr.mult(horResponceMtrx)).invert()
        verAmtrx = (verResponceMtrxTr.mult(verResponceMtrx)).invert()
        #printM(horAmtrx)
        #print "det(horAmtrx) = ",horAmtrx.det()
        horATmtrx = horAmtrx.mult(horResponceMtrxTr)
        verATmtrx = verAmtrx.mult(verResponceMtrxTr)
        #---- matrices for LSQM are ready - now use initial bunch to get
        #---- the trajectory that should be flattened
        bunch_init = Bunch()
        bunch_in.copyBunchTo(bunch_init)
        (bpm_value_hor_arr,
         bpm_value_ver_arr) = self.calculateTrajectory(bunch_init)
        horBPM_V = PhaseVector(len(bpm_value_hor_arr))
        for ind in range(len(bpm_value_hor_arr)):
            horBPM_V.set(ind, bpm_value_hor_arr[ind])
        verBPM_V = PhaseVector(len(bpm_value_ver_arr))
        for ind in range(len(bpm_value_ver_arr)):
            verBPM_V.set(ind, bpm_value_ver_arr[ind])
        dch_val_V = horATmtrx.mult(horBPM_V)
        dcv_val_V = verATmtrx.mult(verBPM_V)
        #print "debug =========== final DCH fields ================"
        for ind in range(dch_val_V.size()):
            dc = self.dch_node_arr[ind]
            delta_field = dch_val_V.get(ind)
            #print "debug corr =",dc.getName()," init field [T] =",dc.getParam("B")," delta [T] =",delta_field
            dc.setParam("B", dc.getParam("B") - delta_field)
        #print "debug =========== final DCV fields ================"
        for ind in range(dcv_val_V.size()):
            dc = self.dcv_node_arr[ind]
            delta_field = dcv_val_V.get(ind)
            #print "debug corr =",dc.getName()," init field [T] =",dc.getParam("B")," delta [T] =",delta_field
            dc.setParam("B", dc.getParam("B") - delta_field)

    def _calculatBPM_Matrix(self,
                            bunch_init,
                            responceMtrx,
                            dc_node_arr,
                            axis=None):
        corr_field_arr = []
        for dc_node in dc_node_arr:
            corr_field_arr.append(dc_node.getParam("B"))
        #---------------------------------------------
        bpm_value_init_arr = self.calculateTrajectory(bunch_init)[axis]
        for dc_node_ind in range(len(dc_node_arr)):
            dc_node = dc_node_arr[dc_node_ind]
            field = corr_field_arr[dc_node_ind] + self.deltaB
            dc_node.setParam("B", field)
            bpm_value_arr = self.calculateTrajectory(bunch_init)[axis]
            for bpm_ind in range(len(self.transvBPM_arr)):
                deltaVal = bpm_value_arr[bpm_ind] - bpm_value_init_arr[bpm_ind]
                derivative = deltaVal / self.deltaB
                responceMtrx.set(bpm_ind, dc_node_ind, derivative)
            dc_node.setParam("B", corr_field_arr[dc_node_ind])

    def calculateTrajectory(self, bunch_init, print_info=False):
        """
		It tracks bunch with one particle through the lattice and
		fills out the BPM data in self.transvBPM_arr
		Returns arrays of x,y corrdinates of the bunch in
		(pm_value_hor_arr,bpm_value_ver_arr) tuple.
		"""
        bunch = Bunch()
        bunch_init.copyBunchTo(bunch)
        (start_ind, stop_ind) = self._getStartStopIndexes()
        self.lattice.trackDesignBunch(bunch, None, None, start_ind, stop_ind)
        self.lattice.trackBunch(bunch, None, None, start_ind, stop_ind)
        bpm_value_hor_arr = []
        bpm_value_ver_arr = []
        for transvBPM in self.transvBPM_arr:
            val_hor = transvBPM.getCoordinates()[0]
            val_ver = transvBPM.getCoordinates()[2]
            bpm_value_hor_arr.append(val_hor)
            bpm_value_ver_arr.append(val_ver)
        #---- Start trajectory printing
        if (print_info):
            print " index name position[m]  x[mm] y[mm] "
            for ind in range(len(bpm_value_hor_arr)):
                hor_val = bpm_value_hor_arr[ind] * 1000.
                ver_val = bpm_value_ver_arr[ind] * 1000.
                bpm_node = self.bpm_node_arr[ind]
                transvBPM = self.transvBPM_arr[ind]
                pos = transvBPM.getPosition()
                print " %2d %20s  %8.3f   %+6.2f %+6.2f " % (
                    ind, bpm_node.getName(), pos, hor_val, ver_val)
        #---- Stop trajectory printing
        return (bpm_value_hor_arr, bpm_value_ver_arr)

    def makeOneParticleBunch(self, bunch_init):
        """
		Returns the bunch with one particle which coordinates
		are equal to the average coordinates in the initial
		bunch.
		"""
        bunch_out = Bunch()
        bunch_init.copyEmptyBunchTo(bunch_out)
        x_avg = 0.
        xp_avg = 0.
        y_avg = 0.
        yp_avg = 0.
        z_avg = 0.
        dE_avg = 0.
        nParts = bunch_init.getSizeGlobal()
        if (nParts > 0):
            self.twiss_analysis.analyzeBunch(bunch_init)
            x_avg = self.twiss_analysis.getAverage(0)
            xp_avg = self.twiss_analysis.getAverage(1)
            y_avg = self.twiss_analysis.getAverage(2)
            yp_avg = self.twiss_analysis.getAverage(3)
            z_avg = self.twiss_analysis.getAverage(4)
            dE_avg = self.twiss_analysis.getAverage(5)
        #----------------------------------------
        #---- add one particle to the bunch_out
        bunch_out.addParticle(x_avg, xp_avg, y_avg, yp_avg, z_avg, dE_avg)
        return bunch_out
예제 #7
0
#

#----------------------------------------------------
# Define output dictionary
#----------------------------------------------------

output_dictionary = Output_dictionary()
output_dictionary.addParameter('turn', lambda: turn)
output_dictionary.addParameter('intensity',
                               lambda: bunchtwissanalysis.getGlobalMacrosize())
output_dictionary.addParameter('n_mp',
                               lambda: bunchtwissanalysis.getGlobalCount())
output_dictionary.addParameter('gamma',
                               lambda: bunch.getSyncParticle().gamma())
output_dictionary.addParameter('mean_x',
                               lambda: bunchtwissanalysis.getAverage(0))
output_dictionary.addParameter('mean_xp',
                               lambda: bunchtwissanalysis.getAverage(1))
output_dictionary.addParameter('mean_y',
                               lambda: bunchtwissanalysis.getAverage(2))
output_dictionary.addParameter('mean_yp',
                               lambda: bunchtwissanalysis.getAverage(3))
output_dictionary.addParameter('mean_z',
                               lambda: bunchtwissanalysis.getAverage(4))
output_dictionary.addParameter('mean_dE',
                               lambda: bunchtwissanalysis.getAverage(5))
output_dictionary.addParameter(
    'epsn_x', lambda: bunchtwissanalysis.getEmittanceNormalized(0))
output_dictionary.addParameter(
    'epsn_y', lambda: bunchtwissanalysis.getEmittanceNormalized(1))
output_dictionary.addParameter(