SPI Maximum Frequency - Kernel Build


I am trying to run the Jetson Nano SPI Hardware closer to the stated maximum. I have been able to reach 25MHz (ground truth verified by an oscilloscope) but have not been able to exceed that. Based on this (SPI maximum frequency - #6 by AliHaeri) post I have tried recompiling the kernel specifying the max_speed_hz to be 65000000 (65 MHz), however after compilation and flashing the CS still does not exceed 25MHz.

Based on this post (How to set spi max frequency more than 24MHz?) I have tried adding debug output and have gotten this from running:

./spidev_test -D /dev/spidev1.0 -s 50000000

[ 2241.376295] spidev spi1.0: setup 8 bpw, ~cpol, ~cpha, 33000000Hz
[ 2241.376404] spidev spi1.0: setup 8 bpw, ~cpol, ~cpha, 33000000Hz
[ 2241.376456] spidev spi1.0: setup 8 bpw, ~cpol, ~cpha, 50000000Hz
[ 2241.377461] spi-tegra114 7000d600.spi: Setting clk_src pll_p
[ 2241.377706] spi-tegra114 7000d600.spi: prod settings failed with error -19
[ 2241.377725] spi-tegra114 7000d600.spi: The def 0x47d08000 and written 0x43c01827

The dtb output of the current flash I have is:

spi@70410000 {
compatible = “nvidia,tegra210-qspi”;
clocks = <0x26 0xd3 0x26 0x119>;
resets = <0x26 0xd3>;
clock-names = “qspi”, “qspi_out”;
status = “okay”;
#address-cells = <0x1>;
interrupts = <0x0 0xa 0x4>;
#size-cells = <0x0>;
dma-names = “rx”, “tx”;
phandle = <0xfc>;
reg = <0x0 0x70410000 0x0 0x1000>;
iommus = <0x30 0xe>;
dmas = <0x51 0x5 0x51 0x5>;
reset-names = “qspi”;
linux,phandle = <0xfc>;
spi-max-frequency = <0x632ea00>;

            spiflash@0 {
                    compatible = "MX25U3235F";
                    #address-cells = <0x1>;
                    #size-cells = <0x1>;
                    reg = <0x0>;
                    spi-max-frequency = <0x632ea00>;

                    controller-data {
                            nvidia,ctrl-bus-clk-ratio = [01];
                            nvidia,x1-bus-speed = <0x632ea00>;
                            nvidia,x1-dymmy-cycle = <0x8>;
                            nvidia,x1-len-limit = <0x10>;
                            nvidia,x4-bus-speed = <0x632ea00>;
                            nvidia,x4-dymmy-cycle = <0x8>;

The hex value there for spi-max-frequency is (in decimal)104,000,000, so we should be able to toggle up to 104MHz based on that (but I assume with the hardware limitation of 65MHz bringing that down to 65)

Is there something I’m doing wrong here?

Try to print more message in set_best_clk_source() in spi-tegra114.c to narrow down it.

static void set_best_clk_source(struct tegra_spi_data *tspi,
965  				unsigned long rate)
966  {
967  	long new_rate;
968  	unsigned long err_rate, crate, prate;
969  	unsigned int cdiv, fin_err = rate;
970  	int ret;
971  	struct clk *pclk, *fpclk = NULL;
972  	const char *pclk_name, *fpclk_name = NULL;
973  	struct device_node *node;
974  	struct property *prop;
976  	node = tspi->master->dev.of_node;
977  	if (!of_property_count_strings(node, "nvidia,clk-parents"))
978  		return;
980  	/* when parent of a clk changes divider is not changed
981  	 * set a min div with which clk will not cross max rate
982  	 */
983  	if (!tspi->min_div) {
984  		of_property_for_each_string(node, "nvidia,clk-parents",
985  					    prop, pclk_name) {
986  			pclk = clk_get(tspi->dev, pclk_name);
987  			if (IS_ERR(pclk))
988  				continue;
989  			prate = clk_get_rate(pclk);
990  			crate = tspi->master->max_speed_hz;
991  			cdiv = DIV_ROUND_UP(prate, crate);
992  			if (cdiv > tspi->min_div)
993  				tspi->min_div = cdiv;
994  		}
995  	}
997  	pclk = clk_get_parent(tspi->clk);
998  	crate = clk_get_rate(tspi->clk);
999  	prate = clk_get_rate(pclk);
1000  	if (crate) {
1001  		cdiv = DIV_ROUND_UP(prate, crate);
1002  		if (cdiv < tspi->min_div) {
1003  			crate = DIV_ROUND_UP(prate, tspi->min_div);
1004  			clk_set_rate(tspi->clk, crate);
1005  	}
1006  	}

I assume you are referring to the dev_dbg function? I have added in some outputs of pclk_name, prate, crate and cdiv, as well as tspi->min_div. Unfortunately, when the image has been flashed to the development board, the debug messages enabled, and the spidev_test application is run, the messages I have added do not show up. I have examined the vmlinux file generated in the build directory, and the strings for those output statements are contained within it in proximity to one another, and some errors occurred with the format strings during compilation, so I am quite certain that the changes have been compiled. However, using the dynamic debugger (use described here: dynamic-debug-howto.html) to describe all the statements (with the function name) on the deployed image shows nothing. Is it possible then that my edits to the spi-tegra114.c file are somehow not being reflected in the image?

  1. Confirm the kernel is apply by sudo uname -a
  2. Need define the DEBUG in the file header to enable the dev_dbg()

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.