Merge branch 'primary-plane' of git://people.freedesktop.org/~robclark/linux into drm-next
Here's the latest iteration of the universal planes work, which I believe is finally ready for merging. Aside from the minor driver patches to use the new drm_for_each_legacy_plane() macro for plane loops, these should all have an r-b from Rob Clark now. Actual userspace-visibility is currently hidden behind a drm.universal_planes module parameter so that we can do some experimental testing of this before flipping it on universally. * 'primary-plane' of git://people.freedesktop.org/~robclark/linux: drm/doc: Update plane documentation and add plane helper library drm: Allow userspace to ask for universal plane list (v2) drm: Remove unused drm_crtc->fb drm: Replace crtc fb with primary plane fb (v3) drm/msm: Switch to universal plane API's drm: Add drm_crtc_init_with_planes() (v2) drm: Add plane type property (v2) drm: Add drm_universal_plane_init() drm: Add primary plane helpers (v3) drm: Make drm_crtc_check_viewport non-static drm/shmobile: Restrict plane loops to only operate on legacy planes drm/i915: Restrict plane loops to only operate on overlay planes (v2) drm/exynos: Restrict plane loops to only operate on overlay planes (v2) drm: Add support for multiple plane types (v2)
This commit is contained in:
commit
2844ea3f25
|
@ -1194,7 +1194,7 @@ int max_width, max_height;</synopsis>
|
|||
pointer to CRTC functions.
|
||||
</para>
|
||||
</sect3>
|
||||
<sect3>
|
||||
<sect3 id="drm-kms-crtcops">
|
||||
<title>CRTC Operations</title>
|
||||
<sect4>
|
||||
<title>Set Configuration</title>
|
||||
|
@ -1335,15 +1335,47 @@ int max_width, max_height;</synopsis>
|
|||
optionally scale it to a destination size. The result is then blended
|
||||
with or overlayed on top of a CRTC.
|
||||
</para>
|
||||
<para>
|
||||
The DRM core recognizes three types of planes:
|
||||
<itemizedlist>
|
||||
<listitem>
|
||||
DRM_PLANE_TYPE_PRIMARY represents a "main" plane for a CRTC. Primary
|
||||
planes are the planes operated upon by by CRTC modesetting and flipping
|
||||
operations described in <xref linkend="drm-kms-crtcops"/>.
|
||||
</listitem>
|
||||
<listitem>
|
||||
DRM_PLANE_TYPE_CURSOR represents a "cursor" plane for a CRTC. Cursor
|
||||
planes are the planes operated upon by the DRM_IOCTL_MODE_CURSOR and
|
||||
DRM_IOCTL_MODE_CURSOR2 ioctls.
|
||||
</listitem>
|
||||
<listitem>
|
||||
DRM_PLANE_TYPE_OVERLAY represents all non-primary, non-cursor planes.
|
||||
Some drivers refer to these types of planes as "sprites" internally.
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
For compatibility with legacy userspace, only overlay planes are made
|
||||
available to userspace by default. Userspace clients may set the
|
||||
DRM_CLIENT_CAP_UNIVERSAL_PLANES client capability bit to indicate that
|
||||
they wish to receive a universal plane list containing all plane types.
|
||||
</para>
|
||||
<sect3>
|
||||
<title>Plane Initialization</title>
|
||||
<para>
|
||||
Planes are optional. To create a plane, a KMS drivers allocates and
|
||||
To create a plane, a KMS drivers allocates and
|
||||
zeroes an instances of struct <structname>drm_plane</structname>
|
||||
(possibly as part of a larger structure) and registers it with a call
|
||||
to <function>drm_plane_init</function>. The function takes a bitmask
|
||||
to <function>drm_universal_plane_init</function>. The function takes a bitmask
|
||||
of the CRTCs that can be associated with the plane, a pointer to the
|
||||
plane functions and a list of format supported formats.
|
||||
plane functions, a list of format supported formats, and the type of
|
||||
plane (primary, cursor, or overlay) being initialized.
|
||||
</para>
|
||||
<para>
|
||||
Cursor and overlay planes are optional. All drivers should provide
|
||||
one primary plane per CRTC (although this requirement may change in
|
||||
the future); drivers that do not wish to provide special handling for
|
||||
primary planes may make use of the helper functions described in
|
||||
<xref linkend="drm-kms-planehelpers"/> to create and register a
|
||||
primary plane with standard capabilities.
|
||||
</para>
|
||||
</sect3>
|
||||
<sect3>
|
||||
|
@ -1774,7 +1806,7 @@ void intel_crt_init(struct drm_device *dev)
|
|||
<sect1>
|
||||
<title>Mode Setting Helper Functions</title>
|
||||
<para>
|
||||
The CRTC, encoder and connector functions provided by the drivers
|
||||
The plane, CRTC, encoder and connector functions provided by the drivers
|
||||
implement the DRM API. They're called by the DRM core and ioctl handlers
|
||||
to handle device state changes and configuration request. As implementing
|
||||
those functions often requires logic not specific to drivers, mid-layer
|
||||
|
@ -1782,8 +1814,8 @@ void intel_crt_init(struct drm_device *dev)
|
|||
</para>
|
||||
<para>
|
||||
The DRM core contains one mid-layer implementation. The mid-layer provides
|
||||
implementations of several CRTC, encoder and connector functions (called
|
||||
from the top of the mid-layer) that pre-process requests and call
|
||||
implementations of several plane, CRTC, encoder and connector functions
|
||||
(called from the top of the mid-layer) that pre-process requests and call
|
||||
lower-level functions provided by the driver (at the bottom of the
|
||||
mid-layer). For instance, the
|
||||
<function>drm_crtc_helper_set_config</function> function can be used to
|
||||
|
@ -2293,6 +2325,10 @@ void intel_crt_init(struct drm_device *dev)
|
|||
!Iinclude/linux/hdmi.h
|
||||
!Edrivers/video/hdmi.c
|
||||
</sect2>
|
||||
<sect2>
|
||||
<title id="drm-kms-planehelpers">Plane Helper Reference</title>
|
||||
!Edrivers/gpu/drm/drm_plane_helper.c Plane Helpers
|
||||
</sect2>
|
||||
</sect1>
|
||||
|
||||
<!-- Internals: kms properties -->
|
||||
|
|
|
@ -13,7 +13,8 @@ drm-y := drm_auth.o drm_buffer.o drm_bufs.o drm_cache.o \
|
|||
drm_crtc.o drm_modes.o drm_edid.o \
|
||||
drm_info.o drm_debugfs.o drm_encoder_slave.o \
|
||||
drm_trace_points.o drm_global.o drm_prime.o \
|
||||
drm_rect.o drm_vma_manager.o drm_flip_work.o
|
||||
drm_rect.o drm_vma_manager.o drm_flip_work.o \
|
||||
drm_plane_helper.o
|
||||
|
||||
drm-$(CONFIG_COMPAT) += drm_ioc32.o
|
||||
drm-$(CONFIG_DRM_GEM_CMA_HELPER) += drm_gem_cma_helper.o
|
||||
|
|
|
@ -478,11 +478,12 @@ static int armada_drm_crtc_mode_set(struct drm_crtc *crtc,
|
|||
unsigned i;
|
||||
bool interlaced;
|
||||
|
||||
drm_framebuffer_reference(crtc->fb);
|
||||
drm_framebuffer_reference(crtc->primary->fb);
|
||||
|
||||
interlaced = !!(adj->flags & DRM_MODE_FLAG_INTERLACE);
|
||||
|
||||
i = armada_drm_crtc_calc_fb(dcrtc->crtc.fb, x, y, regs, interlaced);
|
||||
i = armada_drm_crtc_calc_fb(dcrtc->crtc.primary->fb,
|
||||
x, y, regs, interlaced);
|
||||
|
||||
rm = adj->crtc_hsync_start - adj->crtc_hdisplay;
|
||||
lm = adj->crtc_htotal - adj->crtc_hsync_end;
|
||||
|
@ -567,10 +568,10 @@ static int armada_drm_crtc_mode_set(struct drm_crtc *crtc,
|
|||
}
|
||||
|
||||
val = CFG_GRA_ENA | CFG_GRA_HSMOOTH;
|
||||
val |= CFG_GRA_FMT(drm_fb_to_armada_fb(dcrtc->crtc.fb)->fmt);
|
||||
val |= CFG_GRA_MOD(drm_fb_to_armada_fb(dcrtc->crtc.fb)->mod);
|
||||
val |= CFG_GRA_FMT(drm_fb_to_armada_fb(dcrtc->crtc.primary->fb)->fmt);
|
||||
val |= CFG_GRA_MOD(drm_fb_to_armada_fb(dcrtc->crtc.primary->fb)->mod);
|
||||
|
||||
if (drm_fb_to_armada_fb(dcrtc->crtc.fb)->fmt > CFG_420)
|
||||
if (drm_fb_to_armada_fb(dcrtc->crtc.primary->fb)->fmt > CFG_420)
|
||||
val |= CFG_PALETTE_ENA;
|
||||
|
||||
if (interlaced)
|
||||
|
@ -608,7 +609,7 @@ static int armada_drm_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
struct armada_regs regs[4];
|
||||
unsigned i;
|
||||
|
||||
i = armada_drm_crtc_calc_fb(crtc->fb, crtc->x, crtc->y, regs,
|
||||
i = armada_drm_crtc_calc_fb(crtc->primary->fb, crtc->x, crtc->y, regs,
|
||||
dcrtc->interlaced);
|
||||
armada_reg_queue_end(regs, i);
|
||||
|
||||
|
@ -616,7 +617,7 @@ static int armada_drm_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
wait_event(dcrtc->frame_wait, !dcrtc->frame_work);
|
||||
|
||||
/* Take a reference to the new fb as we're using it */
|
||||
drm_framebuffer_reference(crtc->fb);
|
||||
drm_framebuffer_reference(crtc->primary->fb);
|
||||
|
||||
/* Update the base in the CRTC */
|
||||
armada_drm_crtc_update_regs(dcrtc, regs);
|
||||
|
@ -637,7 +638,7 @@ static void armada_drm_crtc_disable(struct drm_crtc *crtc)
|
|||
struct armada_crtc *dcrtc = drm_to_armada_crtc(crtc);
|
||||
|
||||
armada_drm_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
|
||||
armada_drm_crtc_finish_fb(dcrtc, crtc->fb, true);
|
||||
armada_drm_crtc_finish_fb(dcrtc, crtc->primary->fb, true);
|
||||
|
||||
/* Power down most RAMs and FIFOs */
|
||||
writel_relaxed(CFG_PDWN256x32 | CFG_PDWN256x24 | CFG_PDWN256x8 |
|
||||
|
@ -904,7 +905,7 @@ static int armada_drm_crtc_page_flip(struct drm_crtc *crtc,
|
|||
int ret;
|
||||
|
||||
/* We don't support changing the pixel format */
|
||||
if (fb->pixel_format != crtc->fb->pixel_format)
|
||||
if (fb->pixel_format != crtc->primary->fb->pixel_format)
|
||||
return -EINVAL;
|
||||
|
||||
work = kmalloc(sizeof(*work), GFP_KERNEL);
|
||||
|
@ -912,7 +913,7 @@ static int armada_drm_crtc_page_flip(struct drm_crtc *crtc,
|
|||
return -ENOMEM;
|
||||
|
||||
work->event = event;
|
||||
work->old_fb = dcrtc->crtc.fb;
|
||||
work->old_fb = dcrtc->crtc.primary->fb;
|
||||
|
||||
i = armada_drm_crtc_calc_fb(fb, crtc->x, crtc->y, work->regs,
|
||||
dcrtc->interlaced);
|
||||
|
@ -941,7 +942,7 @@ static int armada_drm_crtc_page_flip(struct drm_crtc *crtc,
|
|||
* will _not_ drop that reference on successful return from this
|
||||
* function. Simply mark this new framebuffer as the current one.
|
||||
*/
|
||||
dcrtc->crtc.fb = fb;
|
||||
dcrtc->crtc.primary->fb = fb;
|
||||
|
||||
/*
|
||||
* Finally, if the display is blanked, we won't receive an
|
||||
|
|
|
@ -81,7 +81,7 @@ static bool ast_get_vbios_mode_info(struct drm_crtc *crtc, struct drm_display_mo
|
|||
u32 refresh_rate_index = 0, mode_id, color_index, refresh_rate;
|
||||
u32 hborder, vborder;
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
vbios_mode->std_table = &vbios_stdtable[VGAModeIndex];
|
||||
color_index = VGAModeIndex - 1;
|
||||
|
@ -176,7 +176,7 @@ static bool ast_get_vbios_mode_info(struct drm_crtc *crtc, struct drm_display_mo
|
|||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x8e, mode_id & 0xff);
|
||||
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x91, 0xa8);
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x92, crtc->fb->bits_per_pixel);
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x92, crtc->primary->fb->bits_per_pixel);
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x93, adjusted_mode->clock / 1000);
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x94, adjusted_mode->crtc_hdisplay);
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x95, adjusted_mode->crtc_hdisplay >> 8);
|
||||
|
@ -340,7 +340,7 @@ static void ast_set_offset_reg(struct drm_crtc *crtc)
|
|||
|
||||
u16 offset;
|
||||
|
||||
offset = crtc->fb->pitches[0] >> 3;
|
||||
offset = crtc->primary->fb->pitches[0] >> 3;
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x13, (offset & 0xff));
|
||||
ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xb0, (offset >> 8) & 0x3f);
|
||||
}
|
||||
|
@ -365,7 +365,7 @@ static void ast_set_ext_reg(struct drm_crtc *crtc, struct drm_display_mode *mode
|
|||
struct ast_private *ast = crtc->dev->dev_private;
|
||||
u8 jregA0 = 0, jregA3 = 0, jregA8 = 0;
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
jregA0 = 0x70;
|
||||
jregA3 = 0x01;
|
||||
|
@ -418,7 +418,7 @@ static void ast_set_sync_reg(struct drm_device *dev, struct drm_display_mode *mo
|
|||
static bool ast_set_dac_reg(struct drm_crtc *crtc, struct drm_display_mode *mode,
|
||||
struct ast_vbios_mode_info *vbios_mode)
|
||||
{
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
break;
|
||||
default:
|
||||
|
@ -490,7 +490,7 @@ static int ast_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
ast_bo_unreserve(bo);
|
||||
}
|
||||
|
||||
ast_fb = to_ast_framebuffer(crtc->fb);
|
||||
ast_fb = to_ast_framebuffer(crtc->primary->fb);
|
||||
obj = ast_fb->obj;
|
||||
bo = gem_to_ast_bo(obj);
|
||||
|
||||
|
|
|
@ -62,10 +62,10 @@ static int bochs_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
}
|
||||
}
|
||||
|
||||
if (WARN_ON(crtc->fb == NULL))
|
||||
if (WARN_ON(crtc->primary->fb == NULL))
|
||||
return -EINVAL;
|
||||
|
||||
bochs_fb = to_bochs_framebuffer(crtc->fb);
|
||||
bochs_fb = to_bochs_framebuffer(crtc->primary->fb);
|
||||
bo = gem_to_bochs_bo(bochs_fb->obj);
|
||||
ret = ttm_bo_reserve(&bo->bo, true, false, false, 0);
|
||||
if (ret)
|
||||
|
|
|
@ -149,7 +149,7 @@ static int cirrus_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
cirrus_bo_unreserve(bo);
|
||||
}
|
||||
|
||||
cirrus_fb = to_cirrus_framebuffer(crtc->fb);
|
||||
cirrus_fb = to_cirrus_framebuffer(crtc->primary->fb);
|
||||
obj = cirrus_fb->obj;
|
||||
bo = gem_to_cirrus_bo(obj);
|
||||
|
||||
|
@ -268,7 +268,7 @@ static int cirrus_crtc_mode_set(struct drm_crtc *crtc,
|
|||
sr07 = RREG8(SEQ_DATA);
|
||||
sr07 &= 0xe0;
|
||||
hdr = 0;
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
sr07 |= 0x11;
|
||||
break;
|
||||
|
@ -291,13 +291,13 @@ static int cirrus_crtc_mode_set(struct drm_crtc *crtc,
|
|||
WREG_SEQ(0x7, sr07);
|
||||
|
||||
/* Program the pitch */
|
||||
tmp = crtc->fb->pitches[0] / 8;
|
||||
tmp = crtc->primary->fb->pitches[0] / 8;
|
||||
WREG_CRT(VGA_CRTC_OFFSET, tmp);
|
||||
|
||||
/* Enable extended blanking and pitch bits, and enable full memory */
|
||||
tmp = 0x22;
|
||||
tmp |= (crtc->fb->pitches[0] >> 7) & 0x10;
|
||||
tmp |= (crtc->fb->pitches[0] >> 6) & 0x40;
|
||||
tmp |= (crtc->primary->fb->pitches[0] >> 7) & 0x10;
|
||||
tmp |= (crtc->primary->fb->pitches[0] >> 6) & 0x40;
|
||||
WREG_CRT(0x1b, tmp);
|
||||
|
||||
/* Enable high-colour modes */
|
||||
|
|
|
@ -121,6 +121,13 @@ static const struct drm_prop_enum_list drm_dpms_enum_list[] =
|
|||
|
||||
DRM_ENUM_NAME_FN(drm_get_dpms_name, drm_dpms_enum_list)
|
||||
|
||||
static const struct drm_prop_enum_list drm_plane_type_enum_list[] =
|
||||
{
|
||||
{ DRM_PLANE_TYPE_OVERLAY, "Overlay" },
|
||||
{ DRM_PLANE_TYPE_PRIMARY, "Primary" },
|
||||
{ DRM_PLANE_TYPE_CURSOR, "Cursor" },
|
||||
};
|
||||
|
||||
/*
|
||||
* Optional properties
|
||||
*/
|
||||
|
@ -662,7 +669,7 @@ void drm_framebuffer_remove(struct drm_framebuffer *fb)
|
|||
drm_modeset_lock_all(dev);
|
||||
/* remove from any CRTC */
|
||||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
if (crtc->fb == fb) {
|
||||
if (crtc->primary->fb == fb) {
|
||||
/* should turn off the crtc */
|
||||
memset(&set, 0, sizeof(struct drm_mode_set));
|
||||
set.crtc = crtc;
|
||||
|
@ -685,9 +692,12 @@ void drm_framebuffer_remove(struct drm_framebuffer *fb)
|
|||
EXPORT_SYMBOL(drm_framebuffer_remove);
|
||||
|
||||
/**
|
||||
* drm_crtc_init - Initialise a new CRTC object
|
||||
* drm_crtc_init_with_planes - Initialise a new CRTC object with
|
||||
* specified primary and cursor planes.
|
||||
* @dev: DRM device
|
||||
* @crtc: CRTC object to init
|
||||
* @primary: Primary plane for CRTC
|
||||
* @cursor: Cursor plane for CRTC
|
||||
* @funcs: callbacks for the new CRTC
|
||||
*
|
||||
* Inits a new object created as base part of a driver crtc object.
|
||||
|
@ -695,8 +705,10 @@ EXPORT_SYMBOL(drm_framebuffer_remove);
|
|||
* Returns:
|
||||
* Zero on success, error code on failure.
|
||||
*/
|
||||
int drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
|
||||
const struct drm_crtc_funcs *funcs)
|
||||
int drm_crtc_init_with_planes(struct drm_device *dev, struct drm_crtc *crtc,
|
||||
struct drm_plane *primary,
|
||||
void *cursor,
|
||||
const struct drm_crtc_funcs *funcs)
|
||||
{
|
||||
int ret;
|
||||
|
||||
|
@ -717,12 +729,16 @@ int drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
|
|||
list_add_tail(&crtc->head, &dev->mode_config.crtc_list);
|
||||
dev->mode_config.num_crtc++;
|
||||
|
||||
crtc->primary = primary;
|
||||
if (primary)
|
||||
primary->possible_crtcs = 1 << drm_crtc_index(crtc);
|
||||
|
||||
out:
|
||||
drm_modeset_unlock_all(dev);
|
||||
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL(drm_crtc_init);
|
||||
EXPORT_SYMBOL(drm_crtc_init_with_planes);
|
||||
|
||||
/**
|
||||
* drm_crtc_cleanup - Clean up the core crtc usage
|
||||
|
@ -1000,26 +1016,25 @@ void drm_encoder_cleanup(struct drm_encoder *encoder)
|
|||
EXPORT_SYMBOL(drm_encoder_cleanup);
|
||||
|
||||
/**
|
||||
* drm_plane_init - Initialise a new plane object
|
||||
* drm_universal_plane_init - Initialize a new universal plane object
|
||||
* @dev: DRM device
|
||||
* @plane: plane object to init
|
||||
* @possible_crtcs: bitmask of possible CRTCs
|
||||
* @funcs: callbacks for the new plane
|
||||
* @formats: array of supported formats (%DRM_FORMAT_*)
|
||||
* @format_count: number of elements in @formats
|
||||
* @priv: plane is private (hidden from userspace)?
|
||||
* @type: type of plane (overlay, primary, cursor)
|
||||
*
|
||||
* Inits a preallocate plane object created as base part of a driver plane
|
||||
* object.
|
||||
* Initializes a plane object of type @type.
|
||||
*
|
||||
* Returns:
|
||||
* Zero on success, error code on failure.
|
||||
*/
|
||||
int drm_plane_init(struct drm_device *dev, struct drm_plane *plane,
|
||||
unsigned long possible_crtcs,
|
||||
const struct drm_plane_funcs *funcs,
|
||||
const uint32_t *formats, uint32_t format_count,
|
||||
bool priv)
|
||||
int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
|
||||
unsigned long possible_crtcs,
|
||||
const struct drm_plane_funcs *funcs,
|
||||
const uint32_t *formats, uint32_t format_count,
|
||||
enum drm_plane_type type)
|
||||
{
|
||||
int ret;
|
||||
|
||||
|
@ -1044,23 +1059,53 @@ int drm_plane_init(struct drm_device *dev, struct drm_plane *plane,
|
|||
memcpy(plane->format_types, formats, format_count * sizeof(uint32_t));
|
||||
plane->format_count = format_count;
|
||||
plane->possible_crtcs = possible_crtcs;
|
||||
plane->type = type;
|
||||
|
||||
/* private planes are not exposed to userspace, but depending on
|
||||
* display hardware, might be convenient to allow sharing programming
|
||||
* for the scanout engine with the crtc implementation.
|
||||
*/
|
||||
if (!priv) {
|
||||
list_add_tail(&plane->head, &dev->mode_config.plane_list);
|
||||
dev->mode_config.num_plane++;
|
||||
} else {
|
||||
INIT_LIST_HEAD(&plane->head);
|
||||
}
|
||||
list_add_tail(&plane->head, &dev->mode_config.plane_list);
|
||||
dev->mode_config.num_total_plane++;
|
||||
if (plane->type == DRM_PLANE_TYPE_OVERLAY)
|
||||
dev->mode_config.num_overlay_plane++;
|
||||
|
||||
drm_object_attach_property(&plane->base,
|
||||
dev->mode_config.plane_type_property,
|
||||
plane->type);
|
||||
|
||||
out:
|
||||
drm_modeset_unlock_all(dev);
|
||||
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL(drm_universal_plane_init);
|
||||
|
||||
/**
|
||||
* drm_plane_init - Initialize a legacy plane
|
||||
* @dev: DRM device
|
||||
* @plane: plane object to init
|
||||
* @possible_crtcs: bitmask of possible CRTCs
|
||||
* @funcs: callbacks for the new plane
|
||||
* @formats: array of supported formats (%DRM_FORMAT_*)
|
||||
* @format_count: number of elements in @formats
|
||||
* @is_primary: plane type (primary vs overlay)
|
||||
*
|
||||
* Legacy API to initialize a DRM plane.
|
||||
*
|
||||
* New drivers should call drm_universal_plane_init() instead.
|
||||
*
|
||||
* Returns:
|
||||
* Zero on success, error code on failure.
|
||||
*/
|
||||
int drm_plane_init(struct drm_device *dev, struct drm_plane *plane,
|
||||
unsigned long possible_crtcs,
|
||||
const struct drm_plane_funcs *funcs,
|
||||
const uint32_t *formats, uint32_t format_count,
|
||||
bool is_primary)
|
||||
{
|
||||
enum drm_plane_type type;
|
||||
|
||||
type = is_primary ? DRM_PLANE_TYPE_PRIMARY : DRM_PLANE_TYPE_OVERLAY;
|
||||
return drm_universal_plane_init(dev, plane, possible_crtcs, funcs,
|
||||
formats, format_count, type);
|
||||
}
|
||||
EXPORT_SYMBOL(drm_plane_init);
|
||||
|
||||
/**
|
||||
|
@ -1078,11 +1123,13 @@ void drm_plane_cleanup(struct drm_plane *plane)
|
|||
drm_modeset_lock_all(dev);
|
||||
kfree(plane->format_types);
|
||||
drm_mode_object_put(dev, &plane->base);
|
||||
/* if not added to a list, it must be a private plane */
|
||||
if (!list_empty(&plane->head)) {
|
||||
list_del(&plane->head);
|
||||
dev->mode_config.num_plane--;
|
||||
}
|
||||
|
||||
BUG_ON(list_empty(&plane->head));
|
||||
|
||||
list_del(&plane->head);
|
||||
dev->mode_config.num_total_plane--;
|
||||
if (plane->type == DRM_PLANE_TYPE_OVERLAY)
|
||||
dev->mode_config.num_overlay_plane--;
|
||||
drm_modeset_unlock_all(dev);
|
||||
}
|
||||
EXPORT_SYMBOL(drm_plane_cleanup);
|
||||
|
@ -1134,6 +1181,21 @@ static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int drm_mode_create_standard_plane_properties(struct drm_device *dev)
|
||||
{
|
||||
struct drm_property *type;
|
||||
|
||||
/*
|
||||
* Standard properties (apply to all planes)
|
||||
*/
|
||||
type = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
|
||||
"type", drm_plane_type_enum_list,
|
||||
ARRAY_SIZE(drm_plane_type_enum_list));
|
||||
dev->mode_config.plane_type_property = type;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* drm_mode_create_dvi_i_properties - create DVI-I specific connector properties
|
||||
* @dev: DRM device
|
||||
|
@ -1652,8 +1714,8 @@ int drm_mode_getcrtc(struct drm_device *dev,
|
|||
crtc_resp->x = crtc->x;
|
||||
crtc_resp->y = crtc->y;
|
||||
crtc_resp->gamma_size = crtc->gamma_size;
|
||||
if (crtc->fb)
|
||||
crtc_resp->fb_id = crtc->fb->base.id;
|
||||
if (crtc->primary->fb)
|
||||
crtc_resp->fb_id = crtc->primary->fb->base.id;
|
||||
else
|
||||
crtc_resp->fb_id = 0;
|
||||
|
||||
|
@ -1897,6 +1959,7 @@ int drm_mode_getplane_res(struct drm_device *dev, void *data,
|
|||
struct drm_plane *plane;
|
||||
uint32_t __user *plane_ptr;
|
||||
int copied = 0, ret = 0;
|
||||
unsigned num_planes;
|
||||
|
||||
if (!drm_core_check_feature(dev, DRIVER_MODESET))
|
||||
return -EINVAL;
|
||||
|
@ -1904,15 +1967,28 @@ int drm_mode_getplane_res(struct drm_device *dev, void *data,
|
|||
drm_modeset_lock_all(dev);
|
||||
config = &dev->mode_config;
|
||||
|
||||
if (file_priv->universal_planes)
|
||||
num_planes = config->num_total_plane;
|
||||
else
|
||||
num_planes = config->num_overlay_plane;
|
||||
|
||||
/*
|
||||
* This ioctl is called twice, once to determine how much space is
|
||||
* needed, and the 2nd time to fill it.
|
||||
*/
|
||||
if (config->num_plane &&
|
||||
(plane_resp->count_planes >= config->num_plane)) {
|
||||
if (num_planes &&
|
||||
(plane_resp->count_planes >= num_planes)) {
|
||||
plane_ptr = (uint32_t __user *)(unsigned long)plane_resp->plane_id_ptr;
|
||||
|
||||
list_for_each_entry(plane, &config->plane_list, head) {
|
||||
/*
|
||||
* Unless userspace set the 'universal planes'
|
||||
* capability bit, only advertise overlays.
|
||||
*/
|
||||
if (plane->type != DRM_PLANE_TYPE_OVERLAY &&
|
||||
!file_priv->universal_planes)
|
||||
continue;
|
||||
|
||||
if (put_user(plane->base.id, plane_ptr + copied)) {
|
||||
ret = -EFAULT;
|
||||
goto out;
|
||||
|
@ -1920,7 +1996,7 @@ int drm_mode_getplane_res(struct drm_device *dev, void *data,
|
|||
copied++;
|
||||
}
|
||||
}
|
||||
plane_resp->count_planes = config->num_plane;
|
||||
plane_resp->count_planes = num_planes;
|
||||
|
||||
out:
|
||||
drm_modeset_unlock_all(dev);
|
||||
|
@ -2156,19 +2232,21 @@ int drm_mode_set_config_internal(struct drm_mode_set *set)
|
|||
* crtcs. Atomic modeset will have saner semantics ...
|
||||
*/
|
||||
list_for_each_entry(tmp, &crtc->dev->mode_config.crtc_list, head)
|
||||
tmp->old_fb = tmp->fb;
|
||||
tmp->old_fb = tmp->primary->fb;
|
||||
|
||||
fb = set->fb;
|
||||
|
||||
ret = crtc->funcs->set_config(set);
|
||||
if (ret == 0) {
|
||||
crtc->primary->crtc = crtc;
|
||||
|
||||
/* crtc->fb must be updated by ->set_config, enforces this. */
|
||||
WARN_ON(fb != crtc->fb);
|
||||
WARN_ON(fb != crtc->primary->fb);
|
||||
}
|
||||
|
||||
list_for_each_entry(tmp, &crtc->dev->mode_config.crtc_list, head) {
|
||||
if (tmp->fb)
|
||||
drm_framebuffer_reference(tmp->fb);
|
||||
if (tmp->primary->fb)
|
||||
drm_framebuffer_reference(tmp->primary->fb);
|
||||
if (tmp->old_fb)
|
||||
drm_framebuffer_unreference(tmp->old_fb);
|
||||
}
|
||||
|
@ -2177,14 +2255,19 @@ int drm_mode_set_config_internal(struct drm_mode_set *set)
|
|||
}
|
||||
EXPORT_SYMBOL(drm_mode_set_config_internal);
|
||||
|
||||
/*
|
||||
* Checks that the framebuffer is big enough for the CRTC viewport
|
||||
* (x, y, hdisplay, vdisplay)
|
||||
/**
|
||||
* drm_crtc_check_viewport - Checks that a framebuffer is big enough for the
|
||||
* CRTC viewport
|
||||
* @crtc: CRTC that framebuffer will be displayed on
|
||||
* @x: x panning
|
||||
* @y: y panning
|
||||
* @mode: mode that framebuffer will be displayed under
|
||||
* @fb: framebuffer to check size of
|
||||
*/
|
||||
static int drm_crtc_check_viewport(const struct drm_crtc *crtc,
|
||||
int x, int y,
|
||||
const struct drm_display_mode *mode,
|
||||
const struct drm_framebuffer *fb)
|
||||
int drm_crtc_check_viewport(const struct drm_crtc *crtc,
|
||||
int x, int y,
|
||||
const struct drm_display_mode *mode,
|
||||
const struct drm_framebuffer *fb)
|
||||
|
||||
{
|
||||
int hdisplay, vdisplay;
|
||||
|
@ -2215,6 +2298,7 @@ static int drm_crtc_check_viewport(const struct drm_crtc *crtc,
|
|||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL(drm_crtc_check_viewport);
|
||||
|
||||
/**
|
||||
* drm_mode_setcrtc - set CRTC configuration
|
||||
|
@ -2266,12 +2350,12 @@ int drm_mode_setcrtc(struct drm_device *dev, void *data,
|
|||
/* If we have a mode we need a framebuffer. */
|
||||
/* If we pass -1, set the mode with the currently bound fb */
|
||||
if (crtc_req->fb_id == -1) {
|
||||
if (!crtc->fb) {
|
||||
if (!crtc->primary->fb) {
|
||||
DRM_DEBUG_KMS("CRTC doesn't have current FB\n");
|
||||
ret = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
fb = crtc->fb;
|
||||
fb = crtc->primary->fb;
|
||||
/* Make refcounting symmetric with the lookup path. */
|
||||
drm_framebuffer_reference(fb);
|
||||
} else {
|
||||
|
@ -4065,7 +4149,7 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
|
|||
crtc = obj_to_crtc(obj);
|
||||
|
||||
mutex_lock(&crtc->mutex);
|
||||
if (crtc->fb == NULL) {
|
||||
if (crtc->primary->fb == NULL) {
|
||||
/* The framebuffer is currently unbound, presumably
|
||||
* due to a hotplug event, that userspace has not
|
||||
* yet discovered.
|
||||
|
@ -4087,7 +4171,7 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
|
|||
if (ret)
|
||||
goto out;
|
||||
|
||||
if (crtc->fb->pixel_format != fb->pixel_format) {
|
||||
if (crtc->primary->fb->pixel_format != fb->pixel_format) {
|
||||
DRM_DEBUG_KMS("Page flip is not allowed to change frame buffer format.\n");
|
||||
ret = -EINVAL;
|
||||
goto out;
|
||||
|
@ -4120,7 +4204,7 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
|
|||
(void (*) (struct drm_pending_event *)) kfree;
|
||||
}
|
||||
|
||||
old_fb = crtc->fb;
|
||||
old_fb = crtc->primary->fb;
|
||||
ret = crtc->funcs->page_flip(crtc, fb, e, page_flip->flags);
|
||||
if (ret) {
|
||||
if (page_flip->flags & DRM_MODE_PAGE_FLIP_EVENT) {
|
||||
|
@ -4138,7 +4222,7 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
|
|||
* Failing to do so will screw with the reference counting
|
||||
* on framebuffers.
|
||||
*/
|
||||
WARN_ON(crtc->fb != fb);
|
||||
WARN_ON(crtc->primary->fb != fb);
|
||||
/* Unref only the old framebuffer. */
|
||||
fb = NULL;
|
||||
}
|
||||
|
@ -4527,6 +4611,7 @@ void drm_mode_config_init(struct drm_device *dev)
|
|||
|
||||
drm_modeset_lock_all(dev);
|
||||
drm_mode_create_standard_connector_properties(dev);
|
||||
drm_mode_create_standard_plane_properties(dev);
|
||||
drm_modeset_unlock_all(dev);
|
||||
|
||||
/* Just to be sure */
|
||||
|
@ -4534,6 +4619,8 @@ void drm_mode_config_init(struct drm_device *dev)
|
|||
dev->mode_config.num_connector = 0;
|
||||
dev->mode_config.num_crtc = 0;
|
||||
dev->mode_config.num_encoder = 0;
|
||||
dev->mode_config.num_overlay_plane = 0;
|
||||
dev->mode_config.num_total_plane = 0;
|
||||
}
|
||||
EXPORT_SYMBOL(drm_mode_config_init);
|
||||
|
||||
|
|
|
@ -307,7 +307,7 @@ static void __drm_helper_disable_unused_functions(struct drm_device *dev)
|
|||
(*crtc_funcs->disable)(crtc);
|
||||
else
|
||||
(*crtc_funcs->dpms)(crtc, DRM_MODE_DPMS_OFF);
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -651,19 +651,19 @@ int drm_crtc_helper_set_config(struct drm_mode_set *set)
|
|||
save_set.mode = &set->crtc->mode;
|
||||
save_set.x = set->crtc->x;
|
||||
save_set.y = set->crtc->y;
|
||||
save_set.fb = set->crtc->fb;
|
||||
save_set.fb = set->crtc->primary->fb;
|
||||
|
||||
/* We should be able to check here if the fb has the same properties
|
||||
* and then just flip_or_move it */
|
||||
if (set->crtc->fb != set->fb) {
|
||||
if (set->crtc->primary->fb != set->fb) {
|
||||
/* If we have no fb then treat it as a full mode set */
|
||||
if (set->crtc->fb == NULL) {
|
||||
if (set->crtc->primary->fb == NULL) {
|
||||
DRM_DEBUG_KMS("crtc has no fb, full mode set\n");
|
||||
mode_changed = true;
|
||||
} else if (set->fb == NULL) {
|
||||
mode_changed = true;
|
||||
} else if (set->fb->pixel_format !=
|
||||
set->crtc->fb->pixel_format) {
|
||||
set->crtc->primary->fb->pixel_format) {
|
||||
mode_changed = true;
|
||||
} else
|
||||
fb_changed = true;
|
||||
|
@ -765,13 +765,13 @@ int drm_crtc_helper_set_config(struct drm_mode_set *set)
|
|||
DRM_DEBUG_KMS("attempting to set mode from"
|
||||
" userspace\n");
|
||||
drm_mode_debug_printmodeline(set->mode);
|
||||
set->crtc->fb = set->fb;
|
||||
set->crtc->primary->fb = set->fb;
|
||||
if (!drm_crtc_helper_set_mode(set->crtc, set->mode,
|
||||
set->x, set->y,
|
||||
save_set.fb)) {
|
||||
DRM_ERROR("failed to set mode on [CRTC:%d]\n",
|
||||
set->crtc->base.id);
|
||||
set->crtc->fb = save_set.fb;
|
||||
set->crtc->primary->fb = save_set.fb;
|
||||
ret = -EINVAL;
|
||||
goto fail;
|
||||
}
|
||||
|
@ -786,13 +786,13 @@ int drm_crtc_helper_set_config(struct drm_mode_set *set)
|
|||
} else if (fb_changed) {
|
||||
set->crtc->x = set->x;
|
||||
set->crtc->y = set->y;
|
||||
set->crtc->fb = set->fb;
|
||||
set->crtc->primary->fb = set->fb;
|
||||
ret = crtc_funcs->mode_set_base(set->crtc,
|
||||
set->x, set->y, save_set.fb);
|
||||
if (ret != 0) {
|
||||
set->crtc->x = save_set.x;
|
||||
set->crtc->y = save_set.y;
|
||||
set->crtc->fb = save_set.fb;
|
||||
set->crtc->primary->fb = save_set.fb;
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
|
@ -989,7 +989,7 @@ void drm_helper_resume_force_mode(struct drm_device *dev)
|
|||
continue;
|
||||
|
||||
ret = drm_crtc_helper_set_mode(crtc, &crtc->mode,
|
||||
crtc->x, crtc->y, crtc->fb);
|
||||
crtc->x, crtc->y, crtc->primary->fb);
|
||||
|
||||
/* Restoring the old config should never fail! */
|
||||
if (ret == false)
|
||||
|
|
|
@ -232,7 +232,7 @@ static struct drm_framebuffer *drm_mode_config_fb(struct drm_crtc *crtc)
|
|||
|
||||
list_for_each_entry(c, &dev->mode_config.crtc_list, head) {
|
||||
if (crtc->base.id == c->base.id)
|
||||
return c->fb;
|
||||
return c->primary->fb;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
|
@ -291,7 +291,8 @@ bool drm_fb_helper_restore_fbdev_mode(struct drm_fb_helper *fb_helper)
|
|||
drm_warn_on_modeset_not_all_locked(dev);
|
||||
|
||||
list_for_each_entry(plane, &dev->mode_config.plane_list, head)
|
||||
drm_plane_force_disable(plane);
|
||||
if (plane->type != DRM_PLANE_TYPE_PRIMARY)
|
||||
drm_plane_force_disable(plane);
|
||||
|
||||
for (i = 0; i < fb_helper->crtc_count; i++) {
|
||||
struct drm_mode_set *mode_set = &fb_helper->crtc_info[i].mode_set;
|
||||
|
@ -365,9 +366,9 @@ static bool drm_fb_helper_is_bound(struct drm_fb_helper *fb_helper)
|
|||
return false;
|
||||
|
||||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
if (crtc->fb)
|
||||
if (crtc->primary->fb)
|
||||
crtcs_bound++;
|
||||
if (crtc->fb == fb_helper->fb)
|
||||
if (crtc->primary->fb == fb_helper->fb)
|
||||
bound++;
|
||||
}
|
||||
|
||||
|
|
|
@ -328,6 +328,13 @@ drm_setclientcap(struct drm_device *dev, void *data, struct drm_file *file_priv)
|
|||
return -EINVAL;
|
||||
file_priv->stereo_allowed = req->value;
|
||||
break;
|
||||
case DRM_CLIENT_CAP_UNIVERSAL_PLANES:
|
||||
if (!drm_universal_planes)
|
||||
return -EINVAL;
|
||||
if (req->value > 1)
|
||||
return -EINVAL;
|
||||
file_priv->universal_planes = req->value;
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
}
|
||||
|
|
|
@ -0,0 +1,333 @@
|
|||
/*
|
||||
* Copyright (C) 2014 Intel Corporation
|
||||
*
|
||||
* DRM universal plane helper functions
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <linux/list.h>
|
||||
#include <drm/drmP.h>
|
||||
#include <drm/drm_rect.h>
|
||||
|
||||
#define SUBPIXEL_MASK 0xffff
|
||||
|
||||
/*
|
||||
* This is the minimal list of formats that seem to be safe for modeset use
|
||||
* with all current DRM drivers. Most hardware can actually support more
|
||||
* formats than this and drivers may specify a more accurate list when
|
||||
* creating the primary plane. However drivers that still call
|
||||
* drm_plane_init() will use this minimal format list as the default.
|
||||
*/
|
||||
const static uint32_t safe_modeset_formats[] = {
|
||||
DRM_FORMAT_XRGB8888,
|
||||
DRM_FORMAT_ARGB8888,
|
||||
};
|
||||
|
||||
/*
|
||||
* Returns the connectors currently associated with a CRTC. This function
|
||||
* should be called twice: once with a NULL connector list to retrieve
|
||||
* the list size, and once with the properly allocated list to be filled in.
|
||||
*/
|
||||
static int get_connectors_for_crtc(struct drm_crtc *crtc,
|
||||
struct drm_connector **connector_list,
|
||||
int num_connectors)
|
||||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_connector *connector;
|
||||
int count = 0;
|
||||
|
||||
list_for_each_entry(connector, &dev->mode_config.connector_list, head)
|
||||
if (connector->encoder && connector->encoder->crtc == crtc) {
|
||||
if (connector_list != NULL && count < num_connectors)
|
||||
*(connector_list++) = connector;
|
||||
|
||||
count++;
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
/**
|
||||
* drm_primary_helper_update() - Helper for primary plane update
|
||||
* @plane: plane object to update
|
||||
* @crtc: owning CRTC of owning plane
|
||||
* @fb: framebuffer to flip onto plane
|
||||
* @crtc_x: x offset of primary plane on crtc
|
||||
* @crtc_y: y offset of primary plane on crtc
|
||||
* @crtc_w: width of primary plane rectangle on crtc
|
||||
* @crtc_h: height of primary plane rectangle on crtc
|
||||
* @src_x: x offset of @fb for panning
|
||||
* @src_y: y offset of @fb for panning
|
||||
* @src_w: width of source rectangle in @fb
|
||||
* @src_h: height of source rectangle in @fb
|
||||
*
|
||||
* Provides a default plane update handler for primary planes. This is handler
|
||||
* is called in response to a userspace SetPlane operation on the plane with a
|
||||
* non-NULL framebuffer. We call the driver's modeset handler to update the
|
||||
* framebuffer.
|
||||
*
|
||||
* SetPlane() on a primary plane of a disabled CRTC is not supported, and will
|
||||
* return an error.
|
||||
*
|
||||
* Note that we make some assumptions about hardware limitations that may not be
|
||||
* true for all hardware --
|
||||
* 1) Primary plane cannot be repositioned.
|
||||
* 2) Primary plane cannot be scaled.
|
||||
* 3) Primary plane must cover the entire CRTC.
|
||||
* 4) Subpixel positioning is not supported.
|
||||
* Drivers for hardware that don't have these restrictions can provide their
|
||||
* own implementation rather than using this helper.
|
||||
*
|
||||
* RETURNS:
|
||||
* Zero on success, error code on failure
|
||||
*/
|
||||
int drm_primary_helper_update(struct drm_plane *plane, struct drm_crtc *crtc,
|
||||
struct drm_framebuffer *fb,
|
||||
int crtc_x, int crtc_y,
|
||||
unsigned int crtc_w, unsigned int crtc_h,
|
||||
uint32_t src_x, uint32_t src_y,
|
||||
uint32_t src_w, uint32_t src_h)
|
||||
{
|
||||
struct drm_mode_set set = {
|
||||
.crtc = crtc,
|
||||
.fb = fb,
|
||||
.mode = &crtc->mode,
|
||||
.x = src_x >> 16,
|
||||
.y = src_y >> 16,
|
||||
};
|
||||
struct drm_rect dest = {
|
||||
.x1 = crtc_x,
|
||||
.y1 = crtc_y,
|
||||
.x2 = crtc_x + crtc_w,
|
||||
.y2 = crtc_y + crtc_h,
|
||||
};
|
||||
struct drm_rect clip = {
|
||||
.x2 = crtc->mode.hdisplay,
|
||||
.y2 = crtc->mode.vdisplay,
|
||||
};
|
||||
struct drm_connector **connector_list;
|
||||
struct drm_framebuffer *tmpfb;
|
||||
int num_connectors, ret;
|
||||
|
||||
if (!crtc->enabled) {
|
||||
DRM_DEBUG_KMS("Cannot update primary plane of a disabled CRTC.\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Disallow subpixel positioning */
|
||||
if ((src_x | src_y | src_w | src_h) & SUBPIXEL_MASK) {
|
||||
DRM_DEBUG_KMS("Primary plane does not support subpixel positioning\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Primary planes are locked to their owning CRTC */
|
||||
if (plane->possible_crtcs != drm_crtc_mask(crtc)) {
|
||||
DRM_DEBUG_KMS("Cannot change primary plane CRTC\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Disallow scaling */
|
||||
if (crtc_w != src_w || crtc_h != src_h) {
|
||||
DRM_DEBUG_KMS("Can't scale primary plane\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Make sure primary plane covers entire CRTC */
|
||||
drm_rect_intersect(&dest, &clip);
|
||||
if (dest.x1 != 0 || dest.y1 != 0 ||
|
||||
dest.x2 != crtc->mode.hdisplay || dest.y2 != crtc->mode.vdisplay) {
|
||||
DRM_DEBUG_KMS("Primary plane must cover entire CRTC\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Framebuffer must be big enough to cover entire plane */
|
||||
ret = drm_crtc_check_viewport(crtc, crtc_x, crtc_y, &crtc->mode, fb);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Find current connectors for CRTC */
|
||||
num_connectors = get_connectors_for_crtc(crtc, NULL, 0);
|
||||
BUG_ON(num_connectors == 0);
|
||||
connector_list = kzalloc(num_connectors * sizeof(*connector_list),
|
||||
GFP_KERNEL);
|
||||
if (!connector_list)
|
||||
return -ENOMEM;
|
||||
get_connectors_for_crtc(crtc, connector_list, num_connectors);
|
||||
|
||||
set.connectors = connector_list;
|
||||
set.num_connectors = num_connectors;
|
||||
|
||||
/*
|
||||
* set_config() adjusts crtc->primary->fb; however the DRM setplane
|
||||
* code that called us expects to handle the framebuffer update and
|
||||
* reference counting; save and restore the current fb before
|
||||
* calling it.
|
||||
*
|
||||
* N.B., we call set_config() directly here rather than using
|
||||
* drm_mode_set_config_internal. We're reprogramming the same
|
||||
* connectors that were already in use, so we shouldn't need the extra
|
||||
* cross-CRTC fb refcounting to accomodate stealing connectors.
|
||||
* drm_mode_setplane() already handles the basic refcounting for the
|
||||
* framebuffers involved in this operation.
|
||||
*/
|
||||
tmpfb = plane->fb;
|
||||
ret = crtc->funcs->set_config(&set);
|
||||
plane->fb = tmpfb;
|
||||
|
||||
kfree(connector_list);
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL(drm_primary_helper_update);
|
||||
|
||||
/**
|
||||
* drm_primary_helper_disable() - Helper for primary plane disable
|
||||
* @plane: plane to disable
|
||||
*
|
||||
* Provides a default plane disable handler for primary planes. This is handler
|
||||
* is called in response to a userspace SetPlane operation on the plane with a
|
||||
* NULL framebuffer parameter. We call the driver's modeset handler with a NULL
|
||||
* framebuffer to disable the CRTC if no other planes are currently enabled.
|
||||
* If other planes are still enabled on the same CRTC, we return -EBUSY.
|
||||
*
|
||||
* Note that some hardware may be able to disable the primary plane without
|
||||
* disabling the whole CRTC. Drivers for such hardware should provide their
|
||||
* own disable handler that disables just the primary plane (and they'll likely
|
||||
* need to provide their own update handler as well to properly re-enable a
|
||||
* disabled primary plane).
|
||||
*
|
||||
* RETURNS:
|
||||
* Zero on success, error code on failure
|
||||
*/
|
||||
int drm_primary_helper_disable(struct drm_plane *plane)
|
||||
{
|
||||
struct drm_plane *p;
|
||||
struct drm_mode_set set = {
|
||||
.crtc = plane->crtc,
|
||||
.fb = NULL,
|
||||
};
|
||||
|
||||
if (plane->crtc == NULL || plane->fb == NULL)
|
||||
/* Already disabled */
|
||||
return 0;
|
||||
|
||||
list_for_each_entry(p, &plane->dev->mode_config.plane_list, head)
|
||||
if (p != plane && p->fb) {
|
||||
DRM_DEBUG_KMS("Cannot disable primary plane while other planes are still active on CRTC.\n");
|
||||
return -EBUSY;
|
||||
}
|
||||
|
||||
/*
|
||||
* N.B. We call set_config() directly here rather than
|
||||
* drm_mode_set_config_internal() since drm_mode_setplane() already
|
||||
* handles the basic refcounting and we don't need the special
|
||||
* cross-CRTC refcounting (no chance of stealing connectors from
|
||||
* other CRTC's with this update).
|
||||
*/
|
||||
return plane->crtc->funcs->set_config(&set);
|
||||
}
|
||||
EXPORT_SYMBOL(drm_primary_helper_disable);
|
||||
|
||||
/**
|
||||
* drm_primary_helper_destroy() - Helper for primary plane destruction
|
||||
* @plane: plane to destroy
|
||||
*
|
||||
* Provides a default plane destroy handler for primary planes. This handler
|
||||
* is called during CRTC destruction. We disable the primary plane, remove
|
||||
* it from the DRM plane list, and deallocate the plane structure.
|
||||
*/
|
||||
void drm_primary_helper_destroy(struct drm_plane *plane)
|
||||
{
|
||||
plane->funcs->disable_plane(plane);
|
||||
drm_plane_cleanup(plane);
|
||||
kfree(plane);
|
||||
}
|
||||
EXPORT_SYMBOL(drm_primary_helper_destroy);
|
||||
|
||||
const struct drm_plane_funcs drm_primary_helper_funcs = {
|
||||
.update_plane = drm_primary_helper_update,
|
||||
.disable_plane = drm_primary_helper_disable,
|
||||
.destroy = drm_primary_helper_destroy,
|
||||
};
|
||||
EXPORT_SYMBOL(drm_primary_helper_funcs);
|
||||
|
||||
/**
|
||||
* drm_primary_helper_create_plane() - Create a generic primary plane
|
||||
* @dev: drm device
|
||||
* @formats: pixel formats supported, or NULL for a default safe list
|
||||
* @num_formats: size of @formats; ignored if @formats is NULL
|
||||
*
|
||||
* Allocates and initializes a primary plane that can be used with the primary
|
||||
* plane helpers. Drivers that wish to use driver-specific plane structures or
|
||||
* provide custom handler functions may perform their own allocation and
|
||||
* initialization rather than calling this function.
|
||||
*/
|
||||
struct drm_plane *drm_primary_helper_create_plane(struct drm_device *dev,
|
||||
const uint32_t *formats,
|
||||
int num_formats)
|
||||
{
|
||||
struct drm_plane *primary;
|
||||
int ret;
|
||||
|
||||
primary = kzalloc(sizeof(*primary), GFP_KERNEL);
|
||||
if (primary == NULL) {
|
||||
DRM_DEBUG_KMS("Failed to allocate primary plane\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (formats == NULL) {
|
||||
formats = safe_modeset_formats;
|
||||
num_formats = ARRAY_SIZE(safe_modeset_formats);
|
||||
}
|
||||
|
||||
/* possible_crtc's will be filled in later by crtc_init */
|
||||
ret = drm_plane_init(dev, primary, 0, &drm_primary_helper_funcs,
|
||||
formats, num_formats,
|
||||
DRM_PLANE_TYPE_PRIMARY);
|
||||
if (ret) {
|
||||
kfree(primary);
|
||||
primary = NULL;
|
||||
}
|
||||
|
||||
return primary;
|
||||
}
|
||||
EXPORT_SYMBOL(drm_primary_helper_create_plane);
|
||||
|
||||
/**
|
||||
* drm_crtc_init - Legacy CRTC initialization function
|
||||
* @dev: DRM device
|
||||
* @crtc: CRTC object to init
|
||||
* @funcs: callbacks for the new CRTC
|
||||
*
|
||||
* Initialize a CRTC object with a default helper-provided primary plane and no
|
||||
* cursor plane.
|
||||
*
|
||||
* Returns:
|
||||
* Zero on success, error code on failure.
|
||||
*/
|
||||
int drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
|
||||
const struct drm_crtc_funcs *funcs)
|
||||
{
|
||||
struct drm_plane *primary;
|
||||
|
||||
primary = drm_primary_helper_create_plane(dev, NULL, 0);
|
||||
return drm_crtc_init_with_planes(dev, crtc, primary, NULL, funcs);
|
||||
}
|
||||
EXPORT_SYMBOL(drm_crtc_init);
|
|
@ -45,6 +45,10 @@ EXPORT_SYMBOL(drm_debug);
|
|||
unsigned int drm_rnodes = 0; /* 1 to enable experimental render nodes API */
|
||||
EXPORT_SYMBOL(drm_rnodes);
|
||||
|
||||
/* 1 to allow user space to request universal planes (experimental) */
|
||||
unsigned int drm_universal_planes = 0;
|
||||
EXPORT_SYMBOL(drm_universal_planes);
|
||||
|
||||
unsigned int drm_vblank_offdelay = 5000; /* Default to 5000 msecs. */
|
||||
EXPORT_SYMBOL(drm_vblank_offdelay);
|
||||
|
||||
|
@ -68,6 +72,7 @@ MODULE_PARM_DESC(timestamp_monotonic, "Use monotonic timestamps");
|
|||
|
||||
module_param_named(debug, drm_debug, int, 0600);
|
||||
module_param_named(rnodes, drm_rnodes, int, 0600);
|
||||
module_param_named(universal_planes, drm_universal_planes, int, 0600);
|
||||
module_param_named(vblankoffdelay, drm_vblank_offdelay, int, 0600);
|
||||
module_param_named(timestamp_precision_usec, drm_timestamp_precision, int, 0600);
|
||||
module_param_named(timestamp_monotonic, drm_timestamp_monotonic, int, 0600);
|
||||
|
|
|
@ -132,19 +132,19 @@ exynos_drm_crtc_mode_set(struct drm_crtc *crtc, struct drm_display_mode *mode,
|
|||
*/
|
||||
memcpy(&crtc->mode, adjusted_mode, sizeof(*adjusted_mode));
|
||||
|
||||
crtc_w = crtc->fb->width - x;
|
||||
crtc_h = crtc->fb->height - y;
|
||||
crtc_w = crtc->primary->fb->width - x;
|
||||
crtc_h = crtc->primary->fb->height - y;
|
||||
|
||||
if (manager->ops->mode_set)
|
||||
manager->ops->mode_set(manager, &crtc->mode);
|
||||
|
||||
ret = exynos_plane_mode_set(plane, crtc, crtc->fb, 0, 0, crtc_w, crtc_h,
|
||||
ret = exynos_plane_mode_set(plane, crtc, crtc->primary->fb, 0, 0, crtc_w, crtc_h,
|
||||
x, y, crtc_w, crtc_h);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
plane->crtc = crtc;
|
||||
plane->fb = crtc->fb;
|
||||
plane->fb = crtc->primary->fb;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -164,10 +164,10 @@ static int exynos_drm_crtc_mode_set_commit(struct drm_crtc *crtc, int x, int y,
|
|||
return -EPERM;
|
||||
}
|
||||
|
||||
crtc_w = crtc->fb->width - x;
|
||||
crtc_h = crtc->fb->height - y;
|
||||
crtc_w = crtc->primary->fb->width - x;
|
||||
crtc_h = crtc->primary->fb->height - y;
|
||||
|
||||
ret = exynos_plane_mode_set(plane, crtc, crtc->fb, 0, 0, crtc_w, crtc_h,
|
||||
ret = exynos_plane_mode_set(plane, crtc, crtc->primary->fb, 0, 0, crtc_w, crtc_h,
|
||||
x, y, crtc_w, crtc_h);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
@ -190,7 +190,7 @@ static void exynos_drm_crtc_disable(struct drm_crtc *crtc)
|
|||
|
||||
exynos_drm_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
|
||||
|
||||
list_for_each_entry(plane, &crtc->dev->mode_config.plane_list, head) {
|
||||
drm_for_each_legacy_plane(plane, &crtc->dev->mode_config.plane_list) {
|
||||
if (plane->crtc != crtc)
|
||||
continue;
|
||||
|
||||
|
@ -218,7 +218,7 @@ static int exynos_drm_crtc_page_flip(struct drm_crtc *crtc,
|
|||
struct drm_device *dev = crtc->dev;
|
||||
struct exynos_drm_private *dev_priv = dev->dev_private;
|
||||
struct exynos_drm_crtc *exynos_crtc = to_exynos_crtc(crtc);
|
||||
struct drm_framebuffer *old_fb = crtc->fb;
|
||||
struct drm_framebuffer *old_fb = crtc->primary->fb;
|
||||
int ret = -EINVAL;
|
||||
|
||||
/* when the page flip is requested, crtc's dpms should be on */
|
||||
|
@ -249,11 +249,11 @@ static int exynos_drm_crtc_page_flip(struct drm_crtc *crtc,
|
|||
atomic_set(&exynos_crtc->pending_flip, 1);
|
||||
spin_unlock_irq(&dev->event_lock);
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
ret = exynos_drm_crtc_mode_set_commit(crtc, crtc->x, crtc->y,
|
||||
NULL);
|
||||
if (ret) {
|
||||
crtc->fb = old_fb;
|
||||
crtc->primary->fb = old_fb;
|
||||
|
||||
spin_lock_irq(&dev->event_lock);
|
||||
drm_vblank_put(dev, exynos_crtc->pipe);
|
||||
|
|
|
@ -101,7 +101,7 @@ static void exynos_drm_encoder_disable(struct drm_encoder *encoder)
|
|||
exynos_drm_encoder_dpms(encoder, DRM_MODE_DPMS_OFF);
|
||||
|
||||
/* all planes connected to this encoder should be also disabled. */
|
||||
list_for_each_entry(plane, &dev->mode_config.plane_list, head) {
|
||||
drm_for_each_legacy_plane(plane, &dev->mode_config.plane_list) {
|
||||
if (plane->crtc == encoder->crtc)
|
||||
plane->funcs->disable_plane(plane);
|
||||
}
|
||||
|
|
|
@ -469,7 +469,7 @@ static bool cdv_intel_pipe_enabled(struct drm_device *dev, int pipe)
|
|||
crtc = dev_priv->pipe_to_crtc_mapping[pipe];
|
||||
gma_crtc = to_gma_crtc(crtc);
|
||||
|
||||
if (crtc->fb == NULL || !gma_crtc->active)
|
||||
if (crtc->primary->fb == NULL || !gma_crtc->active)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -1693,7 +1693,7 @@ done:
|
|||
struct drm_crtc *crtc = encoder->base.crtc;
|
||||
drm_crtc_helper_set_mode(crtc, &crtc->mode,
|
||||
crtc->x, crtc->y,
|
||||
crtc->fb);
|
||||
crtc->primary->fb);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
|
|
@ -192,7 +192,7 @@ static int cdv_hdmi_set_property(struct drm_connector *connector,
|
|||
crtc->saved_mode.vdisplay != 0) {
|
||||
if (centre) {
|
||||
if (!drm_crtc_helper_set_mode(encoder->crtc, &crtc->saved_mode,
|
||||
encoder->crtc->x, encoder->crtc->y, encoder->crtc->fb))
|
||||
encoder->crtc->x, encoder->crtc->y, encoder->crtc->primary->fb))
|
||||
return -1;
|
||||
} else {
|
||||
struct drm_encoder_helper_funcs *helpers
|
||||
|
|
|
@ -494,7 +494,7 @@ static int cdv_intel_lvds_set_property(struct drm_connector *connector,
|
|||
&crtc->saved_mode,
|
||||
encoder->crtc->x,
|
||||
encoder->crtc->y,
|
||||
encoder->crtc->fb))
|
||||
encoder->crtc->primary->fb))
|
||||
return -1;
|
||||
}
|
||||
} else if (!strcmp(property->name, "backlight") && encoder) {
|
||||
|
|
|
@ -59,7 +59,7 @@ int gma_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_psb_private *dev_priv = dev->dev_private;
|
||||
struct gma_crtc *gma_crtc = to_gma_crtc(crtc);
|
||||
struct psb_framebuffer *psbfb = to_psb_fb(crtc->fb);
|
||||
struct psb_framebuffer *psbfb = to_psb_fb(crtc->primary->fb);
|
||||
int pipe = gma_crtc->pipe;
|
||||
const struct psb_offset *map = &dev_priv->regmap[pipe];
|
||||
unsigned long start, offset;
|
||||
|
@ -70,7 +70,7 @@ int gma_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
return 0;
|
||||
|
||||
/* no fb bound */
|
||||
if (!crtc->fb) {
|
||||
if (!crtc->primary->fb) {
|
||||
dev_err(dev->dev, "No FB bound\n");
|
||||
goto gma_pipe_cleaner;
|
||||
}
|
||||
|
@ -81,19 +81,19 @@ int gma_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
if (ret < 0)
|
||||
goto gma_pipe_set_base_exit;
|
||||
start = psbfb->gtt->offset;
|
||||
offset = y * crtc->fb->pitches[0] + x * (crtc->fb->bits_per_pixel / 8);
|
||||
offset = y * crtc->primary->fb->pitches[0] + x * (crtc->primary->fb->bits_per_pixel / 8);
|
||||
|
||||
REG_WRITE(map->stride, crtc->fb->pitches[0]);
|
||||
REG_WRITE(map->stride, crtc->primary->fb->pitches[0]);
|
||||
|
||||
dspcntr = REG_READ(map->cntr);
|
||||
dspcntr &= ~DISPPLANE_PIXFORMAT_MASK;
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
dspcntr |= DISPPLANE_8BPP;
|
||||
break;
|
||||
case 16:
|
||||
if (crtc->fb->depth == 15)
|
||||
if (crtc->primary->fb->depth == 15)
|
||||
dspcntr |= DISPPLANE_15_16BPP;
|
||||
else
|
||||
dspcntr |= DISPPLANE_16BPP;
|
||||
|
@ -518,8 +518,8 @@ void gma_crtc_disable(struct drm_crtc *crtc)
|
|||
|
||||
crtc_funcs->dpms(crtc, DRM_MODE_DPMS_OFF);
|
||||
|
||||
if (crtc->fb) {
|
||||
gt = to_psb_fb(crtc->fb)->gtt;
|
||||
if (crtc->primary->fb) {
|
||||
gt = to_psb_fb(crtc->primary->fb)->gtt;
|
||||
psb_gtt_unpin(gt);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -287,7 +287,7 @@ static int mdfld_dsi_connector_set_property(struct drm_connector *connector,
|
|||
&gma_crtc->saved_mode,
|
||||
encoder->crtc->x,
|
||||
encoder->crtc->y,
|
||||
encoder->crtc->fb))
|
||||
encoder->crtc->primary->fb))
|
||||
goto set_prop_error;
|
||||
} else {
|
||||
struct drm_encoder_helper_funcs *funcs =
|
||||
|
|
|
@ -166,7 +166,7 @@ static int mdfld__intel_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_psb_private *dev_priv = dev->dev_private;
|
||||
struct gma_crtc *gma_crtc = to_gma_crtc(crtc);
|
||||
struct psb_framebuffer *psbfb = to_psb_fb(crtc->fb);
|
||||
struct psb_framebuffer *psbfb = to_psb_fb(crtc->primary->fb);
|
||||
int pipe = gma_crtc->pipe;
|
||||
const struct psb_offset *map = &dev_priv->regmap[pipe];
|
||||
unsigned long start, offset;
|
||||
|
@ -178,12 +178,12 @@ static int mdfld__intel_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
dev_dbg(dev->dev, "pipe = 0x%x.\n", pipe);
|
||||
|
||||
/* no fb bound */
|
||||
if (!crtc->fb) {
|
||||
if (!crtc->primary->fb) {
|
||||
dev_dbg(dev->dev, "No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
ret = check_fb(crtc->fb);
|
||||
ret = check_fb(crtc->primary->fb);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
@ -196,18 +196,18 @@ static int mdfld__intel_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
return 0;
|
||||
|
||||
start = psbfb->gtt->offset;
|
||||
offset = y * crtc->fb->pitches[0] + x * (crtc->fb->bits_per_pixel / 8);
|
||||
offset = y * crtc->primary->fb->pitches[0] + x * (crtc->primary->fb->bits_per_pixel / 8);
|
||||
|
||||
REG_WRITE(map->stride, crtc->fb->pitches[0]);
|
||||
REG_WRITE(map->stride, crtc->primary->fb->pitches[0]);
|
||||
dspcntr = REG_READ(map->cntr);
|
||||
dspcntr &= ~DISPPLANE_PIXFORMAT_MASK;
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
dspcntr |= DISPPLANE_8BPP;
|
||||
break;
|
||||
case 16:
|
||||
if (crtc->fb->depth == 15)
|
||||
if (crtc->primary->fb->depth == 15)
|
||||
dspcntr |= DISPPLANE_15_16BPP;
|
||||
else
|
||||
dspcntr |= DISPPLANE_16BPP;
|
||||
|
@ -700,7 +700,7 @@ static int mdfld_crtc_mode_set(struct drm_crtc *crtc,
|
|||
}
|
||||
#endif
|
||||
|
||||
ret = check_fb(crtc->fb);
|
||||
ret = check_fb(crtc->primary->fb);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
|
|
@ -599,7 +599,7 @@ static int oaktrail_pipe_set_base(struct drm_crtc *crtc,
|
|||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_psb_private *dev_priv = dev->dev_private;
|
||||
struct gma_crtc *gma_crtc = to_gma_crtc(crtc);
|
||||
struct psb_framebuffer *psbfb = to_psb_fb(crtc->fb);
|
||||
struct psb_framebuffer *psbfb = to_psb_fb(crtc->primary->fb);
|
||||
int pipe = gma_crtc->pipe;
|
||||
const struct psb_offset *map = &dev_priv->regmap[pipe];
|
||||
unsigned long start, offset;
|
||||
|
@ -608,7 +608,7 @@ static int oaktrail_pipe_set_base(struct drm_crtc *crtc,
|
|||
int ret = 0;
|
||||
|
||||
/* no fb bound */
|
||||
if (!crtc->fb) {
|
||||
if (!crtc->primary->fb) {
|
||||
dev_dbg(dev->dev, "No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -617,19 +617,19 @@ static int oaktrail_pipe_set_base(struct drm_crtc *crtc,
|
|||
return 0;
|
||||
|
||||
start = psbfb->gtt->offset;
|
||||
offset = y * crtc->fb->pitches[0] + x * (crtc->fb->bits_per_pixel / 8);
|
||||
offset = y * crtc->primary->fb->pitches[0] + x * (crtc->primary->fb->bits_per_pixel / 8);
|
||||
|
||||
REG_WRITE(map->stride, crtc->fb->pitches[0]);
|
||||
REG_WRITE(map->stride, crtc->primary->fb->pitches[0]);
|
||||
|
||||
dspcntr = REG_READ(map->cntr);
|
||||
dspcntr &= ~DISPPLANE_PIXFORMAT_MASK;
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
dspcntr |= DISPPLANE_8BPP;
|
||||
break;
|
||||
case 16:
|
||||
if (crtc->fb->depth == 15)
|
||||
if (crtc->primary->fb->depth == 15)
|
||||
dspcntr |= DISPPLANE_15_16BPP;
|
||||
else
|
||||
dspcntr |= DISPPLANE_16BPP;
|
||||
|
|
|
@ -120,7 +120,7 @@ static int psb_intel_crtc_mode_set(struct drm_crtc *crtc,
|
|||
const struct gma_limit_t *limit;
|
||||
|
||||
/* No scan out no play */
|
||||
if (crtc->fb == NULL) {
|
||||
if (crtc->primary->fb == NULL) {
|
||||
crtc_funcs->mode_set_base(crtc, x, y, old_fb);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -614,7 +614,7 @@ int psb_intel_lvds_set_property(struct drm_connector *connector,
|
|||
&crtc->saved_mode,
|
||||
encoder->crtc->x,
|
||||
encoder->crtc->y,
|
||||
encoder->crtc->fb))
|
||||
encoder->crtc->primary->fb))
|
||||
goto set_prop_error;
|
||||
}
|
||||
} else if (!strcmp(property->name, "backlight")) {
|
||||
|
|
|
@ -1844,7 +1844,7 @@ done:
|
|||
if (psb_intel_sdvo->base.base.crtc) {
|
||||
struct drm_crtc *crtc = psb_intel_sdvo->base.base.crtc;
|
||||
drm_crtc_helper_set_mode(crtc, &crtc->mode, crtc->x,
|
||||
crtc->y, crtc->fb);
|
||||
crtc->y, crtc->primary->fb);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
|
|
@ -2172,8 +2172,8 @@ static void intel_crtc_info(struct seq_file *m, struct intel_crtc *intel_crtc)
|
|||
struct intel_encoder *intel_encoder;
|
||||
|
||||
seq_printf(m, "\tfb: %d, pos: %dx%d, size: %dx%d\n",
|
||||
crtc->fb->base.id, crtc->x, crtc->y,
|
||||
crtc->fb->width, crtc->fb->height);
|
||||
crtc->primary->fb->base.id, crtc->x, crtc->y,
|
||||
crtc->primary->fb->width, crtc->primary->fb->height);
|
||||
for_each_encoder_on_crtc(dev, crtc, intel_encoder)
|
||||
intel_encoder_info(m, intel_crtc, intel_encoder);
|
||||
}
|
||||
|
|
|
@ -2367,8 +2367,8 @@ static void __always_unused i915_pageflip_stall_check(struct drm_device *dev, in
|
|||
} else {
|
||||
int dspaddr = DSPADDR(intel_crtc->plane);
|
||||
stall_detected = I915_READ(dspaddr) == (i915_gem_obj_ggtt_offset(obj) +
|
||||
crtc->y * crtc->fb->pitches[0] +
|
||||
crtc->x * crtc->fb->bits_per_pixel/8);
|
||||
crtc->y * crtc->primary->fb->pitches[0] +
|
||||
crtc->x * crtc->primary->fb->bits_per_pixel/8);
|
||||
}
|
||||
|
||||
spin_unlock_irqrestore(&dev->event_lock, flags);
|
||||
|
|
|
@ -744,7 +744,7 @@ bool intel_crtc_active(struct drm_crtc *crtc)
|
|||
* We can ditch the crtc->fb check as soon as we can
|
||||
* properly reconstruct framebuffers.
|
||||
*/
|
||||
return intel_crtc->active && crtc->fb &&
|
||||
return intel_crtc->active && crtc->primary->fb &&
|
||||
intel_crtc->config.adjusted_mode.crtc_clock;
|
||||
}
|
||||
|
||||
|
@ -2291,8 +2291,8 @@ void intel_display_handle_reset(struct drm_device *dev)
|
|||
* disabling them without disabling the entire crtc) allow again
|
||||
* a NULL crtc->fb.
|
||||
*/
|
||||
if (intel_crtc->active && crtc->fb)
|
||||
dev_priv->display.update_plane(crtc, crtc->fb,
|
||||
if (intel_crtc->active && crtc->primary->fb)
|
||||
dev_priv->display.update_plane(crtc, crtc->primary->fb,
|
||||
crtc->x, crtc->y);
|
||||
mutex_unlock(&crtc->mutex);
|
||||
}
|
||||
|
@ -2417,8 +2417,8 @@ intel_pipe_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
return ret;
|
||||
}
|
||||
|
||||
old_fb = crtc->fb;
|
||||
crtc->fb = fb;
|
||||
old_fb = crtc->primary->fb;
|
||||
crtc->primary->fb = fb;
|
||||
crtc->x = x;
|
||||
crtc->y = y;
|
||||
|
||||
|
@ -3009,7 +3009,7 @@ static void intel_crtc_wait_for_pending_flips(struct drm_crtc *crtc)
|
|||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
|
||||
if (crtc->fb == NULL)
|
||||
if (crtc->primary->fb == NULL)
|
||||
return;
|
||||
|
||||
WARN_ON(waitqueue_active(&dev_priv->pending_flip_queue));
|
||||
|
@ -3018,7 +3018,7 @@ static void intel_crtc_wait_for_pending_flips(struct drm_crtc *crtc)
|
|||
!intel_crtc_has_pending_flip(crtc));
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
intel_finish_fb(crtc->fb);
|
||||
intel_finish_fb(crtc->primary->fb);
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
}
|
||||
|
||||
|
@ -3423,22 +3423,28 @@ static void intel_enable_planes(struct drm_crtc *crtc)
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
enum pipe pipe = to_intel_crtc(crtc)->pipe;
|
||||
struct drm_plane *plane;
|
||||
struct intel_plane *intel_plane;
|
||||
|
||||
list_for_each_entry(intel_plane, &dev->mode_config.plane_list, base.head)
|
||||
drm_for_each_legacy_plane(plane, &dev->mode_config.plane_list) {
|
||||
intel_plane = to_intel_plane(plane);
|
||||
if (intel_plane->pipe == pipe)
|
||||
intel_plane_restore(&intel_plane->base);
|
||||
}
|
||||
}
|
||||
|
||||
static void intel_disable_planes(struct drm_crtc *crtc)
|
||||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
enum pipe pipe = to_intel_crtc(crtc)->pipe;
|
||||
struct drm_plane *plane;
|
||||
struct intel_plane *intel_plane;
|
||||
|
||||
list_for_each_entry(intel_plane, &dev->mode_config.plane_list, base.head)
|
||||
drm_for_each_legacy_plane(plane, &dev->mode_config.plane_list) {
|
||||
intel_plane = to_intel_plane(plane);
|
||||
if (intel_plane->pipe == pipe)
|
||||
intel_plane_disable(&intel_plane->base);
|
||||
}
|
||||
}
|
||||
|
||||
void hsw_enable_ips(struct intel_crtc *crtc)
|
||||
|
@ -4460,11 +4466,11 @@ static void intel_crtc_disable(struct drm_crtc *crtc)
|
|||
assert_cursor_disabled(dev_priv, to_intel_crtc(crtc)->pipe);
|
||||
assert_pipe_disabled(dev->dev_private, to_intel_crtc(crtc)->pipe);
|
||||
|
||||
if (crtc->fb) {
|
||||
if (crtc->primary->fb) {
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
intel_unpin_fb_obj(to_intel_framebuffer(crtc->fb)->obj);
|
||||
intel_unpin_fb_obj(to_intel_framebuffer(crtc->primary->fb)->obj);
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
}
|
||||
|
||||
/* Update computed state. */
|
||||
|
@ -8243,7 +8249,7 @@ void intel_mark_idle(struct drm_device *dev)
|
|||
goto out;
|
||||
|
||||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
if (!crtc->fb)
|
||||
if (!crtc->primary->fb)
|
||||
continue;
|
||||
|
||||
intel_decrease_pllclock(crtc);
|
||||
|
@ -8266,10 +8272,10 @@ void intel_mark_fb_busy(struct drm_i915_gem_object *obj,
|
|||
return;
|
||||
|
||||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
if (!crtc->fb)
|
||||
if (!crtc->primary->fb)
|
||||
continue;
|
||||
|
||||
if (to_intel_framebuffer(crtc->fb)->obj != obj)
|
||||
if (to_intel_framebuffer(crtc->primary->fb)->obj != obj)
|
||||
continue;
|
||||
|
||||
intel_increase_pllclock(crtc);
|
||||
|
@ -8697,7 +8703,7 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_framebuffer *old_fb = crtc->fb;
|
||||
struct drm_framebuffer *old_fb = crtc->primary->fb;
|
||||
struct drm_i915_gem_object *obj = to_intel_framebuffer(fb)->obj;
|
||||
struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
|
||||
struct intel_unpin_work *work;
|
||||
|
@ -8705,7 +8711,7 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
|
|||
int ret;
|
||||
|
||||
/* Can't change pixel format via MI display flips. */
|
||||
if (fb->pixel_format != crtc->fb->pixel_format)
|
||||
if (fb->pixel_format != crtc->primary->fb->pixel_format)
|
||||
return -EINVAL;
|
||||
|
||||
/*
|
||||
|
@ -8713,8 +8719,8 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
|
|||
* Note that pitch changes could also affect these register.
|
||||
*/
|
||||
if (INTEL_INFO(dev)->gen > 3 &&
|
||||
(fb->offsets[0] != crtc->fb->offsets[0] ||
|
||||
fb->pitches[0] != crtc->fb->pitches[0]))
|
||||
(fb->offsets[0] != crtc->primary->fb->offsets[0] ||
|
||||
fb->pitches[0] != crtc->primary->fb->pitches[0]))
|
||||
return -EINVAL;
|
||||
|
||||
if (i915_terminally_wedged(&dev_priv->gpu_error))
|
||||
|
@ -8757,7 +8763,7 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
|
|||
drm_gem_object_reference(&work->old_fb_obj->base);
|
||||
drm_gem_object_reference(&obj->base);
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
|
||||
work->pending_flip_obj = obj;
|
||||
|
||||
|
@ -8780,7 +8786,7 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
|
|||
|
||||
cleanup_pending:
|
||||
atomic_dec(&intel_crtc->unpin_work_count);
|
||||
crtc->fb = old_fb;
|
||||
crtc->primary->fb = old_fb;
|
||||
drm_gem_object_unreference(&work->old_fb_obj->base);
|
||||
drm_gem_object_unreference(&obj->base);
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
|
@ -9797,7 +9803,7 @@ static int intel_set_mode(struct drm_crtc *crtc,
|
|||
|
||||
void intel_crtc_restore_mode(struct drm_crtc *crtc)
|
||||
{
|
||||
intel_set_mode(crtc, &crtc->mode, crtc->x, crtc->y, crtc->fb);
|
||||
intel_set_mode(crtc, &crtc->mode, crtc->x, crtc->y, crtc->primary->fb);
|
||||
}
|
||||
|
||||
#undef for_each_intel_crtc_masked
|
||||
|
@ -9921,9 +9927,9 @@ intel_set_config_compute_mode_changes(struct drm_mode_set *set,
|
|||
* and then just flip_or_move it */
|
||||
if (is_crtc_connector_off(set)) {
|
||||
config->mode_changed = true;
|
||||
} else if (set->crtc->fb != set->fb) {
|
||||
} else if (set->crtc->primary->fb != set->fb) {
|
||||
/* If we have no fb then treat it as a full mode set */
|
||||
if (set->crtc->fb == NULL) {
|
||||
if (set->crtc->primary->fb == NULL) {
|
||||
struct intel_crtc *intel_crtc =
|
||||
to_intel_crtc(set->crtc);
|
||||
|
||||
|
@ -9937,7 +9943,7 @@ intel_set_config_compute_mode_changes(struct drm_mode_set *set,
|
|||
} else if (set->fb == NULL) {
|
||||
config->mode_changed = true;
|
||||
} else if (set->fb->pixel_format !=
|
||||
set->crtc->fb->pixel_format) {
|
||||
set->crtc->primary->fb->pixel_format) {
|
||||
config->mode_changed = true;
|
||||
} else {
|
||||
config->fb_changed = true;
|
||||
|
@ -10150,7 +10156,7 @@ static int intel_crtc_set_config(struct drm_mode_set *set)
|
|||
save_set.mode = &set->crtc->mode;
|
||||
save_set.x = set->crtc->x;
|
||||
save_set.y = set->crtc->y;
|
||||
save_set.fb = set->crtc->fb;
|
||||
save_set.fb = set->crtc->primary->fb;
|
||||
|
||||
/* Compute whether we need a full modeset, only an fb base update or no
|
||||
* change at all. In the future we might also check whether only the
|
||||
|
@ -11467,7 +11473,7 @@ void intel_modeset_setup_hw_state(struct drm_device *dev,
|
|||
dev_priv->pipe_to_crtc_mapping[pipe];
|
||||
|
||||
__intel_set_mode(crtc, &crtc->mode, crtc->x, crtc->y,
|
||||
crtc->fb);
|
||||
crtc->primary->fb);
|
||||
}
|
||||
} else {
|
||||
intel_modeset_update_staged_output_state(dev);
|
||||
|
@ -11516,7 +11522,7 @@ void intel_modeset_cleanup(struct drm_device *dev)
|
|||
|
||||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
/* Skip inactive CRTCs */
|
||||
if (!crtc->fb)
|
||||
if (!crtc->primary->fb)
|
||||
continue;
|
||||
|
||||
intel_increase_pllclock(crtc);
|
||||
|
|
|
@ -1744,7 +1744,7 @@ static bool intel_edp_psr_match_conditions(struct intel_dp *intel_dp)
|
|||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_crtc *crtc = dig_port->base.base.crtc;
|
||||
struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
|
||||
struct drm_i915_gem_object *obj = to_intel_framebuffer(crtc->fb)->obj;
|
||||
struct drm_i915_gem_object *obj = to_intel_framebuffer(crtc->primary->fb)->obj;
|
||||
struct intel_encoder *intel_encoder = &dp_to_dig_port(intel_dp)->base;
|
||||
|
||||
dev_priv->psr.source_ok = false;
|
||||
|
@ -1777,7 +1777,7 @@ static bool intel_edp_psr_match_conditions(struct intel_dp *intel_dp)
|
|||
return false;
|
||||
}
|
||||
|
||||
obj = to_intel_framebuffer(crtc->fb)->obj;
|
||||
obj = to_intel_framebuffer(crtc->primary->fb)->obj;
|
||||
if (obj->tiling_mode != I915_TILING_X ||
|
||||
obj->fence_reg == I915_FENCE_REG_NONE) {
|
||||
DRM_DEBUG_KMS("PSR condition failed: fb not tiled or fenced\n");
|
||||
|
|
|
@ -606,14 +606,14 @@ static void update_colorkey(struct intel_overlay *overlay,
|
|||
{
|
||||
u32 key = overlay->color_key;
|
||||
|
||||
switch (overlay->crtc->base.fb->bits_per_pixel) {
|
||||
switch (overlay->crtc->base.primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
iowrite32(0, ®s->DCLRKV);
|
||||
iowrite32(CLK_RGB8I_MASK | DST_KEY_ENABLE, ®s->DCLRKM);
|
||||
break;
|
||||
|
||||
case 16:
|
||||
if (overlay->crtc->base.fb->depth == 15) {
|
||||
if (overlay->crtc->base.primary->fb->depth == 15) {
|
||||
iowrite32(RGB15_TO_COLORKEY(key), ®s->DCLRKV);
|
||||
iowrite32(CLK_RGB15_MASK | DST_KEY_ENABLE,
|
||||
®s->DCLRKM);
|
||||
|
|
|
@ -92,7 +92,7 @@ static void i8xx_enable_fbc(struct drm_crtc *crtc)
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
|
||||
struct drm_i915_gem_object *obj = intel_fb->obj;
|
||||
struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
|
||||
|
@ -149,7 +149,7 @@ static void g4x_enable_fbc(struct drm_crtc *crtc)
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
|
||||
struct drm_i915_gem_object *obj = intel_fb->obj;
|
||||
struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
|
||||
|
@ -221,7 +221,7 @@ static void ironlake_enable_fbc(struct drm_crtc *crtc)
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
|
||||
struct drm_i915_gem_object *obj = intel_fb->obj;
|
||||
struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
|
||||
|
@ -277,7 +277,7 @@ static void gen7_enable_fbc(struct drm_crtc *crtc)
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
struct intel_framebuffer *intel_fb = to_intel_framebuffer(fb);
|
||||
struct drm_i915_gem_object *obj = intel_fb->obj;
|
||||
struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
|
||||
|
@ -336,11 +336,11 @@ static void intel_fbc_work_fn(struct work_struct *__work)
|
|||
/* Double check that we haven't switched fb without cancelling
|
||||
* the prior work.
|
||||
*/
|
||||
if (work->crtc->fb == work->fb) {
|
||||
if (work->crtc->primary->fb == work->fb) {
|
||||
dev_priv->display.enable_fbc(work->crtc);
|
||||
|
||||
dev_priv->fbc.plane = to_intel_crtc(work->crtc)->plane;
|
||||
dev_priv->fbc.fb_id = work->crtc->fb->base.id;
|
||||
dev_priv->fbc.fb_id = work->crtc->primary->fb->base.id;
|
||||
dev_priv->fbc.y = work->crtc->y;
|
||||
}
|
||||
|
||||
|
@ -393,7 +393,7 @@ static void intel_enable_fbc(struct drm_crtc *crtc)
|
|||
}
|
||||
|
||||
work->crtc = crtc;
|
||||
work->fb = crtc->fb;
|
||||
work->fb = crtc->primary->fb;
|
||||
INIT_DELAYED_WORK(&work->work, intel_fbc_work_fn);
|
||||
|
||||
dev_priv->fbc.fbc_work = work;
|
||||
|
@ -499,14 +499,14 @@ void intel_update_fbc(struct drm_device *dev)
|
|||
}
|
||||
}
|
||||
|
||||
if (!crtc || crtc->fb == NULL) {
|
||||
if (!crtc || crtc->primary->fb == NULL) {
|
||||
if (set_no_fbc_reason(dev_priv, FBC_NO_OUTPUT))
|
||||
DRM_DEBUG_KMS("no output, disabling\n");
|
||||
goto out_disable;
|
||||
}
|
||||
|
||||
intel_crtc = to_intel_crtc(crtc);
|
||||
fb = crtc->fb;
|
||||
fb = crtc->primary->fb;
|
||||
intel_fb = to_intel_framebuffer(fb);
|
||||
obj = intel_fb->obj;
|
||||
adjusted_mode = &intel_crtc->config.adjusted_mode;
|
||||
|
@ -1041,7 +1041,7 @@ static void pineview_update_wm(struct drm_crtc *unused_crtc)
|
|||
crtc = single_enabled_crtc(dev);
|
||||
if (crtc) {
|
||||
const struct drm_display_mode *adjusted_mode;
|
||||
int pixel_size = crtc->fb->bits_per_pixel / 8;
|
||||
int pixel_size = crtc->primary->fb->bits_per_pixel / 8;
|
||||
int clock;
|
||||
|
||||
adjusted_mode = &to_intel_crtc(crtc)->config.adjusted_mode;
|
||||
|
@ -1121,7 +1121,7 @@ static bool g4x_compute_wm0(struct drm_device *dev,
|
|||
clock = adjusted_mode->crtc_clock;
|
||||
htotal = adjusted_mode->crtc_htotal;
|
||||
hdisplay = to_intel_crtc(crtc)->config.pipe_src_w;
|
||||
pixel_size = crtc->fb->bits_per_pixel / 8;
|
||||
pixel_size = crtc->primary->fb->bits_per_pixel / 8;
|
||||
|
||||
/* Use the small buffer method to calculate plane watermark */
|
||||
entries = ((clock * pixel_size / 1000) * display_latency_ns) / 1000;
|
||||
|
@ -1208,7 +1208,7 @@ static bool g4x_compute_srwm(struct drm_device *dev,
|
|||
clock = adjusted_mode->crtc_clock;
|
||||
htotal = adjusted_mode->crtc_htotal;
|
||||
hdisplay = to_intel_crtc(crtc)->config.pipe_src_w;
|
||||
pixel_size = crtc->fb->bits_per_pixel / 8;
|
||||
pixel_size = crtc->primary->fb->bits_per_pixel / 8;
|
||||
|
||||
line_time_us = max(htotal * 1000 / clock, 1);
|
||||
line_count = (latency_ns / line_time_us + 1000) / 1000;
|
||||
|
@ -1247,7 +1247,7 @@ static bool vlv_compute_drain_latency(struct drm_device *dev,
|
|||
return false;
|
||||
|
||||
clock = to_intel_crtc(crtc)->config.adjusted_mode.crtc_clock;
|
||||
pixel_size = crtc->fb->bits_per_pixel / 8; /* BPP */
|
||||
pixel_size = crtc->primary->fb->bits_per_pixel / 8; /* BPP */
|
||||
|
||||
entries = (clock / 1000) * pixel_size;
|
||||
*plane_prec_mult = (entries > 256) ?
|
||||
|
@ -1439,7 +1439,7 @@ static void i965_update_wm(struct drm_crtc *unused_crtc)
|
|||
int clock = adjusted_mode->crtc_clock;
|
||||
int htotal = adjusted_mode->crtc_htotal;
|
||||
int hdisplay = to_intel_crtc(crtc)->config.pipe_src_w;
|
||||
int pixel_size = crtc->fb->bits_per_pixel / 8;
|
||||
int pixel_size = crtc->primary->fb->bits_per_pixel / 8;
|
||||
unsigned long line_time_us;
|
||||
int entries;
|
||||
|
||||
|
@ -1512,7 +1512,7 @@ static void i9xx_update_wm(struct drm_crtc *unused_crtc)
|
|||
crtc = intel_get_crtc_for_plane(dev, 0);
|
||||
if (intel_crtc_active(crtc)) {
|
||||
const struct drm_display_mode *adjusted_mode;
|
||||
int cpp = crtc->fb->bits_per_pixel / 8;
|
||||
int cpp = crtc->primary->fb->bits_per_pixel / 8;
|
||||
if (IS_GEN2(dev))
|
||||
cpp = 4;
|
||||
|
||||
|
@ -1528,7 +1528,7 @@ static void i9xx_update_wm(struct drm_crtc *unused_crtc)
|
|||
crtc = intel_get_crtc_for_plane(dev, 1);
|
||||
if (intel_crtc_active(crtc)) {
|
||||
const struct drm_display_mode *adjusted_mode;
|
||||
int cpp = crtc->fb->bits_per_pixel / 8;
|
||||
int cpp = crtc->primary->fb->bits_per_pixel / 8;
|
||||
if (IS_GEN2(dev))
|
||||
cpp = 4;
|
||||
|
||||
|
@ -1565,7 +1565,7 @@ static void i9xx_update_wm(struct drm_crtc *unused_crtc)
|
|||
int clock = adjusted_mode->crtc_clock;
|
||||
int htotal = adjusted_mode->crtc_htotal;
|
||||
int hdisplay = to_intel_crtc(enabled)->config.pipe_src_w;
|
||||
int pixel_size = enabled->fb->bits_per_pixel / 8;
|
||||
int pixel_size = enabled->primary->fb->bits_per_pixel / 8;
|
||||
unsigned long line_time_us;
|
||||
int entries;
|
||||
|
||||
|
@ -2117,7 +2117,7 @@ static void ilk_compute_wm_parameters(struct drm_crtc *crtc,
|
|||
if (p->active) {
|
||||
p->pipe_htotal = intel_crtc->config.adjusted_mode.crtc_htotal;
|
||||
p->pixel_rate = ilk_pipe_pixel_rate(dev, crtc);
|
||||
p->pri.bytes_per_pixel = crtc->fb->bits_per_pixel / 8;
|
||||
p->pri.bytes_per_pixel = crtc->primary->fb->bits_per_pixel / 8;
|
||||
p->cur.bytes_per_pixel = 4;
|
||||
p->pri.horiz_pixels = intel_crtc->config.pipe_src_w;
|
||||
p->cur.horiz_pixels = 64;
|
||||
|
@ -2129,7 +2129,7 @@ static void ilk_compute_wm_parameters(struct drm_crtc *crtc,
|
|||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
|
||||
config->num_pipes_active += intel_crtc_active(crtc);
|
||||
|
||||
list_for_each_entry(plane, &dev->mode_config.plane_list, head) {
|
||||
drm_for_each_legacy_plane(plane, &dev->mode_config.plane_list) {
|
||||
struct intel_plane *intel_plane = to_intel_plane(plane);
|
||||
|
||||
if (intel_plane->pipe == pipe)
|
||||
|
|
|
@ -29,7 +29,7 @@ static void mga_crtc_load_lut(struct drm_crtc *crtc)
|
|||
struct mga_crtc *mga_crtc = to_mga_crtc(crtc);
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct mga_device *mdev = dev->dev_private;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
int i;
|
||||
|
||||
if (!crtc->enabled)
|
||||
|
@ -742,7 +742,7 @@ static int mga_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
mgag200_bo_unreserve(bo);
|
||||
}
|
||||
|
||||
mga_fb = to_mga_framebuffer(crtc->fb);
|
||||
mga_fb = to_mga_framebuffer(crtc->primary->fb);
|
||||
obj = mga_fb->obj;
|
||||
bo = gem_to_mga_bo(obj);
|
||||
|
||||
|
@ -805,7 +805,7 @@ static int mga_crtc_mode_set(struct drm_crtc *crtc,
|
|||
/* 0x48: */ 0, 0, 0, 0, 0, 0, 0, 0
|
||||
};
|
||||
|
||||
bppshift = mdev->bpp_shifts[(crtc->fb->bits_per_pixel >> 3) - 1];
|
||||
bppshift = mdev->bpp_shifts[(crtc->primary->fb->bits_per_pixel >> 3) - 1];
|
||||
|
||||
switch (mdev->type) {
|
||||
case G200_SE_A:
|
||||
|
@ -843,12 +843,12 @@ static int mga_crtc_mode_set(struct drm_crtc *crtc,
|
|||
break;
|
||||
}
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
dacvalue[MGA1064_MUL_CTL] = MGA1064_MUL_CTL_8bits;
|
||||
break;
|
||||
case 16:
|
||||
if (crtc->fb->depth == 15)
|
||||
if (crtc->primary->fb->depth == 15)
|
||||
dacvalue[MGA1064_MUL_CTL] = MGA1064_MUL_CTL_15bits;
|
||||
else
|
||||
dacvalue[MGA1064_MUL_CTL] = MGA1064_MUL_CTL_16bits;
|
||||
|
@ -896,8 +896,8 @@ static int mga_crtc_mode_set(struct drm_crtc *crtc,
|
|||
WREG_SEQ(3, 0);
|
||||
WREG_SEQ(4, 0xe);
|
||||
|
||||
pitch = crtc->fb->pitches[0] / (crtc->fb->bits_per_pixel / 8);
|
||||
if (crtc->fb->bits_per_pixel == 24)
|
||||
pitch = crtc->primary->fb->pitches[0] / (crtc->primary->fb->bits_per_pixel / 8);
|
||||
if (crtc->primary->fb->bits_per_pixel == 24)
|
||||
pitch = (pitch * 3) >> (4 - bppshift);
|
||||
else
|
||||
pitch = pitch >> (4 - bppshift);
|
||||
|
@ -974,7 +974,7 @@ static int mga_crtc_mode_set(struct drm_crtc *crtc,
|
|||
((vdisplay & 0xc00) >> 7) |
|
||||
((vsyncstart & 0xc00) >> 5) |
|
||||
((vdisplay & 0x400) >> 3);
|
||||
if (crtc->fb->bits_per_pixel == 24)
|
||||
if (crtc->primary->fb->bits_per_pixel == 24)
|
||||
ext_vga[3] = (((1 << bppshift) * 3) - 1) | 0x80;
|
||||
else
|
||||
ext_vga[3] = ((1 << bppshift) - 1) | 0x80;
|
||||
|
@ -1034,9 +1034,9 @@ static int mga_crtc_mode_set(struct drm_crtc *crtc,
|
|||
u32 bpp;
|
||||
u32 mb;
|
||||
|
||||
if (crtc->fb->bits_per_pixel > 16)
|
||||
if (crtc->primary->fb->bits_per_pixel > 16)
|
||||
bpp = 32;
|
||||
else if (crtc->fb->bits_per_pixel > 8)
|
||||
else if (crtc->primary->fb->bits_per_pixel > 8)
|
||||
bpp = 16;
|
||||
else
|
||||
bpp = 8;
|
||||
|
@ -1277,8 +1277,8 @@ static void mga_crtc_disable(struct drm_crtc *crtc)
|
|||
int ret;
|
||||
DRM_DEBUG_KMS("\n");
|
||||
mga_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
|
||||
if (crtc->fb) {
|
||||
struct mga_framebuffer *mga_fb = to_mga_framebuffer(crtc->fb);
|
||||
if (crtc->primary->fb) {
|
||||
struct mga_framebuffer *mga_fb = to_mga_framebuffer(crtc->primary->fb);
|
||||
struct drm_gem_object *obj = mga_fb->obj;
|
||||
struct mgag200_bo *bo = gem_to_mga_bo(obj);
|
||||
ret = mgag200_bo_reserve(bo, false);
|
||||
|
@ -1287,7 +1287,7 @@ static void mga_crtc_disable(struct drm_crtc *crtc)
|
|||
mgag200_bo_push_sysram(bo);
|
||||
mgag200_bo_unreserve(bo);
|
||||
}
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
}
|
||||
|
||||
/* These provide the minimum set of functions required to handle a CRTC */
|
||||
|
|
|
@ -120,7 +120,7 @@ static void update_fb(struct drm_crtc *crtc, struct drm_framebuffer *new_fb)
|
|||
|
||||
/* grab reference to incoming scanout fb: */
|
||||
drm_framebuffer_reference(new_fb);
|
||||
mdp4_crtc->base.fb = new_fb;
|
||||
mdp4_crtc->base.primary->fb = new_fb;
|
||||
mdp4_crtc->fb = new_fb;
|
||||
|
||||
if (old_fb)
|
||||
|
@ -182,7 +182,7 @@ static void pageflip_cb(struct msm_fence_cb *cb)
|
|||
struct mdp4_crtc *mdp4_crtc =
|
||||
container_of(cb, struct mdp4_crtc, pageflip_cb);
|
||||
struct drm_crtc *crtc = &mdp4_crtc->base;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
|
||||
if (!fb)
|
||||
return;
|
||||
|
@ -348,14 +348,14 @@ static int mdp4_crtc_mode_set(struct drm_crtc *crtc,
|
|||
mode->type, mode->flags);
|
||||
|
||||
/* grab extra ref for update_scanout() */
|
||||
drm_framebuffer_reference(crtc->fb);
|
||||
drm_framebuffer_reference(crtc->primary->fb);
|
||||
|
||||
ret = mdp4_plane_mode_set(mdp4_crtc->plane, crtc, crtc->fb,
|
||||
ret = mdp4_plane_mode_set(mdp4_crtc->plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x << 16, y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16);
|
||||
if (ret) {
|
||||
drm_framebuffer_unreference(crtc->fb);
|
||||
drm_framebuffer_unreference(crtc->primary->fb);
|
||||
dev_err(crtc->dev->dev, "%s: failed to set mode on plane: %d\n",
|
||||
mdp4_crtc->name, ret);
|
||||
return ret;
|
||||
|
@ -368,7 +368,7 @@ static int mdp4_crtc_mode_set(struct drm_crtc *crtc,
|
|||
/* take data from pipe: */
|
||||
mdp4_write(mdp4_kms, REG_MDP4_DMA_SRC_BASE(dma), 0);
|
||||
mdp4_write(mdp4_kms, REG_MDP4_DMA_SRC_STRIDE(dma),
|
||||
crtc->fb->pitches[0]);
|
||||
crtc->primary->fb->pitches[0]);
|
||||
mdp4_write(mdp4_kms, REG_MDP4_DMA_DST_SIZE(dma),
|
||||
MDP4_DMA_DST_SIZE_WIDTH(0) |
|
||||
MDP4_DMA_DST_SIZE_HEIGHT(0));
|
||||
|
@ -378,7 +378,7 @@ static int mdp4_crtc_mode_set(struct drm_crtc *crtc,
|
|||
MDP4_OVLP_SIZE_WIDTH(mode->hdisplay) |
|
||||
MDP4_OVLP_SIZE_HEIGHT(mode->vdisplay));
|
||||
mdp4_write(mdp4_kms, REG_MDP4_OVLP_STRIDE(ovlp),
|
||||
crtc->fb->pitches[0]);
|
||||
crtc->primary->fb->pitches[0]);
|
||||
|
||||
mdp4_write(mdp4_kms, REG_MDP4_OVLP_CFG(ovlp), 1);
|
||||
|
||||
|
@ -388,8 +388,8 @@ static int mdp4_crtc_mode_set(struct drm_crtc *crtc,
|
|||
mdp4_write(mdp4_kms, REG_MDP4_DMA_E_QUANT(2), 0x00ff0000);
|
||||
}
|
||||
|
||||
update_fb(crtc, crtc->fb);
|
||||
update_scanout(crtc, crtc->fb);
|
||||
update_fb(crtc, crtc->primary->fb);
|
||||
update_scanout(crtc, crtc->primary->fb);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -420,19 +420,19 @@ static int mdp4_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
int ret;
|
||||
|
||||
/* grab extra ref for update_scanout() */
|
||||
drm_framebuffer_reference(crtc->fb);
|
||||
drm_framebuffer_reference(crtc->primary->fb);
|
||||
|
||||
ret = mdp4_plane_mode_set(plane, crtc, crtc->fb,
|
||||
ret = mdp4_plane_mode_set(plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x << 16, y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16);
|
||||
if (ret) {
|
||||
drm_framebuffer_unreference(crtc->fb);
|
||||
drm_framebuffer_unreference(crtc->primary->fb);
|
||||
return ret;
|
||||
}
|
||||
|
||||
update_fb(crtc, crtc->fb);
|
||||
update_scanout(crtc, crtc->fb);
|
||||
update_fb(crtc, crtc->primary->fb);
|
||||
update_scanout(crtc, crtc->primary->fb);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -740,6 +740,9 @@ void mdp4_crtc_attach(struct drm_crtc *crtc, struct drm_plane *plane)
|
|||
|
||||
void mdp4_crtc_detach(struct drm_crtc *crtc, struct drm_plane *plane)
|
||||
{
|
||||
/* don't actually detatch our primary plane: */
|
||||
if (to_mdp4_crtc(crtc)->plane == plane)
|
||||
return;
|
||||
set_attach(crtc, mdp4_plane_pipe(plane), NULL);
|
||||
}
|
||||
|
||||
|
@ -791,7 +794,7 @@ struct drm_crtc *mdp4_crtc_init(struct drm_device *dev,
|
|||
|
||||
INIT_FENCE_CB(&mdp4_crtc->pageflip_cb, pageflip_cb);
|
||||
|
||||
drm_crtc_init(dev, crtc, &mdp4_crtc_funcs);
|
||||
drm_crtc_init_with_planes(dev, crtc, plane, NULL, &mdp4_crtc_funcs);
|
||||
drm_crtc_helper_add(crtc, &mdp4_crtc_helper_funcs);
|
||||
|
||||
mdp4_plane_install_properties(mdp4_crtc->plane, &crtc->base);
|
||||
|
|
|
@ -222,6 +222,7 @@ struct drm_plane *mdp4_plane_init(struct drm_device *dev,
|
|||
struct drm_plane *plane = NULL;
|
||||
struct mdp4_plane *mdp4_plane;
|
||||
int ret;
|
||||
enum drm_plane_type type;
|
||||
|
||||
mdp4_plane = kzalloc(sizeof(*mdp4_plane), GFP_KERNEL);
|
||||
if (!mdp4_plane) {
|
||||
|
@ -237,9 +238,10 @@ struct drm_plane *mdp4_plane_init(struct drm_device *dev,
|
|||
mdp4_plane->nformats = mdp4_get_formats(pipe_id, mdp4_plane->formats,
|
||||
ARRAY_SIZE(mdp4_plane->formats));
|
||||
|
||||
drm_plane_init(dev, plane, 0xff, &mdp4_plane_funcs,
|
||||
mdp4_plane->formats, mdp4_plane->nformats,
|
||||
private_plane);
|
||||
type = private_plane ? DRM_PLANE_TYPE_PRIMARY : DRM_PLANE_TYPE_OVERLAY;
|
||||
drm_universal_plane_init(dev, plane, 0xff, &mdp4_plane_funcs,
|
||||
mdp4_plane->formats, mdp4_plane->nformats,
|
||||
type);
|
||||
|
||||
mdp4_plane_install_properties(plane, &plane->base);
|
||||
|
||||
|
|
|
@ -102,7 +102,7 @@ static void update_fb(struct drm_crtc *crtc, struct drm_framebuffer *new_fb)
|
|||
|
||||
/* grab reference to incoming scanout fb: */
|
||||
drm_framebuffer_reference(new_fb);
|
||||
mdp5_crtc->base.fb = new_fb;
|
||||
mdp5_crtc->base.primary->fb = new_fb;
|
||||
mdp5_crtc->fb = new_fb;
|
||||
|
||||
if (old_fb)
|
||||
|
@ -289,14 +289,14 @@ static int mdp5_crtc_mode_set(struct drm_crtc *crtc,
|
|||
mode->type, mode->flags);
|
||||
|
||||
/* grab extra ref for update_scanout() */
|
||||
drm_framebuffer_reference(crtc->fb);
|
||||
drm_framebuffer_reference(crtc->primary->fb);
|
||||
|
||||
ret = mdp5_plane_mode_set(mdp5_crtc->plane, crtc, crtc->fb,
|
||||
ret = mdp5_plane_mode_set(mdp5_crtc->plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x << 16, y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16);
|
||||
if (ret) {
|
||||
drm_framebuffer_unreference(crtc->fb);
|
||||
drm_framebuffer_unreference(crtc->primary->fb);
|
||||
dev_err(crtc->dev->dev, "%s: failed to set mode on plane: %d\n",
|
||||
mdp5_crtc->name, ret);
|
||||
return ret;
|
||||
|
@ -306,8 +306,8 @@ static int mdp5_crtc_mode_set(struct drm_crtc *crtc,
|
|||
MDP5_LM_OUT_SIZE_WIDTH(mode->hdisplay) |
|
||||
MDP5_LM_OUT_SIZE_HEIGHT(mode->vdisplay));
|
||||
|
||||
update_fb(crtc, crtc->fb);
|
||||
update_scanout(crtc, crtc->fb);
|
||||
update_fb(crtc, crtc->primary->fb);
|
||||
update_scanout(crtc, crtc->primary->fb);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -338,19 +338,19 @@ static int mdp5_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
int ret;
|
||||
|
||||
/* grab extra ref for update_scanout() */
|
||||
drm_framebuffer_reference(crtc->fb);
|
||||
drm_framebuffer_reference(crtc->primary->fb);
|
||||
|
||||
ret = mdp5_plane_mode_set(plane, crtc, crtc->fb,
|
||||
ret = mdp5_plane_mode_set(plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x << 16, y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16);
|
||||
if (ret) {
|
||||
drm_framebuffer_unreference(crtc->fb);
|
||||
drm_framebuffer_unreference(crtc->primary->fb);
|
||||
return ret;
|
||||
}
|
||||
|
||||
update_fb(crtc, crtc->fb);
|
||||
update_scanout(crtc, crtc->fb);
|
||||
update_fb(crtc, crtc->primary->fb);
|
||||
update_scanout(crtc, crtc->primary->fb);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -524,6 +524,9 @@ void mdp5_crtc_attach(struct drm_crtc *crtc, struct drm_plane *plane)
|
|||
|
||||
void mdp5_crtc_detach(struct drm_crtc *crtc, struct drm_plane *plane)
|
||||
{
|
||||
/* don't actually detatch our primary plane: */
|
||||
if (to_mdp5_crtc(crtc)->plane == plane)
|
||||
return;
|
||||
set_attach(crtc, mdp5_plane_pipe(plane), NULL);
|
||||
}
|
||||
|
||||
|
@ -559,7 +562,7 @@ struct drm_crtc *mdp5_crtc_init(struct drm_device *dev,
|
|||
|
||||
INIT_FENCE_CB(&mdp5_crtc->pageflip_cb, pageflip_cb);
|
||||
|
||||
drm_crtc_init(dev, crtc, &mdp5_crtc_funcs);
|
||||
drm_crtc_init_with_planes(dev, crtc, plane, NULL, &mdp5_crtc_funcs);
|
||||
drm_crtc_helper_add(crtc, &mdp5_crtc_helper_funcs);
|
||||
|
||||
mdp5_plane_install_properties(mdp5_crtc->plane, &crtc->base);
|
||||
|
|
|
@ -358,6 +358,7 @@ struct drm_plane *mdp5_plane_init(struct drm_device *dev,
|
|||
struct drm_plane *plane = NULL;
|
||||
struct mdp5_plane *mdp5_plane;
|
||||
int ret;
|
||||
enum drm_plane_type type;
|
||||
|
||||
mdp5_plane = kzalloc(sizeof(*mdp5_plane), GFP_KERNEL);
|
||||
if (!mdp5_plane) {
|
||||
|
@ -373,9 +374,10 @@ struct drm_plane *mdp5_plane_init(struct drm_device *dev,
|
|||
mdp5_plane->nformats = mdp5_get_formats(pipe, mdp5_plane->formats,
|
||||
ARRAY_SIZE(mdp5_plane->formats));
|
||||
|
||||
drm_plane_init(dev, plane, 0xff, &mdp5_plane_funcs,
|
||||
mdp5_plane->formats, mdp5_plane->nformats,
|
||||
private_plane);
|
||||
type = private_plane ? DRM_PLANE_TYPE_PRIMARY : DRM_PLANE_TYPE_OVERLAY;
|
||||
drm_universal_plane_init(dev, plane, 0xff, &mdp5_plane_funcs,
|
||||
mdp5_plane->formats, mdp5_plane->nformats,
|
||||
type);
|
||||
|
||||
mdp5_plane_install_properties(plane, &plane->base);
|
||||
|
||||
|
|
|
@ -239,7 +239,7 @@ nv_crtc_mode_set_vga(struct drm_crtc *crtc, struct drm_display_mode *mode)
|
|||
struct drm_device *dev = crtc->dev;
|
||||
struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
|
||||
struct nv04_crtc_reg *regp = &nv04_display(dev)->mode_reg.crtc_reg[nv_crtc->index];
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
|
||||
/* Calculate our timings */
|
||||
int horizDisplay = (mode->crtc_hdisplay >> 3) - 1;
|
||||
|
@ -574,7 +574,7 @@ nv_crtc_mode_set_regs(struct drm_crtc *crtc, struct drm_display_mode * mode)
|
|||
regp->CRTC[NV_CIO_CRE_86] = 0x1;
|
||||
}
|
||||
|
||||
regp->CRTC[NV_CIO_CRE_PIXEL_INDEX] = (crtc->fb->depth + 1) / 8;
|
||||
regp->CRTC[NV_CIO_CRE_PIXEL_INDEX] = (crtc->primary->fb->depth + 1) / 8;
|
||||
/* Enable slaved mode (called MODE_TV in nv4ref.h) */
|
||||
if (lvds_output || tmds_output || tv_output)
|
||||
regp->CRTC[NV_CIO_CRE_PIXEL_INDEX] |= (1 << 7);
|
||||
|
@ -588,7 +588,7 @@ nv_crtc_mode_set_regs(struct drm_crtc *crtc, struct drm_display_mode * mode)
|
|||
regp->ramdac_gen_ctrl = NV_PRAMDAC_GENERAL_CONTROL_BPC_8BITS |
|
||||
NV_PRAMDAC_GENERAL_CONTROL_VGA_STATE_SEL |
|
||||
NV_PRAMDAC_GENERAL_CONTROL_PIXMIX_ON;
|
||||
if (crtc->fb->depth == 16)
|
||||
if (crtc->primary->fb->depth == 16)
|
||||
regp->ramdac_gen_ctrl |= NV_PRAMDAC_GENERAL_CONTROL_ALT_MODE_SEL;
|
||||
if (nv_device(drm->device)->chipset >= 0x11)
|
||||
regp->ramdac_gen_ctrl |= NV_PRAMDAC_GENERAL_CONTROL_PIPE_LONG;
|
||||
|
@ -609,7 +609,7 @@ static int
|
|||
nv_crtc_swap_fbs(struct drm_crtc *crtc, struct drm_framebuffer *old_fb)
|
||||
{
|
||||
struct nv04_display *disp = nv04_display(crtc->dev);
|
||||
struct nouveau_framebuffer *nvfb = nouveau_framebuffer(crtc->fb);
|
||||
struct nouveau_framebuffer *nvfb = nouveau_framebuffer(crtc->primary->fb);
|
||||
struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
|
||||
int ret;
|
||||
|
||||
|
@ -808,7 +808,7 @@ nv_crtc_gamma_set(struct drm_crtc *crtc, u16 *r, u16 *g, u16 *b, uint32_t start,
|
|||
* mark the lut values as dirty by setting depth==0, and it'll be
|
||||
* uploaded on the first mode_set_base()
|
||||
*/
|
||||
if (!nv_crtc->base.fb) {
|
||||
if (!nv_crtc->base.primary->fb) {
|
||||
nv_crtc->lut.depth = 0;
|
||||
return;
|
||||
}
|
||||
|
@ -832,7 +832,7 @@ nv04_crtc_do_mode_set_base(struct drm_crtc *crtc,
|
|||
NV_DEBUG(drm, "index %d\n", nv_crtc->index);
|
||||
|
||||
/* no fb bound */
|
||||
if (!atomic && !crtc->fb) {
|
||||
if (!atomic && !crtc->primary->fb) {
|
||||
NV_DEBUG(drm, "No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -844,8 +844,8 @@ nv04_crtc_do_mode_set_base(struct drm_crtc *crtc,
|
|||
drm_fb = passed_fb;
|
||||
fb = nouveau_framebuffer(passed_fb);
|
||||
} else {
|
||||
drm_fb = crtc->fb;
|
||||
fb = nouveau_framebuffer(crtc->fb);
|
||||
drm_fb = crtc->primary->fb;
|
||||
fb = nouveau_framebuffer(crtc->primary->fb);
|
||||
}
|
||||
|
||||
nv_crtc->fb.offset = fb->nvbo->bo.offset;
|
||||
|
@ -857,9 +857,9 @@ nv04_crtc_do_mode_set_base(struct drm_crtc *crtc,
|
|||
|
||||
/* Update the framebuffer format. */
|
||||
regp->CRTC[NV_CIO_CRE_PIXEL_INDEX] &= ~3;
|
||||
regp->CRTC[NV_CIO_CRE_PIXEL_INDEX] |= (crtc->fb->depth + 1) / 8;
|
||||
regp->CRTC[NV_CIO_CRE_PIXEL_INDEX] |= (crtc->primary->fb->depth + 1) / 8;
|
||||
regp->ramdac_gen_ctrl &= ~NV_PRAMDAC_GENERAL_CONTROL_ALT_MODE_SEL;
|
||||
if (crtc->fb->depth == 16)
|
||||
if (crtc->primary->fb->depth == 16)
|
||||
regp->ramdac_gen_ctrl |= NV_PRAMDAC_GENERAL_CONTROL_ALT_MODE_SEL;
|
||||
crtc_wr_cio_state(crtc, regp, NV_CIO_CRE_PIXEL_INDEX);
|
||||
NVWriteRAMDAC(dev, nv_crtc->index, NV_PRAMDAC_GENERAL_CONTROL,
|
||||
|
|
|
@ -415,7 +415,7 @@ static void nv04_dfp_mode_set(struct drm_encoder *encoder,
|
|||
/* Output property. */
|
||||
if ((nv_connector->dithering_mode == DITHERING_MODE_ON) ||
|
||||
(nv_connector->dithering_mode == DITHERING_MODE_AUTO &&
|
||||
encoder->crtc->fb->depth > connector->display_info.bpc * 3)) {
|
||||
encoder->crtc->primary->fb->depth > connector->display_info.bpc * 3)) {
|
||||
if (nv_device(drm->device)->chipset == 0x11)
|
||||
regp->dither = savep->dither | 0x00010000;
|
||||
else {
|
||||
|
|
|
@ -571,7 +571,7 @@ nouveau_display_suspend(struct drm_device *dev)
|
|||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
struct nouveau_framebuffer *nouveau_fb;
|
||||
|
||||
nouveau_fb = nouveau_framebuffer(crtc->fb);
|
||||
nouveau_fb = nouveau_framebuffer(crtc->primary->fb);
|
||||
if (!nouveau_fb || !nouveau_fb->nvbo)
|
||||
continue;
|
||||
|
||||
|
@ -598,7 +598,7 @@ nouveau_display_repin(struct drm_device *dev)
|
|||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
struct nouveau_framebuffer *nouveau_fb;
|
||||
|
||||
nouveau_fb = nouveau_framebuffer(crtc->fb);
|
||||
nouveau_fb = nouveau_framebuffer(crtc->primary->fb);
|
||||
if (!nouveau_fb || !nouveau_fb->nvbo)
|
||||
continue;
|
||||
|
||||
|
@ -695,7 +695,7 @@ nouveau_crtc_page_flip(struct drm_crtc *crtc, struct drm_framebuffer *fb,
|
|||
const int swap_interval = (flags & DRM_MODE_PAGE_FLIP_ASYNC) ? 0 : 1;
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct nouveau_drm *drm = nouveau_drm(dev);
|
||||
struct nouveau_bo *old_bo = nouveau_framebuffer(crtc->fb)->nvbo;
|
||||
struct nouveau_bo *old_bo = nouveau_framebuffer(crtc->primary->fb)->nvbo;
|
||||
struct nouveau_bo *new_bo = nouveau_framebuffer(fb)->nvbo;
|
||||
struct nouveau_page_flip_state *s;
|
||||
struct nouveau_channel *chan = drm->channel;
|
||||
|
@ -769,7 +769,7 @@ nouveau_crtc_page_flip(struct drm_crtc *crtc, struct drm_framebuffer *fb,
|
|||
goto fail_unreserve;
|
||||
|
||||
/* Update the crtc struct and cleanup */
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
|
||||
nouveau_bo_fence(old_bo, fence);
|
||||
ttm_bo_unreserve(&old_bo->bo);
|
||||
|
|
|
@ -651,7 +651,7 @@ nv50_crtc_set_dither(struct nouveau_crtc *nv_crtc, bool update)
|
|||
nv_connector = nouveau_crtc_connector_get(nv_crtc);
|
||||
connector = &nv_connector->base;
|
||||
if (nv_connector->dithering_mode == DITHERING_MODE_AUTO) {
|
||||
if (nv_crtc->base.fb->depth > connector->display_info.bpc * 3)
|
||||
if (nv_crtc->base.primary->fb->depth > connector->display_info.bpc * 3)
|
||||
mode = DITHERING_MODE_DYNAMIC2X2;
|
||||
} else {
|
||||
mode = nv_connector->dithering_mode;
|
||||
|
@ -785,7 +785,8 @@ nv50_crtc_set_scale(struct nouveau_crtc *nv_crtc, bool update)
|
|||
|
||||
if (update) {
|
||||
nv50_display_flip_stop(crtc);
|
||||
nv50_display_flip_next(crtc, crtc->fb, NULL, 1);
|
||||
nv50_display_flip_next(crtc, crtc->primary->fb,
|
||||
NULL, 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1028,7 +1029,7 @@ nv50_crtc_commit(struct drm_crtc *crtc)
|
|||
}
|
||||
|
||||
nv50_crtc_cursor_show_hide(nv_crtc, nv_crtc->cursor.visible, true);
|
||||
nv50_display_flip_next(crtc, crtc->fb, NULL, 1);
|
||||
nv50_display_flip_next(crtc, crtc->primary->fb, NULL, 1);
|
||||
}
|
||||
|
||||
static bool
|
||||
|
@ -1042,7 +1043,7 @@ nv50_crtc_mode_fixup(struct drm_crtc *crtc, const struct drm_display_mode *mode,
|
|||
static int
|
||||
nv50_crtc_swap_fbs(struct drm_crtc *crtc, struct drm_framebuffer *old_fb)
|
||||
{
|
||||
struct nouveau_framebuffer *nvfb = nouveau_framebuffer(crtc->fb);
|
||||
struct nouveau_framebuffer *nvfb = nouveau_framebuffer(crtc->primary->fb);
|
||||
struct nv50_head *head = nv50_head(crtc);
|
||||
int ret;
|
||||
|
||||
|
@ -1139,7 +1140,7 @@ nv50_crtc_mode_set(struct drm_crtc *crtc, struct drm_display_mode *umode,
|
|||
nv50_crtc_set_dither(nv_crtc, false);
|
||||
nv50_crtc_set_scale(nv_crtc, false);
|
||||
nv50_crtc_set_color_vibrance(nv_crtc, false);
|
||||
nv50_crtc_set_image(nv_crtc, crtc->fb, x, y, false);
|
||||
nv50_crtc_set_image(nv_crtc, crtc->primary->fb, x, y, false);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1151,7 +1152,7 @@ nv50_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
|
||||
int ret;
|
||||
|
||||
if (!crtc->fb) {
|
||||
if (!crtc->primary->fb) {
|
||||
NV_DEBUG(drm, "No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -1161,8 +1162,8 @@ nv50_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
return ret;
|
||||
|
||||
nv50_display_flip_stop(crtc);
|
||||
nv50_crtc_set_image(nv_crtc, crtc->fb, x, y, true);
|
||||
nv50_display_flip_next(crtc, crtc->fb, NULL, 1);
|
||||
nv50_crtc_set_image(nv_crtc, crtc->primary->fb, x, y, true);
|
||||
nv50_display_flip_next(crtc, crtc->primary->fb, NULL, 1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -245,7 +245,7 @@ static int omap_crtc_mode_set(struct drm_crtc *crtc,
|
|||
copy_timings_drm_to_omap(&omap_crtc->timings, mode);
|
||||
omap_crtc->full_update = true;
|
||||
|
||||
return omap_plane_mode_set(omap_crtc->plane, crtc, crtc->fb,
|
||||
return omap_plane_mode_set(omap_crtc->plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x << 16, y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16,
|
||||
|
@ -273,7 +273,7 @@ static int omap_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
struct drm_plane *plane = omap_crtc->plane;
|
||||
struct drm_display_mode *mode = &crtc->mode;
|
||||
|
||||
return omap_plane_mode_set(plane, crtc, crtc->fb,
|
||||
return omap_plane_mode_set(plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x << 16, y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16,
|
||||
|
@ -308,14 +308,14 @@ static void page_flip_worker(struct work_struct *work)
|
|||
struct drm_gem_object *bo;
|
||||
|
||||
mutex_lock(&crtc->mutex);
|
||||
omap_plane_mode_set(omap_crtc->plane, crtc, crtc->fb,
|
||||
omap_plane_mode_set(omap_crtc->plane, crtc, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
crtc->x << 16, crtc->y << 16,
|
||||
mode->hdisplay << 16, mode->vdisplay << 16,
|
||||
vblank_cb, crtc);
|
||||
mutex_unlock(&crtc->mutex);
|
||||
|
||||
bo = omap_framebuffer_bo(crtc->fb, 0);
|
||||
bo = omap_framebuffer_bo(crtc->primary->fb, 0);
|
||||
drm_gem_object_unreference_unlocked(bo);
|
||||
}
|
||||
|
||||
|
@ -336,9 +336,10 @@ static int omap_crtc_page_flip_locked(struct drm_crtc *crtc,
|
|||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct omap_crtc *omap_crtc = to_omap_crtc(crtc);
|
||||
struct drm_plane *primary = crtc->primary;
|
||||
struct drm_gem_object *bo;
|
||||
|
||||
DBG("%d -> %d (event=%p)", crtc->fb ? crtc->fb->base.id : -1,
|
||||
DBG("%d -> %d (event=%p)", primary->fb ? primary->fb->base.id : -1,
|
||||
fb->base.id, event);
|
||||
|
||||
if (omap_crtc->old_fb) {
|
||||
|
@ -347,7 +348,7 @@ static int omap_crtc_page_flip_locked(struct drm_crtc *crtc,
|
|||
}
|
||||
|
||||
omap_crtc->event = event;
|
||||
crtc->fb = fb;
|
||||
primary->fb = fb;
|
||||
|
||||
/*
|
||||
* Hold a reference temporarily until the crtc is updated
|
||||
|
|
|
@ -312,7 +312,7 @@ struct drm_connector *omap_framebuffer_get_next_connector(
|
|||
if (connector != from) {
|
||||
struct drm_encoder *encoder = connector->encoder;
|
||||
struct drm_crtc *crtc = encoder ? encoder->crtc : NULL;
|
||||
if (crtc && crtc->fb == fb)
|
||||
if (crtc && crtc->primary->fb == fb)
|
||||
return connector;
|
||||
|
||||
}
|
||||
|
|
|
@ -527,7 +527,7 @@ static int qxl_crtc_mode_set(struct drm_crtc *crtc,
|
|||
bool recreate_primary = false;
|
||||
int ret;
|
||||
int surf_id;
|
||||
if (!crtc->fb) {
|
||||
if (!crtc->primary->fb) {
|
||||
DRM_DEBUG_KMS("No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -536,7 +536,7 @@ static int qxl_crtc_mode_set(struct drm_crtc *crtc,
|
|||
qfb = to_qxl_framebuffer(old_fb);
|
||||
old_bo = gem_to_qxl_bo(qfb->obj);
|
||||
}
|
||||
qfb = to_qxl_framebuffer(crtc->fb);
|
||||
qfb = to_qxl_framebuffer(crtc->primary->fb);
|
||||
bo = gem_to_qxl_bo(qfb->obj);
|
||||
if (!m)
|
||||
/* and do we care? */
|
||||
|
@ -609,14 +609,14 @@ static void qxl_crtc_disable(struct drm_crtc *crtc)
|
|||
struct qxl_crtc *qcrtc = to_qxl_crtc(crtc);
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct qxl_device *qdev = dev->dev_private;
|
||||
if (crtc->fb) {
|
||||
struct qxl_framebuffer *qfb = to_qxl_framebuffer(crtc->fb);
|
||||
if (crtc->primary->fb) {
|
||||
struct qxl_framebuffer *qfb = to_qxl_framebuffer(crtc->primary->fb);
|
||||
struct qxl_bo *bo = gem_to_qxl_bo(qfb->obj);
|
||||
int ret;
|
||||
ret = qxl_bo_reserve(bo, false);
|
||||
qxl_bo_unpin(bo);
|
||||
qxl_bo_unreserve(bo);
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
}
|
||||
|
||||
qxl_monitors_config_set(qdev, qcrtc->index, 0, 0, 0, 0, 0);
|
||||
|
|
|
@ -1106,7 +1106,7 @@ static int dce4_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
int r;
|
||||
|
||||
/* no fb bound */
|
||||
if (!atomic && !crtc->fb) {
|
||||
if (!atomic && !crtc->primary->fb) {
|
||||
DRM_DEBUG_KMS("No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -1116,8 +1116,8 @@ static int dce4_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
target_fb = fb;
|
||||
}
|
||||
else {
|
||||
radeon_fb = to_radeon_framebuffer(crtc->fb);
|
||||
target_fb = crtc->fb;
|
||||
radeon_fb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
target_fb = crtc->primary->fb;
|
||||
}
|
||||
|
||||
/* If atomic, assume fb object is pinned & idle & fenced and
|
||||
|
@ -1316,7 +1316,7 @@ static int dce4_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
/* set pageflip to happen anywhere in vblank interval */
|
||||
WREG32(EVERGREEN_MASTER_UPDATE_MODE + radeon_crtc->crtc_offset, 0);
|
||||
|
||||
if (!atomic && fb && fb != crtc->fb) {
|
||||
if (!atomic && fb && fb != crtc->primary->fb) {
|
||||
radeon_fb = to_radeon_framebuffer(fb);
|
||||
rbo = gem_to_radeon_bo(radeon_fb->obj);
|
||||
r = radeon_bo_reserve(rbo, false);
|
||||
|
@ -1350,7 +1350,7 @@ static int avivo_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
int r;
|
||||
|
||||
/* no fb bound */
|
||||
if (!atomic && !crtc->fb) {
|
||||
if (!atomic && !crtc->primary->fb) {
|
||||
DRM_DEBUG_KMS("No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -1360,8 +1360,8 @@ static int avivo_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
target_fb = fb;
|
||||
}
|
||||
else {
|
||||
radeon_fb = to_radeon_framebuffer(crtc->fb);
|
||||
target_fb = crtc->fb;
|
||||
radeon_fb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
target_fb = crtc->primary->fb;
|
||||
}
|
||||
|
||||
obj = radeon_fb->obj;
|
||||
|
@ -1485,7 +1485,7 @@ static int avivo_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
/* set pageflip to happen anywhere in vblank interval */
|
||||
WREG32(AVIVO_D1MODE_MASTER_UPDATE_MODE + radeon_crtc->crtc_offset, 0);
|
||||
|
||||
if (!atomic && fb && fb != crtc->fb) {
|
||||
if (!atomic && fb && fb != crtc->primary->fb) {
|
||||
radeon_fb = to_radeon_framebuffer(fb);
|
||||
rbo = gem_to_radeon_bo(radeon_fb->obj);
|
||||
r = radeon_bo_reserve(rbo, false);
|
||||
|
@ -1972,12 +1972,12 @@ static void atombios_crtc_disable(struct drm_crtc *crtc)
|
|||
int i;
|
||||
|
||||
atombios_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
|
||||
if (crtc->fb) {
|
||||
if (crtc->primary->fb) {
|
||||
int r;
|
||||
struct radeon_framebuffer *radeon_fb;
|
||||
struct radeon_bo *rbo;
|
||||
|
||||
radeon_fb = to_radeon_framebuffer(crtc->fb);
|
||||
radeon_fb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
rbo = gem_to_radeon_bo(radeon_fb->obj);
|
||||
r = radeon_bo_reserve(rbo, false);
|
||||
if (unlikely(r))
|
||||
|
|
|
@ -3220,12 +3220,12 @@ void r100_bandwidth_update(struct radeon_device *rdev)
|
|||
|
||||
if (rdev->mode_info.crtcs[0]->base.enabled) {
|
||||
mode1 = &rdev->mode_info.crtcs[0]->base.mode;
|
||||
pixel_bytes1 = rdev->mode_info.crtcs[0]->base.fb->bits_per_pixel / 8;
|
||||
pixel_bytes1 = rdev->mode_info.crtcs[0]->base.primary->fb->bits_per_pixel / 8;
|
||||
}
|
||||
if (!(rdev->flags & RADEON_SINGLE_CRTC)) {
|
||||
if (rdev->mode_info.crtcs[1]->base.enabled) {
|
||||
mode2 = &rdev->mode_info.crtcs[1]->base.mode;
|
||||
pixel_bytes2 = rdev->mode_info.crtcs[1]->base.fb->bits_per_pixel / 8;
|
||||
pixel_bytes2 = rdev->mode_info.crtcs[1]->base.primary->fb->bits_per_pixel / 8;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -89,7 +89,7 @@ static void radeon_property_change_mode(struct drm_encoder *encoder)
|
|||
|
||||
if (crtc && crtc->enabled) {
|
||||
drm_crtc_helper_set_mode(crtc, &crtc->mode,
|
||||
crtc->x, crtc->y, crtc->fb);
|
||||
crtc->x, crtc->y, crtc->primary->fb);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1424,7 +1424,7 @@ int radeon_suspend_kms(struct drm_device *dev, bool suspend, bool fbcon)
|
|||
|
||||
/* unpin the front buffers */
|
||||
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
|
||||
struct radeon_framebuffer *rfb = to_radeon_framebuffer(crtc->fb);
|
||||
struct radeon_framebuffer *rfb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
struct radeon_bo *robj;
|
||||
|
||||
if (rfb == NULL || rfb->obj == NULL) {
|
||||
|
|
|
@ -369,7 +369,7 @@ static int radeon_crtc_page_flip(struct drm_crtc *crtc,
|
|||
work->event = event;
|
||||
work->rdev = rdev;
|
||||
work->crtc_id = radeon_crtc->crtc_id;
|
||||
old_radeon_fb = to_radeon_framebuffer(crtc->fb);
|
||||
old_radeon_fb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
new_radeon_fb = to_radeon_framebuffer(fb);
|
||||
/* schedule unpin of the old buffer */
|
||||
obj = old_radeon_fb->obj;
|
||||
|
@ -460,7 +460,7 @@ static int radeon_crtc_page_flip(struct drm_crtc *crtc,
|
|||
spin_unlock_irqrestore(&dev->event_lock, flags);
|
||||
|
||||
/* update crtc fb */
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
|
||||
r = drm_vblank_get(dev, radeon_crtc->crtc_id);
|
||||
if (r) {
|
||||
|
|
|
@ -385,7 +385,7 @@ int radeon_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
|
||||
DRM_DEBUG_KMS("\n");
|
||||
/* no fb bound */
|
||||
if (!atomic && !crtc->fb) {
|
||||
if (!atomic && !crtc->primary->fb) {
|
||||
DRM_DEBUG_KMS("No FB bound\n");
|
||||
return 0;
|
||||
}
|
||||
|
@ -395,8 +395,8 @@ int radeon_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
target_fb = fb;
|
||||
}
|
||||
else {
|
||||
radeon_fb = to_radeon_framebuffer(crtc->fb);
|
||||
target_fb = crtc->fb;
|
||||
radeon_fb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
target_fb = crtc->primary->fb;
|
||||
}
|
||||
|
||||
switch (target_fb->bits_per_pixel) {
|
||||
|
@ -444,7 +444,7 @@ retry:
|
|||
* We don't shutdown the display controller because new buffer
|
||||
* will end up in same spot.
|
||||
*/
|
||||
if (!atomic && fb && fb != crtc->fb) {
|
||||
if (!atomic && fb && fb != crtc->primary->fb) {
|
||||
struct radeon_bo *old_rbo;
|
||||
unsigned long nsize, osize;
|
||||
|
||||
|
@ -555,7 +555,7 @@ retry:
|
|||
WREG32(RADEON_CRTC_OFFSET + radeon_crtc->crtc_offset, crtc_offset);
|
||||
WREG32(RADEON_CRTC_PITCH + radeon_crtc->crtc_offset, crtc_pitch);
|
||||
|
||||
if (!atomic && fb && fb != crtc->fb) {
|
||||
if (!atomic && fb && fb != crtc->primary->fb) {
|
||||
radeon_fb = to_radeon_framebuffer(fb);
|
||||
rbo = gem_to_radeon_bo(radeon_fb->obj);
|
||||
r = radeon_bo_reserve(rbo, false);
|
||||
|
@ -599,7 +599,7 @@ static bool radeon_set_crtc_timing(struct drm_crtc *crtc, struct drm_display_mod
|
|||
}
|
||||
}
|
||||
|
||||
switch (crtc->fb->bits_per_pixel) {
|
||||
switch (crtc->primary->fb->bits_per_pixel) {
|
||||
case 8:
|
||||
format = 2;
|
||||
break;
|
||||
|
@ -1087,12 +1087,12 @@ static void radeon_crtc_commit(struct drm_crtc *crtc)
|
|||
static void radeon_crtc_disable(struct drm_crtc *crtc)
|
||||
{
|
||||
radeon_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
|
||||
if (crtc->fb) {
|
||||
if (crtc->primary->fb) {
|
||||
int r;
|
||||
struct radeon_framebuffer *radeon_fb;
|
||||
struct radeon_bo *rbo;
|
||||
|
||||
radeon_fb = to_radeon_framebuffer(crtc->fb);
|
||||
radeon_fb = to_radeon_framebuffer(crtc->primary->fb);
|
||||
rbo = gem_to_radeon_bo(radeon_fb->obj);
|
||||
r = radeon_bo_reserve(rbo, false);
|
||||
if (unlikely(r))
|
||||
|
|
|
@ -299,7 +299,7 @@ static void rcar_du_crtc_update_base(struct rcar_du_crtc *rcrtc)
|
|||
{
|
||||
struct drm_crtc *crtc = &rcrtc->crtc;
|
||||
|
||||
rcar_du_plane_compute_base(rcrtc->plane, crtc->fb);
|
||||
rcar_du_plane_compute_base(rcrtc->plane, crtc->primary->fb);
|
||||
rcar_du_plane_update_base(rcrtc->plane);
|
||||
}
|
||||
|
||||
|
@ -358,10 +358,10 @@ static int rcar_du_crtc_mode_set(struct drm_crtc *crtc,
|
|||
const struct rcar_du_format_info *format;
|
||||
int ret;
|
||||
|
||||
format = rcar_du_format_info(crtc->fb->pixel_format);
|
||||
format = rcar_du_format_info(crtc->primary->fb->pixel_format);
|
||||
if (format == NULL) {
|
||||
dev_dbg(rcdu->dev, "mode_set: unsupported format %08x\n",
|
||||
crtc->fb->pixel_format);
|
||||
crtc->primary->fb->pixel_format);
|
||||
ret = -EINVAL;
|
||||
goto error;
|
||||
}
|
||||
|
@ -377,7 +377,7 @@ static int rcar_du_crtc_mode_set(struct drm_crtc *crtc,
|
|||
rcrtc->plane->width = mode->hdisplay;
|
||||
rcrtc->plane->height = mode->vdisplay;
|
||||
|
||||
rcar_du_plane_compute_base(rcrtc->plane, crtc->fb);
|
||||
rcar_du_plane_compute_base(rcrtc->plane, crtc->primary->fb);
|
||||
|
||||
rcrtc->outputs = 0;
|
||||
|
||||
|
@ -510,7 +510,7 @@ static int rcar_du_crtc_page_flip(struct drm_crtc *crtc,
|
|||
}
|
||||
spin_unlock_irqrestore(&dev->event_lock, flags);
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
rcar_du_crtc_update_base(rcrtc);
|
||||
|
||||
if (event) {
|
||||
|
|
|
@ -173,7 +173,7 @@ static void shmob_drm_crtc_start(struct shmob_drm_crtc *scrtc)
|
|||
if (scrtc->started)
|
||||
return;
|
||||
|
||||
format = shmob_drm_format_info(crtc->fb->pixel_format);
|
||||
format = shmob_drm_format_info(crtc->primary->fb->pixel_format);
|
||||
if (WARN_ON(format == NULL))
|
||||
return;
|
||||
|
||||
|
@ -247,7 +247,7 @@ static void shmob_drm_crtc_start(struct shmob_drm_crtc *scrtc)
|
|||
lcdc_write(sdev, LDDDSR, value);
|
||||
|
||||
/* Setup planes. */
|
||||
list_for_each_entry(plane, &dev->mode_config.plane_list, head) {
|
||||
drm_for_each_legacy_plane(plane, &dev->mode_config.plane_list) {
|
||||
if (plane->crtc == crtc)
|
||||
shmob_drm_plane_setup(plane);
|
||||
}
|
||||
|
@ -303,7 +303,7 @@ static void shmob_drm_crtc_compute_base(struct shmob_drm_crtc *scrtc,
|
|||
int x, int y)
|
||||
{
|
||||
struct drm_crtc *crtc = &scrtc->crtc;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
struct shmob_drm_device *sdev = crtc->dev->dev_private;
|
||||
struct drm_gem_cma_object *gem;
|
||||
unsigned int bpp;
|
||||
|
@ -382,15 +382,15 @@ static int shmob_drm_crtc_mode_set(struct drm_crtc *crtc,
|
|||
const struct shmob_drm_format_info *format;
|
||||
void *cache;
|
||||
|
||||
format = shmob_drm_format_info(crtc->fb->pixel_format);
|
||||
format = shmob_drm_format_info(crtc->primary->fb->pixel_format);
|
||||
if (format == NULL) {
|
||||
dev_dbg(sdev->dev, "mode_set: unsupported format %08x\n",
|
||||
crtc->fb->pixel_format);
|
||||
crtc->primary->fb->pixel_format);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
scrtc->format = format;
|
||||
scrtc->line_size = crtc->fb->pitches[0];
|
||||
scrtc->line_size = crtc->primary->fb->pitches[0];
|
||||
|
||||
if (sdev->meram) {
|
||||
/* Enable MERAM cache if configured. We need to de-init
|
||||
|
@ -402,7 +402,7 @@ static int shmob_drm_crtc_mode_set(struct drm_crtc *crtc,
|
|||
}
|
||||
|
||||
cache = sh_mobile_meram_cache_alloc(sdev->meram, mdata,
|
||||
crtc->fb->pitches[0],
|
||||
crtc->primary->fb->pitches[0],
|
||||
adjusted_mode->vdisplay,
|
||||
format->meram,
|
||||
&scrtc->line_size);
|
||||
|
@ -489,7 +489,7 @@ static int shmob_drm_crtc_page_flip(struct drm_crtc *crtc,
|
|||
}
|
||||
spin_unlock_irqrestore(&dev->event_lock, flags);
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
shmob_drm_crtc_update_base(scrtc);
|
||||
|
||||
if (event) {
|
||||
|
|
|
@ -235,14 +235,14 @@ static void tegra_dc_finish_page_flip(struct tegra_dc *dc)
|
|||
if (!dc->event)
|
||||
return;
|
||||
|
||||
bo = tegra_fb_get_plane(crtc->fb, 0);
|
||||
bo = tegra_fb_get_plane(crtc->primary->fb, 0);
|
||||
|
||||
/* check if new start address has been latched */
|
||||
tegra_dc_writel(dc, READ_MUX, DC_CMD_STATE_ACCESS);
|
||||
base = tegra_dc_readl(dc, DC_WINBUF_START_ADDR);
|
||||
tegra_dc_writel(dc, 0, DC_CMD_STATE_ACCESS);
|
||||
|
||||
if (base == bo->paddr + crtc->fb->offsets[0]) {
|
||||
if (base == bo->paddr + crtc->primary->fb->offsets[0]) {
|
||||
spin_lock_irqsave(&drm->event_lock, flags);
|
||||
drm_send_vblank_event(drm, dc->pipe, dc->event);
|
||||
drm_vblank_put(drm, dc->pipe);
|
||||
|
@ -284,7 +284,7 @@ static int tegra_dc_page_flip(struct drm_crtc *crtc, struct drm_framebuffer *fb,
|
|||
}
|
||||
|
||||
tegra_dc_set_base(dc, 0, 0, fb);
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -645,7 +645,7 @@ static int tegra_crtc_mode_set(struct drm_crtc *crtc,
|
|||
struct drm_display_mode *adjusted,
|
||||
int x, int y, struct drm_framebuffer *old_fb)
|
||||
{
|
||||
struct tegra_bo *bo = tegra_fb_get_plane(crtc->fb, 0);
|
||||
struct tegra_bo *bo = tegra_fb_get_plane(crtc->primary->fb, 0);
|
||||
struct tegra_dc *dc = to_tegra_dc(crtc);
|
||||
struct tegra_dc_window window;
|
||||
unsigned long div, value;
|
||||
|
@ -682,9 +682,9 @@ static int tegra_crtc_mode_set(struct drm_crtc *crtc,
|
|||
window.dst.y = 0;
|
||||
window.dst.w = mode->hdisplay;
|
||||
window.dst.h = mode->vdisplay;
|
||||
window.format = tegra_dc_format(crtc->fb->pixel_format);
|
||||
window.bits_per_pixel = crtc->fb->bits_per_pixel;
|
||||
window.stride[0] = crtc->fb->pitches[0];
|
||||
window.format = tegra_dc_format(crtc->primary->fb->pixel_format);
|
||||
window.bits_per_pixel = crtc->primary->fb->bits_per_pixel;
|
||||
window.stride[0] = crtc->primary->fb->pitches[0];
|
||||
window.base[0] = bo->paddr;
|
||||
|
||||
err = tegra_dc_setup_window(dc, 0, &window);
|
||||
|
@ -699,7 +699,7 @@ static int tegra_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
|
|||
{
|
||||
struct tegra_dc *dc = to_tegra_dc(crtc);
|
||||
|
||||
return tegra_dc_set_base(dc, x, y, crtc->fb);
|
||||
return tegra_dc_set_base(dc, x, y, crtc->primary->fb);
|
||||
}
|
||||
|
||||
static void tegra_crtc_prepare(struct drm_crtc *crtc)
|
||||
|
|
|
@ -74,7 +74,7 @@ static void set_scanout(struct drm_crtc *crtc, int n)
|
|||
drm_flip_work_queue(&tilcdc_crtc->unref_work, tilcdc_crtc->scanout[n]);
|
||||
drm_flip_work_commit(&tilcdc_crtc->unref_work, priv->wq);
|
||||
}
|
||||
tilcdc_crtc->scanout[n] = crtc->fb;
|
||||
tilcdc_crtc->scanout[n] = crtc->primary->fb;
|
||||
drm_framebuffer_reference(tilcdc_crtc->scanout[n]);
|
||||
tilcdc_crtc->dirty &= ~stat[n];
|
||||
pm_runtime_put_sync(dev->dev);
|
||||
|
@ -84,7 +84,7 @@ static void update_scanout(struct drm_crtc *crtc)
|
|||
{
|
||||
struct tilcdc_crtc *tilcdc_crtc = to_tilcdc_crtc(crtc);
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct drm_framebuffer *fb = crtc->fb;
|
||||
struct drm_framebuffer *fb = crtc->primary->fb;
|
||||
struct drm_gem_cma_object *gem;
|
||||
unsigned int depth, bpp;
|
||||
|
||||
|
@ -159,7 +159,7 @@ static int tilcdc_crtc_page_flip(struct drm_crtc *crtc,
|
|||
return -EBUSY;
|
||||
}
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
tilcdc_crtc->event = event;
|
||||
update_scanout(crtc);
|
||||
|
||||
|
@ -339,7 +339,7 @@ static int tilcdc_crtc_mode_set(struct drm_crtc *crtc,
|
|||
if (priv->rev == 2) {
|
||||
unsigned int depth, bpp;
|
||||
|
||||
drm_fb_get_bpp_depth(crtc->fb->pixel_format, &depth, &bpp);
|
||||
drm_fb_get_bpp_depth(crtc->primary->fb->pixel_format, &depth, &bpp);
|
||||
switch (bpp) {
|
||||
case 16:
|
||||
break;
|
||||
|
|
|
@ -310,7 +310,7 @@ static int udl_crtc_mode_set(struct drm_crtc *crtc,
|
|||
|
||||
{
|
||||
struct drm_device *dev = crtc->dev;
|
||||
struct udl_framebuffer *ufb = to_udl_fb(crtc->fb);
|
||||
struct udl_framebuffer *ufb = to_udl_fb(crtc->primary->fb);
|
||||
struct udl_device *udl = dev->dev_private;
|
||||
char *buf;
|
||||
char *wrptr;
|
||||
|
|
|
@ -468,7 +468,7 @@ static int do_surface_dirty_sou(struct vmw_private *dev_priv,
|
|||
num_units = 0;
|
||||
list_for_each_entry(crtc, &dev_priv->dev->mode_config.crtc_list,
|
||||
head) {
|
||||
if (crtc->fb != &framebuffer->base)
|
||||
if (crtc->primary->fb != &framebuffer->base)
|
||||
continue;
|
||||
units[num_units++] = vmw_crtc_to_du(crtc);
|
||||
}
|
||||
|
@ -882,7 +882,7 @@ static int do_dmabuf_dirty_sou(struct drm_file *file_priv,
|
|||
|
||||
num_units = 0;
|
||||
list_for_each_entry(crtc, &dev_priv->dev->mode_config.crtc_list, head) {
|
||||
if (crtc->fb != &framebuffer->base)
|
||||
if (crtc->primary->fb != &framebuffer->base)
|
||||
continue;
|
||||
units[num_units++] = vmw_crtc_to_du(crtc);
|
||||
}
|
||||
|
@ -1243,7 +1243,7 @@ int vmw_kms_present(struct vmw_private *dev_priv,
|
|||
|
||||
num_units = 0;
|
||||
list_for_each_entry(crtc, &dev_priv->dev->mode_config.crtc_list, head) {
|
||||
if (crtc->fb != &vfb->base)
|
||||
if (crtc->primary->fb != &vfb->base)
|
||||
continue;
|
||||
units[num_units++] = vmw_crtc_to_du(crtc);
|
||||
}
|
||||
|
@ -1380,7 +1380,7 @@ int vmw_kms_readback(struct vmw_private *dev_priv,
|
|||
|
||||
num_units = 0;
|
||||
list_for_each_entry(crtc, &dev_priv->dev->mode_config.crtc_list, head) {
|
||||
if (crtc->fb != &vfb->base)
|
||||
if (crtc->primary->fb != &vfb->base)
|
||||
continue;
|
||||
units[num_units++] = vmw_crtc_to_du(crtc);
|
||||
}
|
||||
|
@ -1723,7 +1723,7 @@ int vmw_du_page_flip(struct drm_crtc *crtc,
|
|||
uint32_t page_flip_flags)
|
||||
{
|
||||
struct vmw_private *dev_priv = vmw_priv(crtc->dev);
|
||||
struct drm_framebuffer *old_fb = crtc->fb;
|
||||
struct drm_framebuffer *old_fb = crtc->primary->fb;
|
||||
struct vmw_framebuffer *vfb = vmw_framebuffer_to_vfb(fb);
|
||||
struct drm_file *file_priv ;
|
||||
struct vmw_fence_obj *fence = NULL;
|
||||
|
@ -1741,7 +1741,7 @@ int vmw_du_page_flip(struct drm_crtc *crtc,
|
|||
if (!vmw_kms_screen_object_flippable(dev_priv, crtc))
|
||||
return -EINVAL;
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
|
||||
/* do a full screen dirty update */
|
||||
clips.x1 = clips.y1 = 0;
|
||||
|
@ -1781,7 +1781,7 @@ int vmw_du_page_flip(struct drm_crtc *crtc,
|
|||
return ret;
|
||||
|
||||
out_no_fence:
|
||||
crtc->fb = old_fb;
|
||||
crtc->primary->fb = old_fb;
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
|
|
@ -93,7 +93,7 @@ static int vmw_ldu_commit_list(struct vmw_private *dev_priv)
|
|||
|
||||
if (crtc == NULL)
|
||||
return 0;
|
||||
fb = entry->base.crtc.fb;
|
||||
fb = entry->base.crtc.primary->fb;
|
||||
|
||||
return vmw_kms_write_svga(dev_priv, w, h, fb->pitches[0],
|
||||
fb->bits_per_pixel, fb->depth);
|
||||
|
@ -101,7 +101,7 @@ static int vmw_ldu_commit_list(struct vmw_private *dev_priv)
|
|||
|
||||
if (!list_empty(&lds->active)) {
|
||||
entry = list_entry(lds->active.next, typeof(*entry), active);
|
||||
fb = entry->base.crtc.fb;
|
||||
fb = entry->base.crtc.primary->fb;
|
||||
|
||||
vmw_kms_write_svga(dev_priv, fb->width, fb->height, fb->pitches[0],
|
||||
fb->bits_per_pixel, fb->depth);
|
||||
|
@ -259,7 +259,7 @@ static int vmw_ldu_crtc_set_config(struct drm_mode_set *set)
|
|||
|
||||
connector->encoder = NULL;
|
||||
encoder->crtc = NULL;
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
crtc->enabled = false;
|
||||
|
||||
vmw_ldu_del_active(dev_priv, ldu);
|
||||
|
@ -280,7 +280,7 @@ static int vmw_ldu_crtc_set_config(struct drm_mode_set *set)
|
|||
|
||||
vmw_fb_off(dev_priv);
|
||||
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
encoder->crtc = crtc;
|
||||
connector->encoder = encoder;
|
||||
crtc->x = set->x;
|
||||
|
|
|
@ -307,7 +307,7 @@ static int vmw_sou_crtc_set_config(struct drm_mode_set *set)
|
|||
|
||||
connector->encoder = NULL;
|
||||
encoder->crtc = NULL;
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
crtc->x = 0;
|
||||
crtc->y = 0;
|
||||
crtc->enabled = false;
|
||||
|
@ -368,7 +368,7 @@ static int vmw_sou_crtc_set_config(struct drm_mode_set *set)
|
|||
|
||||
connector->encoder = NULL;
|
||||
encoder->crtc = NULL;
|
||||
crtc->fb = NULL;
|
||||
crtc->primary->fb = NULL;
|
||||
crtc->x = 0;
|
||||
crtc->y = 0;
|
||||
crtc->enabled = false;
|
||||
|
@ -381,7 +381,7 @@ static int vmw_sou_crtc_set_config(struct drm_mode_set *set)
|
|||
connector->encoder = encoder;
|
||||
encoder->crtc = crtc;
|
||||
crtc->mode = *mode;
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
crtc->x = set->x;
|
||||
crtc->y = set->y;
|
||||
crtc->enabled = true;
|
||||
|
@ -572,5 +572,5 @@ void vmw_kms_screen_object_update_implicit_fb(struct vmw_private *dev_priv,
|
|||
BUG_ON(!sou->base.is_implicit);
|
||||
|
||||
dev_priv->sou_priv->implicit_fb =
|
||||
vmw_framebuffer_to_vfb(sou->base.crtc.fb);
|
||||
vmw_framebuffer_to_vfb(sou->base.crtc.primary->fb);
|
||||
}
|
||||
|
|
|
@ -120,7 +120,7 @@ static int ipu_page_flip(struct drm_crtc *crtc,
|
|||
|
||||
ipu_crtc->newfb = fb;
|
||||
ipu_crtc->page_flip_event = event;
|
||||
crtc->fb = fb;
|
||||
crtc->primary->fb = fb;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -192,7 +192,7 @@ static int ipu_crtc_mode_set(struct drm_crtc *crtc,
|
|||
return ret;
|
||||
}
|
||||
|
||||
return ipu_plane_mode_set(ipu_crtc->plane[0], crtc, mode, crtc->fb,
|
||||
return ipu_plane_mode_set(ipu_crtc->plane[0], crtc, mode, crtc->primary->fb,
|
||||
0, 0, mode->hdisplay, mode->vdisplay,
|
||||
x, y, mode->hdisplay, mode->vdisplay);
|
||||
}
|
||||
|
@ -218,7 +218,7 @@ static irqreturn_t ipu_irq_handler(int irq, void *dev_id)
|
|||
|
||||
if (ipu_crtc->newfb) {
|
||||
ipu_crtc->newfb = NULL;
|
||||
ipu_plane_set_base(ipu_crtc->plane[0], ipu_crtc->base.fb,
|
||||
ipu_plane_set_base(ipu_crtc->plane[0], ipu_crtc->base.primary->fb,
|
||||
ipu_crtc->plane[0]->x, ipu_crtc->plane[0]->y);
|
||||
ipu_crtc_handle_pageflip(ipu_crtc);
|
||||
}
|
||||
|
|
|
@ -409,6 +409,11 @@ struct drm_file {
|
|||
unsigned is_master :1;
|
||||
/* true when the client has asked us to expose stereo 3D mode flags */
|
||||
unsigned stereo_allowed :1;
|
||||
/*
|
||||
* true if client understands CRTC primary planes and cursor planes
|
||||
* in the plane list
|
||||
*/
|
||||
unsigned universal_planes:1;
|
||||
|
||||
struct pid *pid;
|
||||
kuid_t uid;
|
||||
|
@ -1409,6 +1414,7 @@ extern void drm_put_dev(struct drm_device *dev);
|
|||
extern void drm_unplug_dev(struct drm_device *dev);
|
||||
extern unsigned int drm_debug;
|
||||
extern unsigned int drm_rnodes;
|
||||
extern unsigned int drm_universal_planes;
|
||||
|
||||
extern unsigned int drm_vblank_offdelay;
|
||||
extern unsigned int drm_timestamp_precision;
|
||||
|
|
|
@ -270,6 +270,8 @@ struct drm_crtc_funcs {
|
|||
* @dev: parent DRM device
|
||||
* @head: list management
|
||||
* @base: base KMS object for ID tracking etc.
|
||||
* @primary: primary plane for this CRTC
|
||||
* @cursor: cursor plane for this CRTC
|
||||
* @enabled: is this CRTC enabled?
|
||||
* @mode: current mode timings
|
||||
* @hwmode: mode timings as programmed to hw regs
|
||||
|
@ -305,8 +307,9 @@ struct drm_crtc {
|
|||
|
||||
struct drm_mode_object base;
|
||||
|
||||
/* framebuffer the connector is currently bound to */
|
||||
struct drm_framebuffer *fb;
|
||||
/* primary and cursor planes for CRTC */
|
||||
struct drm_plane *primary;
|
||||
struct drm_plane *cursor;
|
||||
|
||||
/* Temporary tracking of the old fb while a modeset is ongoing. Used
|
||||
* by drm_mode_set_config_internal to implement correct refcounting. */
|
||||
|
@ -541,6 +544,12 @@ struct drm_plane_funcs {
|
|||
struct drm_property *property, uint64_t val);
|
||||
};
|
||||
|
||||
enum drm_plane_type {
|
||||
DRM_PLANE_TYPE_OVERLAY,
|
||||
DRM_PLANE_TYPE_PRIMARY,
|
||||
DRM_PLANE_TYPE_CURSOR,
|
||||
};
|
||||
|
||||
/**
|
||||
* drm_plane - central DRM plane control structure
|
||||
* @dev: DRM device this plane belongs to
|
||||
|
@ -553,6 +562,7 @@ struct drm_plane_funcs {
|
|||
* @fb: currently bound fb
|
||||
* @funcs: helper functions
|
||||
* @properties: property tracking for this plane
|
||||
* @type: type of plane (overlay, primary, cursor)
|
||||
*/
|
||||
struct drm_plane {
|
||||
struct drm_device *dev;
|
||||
|
@ -570,6 +580,8 @@ struct drm_plane {
|
|||
const struct drm_plane_funcs *funcs;
|
||||
|
||||
struct drm_object_properties properties;
|
||||
|
||||
enum drm_plane_type type;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -732,7 +744,15 @@ struct drm_mode_config {
|
|||
struct list_head bridge_list;
|
||||
int num_encoder;
|
||||
struct list_head encoder_list;
|
||||
int num_plane;
|
||||
|
||||
/*
|
||||
* Track # of overlay planes separately from # of total planes. By
|
||||
* default we only advertise overlay planes to userspace; if userspace
|
||||
* sets the "universal plane" capability bit, we'll go ahead and
|
||||
* expose all planes.
|
||||
*/
|
||||
int num_overlay_plane;
|
||||
int num_total_plane;
|
||||
struct list_head plane_list;
|
||||
|
||||
int num_crtc;
|
||||
|
@ -754,6 +774,7 @@ struct drm_mode_config {
|
|||
struct list_head property_blob_list;
|
||||
struct drm_property *edid_property;
|
||||
struct drm_property *dpms_property;
|
||||
struct drm_property *plane_type_property;
|
||||
|
||||
/* DVI-I properties */
|
||||
struct drm_property *dvi_i_subconnector_property;
|
||||
|
@ -806,6 +827,11 @@ extern void drm_modeset_lock_all(struct drm_device *dev);
|
|||
extern void drm_modeset_unlock_all(struct drm_device *dev);
|
||||
extern void drm_warn_on_modeset_not_all_locked(struct drm_device *dev);
|
||||
|
||||
extern int drm_crtc_init_with_planes(struct drm_device *dev,
|
||||
struct drm_crtc *crtc,
|
||||
struct drm_plane *primary,
|
||||
void *cursor,
|
||||
const struct drm_crtc_funcs *funcs);
|
||||
extern int drm_crtc_init(struct drm_device *dev,
|
||||
struct drm_crtc *crtc,
|
||||
const struct drm_crtc_funcs *funcs);
|
||||
|
@ -857,14 +883,25 @@ static inline bool drm_encoder_crtc_ok(struct drm_encoder *encoder,
|
|||
return !!(encoder->possible_crtcs & drm_crtc_mask(crtc));
|
||||
}
|
||||
|
||||
extern int drm_universal_plane_init(struct drm_device *dev,
|
||||
struct drm_plane *plane,
|
||||
unsigned long possible_crtcs,
|
||||
const struct drm_plane_funcs *funcs,
|
||||
const uint32_t *formats,
|
||||
uint32_t format_count,
|
||||
enum drm_plane_type type);
|
||||
extern int drm_plane_init(struct drm_device *dev,
|
||||
struct drm_plane *plane,
|
||||
unsigned long possible_crtcs,
|
||||
const struct drm_plane_funcs *funcs,
|
||||
const uint32_t *formats, uint32_t format_count,
|
||||
bool priv);
|
||||
bool is_primary);
|
||||
extern void drm_plane_cleanup(struct drm_plane *plane);
|
||||
extern void drm_plane_force_disable(struct drm_plane *plane);
|
||||
extern int drm_crtc_check_viewport(const struct drm_crtc *crtc,
|
||||
int x, int y,
|
||||
const struct drm_display_mode *mode,
|
||||
const struct drm_framebuffer *fb);
|
||||
|
||||
extern void drm_encoder_cleanup(struct drm_encoder *encoder);
|
||||
|
||||
|
@ -1036,4 +1073,9 @@ static inline struct drm_encoder *drm_encoder_find(struct drm_device *dev,
|
|||
return mo ? obj_to_encoder(mo) : NULL;
|
||||
}
|
||||
|
||||
/* Plane list iterator for legacy (overlay only) planes. */
|
||||
#define drm_for_each_legacy_plane(plane, planelist) \
|
||||
list_for_each_entry(plane, planelist, head) \
|
||||
if (plane->type == DRM_PLANE_TYPE_OVERLAY)
|
||||
|
||||
#endif /* __DRM_CRTC_H__ */
|
||||
|
|
|
@ -0,0 +1,49 @@
|
|||
/*
|
||||
* Copyright (C) 2011-2013 Intel Corporation
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
|
||||
#ifndef DRM_PLANE_HELPER_H
|
||||
#define DRM_PLANE_HELPER_H
|
||||
|
||||
/**
|
||||
* DOC: plane helpers
|
||||
*
|
||||
* Helper functions to assist with creation and handling of CRTC primary
|
||||
* planes.
|
||||
*/
|
||||
|
||||
extern int drm_primary_helper_update(struct drm_plane *plane,
|
||||
struct drm_crtc *crtc,
|
||||
struct drm_framebuffer *fb,
|
||||
int crtc_x, int crtc_y,
|
||||
unsigned int crtc_w, unsigned int crtc_h,
|
||||
uint32_t src_x, uint32_t src_y,
|
||||
uint32_t src_w, uint32_t src_h);
|
||||
extern int drm_primary_helper_disable(struct drm_plane *plane);
|
||||
extern void drm_primary_helper_destroy(struct drm_plane *plane);
|
||||
extern const struct drm_plane_funcs drm_primary_helper_funcs;
|
||||
extern struct drm_plane *drm_primary_helper_create_plane(struct drm_device *dev,
|
||||
uint32_t *formats,
|
||||
int num_formats);
|
||||
|
||||
|
||||
#endif
|
|
@ -646,6 +646,14 @@ struct drm_get_cap {
|
|||
*/
|
||||
#define DRM_CLIENT_CAP_STEREO_3D 1
|
||||
|
||||
/**
|
||||
* DRM_CLIENT_CAP_UNIVERSAL_PLANES
|
||||
*
|
||||
* If set to 1, the DRM core will expose all planes (overlay, primary, and
|
||||
* cursor) to userspace.
|
||||
*/
|
||||
#define DRM_CLIENT_CAP_UNIVERSAL_PLANES 2
|
||||
|
||||
/** DRM_IOCTL_SET_CLIENT_CAP ioctl argument type */
|
||||
struct drm_set_client_cap {
|
||||
__u64 capability;
|
||||
|
|
Loading…
Reference in New Issue