/***************************************************************************//** * @brief dds_set_phase *******************************************************************************/ int32_t dds_set_phase(uint32_t chan, uint32_t phase) { uint32_t pcore_version; uint64_t val64; uint32_t reg; dac_read(DAC_REG_VERSION, &pcore_version); if(DAC_PCORE_VERSION_MAJOR(pcore_version) < 8) { dac_write(DAC_REG_CNTRL_1, 0); } dac_read(DAC_REG_CHAN_CNTRL_2_IIOCHAN(chan), ®); reg &= ~DAC_DDS_INIT(~0); val64 = (uint64_t) phase * 0x10000ULL + (360000 / 2); val64 = val64 / 360000; reg |= DAC_DDS_INIT(val64); dac_write(DAC_REG_CHAN_CNTRL_2_IIOCHAN(chan), reg); if(DAC_PCORE_VERSION_MAJOR(pcore_version) < 8) { dac_write(DAC_REG_CNTRL_1, DAC_ENABLE); } else { dac_write(DAC_REG_CNTRL_1, DAC_SYNC); } return 0; }
int32_t dac_data_src_sel(dac_core *core, int32_t chan, dac_data_src src) { uint32_t pcore_version; uint32_t reg; int32_t i; dac_read(core, DAC_REG_VERSION, &pcore_version); // single core control for all channels if (DAC_PCORE_VERSION_MAJOR(pcore_version) < 7) { dac_read(core, DAC_REG_DATA_CONTROL, ®); reg = (reg & ~DAC_DATA_SEL(~0)) | DAC_DATA_SEL(src); dac_write(core, DAC_REG_DATA_CONTROL, reg); return(0); } // per channel source select for (i = 0; i < (core->no_of_channels * 2); i++) { if ((chan < 0) || (chan == i)) dac_write(core, DAC_REG_DATA_SELECT(i), src); } dac_write(core, DAC_REG_SYNC_CONTROL, DAC_SYNC); return(0); }
int32_t dds_set_scale(dac_core *core, uint32_t chan, int32_t scale_micro_units) { uint32_t pcore_version; uint32_t scale_reg; dac_read(core, DAC_REG_VERSION, &pcore_version); // only ise projects support binary shift scaling, if you think you need // this supported in this driver, let us know. if (DAC_PCORE_VERSION_MAJOR(pcore_version) < 6) { printf("%s ERROR: Sorry, binary scale is NOT supported!\n", __func__); return(-1); } scale_reg = scale_micro_units; if (scale_micro_units < 0) scale_reg = scale_micro_units * -1; if (scale_reg >= 1999000) scale_reg = 1999000; scale_reg = (uint32_t)(((uint64_t)scale_reg * 0x4000) / 1000000); if (scale_micro_units < 0) scale_reg = scale_reg | 0x8000; dac_write(core, DAC_REG_SYNC_CONTROL, 0); dac_write(core, DAC_REG_DDS_SCALE(chan), DAC_DDS_SCALE(scale_reg)); dac_write(core, DAC_REG_SYNC_CONTROL, DAC_SYNC); return(0); }
/***************************************************************************//** * @brief dds_set_frequency *******************************************************************************/ int32_t dds_set_frequency(uint32_t chan, uint32_t freq) { uint32_t pcore_version; uint32_t val; uint64_t val64; uint32_t reg; uint64_t dac_clk; dac_read(DAC_REG_CLK_FREQ, &val); dac_clk = val; dac_read(DAC_REG_CLK_RATIO, &val); dac_clk *= val * 1525; dac_read(DAC_REG_VERSION, &pcore_version); if(DAC_PCORE_VERSION_MAJOR(pcore_version) < 8) { dac_write(DAC_REG_CNTRL_1, 0); } dac_read(DAC_REG_CHAN_CNTRL_2_IIOCHAN(chan), ®); reg &= ~DAC_DDS_INCR(~0); val64 = (uint64_t) freq * 0xFFFFULL; val64 = val64 / dac_clk; reg |= DAC_DDS_INCR(val64) | 1; dac_write(DAC_REG_CHAN_CNTRL_2_IIOCHAN(chan), reg); if(DAC_PCORE_VERSION_MAJOR(pcore_version) < 8) { dac_write(DAC_REG_CNTRL_1, DAC_ENABLE); } else { dac_write(DAC_REG_CNTRL_1, DAC_SYNC); } return 0; }
/***************************************************************************//** * @brief dds_set_scale *******************************************************************************/ int32_t dds_set_scale(uint32_t chan, int32_t scale_micro_units) { uint32_t pcore_version; uint32_t scale_reg; uint32_t sign_part; uint32_t int_part; uint32_t fract_part; dac_read(DAC_REG_VERSION, &pcore_version); if(DAC_PCORE_VERSION_MAJOR(pcore_version) > 6) { if(scale_micro_units >= 1000000) { sign_part = 0; int_part = 1; fract_part = 0; goto set_scale_reg; } if(scale_micro_units <= -1000000) { sign_part = 1; int_part = 1; fract_part = 0; goto set_scale_reg; } if(scale_micro_units < 0) { sign_part = 1; int_part = 0; scale_micro_units *= -1; } else { sign_part = 0; int_part = 0; } fract_part = (uint32_t)(((uint64_t)scale_micro_units * 0x4000) / 1000000); set_scale_reg: scale_reg = (sign_part << 15) | (int_part << 14) | fract_part; } else { if(scale_micro_units >= 1000000) { scale_reg = 0; scale_micro_units = 1000000; } if(scale_micro_units <= 0) { scale_reg = 0; scale_micro_units = 0; } fract_part = (uint32_t)(scale_micro_units); scale_reg = 500000 / fract_part; } if(DAC_PCORE_VERSION_MAJOR(pcore_version) < 8) { dac_write(DAC_REG_CNTRL_1, 0); } dac_write(DAC_REG_CHAN_CNTRL_1_IIOCHAN(chan), DAC_DDS_SCALE(scale_reg)); if(DAC_PCORE_VERSION_MAJOR(pcore_version) < 8) { dac_write(DAC_REG_CNTRL_1, DAC_ENABLE); } else { dac_write(DAC_REG_CNTRL_1, DAC_SYNC); } return 0; }