Skip to content

Allow generic subschedule in conditional playback

Robert Sokolewicz requested to merge cond_playback2 into main

Explanation of changes

Example 1

body = Schedule()
body.add(Square_Pulse(duration=50e-9, port=A, clock=B, ...))
body.add(SSBIntegrationComplex(duration=100e-9, port=A, clock=B))

Will compile to q1asm of the form:

set_awg_gain 10000
play 1,0,4
wait 46
acquire 0,0,100

This has a total duration of 150 ns and has 3 real-time instructions.

passing the body to a conditional:

schedule.add(ConditionalOperation(body, "q0"))

will compile it to the following q1asm:

set_cond 1,1,0,4 # set_enable=1, mask=0, operator=OR, else_duration=4
set_awg_gain 10000 
play 1,0,4       # real-time instruction
wait 46          # real-time instruction
acquire 0,0,100  # real-time instruction

set_cond 1,1,1,4 # set_enable=1, mask=0, operator=NOR, else_duration=4
wait 142         # 150 - 3*4 + 4

set_cond 0,0,0,0 # set_enable=0

If the condition is met (unmet), the first set_cond block will have a duration of 150 ns (12 ns), while the second set_cond block will have a duration of 4 ns (142 ns). In both branches the total duration is 154 ns. (adding an additional 4 ns the second set_cond wait time to make both branches the same duration)

Example 2

body = Schedule()
body.add(SquarePulse(duration=50e-9, port=A, clock=B, ...))
body.add(DragPulse(duration=40e-9, port=A, clock=B, ...))

Will compile to q1asm of the form:

set_awg_gain 10000
play 1,0,4      # real-time instruction
wait 46         # real-time instruction
set_awg_gain 10000
play 1,0,4      # real-time instruction
wait 36         # real-time instruction

This has a total duration of 90 ns and has 4 real-time instructions.

passing the body to a conditional:

schedule.add(ConditionalOperation(body, "q0"))

will compile it to the following q1asm:

set_cond 1,1,0,4 # set_enable=1, mask=0, operator=OR, else_duration=4
set_awg_gain 10000
play 1,0,4      # real-time instruction
wait 46         # real-time instruction
set_awg_gain 10000
play 1,0,4      # real-time instruction
wait 36         # real-time instruction

set_cond 1,1,1,4 # set_enable=1, mask=0, operator=NOR, else_duration=4
wait 78 # 90 - 4*4 + 4

set_cond 0,0,0,0 # set_enable=0

If the condition is met (unmet), the first set_cond block will have a duration of 90 ns (16 ns), while the second set_cond block will have a duration of 4 ns (78 ns). In both branches the total duration is 94 ns. (adding an additional 4 ns the second set_cond wait time to make both branches the same duration)


This implementation will ensure that:

  • any subschedule that is passed to conditional playback will run without raising errors.
  • at the expense of an additional 4 ns.
  • with a limitation that the duration of the body needs to be less than 65528 ns + 4 ns *number_of_real_time_instructions

explanation

The else_duration is the wait time per real time instruction in the conditional block. If a trigger happened, the first block runs normally for 50 ns, the second block runs for 4 ns. If there is no trigger, the first block runs for 3*4 = 12 ns, second block for 42 ns. So the duration in both cases is 42 ns. Note that set_cond itself has zero duration.


todos:

  • fix circular import error
  • add tests
  • raise error when duration > 65528 ns + 4 ns *number_of_real_time_instructions
  • update conditional playback documentation

Merge checklist

See also merge request guidelines

  • Merge request has been reviewed (in-depth by a knowledgeable contributor), and is approved by a project maintainer.
  • New code is covered by unit tests (or N/A).
  • New code is documented and docstrings use numpydoc format (or N/A).
  • New functionality: considered making private instead of extending public API (or N/A).
  • Public API changed: added @deprecated and entry in deprecated code suggestions (or N/A).
  • Newly added/adjusted documentation and docstrings render properly (or N/A).
  • Pipeline fix or dependency update: post in #software-for-developers channel to merge main back in or update local packages (or N/A).
  • Tested on hardware (or N/A).
  • CHANGELOG.md for breaking changes and AUTHORS.md have been updated (or N/A).
  • Update Hardware backends documentation if backend interface change or N/A
  • Check whether performance is significantly affected by looking at the Performance metrics results.
  • Windows tests in CI pipeline pass (manually triggered by maintainers before merging).
    • Maintainers do not hit Auto-merge, we need to actively check as manual tests do not block pipeline

For reference, the issues workflow is described in the contribution guidelines.

Summary by CodeRabbit

  • New Features

    • Introduced ConditionalOperation for executing operations based on conditional logic.
    • Enhanced conditional method in QASMProgram for improved instruction timing.
  • Bug Fixes

    • Improved error handling in various tests related to conditional operations and pulse compensation.
  • Tests

    • Added comprehensive unit tests for conditional operations and control flow.
    • Expanded existing tests to cover edge cases and improve validation accuracy.
  • Documentation

    • Enhanced docstrings and comments for better clarity on functionality and usage.
Edited by CodeRabbit

Merge request reports

Loading