Hello
I am trying to connect deserializer to TX1 board. I wrote simple driver, that connects to DS90UB964 by I2C and configure it to make test pattern. I2C works fine, i can read and write registers.
Code of initialization test pattern i got from datasheet without any changes:
WriteI2C(0x32,0x01) # CSI0 sel and CSI0 enable
WriteI2C(0x33,0x01)
WriteI2C(0xB0,0x00) # Indirect Pattern Gen Registers
WriteI2C(0xB1,0x01) # PGEN_CTL
WriteI2C(0xB2,0x01)
WriteI2C(0xB1,0x02) # PGEN_CFG
WriteI2C(0xB2,0x33)
WriteI2C(0xB1,0x03) # PGEN_CSI_DI
WriteI2C(0xB2,0x24) # THIS MEANS VIDEO FORMAT RGB888
WriteI2C(0xB1,0x04) # PGEN_LINE_SIZE1
WriteI2C(0xB2,0x0F)
WriteI2C(0xB1,0x05) # PGEN_LINE_SIZE0
WriteI2C(0xB2,0x00) # LINE SIZE = 3840
WriteI2C(0xB1,0x06) # PGEN_BAR_SIZE1
WriteI2C(0xB2,0x01)
WriteI2C(0xB1,0x07) # PGEN_BAR_SIZE0
WriteI2C(0xB2,0xE0)
WriteI2C(0xB1,0x08) # PGEN_ACT_LPF1
WriteI2C(0xB2,0x02)
WriteI2C(0xB1,0x09) # PGEN_ACT_LPF0
WriteI2C(0xB2,0xD0) # ACTIVE LINES PER FRAME = 720
WriteI2C(0xB1,0x0A) # PGEN_TOT_LPF1
WriteI2C(0xB2,0x04)
WriteI2C(0xB1,0x0B) # PGEN_TOT_LPF0
WriteI2C(0xB2,0x1A) # TOTAL LINES PER FRAME = 1050
WriteI2C(0xB1,0x0C) # PGEN_LINE_PD1
WriteI2C(0xB2,0x0C)
WriteI2C(0xB1,0x0D) # PGEN_LINE_PD0
WriteI2C(0xB2,0x67) # LINE PERIOD IS 31.75 us
WriteI2C(0xB1,0x0E) # PGEN_VBP
WriteI2C(0xB2,0x21) # vertical back porch = 33
WriteI2C(0xB1,0x0F) # PGEN_VFP
WriteI2C(0xB2,0x0A) # vertical front porch = 10
CSI output i checked with oscilloscope - it looks good. On my ds90ub964 board i use 25MHz-crystal and dont need in clock from TX1. CSI0 of ds90ub964 connected to CSIA+CSIB of TX1 board. Device tree part:
i2c@546c0000 {
#address-cells = <0x1>;
#size-cells = <0x0>;
compatible = "nvidia,tegra210-vii2c";
reg = <0x0 0x546c0000 0x0 0x34000>;
iommus = <0x52 0x12>;
interrupts = <0x0 0x11 0x4>;
scl-gpio = <0x7b 0x92 0x0>;
sda-gpio = <0x7b 0x93 0x0>;
status = "okay";
clocks = <0x41 0xd0 0x41 0x51 0x41 0x1c>;
clock-names = "vii2c", "i2cslow", "host1x";
resets = <0x41 0xd0>;
reset-names = "vii2c";
clock-frequency = <0x186A0>;
bus-pullup-supply = <0x69>;
avdd_dsi_csi-supply = <0x67>;
linux,phandle = <0xe0>;
phandle = <0xe0>;
ap0100_a@30 {
compatible = "nvidia,ap0100";
reg = <0x30>;
status = "okay";
devnode = "video0";
physical_w = "3.674";
physical_h = "2.738";
vertical-flip = "true";
avdd-reg = "vana";
iovdd-reg = "vif";
clocks = <0x41 0x117>;
clock-names = "clk_out_3";
//clock-frequency = <0x16e3600>;
clock-frequency = <0x17D7840>;
mclk = "clk_out_3";
vana-supply = <0x94>;
vif-supply = <0x93>;
mode0 {
mclk_khz = "24000";
num_lanes = "4";
//tegra_sinterface = "serial_ab";
tegra_sinterface = "serial_a";
discontinuous_clk = "no";
dpcm_enable = "false";
cil_settletime = "0";
active_w = "1280";
active_h = "1050";
//pixel_t = "bayer_bggr";
pixel_t = "rgb888";
readout_orientation = "0";
line_length = "3840";
inherent_gain = "1";
mclk_multiplier = "1.41";
pix_clk_hz = "33780000";
min_gain_val = "1.0";
max_gain_val = "16";
min_hdr_ratio = [31 00];
max_hdr_ratio = "64";
min_framerate = "1.816577";
max_framerate = "30";
min_exp_time = "34";
max_exp_time = "550385";
};
ports {
#address-cells = <0x1>;
#size-cells = <0x0>;
port@0 {
reg = <0x0>;
ap0100_out0: endpoint {
csi-port = <0x0>;
bus-width = <0x4>;
remote-endpoint = <&csi_in0>;
linux,phandle = <0xea>;
phandle = <0xea>;
};
};
};
};
};
nvcsi {
num-channels = <0x2>;
#address-cells = <0x1>;
#size-cells = <0x0>;
linux,phandle = <0xe7>;
phandle = <0xe7>;
channel@0 {
reg = <0x0>;
status = "okay";
linux,phandle = <0xe8>;
phandle = <0xe8>;
ports {
#address-cells = <0x1>;
#size-cells = <0x0>;
port@0 {
reg = <0x0>;
status = "okay";
linux,phandle = <0xe9>;
phandle = <0xe9>;
csi_in0: endpoint@0 {
csi-port = <0x0>;
bus-width = <0x4>;
remote-endpoint = <&ap0100_out0>;
status = "okay";
linux,phandle = <0x96>;
phandle = <0x96>;
};
};
port@1 {
reg = <0x1>;
status = "okay";
linux,phandle = <0xeb>;
phandle = <0xeb>;
csi_out0: endpoint@1 {
remote-endpoint = <&vi_in0>;
status = "okay";
linux,phandle = <0x81>;
phandle = <0x81>;
};
};
};
};
channel@1 {
reg = <0x1>;
status = "okay";
linux,phandle = <0xf7>;
phandle = <0xf7>;
ports {
#address-cells = <0x1>;
#size-cells = <0x0>;
port@0 {
reg = <0x0>;
status = "okay";
linux,phandle = <0xf8>;
phandle = <0xf8>;
endpoint@2 {
csi-port = <0x1>;
bus-width = <0x4>;
remote-endpoint = <&ap0100_out0>;
status = "okay";
linux,phandle = <0x97>;
phandle = <0x97>;
};
};
port@1 {
reg = <0x1>;
status = "okay";
linux,phandle = <0xf9>;
phandle = <0xf9>;
endpoint@3 {
remote-endpoint = <&vi_in0>;
status = "okay";
linux,phandle = <0x82>;
phandle = <0x82>;
};
};
};
};
other channels are disabled. ap0100 will be connected to deserializer.
I added RGB888 to sources:
in camera_common.c:
static const struct camera_common_colorfmt camera_common_fmts[] = {
...
{
MEDIA_BUS_FMT_RGB888_1X24,
V4L2_COLORSPACE_SRGB,
V4L2_PIX_FMT_RGB24,
},
...
}
in sensor_common.c:
static int extract_pixel_format( ...
...
else if (strncmp(pixel_t, "rgb888", size) == 0)
*format = V4L2_PIX_FMT_RGB24;
...
Now when i try to start cheese i see black window and this strings in dmesg:
[ 62.487894] ap0100_set_format:0
[ 62.517720] ap0100 6-0030: camera_common_try_fmt: size 1280 x 720
[ 62.524036] ap0100 6-0030: camera_common_try_fmt: break!
[ 62.529561] ap0100 6-0030: camera_common_try_fmt: else!
[ 62.534914] ap0100 6-0030: camera_common_try_fmt: err = 0
[ 62.540850] ap0100_set_format:0
[ 62.544085] ap0100 6-0030: camera_common_try_fmt: size 1280 x 720
[ 62.550635] ap0100 6-0030: camera_common_try_fmt: break!
[ 62.556638] ap0100 6-0030: camera_common_try_fmt: else!
[ 62.562008] ap0100 6-0030: camera_common_try_fmt: err = 0
[ 62.571440] ap0100_set_format:0
[ 62.574625] ap0100 6-0030: camera_common_s_fmt(4106) size 1280 x 720
[ 62.581062] ap0100 6-0030: camera_common_try_fmt: size 1280 x 720
[ 62.587161] ap0100 6-0030: camera_common_try_fmt: break!
[ 62.592559] ap0100 6-0030: camera_common_try_fmt: else!
[ 62.597795] ap0100 6-0030: camera_common_try_fmt: err = 0
[ 62.603282] ap0100 6-0030: camera_common_s_fmt: ret = 0
[ 62.608520] ap0100_set_format:0
[ 62.695317] ap0100_get_format
[ 62.698307] ap0100 6-0030: camera_common_g_fmt++
[ 62.702943] ap0100 6-0030: 1 fmt->code = 4106
[ 62.707430] ap0100 6-0030: 2 fmt->colorspace = 8
[ 62.712248] ap0100 6-0030: 3 s_data->fmt_width = 1280
[ 62.717334] ap0100 6-0030: 4 s_data->fmt_height = 720
[ 62.734245] video4linux video0: valid_ports = 1
[ 62.738791] vi 54080000.vi: Calibrate csi port 0
[ 62.901143] video4linux video0: frame start syncpt timeout!0
[ 62.907046] video4linux video0: TEGRA_VI_CSI_ERROR_STATUS 0x00000000
[ 62.913640] vi 54080000.vi: TEGRA_CSI_PIXEL_PARSER_STATUS 0x00000000
[ 62.920745] vi 54080000.vi: TEGRA_CSI_CIL_STATUS 0x00000010
[ 62.926463] vi 54080000.vi: TEGRA_CSI_CILX_STATUS 0x00040041
[ 62.938432] video4linux video0: valid_ports = 1
[ 63.100444] video4linux video0: frame start syncpt timeout!0
[ 63.106109] video4linux video0: TEGRA_VI_CSI_ERROR_STATUS 0x00000000
[ 63.113257] vi 54080000.vi: TEGRA_CSI_PIXEL_PARSER_STATUS 0x00000000
[ 63.120140] vi 54080000.vi: TEGRA_CSI_CIL_STATUS 0x00000000
[ 63.126124] vi 54080000.vi: TEGRA_CSI_CILX_STATUS 0x00000000
...
[ 66.189582] ap0100 6-0030: ap0100_power_off: power off
0x00000010 and 0x00040041 in status registers means that i made mistakes in line_lenght of device tree? I dont have any idea how to fix errors.
May be somebody use DS90UB964 and can share sources?