Menlo Repetition Rate¶
From: Menlo Systems
Class: herosdevices.hardware.menlo.repetition_rate.RepetitionRate
Driver Quality Index: alpha
Additional Information Check before use¶
Menlo OFC Setup
This driver is split into one core device and several modules attached to it.
OFC opens the single QWebChannel websocket connection to the comb and
exposes its raw control/status tree via get_node/set_node/explore.
Each functional-layer module (DDS,
LaserLock, DualLaserLock,
FXE, RepetitionRate,
CEO, Oscillator) is a
separate HERO. It takes the already-running OFC
HERO as a constructor argument via BOSS’s "ofc": "$device_menlo_ofc" reference, so all modules share the
one physical connection instead of each opening their own.
See examples/menlo/ofc.json for a complete BOSS config wiring one comb with all its modules.
Some CW channels lock two wavelengths through one shared lock loop, with two separate frequency-distribution
blocks instead of one. Deploying plain LaserLock against one of these fails, since it hardcodes a single
frequency-distribution node name that these channels don’t have. Use
DualLaserLock instead, passing both wavelengths’ node names
explicitly; see examples/menlo/ofc.json for an example.
FXE wraps the comb’s 16-channel frequency counter. Unlike the other
modules, it has no default observables, since which channel carries which signal is deployment-specific.
Pass observables for the channels relevant to your comb, e.g. a beat on channel 3:
"arguments": {
"ofc": "$device_ofc",
"observables": {
"cw_beat": {"path": "counterFrequencies.channel03", "unit": "Hz"}
}
}
Node paths (used in get_node/set_node/observables) are firmware-dependent and not documented by
Menlo. Use format_tree() to find them interactively:
>>> print(ofc.format_tree("functionalLayer.rrSettings", depth=2))
functionalLayer.rrSettings
|-- dds
| |-- ddsFrequency = 28286800
| |-- outputOn = True
| `-- outputPower = 0.64
|-- mainControls
| |-- fastOutput ...
| |-- lock = True
| `-- slowOutput ...
`-- repetitionRate
|-- rrCounterRepRate = 250105340.0
`-- rrTargetBeatRF = 250105340
Nodes shown as ... are unexpanded branches; raise depth or call format_tree again rooted at that
path to descend further. explore() returns the same tree as a plain
dict instead of a rendered string, if you want to process it programmatically.
For anything specific to your comb (e.g. a customer-specific fiber-noise-cancellation module),
poll or control it directly instead of adding a new class: every module accepts an observables argument,
merged on top of its DEFAULT_OBSERVABLES, and OFC.get_node/OFC.set_node give full read/write
access to any node regardless.
"arguments": {
"host": "IP_OR_HOSTNAME",
"observables": {
"fnc578_locked": {"path": "functionalLayer.fnc578Settings.mainControls.lock", "unit": ""},
"fnc1157_locked": {"path": "functionalLayer.fnc1157Settings.mainControls.lock", "unit": ""}
}
}
Important
The OFC device’s _ensure_connected method must be reachable from the other modules over the
network. HEROS excludes underscore-prefixed methods from a RemoteHERO proxy unless marked
force_remote, so the OFC row in your BOSS config needs:
"extra_decorators": [["_ensure_connected", "heros.inspect.force_remote"]]
See examples/menlo/ofc.json for this in context.
Warning
The PyPI package named pywebchannel is an unrelated project; installing it will not work. Install it
from source instead:
pip install "pywebchannel @ git+https://github.com/MenloSystems/pywebchannel"
pywebchannel is not declared as a project dependency, so this install step must be run manually wherever the Menlo driver
is used: locally, in CI, and in any Docker image.
In a Docker Container deployment via BOSS, use the BOSS_PIP_PKGS environment variable (see the
BOSS documentation)
instead of extending the image:
services:
device_ofc:
image: registry.gitlab.com/atomiq-project/herosdevices:latest
restart: always
network_mode: host
volumes:
- ./ofc.json:/ofc.json:ro
environment:
- BOSS_PIP_PKGS=pywebchannel@git+https://github.com/MenloSystems/pywebchannel
command: python -m boss.starter -u file:///ofc.json --log info
Driver for the repetition-rate stabilization loop of a Menlo Systems frequency comb.
Wraps the OFC’s functionalLayer.rrSettings sub-tree, a fixed, singleton module (there is only one
repetition-rate loop per OFC, so unlike DDS/
LaserLock there is no funclayer_identifier to select).
Combines DDS (the loop’s underlying DDS, confirmed
identical in shape to a laser-lock module’s) with BeatLoop (the shared lock-loop shape).
This means RepetitionRate implements atomiq’s RFSource interface via the DDS: _set_frequency
tunes the DDS directly, not the loop’s beat-frequency setpoint (see beat_frequency_setpoint for
that).
Also exposes select_monitor (the same node shape seen on CW channels and CEO, so treated as a general default here). One observed comb additionally has amp1542 (laser-diode current control, see amp_node), frequencyDistributionOpticalBeat/frequencyDistributionRfBeat, and an operationMode.lockMode single/dual-lock switch - none of those are modeled here, since they weren’t seen anywhere else and it’s unconfirmed whether they’re a fixed feature of every Menlo repetition-rate loop or specific to that comb’s configuration. Poll/control them via observables or ofc.get_node/ set_node directly if your comb has them.
Bold arguments are mandatory. For more information on the listed arguments refer to the class documentation: herosdevices.hardware.menlo.repetition_rate.RepetitionRate If parameters appear in this list but not in the class definition, please recursively check the linked base classes for the definition of the parameter.
Argument |
Type |
Default Value |
Description |
|---|---|---|---|
ofc |
<class ‘herosdevices.hardware.menlo.ofc.OFC’> |
The OFC HERO this loop belongs to. |
|
amp_node |
str | None |
None |
Relative node name of this loop’s laser-diode current-control block (amp*), if it has one. None (the default) leaves |
observables |
dict[str, dict[str, str]] | None |
None |
Additional observables to poll, merged on top of DEFAULT_OBSERVABLES, see |
The following JSON strings can be used to start a HERO device representation of RepetitionRate using BOSS.
{
"_id": "device_menlo_ofc_rep_rate",
"classname": "herosdevices.hardware.menlo.RepetitionRate",
"arguments": {
"ofc": "$device_menlo_ofc"
},
"datasource": {
"async": false,
"interval": 15
}
}
Note
This example contains a variable that references another HERO with $.
from examples/menlo/ofc.json
{
"_id": "my_RepetitionRate",
"classname": "herosdevices.hardware.menlo.repetition_rate.RepetitionRate",
"arguments": {
"ofc": "<class 'herosdevices.hardware.menlo.ofc.OFC'>",
"amp_node": null,
"observables": null
}
}
generated from signature