Post Go back to editing

How to change the sampling clock of the AD9081 +zcu102 reference design?

Category: Software
Product Number: AD9081

Hi,

My setup is the ZCU102 + AD9081-FMCA-EBZ.  I'm testing the current reference design both versions available with device trees: 

zynqmp-zcu102-rev10-ad9081.dts

zynqmp-zcu102-rev10-ad9081-m8-l4.dts

I'm testing using the IIO Oscilloscope.  The reference design uses 12 GHz for the sampling rate.  This seems to be hardcoded into the design, unlike whatever design is loaded when using the ADS9 with ACE (correct me if I'm wrong on this please).

How do I change this sampling clock from 12 GHz to say 8 GHz?

My first thought was that I need to simply modify the dts file and make for a new system.dtb to be loaded because I noticed this parameter, as well as other parameters, are all listed in the device tree.  However, further investigation leads me to believe that this is either wrong or an insufficient step.  

I've found another question here that I thought was similar (How to change the sampling rate of AD9081 - Q&A - FPGA Reference Designs - EngineerZone (analog.com)), however, the response there was to go modify the system_project.tcl and to do "make" again.  However, I don't fully understand this because looking at system_project.tcl, there is no parameter for reference clock, and also there is no mention there of what to do with the device tree.

Can you please clarify for me what are the steps required to make the change that I need (or another similar change in the future) and direct me on the right path?

Thanks,

  • Hi Dan,

    yes, sometimes the value listed on the device tree just describe the instantiated IP Core for the Linux driver and the driver has no capability to change it on the fly (it is not software programmable). A quick way to check this is checking if the IP Core has the parameter accessible in the register map as read&write, if so, it's software programmable.

    The AD9081 project uses the JESD204 as the protocol for the data packets, and you can configure the lane rates in the JESD204 parameters (datapath configuration) (util_adxcvr parameter doc). The adxcvr cpll/qpll reference clock comes from the on board HMC clock generator and the output clock is "serial line rate"/40.

    The JESD204 Framework doc is available here.

    Therefore, fundamentally sampling clock/sample rate is based on the datapath configuration, JESD transport layer, and external clocking (HMC).

    The configuration you need need to be based on the use-case tables on the AD9081 user-guides for transmit and receive.

    Regards,

    Jorge

  • Hi,

    Thank you for your response. I think I'm getting closer to the answers after your response but I still have more unanswered questions now after I've read more into all of this,  and so I'm not sure how to proceed.

    I understand that there is a relationship between the JES204 parameters and DAC Rate.  I see the Clock relationships in the Reference Manual on p-144.  It seems that those parameters in system_project.tcl determine the Data Rate, but then the DAC Rate is proportional to the Data Rate and Total Interpolation.  According to what I see, the total interpolation is something that is configured by the device tree (and should be something that can be controlled on the fly later).

    1.  So don't I just need to change the interpolation factor in the device tree in order to change the DAC rate?  Assuming of course I want to keep the same JESD204 parameters specified in system_project.tcl.  Because if yes, I can't find any document here that explains the process by which to do this.

    2. It sounds like even if I do end up changing the JESD204 parameters, I still have to change the device tree, thus I am missing something here from your answer.  So this also relates to my question in #1.

    3.  I get that the external clock is coming from the HMC, but then does that mean that the linux driver automatically programs the correct HMC clock for the DAC rate based on the parameters and the interpolation factor?  Or is it still relying on the device tree?  I'm confused from your answer about this.

    Thanks,

  • Hi Dan,

    3. No, the linux driver does not configure the HMC clock based on the DAC Rate or the AD9081 interpolation factor.

    The AD9081 interpolation is software programmable and so is the HMC clk output, for the HMC you can see hmc7044_parse_dts to check which devicetree entries are used to configure/write the HMC.

    1,2. Yes, even if the entry is not software programmable, you must update the devicetree, so the driver knows the current synthesized configuration and to function accordingly. This is a general rule, some IPs would expose the instantiated configuration in the register map, avoiding having to describe in the dts, instead, it would fetch by memory-mapped access during the driver probe.

    Changing the interpolation factor in the device tree would affect register REG_INTRP_MODE_ADDR  described in the page 169 of the UG-1578 and the computed bit rate.

    Returning to your original question, the sampling clock is either an external reference (HMC) or the AD9081 internal PLL+VCO. Configuring the HMC to a different value changes the sampling clock.

  • Hi, thanks for the response.  Please bear with me here.  Each time I understand more, but still there are basic things here that I am not understanding. 

    1. If I understand you correctly, you've confirmed that the device tree is needed to be modified in order to change the interpolation factor or any other parameter.  so How do I do that?  I mean I can take the .dts file and edit it, but how do I convert it to a system.dtf file, which correct me if I'm wrong is required for the boot?

    2.  I don't understand what I need to do with the hmc7044_parse_dts   you linked. I'm assuming that's the hmc7044 driver (correct me if I'm wrong).  How do I change the reference design so that when everything is booted, the HMC is outputting 8 GHz for example, and not 12 GHz for the DAC rate.

    I get that both the interpolation factor can be modified on the fly.  I don't get how to do that?  Is there some command that I can type in the linux prompt that can change the hmc7044?  (maybe I missed it through all my readings).  When I used the ADS9 with ACE those parameters were configurable from ACE.  Here I'm using the IIO Scope.  DAC rate and other parameters are not configurable.

  • 1. See https://wiki.analog.com/resources/tools-software/linux-build/generic/zynqmp , pretty much you clone ADI Linux (with depth 1, so it's faster/smaller), edit the device tree and do `make zynqmp-zcu102-rev10-ad9081-m8-l4.dtb`, the resulting dtb you copy to the boot partition.

    2. Yes, that's the hmc7044, in the linked method, it fetches the parameter of the devicetree and do all kind of configurations. I will follow with the answer for "how to 12GHz -> 8GHz" shortly.

  • The ad9081 have a clk configuration method which is called during setup, with the phy->(dac/adc_frequency_hz) filled from the devicetree entry (changing this entry for the DAC path from 12 to 8GHz *may* be enough).

    Can you please watch this 4 video part series: https://www.youtube.com/watch?v=EwpUaH_0XaQ https://www.youtube.com/watch?v=Jy1MwJdaaeo https://www.youtube.com/watch?v=awmK0cLHyF8 https://www.youtube.com/watch?v=lvdrcaBpI2I , especially the last one. It uses the API to configure common uses cases.

    Then, proceed with the API, and further questions open in the  Mixed-Signal Front Ends (MxFE)
     ? (because they are software related)

    You need to ensure the new values are in range.

    ---

    About the HMC7044, it's configured using the Channel Output 0 control registers, in special, [0xC9 + 0x9*Ch, 0xCA + 0x9*Ch] Channel Divider, where Ch is the channel index, to set the clock output division, a 12-bit value, but you may not need to change it in your use case.

    Still, for the Linux driver, this is abstracted by the method hmc7044_clk_set_rate, which is exposed as a clock ops and further abstracted through IIO.

  • Hi, Thank you very much for elaborating more now on the process.  Per your instruction in #1, I'm trying now to convert the .dts to the .dtb, and running into an error that I could not find a resolution to either here on Zone or elsewhere.

    To summarize what I've done so far; I've successfully cloned ADI Linux.  I'm assuming I only need to convert the .dts to .dtb, and not build a new Linux image so I went straight to that part (per the wiki link you provided and your own make example in #1).  But I get the following error - see image 1 and image 2 (difference between the images is that I run it twice with different paths for the .dtb - first run per your path, and second per the path in the wiki link).   

    Image 1:

    Image 2:

  • Hi, you need to

    * Set your environment to cross-compile to ARM, considering "precision" is x86.

    * Build the defconfig (generates the .config).

    * Build the dtb 

    export ARCH=arm64
    export CROSS_COMPILE=" aarch64-linux-gnu-"

    make adi_zynqmp_defconfig
    make xilinx/zynqmp-zcu102-rev10-ad9081.dtb

    Then, copy the generated blob "arch/arm64/boot/dts/xilinx/zynqmp-zcu102-rev10-ad9081.dtb" to replace the dtb in the boot partition (always do a backup of the file first). If **-m8-l4.dts, just update the last make command.

    The step I skipped from the guide is "Build the kernel", since it is independent from the devicetree, but both uses the same defconfig.

  • Hi,

    Thanks again for the response.  When I try to do "make adi_zynqmp_defconfig", I am getting an error that it can't find the compiler "aarch64-linux-gnu-gcc" (see image 1).  I can't figure out why this is happening.  I checked my .bashrc (see figure 2) and I seem to be exporting all the paths correctly including the one that has the aarch64-linux-gnu-gcc:

    export PATH=$PATH:/tools/Xilinx/vitis/2021.2/gnu/aarch64/lin/aarch64-linux/bin

    Image 1:


    Image 2:

  • I load the AMD Xilinx environment using the provided shell script and then I check with the `which` command:

    # Other installed toolchain
    $ which aarch64-linux-gnu-gcc
    /usr/bin/aarch64-linux-gnu-gcc

    # Load AMD Xilinx enviroment

    $ source /data/opt/Xilinx/Vivado/2023.2/settings64.sh

    # Now the AMD Xilinx-provided toolchain
    $ which aarch64-linux-gnu-gcc
    /data/opt/Xilinx/Vitis/2023.2/gnu/aarch64/lin/aarch64-linux/bin/aarch64-linux-gnu-gcc

    You can alias that `source /data/opt/Xilinx/Vivado/2023.2/settings64.sh` as a `xilinx` method in your bashrc. It is not recommended to always load the vendor environment, since it will "conflict" with other vendors-provided packages (e.g. loading both Altera and AMD Xilinx environments).