mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-12-28 12:37:55 -05:00
drm/msm: Stop passing vm to msm_framebuffer
The fb only deals with kms->vm, so make that explicit. This will start letting us refcount the # of times the fb is pinned, so we can only unpin the vma after last user of the fb is done. Having a single reference count really only works if there is only a single vm. Signed-off-by: Rob Clark <robin.clark@oss.qualcomm.com> Tested-by: Antonino Maniscalco <antomani103@gmail.com> Reviewed-by: Antonino Maniscalco <antomani103@gmail.com> Patchwork: https://patchwork.freedesktop.org/patch/661476/
This commit is contained in:
@@ -563,7 +563,6 @@ static void dpu_encoder_phys_wb_prepare_wb_job(struct dpu_encoder_phys *phys_enc
|
||||
struct drm_writeback_job *job)
|
||||
{
|
||||
const struct msm_format *format;
|
||||
struct msm_gem_vm *vm;
|
||||
struct dpu_hw_wb_cfg *wb_cfg;
|
||||
int ret;
|
||||
struct dpu_encoder_phys_wb *wb_enc = to_dpu_encoder_phys_wb(phys_enc);
|
||||
@@ -573,13 +572,12 @@ static void dpu_encoder_phys_wb_prepare_wb_job(struct dpu_encoder_phys *phys_enc
|
||||
|
||||
wb_enc->wb_job = job;
|
||||
wb_enc->wb_conn = job->connector;
|
||||
vm = phys_enc->dpu_kms->base.vm;
|
||||
|
||||
wb_cfg = &wb_enc->wb_cfg;
|
||||
|
||||
memset(wb_cfg, 0, sizeof(struct dpu_hw_wb_cfg));
|
||||
|
||||
ret = msm_framebuffer_prepare(job->fb, vm, false);
|
||||
ret = msm_framebuffer_prepare(job->fb, false);
|
||||
if (ret) {
|
||||
DPU_ERROR("prep fb failed, %d\n", ret);
|
||||
return;
|
||||
@@ -593,7 +591,7 @@ static void dpu_encoder_phys_wb_prepare_wb_job(struct dpu_encoder_phys *phys_enc
|
||||
return;
|
||||
}
|
||||
|
||||
dpu_format_populate_addrs(vm, job->fb, &wb_cfg->dest);
|
||||
dpu_format_populate_addrs(job->fb, &wb_cfg->dest);
|
||||
|
||||
wb_cfg->dest.width = job->fb->width;
|
||||
wb_cfg->dest.height = job->fb->height;
|
||||
@@ -616,14 +614,11 @@ static void dpu_encoder_phys_wb_cleanup_wb_job(struct dpu_encoder_phys *phys_enc
|
||||
struct drm_writeback_job *job)
|
||||
{
|
||||
struct dpu_encoder_phys_wb *wb_enc = to_dpu_encoder_phys_wb(phys_enc);
|
||||
struct msm_gem_vm *vm;
|
||||
|
||||
if (!job->fb)
|
||||
return;
|
||||
|
||||
vm = phys_enc->dpu_kms->base.vm;
|
||||
|
||||
msm_framebuffer_cleanup(job->fb, vm, false);
|
||||
msm_framebuffer_cleanup(job->fb, false);
|
||||
wb_enc->wb_job = NULL;
|
||||
wb_enc->wb_conn = NULL;
|
||||
}
|
||||
|
||||
@@ -274,15 +274,14 @@ int dpu_format_populate_plane_sizes(
|
||||
return _dpu_format_populate_plane_sizes_linear(fmt, fb, layout);
|
||||
}
|
||||
|
||||
static void _dpu_format_populate_addrs_ubwc(struct msm_gem_vm *vm,
|
||||
struct drm_framebuffer *fb,
|
||||
static void _dpu_format_populate_addrs_ubwc(struct drm_framebuffer *fb,
|
||||
struct dpu_hw_fmt_layout *layout)
|
||||
{
|
||||
const struct msm_format *fmt;
|
||||
uint32_t base_addr = 0;
|
||||
bool meta;
|
||||
|
||||
base_addr = msm_framebuffer_iova(fb, vm, 0);
|
||||
base_addr = msm_framebuffer_iova(fb, 0);
|
||||
|
||||
fmt = msm_framebuffer_format(fb);
|
||||
meta = MSM_FORMAT_IS_UBWC(fmt);
|
||||
@@ -355,26 +354,23 @@ static void _dpu_format_populate_addrs_ubwc(struct msm_gem_vm *vm,
|
||||
}
|
||||
}
|
||||
|
||||
static void _dpu_format_populate_addrs_linear(struct msm_gem_vm *vm,
|
||||
struct drm_framebuffer *fb,
|
||||
static void _dpu_format_populate_addrs_linear(struct drm_framebuffer *fb,
|
||||
struct dpu_hw_fmt_layout *layout)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
/* Populate addresses for simple formats here */
|
||||
for (i = 0; i < layout->num_planes; ++i)
|
||||
layout->plane_addr[i] = msm_framebuffer_iova(fb, vm, i);
|
||||
layout->plane_addr[i] = msm_framebuffer_iova(fb, i);
|
||||
}
|
||||
|
||||
/**
|
||||
* dpu_format_populate_addrs - populate buffer addresses based on
|
||||
* mmu, fb, and format found in the fb
|
||||
* @vm: address space pointer
|
||||
* @fb: framebuffer pointer
|
||||
* @layout: format layout structure to populate
|
||||
*/
|
||||
void dpu_format_populate_addrs(struct msm_gem_vm *vm,
|
||||
struct drm_framebuffer *fb,
|
||||
void dpu_format_populate_addrs(struct drm_framebuffer *fb,
|
||||
struct dpu_hw_fmt_layout *layout)
|
||||
{
|
||||
const struct msm_format *fmt;
|
||||
@@ -384,7 +380,7 @@ void dpu_format_populate_addrs(struct msm_gem_vm *vm,
|
||||
/* Populate the addresses given the fb */
|
||||
if (MSM_FORMAT_IS_UBWC(fmt) ||
|
||||
MSM_FORMAT_IS_TILE(fmt))
|
||||
_dpu_format_populate_addrs_ubwc(vm, fb, layout);
|
||||
_dpu_format_populate_addrs_ubwc(fb, layout);
|
||||
else
|
||||
_dpu_format_populate_addrs_linear(vm, fb, layout);
|
||||
_dpu_format_populate_addrs_linear(fb, layout);
|
||||
}
|
||||
|
||||
@@ -31,8 +31,7 @@ static inline bool dpu_find_format(u32 format, const u32 *supported_formats,
|
||||
return false;
|
||||
}
|
||||
|
||||
void dpu_format_populate_addrs(struct msm_gem_vm *vm,
|
||||
struct drm_framebuffer *fb,
|
||||
void dpu_format_populate_addrs(struct drm_framebuffer *fb,
|
||||
struct dpu_hw_fmt_layout *layout);
|
||||
|
||||
int dpu_format_populate_plane_sizes(
|
||||
|
||||
@@ -646,7 +646,6 @@ static int dpu_plane_prepare_fb(struct drm_plane *plane,
|
||||
struct drm_framebuffer *fb = new_state->fb;
|
||||
struct dpu_plane *pdpu = to_dpu_plane(plane);
|
||||
struct dpu_plane_state *pstate = to_dpu_plane_state(new_state);
|
||||
struct dpu_kms *kms = _dpu_plane_get_kms(&pdpu->base);
|
||||
int ret;
|
||||
|
||||
if (!new_state->fb)
|
||||
@@ -654,9 +653,6 @@ static int dpu_plane_prepare_fb(struct drm_plane *plane,
|
||||
|
||||
DPU_DEBUG_PLANE(pdpu, "FB[%u]\n", fb->base.id);
|
||||
|
||||
/* cache vm */
|
||||
pstate->vm = kms->base.vm;
|
||||
|
||||
/*
|
||||
* TODO: Need to sort out the msm_framebuffer_prepare() call below so
|
||||
* we can use msm_atomic_prepare_fb() instead of doing the
|
||||
@@ -664,13 +660,10 @@ static int dpu_plane_prepare_fb(struct drm_plane *plane,
|
||||
*/
|
||||
drm_gem_plane_helper_prepare_fb(plane, new_state);
|
||||
|
||||
if (pstate->vm) {
|
||||
ret = msm_framebuffer_prepare(new_state->fb,
|
||||
pstate->vm, pstate->needs_dirtyfb);
|
||||
if (ret) {
|
||||
DPU_ERROR("failed to prepare framebuffer\n");
|
||||
return ret;
|
||||
}
|
||||
ret = msm_framebuffer_prepare(new_state->fb, pstate->needs_dirtyfb);
|
||||
if (ret) {
|
||||
DPU_ERROR("failed to prepare framebuffer\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
return 0;
|
||||
@@ -689,8 +682,7 @@ static void dpu_plane_cleanup_fb(struct drm_plane *plane,
|
||||
|
||||
DPU_DEBUG_PLANE(pdpu, "FB[%u]\n", old_state->fb->base.id);
|
||||
|
||||
msm_framebuffer_cleanup(old_state->fb, old_pstate->vm,
|
||||
old_pstate->needs_dirtyfb);
|
||||
msm_framebuffer_cleanup(old_state->fb, old_pstate->needs_dirtyfb);
|
||||
}
|
||||
|
||||
static int dpu_plane_check_inline_rotation(struct dpu_plane *pdpu,
|
||||
@@ -1457,7 +1449,7 @@ static void dpu_plane_sspp_atomic_update(struct drm_plane *plane,
|
||||
pstate->needs_qos_remap |= (is_rt_pipe != pdpu->is_rt_pipe);
|
||||
pdpu->is_rt_pipe = is_rt_pipe;
|
||||
|
||||
dpu_format_populate_addrs(pstate->vm, new_state->fb, &pstate->layout);
|
||||
dpu_format_populate_addrs(new_state->fb, &pstate->layout);
|
||||
|
||||
DPU_DEBUG_PLANE(pdpu, "FB[%u] " DRM_RECT_FP_FMT "->crtc%u " DRM_RECT_FMT
|
||||
", %p4cc ubwc %d\n", fb->base.id, DRM_RECT_FP_ARG(&state->src),
|
||||
|
||||
@@ -17,7 +17,6 @@
|
||||
/**
|
||||
* struct dpu_plane_state: Define dpu extension of drm plane state object
|
||||
* @base: base drm plane state object
|
||||
* @vm: pointer to address space for input/output buffers
|
||||
* @pipe: software pipe description
|
||||
* @r_pipe: software pipe description of the second pipe
|
||||
* @pipe_cfg: software pipe configuration
|
||||
@@ -34,7 +33,6 @@
|
||||
*/
|
||||
struct dpu_plane_state {
|
||||
struct drm_plane_state base;
|
||||
struct msm_gem_vm *vm;
|
||||
struct dpu_sw_pipe pipe;
|
||||
struct dpu_sw_pipe r_pipe;
|
||||
struct dpu_sw_pipe_cfg pipe_cfg;
|
||||
|
||||
@@ -79,30 +79,25 @@ static const struct drm_plane_funcs mdp4_plane_funcs = {
|
||||
static int mdp4_plane_prepare_fb(struct drm_plane *plane,
|
||||
struct drm_plane_state *new_state)
|
||||
{
|
||||
struct msm_drm_private *priv = plane->dev->dev_private;
|
||||
struct msm_kms *kms = priv->kms;
|
||||
|
||||
if (!new_state->fb)
|
||||
return 0;
|
||||
|
||||
drm_gem_plane_helper_prepare_fb(plane, new_state);
|
||||
|
||||
return msm_framebuffer_prepare(new_state->fb, kms->vm, false);
|
||||
return msm_framebuffer_prepare(new_state->fb, false);
|
||||
}
|
||||
|
||||
static void mdp4_plane_cleanup_fb(struct drm_plane *plane,
|
||||
struct drm_plane_state *old_state)
|
||||
{
|
||||
struct mdp4_plane *mdp4_plane = to_mdp4_plane(plane);
|
||||
struct mdp4_kms *mdp4_kms = get_kms(plane);
|
||||
struct msm_kms *kms = &mdp4_kms->base.base;
|
||||
struct drm_framebuffer *fb = old_state->fb;
|
||||
|
||||
if (!fb)
|
||||
return;
|
||||
|
||||
DBG("%s: cleanup: FB[%u]", mdp4_plane->name, fb->base.id);
|
||||
msm_framebuffer_cleanup(fb, kms->vm, false);
|
||||
msm_framebuffer_cleanup(fb, false);
|
||||
}
|
||||
|
||||
|
||||
@@ -141,7 +136,6 @@ static void mdp4_plane_set_scanout(struct drm_plane *plane,
|
||||
{
|
||||
struct mdp4_plane *mdp4_plane = to_mdp4_plane(plane);
|
||||
struct mdp4_kms *mdp4_kms = get_kms(plane);
|
||||
struct msm_kms *kms = &mdp4_kms->base.base;
|
||||
enum mdp4_pipe pipe = mdp4_plane->pipe;
|
||||
|
||||
mdp4_write(mdp4_kms, REG_MDP4_PIPE_SRC_STRIDE_A(pipe),
|
||||
@@ -153,13 +147,13 @@ static void mdp4_plane_set_scanout(struct drm_plane *plane,
|
||||
MDP4_PIPE_SRC_STRIDE_B_P3(fb->pitches[3]));
|
||||
|
||||
mdp4_write(mdp4_kms, REG_MDP4_PIPE_SRCP0_BASE(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 0));
|
||||
msm_framebuffer_iova(fb, 0));
|
||||
mdp4_write(mdp4_kms, REG_MDP4_PIPE_SRCP1_BASE(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 1));
|
||||
msm_framebuffer_iova(fb, 1));
|
||||
mdp4_write(mdp4_kms, REG_MDP4_PIPE_SRCP2_BASE(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 2));
|
||||
msm_framebuffer_iova(fb, 2));
|
||||
mdp4_write(mdp4_kms, REG_MDP4_PIPE_SRCP3_BASE(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 3));
|
||||
msm_framebuffer_iova(fb, 3));
|
||||
}
|
||||
|
||||
static void mdp4_write_csc_config(struct mdp4_kms *mdp4_kms,
|
||||
|
||||
@@ -135,8 +135,6 @@ static const struct drm_plane_funcs mdp5_plane_funcs = {
|
||||
static int mdp5_plane_prepare_fb(struct drm_plane *plane,
|
||||
struct drm_plane_state *new_state)
|
||||
{
|
||||
struct msm_drm_private *priv = plane->dev->dev_private;
|
||||
struct msm_kms *kms = priv->kms;
|
||||
bool needs_dirtyfb = to_mdp5_plane_state(new_state)->needs_dirtyfb;
|
||||
|
||||
if (!new_state->fb)
|
||||
@@ -144,14 +142,12 @@ static int mdp5_plane_prepare_fb(struct drm_plane *plane,
|
||||
|
||||
drm_gem_plane_helper_prepare_fb(plane, new_state);
|
||||
|
||||
return msm_framebuffer_prepare(new_state->fb, kms->vm, needs_dirtyfb);
|
||||
return msm_framebuffer_prepare(new_state->fb, needs_dirtyfb);
|
||||
}
|
||||
|
||||
static void mdp5_plane_cleanup_fb(struct drm_plane *plane,
|
||||
struct drm_plane_state *old_state)
|
||||
{
|
||||
struct mdp5_kms *mdp5_kms = get_kms(plane);
|
||||
struct msm_kms *kms = &mdp5_kms->base.base;
|
||||
struct drm_framebuffer *fb = old_state->fb;
|
||||
bool needed_dirtyfb = to_mdp5_plane_state(old_state)->needs_dirtyfb;
|
||||
|
||||
@@ -159,7 +155,7 @@ static void mdp5_plane_cleanup_fb(struct drm_plane *plane,
|
||||
return;
|
||||
|
||||
DBG("%s: cleanup: FB[%u]", plane->name, fb->base.id);
|
||||
msm_framebuffer_cleanup(fb, kms->vm, needed_dirtyfb);
|
||||
msm_framebuffer_cleanup(fb, needed_dirtyfb);
|
||||
}
|
||||
|
||||
static int mdp5_plane_atomic_check_with_state(struct drm_crtc_state *crtc_state,
|
||||
@@ -467,8 +463,6 @@ static void set_scanout_locked(struct mdp5_kms *mdp5_kms,
|
||||
enum mdp5_pipe pipe,
|
||||
struct drm_framebuffer *fb)
|
||||
{
|
||||
struct msm_kms *kms = &mdp5_kms->base.base;
|
||||
|
||||
mdp5_write(mdp5_kms, REG_MDP5_PIPE_SRC_STRIDE_A(pipe),
|
||||
MDP5_PIPE_SRC_STRIDE_A_P0(fb->pitches[0]) |
|
||||
MDP5_PIPE_SRC_STRIDE_A_P1(fb->pitches[1]));
|
||||
@@ -478,13 +472,13 @@ static void set_scanout_locked(struct mdp5_kms *mdp5_kms,
|
||||
MDP5_PIPE_SRC_STRIDE_B_P3(fb->pitches[3]));
|
||||
|
||||
mdp5_write(mdp5_kms, REG_MDP5_PIPE_SRC0_ADDR(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 0));
|
||||
msm_framebuffer_iova(fb, 0));
|
||||
mdp5_write(mdp5_kms, REG_MDP5_PIPE_SRC1_ADDR(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 1));
|
||||
msm_framebuffer_iova(fb, 1));
|
||||
mdp5_write(mdp5_kms, REG_MDP5_PIPE_SRC2_ADDR(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 2));
|
||||
msm_framebuffer_iova(fb, 2));
|
||||
mdp5_write(mdp5_kms, REG_MDP5_PIPE_SRC3_ADDR(pipe),
|
||||
msm_framebuffer_iova(fb, kms->vm, 3));
|
||||
msm_framebuffer_iova(fb, 3));
|
||||
}
|
||||
|
||||
/* Note: mdp5_plane->pipe_lock must be locked */
|
||||
|
||||
@@ -274,12 +274,9 @@ struct drm_gem_object *msm_gem_prime_import_sg_table(struct drm_device *dev,
|
||||
int msm_gem_prime_pin(struct drm_gem_object *obj);
|
||||
void msm_gem_prime_unpin(struct drm_gem_object *obj);
|
||||
|
||||
int msm_framebuffer_prepare(struct drm_framebuffer *fb,
|
||||
struct msm_gem_vm *vm, bool needs_dirtyfb);
|
||||
void msm_framebuffer_cleanup(struct drm_framebuffer *fb,
|
||||
struct msm_gem_vm *vm, bool needed_dirtyfb);
|
||||
uint32_t msm_framebuffer_iova(struct drm_framebuffer *fb,
|
||||
struct msm_gem_vm *vm, int plane);
|
||||
int msm_framebuffer_prepare(struct drm_framebuffer *fb, bool needs_dirtyfb);
|
||||
void msm_framebuffer_cleanup(struct drm_framebuffer *fb, bool needed_dirtyfb);
|
||||
uint32_t msm_framebuffer_iova(struct drm_framebuffer *fb, int plane);
|
||||
struct drm_gem_object *msm_framebuffer_bo(struct drm_framebuffer *fb, int plane);
|
||||
const struct msm_format *msm_framebuffer_format(struct drm_framebuffer *fb);
|
||||
struct drm_framebuffer *msm_framebuffer_create(struct drm_device *dev,
|
||||
|
||||
@@ -75,10 +75,10 @@ void msm_framebuffer_describe(struct drm_framebuffer *fb, struct seq_file *m)
|
||||
|
||||
/* prepare/pin all the fb's bo's for scanout.
|
||||
*/
|
||||
int msm_framebuffer_prepare(struct drm_framebuffer *fb,
|
||||
struct msm_gem_vm *vm,
|
||||
bool needs_dirtyfb)
|
||||
int msm_framebuffer_prepare(struct drm_framebuffer *fb, bool needs_dirtyfb)
|
||||
{
|
||||
struct msm_drm_private *priv = fb->dev->dev_private;
|
||||
struct msm_gem_vm *vm = priv->kms->vm;
|
||||
struct msm_framebuffer *msm_fb = to_msm_framebuffer(fb);
|
||||
int ret, i, n = fb->format->num_planes;
|
||||
|
||||
@@ -98,10 +98,10 @@ int msm_framebuffer_prepare(struct drm_framebuffer *fb,
|
||||
return 0;
|
||||
}
|
||||
|
||||
void msm_framebuffer_cleanup(struct drm_framebuffer *fb,
|
||||
struct msm_gem_vm *vm,
|
||||
bool needed_dirtyfb)
|
||||
void msm_framebuffer_cleanup(struct drm_framebuffer *fb, bool needed_dirtyfb)
|
||||
{
|
||||
struct msm_drm_private *priv = fb->dev->dev_private;
|
||||
struct msm_gem_vm *vm = priv->kms->vm;
|
||||
struct msm_framebuffer *msm_fb = to_msm_framebuffer(fb);
|
||||
int i, n = fb->format->num_planes;
|
||||
|
||||
@@ -115,8 +115,7 @@ void msm_framebuffer_cleanup(struct drm_framebuffer *fb,
|
||||
memset(msm_fb->iova, 0, sizeof(msm_fb->iova));
|
||||
}
|
||||
|
||||
uint32_t msm_framebuffer_iova(struct drm_framebuffer *fb,
|
||||
struct msm_gem_vm *vm, int plane)
|
||||
uint32_t msm_framebuffer_iova(struct drm_framebuffer *fb, int plane)
|
||||
{
|
||||
struct msm_framebuffer *msm_fb = to_msm_framebuffer(fb);
|
||||
return msm_fb->iova[plane] + fb->offsets[plane];
|
||||
|
||||
Reference in New Issue
Block a user