ScheduleBuilder#
Module: iqm.pulse.builder
- class iqm.pulse.builder.ScheduleBuilder(op_table, calibration, station_properties)#
Bases:
objectBuilds instruction schedules out of quantum circuits or individual quantum operations.
Encapsulates known quantum ops, the calibration information for them, QPU components and their topology, and controller properties.
- Parameters:
op_table (QuantumOpTable) – definitions of known quantum ops
calibration (OpCalibrationDataTree) – calibration data tree for the quantum ops
station_properties (StationProperties) – Static station properties, e.g. QPU topology and available control channels.
Attributes
Station control channel properties.
Station QPU topology.
Mapping from QPU component name to mapping from function to its controller.
Mapping from QPU component name to list of probes that can send feedback bits to control that component.
Set of QPU components that have a physical drive channel.
barrierprxprx_12czmovemeasuremeasure_fidelitymeasure_012cc_prxCache for the CompositeGate TimeBoxes.
Methods
Build a playlist from a number of instruction schedules.
Convert a quantum circuit to a TimeBox.
Get a copy of the gate implementation cache.
Calibration data for the given quantum operation, implementation and locus.
Control channels that directly affect quantum operations at the given locus.
Drive channel for the given QPU component.
Flux channel for the given QPU component.
Provide an implementation for a quantum operation at a given locus.
Implementation class for the given operation.
Probe line channel for the probe line
componentbelongs to.Get the virtual fast feedback channel properties for a source component and a target component.
Get all the virtual fast feedback channel names for a source component and a feedback key.
True iff there is calibration data for the given quantum operation, implementation and locus.
Inject new calibration data, changing
calibrationafter initialisation.Inject gate definition updates, changing
op_tableafter initialisation.Resolve a TimeBox.
Resolve a TimeBox to an instruction schedule.
Temporary helper function, for converting a sequence of TimeBoxes to a Playlist.
Convert a sequence of TimeBoxes to a Playlist.
Check that the calibration data matches the known quantum operations.
Validate a sequence of circuit operations constituting a quantum circuit.
Utility method for applying Block instructions on every channel of the given locus.
- composite_cache#
Cache for the CompositeGate TimeBoxes. Flushed whenever ANY calibration data is injected into the builder.
- property chip_topology: ChipTopology#
Station QPU topology.
- property channels: dict[str, ChannelProperties]#
Station control channel properties.
- property component_channels: dict[str, dict[str, str]]#
Mapping from QPU component name to mapping from function to its controller.
- property feedback_sources: dict[str, list[str]]#
Mapping from QPU component name to list of probes that can send feedback bits to control that component.
- inject_gate_definitions(partial_gate_definitions)#
Inject gate definition updates, changing
op_tableafter initialisation.Currently only supports updating the default implementation for quantum operations.
- Parameters:
partial_gate_definitions (dict[str, Any]) – gate definition data to be injected.
- Raises:
ValueError – if attempting to inject unsupported QuantumOp attributes.
- Return type:
None
- inject_calibration(partial_calibration, cache=None)#
Inject new calibration data, changing
calibrationafter initialisation.Invalidates the GateImplementation caches for the affected operations/implementations/loci. Also invalidates the cache for any factorizable gate implementation, if any of its locus components was affected.
- Parameters:
partial_calibration (dict[str, dict[str, dict[tuple[str, ...], dict[str, Any]]]]) – data to be injected. Must have the same structure as
calibrationbut does not have to contain all operations/implementations/loci/values. Only the parts of the data that are found will be merged intocalibration(including anyNonevalues)._cachewill be invalidated for the found operations/implementations/loci and only if the new calibration data actually differs from the previous.cache (dict[str, dict[str, dict[tuple[str, ...], GateImplementation]]] | None) – if an implementation cache is given, we do not invalidate the cache for affected loci, but instead fetch the implementations from the provided cache (if they exist there).
- Return type:
None
- get_cache(ops=None, implementations=None, loci=None)#
Get a copy of the gate implementation cache.
- validate_calibration()#
Check that the calibration data matches the known quantum operations.
- Raises:
ValueError – there is something wrong with the calibration data
- Return type:
None
- get_drive_channel(component)#
Drive channel for the given QPU component.
- get_flux_channel(component)#
Flux channel for the given QPU component.
See
get_drive_channel().
- get_probe_channel(component)#
Probe line channel for the probe line
componentbelongs to.See
get_drive_channel().
- get_virtual_feedback_channel_names(source_component, feedback_key)#
Get all the virtual fast feedback channel names for a source component and a feedback key.
- Parameters:
- Returns:
- A set of virtual fast feedback channel names that can be used to control the source component,
associated with the given feedback key. If no such channels exist, an empty set is returned.
- Return type:
- get_virtual_feedback_channel_for(source_component, target_component)#
Get the virtual fast feedback channel properties for a source component and a target component.
- Parameters:
- Returns:
The ChannelProperties for the virtual fast feedback channel.
- Return type:
- has_calibration(op_name, impl_name, locus)#
True iff there is calibration data for the given quantum operation, implementation and locus.
- get_calibration(op_name, impl_name, locus, *, strict=True)#
Calibration data for the given quantum operation, implementation and locus.
- Parameters:
- Returns:
Requested calibration data, or an empty dict if
strict == Falseand not found.- Raises:
ValueError – Requested calibration data was not found and
strict == True.- Return type:
- get_control_channels(locus)#
Control channels that directly affect quantum operations at the given locus.
Includes the probe, drive and flux channels of the locus QPU components. Does not include e.g. any neighboring coupler channels, these will have to be added separately in the TimeBox resolution phase.
Will only return channels that are known to exist, i.e. are found in
ScheduleBuilder.channels.
- wait(locus, duration, *, rounding=False)#
Utility method for applying Block instructions on every channel of the given locus.
The Block instructions guarantee the locus components to idle for the given duration, and cannot e.g. be replaced with e.g. dynamical decoupling sequences. They are treated the same as any other TimeBox contents:
Blocks on different channels remain aligned in time during scheduling.
The actual waiting time on a particular channel may thus be >=
duration, if the other channels have less non-blocking space on either side.
Note
TODO For now, this method can round
durationto the nearest value allowed by each channel if requested. This is for the benefit of EXA sweeping over waiting durations. In the future, EXA sweep generation should be responsible for doing the rounding.- Parameters:
locus (Iterable[str]) – locus components that should experience the wait
duration (float) – how long to wait (in seconds)
rounding (bool) – Iff True, for each channel separately,
durationwill be rounded to the nearest value allowed by the granularity of that channel. The Waits will start simultaneously.
- Returns:
box containing
Blockinstructions on every control channel oflocus- Return type:
- get_implementation(op_name: Literal['prx', 'prx_12'], locus: Sequence[str], impl_name: str | None = None, *, strict_locus: bool = False, priority_calibration: dict[str, Any] | None = None, priority_calibration_factorizable: dict[tuple[str, ...], dict[str, Any]] | None = None) PrxGateImplementation#
- get_implementation(op_name: Literal['cz', 'move'], locus: Sequence[str], impl_name: str | None = None, *, strict_locus: bool = False, priority_calibration: dict[str, Any] | None = None, priority_calibration_factorizable: dict[tuple[str, ...], dict[str, Any]] | None = None) FluxPulseGate
- get_implementation(op_name: Literal['measure', 'measure_fidelity', 'measure_012'], locus: Sequence[str], impl_name: str | None = None, *, strict_locus: bool = False, priority_calibration: dict[str, Any] | None = None, priority_calibration_factorizable: dict[tuple[str, ...], dict[str, Any]] | None = None) Measure_CustomWaveforms
- get_implementation(op_name: Literal['cc_prx'], locus: Sequence[str], impl_name: str | None = None, *, strict_locus: bool = False, priority_calibration: dict[str, Any] | None = None, priority_calibration_factorizable: dict[tuple[str, ...], dict[str, Any]] | None = None) CCPRX_Composite
- get_implementation(op_name: str, locus: Sequence[str], impl_name: str | None = None, *, strict_locus: bool = False, priority_calibration: dict[str, Any] | None = None, priority_calibration_factorizable: dict[tuple[str, ...], dict[str, Any]] | None = None) GateImplementation
Provide an implementation for a quantum operation at a given locus.
The GateImplementations are built when they are first requested, and cached for later use.
For convenience, the returned implementation may use a permuted
locus(and the calibration data associated with it) based on the following rules:If the operation is not symmetric (e.g. CX), different
locusorders correspond to different operations, and thus the locus order may not be changed.If the operation is symmetric (e.g. CZ), all
locusorders correspond to the same logical operation. However, symmetric operations may have non-symmetric implementations.If the chosen implementation is symmetric, we order
locusnumerically (not lexicographically!), so that we only need to have calibration data for one locus order.Otherwise, if
strict_locusis False, we check all permutations oflocus, and pick the first one that has calibration data available. The original order is checked first. Ifstrict_locusis True, only the original order may be used.
The attributes
QuantumOp.factorizable,GateImplementation.needs_calibrationand whether the implementation is aCompositeGateinteract in a nontrivial way. Examples of their currently used combinations:composite / not composite
factorizable
not factorizable
needs_calibration
measure_fidelity.shelved_constant/measure.constantcc_prx.prx_composite/prx.drag_crfnot needs_calibration
reset.conditional/ not meaningfulrz.prx_composite/rz.virtual- Parameters:
op_name – Name of the quantum operation.
locus – Locus of the operation.
impl_name – Name of the implementation.
Nonemeans the implementation is chosen automatically usingQuantumOp.get_default_implementation_for_locus().strict_locus – Only has an effect if the operation is symmetric (e.g. CZ). Iff False and the chosen implementation is non-symmetric, the locus order may be changed if no calibration data is available for the requested locus order.
priority_calibration – Single-locus calibration data to override the common calibration data in
calibration. Any non-None values found inpriority_calibrationwill be merged to the common calibration. If used,impl_namemust not be None sincepriority_calibrationis implementation-specific. Note: usingpriority_calibrationwill prevent caching.priority_calibration_factorizable – Like
priority_calibration, but for factorizable QuantumOps. Mapping from single-qubit loci to overrides of their calibration data.
- Returns:
Requested implementation.
- Raises:
ValueError – Requested implementation could not be provided.
- get_implementation_class(op_name, impl_name=None)#
Implementation class for the given operation.
- Parameters:
- Returns:
requested implementation class
- Return type:
- validate_quantum_circuit(operations, *, require_measurements=False)#
Validate a sequence of circuit operations constituting a quantum circuit.
- Parameters:
operations (Iterable[CircuitOperation]) – quantum circuit to be validated
require_measurements (bool) – iff True the circuit must include at least one measurement operation
- Raises:
ValueError –
operationsdo not constitute a valid quantum circuit- Return type:
None
- circuit_to_timebox(circuit, *, name='', scheduling=SchedulingStrategy.ASAP, scheduling_algorithm=SchedulingAlgorithm.HARD_BOUNDARY, locus_mapping=None)#
Convert a quantum circuit to a TimeBox.
- Parameters:
circuit (Iterable[CircuitOperation]) – quantum circuit
name (str) – name of the circuit
scheduling (SchedulingStrategy) – scheduling strategy (e.g. ASAP or ALAP) to be used in resolving the TimeBoxes.
scheduling_algorithm (SchedulingAlgorithm) – scheduling algorithm to be used in resolving the TimeBoxes.
locus_mapping (dict[str, str] | None) – optional mapping of placeholder component names to the physical component names used while resolving the circuit into a TimeBox.
- Returns:
unresolved TimeBox that implements
circuit- Raises:
ValueError – failed to convert
circuitto a TimeBox- Return type:
- timeboxes_to_front_padded_playlist(boxes, *, neighborhood=0)#
Temporary helper function, for converting a sequence of TimeBoxes to a Playlist.
Each individual TimeBox in
boxesis resolved into a Schedule, and then each schedule is front-padded withWaitinstructions on each channel such that the resulting Schedules have equal durations. This is required since for now in Station Control the delay before the final measurement is the same for all the Schedules in a Playlist, and we do not wish to lose coherence waiting for the measurement after each Schedule is done.TODO Once Station Control can handle measurements better, this method should be removed, and
timeboxes_to_playlist()be used instead.- Parameters:
- Returns:
playlist that implements
boxesand the readout metrics for that playlist.- Return type:
- timeboxes_to_playlist(boxes, *, neighborhood=1)#
Convert a sequence of TimeBoxes to a Playlist.
Resolves the boxes, converts them to Schedules, removes unnecessary channels, and then packs the Schedules into a Playlist. Assumes all the TimeBoxes refer to the same QPU and its control channels.
- Parameters:
boxes (Iterable[TimeBox]) – TimeBoxes to include in the playlist
neighborhood (int) – During scheduling, block neighboring channels of the used components this far. The default value ensures that quantum operations work as intended, assuming the station is properly calibrated. Higher values may help defend against crosstalk, at the expense of a longer instruction schedule and thus more decoherence.
- Returns:
playlist that implements
boxes- Return type:
- timebox_to_schedule(box, *, neighborhood=1)#
Resolve a TimeBox to an instruction schedule.
- Parameters:
box (TimeBox) – TimeBox to resolve
neighborhood (int) – During scheduling, block neighboring channels of the used components this far. The default value ensures that quantum operations work as intended, assuming the station is properly calibrated. Higher values may help defend against crosstalk, at the expense of a longer instruction schedule and thus more decoherence.
- Returns:
Schedule that implements
box.- Return type:
- resolve_timebox(box, *, neighborhood, compute_neighborhood_hard_boundary=False)#
Resolve a TimeBox.
Resolves recursively each of the children of the box, and then concatenates the resulting Schedules into a new one using a specific scheduling strategy and algorithm.
The supported algorithms are
HARD_BOUNDARY, which treats each composite TimeBox as a solid rectangle (the longest channel within defines the duration) andTETRIS, which packs the schedule as tightly as possible (solid instructions still cannot overlap) regardless of the TimeBox boundaries.Modifies
boxso that it becomes atomic, if it isn’t already.- Parameters:
box (TimeBox) – TimeBox to resolve
neighborhood (int) – During scheduling, block control channels of neighboring QPU components this far from the locus. Values higher than 0 may help defend against crosstalk, at the expense of a longer instruction schedule and thus more decoherence.
compute_neighborhood_hard_boundary (bool) – Whether to precompute the neighborhood components while resolving a composite
TimeBoxin theHARD_BOUNDARYalgorithm. Typically one does not want to do this on the top layer compositeTimeBox, since it would be unused. The algorithm sets thisTrueon lower layers, where it improves the performance as the neighborhood components are needed in scheduling.
- Returns:
instruction schedule that implements
box- Return type:
- build_playlist(schedules, finish_schedules=True)#
Build a playlist from a number of instruction schedules.
This involves compressing the schedules so that no duplicate information needs to be transferred to Station Control.
- Parameters:
schedules (Sequence[Schedule]) – Instruction schedules to include in the playlist.
finish_schedules (bool) – Whether to finalise the schedules (by calling
_finish_schedule()) before building the playlist. Should be setTrueunless some process has already finalised them before calling this function.
- Returns:
playlist consisting of the compressed
schedulesreadout metrics for the playlist
- Raises:
ValueError –
schedulescannot be converted into a valid Playlist.- Return type:
Inheritance
