qsfp_service

qsfp_service manages the pluggable transceivers (QSFP, OSFP, and similar, using the SFF and CMIS management interfaces) and the external PHYs (retimers, gearboxes) of a switch. The agent programs the ASIC side of each port; qsfp_service brings up the optic and any PHY in between, collects digital optical monitoring (DOM) data, handles insertion and removal, remediates stuck modules, and can upgrade module firmware. This page covers how it identifies the platform, its configuration, flags, state machines, how it works with the agent, and its tests.

Where It Fits

fboss_sw_agent / hw agent  <--- Thrift --->  qsfp_service (5910)  ---> transceivers (I2C via BSP)
                                                  |                 ---> external PHYs (PHY SAI / PAI)
                                                  +--> FSDB (state + stats)
  • The agent tells qsfp_service which ports are enabled and at what profile; qsfp_service configures the matching transceiver (and PHY) and reports transceiver state back.
  • wedge_qsfp_util and fboss2 show transceiver are clients of its Thrift API (QsfpService, port 5910). See Diagnostic Tools.
  • On platforms with external PHYs, qsfp_service is linked against the PHY vendor's SAI SDK (Broadcom PAI), built as a separate pass. See Building FBOSS.

Platform Identification

qsfp_service needs two mappings for the platform it runs on:

  • Platform mapping: the ports, their lanes, and transceiver IDs. For qsfp_service the relevant parts are the number of ports and transceivers.
  • BSP platform mapping: the device paths used to control each transceiver (presence, reset, I2C data access) and, for led_service, the LEDs. It is derived from the platform's platform_manager.json, and the paths are the /run/devmap/xcvrs/ nodes PlatformManager creates.

Both are described in Platform Support. The platform type comes from /var/facebook/fboss/fruid.json (the --fruid_filepath flag). It can be overridden with the --mode flag, typically through defaultCommandLineArgs in the QSFP config, for platforms whose fruid.json is not reliable. For tests, --platform_mapping_override_path and --bsp_platform_mapping_override_path replace the built-in mappings.

Configuration: qsfp.conf

qsfp_service reads /etc/coop/qsfp.conf (--qsfp_config). --qsfp_config_current (/etc/coop/qsfp/current) is a deprecated older location. The file is the JSON form of QsfpServiceConfig in fboss/qsfp_service/if/qsfp_service_config.thrift:

Key Meaning
defaultCommandLineArgs Flag defaults, applied the same way as the agent's
transceiverConfigOverrides Per-transceiver setting overrides (for example by module type or speed)
sdk_version QSFP/PHY SDK version information
qsfpTestConfig Settings used by QSFP hardware tests
transceiverFirmwareVersions Expected firmware versions per module, used by firmware upgrade
transceiverI2cLogging I2C transaction logging settings
transceiverValidationConfig Vendor/part combinations considered valid (with --enable_tcvr_validation)
tunableOpticsConfig Optical channel configuration for tunable optics
phyConfig External PHY configuration
thriftApiToRateLimitInQps Per-API Thrift rate limits

Test configs for many platforms are in fboss/oss/qsfp_test_configs/ and are packaged into /opt/fboss/share/qsfp_test_configs/.

Flags

Flag Default Meaning
--port 5910 Thrift port (--migrated_port, default 5960, is the planned replacement)
--qsfp_config /etc/coop/qsfp.conf Config file
--qsfp_service_volatile_dir /dev/shm/fboss/qsfp_service Where the cold boot flag is stored
--loop_interval 5 Seconds between runs of the main loop that refreshes transceivers and drives the state machines
--stats_publish_interval 60 Seconds between stats publications
--xphy_stats_loop_interval 10 Seconds between external PHY stats updates
--can_qsfp_service_warm_boot true Allow warm boot of qsfp_service
--port_manager_mode false Let a PortManager object own all port-level logic, leaving TransceiverManager with transceiver-level logic only
--firmware_upgrade_supported false Enable module firmware upgrade support
--firmware_upgrade_on_coldboot, --firmware_upgrade_on_tcvr_insert false Upgrade firmware automatically on cold boot, or when a module is inserted
--max_concurrent_evb_fw_upgrade 1 Transceivers sharing one EVB that may upgrade at a time
--firmware_upgrade_time_limit 1080 Seconds before an upgrade counts as slow (an fb303 counter is incremented)
--enable_tcvr_validation false Validate transceivers against transceiverValidationConfig
--transceiver_properties_config Path to a transceiver_properties.json file
--state_machine_update_thread_heartbeat_ms 20000 Heartbeat for the state machine update threads
--qsfp_enable_thrift_acceptor, --qsfp_trusted_subnets false, empty Only accept Thrift connections from loopback and the listed CIDR subnets
--qsfp_thrift_rate_limit_shadow_mode true Rate limiting only logs and counts

The MACsec-related flags (--sak_list_warmboot_config default /var/facebook/fboss/mka_service/sak_lists/, --sak_config_validity_in_secs default 3600) store SAK configuration across restarts for the MKA service.

How It Works

qsfp_service keeps a state machine per transceiver (TransceiverStateMachine) and, in port manager mode, per port (PortStateMachine). Every --loop_interval seconds the main loop:

  1. refreshes presence and data for all transceivers (in parallel across slots, using per-slot threads),
  2. advances each state machine: detect a newly present module, read its EEPROM, discover its type, program it for the port's profile, and mark it ready (or remediate it if it is stuck),
  3. updates the ports known from the agent, and
  4. publishes state, and periodically stats, to FSDB and fb303.

The repository's tests under fboss/qsfp_service/test/ (for example TransceiverStateMachineTest, PortStateMachineTest) document the exact transitions.

Warm boot: on a warm restart qsfp_service keeps modules programmed instead of resetting them. The cold boot flag in --qsfp_service_volatile_dir forces the next start to be a cold boot.

Running It

qsfp_service --qsfp_config /etc/coop/qsfp.conf

or as the qsfp_service systemd unit. run_test.py services start qsfp --qsfp-config <file> starts it with a test config (see Running Tests).

Tests

Binary What it tests Hardware
qsfp_hw_test qsfp_service features on real modules (run_test.py qsfp) Switch with optics
qsfp_hal_test The transceiver hardware abstraction layer Switch
qsfp_hw_test_benchmark Transceiver refresh and programming speed (run_test.py benchmark --qsfp) Switch
cmis_test, transceiver_manager_test, transceiver_state_machine_test Unit tests None

The T0 QSFP suite is share/hw_sanity_tests/t0_qsfp_hw_tests.conf; platforms without transceivers use t0_qsfp_hw_tests_without_transceivers.conf. Known-bad lists are keyed by <platform>/<phy_sdk> style keys. See Test Suites.

Adding a New Optic

The upstream guide is candid that adding support for a new optic is "not straightforward" yet. In practice it means extending the SFF or CMIS module code in fboss/qsfp_service/module/, adding any per-module overrides to transceiverConfigOverrides, and passing the QSFP hardware and link tests. The transceiver onboarding document in the repo describes Meta's process.

See Also