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

Commit 57428171 authored by Steve Cohen's avatar Steve Cohen
Browse files

drm/msm/sde: memory leak fix for virtual plane formats



The supported format list for virtual planes was created dynamically
when needed and in certain cases would only be freed if an error
condition was hit.  This patch fixes the memory leak and cleans up
the design for future improvements to virtual plane formats.

CRs-Fixed: 2078448
Change-Id: I46a8864372644d398758a0557bc8b8a45612b31c
Signed-off-by: default avatarSteve Cohen <cohens@codeaurora.org>
parent f5d01515
Loading
Loading
Loading
Loading
+4 −0
Original line number Diff line number Diff line
@@ -945,6 +945,7 @@ static void _sde_sspp_setup_vig(struct sde_mdss_cfg *sde_cfg,
	}

	sblk->format_list = sde_cfg->vig_formats;
	sblk->virt_format_list = sde_cfg->dma_formats;
}

static void _sde_sspp_setup_rgb(struct sde_mdss_cfg *sde_cfg,
@@ -997,6 +998,7 @@ static void _sde_sspp_setup_rgb(struct sde_mdss_cfg *sde_cfg,
	}

	sblk->format_list = sde_cfg->dma_formats;
	sblk->virt_format_list = NULL;
}

static void _sde_sspp_setup_cursor(struct sde_mdss_cfg *sde_cfg,
@@ -1010,6 +1012,7 @@ static void _sde_sspp_setup_cursor(struct sde_mdss_cfg *sde_cfg,
	sblk->maxupscale = SSPP_UNITY_SCALE;
	sblk->maxdwnscale = SSPP_UNITY_SCALE;
	sblk->format_list = sde_cfg->cursor_formats;
	sblk->virt_format_list = NULL;
	sspp->id = SSPP_CURSOR0 + *cursor_count;
	snprintf(sspp->name, SDE_HW_BLK_NAME_LEN, "sspp_%u",
			sspp->id - SSPP_VIG0);
@@ -1025,6 +1028,7 @@ static void _sde_sspp_setup_dma(struct sde_mdss_cfg *sde_cfg,
	sblk->maxupscale = SSPP_UNITY_SCALE;
	sblk->maxdwnscale = SSPP_UNITY_SCALE;
	sblk->format_list = sde_cfg->dma_formats;
	sblk->virt_format_list = sde_cfg->dma_formats;
	sspp->id = SSPP_DMA0 + *dma_count;
	sspp->clk_ctrl = SDE_CLK_CTRL_DMA0 + *dma_count;
	snprintf(sspp->name, SDE_HW_BLK_NAME_LEN, "sspp_%u",
+3 −1
Original line number Diff line number Diff line
@@ -395,6 +395,7 @@ struct sde_qos_lut_tbl {
 * @danger_vblank: danger priority during vertical blanking
 * @pixel_ram_size: size of latency hiding and de-tiling buffer in bytes
 * @smart_dma_priority: hw priority of rect1 of multirect pipe
 * @max_per_pipe_bw: maximum allowable bandwidth of this pipe in kBps
 * @src_blk:
 * @scaler_blk:
 * @csc_blk:
@@ -403,7 +404,7 @@ struct sde_qos_lut_tbl {
 * @pcc_blk:
 * @igc_blk:
 * @format_list: Pointer to list of supported formats
 * @max_per_pipe_bw: maximum allowable bandwidth of this pipe in kBps
 * @virt_format_list: Pointer to list of supported formats for virtual planes
 */
struct sde_sspp_sub_blks {
	u32 maxlinewidth;
@@ -425,6 +426,7 @@ struct sde_sspp_sub_blks {
	struct sde_pp_blk igc_blk;

	const struct sde_format_extended *format_list;
	const struct sde_format_extended *virt_format_list;
};

/**
+8 −51
Original line number Diff line number Diff line
@@ -3634,7 +3634,6 @@ static void _sde_plane_install_properties(struct drm_plane *plane,
		{SDE_DRM_FB_SEC_DIR_TRANS, "sec_direct_translation"},
	};
	const struct sde_format_extended *format_list;
	struct sde_format_extended *virt_format_list = NULL;
	struct sde_kms_info *info;
	struct sde_plane *psde = to_sde_plane(plane);
	int zpos_max = 255;
@@ -3777,29 +3776,10 @@ static void _sde_plane_install_properties(struct drm_plane *plane,
		DRM_MODE_PROP_IMMUTABLE, PLANE_PROP_INFO);
	sde_kms_info_reset(info);

	if (!master_plane_id) {
		format_list = psde->pipe_sblk->format_list;

	if (master_plane_id) {
		int index, array_size;

		array_size = ARRAY_SIZE(plane_formats)
					+ ARRAY_SIZE(rgb_10bit_formats);
		virt_format_list = kcalloc(array_size,
				sizeof(struct sde_format_extended), GFP_KERNEL);
		if (!virt_format_list) {
			SDE_ERROR(
			"failed to allocate virtual pipe format list\n");
			return;
		}

		index = sde_copy_formats(virt_format_list, array_size,
				0, plane_formats, ARRAY_SIZE(plane_formats));
		sde_copy_formats(virt_format_list, array_size,
				index, rgb_10bit_formats,
				ARRAY_SIZE(rgb_10bit_formats));

		format_list = virt_format_list;

	} else {
		format_list = psde->pipe_sblk->virt_format_list;
		sde_kms_info_add_keyint(info, "primary_smart_plane_id",
						master_plane_id);
	}
@@ -3836,7 +3816,6 @@ static void _sde_plane_install_properties(struct drm_plane *plane,
			PLANE_PROP_INFO);

	kfree(info);
	kfree(virt_format_list);

	if (psde->features & BIT(SDE_SSPP_MEMCOLOR)) {
		snprintf(feature_name, sizeof(feature_name), "%s%d",
@@ -4584,7 +4563,6 @@ struct drm_plane *sde_plane_init(struct drm_device *dev,
{
	struct drm_plane *plane = NULL, *master_plane = NULL;
	const struct sde_format_extended *format_list;
	struct sde_format_extended *virt_format_list = NULL;
	struct sde_plane *psde;
	struct msm_drm_private *priv;
	struct sde_kms *kms;
@@ -4653,30 +4631,10 @@ struct drm_plane *sde_plane_init(struct drm_device *dev,
		goto clean_sspp;
	}

	if (!master_plane_id)
		format_list = psde->pipe_sblk->format_list;

	if (master_plane_id) {
		int index, array_size;

		array_size = ARRAY_SIZE(plane_formats)
					+ ARRAY_SIZE(rgb_10bit_formats);
		virt_format_list = kcalloc(array_size,
					sizeof(struct sde_format_extended),
					GFP_KERNEL);
		if (!virt_format_list) {
			SDE_ERROR(
			"failed to allocate virtual pipe format list\n");
			goto clean_sspp;
		}

		index = sde_copy_formats(virt_format_list, array_size,
				0, plane_formats, ARRAY_SIZE(plane_formats));
		sde_copy_formats(virt_format_list, array_size,
				index, rgb_10bit_formats,
				ARRAY_SIZE(rgb_10bit_formats));

		format_list = virt_format_list;
	}
	else
		format_list = psde->pipe_sblk->virt_format_list;

	psde->nformats = sde_populate_formats(format_list,
				psde->formats,
@@ -4725,6 +4683,5 @@ struct drm_plane *sde_plane_init(struct drm_device *dev,
clean_plane:
	kfree(psde);
exit:
	kfree(virt_format_list);
	return ERR_PTR(ret);
}