Detect camera is connected/disconnected

I’m looking for a simple way to check if a camera is physically connected to the jetson. This system will be subject to vibrations and the camera may disconnect itself.
What I’ve tried so far:

  • ls /dev/video*: this command always lists multiple video devices even when none are connected
  • v4l2-ctl --list-devices: same as above, lists all video devices even when none are connected
  • v4l2-ctl --device=/dev/videoX -I: I’ve noticed that this command outputs Video input : 0 (Camera x: ok) when the camera is connected and Video input : 0 (Camera x: no power) when it is disconnected. The problem is that running the command also outputs Video input : 0 (Camera x: no power) when any gstreamer pipeline with nvarguscamerasrc is running.
  • Using gstreamer to capture one frame works fine as long as there’s no other process using the camera. If there’s already a process using the camera then both processes crash with an error. Also not good.

Any other suggestions?

hello user41388,

may I know what’s the environment setups, did you used SerDes chip?
also, is it multi-cam use-case? may I also know how many cameras in your system?

No idea about the SerDes chip, sorry.
The environment is a Jetson Xavier NX (5.1.2) with a custom carrier board. It is a multi-cam use-case, with either 2 or 3 IMX334 cameras. The camera driver is developed in-house.
All I want to achieve is to have a basic check that tells me whether the camera(s) are physically connected or not.

hello user41388,

please see-also Jetson Virtual Channel with GMSL Camera Framework for more details about SerDes chip.

am I understand correctly it’s well connected while system boot-up (that’s why video node has register correctly).
but, it’ll have some vibrations during camera use-case?

anyways, v4l2-ctl --list-devices it only checks for driver info, it’s not accessing to camera device.
one solid test approach is running with v4l2 IOCTL to fetch the sensor stream directly.
for instance, $ v4l2-ctl -d /dev/video0 --set-fmt-video=width=1920,height=1080,pixelformat=RG10 --set-ctrl bypass_mode=0 --stream-mmap --stream-count=10
assume there’s no functionality failure, you’ll see < for each success capture frames, and it’ll report fps for every second.

Thank you JerryChang, that command does indeed work as expected without side-effects.

While looking closer at my camera driver implementation, I noticed that I never check that I can communicate with the camera during X_board_setup. This has a nice side-effect for me, it guarantees that the /dev/video* order is always the same and matching sensor-id order. I’m just not sure whether there’s a negative side-effect as I now understand that this design doesn’t follow what other camera drivers are doing.

Using nv_imx219 as an example, here is its board_setup function:

static int imx219_board_setup(struct imx219 *priv)
{
	struct camera_common_data *s_data = priv->s_data;
	struct camera_common_pdata *pdata = s_data->pdata;
	struct device *dev = s_data->dev;
	u8 reg_val[2];
	int err = 0;

	if (pdata->mclk_name) {
		err = camera_common_mclk_enable(s_data);
		if (err) {
			dev_err(dev, "error turning on mclk (%d)\n", err);
			goto done;
		}
	}

	err = imx219_power_on(s_data);
	if (err) {
		dev_err(dev, "error during power on sensor (%d)\n", err);
		goto err_power_on;
	}

	/* Probe sensor model id registers */
	err = imx219_read_reg(s_data, IMX219_MODEL_ID_ADDR_MSB, &reg_val[0]);
	if (err) {
		dev_err(dev, "%s: error during i2c read probe (%d)\n",
			__func__, err);
		goto err_reg_probe;
	}
	err = imx219_read_reg(s_data, IMX219_MODEL_ID_ADDR_LSB, &reg_val[1]);
	if (err) {
		dev_err(dev, "%s: error during i2c read probe (%d)\n",
			__func__, err);
		goto err_reg_probe;
	}
	if (!((reg_val[0] == 0x02) && reg_val[1] == 0x19))
		dev_err(dev, "%s: invalid sensor model id: %x%x\n",
			__func__, reg_val[0], reg_val[1]);

	/* Sensor fine integration time */
	err = imx219_get_fine_integ_time(priv, &priv->fine_integ_time);
	if (err)
		dev_err(dev, "%s: error querying sensor fine integ. time\n",
			__func__);

err_reg_probe:
	imx219_power_off(s_data);

err_power_on:
	if (pdata->mclk_name)
		camera_common_mclk_disable(s_data);

done:
	return err;
}

Are there any negative side-effects if I would not probe the registers? like this:

static int imx219_board_setup(struct imx219 *priv)
{
	struct camera_common_data *s_data = priv->s_data;
	struct camera_common_pdata *pdata = s_data->pdata;
	struct device *dev = s_data->dev;
	u8 reg_val[2];
	int err = 0;

	if (pdata->mclk_name) {
		err = camera_common_mclk_enable(s_data);
		if (err) {
			dev_err(dev, "error turning on mclk (%d)\n", err);
			goto done;
		}
	}

	err = imx219_power_on(s_data);
	if (err) {
		dev_err(dev, "error during power on sensor (%d)\n", err);
		goto err_power_on;
	}

	imx219_power_off(s_data);

err_power_on:
	if (pdata->mclk_name)
		camera_common_mclk_disable(s_data);

done:
	return err;
}

hello user41388,

it’s due to design logic (camera driver registration, sensor operation…etc) did not put vibrations and camera disconnect itself as consideration.

note,
the first approach is from hardware side trying to improve the quality of the MIPI signals. for example, strengthen the camera connector to make it stable.
nevertheless,
when it still have hardware level failure to send intermittently signaling. there’s error handling mechanism present to have address such failure. please see-also similar topic for reference, for instance, Topic 243051.

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