Example experimentΒΆ
Experiment
from artiq.experiment import *
from atomiq import AtomiqExperiment
from blocks_example import MOT
class ATQExperiment(AtomiqExperiment):
"""
Atomiq Example Experiment
This is an example experiment to demonstrate the basic ideas of atomiq.
"""
# define components needed in the step function. They will be built and attached to
# the experiment object automatically. If components depend on others, these are also
# built automatically but not attached to the experiment object.
components = ["lock_cooler", "aom_cooler", "aom_repumper", "ttl_test", "ttl_cool", "pubsub", "input_cooler_pd"]
blocks = [MOT]
arguments = {
"dummy_voltage": {"default": 1.2 ,"unit":"V", "scale": 1, "ndecimals": 3},
}
@kernel
def step(self, point):
# emitting debug infomation from kernel functions is a easy as this:
self.log.info("Testmessage from the core")
# Add some slack
delay(3*ms)
# the components we listed above are initialized and readily available
self.aom_cooler.detune(3e6)
self.aom_cooler.set_amplitude(0.3)
# if we need to do something more specific we can also access the nested objects
self.aom_cooler.rfsource.set(frequency=80e6, amplitude=0.3)
# call a block we defined above. Since we essentially call the step() function
# of that class, we need to pass the point variable. That way the parameters
# can be changed through the experiment's arguments.
self.MOT.step(point)
# submit the values of the arguments for the current point to the data sink
self.pubsub.submit_env(point)
# measure photodiode voltage
cooler_pd_voltage = self.input_cooler_pd.measure(samples = 5)
#publish data
self.messagebus.submit_data(["cooler_pd_voltage"], [cooler_pd_voltage])
# submit custom values to the data sink. This could be values measured with a sampler...
self.pubsub.submit_data(["my_parameter", "observable_1"], [0.3, -1.43])
for _ in range(10):
with parallel:
self.aom_cooler.pulse(3*ms)
self.ttl_test.pulse(3*ms)
delay(4*ms)
Components
components = {}
# Add core stuff
components.update({
"log": {
"classname": "atomiq.components.basics.log.KernelLogger"
}
})
# Add locks
components.update({
"lock_cooler": {
"classname": "atomiq.components.lock.ULELock",
"arguments": {
"lock_offset": 34e6
}
}
})
# Add calibrations
components.update({
"cal_pd_cooler": {
"classname": "atomiq.components.basics.calibration.LinearCalibration",
"arguments": {
"input_unit": "mV",
"output_unit": "mW",
"a": 0.342,
"b": 0.002
}
},
"cal_aom_cooler": {
"classname": "atomiq.components.basics.calibration.InvSigmoidCalibration",
"arguments": {
"input_unit": "amp",
"output_unit": "amp",
"A": 5.,
"k": 1.,
"x_offset": 10.,
"y_offset": 0.3
}
}
})
# Add low level Sinara hardware
components.update({
"kasli0": {
"classname": "atomiq.components.sinara.Kasli",
"arguments": {}
},
"sampler0": {
"classname": "atomiq.components.sinara.Sampler",
"arguments": {
"sampler_device": "@sampler0",
"sampler_default_gain": [1, 0, 0, 0, 0, 0, 0, 0]
}
},
"urukul0": {
"classname": "atomiq.components.sinara.Urukul",
"arguments": {
"cpld": "@urukul0_cpld"
}
}
})
# Add low Sinara DIOs
components.update({
"ttl_test": {
"classname": "atomiq.components.sinara.DioOutput",
"arguments": {
"kasli": "&kasli0",
"ttl": "@led0"
}
},
"ttl_cool": {
"classname": "atomiq.components.sinara.DioOutput",
"arguments": {
"kasli": "&kasli0",
"ttl": "@ttl4"
}
},
"ttl_repump": {
"classname": "atomiq.components.sinara.DioOutput",
"arguments": {
"kasli": "&kasli0",
"ttl": "@ttl6"
}
}
})
# Add DDS channels
components.update({
"dds_cooler": {
"classname": "atomiq.components.sinara.UrukulChannel",
"arguments": {
"urukul": "&urukul0",
"device": "@urukul0_ch0",
"ttl": "@ttl_urukul0_sw0"
}
},
"dds_repumper": {
"classname": "atomiq.components.sinara.UrukulChannel",
"arguments": {
"urukul": "&urukul0",
"device": "@urukul0_ch1",
"ttl": "@ttl_urukul0_sw1"
}
}
})
# Add AOMs
components.update({
"aom_cooler": {
"classname": "atomiq.components.optoelectronics.lightmodulator.AOM",
"arguments": {
"rfsource": "&dds_cooler",
"switch": "&dds_cooler",
"center_freq": 80e6,
"switching_delay": 30e-9
}
},
"aom_repumper": {
"classname": "atomiq.components.optoelectronics.lightmodulator.AOM",
"arguments": {
"rfsource": "&dds_repumper",
"switch": "&ttl_repump",
"center_freq": 110e6,
"switching_delay": 45e-9
}
}
})
# Add analog inputs
components.update({
"input_cooler_pd": {
"classname": "atomiq.components.sinara.SamplerChannel",
"arguments": {
"adc_device": "&sampler0",
"channel": 0,
"default_gain": 0
}
},
"input_dummy": {
"classname": "atomiq.components.electronics.adc.ADCChannel",
"arguments": {
"adc_device": "&adc_dummy0",
"channel": 0,
}
},
})
# Add photodiodes
components.update({
"pd_cooler": {
"classname": "atomiq.components.optoelectronics.photodiode.CalibratedPhotodiode",
"arguments": {
"adc_channel": "&input_cooler_pd",
"calibration": "&cal_pd_cooler"
}
}
})
# Add lasers
components.update({
"laser_cooler": {
"classname": "atomiq.components.sinara.BisectionAOMLaser",
"arguments": {
"lock": "&lock_cooler",
"monitor_pd": "&pd_cooler",
"aom": "&aom_cooler"
}
}
})
# Add Datasinks
components.update({
"pubsub": {
"classname": "atomiq.components.basics.datasink.RPCPublisherSink",
"arguments": {
"rpc_publisher": "@messagebuswriter",
"topic_prefix": "artiq.",
"default_topic": "newData"
}
}
})