From patchwork Wed Jun 11 18:27:04 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ajay Kumar X-Patchwork-Id: 4338941 Return-Path: X-Original-To: patchwork-dri-devel@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork2.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.19.201]) by patchwork2.web.kernel.org (Postfix) with ESMTP id 7F852BEECB for ; Thu, 12 Jun 2014 00:23:33 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id 7E5F02016C for ; Thu, 12 Jun 2014 00:23:32 +0000 (UTC) Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) by mail.kernel.org (Postfix) with ESMTP id 7A834201DE for ; Thu, 12 Jun 2014 00:23:31 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 96B476E420; Wed, 11 Jun 2014 17:23:26 -0700 (PDT) X-Original-To: dri-devel@lists.freedesktop.org Delivered-To: dri-devel@lists.freedesktop.org Received: from mailout4.samsung.com (mailout4.samsung.com [203.254.224.34]) by gabe.freedesktop.org (Postfix) with ESMTP id EB6FD6E896 for ; Wed, 11 Jun 2014 11:29:23 -0700 (PDT) Received: from epcpsbgr2.samsung.com (u142.gpu120.samsung.co.kr [203.254.230.142]) by mailout4.samsung.com (Oracle Communications Messaging Server 7u4-24.01 (7.0.4.24.0) 64bit (built Nov 17 2011)) with ESMTP id <0N7000L8NOOZLA90@mailout4.samsung.com> for dri-devel@lists.freedesktop.org; Thu, 12 Jun 2014 03:29:23 +0900 (KST) Received: from epcpsbgm2.samsung.com ( [172.20.52.125]) by epcpsbgr2.samsung.com (EPCPMTA) with SMTP id 02.2A.19452.300A8935; Thu, 12 Jun 2014 03:29:23 +0900 (KST) X-AuditID: cbfee68e-b7fb96d000004bfc-c3-5398a003f892 Received: from epmmp2 ( [203.254.227.17]) by epcpsbgm2.samsung.com (EPCPMTA) with SMTP id 06.0B.07139.200A8935; Thu, 12 Jun 2014 03:29:22 +0900 (KST) Received: from chromebld-server.sisodomain.com ([107.108.73.106]) by mmp2.samsung.com (Oracle Communications Messaging Server 7u4-24.01(7.0.4.24.0) 64bit (built Nov 17 2011)) with ESMTPA id <0N70000F9OO6ED50@mmp2.samsung.com>; Thu, 12 Jun 2014 03:29:22 +0900 (KST) From: Ajay Kumar To: dri-devel@lists.freedesktop.org, linux-samsung-soc@vger.kernel.org, devicetree@vger.kernel.org Subject: [PATCH V4 06/10] drm/bridge: Add a driver which binds drm_bridge with drm_panel Date: Wed, 11 Jun 2014 23:57:04 +0530 Message-id: <1402511228-18945-7-git-send-email-ajaykumar.rs@samsung.com> X-Mailer: git-send-email 1.7.9.5 In-reply-to: <1402511228-18945-1-git-send-email-ajaykumar.rs@samsung.com> References: <1402511228-18945-1-git-send-email-ajaykumar.rs@samsung.com> X-Brightmail-Tracker: H4sIAAAAAAAAA+NgFprJIsWRmVeSWpSXmKPExsWyRsSkVpd5wYxggykHuSwOvD/IYrHhzUJm i4UP7zJbzD9yjtXiytf3bBaT7k9gsfi+6wu7xYzz+5gs5h36zWix6vAGdovnC38wW8w9mGvx c9c8Fgdej9kNF1k89n5bwOKxc9Zddo8Fm0o97ncfZ/Lo27KK0ePzJrkA9igum5TUnMyy1CJ9 uwSujB2bQgo6XCrmPF/J3sB4z6KLkYNDQsBEYtJ/3i5GTiBTTOLCvfVsXYxcHEICSxklVnfd Y4dImEhcvPiUGSIxnVFiaf9KqKoJTBIrJ8xkA6liE9CW2Db9JgvIVBGBFInnf/lAapgFvjNK bD/8kBmkRlggSuLumi5GEJtFQFXiy4ILrCA2r4CHxL3t3SwQFylIzJlkA2JyCnhK7N4dCFIh BFTxd14DC8hICYFr7BKtzxrZIcYISHybfAiqVVZi0wFmiJslJQ6uuMEygVF4ASPDKkbR1ILk guKk9CIjveLE3OLSvHS95PzcTYzAaDn971nfDsabB6wPMSYDjZvILCWanA+MtrySeENjMyML UxNTYyNzSzPShJXEeRc9TAoSEkhPLEnNTk0tSC2KLyrNSS0+xMjEwSnVwLj0XcoOHmtR26m2 5bsMJLLnadcYrHK/8UDrjb5XC9vdLxLaWpYsLbHJuUFqV0Omb+TZIW4qfCpwQXTvF8bnH3aq iizotn/IaRzZuPnC4auLFksGn1e+9XJX3avD680WmFo39v2wqJDg7T2p5Wmx82nBK8aCv11X 5CU+vvYNXaXdnDfzSV77MiWW4oxEQy3mouJEAPYSKqOsAgAA X-Brightmail-Tracker: H4sIAAAAAAAAA+NgFvrOIsWRmVeSWpSXmKPExsVy+t9jQV2mBTOCDZ7etbE48P4gi8WGNwuZ LRY+vMtsMf/IOVaLK1/fs1lMuj+BxeL7ri/sFjPO72OymHfoN6PFqsMb2C2eL/zBbDH3YK7F z13zWBx4PWY3XGTx2PttAYvHzll32T0WbCr1uN99nMmjb8sqRo/Pm+QC2KMaGG0yUhNTUosU UvOS81My89JtlbyD453jTc0MDHUNLS3MlRTyEnNTbZVcfAJ03TJzgK5VUihLzCkFCgUkFhcr 6dthmhAa4qZrAdMYoesbEgTXY2SABhLWMGbs2BRS0OFSMef5SvYGxnsWXYycHBICJhIXLz5l hrDFJC7cW8/WxcjFISQwnVFiaf9KKGcCk8TKCTPZQKrYBLQltk2/ydLFyMEhIpAi8fwvH0gN s8B3Ronthx+CTRIWiJK4u6aLEcRmEVCV+LLgAiuIzSvgIXFvezdYr4SAgsScSTYgJqeAp8Tu 3YEgFUJAFX/nNbBMYORdwMiwilE0tSC5oDgpPddIrzgxt7g0L10vOT93EyM4Gp9J72Bc1WBx iFGAg1GJh5ehdkawEGtiWXFl7iFGCQ5mJRHeiGagEG9KYmVValF+fFFpTmrxIcZkoJsmMkuJ JucDE0VeSbyhsYm5qbGppYmFiZklacJK4rwHW60DhQTSE0tSs1NTC1KLYLYwcXBKNTD29Iuw rj2Q6ciwYU5gx5Twb0dvrtsa8ehhVQfDv2iJ1IchUWz/nt55yjV3RfZMi4Q0rdbC9qvRPQy/ ZuZVBO75/pyhaQPjDmnDk4fKVJauL1zDM/3S/Ef6masFnk7pzm5qXr8p2aPndOFOjnKD3p/S 3JynHjhO4THKOf7xi0fpjyvfeDes5GtVYinOSDTUYi4qTgQAKH5B1AoDAAA= DLP-Filter: Pass X-MTR: 20000000000000000@CPGS X-CFilter-Loop: Reflected X-Mailman-Approved-At: Wed, 11 Jun 2014 17:23:23 -0700 Cc: seanpaul@google.com, daniel.vetter@ffwll.ch, joshi@samsung.com, ajaynumb@gmail.com, marcheu@chromium.org, prashanth.g@samsung.com, Ajay Kumar X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" X-Spam-Status: No, score=-4.8 required=5.0 tests=BAYES_00, RCVD_IN_DNSWL_MED, RP_MATCHES_RCVD, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add a dummy bridge which binds all of the drm_bridge callbacks to corresponding drm_panel callbacks. In theory, this is just a glue layer for the last bridge and the panel attached to it. This driver also implements the required drm_connector ops for the encoder(on which the entire bridge chain is hanging off). Signed-off-by: Ajay Kumar --- drivers/gpu/drm/bridge/Kconfig | 7 ++ drivers/gpu/drm/bridge/Makefile | 1 + drivers/gpu/drm/bridge/panel_binder.c | 193 +++++++++++++++++++++++++++++++++ include/drm/bridge/panel_binder.h | 44 ++++++++ 4 files changed, 245 insertions(+) create mode 100644 drivers/gpu/drm/bridge/panel_binder.c create mode 100644 include/drm/bridge/panel_binder.h diff --git a/drivers/gpu/drm/bridge/Kconfig b/drivers/gpu/drm/bridge/Kconfig index 884923f..e3fb487 100644 --- a/drivers/gpu/drm/bridge/Kconfig +++ b/drivers/gpu/drm/bridge/Kconfig @@ -3,3 +3,10 @@ config DRM_PTN3460 depends on DRM select DRM_KMS_HELPER ---help--- + +config DRM_PANEL_BINDER + tristate "bridge panel binder" + depends on DRM + select DRM_KMS_HELPER + select DRM_PANEL + ---help--- diff --git a/drivers/gpu/drm/bridge/Makefile b/drivers/gpu/drm/bridge/Makefile index b4733e1..ba8b5b8 100644 --- a/drivers/gpu/drm/bridge/Makefile +++ b/drivers/gpu/drm/bridge/Makefile @@ -1,3 +1,4 @@ ccflags-y := -Iinclude/drm obj-$(CONFIG_DRM_PTN3460) += ptn3460.o +obj-$(CONFIG_DRM_PANEL_BINDER) += panel_binder.o diff --git a/drivers/gpu/drm/bridge/panel_binder.c b/drivers/gpu/drm/bridge/panel_binder.c new file mode 100644 index 0000000..93d976b --- /dev/null +++ b/drivers/gpu/drm/bridge/panel_binder.c @@ -0,0 +1,193 @@ +/* + * Copyright (C) 2014 Samsung Electronics Co., Ltd. + * + * This software is licensed under the terms of the GNU General Public + * License version 2, as published by the Free Software Foundation, and + * may be copied, distributed, and modified under those terms. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include +#include + +#include + +#include "drmP.h" +#include "drm_crtc.h" +#include "drm_crtc_helper.h" + +#include "bridge/panel_binder.h" + +struct panel_binder { + struct drm_connector connector; + struct i2c_client *client; + struct drm_encoder *encoder; + struct drm_bridge *bridge; + struct drm_panel *panel; +}; + +static void panel_binder_pre_enable(struct drm_bridge *bridge) +{ + struct panel_binder *panel_binder = bridge->driver_private; + + drm_panel_prepare(panel_binder->panel); +} + +static void panel_binder_enable(struct drm_bridge *bridge) +{ + struct panel_binder *panel_binder = bridge->driver_private; + + drm_panel_enable(panel_binder->panel); +} + +static void panel_binder_disable(struct drm_bridge *bridge) +{ + struct panel_binder *panel_binder = bridge->driver_private; + + drm_panel_disable(panel_binder->panel); +} + +static void panel_binder_post_disable(struct drm_bridge *bridge) +{ + struct panel_binder *panel_binder = bridge->driver_private; + + drm_panel_unprepare(panel_binder->panel); +} + +void panel_binder_destroy(struct drm_bridge *bridge) +{ + struct panel_binder *panel_binder = bridge->driver_private; + + drm_panel_detach(panel_binder->panel); + drm_bridge_cleanup(bridge); +} + +struct drm_bridge_funcs panel_binder_funcs = { + .pre_enable = panel_binder_pre_enable, + .enable = panel_binder_enable, + .disable = panel_binder_disable, + .post_disable = panel_binder_post_disable, + .destroy = panel_binder_destroy, +}; + +static int panel_binder_mode_valid(struct drm_connector *connector, + struct drm_display_mode *mode) +{ + return MODE_OK; +} + +static int panel_binder_get_modes(struct drm_connector *connector) +{ + struct panel_binder *panel_binder; + + panel_binder = container_of(connector, struct panel_binder, connector); + + return panel_binder->panel->funcs->get_modes(panel_binder->panel); +} + +static struct drm_encoder *panel_binder_best_encoder(struct drm_connector + *connector) +{ + struct panel_binder *panel_binder; + + panel_binder = container_of(connector, struct panel_binder, connector); + + return panel_binder->encoder; +} + +static const struct drm_connector_helper_funcs + panel_binder_connector_helper_funcs = { + .get_modes = panel_binder_get_modes, + .mode_valid = panel_binder_mode_valid, + .best_encoder = panel_binder_best_encoder, +}; + +static enum drm_connector_status panel_binder_detect(struct drm_connector + *connector, bool force) +{ + return connector_status_connected; +} + +static void panel_binder_connector_destroy(struct drm_connector *connector) +{ + drm_connector_cleanup(connector); +} + +static const struct drm_connector_funcs panel_binder_connector_funcs = { + .dpms = drm_helper_connector_dpms, + .fill_modes = drm_helper_probe_single_connector_modes, + .detect = panel_binder_detect, + .destroy = panel_binder_connector_destroy, +}; + +struct drm_bridge *panel_binder_init(struct drm_device *dev, + struct drm_encoder *encoder, + struct i2c_client *client, + struct device_node *node, + struct drm_panel *panel, + int connector_type, + uint8_t polled) +{ + int ret; + struct drm_bridge *bridge; + struct panel_binder *panel_binder; + + if (IS_ERR_OR_NULL(panel)) { + DRM_ERROR("invalid drm_panel pointer\n"); + return NULL; + } + + bridge = devm_kzalloc(dev->dev, sizeof(*bridge), GFP_KERNEL); + if (!bridge) { + DRM_ERROR("failed to allocate drm bridge\n"); + return NULL; + } + + panel_binder = devm_kzalloc(dev->dev, sizeof(*panel_binder), + GFP_KERNEL); + if (!panel_binder) { + DRM_ERROR("failed to allocate bridge panel_binder\n"); + return NULL; + } + + panel_binder->client = client; + panel_binder->encoder = encoder; + panel_binder->bridge = bridge; + panel_binder->panel = panel; + + ret = drm_bridge_init(dev, bridge, &panel_binder_funcs); + if (ret) { + DRM_ERROR("failed to initialize bridge with drm\n"); + goto err; + } + + bridge->driver_private = panel_binder; + + drm_panel_attach(panel_binder->panel, &panel_binder->connector); + + if (!encoder->bridge) + /* First entry in the bridge chain */ + encoder->bridge = bridge; + + panel_binder->connector.polled = polled; + ret = drm_connector_init(dev, &panel_binder->connector, + &panel_binder_connector_funcs, connector_type); + if (ret) { + DRM_ERROR("failed to initialize connector with drm\n"); + goto err; + } + drm_connector_helper_add(&panel_binder->connector, + &panel_binder_connector_helper_funcs); + drm_sysfs_connector_add(&panel_binder->connector); + drm_mode_connector_attach_encoder(&panel_binder->connector, encoder); + + return bridge; + +err: + return NULL; +} +EXPORT_SYMBOL(panel_binder_init); diff --git a/include/drm/bridge/panel_binder.h b/include/drm/bridge/panel_binder.h new file mode 100644 index 0000000..b5ebbc2 --- /dev/null +++ b/include/drm/bridge/panel_binder.h @@ -0,0 +1,44 @@ +/* + * Copyright (C) 2014 Samsung Electronics Co., Ltd. + * + * This software is licensed under the terms of the GNU General Public + * License version 2, as published by the Free Software Foundation, and + * may be copied, distributed, and modified under those terms. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef _DRM_BRIDGE_PANEL_H_ +#define _DRM_BRIDGE_PANEL_H_ + +struct drm_device; +struct drm_encoder; +struct i2c_client; +struct device_node; +struct drm_panel; + +#if defined(CONFIG_DRM_PANEL_BINDER) +struct drm_bridge *panel_binder_init(struct drm_device *dev, + struct drm_encoder *encoder, + struct i2c_client *client, + struct device_node *node, + struct drm_panel *panel, + int connector_type, + uint8_t polled); +#else +static inline struct drm_bridge *panel_binder_init(struct drm_device *dev, + struct drm_encoder *encoder, + struct i2c_client *client, + struct device_node *node, + struct drm_panel *panel, + int connector_type, + uint8_t polled) +{ + return 0; +} +#endif + +#endif