int ratio;
};
+#ifndef MODULE
static struct drm_crtc *find_crtc_by_node(struct drm_device *drm_dev,
struct device_node *node)
{
return NULL;
}
+void rockchip_free_loader_memory(struct drm_device *drm)
+{
+ struct rockchip_drm_private *private = drm->dev_private;
+ struct rockchip_logo *logo;
+ void *start, *end;
+
+ if (!private || !private->logo || --private->logo->count)
+ return;
+
+ logo = private->logo;
+ start = phys_to_virt(logo->start);
+ end = phys_to_virt(logo->size);
+
+ if (private->domain) {
+ iommu_unmap(private->domain, logo->dma_addr,
+ logo->iommu_map_size);
+ drm_mm_remove_node(&logo->mm);
+ } else {
+ dma_unmap_sg(drm->dev, logo->sgt->sgl,
+ logo->sgt->nents, DMA_TO_DEVICE);
+ }
+ sg_free_table(logo->sgt);
+ memblock_free(logo->start, logo->size);
+ free_reserved_area(start, end, -1, "drm_logo");
+ kfree(logo);
+ private->logo = NULL;
+}
+
static int init_loader_memory(struct drm_device *drm_dev)
{
struct rockchip_drm_private *private = drm_dev->dev_private;
struct resource res;
int i, ret;
- logo = devm_kmalloc(drm_dev->dev, sizeof(*logo), GFP_KERNEL);
- if (!logo)
- return -ENOMEM;
-
node = of_parse_phandle(np, "memory-region", 0);
if (!node)
return -ENOMEM;
if (!size)
return -ENOMEM;
+ logo = kmalloc(sizeof(*logo), GFP_KERNEL);
+ if (!logo)
+ return -ENOMEM;
+
nr_pages = PAGE_ALIGN(size) >> PAGE_SHIFT;
pages = kmalloc_array(nr_pages, sizeof(*pages), GFP_KERNEL);
if (!pages)
- return -ENOMEM;
+ goto err_free_logo;
i = 0;
while (i < nr_pages) {
pages[i] = phys_to_page(start);
logo->sgt = sgt;
logo->start = res.start;
logo->size = size;
- logo->count = 0;
+ logo->count = 1;
private->logo = logo;
return 0;
drm_mm_remove_node(&logo->mm);
err_free_pages:
kfree(pages);
+err_free_logo:
+ kfree(logo);
return ret;
}
if (ret)
goto err_free_state;
+ rockchip_free_loader_memory(drm_dev);
+
drm_modeset_unlock_all(drm_dev);
return;
if (ret)
dev_err(drm_dev->dev, "failed to show loader logo\n");
}
+#endif
/*
* Attach a (component) device to the shared drm dma mapping from master drm
drm_mode_config_reset(drm_dev);
+#ifndef MODULE
show_loader_logo(drm_dev);
+#endif
ret = rockchip_drm_fbdev_init(drm_dev);
if (ret)
}
#ifndef MODULE
- if (rockchip_fb->logo) {
- struct rockchip_drm_private *private = fb->dev->dev_private;
- struct rockchip_logo *logo = rockchip_fb->logo;
-
- if (!--logo->count) {
- void *start = phys_to_virt(logo->start);
- void *end = phys_to_virt(logo->size);
-
- if (private && private->domain) {
- iommu_unmap(private->domain, logo->dma_addr,
- logo->iommu_map_size);
- drm_mm_remove_node(&logo->mm);
- } else {
- dma_unmap_sg(fb->dev->dev, logo->sgt->sgl,
- logo->sgt->nents, DMA_TO_DEVICE);
- }
- sg_free_table(logo->sgt);
- memblock_free(logo->start, logo->size);
- free_reserved_area(start, end, -1, "drm_logo");
- }
- }
+ if (rockchip_fb->logo)
+ rockchip_free_loader_memory(fb->dev);
#else
WARN_ON(rockchip_fb->logo);
#endif