Source code for mbtrack2.instability.instabilities

# -*- coding: utf-8 -*-
"""
General calculations about instability thresholds.
"""

import math

import matplotlib.pyplot as plt
import numpy as np
from scipy.constants import c, e, epsilon_0, m_e, mu_0, pi


[docs]def mbi_threshold(ring, sigma, R, b): """ Compute the microbunching instability (MBI) threshold for a bunched beam considering the steady-state parallel plate model [1][2]. Parameters ---------- ring : Synchrotron object sigma : float RMS bunch length in [s] R : float dipole bending radius in [m] b : float vertical distance between the conducting parallel plates in [m] Returns ------- I : float MBI current threshold in [A] [1] : Y. Cai, "Theory of microwave instability and coherent synchrotron radiation in electron storage rings", SLAC-PUB-14561 [2] : D. Zhou, "Coherent synchrotron radiation and microwave instability in electron storage rings", PhD thesis, p112 """ sigma = sigma * c Ia = 4 * pi * epsilon_0 * m_e * c**3 / e # Alfven current chi = sigma * (R / b**3)**(1 / 2) # Shielding paramter xi = 0.5 + 0.34*chi N = (ring.L * Ia * ring.ac * ring.gamma * ring.sigma_delta**2 * xi * sigma**(1 / 3) / (c * e * R**(1 / 3))) I = N * e / ring.T0 return I
[docs]def cbi_threshold(ring, I, Vrf, f, beta, Ncav=1): """ Compute the longitudinal and transverse coupled bunch instability thresolds driven by HOMs [1]. Approximate formula, does not take into account variation with Q. For better estimate use lcbi_growth_rate. Parameters ---------- ring : Synchrotron object I : float Total beam current in [A]. Vrf : float Total RF voltage in [V]. f : float Frequency of the HOM in [Hz]. beta : array-like of shape (2,) Horizontal and vertical beta function at the HOM position in [m]. Ncav : int, optional Number of RF cavity. Returns ------- Zlong : float Maximum longitudinal impedance of the HOM in [ohm]. Zxdip : float Maximum horizontal dipolar impedance of the HOM in [ohm/m]. Zydip : float Maximum vertical dipolar impedance of the HOM in [ohm/m]. References ---------- [1] : Ruprecht, Martin, et al. "Calculation of Transverse Coupled Bunch Instabilities in Electron Storage Rings Driven By Quadrupole Higher Order Modes." 7th Int. Particle Accelerator Conf.(IPAC'16), Busan, Korea. """ fs = ring.synchrotron_tune(Vrf) * ring.f0 Zlong = fs / (f * ring.ac * ring.tau[2]) * (2 * ring.E0) / (ring.f0 * I * Ncav) Zxdip = 1 / (ring.tau[0] * beta[0]) * (2 * ring.E0) / (ring.f0 * I * Ncav) Zydip = 1 / (ring.tau[1] * beta[1]) * (2 * ring.E0) / (ring.f0 * I * Ncav) return (Zlong, Zxdip, Zydip)
[docs]def lcbi_growth_rate_mode(ring, I, M, mu, synchrotron_tune=None, Vrf=None, fr=None, RL=None, QL=None, Z=None): """ Compute the longitudinal coupled bunch instability growth rate driven by an impedance for a given coupled bunch mode mu [1]. Use either a list of resonators (fr, RL, QL) or an Impedance object (Z). Parameters ---------- ring : Synchrotron object I : float Total beam current in [A]. M : int Nomber of bunches in the beam. mu : int Coupled bunch mode number (= 0, ..., M-1). synchrotron_tune : float, optional Synchrotron tune. Vrf : float, optinal Total RF voltage in [V] used to compute synchrotron tune if not given. fr : float or list, optional Frequency of the resonator in [Hz]. RL : float or list, optional Loaded shunt impedance of the resonator in [Ohm]. QL : float or list, optional Loaded quality factor of the resonator. Z : Impedance, optional Longitunial impedance to consider. Returns ------- float Coupled bunch instability growth rate for the mode mu in [s-1]. References ---------- [1] : Eq. 51 p139 of Akai, Kazunori. "RF System for Electron Storage Rings." Physics And Engineering Of High Performance Electron Storage Rings And Application Of Superconducting Technology. 2002. 118-149. """ if synchrotron_tune is None and Vrf is None: raise ValueError("Either synchrotron_tune or Vrf is needed.") if synchrotron_tune is None: nu_s = ring.synchrotron_tune(Vrf) else: nu_s = synchrotron_tune factor = ring.eta() * I / (4 * np.pi * ring.E0 * nu_s) if isinstance(fr, (float, int)): fr = np.array([fr]) elif isinstance(fr, list): fr = np.array(fr) if isinstance(RL, (float, int)): RL = np.array([RL]) elif isinstance(RL, list): RL = np.array(RL) if isinstance(QL, (float, int)): QL = np.array([QL]) elif isinstance(QL, list): QL = np.array(QL) if Z is None: omega_r = 2 * np.pi * fr n_max = int(10 * omega_r.max() / (ring.omega0 * M)) def Zr(omega): Z = 0 for i in range(len(fr)): Z += np.real(RL[i] / (1 + 1j * QL[i] * (omega_r[i] / omega - omega / omega_r[i]))) return Z else: fmax = Z.data.index.max() n_max = int(2 * np.pi * fmax / (ring.omega0 * M)) def Zr(omega): return np.real(Z(omega / (2 * np.pi))) n0 = np.arange(n_max) n1 = np.arange(1, n_max) omega_p = ring.omega0 * (n0*M + mu + nu_s) omega_m = ring.omega0 * (n1*M - mu - nu_s) sum_val = np.sum(omega_p * Zr(omega_p)) - np.sum(omega_m * Zr(omega_m)) return factor * sum_val
[docs]def lcbi_growth_rate(ring, I, M, synchrotron_tune=None, Vrf=None, fr=None, RL=None, QL=None, Z=None): """ Compute the maximum growth rate for longitudinal coupled bunch instability driven an impedance [1]. Use either a list of resonators (fr, RL, QL) or an Impedance object (Z). Parameters ---------- ring : Synchrotron object I : float Total beam current in [A]. M : int Nomber of bunches in the beam. synchrotron_tune : float, optional Synchrotron tune. Vrf : float, optinal Total RF voltage in [V] used to compute synchrotron tune if not given. fr : float or list, optional Frequency of the HOM in [Hz]. RL : float or list, optional Loaded shunt impedance of the HOM in [Ohm]. QL : float or list, optional Loaded quality factor of the HOM. Z : Impedance, optional Longitunial impedance to consider. Returns ------- growth_rate : float Maximum coupled bunch instability growth rate in [s-1]. mu : int Coupled bunch mode number corresponding to the maximum coupled bunch instability growth rate. growth_rates : array Coupled bunch instability growth rates for the different mode numbers in [s-1]. References ---------- [1] : Eq. 51 p139 of Akai, Kazunori. "RF System for Electron Storage Rings." Physics And Engineering Of High Performance Electron Storage Rings And Application Of Superconducting Technology. 2002. 118-149. """ growth_rates = np.zeros(M) for i in range(M): growth_rates[i] = lcbi_growth_rate_mode( ring, I, M, i, synchrotron_tune=synchrotron_tune, Vrf=Vrf, fr=fr, RL=RL, QL=QL, Z=Z) growth_rate = np.max(growth_rates) mu = np.argmax(growth_rates) return growth_rate, mu, growth_rates
[docs]def lcbi_stability_diagram(ring, I, M, modes, cavity_list, detune_range, synchrotron_tune=None, Vrf=None): """ Plot longitudinal coupled bunch instability stability diagram for a arbitrary list of CavityResonator objects around a detuning range. Last object in the cavity_list is assumed to be the one with the variable detuning. Parameters ---------- ring : Synchrotron object Ring parameters. I : float Total beam current in [A]. M : int Nomber of bunches in the beam. modes : list Coupled bunch mode numbers to consider. cavity_list : list List of CavityResonator objects to consider, which can be: - active cavities - passive cavities - HOMs - mode dampers detune_range : array Detuning range (list of points) of the last CavityResonator object. synchrotron_tune : float, optional Synchrotron tune. Vrf : float, optinal Total RF voltage in [V] used to compute synchrotron tune if not given. Returns ------- fig : Figure Show the shunt impedance threshold for different coupled bunch modes. """ Rth = np.zeros_like(detune_range) fig, ax = plt.subplots() for mu in modes: fixed_gr = 0 for cav in cavity_list[:-1]: fixed_gr += lcbi_growth_rate_mode( ring, I=I, mu=mu, fr=cav.fr, RL=cav.RL, QL=cav.QL, M=M, synchrotron_tune=synchrotron_tune, Vrf=Vrf) cav = cavity_list[-1] for i, det in enumerate(detune_range): gr = lcbi_growth_rate_mode(ring, I=I, mu=mu, fr=cav.m * ring.f1 + det, RL=cav.RL, QL=cav.QL, M=M, synchrotron_tune=synchrotron_tune, Vrf=Vrf) Rth[i] = (1 / ring.tau[2] - fixed_gr) * cav.Rs / gr ax.plot(detune_range * 1e-3, Rth * 1e-6, label="$\mu$ = " + str(int(mu))) plt.xlabel(r"$\Delta f$ [kHz]") plt.ylabel(r"$R_{s,max}$ $[M\Omega]$") plt.yscale("log") plt.legend() return fig
[docs]def rwmbi_growth_rate(ring, current, beff, rho_material, plane='x'): """ Compute the growth rate of the transverse coupled-bunch instability induced by resistive wall impedance [1]. Parameters ---------- ring : Synchrotron object current : float Total beam current in [A]. beff : float Effective radius of the vacuum chamber in [m]. rho_material : float Resistivity of the chamber's wall material in [Ohm.m]. plane : str, optional The plane in which the instability will be computed. Use 'x' for the horizontal plane, and 'y' for the vertical. Reference --------- [1] Eq. (31) in R. Nagaoka and K. L. F. Bane, "Collective effects in a diffraction-limited storage ring", J. Synchrotron Rad. Vol 21, 2014. pp.937-960 """ plane_dict = {'x': 0, 'y': 1} index = plane_dict[plane] beta0 = ring.optics.local_beta[index] omega0 = ring.omega0 E0 = ring.E0 R = ring.L / (2 * np.pi) frac_tune, int_tune = math.modf(ring.tune[index]) Z0 = mu_0 * c gr = (beta0*omega0*current*R) / (4 * np.pi * E0 * beff**3) * ( (2*c*Z0*rho_material) / ((1-frac_tune) * omega0))**0.5 return gr
[docs]def rwmbi_threshold(ring, beff, rho_material, plane='x'): """ Compute the threshold current of the transverse coupled-bunch instability induced by resistive wall impedance [1]. Parameters ---------- ring : Synchrotron object beff : float Effective radius of the vacuum chamber in [m]. rho_material : float Resistivity of the chamber's wall material in [Ohm.m]. plane : str, optional The plane in which the instability will be computed. Use 'x' for the horizontal plane, and 'y' for the vertical. Reference --------- [1] Eq. (32) in R. Nagaoka and K. L. F. Bane, "Collective effects in a diffraction-limited storage ring", J. Synchrotron Rad. Vol 21, 2014. pp.937-960 """ plane_dict = {'x': 0, 'y': 1} index = plane_dict[plane] beta0 = ring.optics.local_beta[index] omega0 = ring.omega0 E0 = ring.E0 tau_rad = ring.tau[index] frac_tune, int_tune = math.modf(ring.tune[index]) Z0 = mu_0 * c Ith = (4 * np.pi * E0 * beff**3) / (c*beta0*tau_rad) * (( (1-frac_tune) * omega0) / (2*c*Z0*rho_material))**0.5 return Ith