Pulse programs are text files that specify the pulse sequence for a single shot of an experiment. They conventionally use the file suffix .pp
. These text files are run sequentially, line by line, starting from the top.
Any line that begins with two semi-colons is skipped:
;; This is a comment
We can assign names to commonly used durations of time. These come in two varieties: pulse length times, which specify the length of a pulse, and delay times, which specify the length of doing nothing. A suffix u
denotes microsecond, a suffix n
denotes nano second. Times must be multiples of the base sampling rate, 2ns.
define pulse measurementDuration
"measurementDuration = 1u"
define delay settleTime
"settleTime = 5u"
For no particularly good reason, we mimic the Bruker convention and restrict ourselves to five types of variable objects, and allow ourselves a maximum of 99 of each of these types of variables. For most experiments, almost all of these 495 variables will remain unused.
- Delays
(d1-d99) [float]
: Durations of time during which the sytem is idle, in seconds - Pulses
(p1-p99) [float]
: The duration of some (later specified) pulse, in seconds - Phases
(ph1-ph99 [float]
: The static quadrature rotation of a given microwave pulse, between 0 and 1 - Loops
(l1-l99) [int]
: The number of iterations of the given loop - Shapes
(sp1-sp99)
[struct]: Pulse shapes, which have the following propertiespower (sp1-sp99) [float]
: Power of the pulse, in dB, relative to max power (-infinity to 0)mod (m1-m99) [cfloat]
: Amplitude is sin/cosine modulation frequency in Hz, phase is angle from cosineoffset (o1-o99) [float]
: Phase ramping offset of pulse in Hz (relative to center frequency)shape [*float]
: A(n,2)
matrix wheren
is the number of timesteps, the first column are the amplitudes (linear fractions ofpower
), and the second column are the phases (between 0 and 1). Many pulses contain a single time step of amplitude 1 and phase 0, especially digital pulses.
Any line containing only a unit of time specifies a wait period during which nothing is done. These durations can be hard coded:
;; Wait for 200ns
200ns
Or they can be delay macros discussed above:
;; Wait for 5us
settleTime
Or they can be delay variables discussed above:
;; Delay for whatever the current value of d5 is
d5
Devices which are either on or off (laser, switch, etc) use one of the following two syntaxes:
( delay duration:shapeVariable ):channel
( duration:shapeVariable ):channel
This command turns on the given channel
for a length duration
using the given shape variable shapeVariable
. Optionally, this pulse is immediately preceded by the given delay
. The shapeVariable
s shape
property is stretched to meet the specified length duration
.
For example,
;; Turn the laser on for 1us
( measurementDuration:sp1 ):laser
Pulses through the microwave circuit are almost identical, but also require an additional variable:
( delay duration:shapeVariable phase ):quadratureChannel
( duration:shapeVariable phase ):quadratureChannel
This command turns on the given quadratureChannel
for a length duration
using the given shape variable shapeVariable
. This shape variable is rotated by 2*pi*phase
in the x-y plane. Optionally, this pulse is immediately preceded by the given delay
. The shapeVariable
s shape
property is stretched to meet the specified length duration
.
For example,
;; turn the uwaves on for time p2 with shaped pulse sp4 at phase ph3, with a start delay of 10 us
( 10n p2:sp4 ph3 ):uwaveIQ
Any number of pulses appearing on the same line begin simultaneously. If we wish for their pulses start times to be staggered, we can add delays to some of them.
For example,
;; Do the previous two examples at the same time -- the uwave pulse starts 10us after the laser pulse
( measurementDuration:sp1 ):laser ( 10n p2:sp4 ph3 ):uwaveIQ
Phases are primarily used for something called phase cycling, which is common in refocussing sequences. In phase cycling we want the ability for the some pulse within a loop to see different phases. This motivates the at-first-unintuitive syntax explained below.
The exception to the opening rule above "These text files are run sequentially, line by line, starting from the top." is that phases are initialized at the bottom of the file, don't ask me why. This is done with the syntax
phaseVariable (circleDivisions) step1 step2 step3 ... stepN
where phaseVariable
is one of ph1-ph99
, circleDivisions
is a positive integer specifying how many discrete divisions to break the unit circle up into, and the steps specify which multiples of the circle division to use in phase incrementation. All phases begin at the first step, corresponding to an angle 2*pi*step1/circleDivisions
in radians.
To keep ph10
fixed at 0 for the entire experiment, we would use
ph10 = (1) 0
at the bottom of the file, and nothing more. The line
ipp10
for example, increases the phase step of ph10
by one. They loop around, so that step1
follows stepN
. For example, the code
( 10n p2:sp4 ph3 ):uwaveIQ
ipp3
( 10n p2:sp4 ph3 ):uwaveIQ
ipp3
( 10n p2:sp4 ph3 ):uwaveIQ
ipp3
( 10n p2:sp4 ph3 ):uwaveIQ
ph3 (4) 0 1 3
runs the pulse back to back four times, with phases 0, pi/2, pi, 0.
Loops are straight forward and use the following syntax:
myLoop,
;; do anything inside of here. not sure if there is a loop recursion depth limit, have never tried.
lo to myLoop times l3
The name myLoop can be anything that isn't already defined. The number of loops is determined by the loop variable l3
in this example.