/* create extra planes */ int xilinx_drm_plane_create_planes(struct xilinx_drm_plane_manager *manager, unsigned int possible_crtcs) { struct xilinx_drm_plane *plane; int i; int err_ret; xilinx_drm_plane_create_property(manager); /* find if there any available plane, and create if available */ for (i = 0; i < manager->num_planes; i++) { if (manager->planes[i]) continue; plane = xilinx_drm_plane_create(manager, possible_crtcs, false); if (IS_ERR(plane)) { DRM_ERROR("failed to allocate a plane\n"); err_ret = PTR_ERR(plane); goto err_out; } xilinx_drm_plane_attach_property(&plane->base); manager->planes[i] = plane; } return 0; err_out: xilinx_drm_plane_destroy_planes(manager); return err_ret; }
struct xilinx_drm_plane_manager * xilinx_drm_plane_probe_manager(struct drm_device *drm) { struct xilinx_drm_plane_manager *manager; struct device *dev = drm->dev; struct device_node *sub_node; const char *format; int ret; manager = devm_kzalloc(dev, sizeof(*manager), GFP_KERNEL); if (!manager) return ERR_PTR(-ENOMEM); /* this node is used to create a plane */ manager->node = of_get_child_by_name(dev->of_node, "planes"); if (!manager->node) { DRM_ERROR("failed to get a planes node\n"); return ERR_PTR(-EINVAL); } /* check the base pixel format of plane manager */ ret = of_property_read_string(manager->node, "xlnx,pixel-format", &format); if (ret < 0) { DRM_ERROR("failed to get a plane manager format\n"); return ERR_PTR(ret); } ret = xilinx_drm_format_by_name(format, &manager->format); if (ret < 0) { DRM_ERROR("invalid plane manager format\n"); return ERR_PTR(ret); } manager->drm = drm; /* probe an OSD. proceed even if there's no OSD */ sub_node = of_parse_phandle(dev->of_node, "xlnx,osd", 0); if (sub_node) { manager->osd = xilinx_osd_probe(dev, sub_node); of_node_put(sub_node); if (IS_ERR(manager->osd)) { of_node_put(manager->node); DRM_ERROR("failed to probe an osd\n"); return ERR_CAST(manager->osd); } manager->default_alpha = OSD_MAX_ALPHA; } manager->dp_sub = xilinx_drm_dp_sub_of_get(drm->dev->of_node); if (IS_ERR(manager->dp_sub)) { DRM_DEBUG_KMS("failed to get a dp_sub\n"); return ERR_CAST(manager->dp_sub); } else if (manager->dp_sub != NULL) { manager->default_alpha = XILINX_DRM_DP_SUB_MAX_ALPHA; } ret = xilinx_drm_plane_init_manager(manager); if (ret) { DRM_ERROR("failed to init a plane manager\n"); return ERR_PTR(ret); } xilinx_drm_plane_create_property(manager); return manager; }