Merge branch 'msm-fixes-4.0' of git://people.freedesktop.org/~robclark/linux into drm-fixes
Fixup some fallout of the fallout of atomic dpms, few mdp5 cursor fixes, fix a leak in error path, and some fixes for kexec * 'msm-fixes-4.0' of git://people.freedesktop.org/~robclark/linux: drm/msm: kexec fixes drm/msm/mdp5: fix cursor blending drm/msm/mdp5: fix cursor ROI drm/msm/atomic: Don't leak atomic commit object when commit fails drm/msm/mdp5: Avoid flushing registers when CRTC is disabled drm/msm: update generated headers (add 6th lm.base entry) drm/msm/mdp5: fixup "drm/msm: fix fallout of atomic dpms changes"
This commit is contained in:
commit
4afb153477
|
@ -32,7 +32,10 @@ static void mdp4_irq_error_handler(struct mdp_irq *irq, uint32_t irqstatus)
|
|||
void mdp4_irq_preinstall(struct msm_kms *kms)
|
||||
{
|
||||
struct mdp4_kms *mdp4_kms = to_mdp4_kms(to_mdp_kms(kms));
|
||||
mdp4_enable(mdp4_kms);
|
||||
mdp4_write(mdp4_kms, REG_MDP4_INTR_CLEAR, 0xffffffff);
|
||||
mdp4_write(mdp4_kms, REG_MDP4_INTR_ENABLE, 0x00000000);
|
||||
mdp4_disable(mdp4_kms);
|
||||
}
|
||||
|
||||
int mdp4_irq_postinstall(struct msm_kms *kms)
|
||||
|
@ -53,7 +56,9 @@ int mdp4_irq_postinstall(struct msm_kms *kms)
|
|||
void mdp4_irq_uninstall(struct msm_kms *kms)
|
||||
{
|
||||
struct mdp4_kms *mdp4_kms = to_mdp4_kms(to_mdp_kms(kms));
|
||||
mdp4_enable(mdp4_kms);
|
||||
mdp4_write(mdp4_kms, REG_MDP4_INTR_ENABLE, 0x00000000);
|
||||
mdp4_disable(mdp4_kms);
|
||||
}
|
||||
|
||||
irqreturn_t mdp4_irq(struct msm_kms *kms)
|
||||
|
|
|
@ -8,17 +8,9 @@ http://github.com/freedreno/envytools/
|
|||
git clone https://github.com/freedreno/envytools.git
|
||||
|
||||
The rules-ng-ng source files this header was generated from are:
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/msm.xml ( 676 bytes, from 2014-12-05 15:34:49)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/freedreno_copyright.xml ( 1453 bytes, from 2013-03-31 16:51:27)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/mdp/mdp4.xml ( 20908 bytes, from 2014-12-08 16:13:00)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/mdp/mdp_common.xml ( 2357 bytes, from 2014-12-08 16:13:00)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/mdp/mdp5.xml ( 27208 bytes, from 2015-01-13 23:56:11)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/dsi/dsi.xml ( 11712 bytes, from 2013-08-17 17:13:43)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/dsi/sfpb.xml ( 344 bytes, from 2013-08-11 19:26:32)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/dsi/mmss_cc.xml ( 1686 bytes, from 2014-10-31 16:48:57)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/hdmi/qfprom.xml ( 600 bytes, from 2013-07-05 19:21:12)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/hdmi/hdmi.xml ( 26848 bytes, from 2015-01-13 23:55:57)
|
||||
- /home/robclark/src/freedreno/envytools/rnndb/edp/edp.xml ( 8253 bytes, from 2014-12-08 16:13:00)
|
||||
- /local/mnt2/workspace2/sviau/envytools/rnndb/mdp/mdp5.xml ( 27229 bytes, from 2015-02-10 17:00:41)
|
||||
- /local/mnt2/workspace2/sviau/envytools/rnndb/freedreno_copyright.xml ( 1453 bytes, from 2014-06-02 18:31:15)
|
||||
- /local/mnt2/workspace2/sviau/envytools/rnndb/mdp/mdp_common.xml ( 2357 bytes, from 2015-01-23 16:20:19)
|
||||
|
||||
Copyright (C) 2013-2015 by the following authors:
|
||||
- Rob Clark <robdclark@gmail.com> (robclark)
|
||||
|
@ -910,6 +902,7 @@ static inline uint32_t __offset_LM(uint32_t idx)
|
|||
case 2: return (mdp5_cfg->lm.base[2]);
|
||||
case 3: return (mdp5_cfg->lm.base[3]);
|
||||
case 4: return (mdp5_cfg->lm.base[4]);
|
||||
case 5: return (mdp5_cfg->lm.base[5]);
|
||||
default: return INVALID_IDX(idx);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -62,8 +62,8 @@ struct mdp5_crtc {
|
|||
|
||||
/* current cursor being scanned out: */
|
||||
struct drm_gem_object *scanout_bo;
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
uint32_t width, height;
|
||||
uint32_t x, y;
|
||||
} cursor;
|
||||
};
|
||||
#define to_mdp5_crtc(x) container_of(x, struct mdp5_crtc, base)
|
||||
|
@ -103,8 +103,8 @@ static void crtc_flush_all(struct drm_crtc *crtc)
|
|||
struct drm_plane *plane;
|
||||
uint32_t flush_mask = 0;
|
||||
|
||||
/* we could have already released CTL in the disable path: */
|
||||
if (!mdp5_crtc->ctl)
|
||||
/* this should not happen: */
|
||||
if (WARN_ON(!mdp5_crtc->ctl))
|
||||
return;
|
||||
|
||||
drm_atomic_crtc_for_each_plane(plane, crtc) {
|
||||
|
@ -143,6 +143,11 @@ static void complete_flip(struct drm_crtc *crtc, struct drm_file *file)
|
|||
drm_atomic_crtc_for_each_plane(plane, crtc) {
|
||||
mdp5_plane_complete_flip(plane);
|
||||
}
|
||||
|
||||
if (mdp5_crtc->ctl && !crtc->state->enable) {
|
||||
mdp5_ctl_release(mdp5_crtc->ctl);
|
||||
mdp5_crtc->ctl = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static void unref_cursor_worker(struct drm_flip_work *work, void *val)
|
||||
|
@ -386,14 +391,17 @@ static void mdp5_crtc_atomic_flush(struct drm_crtc *crtc)
|
|||
mdp5_crtc->event = crtc->state->event;
|
||||
spin_unlock_irqrestore(&dev->event_lock, flags);
|
||||
|
||||
/*
|
||||
* If no CTL has been allocated in mdp5_crtc_atomic_check(),
|
||||
* it means we are trying to flush a CRTC whose state is disabled:
|
||||
* nothing else needs to be done.
|
||||
*/
|
||||
if (unlikely(!mdp5_crtc->ctl))
|
||||
return;
|
||||
|
||||
blend_setup(crtc);
|
||||
crtc_flush_all(crtc);
|
||||
request_pending(crtc, PENDING_FLIP);
|
||||
|
||||
if (mdp5_crtc->ctl && !crtc->state->enable) {
|
||||
mdp5_ctl_release(mdp5_crtc->ctl);
|
||||
mdp5_crtc->ctl = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static int mdp5_crtc_set_property(struct drm_crtc *crtc,
|
||||
|
@ -403,6 +411,32 @@ static int mdp5_crtc_set_property(struct drm_crtc *crtc,
|
|||
return -EINVAL;
|
||||
}
|
||||
|
||||
static void get_roi(struct drm_crtc *crtc, uint32_t *roi_w, uint32_t *roi_h)
|
||||
{
|
||||
struct mdp5_crtc *mdp5_crtc = to_mdp5_crtc(crtc);
|
||||
uint32_t xres = crtc->mode.hdisplay;
|
||||
uint32_t yres = crtc->mode.vdisplay;
|
||||
|
||||
/*
|
||||
* Cursor Region Of Interest (ROI) is a plane read from cursor
|
||||
* buffer to render. The ROI region is determined by the visibility of
|
||||
* the cursor point. In the default Cursor image the cursor point will
|
||||
* be at the top left of the cursor image, unless it is specified
|
||||
* otherwise using hotspot feature.
|
||||
*
|
||||
* If the cursor point reaches the right (xres - x < cursor.width) or
|
||||
* bottom (yres - y < cursor.height) boundary of the screen, then ROI
|
||||
* width and ROI height need to be evaluated to crop the cursor image
|
||||
* accordingly.
|
||||
* (xres-x) will be new cursor width when x > (xres - cursor.width)
|
||||
* (yres-y) will be new cursor height when y > (yres - cursor.height)
|
||||
*/
|
||||
*roi_w = min(mdp5_crtc->cursor.width, xres -
|
||||
mdp5_crtc->cursor.x);
|
||||
*roi_h = min(mdp5_crtc->cursor.height, yres -
|
||||
mdp5_crtc->cursor.y);
|
||||
}
|
||||
|
||||
static int mdp5_crtc_cursor_set(struct drm_crtc *crtc,
|
||||
struct drm_file *file, uint32_t handle,
|
||||
uint32_t width, uint32_t height)
|
||||
|
@ -416,6 +450,7 @@ static int mdp5_crtc_cursor_set(struct drm_crtc *crtc,
|
|||
unsigned int depth;
|
||||
enum mdp5_cursor_alpha cur_alpha = CURSOR_ALPHA_PER_PIXEL;
|
||||
uint32_t flush_mask = mdp_ctl_flush_mask_cursor(0);
|
||||
uint32_t roi_w, roi_h;
|
||||
unsigned long flags;
|
||||
|
||||
if ((width > CURSOR_WIDTH) || (height > CURSOR_HEIGHT)) {
|
||||
|
@ -446,6 +481,12 @@ static int mdp5_crtc_cursor_set(struct drm_crtc *crtc,
|
|||
spin_lock_irqsave(&mdp5_crtc->cursor.lock, flags);
|
||||
old_bo = mdp5_crtc->cursor.scanout_bo;
|
||||
|
||||
mdp5_crtc->cursor.scanout_bo = cursor_bo;
|
||||
mdp5_crtc->cursor.width = width;
|
||||
mdp5_crtc->cursor.height = height;
|
||||
|
||||
get_roi(crtc, &roi_w, &roi_h);
|
||||
|
||||
mdp5_write(mdp5_kms, REG_MDP5_LM_CURSOR_STRIDE(lm), stride);
|
||||
mdp5_write(mdp5_kms, REG_MDP5_LM_CURSOR_FORMAT(lm),
|
||||
MDP5_LM_CURSOR_FORMAT_FORMAT(CURSOR_FMT_ARGB8888));
|
||||
|
@ -453,19 +494,14 @@ static int mdp5_crtc_cursor_set(struct drm_crtc *crtc,
|
|||
MDP5_LM_CURSOR_IMG_SIZE_SRC_H(height) |
|
||||
MDP5_LM_CURSOR_IMG_SIZE_SRC_W(width));
|
||||
mdp5_write(mdp5_kms, REG_MDP5_LM_CURSOR_SIZE(lm),
|
||||
MDP5_LM_CURSOR_SIZE_ROI_H(height) |
|
||||
MDP5_LM_CURSOR_SIZE_ROI_W(width));
|
||||
MDP5_LM_CURSOR_SIZE_ROI_H(roi_h) |
|
||||
MDP5_LM_CURSOR_SIZE_ROI_W(roi_w));
|
||||
mdp5_write(mdp5_kms, REG_MDP5_LM_CURSOR_BASE_ADDR(lm), cursor_addr);
|
||||
|
||||
|
||||
blendcfg = MDP5_LM_CURSOR_BLEND_CONFIG_BLEND_EN;
|
||||
blendcfg |= MDP5_LM_CURSOR_BLEND_CONFIG_BLEND_TRANSP_EN;
|
||||
blendcfg |= MDP5_LM_CURSOR_BLEND_CONFIG_BLEND_ALPHA_SEL(cur_alpha);
|
||||
mdp5_write(mdp5_kms, REG_MDP5_LM_CURSOR_BLEND_CONFIG(lm), blendcfg);
|
||||
|
||||
mdp5_crtc->cursor.scanout_bo = cursor_bo;
|
||||
mdp5_crtc->cursor.width = width;
|
||||
mdp5_crtc->cursor.height = height;
|
||||
spin_unlock_irqrestore(&mdp5_crtc->cursor.lock, flags);
|
||||
|
||||
ret = mdp5_ctl_set_cursor(mdp5_crtc->ctl, true);
|
||||
|
@ -489,31 +525,18 @@ static int mdp5_crtc_cursor_move(struct drm_crtc *crtc, int x, int y)
|
|||
struct mdp5_kms *mdp5_kms = get_kms(crtc);
|
||||
struct mdp5_crtc *mdp5_crtc = to_mdp5_crtc(crtc);
|
||||
uint32_t flush_mask = mdp_ctl_flush_mask_cursor(0);
|
||||
uint32_t xres = crtc->mode.hdisplay;
|
||||
uint32_t yres = crtc->mode.vdisplay;
|
||||
uint32_t roi_w;
|
||||
uint32_t roi_h;
|
||||
unsigned long flags;
|
||||
|
||||
x = (x > 0) ? x : 0;
|
||||
y = (y > 0) ? y : 0;
|
||||
/* In case the CRTC is disabled, just drop the cursor update */
|
||||
if (unlikely(!crtc->state->enable))
|
||||
return 0;
|
||||
|
||||
/*
|
||||
* Cursor Region Of Interest (ROI) is a plane read from cursor
|
||||
* buffer to render. The ROI region is determined by the visiblity of
|
||||
* the cursor point. In the default Cursor image the cursor point will
|
||||
* be at the top left of the cursor image, unless it is specified
|
||||
* otherwise using hotspot feature.
|
||||
*
|
||||
* If the cursor point reaches the right (xres - x < cursor.width) or
|
||||
* bottom (yres - y < cursor.height) boundary of the screen, then ROI
|
||||
* width and ROI height need to be evaluated to crop the cursor image
|
||||
* accordingly.
|
||||
* (xres-x) will be new cursor width when x > (xres - cursor.width)
|
||||
* (yres-y) will be new cursor height when y > (yres - cursor.height)
|
||||
*/
|
||||
roi_w = min(mdp5_crtc->cursor.width, xres - x);
|
||||
roi_h = min(mdp5_crtc->cursor.height, yres - y);
|
||||
mdp5_crtc->cursor.x = x = max(x, 0);
|
||||
mdp5_crtc->cursor.y = y = max(y, 0);
|
||||
|
||||
get_roi(crtc, &roi_w, &roi_h);
|
||||
|
||||
spin_lock_irqsave(&mdp5_crtc->cursor.lock, flags);
|
||||
mdp5_write(mdp5_kms, REG_MDP5_LM_CURSOR_SIZE(mdp5_crtc->lm),
|
||||
|
@ -544,8 +567,8 @@ static const struct drm_crtc_funcs mdp5_crtc_funcs = {
|
|||
static const struct drm_crtc_helper_funcs mdp5_crtc_helper_funcs = {
|
||||
.mode_fixup = mdp5_crtc_mode_fixup,
|
||||
.mode_set_nofb = mdp5_crtc_mode_set_nofb,
|
||||
.prepare = mdp5_crtc_disable,
|
||||
.commit = mdp5_crtc_enable,
|
||||
.disable = mdp5_crtc_disable,
|
||||
.enable = mdp5_crtc_enable,
|
||||
.atomic_check = mdp5_crtc_atomic_check,
|
||||
.atomic_begin = mdp5_crtc_atomic_begin,
|
||||
.atomic_flush = mdp5_crtc_atomic_flush,
|
||||
|
|
|
@ -267,14 +267,14 @@ static void mdp5_encoder_enable(struct drm_encoder *encoder)
|
|||
mdp5_write(mdp5_kms, REG_MDP5_INTF_TIMING_ENGINE_EN(intf), 1);
|
||||
spin_unlock_irqrestore(&mdp5_encoder->intf_lock, flags);
|
||||
|
||||
mdp5_encoder->enabled = false;
|
||||
mdp5_encoder->enabled = true;
|
||||
}
|
||||
|
||||
static const struct drm_encoder_helper_funcs mdp5_encoder_helper_funcs = {
|
||||
.mode_fixup = mdp5_encoder_mode_fixup,
|
||||
.mode_set = mdp5_encoder_mode_set,
|
||||
.prepare = mdp5_encoder_disable,
|
||||
.commit = mdp5_encoder_enable,
|
||||
.disable = mdp5_encoder_disable,
|
||||
.enable = mdp5_encoder_enable,
|
||||
};
|
||||
|
||||
/* initialize encoder */
|
||||
|
|
|
@ -34,7 +34,10 @@ static void mdp5_irq_error_handler(struct mdp_irq *irq, uint32_t irqstatus)
|
|||
void mdp5_irq_preinstall(struct msm_kms *kms)
|
||||
{
|
||||
struct mdp5_kms *mdp5_kms = to_mdp5_kms(to_mdp_kms(kms));
|
||||
mdp5_enable(mdp5_kms);
|
||||
mdp5_write(mdp5_kms, REG_MDP5_INTR_CLEAR, 0xffffffff);
|
||||
mdp5_write(mdp5_kms, REG_MDP5_INTR_EN, 0x00000000);
|
||||
mdp5_disable(mdp5_kms);
|
||||
}
|
||||
|
||||
int mdp5_irq_postinstall(struct msm_kms *kms)
|
||||
|
@ -57,7 +60,9 @@ int mdp5_irq_postinstall(struct msm_kms *kms)
|
|||
void mdp5_irq_uninstall(struct msm_kms *kms)
|
||||
{
|
||||
struct mdp5_kms *mdp5_kms = to_mdp5_kms(to_mdp_kms(kms));
|
||||
mdp5_enable(mdp5_kms);
|
||||
mdp5_write(mdp5_kms, REG_MDP5_INTR_EN, 0x00000000);
|
||||
mdp5_disable(mdp5_kms);
|
||||
}
|
||||
|
||||
static void mdp5_irq_mdp(struct mdp_kms *mdp_kms)
|
||||
|
|
|
@ -219,8 +219,10 @@ int msm_atomic_commit(struct drm_device *dev,
|
|||
* mark our set of crtc's as busy:
|
||||
*/
|
||||
ret = start_atomic(dev->dev_private, c->crtc_mask);
|
||||
if (ret)
|
||||
if (ret) {
|
||||
kfree(c);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* This is the point of no return - everything below never fails except
|
||||
|
|
Loading…
Reference in New Issue