ipu_plane
struct ipu_plane *plane = ipu_crtc->plane[i];
struct ipu_plane *plane[2];
struct ipu_plane *primary_plane;
int ipu_plane_irq(struct ipu_plane *ipu_plane)
return ipu_idmac_channel_irq(ipu_plane->ipu, ipu_plane->ipu_ch,
struct ipu_plane *ipu_plane = ptr;
if (!IS_ERR_OR_NULL(ipu_plane->dp))
ipu_dp_put(ipu_plane->dp);
if (!IS_ERR_OR_NULL(ipu_plane->dmfc))
ipu_dmfc_put(ipu_plane->dmfc);
if (!IS_ERR_OR_NULL(ipu_plane->ipu_ch))
ipu_idmac_put(ipu_plane->ipu_ch);
if (!IS_ERR_OR_NULL(ipu_plane->alpha_ch))
ipu_idmac_put(ipu_plane->alpha_ch);
struct ipu_plane *ipu_plane)
ipu_plane->ipu_ch = ipu_idmac_get(ipu_plane->ipu, ipu_plane->dma);
if (IS_ERR(ipu_plane->ipu_ch)) {
ret = PTR_ERR(ipu_plane->ipu_ch);
ret = drmm_add_action_or_reset(dev, ipu_plane_put_resources, ipu_plane);
alpha_ch = ipu_channel_alpha_channel(ipu_plane->dma);
ipu_plane->alpha_ch = ipu_idmac_get(ipu_plane->ipu, alpha_ch);
if (IS_ERR(ipu_plane->alpha_ch)) {
ret = PTR_ERR(ipu_plane->alpha_ch);
ipu_plane->dmfc = ipu_dmfc_get(ipu_plane->ipu, ipu_plane->dma);
if (IS_ERR(ipu_plane->dmfc)) {
ret = PTR_ERR(ipu_plane->dmfc);
if (ipu_plane->dp_flow >= 0) {
ipu_plane->dp = ipu_dp_get(ipu_plane->ipu, ipu_plane->dp_flow);
if (IS_ERR(ipu_plane->dp)) {
ret = PTR_ERR(ipu_plane->dp);
static bool ipu_plane_separate_alpha(struct ipu_plane *ipu_plane)
switch (ipu_plane->base.state->fb->format->format) {
static void ipu_plane_enable(struct ipu_plane *ipu_plane)
if (ipu_plane->dp)
ipu_dp_enable(ipu_plane->ipu);
ipu_dmfc_enable_channel(ipu_plane->dmfc);
ipu_idmac_enable_channel(ipu_plane->ipu_ch);
if (ipu_plane_separate_alpha(ipu_plane))
ipu_idmac_enable_channel(ipu_plane->alpha_ch);
if (ipu_plane->dp)
ipu_dp_enable_channel(ipu_plane->dp);
void ipu_plane_disable(struct ipu_plane *ipu_plane, bool disable_dp_channel)
ret = ipu_idmac_wait_busy(ipu_plane->ipu_ch, 50);
ipu_plane->base.base.id);
if (ipu_plane->dp && disable_dp_channel)
ipu_dp_disable_channel(ipu_plane->dp, false);
ipu_idmac_disable_channel(ipu_plane->ipu_ch);
if (ipu_plane->alpha_ch)
ipu_idmac_disable_channel(ipu_plane->alpha_ch);
ipu_dmfc_disable_channel(ipu_plane->dmfc);
if (ipu_plane->dp)
ipu_dp_disable(ipu_plane->ipu);
if (ipu_prg_present(ipu_plane->ipu))
ipu_prg_channel_disable(ipu_plane->ipu_ch);
struct ipu_plane *ipu_plane = to_ipu_plane(plane);
if (ipu_plane->disabling) {
ipu_plane->disabling = false;
ipu_plane_disable(ipu_plane, false);
static inline struct ipu_plane *to_ipu_plane(struct drm_plane *p)
return container_of(p, struct ipu_plane, base);
struct ipu_plane *ipu_plane = to_ipu_plane(plane);
if (ipu_plane->dp)
ipu_dp_disable_channel(ipu_plane->dp, true);
ipu_plane->disabling = true;
struct ipu_plane *ipu_plane = to_ipu_plane(plane);
if (ipu_plane->dp_flow == IPU_DP_FLOW_SYNC_FG)
ipu_dp_set_window_pos(ipu_plane->dp, dst->x1, dst->y1);
switch (ipu_plane->dp_flow) {
ipu_dp_set_global_alpha(ipu_plane->dp,
ipu_dp_set_global_alpha(ipu_plane->dp, true, 0, true);
ipu_dp_set_global_alpha(ipu_plane->dp,
if (ipu_plane->dp_flow == IPU_DP_FLOW_SYNC_BG)
axi_id = ipu_chan_assign_axi_id(ipu_plane->dma);
ipu_prg_channel_configure(ipu_plane->ipu_ch, axi_id, width,
switch (ipu_plane->dp_flow) {
ipu_dp_setup_channel(ipu_plane->dp, new_state->color_encoding,
ipu_dp_setup_channel(ipu_plane->dp, new_state->color_encoding,
active = ipu_idmac_get_current_buffer(ipu_plane->ipu_ch);
ipu_cpmem_set_buffer(ipu_plane->ipu_ch, !active, eba);
ipu_idmac_select_buffer(ipu_plane->ipu_ch, !active);
if (ipu_plane_separate_alpha(ipu_plane)) {
active = ipu_idmac_get_current_buffer(ipu_plane->alpha_ch);
ipu_cpmem_set_buffer(ipu_plane->alpha_ch, !active,
ipu_idmac_select_buffer(ipu_plane->alpha_ch, !active);
switch (ipu_plane->dp_flow) {
ipu_dp_setup_channel(ipu_plane->dp, DRM_COLOR_YCBCR_BT601,
ipu_dp_setup_channel(ipu_plane->dp, DRM_COLOR_YCBCR_BT601,
ipu_dmfc_config_wait4eot(ipu_plane->dmfc, width);
ipu_cpmem_zero(ipu_plane->ipu_ch);
ipu_cpmem_set_resolution(ipu_plane->ipu_ch, width, height);
ipu_cpmem_set_fmt(ipu_plane->ipu_ch, fb->format->format);
ipu_cpmem_set_burstsize(ipu_plane->ipu_ch, burstsize);
ipu_cpmem_set_high_priority(ipu_plane->ipu_ch);
ipu_idmac_enable_watermark(ipu_plane->ipu_ch, true);
ipu_idmac_set_double_buffer(ipu_plane->ipu_ch, 1);
ipu_cpmem_set_stride(ipu_plane->ipu_ch, fb->pitches[0]);
ipu_cpmem_set_axi_id(ipu_plane->ipu_ch, axi_id);
ipu_cpmem_set_yuv_planar_full(ipu_plane->ipu_ch,
dev_dbg(ipu_plane->base.dev->dev,
ipu_cpmem_set_yuv_planar_full(ipu_plane->ipu_ch,
dev_dbg(ipu_plane->base.dev->dev,
dev_dbg(ipu_plane->base.dev->dev, "phys = %lu %lu, x = %d, y = %d",
ipu_cpmem_set_burstsize(ipu_plane->ipu_ch, 16);
ipu_cpmem_zero(ipu_plane->alpha_ch);
ipu_cpmem_set_resolution(ipu_plane->alpha_ch, width, height);
ipu_cpmem_set_format_passthrough(ipu_plane->alpha_ch, 8);
ipu_cpmem_set_high_priority(ipu_plane->alpha_ch);
ipu_idmac_set_double_buffer(ipu_plane->alpha_ch, 1);
ipu_cpmem_set_stride(ipu_plane->alpha_ch, fb->pitches[1]);
ipu_cpmem_set_burstsize(ipu_plane->alpha_ch, 16);
ipu_cpmem_set_buffer(ipu_plane->alpha_ch, 0, alpha_eba);
ipu_cpmem_set_buffer(ipu_plane->alpha_ch, 1, alpha_eba);
dev_dbg(ipu_plane->base.dev->dev, "phys = %lu, x = %d, y = %d",
ipu_cpmem_set_buffer(ipu_plane->ipu_ch, 0, eba);
ipu_cpmem_set_buffer(ipu_plane->ipu_ch, 1, eba);
ipu_idmac_lock_enable(ipu_plane->ipu_ch, num_bursts);
ipu_plane_enable(ipu_plane);
struct ipu_plane *ipu_plane = to_ipu_plane(plane);
return ipu_prg_channel_configure_pending(ipu_plane->ipu_ch);
struct ipu_plane *ipu_plane;
ipu_plane = to_ipu_plane(plane);
if (!ipu_prg_present(ipu_plane->ipu) || !available_pres)
if (!ipu_prg_format_supported(ipu_plane->ipu,
ipu_plane = to_ipu_plane(plane);
if (ipu_prg_present(ipu_plane->ipu) && available_pres &&
ipu_prg_format_supported(ipu_plane->ipu,
struct ipu_plane *ipu_plane_init(struct drm_device *dev, struct ipu_soc *ipu,
struct ipu_plane *ipu_plane;
ipu_plane = drmm_universal_plane_alloc(dev, struct ipu_plane, base,
if (IS_ERR(ipu_plane)) {
return ipu_plane;
ipu_plane->ipu = ipu;
ipu_plane->dma = dma;
ipu_plane->dp_flow = dp;
drm_plane_helper_add(&ipu_plane->base, &ipu_primary_plane_helper_funcs);
drm_plane_helper_add(&ipu_plane->base, &ipu_plane_helper_funcs);
ret = drm_plane_create_zpos_property(&ipu_plane->base, zpos, 0,
ret = drm_plane_create_zpos_immutable_property(&ipu_plane->base,
ret = drm_plane_create_color_properties(&ipu_plane->base,
ret = ipu_plane_get_resources(dev, ipu_plane);
return ipu_plane;
struct ipu_plane *ipu_plane_init(struct drm_device *dev, struct ipu_soc *ipu,
int ipu_plane_mode_set(struct ipu_plane *plane, struct drm_crtc *crtc,
int ipu_plane_irq(struct ipu_plane *plane);
void ipu_plane_disable(struct ipu_plane *ipu_plane, bool disable_dp_channel);
priv->ipu_plane = drm_plane_from_index(drm, 2);
if (!priv->ipu_plane) {
if (IS_ENABLED(CONFIG_DRM_INGENIC_IPU) && priv->ipu_plane) {
priv->ipu_plane);
if (priv->ipu_plane && priv->ipu_plane->state->fb)
struct drm_plane f0, f1, *ipu_plane;