Overview
This page summarizes the design & implementation of the interface between the live FACET-II controls system and the FACET2E Bmad model.
Code is still WIP. Design details here are subject to change.
GitHub mirror: F2_live_model.git
API documentation: f2-live-model.readthedocs.io/
BmadLiveModel
The BmadLiveModel python class loads the FACET2E lattice and runs a local copy of Tao.v This object connects to the production controls system via EPICS Channel Access, and connects callback functions to each live quantity (PV) of interest. When live quantities change, these callbacks will submit tao update commands to a shared queue. Additionally, a daemon thread will periodically empty the queue and execute all the scheduled update commands and then update the BmadLiveModel.live
data structure.
Modes of use
The BmadLiveModel can be used in three distinct modes, depending on the input flags at construction:
Mode | kw arg | Code snippet | Notes |
---|---|---|---|
design model only | design_only | f2m = BmadLiveModel(design_only=True) | static data only, BmadLiveModel.live is not defined |
live model data with manual updates | instanced | f2m = BmadLiveModel(instanced=True) | This mode is designed for making lattice tweaks in Tao relative to extant machine settings |
live model data with real-time streaming | f2m = BmadLiveModel() or: with BmadLiveModel() as f2m: | Use of the context manager is the "most pythonic" practice, but manual start() and stop() functions are also defined |
Daemon process design
Controls system communication is asynchronous to maximize update frequency. Responsibility of each thread should be designed for load balancing, to maximize the live model response time.
Upon PV value change, each callback
function will
- convert the new value into Bmad units (i.e. from kGm → T, GeV → eV etc)
- generate a
tao
command string of the form:"set ele <element> -attr <attribute> = <value>"
- submit the update command to the command queue
Separately, the model-update
thread will do the following at each iteration:
- empty the command queue of (approximately*) all submitted commands
- disable lattice recalculation, run all the
set ele
commands, then re-enable lattice recalculation (and recalculate lattice parameters) - update the
live.p0c, live.e_tot, live.twiss, live.quads, live.xcors, live.ycors, live.bends, live.rf
data structures (← or update on request?)
F2 Live Model Server
The live model server runs its own BmadLiveModel, and periodically writes live model data for NTTables accessible on the controls system via EPICS PVAccess. The table PVs are as follows
Access to the live Bmad model server (for twiss/rmat data), should be provided through the python meme
service
PV name | table columns | notes |
---|---|---|
BMAD:SYS0:1:FACET2E:LIVE:TWISS | element, device_name, s, z, length, p0c, alpha_x, beta_x, eta_x, etap_x, psi_x, alpha_y, ..., psi_y | not sure if s and z are both helpful |
BMAD:SYS0:1:FACET2E:LIVE:RMAT | element, device_name, s, z, length, r11, r12, r13, r14, r15, r16, r21, r22, ..., r65, r66 | |
BMAD:SYS0:1:FACET2E:DESIGN:TWISS | element, device_name, s, z, length, p0c, alpha_x, beta_x, eta_x, etap_x, psi_x, alpha_y, ..., psi_y | |
BMAD:SYS0:1:FACET2E:DESIGN:RMAT | element, device_name, s, z, length, r11, r12, r13, r14, r15, r16, r21, r22, ..., r65, r66 | |
BMAD:SYS0:1:FACET2E:LEM_DATA | element, device_name, EREF, EACT, BREF, BACT, BERR, more ?? | single NTTable seems simpler than lcls-style per-device PVs |
Implementation details
Source: F2_live_model/ | Details |
---|---|
~/structs.py | auxiliary data structures for holding beamline data |
~/bmad.py | implements the BmadLiveModel class |
~/server.py | live model PVA service |