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

Commit a9ea69b5 authored by Ravi kumar Koyyana's avatar Ravi kumar Koyyana Committed by VijayaKumar T M
Browse files

msm: camera2: cpp: Fix iommu_attach/detach compat_ioctl issue



When the Camera application exercises the  V4L2  ioctl operations, CPP
driver would attempt to the copy  user space buffer  contents into the
internal kernel buffer.  If an invalid length of the user space buffer
is passed onto the driver, it could trigger buffer overflow condition.

Thus, fix this by copying user space buffer contents into kernel space
buffer of the  driver for further processing,  only after checking for
proper length of user space buffer.

CRs-fixed: 2025367
Change-Id: I85cf4a961884c7bb0d036299b886044aef7baf7c
Signed-off-by: default avatarRavi kumar Koyyana <rkoyyana@codeaurora.org>
Signed-off-by: default avatarVijayaKumar T M <vtmuni@codeaurora.org>
parent d5746b4f
Loading
Loading
Loading
Loading
+40 −6
Original line number Diff line number Diff line
@@ -1891,17 +1891,49 @@ static int msm_cpp_copy_from_ioctl_ptr(void *dst_ptr,
}
#endif

static int msm_cpp_validate_ioctl_input(unsigned int cmd, void *arg,
	struct msm_camera_v4l2_ioctl_t **ioctl_ptr)
{
	switch (cmd) {
	case MSM_SD_SHUTDOWN:
	case MSM_SD_NOTIFY_FREEZE:
	case VIDIOC_MSM_CPP_IOMMU_ATTACH:
	case VIDIOC_MSM_CPP_IOMMU_DETACH:
		break;
	default:
		if (ioctl_ptr == NULL) {
			pr_err("Wrong ioctl_ptr for cmd %u\n", cmd);
			return -EINVAL;
		}

		*ioctl_ptr = arg;
		if (((*ioctl_ptr) == NULL) ||
			((*ioctl_ptr)->ioctl_ptr == NULL) ||
			((*ioctl_ptr)->len == 0)) {
			pr_err("Error invalid ioctl argument cmd %u", cmd);
			return -EINVAL;
		}
		break;
	}
	return 0;
}

long msm_cpp_subdev_ioctl(struct v4l2_subdev *sd,
			unsigned int cmd, void *arg)
{
	struct cpp_device *cpp_dev = NULL;
	struct msm_camera_v4l2_ioctl_t *ioctl_ptr = arg;
	struct msm_camera_v4l2_ioctl_t *ioctl_ptr = NULL;
	int rc = 0;

	if ((sd == NULL) || (ioctl_ptr == NULL)) {
		pr_err("Wrong ioctl_ptr %p, sd %p\n", ioctl_ptr, sd);
	if (sd == NULL) {
		pr_err("sd %pK\n", sd);
		return -EINVAL;
	}
	rc = msm_cpp_validate_ioctl_input(cmd, arg, &ioctl_ptr);
	if (rc != 0) {
		pr_err("input validation failed\n");
		return rc;
	}

	if (_IOC_DIR(cmd) == _IOC_NONE) {
		pr_err("Invalid ioctl/subdev cmd %u", cmd);
@@ -2315,6 +2347,7 @@ long msm_cpp_subdev_ioctl(struct v4l2_subdev *sd,
				pr_err("%s:%dError iommu_attach_device failed\n",
					__func__, __LINE__);
				rc = -EINVAL;
				break;
			}
			cpp_dev->iommu_state = CPP_IOMMU_STATE_ATTACHED;
		} else {
@@ -2331,8 +2364,9 @@ long msm_cpp_subdev_ioctl(struct v4l2_subdev *sd,
				cpp_dev->iommu_ctx);
			cpp_dev->iommu_state = CPP_IOMMU_STATE_DETACHED;
		} else {
			pr_err("%s:%d IOMMMU attach triggered in invalid state\n",
			pr_err("%s:%d IOMMMU detach triggered in invalid state\n",
				__func__, __LINE__);
			rc = -EINVAL;
		}
		break;
	}
@@ -2855,7 +2889,7 @@ static long msm_cpp_subdev_fops_compat_ioctl(struct file *file,
	default:
		pr_err_ratelimited("%s: unsupported compat type :%d\n",
				__func__, cmd);
		break;
		return -EINVAL;
	}

	switch (cmd) {
@@ -2882,7 +2916,7 @@ static long msm_cpp_subdev_fops_compat_ioctl(struct file *file,
	default:
		pr_err_ratelimited("%s: unsupported compat type :%d\n",
				__func__, cmd);
		break;
		return -EINVAL;
	}

	if (is_copytouser_req) {