Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8f980a99 authored by Arun Menon's avatar Arun Menon
Browse files

msm: vidc: defer probe if iommu_group_find fails



v4l2 video driver probe needs to defer till
iommu domains probe has been called. Without this
change, v4l2 video driver probe will fail if
iommu domains probe is not invoked prior to it.

Change-Id: Idbc1a4c90e558952f41f51ec96fdd3e7974490cd
Signed-off-by: default avatarArun Menon <avmenon@codeaurora.org>
parent f28186f6
Loading
Loading
Loading
Loading
+10 −4
Original line number Diff line number Diff line
@@ -389,13 +389,13 @@ static int msm_vidc_probe(struct platform_device *pdev)
	rc = msm_vidc_initialize_core(pdev, core);
	if (rc) {
		dprintk(VIDC_ERR, "Failed to init core\n");
		goto err_v4l2_register;
		goto err_core_init;
	}
	rc = device_create_file(&pdev->dev, &dev_attr_pwr_collapse_delay);
	if (rc) {
		dprintk(VIDC_ERR,
				"Failed to create pwr_collapse_delay sysfs node");
		goto err_v4l2_register;
		goto err_core_init;
	}
	if (core->hfi_type == VIDC_HFI_Q6) {
		dprintk(VIDC_DBG, "Q6 hfi device probe called\n");
@@ -460,11 +460,15 @@ static int msm_vidc_probe(struct platform_device *pdev)

	core->device = vidc_hfi_initialize(core->hfi_type, core->id,
				&core->resources, &handle_cmd_response);
	if (!core->device) {
		dprintk(VIDC_ERR, "Failed to create HFI device\n");
	if (IS_ERR_OR_NULL(core->device)) {
		mutex_lock(&vidc_driver->lock);
		vidc_driver->num_cores--;
		mutex_unlock(&vidc_driver->lock);
		rc = PTR_ERR(core->device);
		if (rc != -EPROBE_DEFER)
			dprintk(VIDC_ERR, "Failed to create HFI device\n");
		else
			dprintk(VIDC_DBG, "msm_vidc: request probe defer\n");
		goto err_cores_exceeded;
	}

@@ -489,6 +493,8 @@ err_dec_attr_link_name:
err_dec_register:
	v4l2_device_unregister(&core->v4l2_dev);
err_v4l2_register:
	device_remove_file(&pdev->dev, &dev_attr_pwr_collapse_delay);
err_core_init:
	kfree(core);
err_no_mem:
	return rc;
+5 −2
Original line number Diff line number Diff line
@@ -212,8 +212,9 @@ static int q6_hfi_register_iommu_domains(struct q6_hfi_device *device)
		iommu_map = &iommu_group_set->iommu_maps[i];
		iommu_map->group = iommu_group_find(iommu_map->name);
		if (!iommu_map->group) {
			dprintk(VIDC_ERR, "Failed to find group :%s\n",
			dprintk(VIDC_DBG, "Failed to find group :%s\n",
					iommu_map->name);
			rc = -EPROBE_DEFER;
			goto fail_group;
		}
		domain = iommu_group_get_iommudata(iommu_map->group);
@@ -221,6 +222,7 @@ static int q6_hfi_register_iommu_domains(struct q6_hfi_device *device)
			dprintk(VIDC_ERR,
					"Failed to get domain data for group %p",
					iommu_map->group);
			rc = -EINVAL;
			goto fail_group;
		}
		iommu_map->domain = msm_find_domain_no(domain);
@@ -228,6 +230,7 @@ static int q6_hfi_register_iommu_domains(struct q6_hfi_device *device)
			dprintk(VIDC_ERR,
					"Failed to get domain index for domain %p",
					domain);
			rc = -EINVAL;
			goto fail_group;
		}
	}
@@ -241,7 +244,7 @@ fail_group:
		iommu_map->group = NULL;
		iommu_map->domain = -1;
	}
	return -EINVAL;
	return rc;
}

static void q6_hfi_deregister_iommu_domains(struct q6_hfi_device *device)
+17 −5
Original line number Diff line number Diff line
@@ -2833,8 +2833,9 @@ static int venus_hfi_register_iommu_domains(struct venus_hfi_device *device,
		iommu_map = &iommu_group_set->iommu_maps[i];
		iommu_map->group = iommu_group_find(iommu_map->name);
		if (!iommu_map->group) {
			dprintk(VIDC_ERR, "Failed to find group :%s\n",
			dprintk(VIDC_DBG, "Failed to find group :%s\n",
				iommu_map->name);
			rc = -EPROBE_DEFER;
			goto fail_group;
		}
		domain = iommu_group_get_iommudata(iommu_map->group);
@@ -2842,6 +2843,7 @@ static int venus_hfi_register_iommu_domains(struct venus_hfi_device *device,
			dprintk(VIDC_ERR,
				"Failed to get domain data for group %p",
				iommu_map->group);
			rc = -EINVAL;
			goto fail_group;
		}
		iommu_map->domain = msm_find_domain_no(domain);
@@ -2849,6 +2851,7 @@ static int venus_hfi_register_iommu_domains(struct venus_hfi_device *device,
			dprintk(VIDC_ERR,
				"Failed to get domain index for domain %p",
				domain);
			rc = -EINVAL;
			goto fail_group;
		}
	}
@@ -2862,7 +2865,7 @@ fail_group:
		iommu_map->group = NULL;
		iommu_map->domain = -1;
	}
	return -EINVAL;
	return rc;
}

static void venus_hfi_deregister_iommu_domains(struct venus_hfi_device *device)
@@ -3180,7 +3183,10 @@ static int venus_hfi_init_resources(struct venus_hfi_device *device,

	rc = venus_hfi_register_iommu_domains(device, res);
	if (rc) {
		dprintk(VIDC_ERR, "Failed to register iommu domains: %d\n", rc);
		if (rc != -EPROBE_DEFER) {
			dprintk(VIDC_ERR,
				"Failed to register iommu domains: %d\n", rc);
		}
		goto err_register_iommu_domain;
	}

@@ -3667,6 +3673,7 @@ static void *venus_hfi_get_device(u32 device_id,

	rc = venus_hfi_init_resources(device, res);
	if (rc) {
		if (rc != -EPROBE_DEFER)
			dprintk(VIDC_ERR, "Failed to init resources: %d\n", rc);
		goto err_fail_init_res;
	}
@@ -3674,7 +3681,7 @@ static void *venus_hfi_get_device(u32 device_id,

err_fail_init_res:
	venus_hfi_delete_device(device);
	return NULL;
	return ERR_PTR(rc);
}

void venus_hfi_delete_device(void *device)
@@ -3757,6 +3764,11 @@ int venus_hfi_initialize(struct hfi_device *hdev, u32 device_id,
	}
	hdev->hfi_device_data = venus_hfi_get_device(device_id, res, callback);

	if (IS_ERR_OR_NULL(hdev->hfi_device_data)) {
		rc = PTR_ERR(hdev->hfi_device_data);
		goto err_venus_hfi_init;
	}

	venus_init_hfi_callbacks(hdev);

err_venus_hfi_init:
+3 −2
Original line number Diff line number Diff line
@@ -44,6 +44,7 @@ void *vidc_hfi_initialize(enum msm_vidc_hfi_type hfi_type, u32 device_id,
	}

	if (rc) {
		if (rc != -EPROBE_DEFER)
			dprintk(VIDC_ERR, "%s device init failed rc = %d",
				__func__, rc);
		goto err_hfi_init;
@@ -53,7 +54,7 @@ void *vidc_hfi_initialize(enum msm_vidc_hfi_type hfi_type, u32 device_id,

err_hfi_init:
	kfree(hdev);
	return NULL;
	return ERR_PTR(rc);
}

void vidc_hfi_deinitialize(enum msm_vidc_hfi_type hfi_type,