Commit 173fa4ec authored by Dave Airlie's avatar Dave Airlie

Merge branch 'exynos-drm-fixes' of...

Merge branch 'exynos-drm-fixes' of git://git.infradead.org/users/kmpark/linux-samsung into drm-intel-fixes

* 'exynos-drm-fixes' of git://git.infradead.org/users/kmpark/linux-samsung:
  drm/exynos: fixed exynos broken ioctl
  drm/exynos: fix to pointer manager member of struct exynos_drm_subdrv
  drm/exynos: fix struct for operation callback functions to driver name
  drm/exynos: use define instead of default_win member in struct mixer_context
  drm/exynos: rename s/HDMI_OVERLAY_NUMBER/MIXER_WIN_NR
  drm/exynos: remove unused codes in hdmi and mixer
  drm/exynos: remove unnecessary type conversion of hdmi and mixer
  drm/exynos: add format list of plane
  drm/exynos: fixed duplicated page allocation bug.
  drm/exynos: fixed page align and code clean.
parents 19e5c4e7 490aa60e
...@@ -34,14 +34,14 @@ ...@@ -34,14 +34,14 @@
static int lowlevel_buffer_allocate(struct drm_device *dev, static int lowlevel_buffer_allocate(struct drm_device *dev,
unsigned int flags, struct exynos_drm_gem_buf *buf) unsigned int flags, struct exynos_drm_gem_buf *buf)
{ {
dma_addr_t start_addr, end_addr; dma_addr_t start_addr;
unsigned int npages, page_size, i = 0; unsigned int npages, page_size, i = 0;
struct scatterlist *sgl; struct scatterlist *sgl;
int ret = 0; int ret = 0;
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (flags & EXYNOS_BO_NONCONTIG) { if (IS_NONCONTIG_BUFFER(flags)) {
DRM_DEBUG_KMS("not support allocation type.\n"); DRM_DEBUG_KMS("not support allocation type.\n");
return -EINVAL; return -EINVAL;
} }
...@@ -52,13 +52,13 @@ static int lowlevel_buffer_allocate(struct drm_device *dev, ...@@ -52,13 +52,13 @@ static int lowlevel_buffer_allocate(struct drm_device *dev,
} }
if (buf->size >= SZ_1M) { if (buf->size >= SZ_1M) {
npages = (buf->size >> SECTION_SHIFT) + 1; npages = buf->size >> SECTION_SHIFT;
page_size = SECTION_SIZE; page_size = SECTION_SIZE;
} else if (buf->size >= SZ_64K) { } else if (buf->size >= SZ_64K) {
npages = (buf->size >> 16) + 1; npages = buf->size >> 16;
page_size = SZ_64K; page_size = SZ_64K;
} else { } else {
npages = (buf->size >> PAGE_SHIFT) + 1; npages = buf->size >> PAGE_SHIFT;
page_size = PAGE_SIZE; page_size = PAGE_SIZE;
} }
...@@ -76,26 +76,13 @@ static int lowlevel_buffer_allocate(struct drm_device *dev, ...@@ -76,26 +76,13 @@ static int lowlevel_buffer_allocate(struct drm_device *dev,
return -ENOMEM; return -ENOMEM;
} }
buf->kvaddr = dma_alloc_writecombine(dev->dev, buf->size, buf->kvaddr = dma_alloc_writecombine(dev->dev, buf->size,
&buf->dma_addr, GFP_KERNEL); &buf->dma_addr, GFP_KERNEL);
if (!buf->kvaddr) { if (!buf->kvaddr) {
DRM_ERROR("failed to allocate buffer.\n"); DRM_ERROR("failed to allocate buffer.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto err1; goto err1;
} }
start_addr = buf->dma_addr;
end_addr = buf->dma_addr + buf->size;
buf->pages = kzalloc(sizeof(struct page) * npages, GFP_KERNEL);
if (!buf->pages) {
DRM_ERROR("failed to allocate pages.\n");
ret = -ENOMEM;
goto err2;
}
start_addr = buf->dma_addr;
end_addr = buf->dma_addr + buf->size;
buf->pages = kzalloc(sizeof(struct page) * npages, GFP_KERNEL); buf->pages = kzalloc(sizeof(struct page) * npages, GFP_KERNEL);
if (!buf->pages) { if (!buf->pages) {
...@@ -105,23 +92,17 @@ static int lowlevel_buffer_allocate(struct drm_device *dev, ...@@ -105,23 +92,17 @@ static int lowlevel_buffer_allocate(struct drm_device *dev,
} }
sgl = buf->sgt->sgl; sgl = buf->sgt->sgl;
start_addr = buf->dma_addr;
while (i < npages) { while (i < npages) {
buf->pages[i] = phys_to_page(start_addr); buf->pages[i] = phys_to_page(start_addr);
sg_set_page(sgl, buf->pages[i], page_size, 0); sg_set_page(sgl, buf->pages[i], page_size, 0);
sg_dma_address(sgl) = start_addr; sg_dma_address(sgl) = start_addr;
start_addr += page_size; start_addr += page_size;
if (end_addr - start_addr < page_size)
break;
sgl = sg_next(sgl); sgl = sg_next(sgl);
i++; i++;
} }
buf->pages[i] = phys_to_page(start_addr);
sgl = sg_next(sgl);
sg_set_page(sgl, buf->pages[i+1], end_addr - start_addr, 0);
DRM_DEBUG_KMS("vaddr(0x%lx), dma_addr(0x%lx), size(0x%lx)\n", DRM_DEBUG_KMS("vaddr(0x%lx), dma_addr(0x%lx), size(0x%lx)\n",
(unsigned long)buf->kvaddr, (unsigned long)buf->kvaddr,
(unsigned long)buf->dma_addr, (unsigned long)buf->dma_addr,
...@@ -150,7 +131,7 @@ static void lowlevel_buffer_deallocate(struct drm_device *dev, ...@@ -150,7 +131,7 @@ static void lowlevel_buffer_deallocate(struct drm_device *dev,
* non-continuous memory would be released by exynos * non-continuous memory would be released by exynos
* gem framework. * gem framework.
*/ */
if (flags & EXYNOS_BO_NONCONTIG) { if (IS_NONCONTIG_BUFFER(flags)) {
DRM_DEBUG_KMS("not support allocation type.\n"); DRM_DEBUG_KMS("not support allocation type.\n");
return; return;
} }
......
...@@ -54,16 +54,18 @@ static int exynos_drm_subdrv_probe(struct drm_device *dev, ...@@ -54,16 +54,18 @@ static int exynos_drm_subdrv_probe(struct drm_device *dev,
* *
* P.S. note that this driver is considered for modularization. * P.S. note that this driver is considered for modularization.
*/ */
ret = subdrv->probe(dev, subdrv->manager.dev); ret = subdrv->probe(dev, subdrv->dev);
if (ret) if (ret)
return ret; return ret;
} }
if (subdrv->is_local) if (!subdrv->manager)
return 0; return 0;
subdrv->manager->dev = subdrv->dev;
/* create and initialize a encoder for this sub driver. */ /* create and initialize a encoder for this sub driver. */
encoder = exynos_drm_encoder_create(dev, &subdrv->manager, encoder = exynos_drm_encoder_create(dev, subdrv->manager,
(1 << MAX_CRTC) - 1); (1 << MAX_CRTC) - 1);
if (!encoder) { if (!encoder) {
DRM_ERROR("failed to create encoder\n"); DRM_ERROR("failed to create encoder\n");
...@@ -186,7 +188,7 @@ int exynos_drm_subdrv_open(struct drm_device *dev, struct drm_file *file) ...@@ -186,7 +188,7 @@ int exynos_drm_subdrv_open(struct drm_device *dev, struct drm_file *file)
list_for_each_entry(subdrv, &exynos_drm_subdrv_list, list) { list_for_each_entry(subdrv, &exynos_drm_subdrv_list, list) {
if (subdrv->open) { if (subdrv->open) {
ret = subdrv->open(dev, subdrv->manager.dev, file); ret = subdrv->open(dev, subdrv->dev, file);
if (ret) if (ret)
goto err; goto err;
} }
...@@ -197,7 +199,7 @@ int exynos_drm_subdrv_open(struct drm_device *dev, struct drm_file *file) ...@@ -197,7 +199,7 @@ int exynos_drm_subdrv_open(struct drm_device *dev, struct drm_file *file)
err: err:
list_for_each_entry_reverse(subdrv, &subdrv->list, list) { list_for_each_entry_reverse(subdrv, &subdrv->list, list) {
if (subdrv->close) if (subdrv->close)
subdrv->close(dev, subdrv->manager.dev, file); subdrv->close(dev, subdrv->dev, file);
} }
return ret; return ret;
} }
...@@ -209,7 +211,7 @@ void exynos_drm_subdrv_close(struct drm_device *dev, struct drm_file *file) ...@@ -209,7 +211,7 @@ void exynos_drm_subdrv_close(struct drm_device *dev, struct drm_file *file)
list_for_each_entry(subdrv, &exynos_drm_subdrv_list, list) { list_for_each_entry(subdrv, &exynos_drm_subdrv_list, list) {
if (subdrv->close) if (subdrv->close)
subdrv->close(dev, subdrv->manager.dev, file); subdrv->close(dev, subdrv->dev, file);
} }
} }
EXPORT_SYMBOL_GPL(exynos_drm_subdrv_close); EXPORT_SYMBOL_GPL(exynos_drm_subdrv_close);
...@@ -225,24 +225,25 @@ struct exynos_drm_private { ...@@ -225,24 +225,25 @@ struct exynos_drm_private {
* Exynos drm sub driver structure. * Exynos drm sub driver structure.
* *
* @list: sub driver has its own list object to register to exynos drm driver. * @list: sub driver has its own list object to register to exynos drm driver.
* @dev: pointer to device object for subdrv device driver.
* @drm_dev: pointer to drm_device and this pointer would be set * @drm_dev: pointer to drm_device and this pointer would be set
* when sub driver calls exynos_drm_subdrv_register(). * when sub driver calls exynos_drm_subdrv_register().
* @is_local: appear encoder and connector disrelated device. * @manager: subdrv has its own manager to control a hardware appropriately
* and we can access a hardware drawing on this manager.
* @probe: this callback would be called by exynos drm driver after * @probe: this callback would be called by exynos drm driver after
* subdrv is registered to it. * subdrv is registered to it.
* @remove: this callback is used to release resources created * @remove: this callback is used to release resources created
* by probe callback. * by probe callback.
* @open: this would be called with drm device file open. * @open: this would be called with drm device file open.
* @close: this would be called with drm device file close. * @close: this would be called with drm device file close.
* @manager: subdrv has its own manager to control a hardware appropriately
* and we can access a hardware drawing on this manager.
* @encoder: encoder object owned by this sub driver. * @encoder: encoder object owned by this sub driver.
* @connector: connector object owned by this sub driver. * @connector: connector object owned by this sub driver.
*/ */
struct exynos_drm_subdrv { struct exynos_drm_subdrv {
struct list_head list; struct list_head list;
struct device *dev;
struct drm_device *drm_dev; struct drm_device *drm_dev;
bool is_local; struct exynos_drm_manager *manager;
int (*probe)(struct drm_device *drm_dev, struct device *dev); int (*probe)(struct drm_device *drm_dev, struct device *dev);
void (*remove)(struct drm_device *dev); void (*remove)(struct drm_device *dev);
...@@ -251,7 +252,6 @@ struct exynos_drm_subdrv { ...@@ -251,7 +252,6 @@ struct exynos_drm_subdrv {
void (*close)(struct drm_device *drm_dev, struct device *dev, void (*close)(struct drm_device *drm_dev, struct device *dev,
struct drm_file *file); struct drm_file *file);
struct exynos_drm_manager manager;
struct drm_encoder *encoder; struct drm_encoder *encoder;
struct drm_connector *connector; struct drm_connector *connector;
}; };
......
...@@ -172,7 +172,7 @@ static void fimd_dpms(struct device *subdrv_dev, int mode) ...@@ -172,7 +172,7 @@ static void fimd_dpms(struct device *subdrv_dev, int mode)
static void fimd_apply(struct device *subdrv_dev) static void fimd_apply(struct device *subdrv_dev)
{ {
struct fimd_context *ctx = get_fimd_context(subdrv_dev); struct fimd_context *ctx = get_fimd_context(subdrv_dev);
struct exynos_drm_manager *mgr = &ctx->subdrv.manager; struct exynos_drm_manager *mgr = ctx->subdrv.manager;
struct exynos_drm_manager_ops *mgr_ops = mgr->ops; struct exynos_drm_manager_ops *mgr_ops = mgr->ops;
struct exynos_drm_overlay_ops *ovl_ops = mgr->overlay_ops; struct exynos_drm_overlay_ops *ovl_ops = mgr->overlay_ops;
struct fimd_win_data *win_data; struct fimd_win_data *win_data;
...@@ -577,6 +577,13 @@ static struct exynos_drm_overlay_ops fimd_overlay_ops = { ...@@ -577,6 +577,13 @@ static struct exynos_drm_overlay_ops fimd_overlay_ops = {
.disable = fimd_win_disable, .disable = fimd_win_disable,
}; };
static struct exynos_drm_manager fimd_manager = {
.pipe = -1,
.ops = &fimd_manager_ops,
.overlay_ops = &fimd_overlay_ops,
.display_ops = &fimd_display_ops,
};
static void fimd_finish_pageflip(struct drm_device *drm_dev, int crtc) static void fimd_finish_pageflip(struct drm_device *drm_dev, int crtc)
{ {
struct exynos_drm_private *dev_priv = drm_dev->dev_private; struct exynos_drm_private *dev_priv = drm_dev->dev_private;
...@@ -628,7 +635,7 @@ static irqreturn_t fimd_irq_handler(int irq, void *dev_id) ...@@ -628,7 +635,7 @@ static irqreturn_t fimd_irq_handler(int irq, void *dev_id)
struct fimd_context *ctx = (struct fimd_context *)dev_id; struct fimd_context *ctx = (struct fimd_context *)dev_id;
struct exynos_drm_subdrv *subdrv = &ctx->subdrv; struct exynos_drm_subdrv *subdrv = &ctx->subdrv;
struct drm_device *drm_dev = subdrv->drm_dev; struct drm_device *drm_dev = subdrv->drm_dev;
struct exynos_drm_manager *manager = &subdrv->manager; struct exynos_drm_manager *manager = subdrv->manager;
u32 val; u32 val;
val = readl(ctx->regs + VIDINTCON1); val = readl(ctx->regs + VIDINTCON1);
...@@ -744,7 +751,7 @@ static void fimd_clear_win(struct fimd_context *ctx, int win) ...@@ -744,7 +751,7 @@ static void fimd_clear_win(struct fimd_context *ctx, int win)
static int fimd_power_on(struct fimd_context *ctx, bool enable) static int fimd_power_on(struct fimd_context *ctx, bool enable)
{ {
struct exynos_drm_subdrv *subdrv = &ctx->subdrv; struct exynos_drm_subdrv *subdrv = &ctx->subdrv;
struct device *dev = subdrv->manager.dev; struct device *dev = subdrv->dev;
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
...@@ -867,13 +874,10 @@ static int __devinit fimd_probe(struct platform_device *pdev) ...@@ -867,13 +874,10 @@ static int __devinit fimd_probe(struct platform_device *pdev)
subdrv = &ctx->subdrv; subdrv = &ctx->subdrv;
subdrv->dev = dev;
subdrv->manager = &fimd_manager;
subdrv->probe = fimd_subdrv_probe; subdrv->probe = fimd_subdrv_probe;
subdrv->remove = fimd_subdrv_remove; subdrv->remove = fimd_subdrv_remove;
subdrv->manager.pipe = -1;
subdrv->manager.ops = &fimd_manager_ops;
subdrv->manager.overlay_ops = &fimd_overlay_ops;
subdrv->manager.display_ops = &fimd_display_ops;
subdrv->manager.dev = dev;
mutex_init(&ctx->lock); mutex_init(&ctx->lock);
......
...@@ -56,9 +56,28 @@ static unsigned int convert_to_vm_err_msg(int msg) ...@@ -56,9 +56,28 @@ static unsigned int convert_to_vm_err_msg(int msg)
return out_msg; return out_msg;
} }
static unsigned int mask_gem_flags(unsigned int flags) static int check_gem_flags(unsigned int flags)
{ {
return flags &= EXYNOS_BO_NONCONTIG; if (flags & ~(EXYNOS_BO_MASK)) {
DRM_ERROR("invalid flags.\n");
return -EINVAL;
}
return 0;
}
static unsigned long roundup_gem_size(unsigned long size, unsigned int flags)
{
if (!IS_NONCONTIG_BUFFER(flags)) {
if (size >= SZ_1M)
return roundup(size, SECTION_SIZE);
else if (size >= SZ_64K)
return roundup(size, SZ_64K);
else
goto out;
}
out:
return roundup(size, PAGE_SIZE);
} }
static struct page **exynos_gem_get_pages(struct drm_gem_object *obj, static struct page **exynos_gem_get_pages(struct drm_gem_object *obj,
...@@ -319,10 +338,17 @@ struct exynos_drm_gem_obj *exynos_drm_gem_create(struct drm_device *dev, ...@@ -319,10 +338,17 @@ struct exynos_drm_gem_obj *exynos_drm_gem_create(struct drm_device *dev,
struct exynos_drm_gem_buf *buf; struct exynos_drm_gem_buf *buf;
int ret; int ret;
size = roundup(size, PAGE_SIZE); if (!size) {
DRM_DEBUG_KMS("%s: size = 0x%lx\n", __FILE__, size); DRM_ERROR("invalid size.\n");
return ERR_PTR(-EINVAL);
}
flags = mask_gem_flags(flags); size = roundup_gem_size(size, flags);
DRM_DEBUG_KMS("%s\n", __FILE__);
ret = check_gem_flags(flags);
if (ret)
return ERR_PTR(ret);
buf = exynos_drm_init_buf(dev, size); buf = exynos_drm_init_buf(dev, size);
if (!buf) if (!buf)
...@@ -331,7 +357,7 @@ struct exynos_drm_gem_obj *exynos_drm_gem_create(struct drm_device *dev, ...@@ -331,7 +357,7 @@ struct exynos_drm_gem_obj *exynos_drm_gem_create(struct drm_device *dev,
exynos_gem_obj = exynos_drm_gem_init(dev, size); exynos_gem_obj = exynos_drm_gem_init(dev, size);
if (!exynos_gem_obj) { if (!exynos_gem_obj) {
ret = -ENOMEM; ret = -ENOMEM;
goto err; goto err_fini_buf;
} }
exynos_gem_obj->buffer = buf; exynos_gem_obj->buffer = buf;
...@@ -347,18 +373,19 @@ struct exynos_drm_gem_obj *exynos_drm_gem_create(struct drm_device *dev, ...@@ -347,18 +373,19 @@ struct exynos_drm_gem_obj *exynos_drm_gem_create(struct drm_device *dev,
ret = exynos_drm_gem_get_pages(&exynos_gem_obj->base); ret = exynos_drm_gem_get_pages(&exynos_gem_obj->base);
if (ret < 0) { if (ret < 0) {
drm_gem_object_release(&exynos_gem_obj->base); drm_gem_object_release(&exynos_gem_obj->base);
goto err; goto err_fini_buf;
} }
} else { } else {
ret = exynos_drm_alloc_buf(dev, buf, flags); ret = exynos_drm_alloc_buf(dev, buf, flags);
if (ret < 0) { if (ret < 0) {
drm_gem_object_release(&exynos_gem_obj->base); drm_gem_object_release(&exynos_gem_obj->base);
goto err; goto err_fini_buf;
} }
} }
return exynos_gem_obj; return exynos_gem_obj;
err:
err_fini_buf:
exynos_drm_fini_buf(dev, buf); exynos_drm_fini_buf(dev, buf);
return ERR_PTR(ret); return ERR_PTR(ret);
} }
......
...@@ -29,6 +29,8 @@ ...@@ -29,6 +29,8 @@
#define to_exynos_gem_obj(x) container_of(x,\ #define to_exynos_gem_obj(x) container_of(x,\
struct exynos_drm_gem_obj, base) struct exynos_drm_gem_obj, base)
#define IS_NONCONTIG_BUFFER(f) (f & EXYNOS_BO_NONCONTIG)
/* /*
* exynos drm gem buffer structure. * exynos drm gem buffer structure.
* *
......
...@@ -30,9 +30,8 @@ ...@@ -30,9 +30,8 @@
struct drm_hdmi_context, subdrv); struct drm_hdmi_context, subdrv);
/* these callback points shoud be set by specific drivers. */ /* these callback points shoud be set by specific drivers. */
static struct exynos_hdmi_display_ops *hdmi_display_ops; static struct exynos_hdmi_ops *hdmi_ops;
static struct exynos_hdmi_manager_ops *hdmi_manager_ops; static struct exynos_mixer_ops *mixer_ops;
static struct exynos_hdmi_overlay_ops *hdmi_overlay_ops;
struct drm_hdmi_context { struct drm_hdmi_context {
struct exynos_drm_subdrv subdrv; struct exynos_drm_subdrv subdrv;
...@@ -40,31 +39,20 @@ struct drm_hdmi_context { ...@@ -40,31 +39,20 @@ struct drm_hdmi_context {
struct exynos_drm_hdmi_context *mixer_ctx; struct exynos_drm_hdmi_context *mixer_ctx;
}; };
void exynos_drm_display_ops_register(struct exynos_hdmi_display_ops void exynos_hdmi_ops_register(struct exynos_hdmi_ops *ops)
*display_ops)
{ {
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (display_ops) if (ops)
hdmi_display_ops = display_ops; hdmi_ops = ops;
} }
void exynos_drm_manager_ops_register(struct exynos_hdmi_manager_ops void exynos_mixer_ops_register(struct exynos_mixer_ops *ops)
*manager_ops)
{ {
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (manager_ops) if (ops)
hdmi_manager_ops = manager_ops; mixer_ops = ops;
}
void exynos_drm_overlay_ops_register(struct exynos_hdmi_overlay_ops
*overlay_ops)
{
DRM_DEBUG_KMS("%s\n", __FILE__);
if (overlay_ops)
hdmi_overlay_ops = overlay_ops;
} }
static bool drm_hdmi_is_connected(struct device *dev) static bool drm_hdmi_is_connected(struct device *dev)
...@@ -73,8 +61,8 @@ static bool drm_hdmi_is_connected(struct device *dev) ...@@ -73,8 +61,8 @@ static bool drm_hdmi_is_connected(struct device *dev)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_display_ops && hdmi_display_ops->is_connected) if (hdmi_ops && hdmi_ops->is_connected)
return hdmi_display_ops->is_connected(ctx->hdmi_ctx->ctx); return hdmi_ops->is_connected(ctx->hdmi_ctx->ctx);
return false; return false;
} }
...@@ -86,9 +74,9 @@ static int drm_hdmi_get_edid(struct device *dev, ...@@ -86,9 +74,9 @@ static int drm_hdmi_get_edid(struct device *dev,
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_display_ops && hdmi_display_ops->get_edid) if (hdmi_ops && hdmi_ops->get_edid)
return hdmi_display_ops->get_edid(ctx->hdmi_ctx->ctx, return hdmi_ops->get_edid(ctx->hdmi_ctx->ctx, connector, edid,
connector, edid, len); len);
return 0; return 0;
} }
...@@ -99,9 +87,8 @@ static int drm_hdmi_check_timing(struct device *dev, void *timing) ...@@ -99,9 +87,8 @@ static int drm_hdmi_check_timing(struct device *dev, void *timing)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_display_ops && hdmi_display_ops->check_timing) if (hdmi_ops && hdmi_ops->check_timing)
return hdmi_display_ops->check_timing(ctx->hdmi_ctx->ctx, return hdmi_ops->check_timing(ctx->hdmi_ctx->ctx, timing);
timing);
return 0; return 0;
} }
...@@ -112,8 +99,8 @@ static int drm_hdmi_power_on(struct device *dev, int mode) ...@@ -112,8 +99,8 @@ static int drm_hdmi_power_on(struct device *dev, int mode)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_display_ops && hdmi_display_ops->power_on) if (hdmi_ops && hdmi_ops->power_on)
return hdmi_display_ops->power_on(ctx->hdmi_ctx->ctx, mode); return hdmi_ops->power_on(ctx->hdmi_ctx->ctx, mode);
return 0; return 0;
} }
...@@ -130,13 +117,13 @@ static int drm_hdmi_enable_vblank(struct device *subdrv_dev) ...@@ -130,13 +117,13 @@ static int drm_hdmi_enable_vblank(struct device *subdrv_dev)
{ {
struct drm_hdmi_context *ctx = to_context(subdrv_dev); struct drm_hdmi_context *ctx = to_context(subdrv_dev);
struct exynos_drm_subdrv *subdrv = &ctx->subdrv; struct exynos_drm_subdrv *subdrv = &ctx->subdrv;
struct exynos_drm_manager *manager = &subdrv->manager; struct exynos_drm_manager *manager = subdrv->manager;
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_overlay_ops && hdmi_overlay_ops->enable_vblank) if (mixer_ops && mixer_ops->enable_vblank)
return hdmi_overlay_ops->enable_vblank(ctx->mixer_ctx->ctx, return mixer_ops->enable_vblank(ctx->mixer_ctx->ctx,
manager->pipe); manager->pipe);
return 0; return 0;
} }
...@@ -147,8 +134,8 @@ static void drm_hdmi_disable_vblank(struct device *subdrv_dev) ...@@ -147,8 +134,8 @@ static void drm_hdmi_disable_vblank(struct device *subdrv_dev)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_overlay_ops && hdmi_overlay_ops->disable_vblank) if (mixer_ops && mixer_ops->disable_vblank)
return hdmi_overlay_ops->disable_vblank(ctx->mixer_ctx->ctx); return mixer_ops->disable_vblank(ctx->mixer_ctx->ctx);
} }
static void drm_hdmi_mode_fixup(struct device *subdrv_dev, static void drm_hdmi_mode_fixup(struct device *subdrv_dev,
...@@ -160,9 +147,9 @@ static void drm_hdmi_mode_fixup(struct device *subdrv_dev, ...@@ -160,9 +147,9 @@ static void drm_hdmi_mode_fixup(struct device *subdrv_dev,
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_manager_ops && hdmi_manager_ops->mode_fixup) if (hdmi_ops && hdmi_ops->mode_fixup)
hdmi_manager_ops->mode_fixup(ctx->hdmi_ctx->ctx, connector, hdmi_ops->mode_fixup(ctx->hdmi_ctx->ctx, connector, mode,
mode, adjusted_mode); adjusted_mode);
} }
static void drm_hdmi_mode_set(struct device *subdrv_dev, void *mode) static void drm_hdmi_mode_set(struct device *subdrv_dev, void *mode)
...@@ -171,8 +158,8 @@ static void drm_hdmi_mode_set(struct device *subdrv_dev, void *mode) ...@@ -171,8 +158,8 @@ static void drm_hdmi_mode_set(struct device *subdrv_dev, void *mode)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_manager_ops && hdmi_manager_ops->mode_set) if (hdmi_ops && hdmi_ops->mode_set)
hdmi_manager_ops->mode_set(ctx->hdmi_ctx->ctx, mode); hdmi_ops->mode_set(ctx->hdmi_ctx->ctx, mode);
} }
static void drm_hdmi_get_max_resol(struct device *subdrv_dev, static void drm_hdmi_get_max_resol(struct device *subdrv_dev,
...@@ -182,9 +169,8 @@ static void drm_hdmi_get_max_resol(struct device *subdrv_dev, ...@@ -182,9 +169,8 @@ static void drm_hdmi_get_max_resol(struct device *subdrv_dev,
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_manager_ops && hdmi_manager_ops->get_max_resol) if (hdmi_ops && hdmi_ops->get_max_resol)
hdmi_manager_ops->get_max_resol(ctx->hdmi_ctx->ctx, width, hdmi_ops->get_max_resol(ctx->hdmi_ctx->ctx, width, height);
height);
} }
static void drm_hdmi_commit(struct device *subdrv_dev) static void drm_hdmi_commit(struct device *subdrv_dev)
...@@ -193,8 +179,8 @@ static void drm_hdmi_commit(struct device *subdrv_dev) ...@@ -193,8 +179,8 @@ static void drm_hdmi_commit(struct device *subdrv_dev)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_manager_ops && hdmi_manager_ops->commit) if (hdmi_ops && hdmi_ops->commit)
hdmi_manager_ops->commit(ctx->hdmi_ctx->ctx); hdmi_ops->commit(ctx->hdmi_ctx->ctx);
} }
static void drm_hdmi_dpms(struct device *subdrv_dev, int mode) static void drm_hdmi_dpms(struct device *subdrv_dev, int mode)
...@@ -209,8 +195,8 @@ static void drm_hdmi_dpms(struct device *subdrv_dev, int mode) ...@@ -209,8 +195,8 @@ static void drm_hdmi_dpms(struct device *subdrv_dev, int mode)
case DRM_MODE_DPMS_STANDBY: case DRM_MODE_DPMS_STANDBY:
case DRM_MODE_DPMS_SUSPEND: case DRM_MODE_DPMS_SUSPEND:
case DRM_MODE_DPMS_OFF: case DRM_MODE_DPMS_OFF:
if (hdmi_manager_ops && hdmi_manager_ops->disable) if (hdmi_ops && hdmi_ops->disable)
hdmi_manager_ops->disable(ctx->hdmi_ctx->ctx); hdmi_ops->disable(ctx->hdmi_ctx->ctx);
break; break;
default: default:
DRM_DEBUG_KMS("unkown dps mode: %d\n", mode); DRM_DEBUG_KMS("unkown dps mode: %d\n", mode);
...@@ -235,8 +221,8 @@ static void drm_mixer_mode_set(struct device *subdrv_dev, ...@@ -235,8 +221,8 @@ static void drm_mixer_mode_set(struct device *subdrv_dev,
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_overlay_ops && hdmi_overlay_ops->win_mode_set) if (mixer_ops && mixer_ops->win_mode_set)
hdmi_overlay_ops->win_mode_set(ctx->mixer_ctx->ctx, overlay); mixer_ops->win_mode_set(ctx->mixer_ctx->ctx, overlay);
} }
static void drm_mixer_commit(struct device *subdrv_dev, int zpos) static void drm_mixer_commit(struct device *subdrv_dev, int zpos)
...@@ -245,8 +231,8 @@ static void drm_mixer_commit(struct device *subdrv_dev, int zpos) ...@@ -245,8 +231,8 @@ static void drm_mixer_commit(struct device *subdrv_dev, int zpos)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_overlay_ops && hdmi_overlay_ops->win_commit) if (mixer_ops && mixer_ops->win_commit)
hdmi_overlay_ops->win_commit(ctx->mixer_ctx->ctx, zpos); mixer_ops->win_commit(ctx->mixer_ctx->ctx, zpos);
} }
static void drm_mixer_disable(struct device *subdrv_dev, int zpos) static void drm_mixer_disable(struct device *subdrv_dev, int zpos)
...@@ -255,8 +241,8 @@ static void drm_mixer_disable(struct device *subdrv_dev, int zpos) ...@@ -255,8 +241,8 @@ static void drm_mixer_disable(struct device *subdrv_dev, int zpos)
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
if (hdmi_overlay_ops && hdmi_overlay_ops->win_disable) if (mixer_ops && mixer_ops->win_disable)
hdmi_overlay_ops->win_disable(ctx->mixer_ctx->ctx, zpos); mixer_ops->win_disable(ctx->mixer_ctx->ctx, zpos);
} }
static struct exynos_drm_overlay_ops drm_hdmi_overlay_ops = { static struct exynos_drm_overlay_ops drm_hdmi_overlay_ops = {
...@@ -265,6 +251,12 @@ static struct exynos_drm_overlay_ops drm_hdmi_overlay_ops = { ...@@ -265,6 +251,12 @@ static struct exynos_drm_overlay_ops drm_hdmi_overlay_ops = {
.disable = drm_mixer_disable, .disable = drm_mixer_disable,
}; };
static struct exynos_drm_manager hdmi_manager = {
.pipe = -1,
.ops = &drm_hdmi_manager_ops,
.overlay_ops = &drm_hdmi_overlay_ops,
.display_ops = &drm_hdmi_display_ops,
};
static int hdmi_subdrv_probe(struct drm_device *drm_dev, static int hdmi_subdrv_probe(struct drm_device *drm_dev,
struct device *dev) struct device *dev)
...@@ -332,12 +324,9 @@ static int __devinit exynos_drm_hdmi_probe(struct platform_device *pdev) ...@@ -332,12 +324,9 @@ static int __devinit exynos_drm_hdmi_probe(struct platform_device *pdev)
subdrv = &ctx->subdrv; subdrv = &ctx->subdrv;
subdrv->dev = dev;
subdrv->manager = &hdmi_manager;
subdrv->probe = hdmi_subdrv_probe; subdrv->probe = hdmi_subdrv_probe;
subdrv->manager.pipe = -1;
subdrv->manager.ops = &drm_hdmi_manager_ops;
subdrv->manager.overlay_ops = &drm_hdmi_overlay_ops;
subdrv->manager.display_ops = &drm_hdmi_display_ops;
subdrv->manager.dev = dev;
platform_set_drvdata(pdev, subdrv); platform_set_drvdata(pdev, subdrv);
......
...@@ -38,15 +38,15 @@ struct exynos_drm_hdmi_context { ...@@ -38,15 +38,15 @@ struct exynos_drm_hdmi_context {
void *ctx; void *ctx;
}; };
struct exynos_hdmi_display_ops { struct exynos_hdmi_ops {
/* display */
bool (*is_connected)(void *ctx); bool (*is_connected)(void *ctx);
int (*get_edid)(void *ctx, struct drm_connector *connector, int (*get_edid)(void *ctx, struct drm_connector *connector,
u8 *edid, int len); u8 *edid, int len);
int (*check_timing)(void *ctx, void *timing); int (*check_timing)(void *ctx, void *timing);
int (*power_on)(void *ctx, int mode); int (*power_on)(void *ctx, int mode);
};
struct exynos_hdmi_manager_ops { /* manager */
void (*mode_fixup)(void *ctx, struct drm_connector *connector, void (*mode_fixup)(void *ctx, struct drm_connector *connector,
struct drm_display_mode *mode, struct drm_display_mode *mode,
struct drm_display_mode *adjusted_mode); struct drm_display_mode *adjusted_mode);
...@@ -57,22 +57,17 @@ struct exynos_hdmi_manager_ops { ...@@ -57,22 +57,17 @@ struct exynos_hdmi_manager_ops {
void (*disable)(void *ctx); void (*disable)(void *ctx);
}; };
struct exynos_hdmi_overlay_ops { struct exynos_mixer_ops {
/* manager */
int (*enable_vblank)(void *ctx, int pipe); int (*enable_vblank)(void *ctx, int pipe);
void (*disable_vblank)(void *ctx); void (*disable_vblank)(void *ctx);
/* overlay */
void (*win_mode_set)(void *ctx, struct exynos_drm_overlay *overlay); void (*win_mode_set)(void *ctx, struct exynos_drm_overlay *overlay);
void (*win_commit)(void *ctx, int zpos); void (*win_commit)(void *ctx, int zpos);
void (*win_disable)(void *ctx, int zpos); void (*win_disable)(void *ctx, int zpos);
}; };
extern struct platform_driver hdmi_driver; void exynos_hdmi_ops_register(struct exynos_hdmi_ops *ops);
extern struct platform_driver mixer_driver; void exynos_mixer_ops_register(struct exynos_mixer_ops *ops);
void exynos_drm_display_ops_register(struct exynos_hdmi_display_ops
*display_ops);
void exynos_drm_manager_ops_register(struct exynos_hdmi_manager_ops
*manager_ops);
void exynos_drm_overlay_ops_register(struct exynos_hdmi_overlay_ops
*overlay_ops);
#endif #endif
...@@ -24,6 +24,10 @@ struct exynos_plane { ...@@ -24,6 +24,10 @@ struct exynos_plane {
static const uint32_t formats[] = { static const uint32_t formats[] = {
DRM_FORMAT_XRGB8888, DRM_FORMAT_XRGB8888,
DRM_FORMAT_ARGB8888,
DRM_FORMAT_NV12,
DRM_FORMAT_NV12M,
DRM_FORMAT_NV12MT,
}; };
static int static int
......
...@@ -199,7 +199,7 @@ static void vidi_dpms(struct device *subdrv_dev, int mode) ...@@ -199,7 +199,7 @@ static void vidi_dpms(struct device *subdrv_dev, int mode)
static void vidi_apply(struct device *subdrv_dev) static void vidi_apply(struct device *subdrv_dev)
{ {
struct vidi_context *ctx = get_vidi_context(subdrv_dev); struct vidi_context *ctx = get_vidi_context(subdrv_dev);
struct exynos_drm_manager *mgr = &ctx->subdrv.manager; struct exynos_drm_manager *mgr = ctx->subdrv.manager;
struct exynos_drm_manager_ops *mgr_ops = mgr->ops; struct exynos_drm_manager_ops *mgr_ops = mgr->ops;
struct exynos_drm_overlay_ops *ovl_ops = mgr->overlay_ops; struct exynos_drm_overlay_ops *ovl_ops = mgr->overlay_ops;
struct vidi_win_data *win_data; struct vidi_win_data *win_data;
...@@ -374,6 +374,13 @@ static struct exynos_drm_overlay_ops vidi_overlay_ops = { ...@@ -374,6 +374,13 @@ static struct exynos_drm_overlay_ops vidi_overlay_ops = {
.disable = vidi_win_disable, .disable = vidi_win_disable,
}; };
static struct exynos_drm_manager vidi_manager = {
.pipe = -1,
.ops = &vidi_manager_ops,
.overlay_ops = &vidi_overlay_ops,
.display_ops = &vidi_display_ops,
};
static void vidi_finish_pageflip(struct drm_device *drm_dev, int crtc) static void vidi_finish_pageflip(struct drm_device *drm_dev, int crtc)
{ {
struct exynos_drm_private *dev_priv = drm_dev->dev_private; struct exynos_drm_private *dev_priv = drm_dev->dev_private;
...@@ -425,7 +432,7 @@ static void vidi_fake_vblank_handler(struct work_struct *work) ...@@ -425,7 +432,7 @@ static void vidi_fake_vblank_handler(struct work_struct *work)
struct vidi_context *ctx = container_of(work, struct vidi_context, struct vidi_context *ctx = container_of(work, struct vidi_context,
work); work);
struct exynos_drm_subdrv *subdrv = &ctx->subdrv; struct exynos_drm_subdrv *subdrv = &ctx->subdrv;
struct exynos_drm_manager *manager = &subdrv->manager; struct exynos_drm_manager *manager = subdrv->manager;
if (manager->pipe < 0) if (manager->pipe < 0)
return; return;
...@@ -471,7 +478,7 @@ static void vidi_subdrv_remove(struct drm_device *drm_dev) ...@@ -471,7 +478,7 @@ static void vidi_subdrv_remove(struct drm_device *drm_dev)
static int vidi_power_on(struct vidi_context *ctx, bool enable) static int vidi_power_on(struct vidi_context *ctx, bool enable)
{ {
struct exynos_drm_subdrv *subdrv = &ctx->subdrv; struct exynos_drm_subdrv *subdrv = &ctx->subdrv;
struct device *dev = subdrv->manager.dev; struct device *dev = subdrv->dev;
DRM_DEBUG_KMS("%s\n", __FILE__); DRM_DEBUG_KMS("%s\n", __FILE__);
...@@ -611,13 +618,10 @@ static int __devinit vidi_probe(struct platform_device *pdev) ...@@ -611,13 +618,10 @@ static int __devinit vidi_probe(struct platform_device *pdev)
ctx->raw_edid = (struct edid *)fake_edid_info; ctx->raw_edid = (struct edid *)fake_edid_info;
subdrv = &ctx->subdrv; subdrv = &ctx->subdrv;
subdrv->dev = dev;
subdrv->manager = &vidi_manager;
subdrv->probe = vidi_subdrv_probe; subdrv->probe = vidi_subdrv_probe;
subdrv->remove = vidi_subdrv_remove; subdrv->remove = vidi_subdrv_remove;
subdrv->manager.pipe = -1;
subdrv->manager.ops = &vidi_manager_ops;
subdrv->manager.overlay_ops = &vidi_overlay_ops;
subdrv->manager.display_ops = &vidi_display_ops;
subdrv->manager.dev = dev;
mutex_init(&ctx->lock); mutex_init(&ctx->lock);
......
...@@ -40,7 +40,6 @@ ...@@ -40,7 +40,6 @@
#include "exynos_hdmi.h" #include "exynos_hdmi.h"
#define HDMI_OVERLAY_NUMBER 3
#define MAX_WIDTH 1920 #define MAX_WIDTH 1920
#define MAX_HEIGHT 1080 #define MAX_HEIGHT 1080
#define get_hdmi_context(dev) platform_get_drvdata(to_platform_device(dev)) #define get_hdmi_context(dev) platform_get_drvdata(to_platform_device(dev))
...@@ -1194,7 +1193,7 @@ static int hdmi_conf_index(struct hdmi_context *hdata, ...@@ -1194,7 +1193,7 @@ static int hdmi_conf_index(struct hdmi_context *hdata,
static bool hdmi_is_connected(void *ctx) static bool hdmi_is_connected(void *ctx)
{ {
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
u32 val = hdmi_reg_read(hdata, HDMI_HPD_STATUS); u32 val = hdmi_reg_read(hdata, HDMI_HPD_STATUS);
if (val) if (val)
...@@ -1207,7 +1206,7 @@ static int hdmi_get_edid(void *ctx, struct drm_connector *connector, ...@@ -1207,7 +1206,7 @@ static int hdmi_get_edid(void *ctx, struct drm_connector *connector,
u8 *edid, int len) u8 *edid, int len)
{ {
struct edid *raw_edid; struct edid *raw_edid;
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
...@@ -1275,7 +1274,7 @@ static int hdmi_v14_check_timing(struct fb_videomode *check_timing) ...@@ -1275,7 +1274,7 @@ static int hdmi_v14_check_timing(struct fb_videomode *check_timing)
static int hdmi_check_timing(void *ctx, void *timing) static int hdmi_check_timing(void *ctx, void *timing)
{ {
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
struct fb_videomode *check_timing = timing; struct fb_videomode *check_timing = timing;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
...@@ -1312,13 +1311,6 @@ static int hdmi_display_power_on(void *ctx, int mode) ...@@ -1312,13 +1311,6 @@ static int hdmi_display_power_on(void *ctx, int mode)
return 0; return 0;
} }
static struct exynos_hdmi_display_ops display_ops = {
.is_connected = hdmi_is_connected,
.get_edid = hdmi_get_edid,
.check_timing = hdmi_check_timing,
.power_on = hdmi_display_power_on,
};
static void hdmi_set_acr(u32 freq, u8 *acr) static void hdmi_set_acr(u32 freq, u8 *acr)
{ {
u32 n, cts; u32 n, cts;
...@@ -1914,7 +1906,7 @@ static void hdmi_mode_fixup(void *ctx, struct drm_connector *connector, ...@@ -1914,7 +1906,7 @@ static void hdmi_mode_fixup(void *ctx, struct drm_connector *connector,
struct drm_display_mode *adjusted_mode) struct drm_display_mode *adjusted_mode)
{ {
struct drm_display_mode *m; struct drm_display_mode *m;
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
int index; int index;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
...@@ -1951,7 +1943,7 @@ static void hdmi_mode_fixup(void *ctx, struct drm_connector *connector, ...@@ -1951,7 +1943,7 @@ static void hdmi_mode_fixup(void *ctx, struct drm_connector *connector,
static void hdmi_mode_set(void *ctx, void *mode) static void hdmi_mode_set(void *ctx, void *mode)
{ {
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
int conf_idx; int conf_idx;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
...@@ -1974,7 +1966,7 @@ static void hdmi_get_max_resol(void *ctx, unsigned int *width, ...@@ -1974,7 +1966,7 @@ static void hdmi_get_max_resol(void *ctx, unsigned int *width,
static void hdmi_commit(void *ctx) static void hdmi_commit(void *ctx)
{ {
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
...@@ -1985,7 +1977,7 @@ static void hdmi_commit(void *ctx) ...@@ -1985,7 +1977,7 @@ static void hdmi_commit(void *ctx)
static void hdmi_disable(void *ctx) static void hdmi_disable(void *ctx)
{ {
struct hdmi_context *hdata = (struct hdmi_context *)ctx; struct hdmi_context *hdata = ctx;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
...@@ -1996,7 +1988,14 @@ static void hdmi_disable(void *ctx) ...@@ -1996,7 +1988,14 @@ static void hdmi_disable(void *ctx)
} }
} }
static struct exynos_hdmi_manager_ops manager_ops = { static struct exynos_hdmi_ops hdmi_ops = {
/* display */
.is_connected = hdmi_is_connected,
.get_edid = hdmi_get_edid,
.check_timing = hdmi_check_timing,
.power_on = hdmi_display_power_on,
/* manager */
.mode_fixup = hdmi_mode_fixup, .mode_fixup = hdmi_mode_fixup,
.mode_set = hdmi_mode_set, .mode_set = hdmi_mode_set,
.get_max_resol = hdmi_get_max_resol, .get_max_resol = hdmi_get_max_resol,
...@@ -2020,7 +2019,7 @@ static void hdmi_hotplug_func(struct work_struct *work) ...@@ -2020,7 +2019,7 @@ static void hdmi_hotplug_func(struct work_struct *work)
static irqreturn_t hdmi_irq_handler(int irq, void *arg) static irqreturn_t hdmi_irq_handler(int irq, void *arg)
{ {
struct exynos_drm_hdmi_context *ctx = arg; struct exynos_drm_hdmi_context *ctx = arg;
struct hdmi_context *hdata = (struct hdmi_context *)ctx->ctx; struct hdmi_context *hdata = ctx->ctx;
u32 intc_flag; u32 intc_flag;
intc_flag = hdmi_reg_read(hdata, HDMI_INTC_FLAG); intc_flag = hdmi_reg_read(hdata, HDMI_INTC_FLAG);
...@@ -2173,7 +2172,7 @@ static int hdmi_runtime_suspend(struct device *dev) ...@@ -2173,7 +2172,7 @@ static int hdmi_runtime_suspend(struct device *dev)
DRM_DEBUG_KMS("%s\n", __func__); DRM_DEBUG_KMS("%s\n", __func__);
hdmi_resource_poweroff((struct hdmi_context *)ctx->ctx); hdmi_resource_poweroff(ctx->ctx);
return 0; return 0;
} }
...@@ -2184,7 +2183,7 @@ static int hdmi_runtime_resume(struct device *dev) ...@@ -2184,7 +2183,7 @@ static int hdmi_runtime_resume(struct device *dev)
DRM_DEBUG_KMS("%s\n", __func__); DRM_DEBUG_KMS("%s\n", __func__);
hdmi_resource_poweron((struct hdmi_context *)ctx->ctx); hdmi_resource_poweron(ctx->ctx);
return 0; return 0;
} }
...@@ -2322,8 +2321,7 @@ static int __devinit hdmi_probe(struct platform_device *pdev) ...@@ -2322,8 +2321,7 @@ static int __devinit hdmi_probe(struct platform_device *pdev)
hdata->irq = res->start; hdata->irq = res->start;
/* register specific callbacks to common hdmi. */ /* register specific callbacks to common hdmi. */
exynos_drm_display_ops_register(&display_ops); exynos_hdmi_ops_register(&hdmi_ops);
exynos_drm_manager_ops_register(&manager_ops);
hdmi_resource_poweron(hdata); hdmi_resource_poweron(hdata);
...@@ -2351,7 +2349,7 @@ static int __devinit hdmi_probe(struct platform_device *pdev) ...@@ -2351,7 +2349,7 @@ static int __devinit hdmi_probe(struct platform_device *pdev)
static int __devexit hdmi_remove(struct platform_device *pdev) static int __devexit hdmi_remove(struct platform_device *pdev)
{ {
struct exynos_drm_hdmi_context *ctx = platform_get_drvdata(pdev); struct exynos_drm_hdmi_context *ctx = platform_get_drvdata(pdev);
struct hdmi_context *hdata = (struct hdmi_context *)ctx->ctx; struct hdmi_context *hdata = ctx->ctx;
DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__); DRM_DEBUG_KMS("[%d] %s\n", __LINE__, __func__);
......
...@@ -37,7 +37,8 @@ ...@@ -37,7 +37,8 @@
#include "exynos_drm_drv.h" #include "exynos_drm_drv.h"
#include "exynos_drm_hdmi.h" #include "exynos_drm_hdmi.h"
#define HDMI_OVERLAY_NUMBER 3 #define MIXER_WIN_NR 3
#define MIXER_DEFAULT_WIN 0
#define get_mixer_context(dev) platform_get_drvdata(to_platform_device(dev)) #define get_mixer_context(dev) platform_get_drvdata(to_platform_device(dev))
...@@ -75,16 +76,12 @@ struct mixer_resources { ...@@ -75,16 +76,12 @@ struct mixer_resources {
}; };
struct mixer_context { struct mixer_context {
struct fb_videomode *default_timing;
unsigned int default_win;
unsigned int default_bpp;
unsigned int irq; unsigned int irq;
int pipe; int pipe;
bool interlace; bool interlace;
bool vp_enabled;
struct mixer_resources mixer_res; struct mixer_resources mixer_res;
struct hdmi_win_data win_data[HDMI_OVERLAY_NUMBER]; struct hdmi_win_data win_data[MIXER_WIN_NR];
}; };
static const u8 filter_y_horiz_tap8[] = { static const u8 filter_y_horiz_tap8[] = {
...@@ -643,9 +640,9 @@ static void mixer_win_mode_set(void *ctx, ...@@ -643,9 +640,9 @@ static void mixer_win_mode_set(void *ctx,
win = overlay->zpos; win = overlay->zpos;
if (win == DEFAULT_ZPOS) if (win == DEFAULT_ZPOS)
win = mixer_ctx->default_win; win = MIXER_DEFAULT_WIN;
if (win < 0 || win > HDMI_OVERLAY_NUMBER) { if (win < 0 || win > MIXER_WIN_NR) {
DRM_ERROR("overlay plane[%d] is wrong\n", win); DRM_ERROR("overlay plane[%d] is wrong\n", win);
return; return;
} }
...@@ -683,9 +680,9 @@ static void mixer_win_commit(void *ctx, int zpos) ...@@ -683,9 +680,9 @@ static void mixer_win_commit(void *ctx, int zpos)
DRM_DEBUG_KMS("[%d] %s, win: %d\n", __LINE__, __func__, win); DRM_DEBUG_KMS("[%d] %s, win: %d\n", __LINE__, __func__, win);
if (win == DEFAULT_ZPOS) if (win == DEFAULT_ZPOS)
win = mixer_ctx->default_win; win = MIXER_DEFAULT_WIN;
if (win < 0 || win > HDMI_OVERLAY_NUMBER) { if (win < 0 || win > MIXER_WIN_NR) {
DRM_ERROR("overlay plane[%d] is wrong\n", win); DRM_ERROR("overlay plane[%d] is wrong\n", win);
return; return;
} }
...@@ -706,9 +703,9 @@ static void mixer_win_disable(void *ctx, int zpos) ...@@ -706,9 +703,9 @@ static void mixer_win_disable(void *ctx, int zpos)
DRM_DEBUG_KMS("[%d] %s, win: %d\n", __LINE__, __func__, win); DRM_DEBUG_KMS("[%d] %s, win: %d\n", __LINE__, __func__, win);
if (win == DEFAULT_ZPOS) if (win == DEFAULT_ZPOS)
win = mixer_ctx->default_win; win = MIXER_DEFAULT_WIN;
if (win < 0 || win > HDMI_OVERLAY_NUMBER) { if (win < 0 || win > MIXER_WIN_NR) {
DRM_ERROR("overlay plane[%d] is wrong\n", win); DRM_ERROR("overlay plane[%d] is wrong\n", win);
return; return;
} }
...@@ -722,9 +719,12 @@ static void mixer_win_disable(void *ctx, int zpos) ...@@ -722,9 +719,12 @@ static void mixer_win_disable(void *ctx, int zpos)
spin_unlock_irqrestore(&res->reg_slock, flags); spin_unlock_irqrestore(&res->reg_slock, flags);
} }
static struct exynos_hdmi_overlay_ops overlay_ops = { static struct exynos_mixer_ops mixer_ops = {
/* manager */
.enable_vblank = mixer_enable_vblank, .enable_vblank = mixer_enable_vblank,
.disable_vblank = mixer_disable_vblank, .disable_vblank = mixer_disable_vblank,
/* overlay */
.win_mode_set = mixer_win_mode_set, .win_mode_set = mixer_win_mode_set,
.win_commit = mixer_win_commit, .win_commit = mixer_win_commit,
.win_disable = mixer_win_disable, .win_disable = mixer_win_disable,
...@@ -771,8 +771,7 @@ static void mixer_finish_pageflip(struct drm_device *drm_dev, int crtc) ...@@ -771,8 +771,7 @@ static void mixer_finish_pageflip(struct drm_device *drm_dev, int crtc)
static irqreturn_t mixer_irq_handler(int irq, void *arg) static irqreturn_t mixer_irq_handler(int irq, void *arg)
{ {
struct exynos_drm_hdmi_context *drm_hdmi_ctx = arg; struct exynos_drm_hdmi_context *drm_hdmi_ctx = arg;
struct mixer_context *ctx = struct mixer_context *ctx = drm_hdmi_ctx->ctx;
(struct mixer_context *)drm_hdmi_ctx->ctx;
struct mixer_resources *res = &ctx->mixer_res; struct mixer_resources *res = &ctx->mixer_res;
u32 val, val_base; u32 val, val_base;
...@@ -902,7 +901,7 @@ static int mixer_runtime_resume(struct device *dev) ...@@ -902,7 +901,7 @@ static int mixer_runtime_resume(struct device *dev)
DRM_DEBUG_KMS("resume - start\n"); DRM_DEBUG_KMS("resume - start\n");
mixer_resource_poweron((struct mixer_context *)ctx->ctx); mixer_resource_poweron(ctx->ctx);
return 0; return 0;
} }
...@@ -913,7 +912,7 @@ static int mixer_runtime_suspend(struct device *dev) ...@@ -913,7 +912,7 @@ static int mixer_runtime_suspend(struct device *dev)
DRM_DEBUG_KMS("suspend - start\n"); DRM_DEBUG_KMS("suspend - start\n");
mixer_resource_poweroff((struct mixer_context *)ctx->ctx); mixer_resource_poweroff(ctx->ctx);
return 0; return 0;
} }
...@@ -926,8 +925,7 @@ static const struct dev_pm_ops mixer_pm_ops = { ...@@ -926,8 +925,7 @@ static const struct dev_pm_ops mixer_pm_ops = {
static int __devinit mixer_resources_init(struct exynos_drm_hdmi_context *ctx, static int __devinit mixer_resources_init(struct exynos_drm_hdmi_context *ctx,
struct platform_device *pdev) struct platform_device *pdev)
{ {
struct mixer_context *mixer_ctx = struct mixer_context *mixer_ctx = ctx->ctx;
(struct mixer_context *)ctx->ctx;
struct device *dev = &pdev->dev; struct device *dev = &pdev->dev;
struct mixer_resources *mixer_res = &mixer_ctx->mixer_res; struct mixer_resources *mixer_res = &mixer_ctx->mixer_res;
struct resource *res; struct resource *res;
...@@ -1076,7 +1074,7 @@ static int __devinit mixer_probe(struct platform_device *pdev) ...@@ -1076,7 +1074,7 @@ static int __devinit mixer_probe(struct platform_device *pdev)
goto fail; goto fail;
/* register specific callback point to common hdmi. */ /* register specific callback point to common hdmi. */
exynos_drm_overlay_ops_register(&overlay_ops); exynos_mixer_ops_register(&mixer_ops);
mixer_resource_poweron(ctx); mixer_resource_poweron(ctx);
...@@ -1093,7 +1091,7 @@ static int mixer_remove(struct platform_device *pdev) ...@@ -1093,7 +1091,7 @@ static int mixer_remove(struct platform_device *pdev)
struct device *dev = &pdev->dev; struct device *dev = &pdev->dev;
struct exynos_drm_hdmi_context *drm_hdmi_ctx = struct exynos_drm_hdmi_context *drm_hdmi_ctx =
platform_get_drvdata(pdev); platform_get_drvdata(pdev);
struct mixer_context *ctx = (struct mixer_context *)drm_hdmi_ctx->ctx; struct mixer_context *ctx = drm_hdmi_ctx->ctx;
dev_info(dev, "remove successful\n"); dev_info(dev, "remove successful\n");
......
...@@ -85,7 +85,7 @@ struct drm_exynos_gem_mmap { ...@@ -85,7 +85,7 @@ struct drm_exynos_gem_mmap {
struct drm_exynos_vidi_connection { struct drm_exynos_vidi_connection {
unsigned int connection; unsigned int connection;
unsigned int extensions; unsigned int extensions;
uint64_t *edid; uint64_t edid;
}; };
struct drm_exynos_plane_set_zpos { struct drm_exynos_plane_set_zpos {
...@@ -96,7 +96,8 @@ struct drm_exynos_plane_set_zpos { ...@@ -96,7 +96,8 @@ struct drm_exynos_plane_set_zpos {
/* memory type definitions. */ /* memory type definitions. */
enum e_drm_exynos_gem_mem_type { enum e_drm_exynos_gem_mem_type {
/* Physically Non-Continuous memory. */ /* Physically Non-Continuous memory. */
EXYNOS_BO_NONCONTIG = 1 << 0 EXYNOS_BO_NONCONTIG = 1 << 0,
EXYNOS_BO_MASK = EXYNOS_BO_NONCONTIG
}; };
#define DRM_EXYNOS_GEM_CREATE 0x00 #define DRM_EXYNOS_GEM_CREATE 0x00
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment