Skip to content

Instantly share code, notes, and snippets.

@kralo
Last active October 18, 2023 00:27
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save kralo/5e489247d23dd13f4564fd6baa443416 to your computer and use it in GitHub Desktop.
Save kralo/5e489247d23dd13f4564fd6baa443416 to your computer and use it in GitHub Desktop.
Raspberry Pi 4 CMIO with 2 ov9281 camera sensors

Raspberry Pi 4 CMIO with 2 ov9281 camera sensors

THIS HAS CHANGED!

Now, all you need to do is add the following lines to your /boot/config.txt:

dtoverlay=ov9281
dtoverlay=ov9281,cam0

... and that's it!

This was the old story

Tested with 2 Arducam "UC-599" and 2 Inno-maker "cam-mipiov9281"

Credits to 6by9 on the raspberrypi forums.

Howto:

  1. Connect the jumpers on the J6
  2. Download the *.dtbo file to /boot/overlays/
  3. Add the line to /boot/config.txt: dtoverlay=ov9281dual
  4. Reboot

App A: Helpful Commands

See logs, loaded overlays:

$ sudo vcdbg log msg

This is expected, the firmware is not driving the cameras, the kernel is:

$ sudo vcgencmd get_camera
supported=0 detected=0

# Potential Output from dmesg:    
$ dmesg | grep 'ov9\|unicam'
[    4.944136] unicam fe800000.csi: ep_node is /soc/csi@7e800000/port/endpoint
[    4.944170] unicam fe800000.csi: found subdevice /soc/i2c0mux/i2c@0/ov9281_1@60
[    4.944217] unicam fe800000.csi: parsed local endpoint, bus_type 5
[    4.944237] unicam fe800000.csi: subdevice /soc/i2c0mux/i2c@0/ov9281_1@60: CSI-2 bus, 2 data lanes, flags=0x00000200
[    4.946557] unicam fe801000.csi: ep_node is /soc/csi@7e801000/port/endpoint
[    4.946587] unicam fe801000.csi: found subdevice /soc/i2c0mux/i2c@1/ov9281_0@60
[    4.946629] unicam fe801000.csi: parsed local endpoint, bus_type 5
[    4.946649] unicam fe801000.csi: subdevice /soc/i2c0mux/i2c@1/ov9281_0@60: CSI-2 bus, 2 data lanes, flags=0x00000200
[    5.954186] ov9281 0-0060: Detected OV009281 sensor
[    5.954234] unicam fe800000.csi: Using sensor mov9281 0-0060 for capture
[    5.954259] unicam fe800000.csi: __subdev_get_format 1280x800 code:0000
[    5.954278] unicam fe800000.csi: subdev mov9281 0-0060: code: 0x0000200a idx: 0
[    5.954295] unicam fe800000.csi: fmt 0x0000200a returned as (ptrval), V4L2 FOURCC 0x50303159, csi_dt 0x2b
[    5.954320] unicam fe800000.csi: __subdev_set_format 1280x800 code:200a
[    5.954335] unicam fe800000.csi: __subdev_get_format 1280x800 code:200a
[    5.954354] unicam fe800000.csi: unicam_calc_format_size_bpl: fourcc: 50303159 size: 1280x800 bpl:1600 img_size:1280000
[    5.962005] ov9281 10-0060: Detected OV009281 sensor
[    5.962056] unicam fe801000.csi: Using sensor mov9281 10-0060 for capture
[    5.962079] unicam fe801000.csi: __subdev_get_format 1280x800 code:0000
[    5.962098] unicam fe801000.csi: subdev mov9281 10-0060: code: 0x0000200a idx: 0
[    5.962115] unicam fe801000.csi: fmt 0x0000200a returned as (ptrval), V4L2 FOURCC 0x50303159, csi_dt 0x2b
[    5.962140] unicam fe801000.csi: __subdev_set_format 1280x800 code:200a
[    5.962155] unicam fe801000.csi: __subdev_get_format 1280x800 code:200a
[    5.962174] unicam fe801000.csi: unicam_calc_format_size_bpl: fourcc: 50303159 size: 1280x800 bpl:1600 img_size:1280000
[   31.847414] ov9281_dvdd: disabling
[   31.847436] ov9281_dovdd: disabling
[   31.847461] ov9281_avdd: disabling

App B: Howto build the binary

# get the linux sources to use the "#include"
# git clone --depth 1 https://github.com/raspberrypi/linux.git --branch rpi-5.4.y --single-branch
cpp -nostdinc -I ../linux/include/ -I arch  -undef -x assembler-with-cpp ov9281dual.dts ov9281dual.dts.prepro
dtc -I dts -O dtb -o ov9281dual.dtbo ov9281dual.dts.prepro
sudo cp ov9281dual.dtbo /boot/overlays/
// SPDX-License-Identifier: GPL-2.0-only
// Definitions for dual OV9281 camera modules
/dts-v1/;
/plugin/;
#include <dt-bindings/gpio/gpio.h>
/{
compatible = "brcm,bcm2835";
fragment@0 {
target = <&i2c_csi_dsi>;
__overlay__ {
#address-cells = <1>;
#size-cells = <0>;
status = "okay";
ov9281_0: ov9281_0@60 {
compatible = "ovti,ov9281";
reg = <0x60>;
status = "okay";
clocks = <&ov9281_clk_0>;
clock-names = "xvclk";
avdd-supply = <&ov9281_avdd>;
dovdd-supply = <&ov9281_dovdd>;
dvdd-supply = <&ov9281_dvdd>;
port {
ov9281_0_ep: endpoint {
remote-endpoint = <&csi1_ep>;
clock-lanes = <0>;
data-lanes = <1 2>;
clock-noncontinuous;
link-frequencies =
/bits/ 64 <400000000>;
};
};
};
};
};
fragment@1 {
target = <&csi1>;
__overlay__ {
status = "okay";
port {
csi1_ep: endpoint {
remote-endpoint = <&ov9281_0_ep>;
data-lanes = <1 2>;
clock-noncontinuous;
};
};
};
};
fragment@10 {
target = <&i2c_vc>;
__overlay__ {
#address-cells = <1>;
#size-cells = <0>;
status = "okay";
ov9281_1: ov9281_1@60 {
compatible = "ovti,ov9281";
reg = <0x60>;
status = "okay";
clocks = <&ov9281_clk_1>;
clock-names = "xvclk";
avdd-supply = <&ov9281_avdd>;
dovdd-supply = <&ov9281_dovdd>;
dvdd-supply = <&ov9281_dvdd>;
port {
ov9281_1_ep: endpoint {
remote-endpoint = <&csi0_ep>;
clock-lanes = <0>;
data-lanes = <1 2>;
clock-noncontinuous;
link-frequencies =
/bits/ 64 <400000000>;
};
};
};
};
};
fragment@11 {
target = <&csi0>;
__overlay__ {
status = "okay";
port {
csi0_ep: endpoint {
remote-endpoint = <&ov9281_1_ep>;
data-lanes = <1 2>;
clock-noncontinuous;
};
};
};
};
fragment@2 {
target = <&i2c0if>;
__overlay__ {
status = "okay";
};
};
fragment@3 {
target-path="/";
__overlay__ {
ov9281_avdd: fixedregulator_ov9281@0 {
compatible = "regulator-fixed";
regulator-name = "ov9281_avdd";
regulator-min-microvolt = <2800000>;
regulator-max-microvolt = <2800000>;
gpio = <&expgpio 5 GPIO_ACTIVE_HIGH>;
enable-active-high;
};
ov9281_dovdd: fixedregulator_ov9281@1 {
compatible = "regulator-fixed";
regulator-name = "ov9281_dovdd";
regulator-min-microvolt = <1800000>;
regulator-max-microvolt = <1800000>;
};
ov9281_dvdd: fixedregulator_ov9281@2 {
compatible = "regulator-fixed";
regulator-name = "ov9281_dvdd";
regulator-min-microvolt = <1200000>;
regulator-max-microvolt = <1200000>;
};
ov9281_clk_0: ov9281-clk_ov9281_0 {
compatible = "fixed-clock";
#clock-cells = <0>;
clock-frequency = <24000000>;
};
ov9281_clk_1: ov9281-clk_ov9281_1 {
compatible = "fixed-clock";
#clock-cells = <0>;
clock-frequency = <24000000>;
};
};
};
fragment@4 {
target = <&i2c0mux>;
__overlay__ {
status = "okay";
};
};
fragment@5 {
target-path="/__overrides__";
__overlay__ {
cam0-pwdn-ctrl = <&ov9281_avdd>,"gpio:0";
cam0-pwdn = <&ov9281_avdd>,"gpio:4";
};
};
};
@okalachev
Copy link

Thanks! Somewhat related solution to run an OV7251 on CAM0, based on yours: https://gist.github.com/okalachev/b75e22a82e2bcca82b451967be9f8c06.

@juanmf
Copy link

juanmf commented Oct 18, 2023

Hi, thanks for your post.
I'm struggling with inno-Maker CAM-MIPIOV9281V2
I don't see /dev/video0 tried your approach, theirs and created an issue in their repo. But I don't see activity in their issues list.

How can I debug, I'm not even sure it's functional.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment