Full procedure for enabling SPI on the TX1?

I’m trying to make SPI work on the TX1 without any luck.

I found instructions on how to compile the TX1 kernel and upload it on http://developer.ridgerun.com/wiki/index.php?title=Compiling_Tegra_X1_source_code, and I managed to compile my own kernel.

I tried adding support for SPI in the kernel in two different ways:

  1. By adding the following lines in the tegra21_defconfig (after the CONFIG_SPI_TEGRA114=y line).
  1. In the menu-config I followed the instructions from http://neurorobotictech.com/Community/Blog/tabid/184/ID/12/Using-the-Jetson-TK1-SPI–Part-2-Configuring-the-kernel-for-SPI.aspx: setting “User mode SPI device driver support” to built-in.

When I had flashed TX1 with the new kernel I followed the instructions at https://devtalk.nvidia.com/default/topic/915614/did-anybody-get-spi-interface-working-on-tx1-:
I converted the /boot/tegra210-jetson-cv-base-p2597-2180-a00.dtb file to a .dts-file, and then added the following to the end of the gpio@6000d000 element:

gpio_default: default {
    gpio-to-sfio = <16 17 18 19 20>;

And the following to the end of the spi@7000d400 element:

spi0_0 {
    #address-cells = <0x1>;
    #size-cells = <0x0>;
    compatible = "spidev";
    reg = <0x0>;
    spi-max-frequency = <20000000>;
    nvidia,cs-setup-clk-count = <0x1e>;
    nvidia,cs-hold-clk-count = <0x1e>;
    nvidia,rx-clk-tap-delay = <0x1f>;
    nvidia,tx-clk-tap-delay = <0x0>;

I then convert the .dts-file back to /boot/tegra210-jetson-cv-base-p2597-2180-a00.dtb, rebooted, and connected the SPI_MOSI and SPI1_MISO pins (19 and 21 on the J21 header, the 10th and 11th pin on the row closest to the edge of the dev board, counting from the one closest to the J17 header, right?).

But I do not get anything showing up in /dev. What am I doing wrong?

Unless you’ve optionally switched to fastboot you don’t flash kernels, they’re just a file copy to “/boot” (take a look at “/boot/extlinux/extlinux.conf”), and modules to the relevant “/lib/modules” location. Starting in R24.2 an initrd is also used. In order to verify if your kernel made it in or not I’d advise adjust the CONFIG_LOCALVERSION and check if “uname -r” reflects that customization (e.g., set to “-custom1”).

I’m going to be trying to get SPI working myself shortly.

I noticed that you changed the wrong device tree file (at least if you’re trying to change it on the TX1). The TX1 only loads one of the .dtb files at the start, you can delete the others with no effect. From dmesg:

[    0.000000] DTS File Name: arch/arm64/boot/dts/tegra210-jetson-tx1-p2597-2180-a01-devkit.dts

If you want the changes made in tegra210-jetson-cv-base-p2597-2180-a00.dtb to take effect you’ll need to recompile the dtbs (make dtbs) so that your changes are written in to arch/arm64/boot/dts/tegra210-jetson-tx1-p2597-2180-a01-devkit.dtb

Note that the DTB actually used is named in the “/boot/extlinux/extlinux.conf” file via the FDT key/value pair (the same file where key/value pairs give the kernel file location, initrd location, and kernel parameters upon passing from boot loader to kernel).

Thank you both. I set the CONFIG_LOCALVERSION and the kernel indeed uploaded successfully.

I found in “/boot/extlinux/extlinux.conf” that it was indeed another dtb file being loaded: /boot/tegra210-jetson-tx1-p2597-2180-a01-devkit.dtb

So I made the same changes to that dtb file as I had done before, and it works!

It seems I was too excited about it merely showing up in /dev/spidev0.0. When I try to access it (using spidev_test -D /dev/spidev0.0) I get “can’t set spi mode: Inappropriate ioctl for device. Aborted.”

EDIT: I used the default spidev_test.c file. I tried the one written for RPi and it works now!

Awesome! I need to get SPI working myself so this is very helpful


I am also finding the method to enable SPI, and studying the article you create which names “Full procedure for enabling SPI on the TX1?”.
May I ask one question?
How to set CONFIG_LOCALVERSION, where could I find this parameter?


CONFIG_LOCALVERSION is part of the kernel source code. Every configuration in “make menuconfig” (or other ways of editing config) has an entry like that. You could edit the generated “.config” file directly, and put the text in the quoted value half of the key/value pair.

If you use something like “make menuconfig” or “make nconfig”, then go into “General setup —>”, note that usually the second line of that next menu is “() Local version - append to kernel release (NEW)”. That is the normal way of setting local version.

Hello, here’s a link to a wiki article documenting the procedure for enabling and testing SPI with loopback:


It includes changing over the DTB, and building SPIdev kernel module with the correct LOCALVERSION.

Thanks for every reply


I was looking over the wiki page you posted and I’m a bit confused on the spi numbering.

Under “aliases” in the TX1 dtb there is the following list:

spi0 = "/spi@7000d400";
spi1 = "/spi@7000d600";
spi2 = "/spi@7000d800";
spi3 = "/spi@7000da00";

On the wiki page it is written:

You also use “spi0_0” as your example, which would match the alias, but does not match the above quote. Would you mind clarifying? Is SPI1 actually at 7000d400, or is it at 7000d600 like aliases shows?

Based on this post, and my own testing I confirmed that the wiki page is correct.

spi1 on the J21 header is under spi@7000d400. What’s strange to me is that it gets registered as device spi0_0 even if you try to call it spi1_0.

Anywho, follow the wiki page.

The method is same for TX2 as well?

Does that article also work for TK1? (https://elinux.org/Jetson/TX1_SPI)
Which steps will I have to change to make it work?