Overview
This page summarizes the design & implementation of the inference between the live FACET-II controls system and the FACET2E Bmad model.
...
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) | totally static, contents of BmadLiveModel.live will be identical to .design |
live model data with manual updates | instanced |
| This mode is designed for making lattice tweaks in Tao relative to extant machine settings, might be an edge-case use... |
live model data with real-time streaming |
| 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.
At each iteration, the watcher threads will:
- check the PVs associated with every live device they are responsible for setting
- check if device setting has changed beyond some tolerance (exact tolerance band could be device dependent, picked to prevent analog/digital noise from prompting constant updates)
- push tao commands to a shared queue of updates (how implement?)
Separately, the model-update thread will do the following at each iteration:
- read in and execute the queue of tao commands
- write new data to the
BmadLiveModel.live
data structure
Name | responsibility | notes |
---|---|---|
rf-watcher |
| main challenge here is going from overall klystron ampl/phase to parameters for A/B/C/D structures |
mag1-watcher |
| is converting from integrated field strength in kGm as simple as dividing by L_eff ??? |
mag2-watcher |
| other stuff: solenoid, sextupoles, skew devices? |
model-update |
| needs exclusive write access to model data structs to avoid races, resource starvation etc... |
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
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 |
~/receiver.py | contains functions for getting data from the live model PVA server (analogous to F2_ModelReceiver.m ) |