forked from M-Labs/artiq
shuttler: change 0th order accumulator width
It now truncates the LSBs instead of the MSBs.
This commit is contained in:
parent
bafb85a274
commit
a772dee1cc
@ -12,7 +12,7 @@ def shuttler_volt_to_mu(volt):
|
||||
"""Return the equivalent DAC code. Valid input range is from -10 to
|
||||
10 - LSB.
|
||||
"""
|
||||
return round((1 << 14) * (volt / 20.0)) & 0x3fff
|
||||
return round((1 << 16) * (volt / 20.0)) & 0xffff
|
||||
|
||||
|
||||
class Config:
|
||||
@ -25,7 +25,7 @@ class Config:
|
||||
output data with pre-DAC gain, then adds the offset.
|
||||
|
||||
.. note::
|
||||
The DAC code is capped at 0x1fff and 0x2000.
|
||||
The DAC code is capped at 0x7fff and 0x8000.
|
||||
|
||||
:param channel: RTIO channel number of this interface.
|
||||
:param core_device: Core device name.
|
||||
@ -152,8 +152,8 @@ class Volt:
|
||||
|
||||
a_3 &= p_3T^3
|
||||
|
||||
:math:`a_0`, :math:`a_1`, :math:`a_2` and :math:`a_3` are 14, 30, 46
|
||||
and 46 bits in width respectively. See :meth:`shuttler_volt_to_mu` for
|
||||
:math:`a_0`, :math:`a_1`, :math:`a_2` and :math:`a_3` are 16, 32, 48
|
||||
and 48 bits in width respectively. See :meth:`shuttler_volt_to_mu` for
|
||||
machine unit conversion.
|
||||
|
||||
Note: The waveform is not updated to the Shuttler Core until
|
||||
@ -238,8 +238,8 @@ class Dds:
|
||||
|
||||
c_2 &= r_2T^2
|
||||
|
||||
:math:`b_0`, :math:`b_1`, :math:`b_2` and :math:`b_3` are 14, 30, 46
|
||||
and 46 bits in width respectively. See :meth:`shuttler_volt_to_mu` for
|
||||
:math:`b_0`, :math:`b_1`, :math:`b_2` and :math:`b_3` are 16, 32, 48
|
||||
and 48 bits in width respectively. See :meth:`shuttler_volt_to_mu` for
|
||||
machine unit conversion. :math:`c_0`, :math:`c_1` and :math:`c_2` are
|
||||
16, 32 and 32 bits in width respectively.
|
||||
|
||||
|
@ -26,15 +26,15 @@ def shuttler_volt_amp_mu(volt):
|
||||
|
||||
@portable
|
||||
def shuttler_volt_damp_mu(volt_per_us):
|
||||
return round(float(2) ** 30 * (volt_per_us / 20) / DAC_Fs_MHZ)
|
||||
return round(float(2) ** 32 * (volt_per_us / 20) / DAC_Fs_MHZ)
|
||||
|
||||
@portable
|
||||
def shuttler_volt_ddamp_mu(volt_per_us_square):
|
||||
return round(float(2) ** 46 * (volt_per_us_square / 20) * 2 / (DAC_Fs_MHZ ** 2))
|
||||
return round(float(2) ** 48 * (volt_per_us_square / 20) * 2 / (DAC_Fs_MHZ ** 2))
|
||||
|
||||
@portable
|
||||
def shuttler_volt_dddamp_mu(volt_per_us_cube):
|
||||
return round(float(2) ** 46 * (volt_per_us_cube / 20) * 6 / (DAC_Fs_MHZ ** 3))
|
||||
return round(float(2) ** 48 * (volt_per_us_cube / 20) * 6 / (DAC_Fs_MHZ ** 3))
|
||||
|
||||
@portable
|
||||
def shuttler_dds_amp_mu(volt):
|
||||
|
@ -124,16 +124,18 @@ class Dac(Module):
|
||||
]
|
||||
|
||||
# Infer signed multiplication
|
||||
data_raw = Signal((14, True))
|
||||
data_buf = Signal(16)
|
||||
data_raw = Signal((16, True))
|
||||
# Buffer data should have 2 more bits than the desired output width
|
||||
# It is to perform overflow/underflow detection
|
||||
data_buf = Signal(18)
|
||||
self.sync.rio += [
|
||||
data_raw.eq(reduce(add, [sub.data for sub in subs])),
|
||||
# Extra buffer for timing for the DSP
|
||||
data_buf.eq(((data_raw * Cat(self.gain, ~self.gain[-1])) + (self.offset << 16))[16:]),
|
||||
If(overflow,
|
||||
self.data.eq(0x1fff),
|
||||
self.data.eq(0x7fff),
|
||||
).Elif(underflow,
|
||||
self.data.eq(0x2000),
|
||||
self.data.eq(0x8000),
|
||||
).Else(
|
||||
self.data.eq(data_buf),
|
||||
),
|
||||
@ -350,7 +352,7 @@ class Shuttler(Module, AutoCSR):
|
||||
dac.clear.eq(self.cfg.clr[idx]),
|
||||
dac.gain.eq(self.cfg.gain[idx]),
|
||||
dac.offset.eq(self.cfg.offset[idx]),
|
||||
self.dac_interface.data[idx // 2][idx % 2].eq(dac.data)
|
||||
self.dac_interface.data[idx // 2][idx % 2].eq(dac.data[2:])
|
||||
]
|
||||
|
||||
for i in dac.i:
|
||||
|
Loading…
Reference in New Issue
Block a user