.. _ph_acc: ph_acc ====== Description ''''''''''' | | Phase accumulator, to act as basis for DDS (direct digital synthesizer). | Tuned to allow 32-bit control, divided 20-bit high and 12-bit low, | which gets merged to 32-bit binary when modulo is zero. | But also supports non-binary frequencies: see the modulo input port. | | Note that phase_step_h and phase_step_l combined fit in a 32-bit word. | This is intentional, to allow atomic updates of the two controls | in 32-bit systems. Indeed, when modulo==0, those 32 bits can be considered | a single phase step increment | | The phase generation algorithm | 0. The phase increments for dds are generated using a technique described | in these 2 places: | Section: PROGRAMMABLE MODULUS MODE in: | https://www.analog.com/media/en/technical-documentation/data-sheets/ad9915.pdf | (AND) https://en.wikipedia.org/wiki/Bresenham%27s_line_algorithm | Basically, increment the phase step at a coarse resolution, accumulate the | error on the side, and when that error accumulates to the lowest bit of | the coarse counter, add an extra 1 to the following phase step. | 1. phase_step_h is the coarse (20 bit) integer truncated phase increment for | the cordic. There is a 1-bit increment of phase that comes from | accumulating residue phase. | 2. This residue phase is accumulating in steps of phase_step_l, in a 12-bit | counter. | 3. However, there will be an extra residue even for this 12-bit counter, | which is the modulus, and this added as an offset when the counter crosses 0 | | 12-bit modulo supports largest known periodicity in a suggested LLRF system, | 1427 for JLab. For more normal periodicities, use a multiple to get finer | granularity. | Note that the downloaded modulo control is the 2's complement of the | mathematical modulus. | e.g., SSRF IF/F_s ratio 8/11, use | modulo = 4096 - 372*11 = 4 | phase_step_h = 2^20*8/11 = 762600 | phase_step_l = (2^20*8%11)*372 = 2976 | e.g., Argonne RIA test IF/F_s ratio 9/13, use | modulo = 4096 - 315*13 = 1 | phase_step_h = 2^20*9/13 = 725937 | phase_step_l = (2^20*9%13)*315 = 945 | Pinout '''''' .. _fig:ph_acc_block: .. figure:: ph_acc_block.png :alt: Schematic symbol Ports ''''' .. list-table:: ph_acc_port_table :header-rows: 1 * - Signal - Direction - Description * - clk - Input - Rising edge clock input; all logic is synchronous in this domain * - reset - Input - Active high, synchronous with clk * - en - Input - Enable * - phase_acc[18:0] - Output - Output phase word * - phase_step_h[19:0] - Input - High order (coarse, binary) phase step * - phase_step_l[11:0] - Input - Low order (fine, possibly non-binary) phase step * - modulo[11:0] - Input - Encoding of non-binary modulus; 0 means binary Implementation and use '''''''''''''''''''''' The `portable`_ `Verilog`_ implementation can be found in :ref:`ph_acc_source` .. _`portable`: https://en.wikipedia.org/wiki/Software_portability .. _`Verilog`: https://en.wikipedia.org/wiki/Verilog