@@ -53,7 +53,7 @@  public:
 	std::map<PixelFormat, std::vector<SizeRange>> formats_;
 
 private:
-	bool generateId();
+	bool generateId(V4L2VideoDevice *video);
 
 	std::string id_;
 };
@@ -74,6 +74,9 @@  class PipelineHandlerUVC : public PipelineHandler
 public:
 	PipelineHandlerUVC(CameraManager *manager);
 
+	bool acquireDevice(Camera *camera);
+	void releaseDevice(Camera *camera);
+
 	std::unique_ptr<CameraConfiguration> generateConfiguration(Camera *camera,
 		const StreamRoles &roles) override;
 	int configure(Camera *camera, CameraConfiguration *config) override;
@@ -178,6 +181,28 @@  PipelineHandlerUVC::PipelineHandlerUVC(CameraManager *manager)
 {
 }
 
+bool PipelineHandlerUVC::acquireDevice(Camera *camera)
+{
+	UVCCameraData *data = cameraData(camera);
+
+	int ret = data->video_->open();
+	if (ret)
+		return false;
+
+	data->video_->bufferReady.connect(data, &UVCCameraData::bufferReady);
+
+	return true;
+}
+
+void PipelineHandlerUVC::releaseDevice(Camera *camera)
+{
+	UVCCameraData *data = cameraData(camera);
+
+	data->video_->bufferReady.disconnect();
+
+	data->video_->close();
+}
+
 std::unique_ptr<CameraConfiguration>
 PipelineHandlerUVC::generateConfiguration(Camera *camera,
 	const StreamRoles &roles)
@@ -426,16 +451,15 @@  int UVCCameraData::init(MediaDevice *media)
 		return -ENODEV;
 	}
 
+	std::unique_ptr<V4L2VideoDevice> video = std::make_unique<V4L2VideoDevice>(*entity);
+
 	/* Create and open the video device. */
-	video_ = std::make_unique<V4L2VideoDevice>(*entity);
-	ret = video_->open();
+	ret = video->open();
 	if (ret)
 		return ret;
 
-	video_->bufferReady.connect(this, &UVCCameraData::bufferReady);
-
 	/* Generate the camera ID. */
-	if (!generateId()) {
+	if (!generateId(video.get())) {
 		LOG(UVC, Error) << "Failed to generate camera ID";
 		return -EINVAL;
 	}
@@ -445,7 +469,7 @@  int UVCCameraData::init(MediaDevice *media)
 	 * resolution from the largest size it advertises.
 	 */
 	Size resolution;
-	for (const auto &format : video_->formats()) {
+	for (const auto &format : video->formats()) {
 		PixelFormat pixelFormat = format.first.toPixelFormat();
 		if (!pixelFormat.isValid())
 			continue;
@@ -485,7 +509,7 @@  int UVCCameraData::init(MediaDevice *media)
 	 * the _UPC.
 	 */
 	properties::LocationEnum location = properties::CameraLocationExternal;
-	std::ifstream file(video_->devicePath() + "/../removable");
+	std::ifstream file(video->devicePath() + "/../removable");
 	if (file.is_open()) {
 		std::string value;
 		std::getline(file, value);
@@ -503,7 +527,7 @@  int UVCCameraData::init(MediaDevice *media)
 	/* Initialise the supported controls. */
 	ControlInfoMap::Map ctrls;
 
-	for (const auto &ctrl : video_->controls()) {
+	for (const auto &ctrl : video->controls()) {
 		uint32_t cid = ctrl.first->id();
 		const ControlInfo &info = ctrl.second;
 
@@ -512,12 +536,21 @@  int UVCCameraData::init(MediaDevice *media)
 
 	controlInfo_ = ControlInfoMap(std::move(ctrls), controls::controls);
 
+	/*
+	 * Close the camera until it is acquired to prevent holding on to
+	 * resources that we do not own, or keeping devices powered when not in
+	 * use.
+	 */
+	video->close();
+
+	video_ = std::move(video);
+
 	return 0;
 }
 
-bool UVCCameraData::generateId()
+bool UVCCameraData::generateId(V4L2VideoDevice *video)
 {
-	const std::string path = video_->devicePath();
+	const std::string path = video->devicePath();
 
 	/* Create a controller ID from first device described in firmware. */
 	std::string controllerId;