AWG frequency error/offset

Moku model: Moku Pro
Operating system: Windows
**Software version: 3.1.2, firmware 587

Bug/support request description:

Apologies, this is maybe a niche bug.

It seems that there is a small frequency offset/error between different channels in the arbitrary waveform generator. This only occurs when the frequencies are an order of magnitudes apart or more. It is usually small (7 milliHertz - 2 Hertz) but over the course of a 1-10 second experiment, it can cause signals to drift entirely out of phase. This is just a guess, but perhaps clock divisor/ multiplier is different in each channel, and their ratios are either non-rational, or the minimum resolutions do not coincide at the same frequency points… :man_shrugging:

I have found that I can often correct for this by adding small frequency increments to either waveform to compensate for the drift. But I have to do it dynamically depending on the difference between the two generated frequencies, as well as the number of points used in the waveform…

I have included some Python code to replicate the issue.

If I am missing something? is there is a simpler way to fix this? Any help would be greatly appreciated…

** Code/Steps to replicate **

from moku.instruments import Oscilloscope, MultiInstrument, ArbitraryWaveformGenerator
from time import sleep

show_error = True # Change to false to show the correction

moku_ip= "XXXXXXXXXXXXX"
mim = MultiInstrument(moku_ip, force_connect=True, platform_id=4)
arb = mim.set_instrument(1, ArbitraryWaveformGenerator)
osc = mim.set_instrument(2, Oscilloscope) 
mim.set_connections([
    {"source": "Slot1OutA", "destination": "Slot2InA"},
    {"source": "Slot1OutB", "destination": "Slot2InB"}])

osc.set_trigger(type="Edge", edge="Rising", source="ChannelB", level=300e-3, nth_event=4


arb.enable_output(1, enable=True)
arb.enable_output(2, enable=True)
 
if show_error:
    # Frequency ratio is exactly 15, but the waveforms drift out of phase
    arb.generate_waveform(channel=1, sample_rate='Auto', lut_data=list([1,1,1,1,0,1,0,1,1,0,0,1,0,0,0]), frequency=150e3, amplitude=1)
    arb.generate_waveform(channel=2,  sample_rate='Auto', lut_data=list([1,1,1,1,0,1,0,1,1,0,0,1,0,0,0]), frequency=10e3, amplitude=1)
else:
    #  Frequency ratio is 14.99997... and now the waveforms are syncronised
    #  The larger the gap in frequency, the larger the correction required.
    arb.generate_waveform(channel=1, sample_rate='Auto', lut_data=list([1,1,1,1,0,1,0,1,1,0,0,1,0,0,0]), frequency=149.999995e3, amplitude=1)
    arb.generate_waveform(channel=2,  sample_rate='Auto', lut_data=list([1,1,1,1,0,1,0,1,1,0,0,1,0,0,0]), frequency=10e3, amplitude=1)


osc.set_trigger(type="Edge", edge="Rising", source="ChannelB", level=300e-3, nth_event=4)
osc.set_timebase(-10e-6, 10e-6)
d1 = osc.get_data()
sleep(2)
d2 = osc.get_data()

plt.plot(np.array(d1["ch2"]) + 0.01) # Small offset just to show that the position of the trigger waveform is the same
plt.plot(np.array(d1["ch1"]) + 0.55)

plt.plot(d2["ch2"])
plt.plot(np.array(d2["ch1"]) + 0.55)

plt.show()

mim.relinquish_ownership()

Hi @nnosk55 Claude,

I am going to reproduce it on my end and let you know the progress. My guess at this moment is that the AWG’s frequency resolution could be limited by the resolution and number of samples of the waveforms. I will let you know as soon as I can.

Thank you,
Hank

1 Like

Hi @nnosk55 Claude,

In my tests, I can observe the same issue as you were experiencing.

The issue stems from the clock rate of the FPGA. The clock rate on Moku:Pro is 312.5 MHz. If you pick the frequencies as (312.5 MHz / integer), then you will find that there are no frequency drifts between two channels.

For example, you might pick two frequencies as 312.5 MHz / 2 = 156.25 MHz, and 312.5 MHz / 30 = 10.41666666667 MHz. Then, two channels will be synchronized as expected.

The issue might be that your time series only has 15 points which means the phase counter’s phase step resolution is very limited (only 15 phase step available). If you can have a 16,384-point waveform, the two channels should be able to synchronize with each other even when the frequencies are 150 MHz and 10 MHz (some points will be missing though).

Thank you very much for your understanding and patience! I will talk to our dev team to see what we can do .

Best regards,
Hank

Hi Hank,

I’d tested of the FPGA Clock/integer yesterday, but that doesn’t seem to work as a fix on my end… For example, 312.5e6 / 200 = 156250.0 Hz and 312.5e6 / 30000 = 10416.666666666666 still creates the issue.

Adding more points to the waveform definitely helps. I interpolated both waveforms, and it reduces the issue but it still happens if I push the frequency further apart.

I’ve realised that the way Im going about this experiment is maybe a bit unrealistic. This morning I shifted to a clocked/triggered approach using an unused channel on an ordinary waveform generator, and it seems to resolve the experimental issue I’ve been having.

Thanks for your time and help!

Cheers,
Claude

Hi Claude @nnosk55 ,

Thank you very much for your feedback!

I understand you have figured out this issue already with a workaround. And that’s a brilliant way to generate synchronized waveforms! I just wanted to leave a note to this thread.

Our dev team has got back to me that (on fw587) the two channels should be able to synchronize with each other if we can make the actual sample rate divide evenly into the sample rate1.25 GSa/s. For example, 156250 * 15 = 2,343,750 pts/s, and 1.25G / 2,343,750 = 533.33333. This setting would cause a little bit phase drift between two channels.

We are actively working on that to eliminate the phase drift. Thank you very much for your patience and understanding!

Best regards,
Hank

1 Like