Device tree not updated for new camera driver

Hi all,

I have refered to Camera Development section in NVIDIA Tegra Linux Driver Package Development Guide R32.1, to create a new camera based on IMX204.

Here are the steps:

  1. Create a new .dtsi file for IMX421 camera inside Linux_for_Tegra/sources/hardware/platform/t19x/common/kernel-dts/t19x-common-modules (copy from Tegra194-camera-e3377-a00.dtsi for IMX204 with the update to new camera). They both share the same spi@c2600000 driver

  2. update tegra194-camera-plugin-manager.dtsi with the new camera as below

/* E3377 camera board */
		fragment-e3377@0 {
			ids = "3377-1000-*";
			override@0 {
				target = <&e3377_cam0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@1 {
				target = <&cam_module0>;
				_overlay_ {
					status = "okay";
					badge = "e3377_rear_IMX204";
					position = "rear";
					orientation = "1";
				};
			};
			override@2 {
				target = <&cam_module0_drivernode0>;
				_overlay_ {
					status = "okay";
					pcl_id = "v4l2_sensor";
					devname = "imx204_spi";
					proc-device-tree = "/proc/device-tree/spi@c260000/imx204@0";
				};
			};
			/* Enable VI ports */
			override@4 {
				target = <&vi_base>;
				_overlay_ {
					num-channels=<1>;
				};
			};
			override@5 {
				target = <&vi_port0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@6 {
				target = <&e3377_vi_in0>;
				_overlay_ {
					status = "okay";
					port-index = <0>;
					bus-width = <4>;
					remote-endpoint = <&e3377_slvs_ec_out0>;
				};
			};
			/* Enable SLVS-EC ports */
			override@8 {
				target = <&slvs_ec_stream0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@9 {
				target = <&slvs_ec_stream0_port0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@10 {
				target = <&e3377_slvs_ec_in0>;
				_overlay_ {
					status = "okay";
					port-index = <0>;
					bus-width = <4>;
					remote-endpoint = <&e3377_imx204_out0>;
				};
			};
			override@11 {
				target = <&slvs_ec_stream0_port1>;
				_overlay_ {
					status = "okay";
				};
			};
			override@12 {
				target = <&e3377_slvs_ec_out0>;
				_overlay_ {
					status = "okay";
					remote-endpoint = <&e3377_vi_in0>;
				};
			};
			/* GPIO */
			override@14 {
				target = <&{/gpio@2200000}>;
				_overlay_ {
					camera-control-input {
						status = "disabled";
					};
					camera-control-output-low {
						gpio-hog;
						gpios = <SLVS_CAM0_RST_L 0>;
						label = "slvs-cam0-rst";
						output-low;
						status = "okay";
					};
					camera-control-output-high {
						status = "disabled";
					};
				};
			};
		};

		/* E3377IMX421 camera board */
		fragment-imx421@0 {
			ids = "imx421-1000-*";
			override@0 {
				target = <&imx421_cam0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@1 {
				target = <&cam_module0>;
				_overlay_ {
					status = "okay";
					badge = "imx421_rear_IMX421";
					position = "rear";
					orientation = "1";
				};
			};
			override@2 {
				target = <&cam_module0_drivernode0>;
				_overlay_ {
					status = "okay";
					pcl_id = "v4l2_sensor";
					devname = "imx421_spi";
					proc-device-tree = "/proc/device-tree/spi@c260000/imx421@0";
				};
			};
			/* Enable VI ports */
			override@4 {
				target = <&vi_base>;
				_overlay_ {
					num-channels=<1>;
				};
			};
			override@5 {
				target = <&vi_port0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@6 {
				target = <&imx421_vi_in0>;
				_overlay_ {
					status = "okay";
					port-index = <0>;
					bus-width = <4>;
					remote-endpoint = <&imx421_slvs_ec_out0>;
				};
			};
			/* Enable SLVS-EC ports */
			override@8 {
				target = <&slvs_ec_stream0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@9 {
				target = <&slvs_ec_stream0_port0>;
				_overlay_ {
					status = "okay";
				};
			};
			override@10 {
				target = <&imx421_slvs_ec_in0>;
				_overlay_ {
					status = "okay";
					port-index = <0>;
					bus-width = <4>;
					remote-endpoint = <&imx421_imx421_out0>;
				};
			};
			override@11 {
				target = <&slvs_ec_stream0_port1>;
				_overlay_ {
					status = "okay";
				};
			};
			override@12 {
				target = <&imx421_slvs_ec_out0>;
				_overlay_ {
					status = "okay";
					remote-endpoint = <&imx421_vi_in0>;
				};
			};
			/* GPIO */
			override@14 {
				target = <&{/gpio@2200000}>;
				_overlay_ {
					camera-control-input {
						status = "disabled";
					};
					camera-control-output-low {
						gpio-hog;
						gpios = <SLVS_CAM0_RST_L 0>;
						label = "slvs-cam0-rst";
						output-low;
						status = "okay";
					};
					camera-control-output-high {
						status = "disabled";
					};
				};
			};
		};
  1. Add the new camera .dtsi into …/galen/kernel-dts/common/tegra194-p2822-camera-modules.dtsi
  2. New files imx421.c and imx421.h created, and updated in kernel folder.
  3. Updated respective tegra_deconfig and Make file for new camera driver

Compilation success without failure, after flashing to target, there were few issues:

a. Could not locate imx421@0 folder inside sys/firmware/devicetree/base/spi@c260000, it contains only imx204@0 folder
b. imx421.h is not included inside usr/src/linux-headers-4.9.140-tegra-linux_x86_64/nvidia/include/media and other include folder for application usage.

Please share me how to fix the device tree problem if you have the solution. Thanks a lot!

hello quochung11,

there are two confirmation methods that you could have another try.

  1. please confirm IMX421 settings included in tegra194.dtb, please disassembler the dtb file into txt file for checking.
    for example,
$ dtc -I dtb -O dts -o temp.txt $OUT/kernel/dtb/tegra194-p2888-0001-p2822-0000.dtb
  1. once you confirmed the dtb correctness. please execute below command to update DTB partition.
$ sudo ./flash.sh -r -k kernel-dtb jetson-xavier mmcblk0p1

Nvidia has a very convenient way to quickly check that the device tree is the one you expect.

The following will tell you when your DTB was built. This is usually enough to prove to yourself that you have the device tree loaded that you expect.

cat /proc/device-tree/nvidia,dtbbuildtime

hello Cherry,

You are right, IMX421 setting was not there in tegra194-p2888-0001-p2822-0000.dtb, only IMX204. But I was not so clear why it was not included there.

I checked that IMX421.dtsi was included into tegra194-p2888-0001-p2822-0000.dts.

I have compiled the kernel many times, dtb should be compiled as well.

Any hint from your side. Thanks a lot!

hello Growe,

After running this command on Xavier, the dtbbuildtime was so old, much before the date I added the new device. Do you have any idea?

Many thanks!

I’ve had some trouble with flash.sh. With R28 on Tx2 I used to be able to specify a specific DTB file using the -d parameter. With later releases (including all releases for Xavier) it doesn’t honor the -d parameter so I have to workaround the problem.

I do the following when I flash a DTB.

  • L4T_DIR is the L4 install directory
  • SYSTEM_TYPE is jetson-xavier, jetson-nano, etc
  • DTB_FILE is the dtb file to flash
sudo cp "@DTB_FILE@" "@L4TDIR@/kernel/dtb/tegra186-quill-p3310-1000-c03-00-base.dtb"
cd "@L4TDIR@"
sudo ./flash.sh -k kernel-dtb @SYSTEM_TYPE@ mmcblk0p1

Hello Cherry, Growe

I finally figured out that I copied the wrong one:

I changed from:

cp -r ./arch/arm64/boot/dts ${JETPACK}/Linux_for_Tegra/kernel/dtb

to

cp -r ./arch/arm64/boot/dts/. ${JETPACK}/Linux_for_Tegra/kernel/dtb

just copy the content of dts folder, not the folder to dtb.

Many thanks for your support!

Awesome! Nice catch!

1 Like

I have the same problem with my camera driver for Jetson Nano.
I wrote my camera driver based on camera dual imx219.
Because I do not the file flash.sh
After rebuild the kernel I copy
sudo cp $TEGRA_KERNEL_OUT/arch/arm64/boot/Image /boot/.
sudo cp -r $TEGRA_KERNEL_OUT/arch/arm64/boot/dts/* /boot/dtb/.

But finally I can not find the way to generate device-tree for my camera.

Could you pls help me? Thanks

Hi Thanh-Binh.To,

Please help to open a new topic if it’s still an issue. Thanks